li.shaoyi 1 سال پیش
والد
کامیت
1ad0cea982

+ 1 - 1
src/business/login/index.ts

@@ -152,7 +152,7 @@ export function useLogin(persist = false) {
         quoteSocket.close()
         timerTask.clearAll()
 
-        userStore.$reset() // 待处理,重置后可能会出现多个重复的 store 实例
+        userStore.clearUserData() // 待处理,重置后可能会出现多个重复的 store 实例
         accountStore.$reset() // 待处理,重置后可能会出现多个重复的 store 实例
         loginStore.clearAutoLoginData()
         loginStore.clearLoginInfo()

+ 50 - 0
src/packages/mobile/assets/themes/global/global.less

@@ -390,6 +390,56 @@
     }
 }
 
+/* 商品列表 */
+.g-product-list {
+    padding: 10px;
+    padding-bottom: 0;
+
+    &__box {
+        &:not(:first-child) {
+            margin-top: 12px;
+        }
+
+        background-color: #fff;
+        border-radius: 8px;
+        padding: 16px;
+    }
+
+    &__titlebar {
+        display: flex;
+        justify-content: space-between;
+        align-items: center;
+        margin-bottom: 12px;
+    }
+
+    &__content {
+        display: flex;
+
+        .left {
+            margin-right: 12px;
+        }
+
+        .right {
+            flex: 1;
+            font-size: 13px;
+            line-height: 1.6;
+            color: #777;
+        }
+    }
+
+    &__btnbar {
+        display: flex;
+        justify-content: flex-end;
+        gap: 8px;
+        margin-top: 10px;
+
+        .van-button {
+            width: 80px;
+            border-width: 1px;
+        }
+    }
+}
+
 .g-detail {
     &__buy {
         background-color: #fff;

+ 40 - 33
src/packages/mobile/components/base/waterfall/index.vue

@@ -1,6 +1,6 @@
 <template>
     <div class="app-waterfall">
-        <ul ref="warterfallRef" v-if="dataList.length">
+        <ul ref="waterfallRef" v-if="dataList.length">
             <li v-for="(item, index) in dataList" :key="index">
                 <slot :item="item">{{ item }}</slot>
             </li>
@@ -9,7 +9,7 @@
 </template>
 
 <script lang="ts" setup>
-import { shallowRef, watch, nextTick, onActivated, onMounted } from 'vue'
+import { shallowReactive, shallowRef, computed, watch, nextTick, onActivated, onMounted } from 'vue'
 
 const props = defineProps({
     //数据列表
@@ -29,19 +29,20 @@ const props = defineProps({
     }
 })
 
-const warterfallRef = shallowRef<HTMLDivElement>()
+const waterfallRef = shallowRef<HTMLDivElement>()
 
-const state: { total: number; hightList: number[]; } = {
+const state = shallowReactive({
+    isRendering: false,
     total: 0,
-    hightList: [] //瀑布流高度列表
-}
+    heightList: [] as number[] //瀑布流高度列表
+})
 
 const render = () => {
-    state.total = 0
-    state.hightList = []
+    if (state.isRendering) return
+    state.isRendering = true
 
     nextTick(async () => {
-        const el = warterfallRef.value
+        const el = waterfallRef.value
         if (el) {
             const nodes = el.querySelectorAll('li')
 
@@ -50,22 +51,18 @@ const render = () => {
                 const images = li.querySelectorAll('img')
 
                 // 等待所有图片加载完成
-                for (let n = 0; n < images.length; n++) {
-                    await new Promise<void>((resolve) => {
-                        if (images[n].complete) {
-                            resolve()
-                        } else {
-                            images[n].onload = () => resolve()
-                            images[n].onerror = () => resolve()
-                        }
-                    })
-                }
-
-                if (!el.offsetWidth) {
-                    // 在 keepalive 组件下,如果在数据未全部加载出来之前跳转了页面,这会导致元素获取不到宽度,从而影响瀑布流布局的正常显示
-                    // 所以需要停止还未加载完成的数据渲染,待页面重新打开后继续加载
-                    break
-                }
+                await Promise.all([...images].map((img) => new Promise<void>((resolve) => {
+                    if (img.complete) {
+                        resolve()
+                    } else {
+                        img.onload = () => resolve()
+                        img.onerror = () => resolve()
+                    }
+                })))
+
+                // 在 keepalive 组件下,如果数据还未全部加载完成之前跳转了页面,这会导致元素获取不到宽度,从而影响布局的正常显示
+                // 所以需要暂停数据的加载,待页面重新显示后继续渲染
+                if (!el.offsetWidth) break
 
                 const space = (props.column - 1) * props.gap // 总间距
                 const width = (el.offsetWidth - space) / props.column // 每列的宽度
@@ -77,33 +74,43 @@ const render = () => {
                 if (i < props.column) {
                     li.style.top = '0'
                     li.style.left = (width * i) + (props.gap * i) + 'px'
-                    state.hightList.push(li.offsetHeight + props.gap)
+                    state.heightList.push(li.offsetHeight + props.gap)
                 } else {
-                    const minHeight = Math.min(...state.hightList) // 获取数组中最小值
-                    const index = state.hightList.findIndex((e) => e === minHeight) // 最小值的索引位置
+                    const minHeight = Math.min(...state.heightList) // 获取数组中最小值
+                    const index = state.heightList.findIndex((e) => e === minHeight) // 最小值的索引位置
                     li.style.top = minHeight + 'px'
                     li.style.left = (width * index) + (props.gap * index) + 'px'
-                    state.hightList[index] += li.offsetHeight + props.gap
+                    state.heightList[index] += li.offsetHeight + props.gap
                 }
 
                 state.total++
             }
 
-            const maxHeight = Math.max(...state.hightList); // 获取数组中最大值
+            const maxHeight = Math.max(...state.heightList); // 获取数组中最大值
             el.style.height = (maxHeight - props.gap) + 'px'
         }
+
+        state.isRendering = false
     })
 }
 
-watch(() => props.dataList, () => render())
+// 渲染标志位
+const shouldRender = computed(() => props.dataList.length > state.total)
+
+watch(() => props.dataList, () => {
+    state.total = 0
+    state.heightList = []
+    render()
+})
 
 onMounted(() => {
     render()
 
     onActivated(() => {
         // 对未完成加载的数据进行渲染
-        if (props.dataList.length > state.total) {
-            render()
+        if (shouldRender.value) {
+            // 延迟回调,如果 dataList 数据变更,会优先触发 watch 函数
+            nextTick(() => render())
         }
     })
 })

+ 0 - 114
src/packages/mobile/components/base/waterfall/next.vue

@@ -1,114 +0,0 @@
-<template>
-    <div class="app-waterfall">
-        <ul ref="warterfallRef" v-if="dataList.length">
-            <li v-for="(item, index) in dataList" :key="index">
-                <slot :item="item">{{ item }}</slot>
-            </li>
-        </ul>
-    </div>
-</template>
-
-<script lang="ts" setup>
-import { shallowRef, watch, nextTick, onActivated, onMounted } from 'vue'
-
-const props = defineProps({
-    //数据列表
-    dataList: {
-        type: Array,
-        default: () => ([])
-    },
-    //列数
-    column: {
-        type: Number,
-        default: 2
-    },
-    //间距
-    gap: {
-        type: Number,
-        default: 10
-    }
-})
-
-const warterfallRef = shallowRef<HTMLDivElement>()
-
-const state: { total: number; hightList: number[]; } = {
-    total: 0,
-    hightList: [] //瀑布流高度列表
-}
-
-const render = () => {
-    state.total = 0
-    state.hightList = []
-
-    nextTick(async () => {
-        const el = warterfallRef.value
-        if (el) {
-            const nodes = el.querySelectorAll('li')
-
-            for (let i = state.total; i < nodes.length; i++) {
-                const li = nodes[i]
-                const images = li.querySelectorAll('img')
-
-                // 等待所有图片加载完成
-                for (let n = 0; n < images.length; n++) {
-                    await new Promise<void>((resolve) => {
-                        if (images[n].complete) {
-                            resolve()
-                        } else {
-                            images[n].onload = () => resolve()
-                            images[n].onerror = () => resolve()
-                        }
-                    })
-                }
-
-                if (!el.offsetWidth) {
-                    // 在 keepalive 组件下,如果在数据未全部加载出来之前跳转了页面,这会导致元素获取不到宽度,从而影响瀑布流布局的正常显示
-                    // 所以需要停止还未加载完成的数据渲染,待页面重新打开后继续加载
-                    break
-                }
-
-                const space = (props.column - 1) * props.gap // 总间距
-                const width = (el.offsetWidth - space) / props.column // 每列的宽度
-
-                li.style.width = width + 'px'
-                li.style.opacity = '1'
-
-                //判断是否首行
-                if (i < props.column) {
-                    li.style.top = '0'
-                    li.style.left = (width * i) + (props.gap * i) + 'px'
-                    state.hightList.push(li.offsetHeight + props.gap)
-                } else {
-                    const minHeight = Math.min(...state.hightList) // 获取数组中最小值
-                    const index = state.hightList.findIndex((e) => e === minHeight) // 最小值的索引位置
-                    li.style.top = minHeight + 'px'
-                    li.style.left = (width * index) + (props.gap * index) + 'px'
-                    state.hightList[index] += li.offsetHeight + props.gap
-                }
-
-                state.total++
-            }
-
-            const maxHeight = Math.max(...state.hightList); // 获取数组中最大值
-            el.style.height = (maxHeight - props.gap) + 'px'
-        }
-    })
-}
-
-watch(() => props.dataList, () => render())
-
-onMounted(() => {
-    render()
-
-    onActivated(() => {
-        // 对未完成加载的数据进行渲染
-        if (props.dataList.length > state.total) {
-            render()
-        }
-    })
-})
-</script>
-
-<style lang="less">
-@import './index.less';
-</style>

+ 1 - 1
src/packages/mobile/views/user/register/Index.vue

@@ -5,7 +5,7 @@
     </template>
     <Form ref="formRef" class="g-form__container register__form" @submit="formSubmit">
       <CellGroup inset>
-        <Field v-model="formData.mobilephone" type="tel" name="mobilephone" :label="$t('user.register.mobile')"
+        <Field v-model="formData.mobilephone" type="digit" name="mobilephone" :label="$t('user.register.mobile')"
           :placeholder="$t('common.required')" :rules="formRules.mobilephone" />
         <Field v-model="formData.vcode" type="digit" name="vcode" :label="$t('user.register.vcode')"
           :placeholder="$t('common.required')" :rules="formRules.vcode">

+ 50 - 0
src/packages/tss/assets/themes/global/global.less

@@ -370,6 +370,56 @@
     }
 }
 
+/* 商品列表 */
+.g-product-list {
+    padding: 10px;
+    padding-bottom: 0;
+
+    &__box {
+        &:not(:first-child) {
+            margin-top: 12px;
+        }
+
+        background-color: #fff;
+        border-radius: 8px;
+        padding: 16px;
+    }
+
+    &__titlebar {
+        display: flex;
+        justify-content: space-between;
+        align-items: center;
+        margin-bottom: 12px;
+    }
+
+    &__content {
+        display: flex;
+
+        .left {
+            margin-right: 12px;
+        }
+
+        .right {
+            flex: 1;
+            font-size: 13px;
+            line-height: 1.6;
+            color: #777;
+        }
+    }
+
+    &__btnbar {
+        display: flex;
+        justify-content: flex-end;
+        gap: 8px;
+        margin-top: 10px;
+
+        .van-button {
+            width: 80px;
+            border-width: 1px;
+        }
+    }
+}
+
 .g-detail {
     &__buy {
         background-color: #fff;

+ 6 - 10
src/packages/tss/views/order/position/Index.vue

@@ -13,9 +13,9 @@
         </template>
         <app-pull-refresh ref="pullRefreshRef" v-model:loading="loading" v-model:error="error"
             @refresh="getSBYJMyOrders">
-            <div class="order-list">
-                <div class="order-list__box" v-for="(item, index) in orderComputedList" :key="index">
-                    <div class="order-list__titlebar">
+            <div class="g-product-list">
+                <div class="g-product-list__box" v-for="(item, index) in orderComputedList" :key="index">
+                    <div class="g-product-list__titlebar">
                         <div class="left">
                             <b>订单号:{{ item.tHDetailEx.tradeID }}</b>
                         </div>
@@ -25,7 +25,7 @@
                             </b>
                         </div>
                     </div>
-                    <div class="order-list__content">
+                    <div class="g-product-list__content">
                         <div class="left">
                             <Image width="100" height="100" radius="4" :src="getImageUrl(item.thumurls)" />
                         </div>
@@ -76,7 +76,7 @@
                             </ul>
                         </div>
                     </div>
-                    <div class="order-list__btnbar" v-if="item.tHDetailEx.holderQty">
+                    <div class="g-product-list__btnbar" v-if="item.tHDetailEx.holderQty">
                         <Button size="small" v-if="enableqty(item)" @click="showComponent('close', item)" round>
                             {{ $t('operation.close') }}
                         </Button>
@@ -133,8 +133,4 @@ const getImageUrl = (url: string) => {
     const [firstImg] = url.split(',')
     return firstImg ? getFileUrl(firstImg) : ''
 }
-</script>
-
-<style lang="less">
-@import './index.less';
-</style>
+</script>

+ 0 - 48
src/packages/tss/views/order/position/index.less

@@ -1,48 +0,0 @@
-.order-list {
-    padding: 10px;
-    padding-bottom: 0;
-
-    &__box {
-        &:not(:first-child) {
-            margin-top: 12px;
-        }
-
-        background-color: #fff;
-        border-radius: 8px;
-        padding: 16px;
-    }
-
-    &__titlebar {
-        display: flex;
-        justify-content: space-between;
-        align-items: center;
-        margin-bottom: 12px;
-    }
-
-    &__content {
-        display: flex;
-
-        .left {
-            margin-right: 12px;
-        }
-
-        .right {
-            flex: 1;
-            font-size: 13px;
-            line-height: 1.6;
-            color: #777;
-        }
-    }
-
-    &__btnbar {
-        display: flex;
-        justify-content: flex-end;
-        gap: 8px;
-        margin-top: 10px;
-
-        .van-button {
-            width: 80px;
-            border-width: 1px;
-        }
-    }
-}

+ 17 - 1
src/stores/modules/user.ts

@@ -126,6 +126,21 @@ export const useUserStore = defineStore(() => {
         })?.paramvalue
     }
 
+    // 清除用户信息,待优化
+    const clearUserData = () => {
+        state.userData = <Model.LoginQueryRsp>Object.create({
+            arearole: [],
+            exchangeRateConfigs: [],
+            externalExchanges: [],
+            goodsgroups: [],
+            loginAccount: {},
+            markets: [],
+            userAccount: {},
+            userInfo: {},
+            username: '',
+        })
+    }
+
     // 接收账户变更通知
     const userChangeNtf = eventBus.$on('UserChangeNtf', () => getUserData())
 
@@ -146,6 +161,7 @@ export const useUserStore = defineStore(() => {
         userChangeNtf,
         getMarketId,
         hasMarket,
-        getMarketName
+        getMarketName,
+        clearUserData
     }
 })