mirror of
https://github.com/stronk-dev/RandomChad.git
synced 2025-07-05 10:35:08 +02:00
Working outfit switch, started on styled components
This commit is contained in:
parent
c0d5e193ad
commit
605e977bad
File diff suppressed because it is too large
Load Diff
@ -32,13 +32,10 @@ exports.generateNewOutfit = async function( req, res ) {
|
|||||||
// Validate message
|
// Validate message
|
||||||
const messageObject = JSON.parse( message )
|
const messageObject = JSON.parse( message )
|
||||||
const { signer, rocketeerId, chainId } = messageObject
|
const { signer, rocketeerId, chainId } = messageObject
|
||||||
if( signer.toLowerCase() !== confirmedSignatory.toLowerCase() || !rocketeerId || chainId !== chain || !network ) throw new Error( `Invalid message` )
|
const network = chainId == '0x1' ? 'mainnet' : 'rinkeby'
|
||||||
|
if( signer.toLowerCase() !== confirmedSignatory.toLowerCase() || !rocketeerId || !network ) throw new Error( `Invalid generateNewOutfit message with ${signer}, ${confirmedSignatory}, ${rocketeerId}, ${network}` )
|
||||||
if( rocketeerId != id ) throw new Error( `Invalid Rocketeer in message` )
|
if( rocketeerId != id ) throw new Error( `Invalid Rocketeer in message` )
|
||||||
|
|
||||||
// Set chain based on envronnment
|
|
||||||
const chain = process.env.NODE_ENV == 'development' ? '0x4' : '0x1'
|
|
||||||
const network = chain == '0x1' ? 'mainnet' : 'rinkeby'
|
|
||||||
|
|
||||||
// Generate new rocketeer svg
|
// Generate new rocketeer svg
|
||||||
const mediaLink = await generateNewOutfitFromId( id, network )
|
const mediaLink = await generateNewOutfitFromId( id, network )
|
||||||
|
|
||||||
@ -88,7 +85,8 @@ exports.setPrimaryOutfit = async function( req, res ) {
|
|||||||
// Validate message
|
// Validate message
|
||||||
const messageObject = JSON.parse( message )
|
const messageObject = JSON.parse( message )
|
||||||
let { signer, outfitId, chainId } = messageObject
|
let { signer, outfitId, chainId } = messageObject
|
||||||
if( signer.toLowerCase() !== confirmedSignatory.toLowerCase() || !outfitId || chainId !== chain || !network ) throw new Error( `Invalid message` )
|
const network = chainId == '0x1' ? 'mainnet' : 'rinkeby'
|
||||||
|
if( signer.toLowerCase() !== confirmedSignatory.toLowerCase() || outfitId == undefined || !network ) throw new Error( `Invalid setPrimaryOutfit message with ${ signer }, ${confirmedSignatory}, ${outfitId}, ${chainId}, ${network}` )
|
||||||
|
|
||||||
// Validate id format
|
// Validate id format
|
||||||
outfitId = Math.floor( Math.abs( outfitId ) )
|
outfitId = Math.floor( Math.abs( outfitId ) )
|
||||||
@ -97,10 +95,6 @@ exports.setPrimaryOutfit = async function( req, res ) {
|
|||||||
// Set ID to string so firestore can handle it
|
// Set ID to string so firestore can handle it
|
||||||
outfitId = `${ outfitId }`
|
outfitId = `${ outfitId }`
|
||||||
|
|
||||||
// Set chain based on envronnment
|
|
||||||
const chain = process.env.NODE_ENV == 'development' ? '0x4' : '0x1'
|
|
||||||
const network = chain == '0x1' ? 'mainnet' : 'rinkeby'
|
|
||||||
|
|
||||||
// Retreive old Rocketeer data
|
// Retreive old Rocketeer data
|
||||||
const rocketeer = await db.collection( `${ network }Rocketeers` ).doc( id ).get().then( dataFromSnap )
|
const rocketeer = await db.collection( `${ network }Rocketeers` ).doc( id ).get().then( dataFromSnap )
|
||||||
|
|
||||||
@ -116,6 +110,8 @@ exports.setPrimaryOutfit = async function( req, res ) {
|
|||||||
image: `https://storage.googleapis.com/rocketeer-nft.appspot.com/${ network }Rocketeers/${ imagePath }`
|
image: `https://storage.googleapis.com/rocketeer-nft.appspot.com/${ network }Rocketeers/${ imagePath }`
|
||||||
}, { merge: true } )
|
}, { merge: true } )
|
||||||
|
|
||||||
|
return res.json( { success: true } )
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
} catch( e ) {
|
} catch( e ) {
|
||||||
|
@ -29,7 +29,7 @@ exports.generateNewOutfitFromId = async function( id, network='mainnet' ) {
|
|||||||
|
|
||||||
// Check whether this Rocketeer is allowed to change
|
// Check whether this Rocketeer is allowed to change
|
||||||
const timeUntilAllowedToChange = newOutfitAllowedInterval - ( Date.now() - last_outfit_change )
|
const timeUntilAllowedToChange = newOutfitAllowedInterval - ( Date.now() - last_outfit_change )
|
||||||
if( timeUntilAllowedToChange > 0 ) throw new Error( `You changed your outfit too recently, a change is avalable in ${ Math.floor( timeUntilAllowedToChange / ( 1000 * 60 * 60 ) ) } hours` )
|
if( timeUntilAllowedToChange > 0 ) throw new Error( `You changed your outfit too recently, a change is avalable in ${ Math.floor( timeUntilAllowedToChange / ( 1000 * 60 * 60 ) ) } hours (${ new Date( Date.now() + timeUntilAllowedToChange ).toString() })` )
|
||||||
|
|
||||||
// Grab attributes that will not change
|
// Grab attributes that will not change
|
||||||
const staticAttributes = rocketeer.attributes.filter( ( { trait_type } ) => ![ 'last outfit change', 'available outfits' ].includes( trait_type ) )
|
const staticAttributes = rocketeer.attributes.filter( ( { trait_type } ) => ![ 'last outfit change', 'available outfits' ].includes( trait_type ) )
|
||||||
|
116
minter/package-lock.json
generated
116
minter/package-lock.json
generated
@ -1203,6 +1203,29 @@
|
|||||||
"resolved": "https://registry.npmjs.org/@csstools/normalize.css/-/normalize.css-10.1.0.tgz",
|
"resolved": "https://registry.npmjs.org/@csstools/normalize.css/-/normalize.css-10.1.0.tgz",
|
||||||
"integrity": "sha512-ij4wRiunFfaJxjB0BdrYHIH8FxBJpOwNPhhAcunlmPdXudL1WQV1qoP9un6JsEBAgQH+7UXyyjh0g7jTxXK6tg=="
|
"integrity": "sha512-ij4wRiunFfaJxjB0BdrYHIH8FxBJpOwNPhhAcunlmPdXudL1WQV1qoP9un6JsEBAgQH+7UXyyjh0g7jTxXK6tg=="
|
||||||
},
|
},
|
||||||
|
"@emotion/is-prop-valid": {
|
||||||
|
"version": "0.8.8",
|
||||||
|
"resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-0.8.8.tgz",
|
||||||
|
"integrity": "sha512-u5WtneEAr5IDG2Wv65yhunPSMLIpuKsbuOktRojfrEiEvRyC85LgPMZI63cr7NUqT8ZIGdSVg8ZKGxIug4lXcA==",
|
||||||
|
"requires": {
|
||||||
|
"@emotion/memoize": "0.7.4"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@emotion/memoize": {
|
||||||
|
"version": "0.7.4",
|
||||||
|
"resolved": "https://registry.npmjs.org/@emotion/memoize/-/memoize-0.7.4.tgz",
|
||||||
|
"integrity": "sha512-Ja/Vfqe3HpuzRsG1oBtWTHk2PGZ7GR+2Vz5iYGelAw8dx32K0y7PjVuxK6z1nMpZOqAFsRUPCkK1YjJ56qJlgw=="
|
||||||
|
},
|
||||||
|
"@emotion/stylis": {
|
||||||
|
"version": "0.8.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@emotion/stylis/-/stylis-0.8.5.tgz",
|
||||||
|
"integrity": "sha512-h6KtPihKFn3T9fuIrwvXXUOwlx3rfUvfZIcP5a6rh8Y7zjE3O06hT5Ss4S/YI1AYhuZ1kjaE/5EaOOI2NqSylQ=="
|
||||||
|
},
|
||||||
|
"@emotion/unitless": {
|
||||||
|
"version": "0.7.5",
|
||||||
|
"resolved": "https://registry.npmjs.org/@emotion/unitless/-/unitless-0.7.5.tgz",
|
||||||
|
"integrity": "sha512-OWORNpfjMsSSUBVrRBVGECkhWcULOAJz9ZW8uK9qgxD+87M7jHRcvh/A96XXNhXTLmKcoYSQtBEX7lHMO7YRwg=="
|
||||||
|
},
|
||||||
"@eslint/eslintrc": {
|
"@eslint/eslintrc": {
|
||||||
"version": "0.4.3",
|
"version": "0.4.3",
|
||||||
"resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-0.4.3.tgz",
|
"resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-0.4.3.tgz",
|
||||||
@ -3886,6 +3909,49 @@
|
|||||||
"@babel/helper-define-polyfill-provider": "^0.2.2"
|
"@babel/helper-define-polyfill-provider": "^0.2.2"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"babel-plugin-styled-components": {
|
||||||
|
"version": "2.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/babel-plugin-styled-components/-/babel-plugin-styled-components-2.0.1.tgz",
|
||||||
|
"integrity": "sha512-U3wmORxerYBiqcRCo6thItIosEIga3F+ph0jJPkiOZJjyhpZyUZFQV9XvrZ2CbBIihJ3rDBC/itQ+Wx3VHMauw==",
|
||||||
|
"requires": {
|
||||||
|
"@babel/helper-annotate-as-pure": "^7.16.0",
|
||||||
|
"@babel/helper-module-imports": "^7.16.0",
|
||||||
|
"babel-plugin-syntax-jsx": "^6.18.0",
|
||||||
|
"lodash": "^4.17.11"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"@babel/helper-annotate-as-pure": {
|
||||||
|
"version": "7.16.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@babel/helper-annotate-as-pure/-/helper-annotate-as-pure-7.16.0.tgz",
|
||||||
|
"integrity": "sha512-ItmYF9vR4zA8cByDocY05o0LGUkp1zhbTQOH1NFyl5xXEqlTJQCEJjieriw+aFpxo16swMxUnUiKS7a/r4vtHg==",
|
||||||
|
"requires": {
|
||||||
|
"@babel/types": "^7.16.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@babel/helper-module-imports": {
|
||||||
|
"version": "7.16.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@babel/helper-module-imports/-/helper-module-imports-7.16.0.tgz",
|
||||||
|
"integrity": "sha512-kkH7sWzKPq0xt3H1n+ghb4xEMP8k0U7XV3kkB+ZGy69kDk2ySFW1qPi06sjKzFY3t1j6XbJSqr4mF9L7CYVyhg==",
|
||||||
|
"requires": {
|
||||||
|
"@babel/types": "^7.16.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@babel/types": {
|
||||||
|
"version": "7.16.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/@babel/types/-/types-7.16.0.tgz",
|
||||||
|
"integrity": "sha512-PJgg/k3SdLsGb3hhisFvtLOw5ts113klrpLuIPtCJIU+BB24fqq6lf8RWqKJEjzqXR9AEH1rIb5XTqwBHB+kQg==",
|
||||||
|
"requires": {
|
||||||
|
"@babel/helper-validator-identifier": "^7.15.7",
|
||||||
|
"to-fast-properties": "^2.0.0"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"babel-plugin-syntax-jsx": {
|
||||||
|
"version": "6.18.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/babel-plugin-syntax-jsx/-/babel-plugin-syntax-jsx-6.18.0.tgz",
|
||||||
|
"integrity": "sha1-CvMqmm4Tyno/1QaeYtew9Y0NiUY="
|
||||||
|
},
|
||||||
"babel-plugin-syntax-object-rest-spread": {
|
"babel-plugin-syntax-object-rest-spread": {
|
||||||
"version": "6.13.0",
|
"version": "6.13.0",
|
||||||
"resolved": "https://registry.npmjs.org/babel-plugin-syntax-object-rest-spread/-/babel-plugin-syntax-object-rest-spread-6.13.0.tgz",
|
"resolved": "https://registry.npmjs.org/babel-plugin-syntax-object-rest-spread/-/babel-plugin-syntax-object-rest-spread-6.13.0.tgz",
|
||||||
@ -4662,6 +4728,11 @@
|
|||||||
"resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.2.0.tgz",
|
"resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.2.0.tgz",
|
||||||
"integrity": "sha512-c7wVvbw3f37nuobQNtgsgG9POC9qMbNuMQmTCqZv23b6MIz0fcYpBiOlv9gEN/hdLdnZTDQhg6e9Dq5M1vKvfg=="
|
"integrity": "sha512-c7wVvbw3f37nuobQNtgsgG9POC9qMbNuMQmTCqZv23b6MIz0fcYpBiOlv9gEN/hdLdnZTDQhg6e9Dq5M1vKvfg=="
|
||||||
},
|
},
|
||||||
|
"camelize": {
|
||||||
|
"version": "1.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/camelize/-/camelize-1.0.0.tgz",
|
||||||
|
"integrity": "sha1-FkpUg+Yw+kMh5a8HAg5TGDGyYJs="
|
||||||
|
},
|
||||||
"caniuse-api": {
|
"caniuse-api": {
|
||||||
"version": "3.0.0",
|
"version": "3.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/caniuse-api/-/caniuse-api-3.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/caniuse-api/-/caniuse-api-3.0.0.tgz",
|
||||||
@ -5270,6 +5341,11 @@
|
|||||||
"postcss": "^7.0.5"
|
"postcss": "^7.0.5"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"css-color-keywords": {
|
||||||
|
"version": "1.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/css-color-keywords/-/css-color-keywords-1.0.0.tgz",
|
||||||
|
"integrity": "sha1-/qJhbcZ2spYmhrOvjb2+GAskTgU="
|
||||||
|
},
|
||||||
"css-color-names": {
|
"css-color-names": {
|
||||||
"version": "0.0.4",
|
"version": "0.0.4",
|
||||||
"resolved": "https://registry.npmjs.org/css-color-names/-/css-color-names-0.0.4.tgz",
|
"resolved": "https://registry.npmjs.org/css-color-names/-/css-color-names-0.0.4.tgz",
|
||||||
@ -5353,6 +5429,16 @@
|
|||||||
"resolved": "https://registry.npmjs.org/css-select-base-adapter/-/css-select-base-adapter-0.1.1.tgz",
|
"resolved": "https://registry.npmjs.org/css-select-base-adapter/-/css-select-base-adapter-0.1.1.tgz",
|
||||||
"integrity": "sha512-jQVeeRG70QI08vSTwf1jHxp74JoZsr2XSgETae8/xC8ovSnL2WF87GTLO86Sbwdt2lK4Umg4HnnwMO4YF3Ce7w=="
|
"integrity": "sha512-jQVeeRG70QI08vSTwf1jHxp74JoZsr2XSgETae8/xC8ovSnL2WF87GTLO86Sbwdt2lK4Umg4HnnwMO4YF3Ce7w=="
|
||||||
},
|
},
|
||||||
|
"css-to-react-native": {
|
||||||
|
"version": "3.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/css-to-react-native/-/css-to-react-native-3.0.0.tgz",
|
||||||
|
"integrity": "sha512-Ro1yETZA813eoyUp2GDBhG2j+YggidUmzO1/v9eYBKR2EHVEniE2MI/NqpTQ954BMpTPZFsGNPm46qFB9dpaPQ==",
|
||||||
|
"requires": {
|
||||||
|
"camelize": "^1.0.0",
|
||||||
|
"css-color-keywords": "^1.0.0",
|
||||||
|
"postcss-value-parser": "^4.0.2"
|
||||||
|
}
|
||||||
|
},
|
||||||
"css-tree": {
|
"css-tree": {
|
||||||
"version": "1.0.0-alpha.37",
|
"version": "1.0.0-alpha.37",
|
||||||
"resolved": "https://registry.npmjs.org/css-tree/-/css-tree-1.0.0-alpha.37.tgz",
|
"resolved": "https://registry.npmjs.org/css-tree/-/css-tree-1.0.0-alpha.37.tgz",
|
||||||
@ -8104,6 +8190,14 @@
|
|||||||
"minimalistic-crypto-utils": "^1.0.1"
|
"minimalistic-crypto-utils": "^1.0.1"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"hoist-non-react-statics": {
|
||||||
|
"version": "3.3.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/hoist-non-react-statics/-/hoist-non-react-statics-3.3.2.tgz",
|
||||||
|
"integrity": "sha512-/gGivxi8JPKWNm/W0jSmzcMPpfpPLc3dY/6GxhX2hQ9iGj3aDfklV4ET7NjKpSinLpJ5vafa9iiGIEZg10SfBw==",
|
||||||
|
"requires": {
|
||||||
|
"react-is": "^16.7.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"hoopy": {
|
"hoopy": {
|
||||||
"version": "0.1.4",
|
"version": "0.1.4",
|
||||||
"resolved": "https://registry.npmjs.org/hoopy/-/hoopy-0.1.4.tgz",
|
"resolved": "https://registry.npmjs.org/hoopy/-/hoopy-0.1.4.tgz",
|
||||||
@ -14620,6 +14714,11 @@
|
|||||||
"safe-buffer": "^5.0.1"
|
"safe-buffer": "^5.0.1"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"shallowequal": {
|
||||||
|
"version": "1.1.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/shallowequal/-/shallowequal-1.1.0.tgz",
|
||||||
|
"integrity": "sha512-y0m1JoUZSlPAjXVtPPW70aZWfIL/dSP7AFkRnniLCrK/8MDKog3TySTBmckD+RObVxH0v4Tox67+F14PdED2oQ=="
|
||||||
|
},
|
||||||
"shebang-command": {
|
"shebang-command": {
|
||||||
"version": "1.2.0",
|
"version": "1.2.0",
|
||||||
"resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz",
|
"resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz",
|
||||||
@ -15278,6 +15377,23 @@
|
|||||||
"schema-utils": "^2.7.0"
|
"schema-utils": "^2.7.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"styled-components": {
|
||||||
|
"version": "5.3.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/styled-components/-/styled-components-5.3.3.tgz",
|
||||||
|
"integrity": "sha512-++4iHwBM7ZN+x6DtPPWkCI4vdtwumQ+inA/DdAsqYd4SVgUKJie5vXyzotA00ttcFdQkCng7zc6grwlfIfw+lw==",
|
||||||
|
"requires": {
|
||||||
|
"@babel/helper-module-imports": "^7.0.0",
|
||||||
|
"@babel/traverse": "^7.4.5",
|
||||||
|
"@emotion/is-prop-valid": "^0.8.8",
|
||||||
|
"@emotion/stylis": "^0.8.4",
|
||||||
|
"@emotion/unitless": "^0.7.4",
|
||||||
|
"babel-plugin-styled-components": ">= 1.12.0",
|
||||||
|
"css-to-react-native": "^3.0.0",
|
||||||
|
"hoist-non-react-statics": "^3.0.0",
|
||||||
|
"shallowequal": "^1.1.0",
|
||||||
|
"supports-color": "^5.5.0"
|
||||||
|
}
|
||||||
|
},
|
||||||
"stylehacks": {
|
"stylehacks": {
|
||||||
"version": "4.0.3",
|
"version": "4.0.3",
|
||||||
"resolved": "https://registry.npmjs.org/stylehacks/-/stylehacks-4.0.3.tgz",
|
"resolved": "https://registry.npmjs.org/stylehacks/-/stylehacks-4.0.3.tgz",
|
||||||
|
@ -11,6 +11,7 @@
|
|||||||
"react-dom": "^17.0.2",
|
"react-dom": "^17.0.2",
|
||||||
"react-router-dom": "^6.0.0",
|
"react-router-dom": "^6.0.0",
|
||||||
"react-scripts": "4.0.3",
|
"react-scripts": "4.0.3",
|
||||||
|
"styled-components": "^5.3.3",
|
||||||
"use-interval": "^1.4.0",
|
"use-interval": "^1.4.0",
|
||||||
"web-vitals": "^1.1.2",
|
"web-vitals": "^1.1.2",
|
||||||
"web3": "^1.6.0"
|
"web3": "^1.6.0"
|
||||||
|
@ -48,7 +48,7 @@ p.row {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*Login button*/
|
/*Login button*/
|
||||||
a.button {
|
.button {
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: row;
|
flex-direction: row;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
|
@ -2,6 +2,8 @@ import { Container } from './components/generic'
|
|||||||
import { useState, useEffect } from 'react'
|
import { useState, useEffect } from 'react'
|
||||||
import { HashRouter} from 'react-router-dom'
|
import { HashRouter} from 'react-router-dom'
|
||||||
import Router from './components/router'
|
import Router from './components/router'
|
||||||
|
import Theme from './components/atoms/Theme'
|
||||||
|
|
||||||
|
|
||||||
function App() {
|
function App() {
|
||||||
|
|
||||||
@ -22,14 +24,19 @@ function App() {
|
|||||||
// ///////////////////////////////
|
// ///////////////////////////////
|
||||||
// Rendering
|
// Rendering
|
||||||
// ///////////////////////////////
|
// ///////////////////////////////
|
||||||
if( error || loading ) return <Container>
|
if( error || loading ) return <Theme>
|
||||||
<p>{ error || loading }</p>
|
<Container>
|
||||||
</Container>
|
<p>{ error || loading }</p>
|
||||||
return <HashRouter>
|
</Container>
|
||||||
|
</Theme>
|
||||||
|
|
||||||
<Router />
|
return <Theme>
|
||||||
|
<HashRouter>
|
||||||
|
|
||||||
</HashRouter>
|
<Router />
|
||||||
|
|
||||||
|
</HashRouter>
|
||||||
|
</Theme>
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -38,7 +38,7 @@ export default function Verifier() {
|
|||||||
|
|
||||||
const signature = await sign( JSON.stringify( {
|
const signature = await sign( JSON.stringify( {
|
||||||
signer: address.toLowerCase(),
|
signer: address.toLowerCase(),
|
||||||
outfitId: outfitId,
|
outfitId,
|
||||||
chainId,
|
chainId,
|
||||||
} ), address )
|
} ), address )
|
||||||
|
|
||||||
@ -46,6 +46,48 @@ export default function Verifier() {
|
|||||||
|
|
||||||
setLoading( 'Updating profile' )
|
setLoading( 'Updating profile' )
|
||||||
|
|
||||||
|
const { error, success } = await callApi( `/rocketeer/${ rocketeerId }/outfits`, {
|
||||||
|
method: 'PUT',
|
||||||
|
headers: { 'Content-Type': 'application/json' },
|
||||||
|
body: JSON.stringify( signature )
|
||||||
|
} )
|
||||||
|
|
||||||
|
if( error ) throw new Error( error )
|
||||||
|
|
||||||
|
alert( `Success! Outfit changed, please click "refresh metadata" on Opensea to update it there.\nForwarding you to the tools homepage.` )
|
||||||
|
navigate( `/` )
|
||||||
|
|
||||||
|
} catch( e ) {
|
||||||
|
|
||||||
|
log( e )
|
||||||
|
alert( e.message )
|
||||||
|
|
||||||
|
} finally {
|
||||||
|
|
||||||
|
setLoading( false )
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
async function generateNewOutfit( ) {
|
||||||
|
|
||||||
|
try {
|
||||||
|
|
||||||
|
log( `Generating new outfit for #${ rocketeerId }` )
|
||||||
|
setLoading( `Generating new outfit for #${ rocketeerId }` )
|
||||||
|
alert( 'You will be prompted to sign a message, this is NOT a transaction' )
|
||||||
|
|
||||||
|
const signature = await sign( JSON.stringify( {
|
||||||
|
signer: address.toLowerCase(),
|
||||||
|
rocketeerId,
|
||||||
|
chainId,
|
||||||
|
} ), address )
|
||||||
|
|
||||||
|
log( 'Making request with ', signature )
|
||||||
|
|
||||||
|
setLoading( 'Generating new outfit, this can take a minute' )
|
||||||
|
|
||||||
const { error, success } = await callApi( `/rocketeer/${ rocketeerId }/outfits`, {
|
const { error, success } = await callApi( `/rocketeer/${ rocketeerId }/outfits`, {
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
headers: { 'Content-Type': 'application/json' },
|
headers: { 'Content-Type': 'application/json' },
|
||||||
@ -54,8 +96,9 @@ export default function Verifier() {
|
|||||||
|
|
||||||
if( error ) throw new Error( error )
|
if( error ) throw new Error( error )
|
||||||
|
|
||||||
alert( `Success! Outfit changed, please click "refresh metadata" on Opensea to update it there.\nForwarding you to the tools homepage.` )
|
alert( `Success! Outfit generated.` )
|
||||||
navigate( `/` )
|
window?.location.reload()
|
||||||
|
|
||||||
|
|
||||||
} catch( e ) {
|
} catch( e ) {
|
||||||
|
|
||||||
@ -84,8 +127,16 @@ export default function Verifier() {
|
|||||||
|
|
||||||
// If the selected rocketeer is available, compute it's available outfits to an easy to access property
|
// If the selected rocketeer is available, compute it's available outfits to an easy to access property
|
||||||
if( selected ) {
|
if( selected ) {
|
||||||
const { value: outfits } = selected.attributes.find( ( { trait_type } ) => trait_type === 'available outfits' ) || 0
|
|
||||||
|
const newOutfitAllowedInterval = 1000 * 60 * 60 * 24 * 30
|
||||||
|
const { value: outfits } = selected.attributes.find( ( { trait_type } ) => trait_type === 'available outfits' ) || { value: 0 }
|
||||||
|
const { value: last_outfit_change } = selected.attributes.find( ( { trait_type } ) => trait_type === 'last outfit change' ) || { value: 0 }
|
||||||
|
const timeUntilAllowedToChange = newOutfitAllowedInterval - ( Date.now() - last_outfit_change )
|
||||||
|
|
||||||
selected.outfits = outfits
|
selected.outfits = outfits
|
||||||
|
selected.last_outfit_change = last_outfit_change
|
||||||
|
selected.new_outfit_available = timeUntilAllowedToChange < 0
|
||||||
|
selected.when_new_outfit = new Date( Date.now() + timeUntilAllowedToChange )
|
||||||
}
|
}
|
||||||
|
|
||||||
log( "Selecting rocketeer ", selected )
|
log( "Selecting rocketeer ", selected )
|
||||||
@ -93,7 +144,7 @@ export default function Verifier() {
|
|||||||
// Set the selected rocketeer to state
|
// Set the selected rocketeer to state
|
||||||
if( selected ) setRocketeer( selected )
|
if( selected ) setRocketeer( selected )
|
||||||
|
|
||||||
}, [ rocketeerId, rocketeers ] )
|
}, [ rocketeerId, rocketeers.length ] )
|
||||||
|
|
||||||
// ///////////////////////////////
|
// ///////////////////////////////
|
||||||
// Rendering
|
// Rendering
|
||||||
@ -124,16 +175,18 @@ export default function Verifier() {
|
|||||||
// Changing room
|
// Changing room
|
||||||
if( rocketeer ) return <Container id="avatar" className={ rocketeer.outfits > 0 ? 'wide' : '' }>
|
if( rocketeer ) return <Container id="avatar" className={ rocketeer.outfits > 0 ? 'wide' : '' }>
|
||||||
|
|
||||||
<h1>Changing room for Rocketeer { rocketeerId }</h1>
|
<h1>{ rocketeer.name }</h1>
|
||||||
|
|
||||||
<img key={ rocketeer.id } className='rocketeer' src={ rocketeer.image } alt={ `Rocketeer number ${ rocketeer.id }` } />
|
<img key={ rocketeer.id } className='rocketeer' src={ rocketeer.image } alt={ `Rocketeer number ${ rocketeer.id }` } />
|
||||||
|
{ rocketeer.new_outfit_available ? <button onClick={ generateNewOutfit } className="button">Generate new outfit</button> : <p>New outfit available on { rocketeer.when_new_outfit.toString() }</p> }
|
||||||
<p>This Rocketeer has { 1 + rocketeer.outfits } outfits. { rocketeer.outfits > 0 && 'Click any outfit to select it as primary.' }</p>
|
<p>This Rocketeer has { 1 + rocketeer.outfits } outfits. { rocketeer.outfits > 0 && 'Click any outfit to select it as primary.' }</p>
|
||||||
|
|
||||||
<div className="row">
|
<div className="row">
|
||||||
|
|
||||||
<img key={ rocketeer.id + 0 } onClick={ f => setPrimaryOutfit( 0 ) } className='rocketeer' src={ rocketeer.image } alt={ `Rocketeer number ${ rocketeer.id }` } />
|
<img key={ rocketeer.id + 0 } onClick={ f => setPrimaryOutfit( 0 ) } className='rocketeer' src={ rocketeer.image.replace( /-\d\.jpg/, '.jpg' ) } alt={ `Rocketeer number ${ rocketeer.id }` } />
|
||||||
|
|
||||||
{ Array.from( Array( rocketeer.outfits ) ).map( ( val, i ) => {
|
{ Array.from( Array( rocketeer.outfits ) ).map( ( val, i ) => {
|
||||||
return <img onClick={ f => setPrimaryOutfit( i ) } key={ rocketeer.id + i } className='rocketeer' src={ rocketeer.image.replace( '.jpg', `-${ i + 1 }.jpg` ) } alt={ `Rocketeer number ${ rocketeer.id }` } />
|
return <img onClick={ f => setPrimaryOutfit( i + 1 ) } key={ rocketeer.id + i } className='rocketeer' src={ rocketeer.image.replace( /-\d\.jpg/, `-${ i + 1 }.jpg` ) } alt={ `Rocketeer number ${ rocketeer.id }` } />
|
||||||
} ) }
|
} ) }
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
@ -3,7 +3,7 @@ import Metamask from './metamask'
|
|||||||
import Verifier from './verifier'
|
import Verifier from './verifier'
|
||||||
import Avatar from './avatar'
|
import Avatar from './avatar'
|
||||||
import Portfolio from './portfolio'
|
import Portfolio from './portfolio'
|
||||||
import Outfits from './outfits'
|
import Outfits from './organisms/Outfits'
|
||||||
import { useState, useEffect } from 'react'
|
import { useState, useEffect } from 'react'
|
||||||
import { log } from '../modules/helpers'
|
import { log } from '../modules/helpers'
|
||||||
import { useAddress } from '../modules/web3'
|
import { useAddress } from '../modules/web3'
|
||||||
|
@ -14,7 +14,7 @@ export async function callApi( path, options={} ) {
|
|||||||
const chain = ( isLocal || querySaysTestnet ) ? 'testnet' : 'mainnet'
|
const chain = ( isLocal || querySaysTestnet ) ? 'testnet' : 'mainnet'
|
||||||
const callPath = api[ chain ] + path
|
const callPath = api[ chain ] + path
|
||||||
|
|
||||||
log( 'Calling ', callPath )
|
log( 'Calling ', callPath, ' with ', options )
|
||||||
return fetch( `${ api[ chain ] }${ path }`, options ).then( res => res.json() )
|
return fetch( `${ api[ chain ] }${ path }`, options ).then( res => res.json() )
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -224,34 +224,38 @@ export function useTokenIds() {
|
|||||||
const [ tokens, setTokens ] = useState( [] )
|
const [ tokens, setTokens ] = useState( [] )
|
||||||
|
|
||||||
// Grab tokens from contract
|
// Grab tokens from contract
|
||||||
useEffect( f => {
|
useEffect( ( ) => {
|
||||||
|
|
||||||
// Do nothing if there is no data yet
|
// Do nothing if there is no data yet
|
||||||
if( !contract || !balance || !address ) return
|
if( !contract || !balance || !address ) return
|
||||||
|
|
||||||
// Load initial supply value
|
let cancelled = false;
|
||||||
( async ( ) => {
|
|
||||||
|
( async () => {
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|
||||||
const ids = await Promise.all( Array.from( { length: balance } ).map( async ( val, index ) => {
|
const ids = await Promise.all( Array.from( { length: balance } ).map( async ( val, index ) => {
|
||||||
const id = await contract.tokenOfOwnerByIndex( address, index )
|
const id = await contract.tokenOfOwnerByIndex( address, index )
|
||||||
return id.toString()
|
return id.toString()
|
||||||
} ) )
|
} ) )
|
||||||
log( 'Tokens detected: ', ids )
|
|
||||||
setTokens( ids )
|
|
||||||
|
|
||||||
} catch( e ) {
|
log( 'Tokens detected: ', ids )
|
||||||
|
if( !cancelled ) setTokens( ids )
|
||||||
|
|
||||||
log( 'Error getting tokens of address: ', e )
|
} catch( e ) {
|
||||||
|
|
||||||
}
|
log( 'Error getting tokens of address: ', e )
|
||||||
|
|
||||||
} )( )
|
}
|
||||||
|
|
||||||
|
} )( )
|
||||||
|
|
||||||
|
return () => cancelled = true
|
||||||
|
|
||||||
}, [ contract, address, balance ] )
|
}, [ contract, address, balance ] )
|
||||||
|
|
||||||
|
|
||||||
return tokens
|
return tokens
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user