Smart Contract
PagesX
A.fdfe39186c5e3b90.PagesX
1import NonFungibleToken from 0x1d7e57aa55817448
2import MetadataViews from 0x1d7e57aa55817448
3import ViewResolver from 0x1d7e57aa55817448
4
5access(all) contract PagesX: NonFungibleToken {
6
7 access(all) let CollectionStoragePath: StoragePath
8 access(all) let CollectionPublicPath: PublicPath
9 access(all) let CollectionPrivatePath: PrivatePath
10 access(all) let AdminStoragePath: StoragePath
11
12 access(all) var totalSupply: UInt64
13
14 access(all) struct PagesXMetadata {
15 access(all) let id: UInt64
16 access(all) let name: String
17 access(all) let description: String
18 access(all) let image: String
19 access(all) let traits: [{String: String}]
20
21 init(id: UInt64 ,name: String, description: String, image: String, traits: [{String: String}]) {
22 self.id = id
23 self.name = name
24 self.description = description
25 self.image = image
26 self.traits = traits
27 }
28 }
29
30 access(all) resource NFT: NonFungibleToken.NFT {
31 access(all) let id: UInt64
32 access(all) let name: String
33 access(all) let description: String
34 access(all) var image: String
35 access(all) let traits: [{String: String}]
36
37 init(id: UInt64, name: String, description: String, image: String, traits: [{String: String}]) {
38 self.id = id
39 self.name = name
40 self.description = description
41 self.image = image
42 self.traits = traits
43 }
44
45 access(all) fun revealThumbnail() {
46 let urlBase = self.image.slice(from: 0, upTo: 47)
47 let newImage = urlBase.concat(self.id.toString()).concat(".png")
48 self.image = newImage
49 }
50
51
52 access(all) fun createEmptyCollection(): @{NonFungibleToken.Collection} {
53 return <- PagesX.createEmptyCollection(nftType: Type<@NFT>())
54 }
55
56 access(all) view fun getViews(): [Type] {
57 return [
58 Type<MetadataViews.NFTView>(),
59 Type<MetadataViews.Display>(),
60 Type<MetadataViews.ExternalURL>(),
61 Type<MetadataViews.NFTCollectionData>(),
62 Type<MetadataViews.NFTCollectionDisplay>(),
63 Type<PagesX.PagesXMetadata>(),
64 Type<MetadataViews.Royalties>(),
65 Type<MetadataViews.Traits>()
66 ]
67 }
68
69 access(all) fun resolveView(_ view: Type): AnyStruct? {
70 switch view {
71 case Type<MetadataViews.Display>():
72 return MetadataViews.Display(
73 name: self.name,
74 description: self.description,
75 thumbnail: MetadataViews.IPFSFile(
76 cid: self.image,
77 path: nil
78 )
79 )
80 case Type<MetadataViews.ExternalURL>():
81 return MetadataViews.ExternalURL("https://titpalace.xyz")
82 case Type<MetadataViews.NFTCollectionData>():
83 return PagesX.resolveContractView(resourceType: Type<@NFT>(), viewType: Type<MetadataViews.NFTCollectionData>())
84 case Type<MetadataViews.NFTCollectionDisplay>():
85 return PagesX.resolveContractView(resourceType: Type<@NFT>(), viewType: Type<MetadataViews.NFTCollectionDisplay>())
86 case Type<PagesX.PagesXMetadata>():
87 return PagesX.PagesXMetadata(
88 id: self.id,
89 name: self.name,
90 description: self.description,
91 image: self.image,
92 traits: self.traits
93 )
94 case Type<MetadataViews.Royalties>():
95 return MetadataViews.Royalties([])
96 case Type<MetadataViews.Traits>():
97 let traits: [MetadataViews.Trait] = []
98 for traitDict in self.traits {
99 for key in traitDict.keys {
100 let value = traitDict[key]!
101 traits.append(MetadataViews.Trait(
102 name: key,
103 value: value,
104 displayType: nil,
105 rarity: nil
106 ))
107 }
108 }
109 return MetadataViews.Traits(traits)
110 }
111
112
113
114 return nil
115 }
116 }
117
118
119
120 access(all) resource interface CollectionPublic {
121 access(all) fun deposit(token: @{NonFungibleToken.NFT})
122 access(all) view fun getIDs(): [UInt64]
123 access(all) fun borrowPagesX(id: UInt64): &PagesX.NFT? {
124 // If the result isn't nil, the id of the returned reference
125 // should be the same as the argument to the function
126 post {
127 (result == nil) || (result?.id == id):
128 "Cannot borrow Car Club reference: The ID of the returned reference is incorrect"
129 }
130 }
131 }
132
133 access(all) resource Collection: CollectionPublic, NonFungibleToken.Collection {
134 access(all) var ownedNFTs: @{UInt64: {NonFungibleToken.NFT}}
135
136 access(NonFungibleToken.Withdraw) fun withdraw(withdrawID: UInt64): @{NonFungibleToken.NFT} {
137 let token <- self.ownedNFTs.remove(key: withdrawID) ?? panic("missing NFT")
138 return <-token
139 }
140
141 access(all) fun deposit(token: @{NonFungibleToken.NFT}) {
142 let token <- token as! @PagesX.NFT
143 let id: UInt64 = token.id
144 let oldToken <- self.ownedNFTs[id] <- token
145 destroy oldToken
146 }
147
148 access(all) view fun getSupportedNFTTypes(): {Type: Bool} {
149 let supportedTypes: {Type: Bool} = {}
150 supportedTypes[Type<@NFT>()] = true
151 return supportedTypes
152 }
153
154 access(all) view fun isSupportedNFTType(type: Type): Bool {
155 return type == Type<@NFT>()
156 }
157
158 access(all) view fun getIDs(): [UInt64] {
159 return self.ownedNFTs.keys
160 }
161
162 access(all) view fun borrowViewResolver(id: UInt64): &{ViewResolver.Resolver}? {
163 if let nft = &self.ownedNFTs[id] as &{NonFungibleToken.NFT}? {
164 return nft as &{ViewResolver.Resolver}
165 }
166 return nil
167 }
168
169 access(all) view fun borrowNFT(_ id: UInt64): &{NonFungibleToken.NFT}? {
170 return (&self.ownedNFTs[id] as &{NonFungibleToken.NFT}?)
171 }
172
173 access(all) fun borrowPagesX(id: UInt64): &PagesX.NFT? {
174 if let nft = &self.ownedNFTs[id] as &{NonFungibleToken.NFT}? {
175 return nft as! &NFT
176 }
177 return nil
178 }
179
180 access(all) fun createEmptyCollection(): @{NonFungibleToken.Collection} {
181 return <- PagesX.createEmptyCollection(nftType: Type<@NFT>())
182 }
183
184 init () {
185 self.ownedNFTs <- {}
186 }
187 }
188
189 access(all) fun createEmptyCollection(nftType: Type): @{NonFungibleToken.Collection} {
190 return <- create Collection()
191 }
192
193 access(all) resource Admin {
194 access(all) fun mintNFT(
195 recipient: &{NonFungibleToken.CollectionPublic},
196 name: String,
197 description: String,
198 image: String,
199 traits: [{String: String}]
200 ) {
201 PagesX.totalSupply = PagesX.totalSupply + 1
202
203 recipient.deposit(token: <- create PagesX.NFT(
204 id: PagesX.totalSupply,
205 name: name,
206 description: description,
207 image:image,
208 traits: traits
209 ))
210 }
211 }
212
213 access(all) view fun getContractViews(resourceType: Type?): [Type] {
214 return [
215 Type<MetadataViews.NFTCollectionData>(),
216 Type<MetadataViews.NFTCollectionDisplay>()
217 ]
218 }
219
220 access(all) fun resolveContractView(resourceType: Type?, viewType: Type): AnyStruct? {
221 switch viewType {
222 case Type<MetadataViews.NFTCollectionData>():
223 let collectionData = MetadataViews.NFTCollectionData(
224 storagePath: self.CollectionStoragePath,
225 publicPath: self.CollectionPublicPath,
226 publicCollection: Type<&Collection>(),
227 publicLinkedType: Type<&Collection>(),
228 createEmptyCollectionFunction: (fun(): @{NonFungibleToken.Collection} {
229 return <- PagesX.createEmptyCollection(nftType: Type<@NFT>())
230 })
231 )
232 return collectionData
233 case Type<MetadataViews.NFTCollectionDisplay>():
234 let squareMedia = MetadataViews.Media(
235 file: MetadataViews.HTTPFile(
236 url: "https://imgur.com/a/uWFXdzc"
237 ),
238 mediaType: "image"
239 )
240 let bannerMedia = MetadataViews.Media(
241 file: MetadataViews.HTTPFile(
242 url: "https://imgur.com/a/uWFXdzc"
243 ),
244 mediaType: "image"
245 )
246 return MetadataViews.NFTCollectionDisplay(
247 name: "Tit Palace",
248 description: "Tit Palace Collectibles",
249 externalURL: MetadataViews.ExternalURL("https://titpalace.xyz/"),
250 squareImage: squareMedia,
251 bannerImage: bannerMedia,
252 socials: {
253 "twitter": MetadataViews.ExternalURL("https://x.com/vertico_defi"),
254 "instagram": MetadataViews.ExternalURL("https://www.instagram.com/titpalace/")
255 }
256 )
257 }
258 return nil
259 }
260
261 init() {
262 self.CollectionStoragePath = /storage/pagesXCollection
263 self.CollectionPublicPath = /public/pagesXCollection
264 self.CollectionPrivatePath = /private/pagesXCollection
265 self.AdminStoragePath = /storage/pagesXMinter
266
267 self.totalSupply = 0
268
269 let minter <- create Admin()
270 self.account.storage.save(<-minter, to: self.AdminStoragePath)
271
272 let collection <- create Collection()
273 self.account.storage.save(<-collection, to: PagesX.CollectionStoragePath)
274 let collectionCap = self.account.capabilities.storage.issue<&Collection>(self.CollectionStoragePath)
275 self.account.capabilities.publish(collectionCap, at: self.CollectionPublicPath)
276 }
277}