panhui 3 jaren geleden
bovenliggende
commit
59cd06961d

BIN
src/assets/png-bg-shangping2.png


BIN
src/assets/png-fuhe.png


BIN
src/assets/png-renzheng.png


BIN
src/assets/png-shibai.png


BIN
src/assets/png-zhengshu-diwen.png


+ 311 - 0
src/components/star/post.vue

@@ -0,0 +1,311 @@
+<template>
+    <van-overlay :show="show" :lock-scroll="false" @click="show = false" z-index="99">
+        <div class="box">
+            <img v-if="img" @click.stop="" :src="img" alt="" class="post-img" />
+            <div v-else class="post" ref="post" @click.stop="">
+                <div class="post-content">
+                    <div class="title">
+                        <div class="text1">{{ info.name }}</div>
+                        <div class="text2">铸造者: {{ info.minter }}</div>
+                    </div>
+                    <div class="post-box">
+                        <div class="show-box">
+                            <img class="show-bg" ref="showBg" src="@assets/png-bg-shangping2.png" alt="" />
+                            <div class="banner">
+                                <van-image width="53vw" height="53vw" :src="detailImg" fit="cover" />
+                            </div>
+                        </div>
+                        <div class="info-box">
+                            <img src="@assets/png-renzheng.png" alt="" class="renzhen" />
+                            <template v-if="info.txHash">
+                                <div class="info">
+                                    <div class="text1">哈希值</div>
+                                    <div class="text2" ref="txHash">
+                                        <span>{{ getShort(info.txHash, 15) }}</span>
+                                    </div>
+                                </div>
+                                <div class="info">
+                                    <div class="text1">令牌ID</div>
+                                    <div class="text2" ref="tokenId">
+                                        <span>{{ getShort(info.tokenId, 30) }}</span>
+                                    </div>
+                                </div>
+                                <div class="info">
+                                    <div class="text1">IPFS地址</div>
+                                    <div class="text2" ref="ipfsUrl">
+                                        <span>{{ getShort(info.ipfsUrl, 30) }}</span>
+                                    </div>
+                                </div>
+                            </template>
+
+                            <template v-if="info.hcTxHash">
+                                <div class="info">
+                                    <div class="text1">CRC华储链哈希值</div>
+                                    <div class="text2" ref="hcTxHash">
+                                        <span>{{ getShort(info.hcTxHash, 15) }}</span>
+                                    </div>
+                                </div>
+                                <div class="info">
+                                    <div class="text1">CRC华储链令牌ID</div>
+                                    <div class="text2" ref="hcTokenId">
+                                        <span>{{ getShort(info.hcTokenId, 30) }}</span>
+                                    </div>
+                                </div>
+                            </template>
+
+                            <div class="info">
+                                <div class="text1">生成时间 2022.09.02 13:41</div>
+                            </div>
+                        </div>
+                        <img src="@assets/png-zhengshu-diwen.png" alt="" class="box-bg" />
+                    </div>
+                </div>
+            </div>
+
+            <img
+                src="@assets/copy_icon.png"
+                v-for="(item, index) in copys"
+                :key="index"
+                :style="this[item]"
+                alt=""
+                class="copy"
+                @click.stop="copy(item)"
+            />
+
+            <div class="btn" @click.stop="">
+                <van-button block round type="primary">保存图片</van-button>
+            </div>
+        </div>
+    </van-overlay>
+</template>
+
+<script>
+import product from '../../mixins/product';
+import html2canvas from 'html2canvas';
+export default {
+    mixins: [product],
+    props: {
+        info: {
+            type: Object,
+            default: () => {
+                return {};
+            }
+        }
+    },
+    data() {
+        return {
+            show: false,
+            img: '',
+            detailImg: '',
+            txHash: {},
+            tokenId: {},
+            ipfsUrl: {},
+            hcTxHash: {},
+            hcTokenId: {},
+            copys: ['txHash', 'tokenId', 'ipfsUrl', 'hcTxHash', 'hcTokenId']
+        };
+    },
+    mounted() {
+        setTimeout(() => {
+            this.init();
+        }, 1000);
+    },
+    methods: {
+        init() {
+            this.show = true;
+            if (!this.img) {
+                this.$toast.loading({
+                    message: '加载中...',
+                    forbidClick: true
+                });
+                this.$nextTick(() => {
+                    this.getImgBase64(this.getImg(this.changeImgs(this.info.pic, 600)), 'detailImg');
+                    setTimeout(() => {
+                        [...this.copys].forEach(item => {
+                            this.getCopy(item);
+                        });
+                    }, 50);
+                    setTimeout(() => {
+                        this.loadImg();
+                    }, 1000);
+                });
+            }
+        },
+        getCopy(refName = 'txHash') {
+            let top = this.$refs[refName].parentNode.offsetTop + 167 + this.$refs.showBg.offsetHeight;
+            let left = this.$refs[refName].childNodes[0].offsetWidth + 53;
+            this[refName] = {
+                top: top + 'px',
+                left: left + 'px'
+            };
+        },
+        loadImg() {
+            html2canvas(this.$refs.post, {
+                useCORS: true,
+                allowTaint: true,
+                backgroundColor: null,
+                scale: 3
+            }).then(canvas => {
+                this.$toast.clear();
+                this.img = canvas.toDataURL('image/png');
+            });
+        },
+        getImgBase64(img2, key) {
+            let img = new Image();
+            img.crossOrigin = 'anonymous';
+            let _this = this;
+            img.onload = function () {
+                let src = _this.image2Base64(img);
+                _this[key] = src;
+            };
+            img.src = img2;
+        },
+        image2Base64(img) {
+            let canvas = document.createElement('canvas');
+            canvas.width = img.width;
+            canvas.height = img.height;
+            let ctx = canvas.getContext('2d');
+            ctx.drawImage(img, 0, 0, img.width, img.height);
+            let dataURL = canvas.toDataURL('image/png');
+            return dataURL;
+        },
+        copy(key) {
+            this.$copyText(this.info[key]).then(
+                e => {
+                    this.$toast.success('复制成功');
+                    console.log(e);
+                },
+                e => {
+                    this.$toast('复制失败');
+                    console.log(e);
+                }
+            );
+        }
+    }
+};
+</script>
+
+<style lang="less" scoped>
+.box {
+    .flex-col();
+    align-items: center;
+    position: fixed;
+    top: 0;
+    left: 0;
+    width: 100%;
+    height: 100%;
+    overflow: auto;
+    box-sizing: border-box;
+    padding: 50px 0;
+}
+
+.post-img {
+    width: calc(100vw - 32px);
+    display: block;
+}
+
+.post {
+    width: calc(100vw - 32px);
+    border-radius: 12px;
+    border: 1px solid rgba(243, 224, 184, 0.5);
+    padding: 12px;
+    box-sizing: border-box;
+    background-color: #0f0f0f;
+    .post-content {
+        background: linear-gradient(180deg, #ffd694 0%, #f3e0b8 17%, #9f875e 100%);
+        border-radius: 12px;
+        padding: 1px;
+        .title {
+            padding: 16px;
+            .text1 {
+                font-size: 20px;
+                font-weight: bold;
+                color: #0d090b;
+                line-height: 24px;
+            }
+            .text2 {
+                font-size: 12px;
+                font-weight: bold;
+                color: rgba(13, 9, 11, 0.5);
+                line-height: 17px;
+            }
+        }
+    }
+}
+
+.post-box {
+    background: linear-gradient(180deg, #0f0f0f 0%, #0a0a0a 100%);
+    border-radius: 12px;
+    padding-bottom: 20px;
+    position: relative;
+
+    .info {
+        padding: 6px 16px;
+        .text1 {
+            font-size: 12px;
+            font-weight: bold;
+            color: #939599;
+            line-height: 17px;
+        }
+        .text2 {
+            font-size: 14px;
+            color: #ffffff;
+            line-height: 24px;
+            margin-top: 4px;
+        }
+    }
+
+    .box-bg {
+        width: 100%;
+        position: absolute;
+        bottom: 0;
+        left: 0;
+        right: 0;
+        z-index: 0;
+    }
+}
+.info-box {
+    position: relative;
+    z-index: 1;
+    .renzhen {
+        width: 108px;
+        height: 108px;
+        position: absolute;
+        top: 29px;
+        right: 8px;
+    }
+}
+.show-box {
+    position: relative;
+    .show-bg {
+        width: 100%;
+        display: block;
+    }
+    .banner {
+        position: absolute;
+        box-shadow: 0px 0px 5px 0px #ffffff;
+        border-radius: 16px;
+        padding: 8px;
+        border: 1px solid rgba(255, 255, 255, 0.2);
+        left: 50%;
+        transform: translateX(-50%);
+        top: 9.3vw;
+        .van-image {
+            border: 2px solid #2f2f2f;
+            border-radius: 16px;
+        }
+    }
+}
+
+.btn {
+    width: calc(100vw - 102px);
+    margin: 20px 0 0;
+    --van-button-primary-background-color: #303133;
+}
+.copy {
+    position: absolute;
+    width: 18px;
+    height: 18px;
+    z-index: 20;
+}
+</style>

+ 3 - 3
src/mixins/product.js

@@ -148,9 +148,9 @@ export default {
                 return num;
                 return num;
             }
             }
         },
         },
