Smart Contract
HouseBadge
A.e217638793f1e461.HouseBadge
1import NonFungibleToken from 0x1d7e57aa55817448
2import MetadataViews from 0x1d7e57aa55817448
3import ViewResolver from 0x1d7e57aa55817448
4
5access(all) contract HouseBadge: NonFungibleToken {
6
7 access(all) var totalSupply: UInt64
8
9 /***********************************************/
10 /******************** PATHS ********************/
11 /***********************************************/
12 access(all) var collectionPublicPath: PublicPath
13 access(all) var collectionStoragePath: StoragePath
14 // access(all) var minterPublicPath: PublicPath
15 access(all) var minterStoragePath: StoragePath
16
17 /************************************************/
18 /******************** EVENTS ********************/
19 /************************************************/
20 access(all) event Mint(id: UInt64, creator: Address, metadata: {String:String}, totalSupply: UInt64)
21
22 access(all) resource NFT: NonFungibleToken.NFT {
23 access(all) let id: UInt64
24 access(all) let creator: Address
25 access(self) let metadata: {String:String}
26
27 init(id: UInt64, creator: Address, metadata: {String:String}) {
28 self.id = id
29 self.creator = creator
30 self.metadata = metadata
31 }
32
33 access(all) view fun getViews(): [Type] {
34 return [Type<MetadataViews.Display>()]
35 }
36
37 access(all) fun resolveView(_ view: Type): AnyStruct? {
38 switch view {
39 case Type<MetadataViews.Display>():
40 return MetadataViews.Display(
41 name: self.metadata["name"] ?? "",
42 description: self.metadata["description"] ?? "",
43 thumbnail: MetadataViews.HTTPFile(url: self.metadata["metaURI"] ?? ""),
44 )
45 }
46 return nil
47 }
48
49 access(all) fun getMetadata(): {String:String} {
50 return self.metadata
51 }
52
53 access(contract) fun rename(newName: String) {
54 self.metadata["name"] = newName
55 }
56
57 access(all) fun createEmptyCollection(): @{NonFungibleToken.Collection} {
58 return <- HouseBadge.createEmptyCollection(nftType: Type<@HouseBadge.NFT>())
59 }
60 }
61
62 access(all) resource Admin {
63 access(all) fun rename(nft: &NFT, newName: String) {
64 nft.rename(newName: newName)
65 }
66 }
67
68 access(all) resource interface CollectionPublic {
69 access(all) view fun borrow(id: UInt64): &NFT?
70 }
71
72 access(all) resource interface Renameable {}
73
74 access(all) resource Collection: NonFungibleToken.Collection, CollectionPublic, Renameable {
75 access(all) var ownedNFTs: @{UInt64: {NonFungibleToken.NFT}}
76
77 init() {
78 self.ownedNFTs <- {}
79 }
80
81 access(all) view fun getSupportedNFTTypes(): {Type: Bool} {
82 let supportedTypes: {Type: Bool} = {}
83 supportedTypes[Type<@HouseBadge.NFT>()] = true
84 return supportedTypes
85 }
86
87 access(all) view fun isSupportedNFTType(type: Type): Bool {
88 return type == Type<@HouseBadge.NFT>()
89 }
90
91 access(NonFungibleToken.Withdraw) fun withdraw(withdrawID: UInt64): @{NonFungibleToken.NFT} {
92 let token <- self.ownedNFTs.remove(key: withdrawID) ?? panic("Missing NFT")
93 return <- token
94 }
95
96 access(all) fun deposit(token: @{NonFungibleToken.NFT}) {
97 let token <- token as! @HouseBadge.NFT
98 let id: UInt64 = token.id
99 let dummy <- self.ownedNFTs[id] <- token
100 destroy dummy
101 }
102
103 access(all) view fun getIDs(): [UInt64] {
104 return self.ownedNFTs.keys
105 }
106
107 access(all) view fun getLength(): Int {
108 return self.ownedNFTs.length
109 }
110
111 access(all) view fun borrowNFT(_ id: UInt64): &{NonFungibleToken.NFT}? {
112 return &self.ownedNFTs[id] as &{NonFungibleToken.NFT}?
113 }
114
115 access(all) view fun borrowViewResolver(id: UInt64): &{ViewResolver.Resolver}? {
116 if let nft = &self.ownedNFTs[id] as &{NonFungibleToken.NFT}? {
117 return nft as &{ViewResolver.Resolver}
118 }
119 return nil
120 }
121
122 access(all) view fun borrow(id: UInt64): &NFT? {
123 let ref = (&self.ownedNFTs[id] as &{NonFungibleToken.NFT}?)!
124 return ref as! &NFT
125 }
126
127 access(all) fun getMetadata(id: UInt64): {String:String} {
128 let ref = (&self.ownedNFTs[id] as &{NonFungibleToken.NFT}?)!
129 return (ref as! &HouseBadge.NFT).getMetadata()
130 }
131
132 access(all) fun createEmptyCollection(): @{NonFungibleToken.Collection} {
133 return <- HouseBadge.createEmptyCollection(nftType: Type<@HouseBadge.NFT>())
134 }
135 }
136
137 access(all) fun createEmptyCollection(nftType: Type): @{NonFungibleToken.Collection} {
138 return <- create Collection()
139 }
140
141 access(all) view fun getContractViews(resourceType: Type?): [Type] {
142 return [
143 Type<MetadataViews.NFTCollectionData>()
144 ]
145 }
146
147 access(all) view fun resolveContractView(resourceType: Type?, viewType: Type): AnyStruct? {
148 switch viewType {
149 case Type<MetadataViews.NFTCollectionData>():
150 let collectionData = MetadataViews.NFTCollectionData(
151 storagePath: self.collectionStoragePath,
152 publicPath: self.collectionPublicPath,
153 publicCollection: Type<&HouseBadge.Collection>(),
154 publicLinkedType: Type<&HouseBadge.Collection>(),
155 createEmptyCollectionFunction: (fun(): @{NonFungibleToken.Collection} {
156 return <- HouseBadge.createEmptyCollection(nftType: Type<@HouseBadge.NFT>())
157 })
158 )
159 return collectionData
160 }
161 return nil
162 }
163
164 access(all) resource Minter {
165 access(all) fun mintTo(creator: Capability<&{NonFungibleToken.Receiver}>, metadata: {String:String}): UInt64 {
166 let id = HouseBadge.totalSupply
167 let meta = {
168 "name": metadata["name"] ?? "",
169 "description": metadata["description"] ?? "",
170 "metaURI": "https://nft.tobiratory.com/housebadge/metadata/".concat(id.toString())
171 };
172 let token <- create NFT(
173 id: id,
174 creator: creator.address,
175 metadata: meta
176 )
177 HouseBadge.totalSupply = HouseBadge.totalSupply + 1
178 emit Mint(id: token.id, creator: creator.address, metadata: meta, totalSupply: HouseBadge.totalSupply)
179 creator.borrow()!.deposit(token: <- token)
180 return id
181 }
182 }
183
184 access(all) fun createAdmin() {
185 if self.account.storage.borrow<&Admin>(from: /storage/HouseBadgeAdmin) == nil {
186 self.account.storage.save(<- create Admin(), to: /storage/HouseBadgeAdmin)
187 }
188 }
189
190 // access(all) fun minter(): Capability<&Minter> {
191 // return self.account.getCapability<&Minter>(self.minterPublicPath)
192 // }
193
194 init() {
195 self.totalSupply = 0
196 self.collectionPublicPath = /public/HouseBadgeCollection
197
198 self.collectionStoragePath = /storage/HouseBadgeCollection
199 // self.minterPublicPath = /public/HouseBadgeMinter
200 self.minterStoragePath = /storage/HouseBadgeMinter
201
202 if self.account.storage.borrow<&Minter>(from: self.minterStoragePath) == nil {
203 self.account.storage.save(<- create Minter(), to: self.minterStoragePath)
204 }
205
206 if self.account.storage.borrow<&Admin>(from: /storage/HouseBadgeAdmin) == nil {
207 let admin <- create Admin()
208 self.account.storage.save(<- admin, to: /storage/HouseBadgeAdmin)
209 }
210
211 if self.account.storage.borrow<&HouseBadge.Collection>(from: HouseBadge.collectionStoragePath) == nil {
212 self.account.storage.save(<- create Collection(), to: self.collectionStoragePath)
213 let cap: Capability = self.account.capabilities.storage.issue<&HouseBadge.Collection>(self.collectionStoragePath)
214 self.account.capabilities.publish(cap, at: self.collectionPublicPath)
215 }
216 }
217}