Skip to content

Commit

Permalink
feat: NFT details panel (#476)
Browse files Browse the repository at this point in the history
Co-authored-by: Michele F. <michele-franchi@users.noreply.github.com>
  • Loading branch information
janmichek and michele-franchi committed Sep 4, 2023
1 parent 6c9c236 commit c3fa902
Show file tree
Hide file tree
Showing 13 changed files with 301 additions and 24 deletions.
164 changes: 164 additions & 0 deletions src/components/NftDetailsPanel.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,164 @@
<template>
<app-panel class="nft-details-panel">
<template #heading>
DETAILS
</template>
<template #header>
<copy-chip
:label="nftDetails.contractId"
class="nft-details-panel__chip"/>
<copy-chip
:label="formatEllipseHash(nftDetails.contractId)"
:clipboard-text="nftDetails.contractId"
class="nft-details-panel__chip-ellipse"/>
</template>

<table>
<tbody>
<tr class="nft-details-panel__row">
<th class="nft-details-panel__table-header">
Collection Name
<hint-tooltip>
{{ nftsHints.collectionName }}
</hint-tooltip>
</th>
<td class="nft-details-panel__data">
{{ nftDetails.name }}
</td>
</tr>
<tr class="nft-details-panel__row">
<th class="nft-details-panel__table-header">
Owners
<hint-tooltip>
{{ nftsHints.owners }}
</hint-tooltip>
</th>
<td class="nft-details-panel__data">
{{ nftDetails.nftOwners }}
</td>
</tr>
<tr class="nft-details-panel__row">
<th class="nft-details-panel__table-header">
Amount
<hint-tooltip>
{{ nftsHints.amount }}
</hint-tooltip>
</th>
<td class="nft-details-panel__data">
{{ nftDetails.nftsAmount }}
</td>
</tr>
<tr
class="nft-details-panel__row">
<th class="nft-details-panel__table-header">
Extensions
<hint-tooltip>
{{ nftsHints.extensions }}
</hint-tooltip>
</th>
<td class="nft-details-panel__data">
<div
v-if="!!nftDetails.extensions.length"
class="nft-details-panel__extensions">
<app-chip
v-for="extension in nftDetails.extensions"
:key="extension"
size="sm">
{{ extension }}
</app-chip>
</div>
<template v-else>
N/A
</template>
</td>
</tr>
<tr
v-if="nftDetails.tokenLimit !== null"
class="nft-details-panel__row">
<th class="nft-details-panel__table-header">
Token limit
<hint-tooltip>
{{ nftsHints.tokenLimit }}
</hint-tooltip>
</th>
<td class="nft-details-panel__data">
{{ nftDetails.tokenLimit }}
</td>
</tr>
<tr
v-if="nftDetails.templateLimit !== null"
class="nft-details-panel__row">
<th class="nft-details-panel__table-header">
Template limit
<hint-tooltip>
{{ nftsHints.templateLimit }}
</hint-tooltip>
</th>
<td class="nft-details-panel__data">
{{ nftDetails.templateLimit }}
</td>
</tr>
</tbody>
</table>
</app-panel>
</template>

<script setup>
import AppPanel from '@/components/AppPanel'
import { nftsHints } from '@/utils/hints/nftHints'
defineProps({
nftDetails: {
type: Object,
required: true,
},
})
</script>

<style scoped>
.nft-details-panel {
&__table-header {
border-bottom: 1px solid var(--color-midnight-25);
}
&__data {
text-align: right;
}
&__row:last-of-type &__table-header {
border-bottom: 0;
}
&__link {
display: inline-flex;
align-items: center;
&:first-child {
margin-right: var(--space-3);
}
}
&__extensions {
display: flex;
flex-wrap: wrap;
gap: var(--space-1);
justify-content: flex-end;
}
&__chip,
&__hash {
display: none;
@media (--desktop) {
display: inline-flex;
}
}
&__chip-ellipse,
&__hash-ellipse {
@media (--desktop) {
display: none;
}
}
}
</style>
11 changes: 2 additions & 9 deletions src/components/TokenDetailsPanel.vue
Original file line number Diff line number Diff line change
Expand Up @@ -103,8 +103,7 @@
<app-chip
v-for="extension in tokenDetails.extensions"
:key="extension"
size="sm"
class="token-details-panel__chip">
size="sm">
{{ extension }}
</app-chip>
</div>
Expand Down Expand Up @@ -189,7 +188,6 @@ const marketCap = computed(() =>

<style scoped>
.token-details-panel {
&__table-header {
border-bottom: 1px solid var(--color-midnight-25);
}
Expand Down Expand Up @@ -223,7 +221,7 @@ const marketCap = computed(() =>
&__extensions {
display: flex;
flex-wrap: wrap;
row-gap: var(--space-1);
gap: var(--space-1);
justify-content: flex-end;
}
Expand All @@ -236,11 +234,6 @@ const marketCap = computed(() =>
}
}
&__chip {
margin-left: var(--space-1);
display: inline-flex;
}
&__hash {
display: none;
@media (--desktop) {
Expand Down
1 change: 0 additions & 1 deletion src/pages/contracts/[id].vue
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@

<template v-if="!isLoading">
<contract-details-panel
v-if="contractDetails"
class="contract-details__panel"
:contract-details="contractDetails"/>

Expand Down
1 change: 0 additions & 1 deletion src/pages/keyblocks/[id].vue
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@

<template v-if="!isLoading">
<keyblock-details-panel
v-if="keyblockDetails"
class="keyblock-details__keyblock-details-panel"
:keyblock-details="keyblockDetails"/>

Expand Down
1 change: 0 additions & 1 deletion src/pages/microblocks/[id].vue
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@
</page-header>
<template v-if="!isLoading">
<microblock-details-panel
v-if="microblockDetails"
class="microblock-details__microblock-details-panel"
:microblock-details="microblockDetails"/>
<app-tabs>
Expand Down
48 changes: 48 additions & 0 deletions src/pages/nfts/[id].vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
<template>
<Head>
<Title>{{ APP_TITLE_SHORT }} | NFT</Title>
</Head>

<page-header>
NFT
<template #tooltip>
{{ nftsHints.nft }}
</template>
</page-header>
<template v-if="!isLoading">
<nft-details-panel
v-if="nftDetails"
:nft-details="nftDetails"/>
</template>
<loader-panel v-else/>
</template>

<script setup>
import { storeToRefs } from 'pinia'
import { nftsHints } from '@/utils/hints/nftHints'
import PageHeader from '@/components/PageHeader'
import { useNftDetailsStore } from '@/stores/nftDetails'
import NftDetailsPanel from '@/components/NftDetailsPanel'
const nftDetailsStore = useNftDetailsStore()
const { nftDetails } = storeToRefs(nftDetailsStore)
const { fetchNftDetails } = nftDetailsStore
const route = useRoute()
const { isLoading } = useLoading()
try {
await fetchNftDetails(route.params.id)
} catch (error) {
if ([400, 404].includes(error.response?.status)) {
throw showError({
data: {
entityId: route.params.id,
entityName: 'NFT',
},
statusMessage: 'EntityDetailsNotFound',
})
}
throw error
}
</script>
1 change: 0 additions & 1 deletion src/pages/oracles/[id].vue
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@

<template v-if="!isLoading">
<oracle-details-panel
v-if="oracleDetails"
class="oracle-details__panel"
:oracle-details="oracleDetails"/>

Expand Down
3 changes: 1 addition & 2 deletions src/pages/state-channels/[id].vue
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
class="state-channel-details__state-channel-details-panel"
:state-channel-details="stateChannelDetails"/>

<app-tabs v-if="stateChannelDetails">
<app-tabs>
<app-tab title="Transactions">
<state-channel-transactions-panel/>
</app-tab>
Expand All @@ -46,7 +46,6 @@ const { fetchStateChannelDetails } = stateChannelDetailsStore
const route = useRoute()
const { isLoading } = useLoading()
const { error } = await useAsyncData(() => fetchStateChannelDetails(route.params.id))
if (error.value) {
Expand Down
1 change: 0 additions & 1 deletion src/pages/tokens/[id].vue
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@

<template v-if="!isLoading">
<token-details-panel
v-if="tokenDetails"
class="token-details__panel"
:token-details="tokenDetails"/>

Expand Down
27 changes: 27 additions & 0 deletions src/stores/nftDetails.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import { defineStore } from 'pinia'
import { useRuntimeConfig } from 'nuxt/app'
import useAxios from '@/composables/useAxios'
import { adaptNftDetails } from '@/utils/adapters'

export const useNftDetailsStore = defineStore('nftDetails', () => {
const { MIDDLEWARE_URL } = useRuntimeConfig().public
const axios = useAxios()

const rawNftDetails = ref(null)

const nftDetails = computed(() => {
return rawNftDetails.value
? adaptNftDetails(rawNftDetails.value)
: null
})

async function fetchNftDetails(contractId) {
const { data } = await axios.get(`${MIDDLEWARE_URL}/v2/aex141/${contractId}`)
rawNftDetails.value = data
}

return {
nftDetails,
fetchNftDetails,
}
})
27 changes: 19 additions & 8 deletions src/utils/adapters.js
Original file line number Diff line number Diff line change
@@ -1,14 +1,17 @@
import { DateTime } from 'luxon'
import { useRuntimeConfig } from 'nuxt/app'
import { BigNumber } from 'bignumber.js'
import { formatAettosToAe, formatBlockDiffAsDatetime, formatDecodeBase64, formatNameStatus } from '@/utils/format'
import { MINUTES_PER_BLOCK, SPECIAL_POINTERS_PRESET_KEYS } from '@/utils/constants'
import {
formatAettosToAe,
formatBlockDiffAsDatetime,
formatDecodeBase64,
formatIsAuction,
formatNameStatus,
formatTemplateLimit,
formatTokenLimit,
} from '@/utils/format'

function isAuction(name) {
const auctionLength = 13
const suffixLength = 6
return name.length - suffixLength < auctionLength
}
import { MINUTES_PER_BLOCK, SPECIAL_POINTERS_PRESET_KEYS } from '@/utils/constants'

export function adaptKeyblock(keyblock, keyblockDeltaStats = null) {
if (keyblock) {
Expand Down Expand Up @@ -106,7 +109,7 @@ export function adaptNames(names, blockHeight) {
name.info.activeFrom,
blockHeight,
),
isAuction: isAuction(name.name),
isAuction: formatIsAuction(name.name),
price: formatAettosToAe(name.info.claims.at(-1)?.tx.nameFee),
}
})
Expand Down Expand Up @@ -568,3 +571,11 @@ export function adaptNamesResults(names) {
prev: names.prev,
}
}

export function adaptNftDetails(nft) {
return {
...nft,
tokenLimit: formatTokenLimit(nft.extensions, nft.limits.tokenLimit),
templateLimit: formatTemplateLimit(nft.extensions, nft.limits.templateLimit),
}
}

0 comments on commit c3fa902

Please sign in to comment.