-        getShort(str = '') {
-            if (str) {
-                str = '...' + str.substr(-8, 8);
+        getShort(str = '', num = 8) {
+            if (str && str.length > num) {
+                str = '...' + str.substr(0 - num, num);
             }
             }
             return str;
             return str;
         },
         },

+ 8 - 0
src/router/index.js

@@ -739,6 +739,14 @@ const routes = [
         meta: {
         meta: {
             tabColor: '#272B2E'
             tabColor: '#272B2E'
         }
         }
+    },
+    {
+        path: '/starCreateResult',
+        name: 'starCreateResult',
+        component: () => import('../views/star/CreateResult.vue'),
+        meta: {
+            tabColor: '#272B2E'
+        }
     }
     }
 ];
 ];
 
 

+ 6 - 2
src/views/asset/Detail.vue

@@ -449,6 +449,8 @@
             </div>
             </div>
         </div>
         </div>
     </van-overlay>
     </van-overlay>
+
+    <star-post :info='info'></star-post>
 </template>
 </template>
 
 
 <script>
 <script>
@@ -462,12 +464,14 @@ import HashCode from '../../components/product/HashCode.vue';
 import ProductTitle from '../../components/product/ProductTitle.vue';
 import ProductTitle from '../../components/product/ProductTitle.vue';
 import ProductBanner from '../../components/product/ProductBanner.vue';
 import ProductBanner from '../../components/product/ProductBanner.vue';
 import OrderOpen from '../../components/order/OrderOpen.vue';
 import OrderOpen from '../../components/order/OrderOpen.vue';
