1use core::marker::PhantomData;23use sp_std::collections::btree_map::BTreeMap;4use frame_support::{dispatch::DispatchResultWithPostInfo, fail, weights::Weight};5use nft_data_structs::TokenId;6use pallet_common::{7 CommonCollectionOperations, CommonWeightInfo, account::CrossAccountId, with_weight,8};9use sp_runtime::DispatchError;10use sp_std::vec::Vec;1112use crate::{13 AccountBalance, Allowance, Balance, Config, CreateItemData, Error, Owned, Pallet,14 RefungibleHandle, SelfWeightOf, TokenData, weights::WeightInfo, TokensMinted,15};1617macro_rules! max_weight_of {18 ($($method:ident ($($args:tt)*)),*) => {19 020 $(21 .max(<SelfWeightOf<T>>::$method($($args)*))22 )*23 };24}2526pub struct CommonWeights<T: Config>(PhantomData<T>);27impl<T: Config> CommonWeightInfo for CommonWeights<T> {28 fn create_item() -> Weight {29 <SelfWeightOf<T>>::create_item()30 }3132 fn create_multiple_items(amount: u32) -> Weight {33 <SelfWeightOf<T>>::create_multiple_items(amount)34 }3536 fn burn_item() -> Weight {37 max_weight_of!(burn_item_partial(), burn_item_fully())38 }3940 fn transfer() -> Weight {41 max_weight_of!(42 transfer_normal(),43 transfer_creating(),44 transfer_removing(),45 transfer_creating_removing()46 )47 }4849 fn approve() -> Weight {50 <SelfWeightOf<T>>::approve()51 }5253 fn transfer_from() -> Weight {54 max_weight_of!(55 transfer_from_normal(),56 transfer_from_creating(),57 transfer_from_removing(),58 transfer_from_creating_removing()59 )60 }6162 fn set_variable_metadata(bytes: u32) -> Weight {63 <SelfWeightOf<T>>::set_variable_metadata(bytes)64 }65}6667fn map_create_data<T: Config>(68 data: nft_data_structs::CreateItemData,69 to: &T::CrossAccountId,70) -> Result<CreateItemData<T>, DispatchError> {71 match data {72 nft_data_structs::CreateItemData::ReFungible(data) => Ok(CreateItemData {73 const_data: data.const_data,74 variable_data: data.variable_data,75 users: {76 let mut out = BTreeMap::new();77 out.insert(to.clone(), data.pieces);78 out79 },80 }),81 _ => fail!(<Error<T>>::NotRefungibleDataUsedToMintFungibleCollectionToken),82 }83}8485impl<T: Config> CommonCollectionOperations<T> for RefungibleHandle<T> {86 fn create_item(87 &self,88 sender: T::CrossAccountId,89 to: T::CrossAccountId,90 data: nft_data_structs::CreateItemData,91 ) -> DispatchResultWithPostInfo {92 with_weight(93 <Pallet<T>>::create_item(self, &sender, map_create_data(data, &to)?),94 <CommonWeights<T>>::create_item(),95 )96 }9798 fn create_multiple_items(99 &self,100 sender: T::CrossAccountId,101 to: T::CrossAccountId,102 data: Vec<nft_data_structs::CreateItemData>,103 ) -> DispatchResultWithPostInfo {104 let data = data105 .into_iter()106 .map(|d| map_create_data::<T>(d, &to))107 .collect::<Result<Vec<_>, DispatchError>>()?;108109 let amount = data.len();110 with_weight(111 <Pallet<T>>::create_multiple_items(self, &sender, data),112 <CommonWeights<T>>::create_multiple_items(amount as u32),113 )114 }115116 fn burn_item(117 &self,118 sender: T::CrossAccountId,119 token: TokenId,120 amount: u128,121 ) -> DispatchResultWithPostInfo {122 with_weight(123 <Pallet<T>>::burn(self, &sender, token, amount),124 <CommonWeights<T>>::burn_item(),125 )126 }127128 fn transfer(129 &self,130 from: T::CrossAccountId,131 to: T::CrossAccountId,132 token: TokenId,133 amount: u128,134 ) -> DispatchResultWithPostInfo {135 with_weight(136 <Pallet<T>>::transfer(&self, &from, &to, token, amount),137 <CommonWeights<T>>::transfer(),138 )139 }140141 fn approve(142 &self,143 sender: T::CrossAccountId,144 spender: T::CrossAccountId,145 token: TokenId,146 amount: u128,147 ) -> DispatchResultWithPostInfo {148 with_weight(149 <Pallet<T>>::set_allowance(&self, &sender, &spender, token, amount),150 <CommonWeights<T>>::approve(),151 )152 }153154 fn transfer_from(155 &self,156 sender: T::CrossAccountId,157 from: T::CrossAccountId,158 to: T::CrossAccountId,159 token: TokenId,160 amount: u128,161 ) -> DispatchResultWithPostInfo {162 with_weight(163 <Pallet<T>>::transfer_from(&self, &sender, &from, &to, token, amount),164 <CommonWeights<T>>::approve(),165 )166 }167168 fn set_variable_metadata(169 &self,170 sender: T::CrossAccountId,171 token: TokenId,172 data: Vec<u8>,173 ) -> DispatchResultWithPostInfo {174 let len = data.len();175 with_weight(176 <Pallet<T>>::set_variable_metadata(&self, &sender, token, data),177 <CommonWeights<T>>::set_variable_metadata(len as u32),178 )179 }180181 fn account_tokens(&self, account: T::CrossAccountId) -> Vec<TokenId> {182 <Owned<T>>::iter_prefix((self.id, account.as_sub()))183 .map(|(id, _)| id)184 .collect()185 }186187 fn token_exists(&self, token: TokenId) -> bool {188 <Pallet<T>>::token_exists(self, token)189 }190191 fn last_token_id(&self) -> TokenId {192 TokenId(<TokensMinted<T>>::get(self.id))193 }194195 fn token_owner(&self, _token: TokenId) -> T::CrossAccountId {196 T::CrossAccountId::default()197 }198 fn const_metadata(&self, token: TokenId) -> Vec<u8> {199 <TokenData<T>>::get((self.id, token)).const_data200 }201 fn variable_metadata(&self, token: TokenId) -> Vec<u8> {202 <TokenData<T>>::get((self.id, token)).variable_data203 }204205 fn collection_tokens(&self) -> u32 {206 <Pallet<T>>::total_supply(self)207 }208209 fn account_balance(&self, account: T::CrossAccountId) -> u32 {210 <AccountBalance<T>>::get((self.id, account.as_sub()))211 }212213 fn balance(&self, account: T::CrossAccountId, token: TokenId) -> u128 {214 <Balance<T>>::get((self.id, token, account.as_sub()))215 }216217 fn allowance(218 &self,219 sender: T::CrossAccountId,220 spender: T::CrossAccountId,221 token: TokenId,222 ) -> u128 {223 <Allowance<T>>::get((self.id, token, sender.as_sub(), spender))224 }225}