+import starPost from '../../components/star/post.vue';
 export default {
 export default {
     components: {
     components: {
         HashCode,
         HashCode,
         ProductTitle,
         ProductTitle,
         ProductBanner,
         ProductBanner,
-        OrderOpen
+        OrderOpen,
+        starPost
     },
     },
     mixins: [asset, product],
     mixins: [asset, product],
     data() {
     data() {
@@ -946,7 +950,7 @@ export default {
         destroyCartridgeConfirm() {
         destroyCartridgeConfirm() {
             this.transactionShow = true;
             this.transactionShow = true;
             this.destroyCartridge = false;
             this.destroyCartridge = false;
-            this.transactionPassword = ''
+            this.transactionPassword = '';
         },
         },
         // 藏品销毁
         // 藏品销毁
         bind() {
         bind() {

+ 381 - 17
src/views/star/Create.vue

@@ -1,21 +1,180 @@
 <template>
 <template>
     <div class="container">
     <div class="container">
-        <div class="steps">
-            <div class="step" v-for="(item, index) in steps" :key="index">
-                <div class="box">{{ index }}</div>
-                <div class="step-text">{{ item }}</div>
+        <van-sticky :offset-top="barHeight">
+            <div class="steps">
+                <div class="step" :class="{ active: step >= index }" v-for="(item, index) in steps" :key="index">
+                    <div class="box">
+                        <div>{{ index + 1 }}</div>
+                    </div>
+                    <div class="step-text">{{ item }}</div>
+                </div>
             </div>
             </div>
-        </div>
+        </van-sticky>
+
+        <van-pull-refresh
+            success-text="刷新成功"
+            success-duration="500"
+            class="discover"
+            v-model="isLoading"
+            @refresh="onRefresh"
+            v-if="step == 0"
+        >
+            <van-list class="list" v-model:loading="loading" :finished="finished" finished-text="" @load="getData">
+                <van-empty
+                    v-if="empty"
+                    description="没有符合兑换的藏品哦~"
+                    :image="require('../../assets/empty_img_asset.png')"
+                />
+                <div
+                    class="product"
+                    :class="{ active: chooseId === item.id }"
+                    v-for="item in list"
+                    :key="item.id"
+                    @click="choose(item.id)"
+                >
+                    <img
+                        class="icon"
+                        :src="
+                            chooseId === item.id
+                                ? require('../../assets/icon_gouxuan_pre.png')
+                                : require('../../assets/icon_gouxuan_huise.png')
+                        "
+                        alt=""
+                    />
+                    <div class="product-content">
+                        <van-image
+                            width="60"
+                            height="60"
+                            radius="6"
+                            :src="getImg(changeImgs(item.pic, 600))"
+                            fit="contain"
+                        />
+                        <div class="product-info">
+                            <div class="text1 van-ellipsis">{{ item.name }}</div>
+                            <div class="flex1"></div>
+                            <div class="text2" v-if="item.category">{{ item.category }}</div>
+                            <div class="text2" v-if="item.number">编号:{{ item.number }}</div>
+                        </div>
+                    </div>
+                </div>
+
+                <div class="btn" v-if="chooseId">
+                    <van-button @click="step = 1" type="primary" block round>确认销毁,下一步</van-button>
+                </div>
+            </van-list>
+        </van-pull-refresh>
+
+        <van-form @submit="submit" v-else-if="step == 1" :border="false">
+            <van-field
+                :border="false"
+                name="uploader"
+                label="上传图片"
+                :rules="[{ required: true, message: '请上传凭证' }]"
+            >
+                <template #label>
+                    <div class="title">
+                        <span>上传图片</span>
+                        <span>建议1:1大小,图片不大于250KB</span>
+                    </div>
+                </template>
+                <template #input>
+                    <van-uploader
+                        :max-count="1"
+                        upload-text="点击上传"
+                        upload-icon="plus"
+                        v-model="form.pic"
+                        :after-read="afterRead"
+                        preview-size="100"
+                    />
+                </template>
+            </van-field>
+            <van-field
+                name="图片名称"
+                label="图片名称"
+                placeholder="请输入图片名称"
+                v-model="form.name"
+                required
+                :rules="[{ required: true, message: '请填写图片名称' }]"
+            />
+            <van-field
+                :border="false"
+                class="textarea"
+                name="图片介绍"
+                label="图片介绍"
+                placeholder="请输入图片介绍,让大家更了解~"
+                v-model="form.detail"
+                clearable
+                rows="4"
+                autosize
+                type="textarea"
+                maxlength="800"
+                show-word-limit
+                :rules="[{ required: true, message: '请输入问题描述' }]"
+            />
+            <div class="tips">
+                <div class="text1">铸造提示</div>
+                <div class="text2">
+                    1.所有上传作品,需后台审核。审核冷却期为24小时,在藏品室可查看,但是不可以进行展示与转让。24小时到后,可进行展示与转让。<br />
+                    2.上传作品,仅可展示,可以转让,不可以交易
+                </div>
+            </div>
+            <div class="btn btns">
+                <van-button type="primary" @click="step = 0" plain round> 上一步</van-button>
+                <van-button round type="primary" native-type="submit">提交审核</van-button>
+            </div>
+        </van-form>
     </div>
     </div>
 </template>
 </template>
 
 
 <script>
 <script>
+import product from '../../mixins/product';
+import list from '../../mixins/list';
 export default {
 export default {
+    mixins: [product, list],
     data() {
     data() {
         return {
         return {
-            active: 0,
-            steps: ['销毁藏品', '上传图片', '提交审核']
+            step: 0,
+            steps: ['销毁藏品', '上传图片', '提交审核'],
+            empty: false,
+            list: [],
+            chooseId: 0,
+            refreshing: false,
+            url: '/asset/all',
+            form: {}
         };
         };
+    },
+    inject: ['barHeight'],
+    methods: {
+        beforeData() {
+            return {
+                query: {
+                    userId: this.$store.state.userInfo.id
+                },
+                sort: 'id,desc'
+            };
+        },
+        choose(id) {
+            if (this.chooseId == id) {
+                this.chooseId = 0;
+            } else {
+                this.chooseId = id;
+            }
+        },
+        onRefresh() {
+            this.isLoading = true;
+            this.getData().then(() => {
+                this.isLoading = false;
+            });
+        },
+        afterRead(file, e) {
+            file.status = 'uploading';
+            this.updateFile(file, 'id', 1000).then(img => {
+                console.log(img);
+                file.url = img;
+                file.status = 'done';
+            });
+        },
+        submit() {}
     }
     }
 };
 };
 </script>
 </script>
@@ -29,28 +188,233 @@ export default {
     height: 72px;
     height: 72px;
     .flex();
     .flex();
     .step {
     .step {
-        flex-grow: 1;
+        width: 33.33vw;
         .flex-col();
         .flex-col();
         align-items: center;
         align-items: center;
         .box {
         .box {
-            font-size: 10px;
-            color: #a2885c;
-            line-height: 12px;
-            border-radius: 12px;
-            background-color: #3b260c30;
-            width: 12px;
-            text-align: center;
             position: relative;
             position: relative;
+            div {
+                font-size: 10px;
+                color: #a2885c;
+                line-height: 12px;
+                border-radius: 12px;
+                background-color: #d5ba83;
+                width: 12px;
+                text-align: center;
+                position: relative;
+                z-index: 1;
+            }
             &::after {
             &::after {
                 content: '';
                 content: '';
-                width: 33vw;
-                background-color: #3b260c30;
+                width: 40vw;
+                background-color: #a2885c;
                 height: 1px;
                 height: 1px;
                 position: absolute;
                 position: absolute;
+                top: 0;
                 left: 6px;
                 left: 6px;
                 transform: translate(-50%, 6px);
                 transform: translate(-50%, 6px);
+                z-index: 0;
+            }
+        }
+
+        .step-text {
+            margin-top: 9px;
+            font-size: 12px;
+            color: #a2885c;
+            line-height: 17px;
+        }
+
+        &:nth-child(1) {
+            .box {
+                &::after {
+                    width: 16.5vw;
+                    left: 12px;
+                    transform: translate(0, 6px);
+                }
+            }
+        }
+
+        &:nth-child(3) {
+            .box {
+                &::after {
+                    width: 16.5vw;
+                    left: 12px;
+                    transform: translate(-100%, 6px);
+                }
+            }
+        }
+
+        &.active {
+            .box {
+                &::after {
+                    background-color: #3b260c;
+                }
+
+                div {
+                    background: #3b260c;
+                    color: #fff;
+                }
+                &::before {
+                    content: '';
+                    width: 22px;
+                    height: 22px;
+                    background: #d5ba83;
+                    position: absolute;
+                    top: 50%;
+                    left: 50%;
+                    transform: translate(-50%, -50%);
+                    border-radius: 100%;
+                }
+            }
+            .step-text {
+                color: #3b260c;
+            }
+        }
+    }
+}
+
+.product {
+    margin: 10px 10px;
+    background: #222426;
+    border-radius: 12px;
+    padding: 10px;
+    .flex();
+    .icon {
+        width: 24px;
+        height: 24px;
+    }
+    .product-content {
+        margin-left: 10px;
+        flex-grow: 1;
+        overflow: hidden;
+        .flex();
+        align-items: stretch;
+        .van-image {
+            flex-shrink: 0;
+        }
+        .product-info {
+            .flex-col();
+            margin-left: 12px;
+            overflow: hidden;
+
+            .text1 {
+                font-size: 12px;
+                color: #fff;
+                line-height: 24px;
+            }
+
+            .text2 {
+                font-size: 12px;
+                color: @text3;
+                line-height: 17px;
             }
             }
         }
         }
     }
     }
 }
 }
+.list {
+    padding-bottom: 100px;
+}
+.btn {
+    position: fixed;
+    z-index: 20;
+    padding: 9px 48px;
+    left: 0;
+    right: 0;
+    bottom: 0;
+    .bottom(9px);
+    background-color: #222426;
+}
+
+.btns {
+    .flex();
+    padding: 9px 16px;
+
+    .van-button {
+        &:nth-child(1) {
+            width: 100px;
+            border: 1px solid #43ce00;
+        }
+
+        &:nth-child(2) {
+            flex-grow: 1;
+            margin-left: 16px;
+        }
+    }
+}
+.van-form {
+    padding-bottom: 100px;
+}
+
+/deep/.van-cell {
+    flex-direction: column;
+    align-items: flex-start;
+    --van-field-input-text-color: #fff;
+    --van-uploader-text-color: #939599;
+    --van-uploader-icon-color: #939599;
+    --van-cell-border-color: #373b3e;
+    padding: 5px 16px 16px;
+    .van-field__label {
+        margin-right: 0;
+        font-size: 16px;
+        font-weight: bold;
+        color: #ffffff;
+        line-height: 24px;
+        width: auto;
+        .flex();
+        flex-direction: row-reverse;
+        padding-top: 16px;
+        .title {
+            span {
+                &:nth-child(2) {
+                    font-size: 12px;
+                    color: rgba(147, 149, 153, 0.7);
+                    line-height: 17px;
+                    margin-left: 10px;
+                }
+            }
+        }
+    }
+    .van-field__value {
+        width: 100%;
+        margin-top: 16px;
+        line-height: 24px;
+    }
+
+    .van-field__control::-webkit-input-placeholder {
+        font-size: 12px;
+        color: #939599;
+        line-height: 24px;
+    }
+
+    .van-uploader__upload {
+        border-radius: 8px;
+        border: 1px dashed #939599;
+        margin: 0 0;
+        .van-uploader__upload-text {
+            margin-top: 0;
+        }
+    }
+    .van-uploader__preview {
+        border-radius: 8px;
+        border: 1px dashed #939599;
+        margin: 0 0;
+        overflow: hidden;
+    }
+}
+
+.tips {
+    padding: 20px 16px;
+    color: #939599;
+    .text1 {
+        font-size: 14px;
+        color: #939599;
+        line-height: 24px;
+    }
+    .text2 {
+        font-size: 12px;
+        color: #939599;
+        line-height: 20px;
+        margin-top: 6px;
+    }
+}
 </style>
 </style>

+ 54 - 0
src/views/star/CreateResult.vue

@@ -0,0 +1,54 @@
+<template>
+    <div class="result">
+        <img class="icon" src="@assets/png-fuhe.png" alt="" />
+        <div class="text1">提交成功</div>
+        <div class="text2">
+            审核冷却期为24小时,在藏品室可查看,但是不可以进行展示与转让。24小时到后,可进行展示与转让。
+        </div>
+
+        <div class="btn">
+            <van-button type="primary" plain round block>继续上传</van-button>
+        </div>
+    </div>
+</template>
+
+<script>
+export default {};
+</script>
+
+<style lang="less" scoped>
+.result {
+    background: #272b2e;
+
+    .flex-col();
+    align-items: center;
+    padding: 60px 48px;
+}
+
+.icon {
+    width: 92px;
+    height: 92px;
+}
+
+.text1 {
+    font-size: 20px;
+    font-weight: bold;
+    color: #43ce00;
+    line-height: 28px;
+    margin: 6px 0 15px;
+}
+
+.text2 {
+    font-size: 14px;
+    color: #939599;
+    line-height: 20px;
+    text-align: center;
+}
+.btn {
+    margin-top: 80px;
+    align-self: stretch;
+    .van-button {
+        border: 1px solid #43ce00;
+    }
+}
+</style>