Browse Source

颜选美学v1.3线上版本优化

yuwenjun1997 2 years ago
parent
commit
e219e68d74

+ 85 - 68
components/views/cm-cart-navbar/cm-cart-navbar.vue

@@ -1,81 +1,98 @@
 <template>
     <view class="cart-navbar">
-        <view class="navbar">
-            <view class="icon iconfont" :class="isCheckedAll ? 'icon-xuanze' : 'icon-weixuanze'" @click="$emit('all')">
-                <text>全选</text>
-            </view>
-            <template v-if="isDeleted">
-                <view class="control">
-                    <tui-button
-                        type="gray"
-                        width="210rpx"
-                        height="80rpx"
-                        :size="30"
-                        shape="circle"
-                        @click="$emit('cancel')"
-                    >
-                        取消
-                    </tui-button>
+        <simple-safe-view :safeStatus="safeArea">
+            <view class="navbar">
+                <view
+                    class="icon iconfont"
+                    :class="isCheckedAll ? 'icon-xuanze' : 'icon-weixuanze'"
+                    @click="$emit('all')"
+                >
+                    <text>全选</text>
+                </view>
+                <template v-if="isDeleted">
+                    <view class="control">
+                        <tui-button
+                            type="gray"
+                            width="210rpx"
+                            height="80rpx"
+                            :size="30"
+                            shape="circle"
+                            @click="$emit('cancel')"
+                        >
+                            取消
+                        </tui-button>
+                        <tui-button
+                            type="base"
+                            width="210rpx"
+                            height="80rpx"
+                            :size="30"
+                            shape="circle"
+                            @click="$emit('remove')"
+                        >
+                            删除
+                        </tui-button>
+                    </view>
+                </template>
+
+                <template v-else>
+                    <view class="center">
+                        <view class="total">
+                            <text>总价:</text>
+                            <text class="price">¥{{ data.finallyPrice | priceFormat }}</text>
+                            <text class="delete" v-if="data.allPrice > data.finallyPrice">
+                                ¥{{ data.allPrice | priceFormat }}
+                            </text>
+                        </view>
+                        <view class="reduce" v-if="data.discountedPrice">
+                            <text class="price" v-if="data.discountedPrice">
+                                共减¥{{ data.discountedPrice | priceFormat }}
+                            </text>
+                            <text class="detail" @click="popupShow = true">优惠明细</text>
+                            <tui-icon
+                                :name="popupShow ? 'arrowup' : 'arrowdown'"
+                                color="#fc32b4"
+                                size="30rpx"
+                            ></tui-icon>
+                        </view>
+                    </view>
                     <tui-button
                         type="base"
                         width="210rpx"
                         height="80rpx"
                         :size="30"
                         shape="circle"
-                        @click="$emit('remove')"
+                        @click="$emit('submit')"
                     >
-                        删除
+                        去结算({{ data.count }})
                     </tui-button>
-                </view>
-            </template>
-
-            <template v-else>
-                <view class="center">
-                    <view class="total">
-                        <text>总价:</text> <text class="price">¥{{ data.finallyPrice | priceFormat }}</text>
-                        <text class="delete" v-if="data.allPrice > data.finallyPrice"
-                            >¥{{ data.allPrice | priceFormat }}</text
-                        >
-                    </view>
-                    <view class="reduce" v-if="data.discountedPrice">
-                        <text class="price" v-if="data.discountedPrice">
-                            共减¥{{ data.discountedPrice | priceFormat }}
-                        </text>
-                        <text class="detail" @click="popupShow = true">优惠明细</text>
-                        <tui-icon :name="popupShow ? 'arrowup' : 'arrowdown'" color="#fc32b4" size="30rpx"></tui-icon>
-                    </view>
-                </view>
-                <tui-button
-                    type="base"
-                    width="210rpx"
-                    height="80rpx"
-                    :size="30"
-                    shape="circle"
-                    @click="$emit('submit')"
-                >
-                    去结算({{ data.count }})
-                </tui-button>
-            </template>
-        </view>
-        <cm-safe-area-bottom v-if="safeArea"></cm-safe-area-bottom>
+                </template>
+            </view>
+        </simple-safe-view>
         <!-- 弹出 优惠明细-->
         <tui-bottom-popup :zIndex="89" :maskZIndex="88" :show="popupShow">
             <template>
                 <view class="popup-content">
-                    <view class="icon-iconfontguanbi iconfont colse" @click="popupShow = false"></view>
-                    <view class="title">优惠明细</view>
-                    <view class="row">
-                        <text>商品总额</text> <text>¥{{ data.allPrice | priceFormat }}</text>
-                    </view>
-                    <view class="row"> <text>促销满减</text> <text class="reduce">-¥0.00</text> </view>
-                    <view class="row">
-                        <text>优惠券</text> <text class="reduce">-¥{{ data.couponAmount | priceFormat }}</text>
-                    </view>
-                    <view class="row total-price">
-                        <text>总计</text> <text>¥{{ data.finallyPrice | priceFormat }}</text>
-                    </view>
-                    <view class="tip">实际订单金额已结算页为准</view>
-                    <cm-safe-area-bottom v-if="safeArea"></cm-safe-area-bottom>
+                    <simple-safe-view :safeStatus="safeArea">
+                        <view class="icon-iconfontguanbi iconfont colse" @click="popupShow = false"></view>
+                        <view class="title">优惠明细</view>
+                        <view class="row">
+                            <text>商品总额</text>
+                            <text>¥{{ data.allPrice | priceFormat }}</text>
+                        </view>
+                        <view class="row">
+                            <text>促销满减</text>
+                            <text class="reduce">-¥0.00</text>
+                        </view>
+                        <view class="row">
+                            <text>优惠券</text>
+                            <text class="reduce">-¥{{ data.couponAmount | priceFormat }}</text>
+                        </view>
+                        <view class="row total-price">
+                            <text>总计</text>
+                            <text>¥{{ data.finallyPrice | priceFormat }}</text>
+                        </view>
+                        <view class="tip">实际订单金额已结算页为准</view>
+                    </simple-safe-view>
                 </view>
             </template>
         </tui-bottom-popup>
@@ -127,9 +144,9 @@ export default {
         padding: 0 24rpx;
         z-index: 90;
         background-color: #fff;
-        
-        &::after{
-            content: "";
+
+        &::after {
+            content: '';
             display: block;
             width: 750rpx;
             height: 100rpx;
@@ -138,7 +155,7 @@ export default {
             left: 0;
             background-color: #fff;
         }
-        
+
         .icon {
             margin-right: 6rpx;
             text {

+ 7 - 0
components/views/cm-cart-product/cm-cart-product.vue

@@ -51,6 +51,13 @@ export default {
     computed: {
         userId() {
             return this.$store.getters.userId
+        },
+        limitedNum() {
+            if (this.productInfo.collageStatus > 0) {
+                return this.productInfo.collageProduct.limitedNum || this.productInfo.stock
+            } else {
+                return this.productInfo.stock
+            }
         }
     },
     methods: {

+ 17 - 15
components/views/cm-coupon-popup/cm-coupon-popup.vue

@@ -41,23 +41,25 @@
                         v-else
                         :style="{ paddingTop: paddingTop, paddingBottom: paddingBottom }"
                     >
-                        <view class="coupon-section" v-for="item in list" :key="item.couponId">
-                            <cm-coupon
-                                :controlType="item.controlType || 'use'"
-                                :status="item.couponStatus"
-                                :checked="item.checked"
-                                :key="item.couponId"
-                                :couponData="item"
-                                @click="$emit('couponClick', item)"
-                            ></cm-coupon>
-                        </view>
-                        <cm-safe-area-bottom v-if="hasSafeArea"></cm-safe-area-bottom>
+                        <simple-safe-view>
+                            <view class="coupon-section" v-for="item in list" :key="item.couponId">
+                                <cm-coupon
+                                    :controlType="item.controlType || 'use'"
+                                    :status="item.couponStatus"
+                                    :checked="item.checked"
+                                    :key="item.couponId"
+                                    :couponData="item"
+                                    @click="$emit('couponClick', item)"
+                                ></cm-coupon>
+                            </view>
+                        </simple-safe-view>
                     </scroll-view>
                     <view class="confirm-control" v-if="hasConfirm">
-                        <tui-button width="650rpx" height="88rpx" type="base" shape="circle" @click="handleClose">
-                            确定
-                        </tui-button>
-                        <cm-safe-area-bottom v-if="hasSafeArea"></cm-safe-area-bottom>
+                        <simple-safe-view>
+                            <tui-button width="650rpx" height="88rpx" type="base" shape="circle" @click="handleClose">
+                                确定
+                            </tui-button>
+                        </simple-safe-view>
                     </view>
                 </view>
             </view>

+ 198 - 89
components/views/cm-number-box/cm-number-box.vue

@@ -1,131 +1,240 @@
 <template>
-    <view class="number-box">
-        <view class="sub" @click="onSub" :class="{ disabled: subDisabled }"></view>
-        <input type="number" class="control-input" :value="value" @input="onInput" />
-        <view class="add" @click="onAdd" :class="{ disabled: addDisabled }"></view>
+    <view class="cm-number-box">
+        <view @click="_calcValue('minus')" class="cm-number-box__minus cm-number-box-btns">
+            <text
+                class="cm-number-box--text"
+                :class="{ 'cm-number-box--disabled': inputValue <= min || disabled }"
+                :style="{ color }"
+            >
+                -
+            </text>
+        </view>
+        <input
+            :disabled="disabled"
+            @focus="_onFocus"
+            @blur="_onBlur"
+            class="cm-number-box__value"
+            type="number"
+            v-model="inputValue"
+            :style="{ background, color }"
+        />
+        <view @click="_calcValue('plus')" class="cm-number-box__plus cm-number-box-btns">
+            <text
+                class="cm-number-box--text"
+                :class="{ 'cm-number-box--disabled': inputValue >= max || disabled }"
+                :style="{ color }"
+            >
+                +
+            </text>
+        </view>
     </view>
 </template>
-
 <script>
+/**
+ * NumberBox 数字输入框
+ * @description 带加减按钮的数字输入框
+ * @tutorial https://ext.dcloud.net.cn/plugin?id=31
+ * @property {Number} value 输入框当前值
+ * @property {Number} min 最小值
+ * @property {Number} max 最大值
+ * @property {Number} step 每次点击改变的间隔大小
+ * @property {String} background 背景色
+ * @property {String} color 字体颜色(前景色)
+ * @property {Boolean} disabled = [true|false] 是否为禁用状态
+ * @event {Function} change 输入框值改变时触发的事件,参数为输入框当前的 value
+ * @event {Function} focus 输入框聚焦时触发的事件,参数为 event 对象
+ * @event {Function} blur 输入框失焦时触发的事件,参数为 event 对象
+ */
+
 export default {
-    model: {
-        prop: 'value',
-        event: 'input'
-    },
+    name: 'UniNumberBox',
+    emits: ['change', 'input', 'update:modelValue', 'blur', 'focus'],
     props: {
+        value: {
+            type: [Number, String],
+            default: 1
+        },
+        modelValue: {
+            type: [Number, String],
+            default: 1
+        },
         min: {
             type: Number,
             default: 1
         },
         max: {
             type: Number,
-            default: 99999
+            default: 100
         },
-        value: {
+        step: {
             type: Number,
             default: 1
+        },
+        background: {
+            type: String,
+            default: '#f5f5f5'
+        },
+        color: {
+            type: String,
+            default: '#333'
+        },
+        disabled: {
+            type: Boolean,
+            default: false
         }
     },
-    computed: {
-        addDisabled() {
-            return this.value === this.max
-        },
-        subDisabled() {
-            return this.value === this.min
+    data() {
+        return {
+            inputValue: 0
         }
     },
     watch: {
-        value(nval) {
-            console.log(nval)
+        value(val) {
+            this.inputValue = +val
+        },
+        modelValue(val) {
+            this.inputValue = +val
+        }
+    },
+    created() {
+        if (this.value === 1) {
+            this.inputValue = +this.modelValue
+        }
+        if (this.modelValue === 1) {
+            this.inputValue = +this.value
         }
     },
     methods: {
-        // 减法
-        onSub() {
-            if (this.subDisabled) return
-            let inputValue = this.value
-            if (inputValue <= this.min) {
-                inputValue = this.min
-            } else {
-                inputValue--
+        _calcValue(type) {
+            if (this.disabled) {
+                return
+            }
+            const scale = this._getDecimalScale()
+            let value = this.inputValue * scale
+            let step = this.step * scale
+            if (type === 'minus') {
+                value -= step
+                if (value < this.min * scale) {
+                    return
+                }
+                if (value > this.max * scale) {
+                    value = this.max * scale
+                }
+            }
+
+            if (type === 'plus') {
+                value += step
+                if (value > this.max * scale) {
+                    return
+                }
+                if (value < this.min * scale) {
+                    value = this.min * scale
+                }
             }
-            this.$emit('input', inputValue)
-            this.$emit('change', inputValue)
+
+            this.inputValue = (value / scale).toFixed(String(scale).length - 1)
+            this.$emit('change', +this.inputValue)
+            // TODO vue2 兼容
+            this.$emit('input', +this.inputValue)
+            // TODO vue3 兼容
+            this.$emit('update:modelValue', +this.inputValue)
         },
-        // 加法
-        onAdd() {
-            if (this.addDisabled) return
-            let inputValue = this.value
-            if (inputValue >= this.max) {
-                inputValue = this.max
-            } else {
-                inputValue++
+        _getDecimalScale() {
+            let scale = 1
+            // 浮点型
+            if (~~this.step !== this.step) {
+                scale = Math.pow(10, String(this.step).split('.')[1].length)
             }
-            this.$emit('input', inputValue)
-            this.$emit('change', inputValue)
+            return scale
         },
-        // 失去焦点
-        onInput(e) {
-            let inputValue = parseInt(e.detail.value)
-            if (isNaN(inputValue)) {
-                inputValue = this.min
+        _onBlur(event) {
+            this.$emit('blur', event)
+            let value = event.detail.value
+            if (!value) {
+                // this.inputValue = 0;
+                return
             }
-            if (inputValue < this.min) {
-                inputValue = this.min
-            } else if (inputValue > this.max) {
-                inputValue = this.max
+            value = +value
+            if (value > this.max) {
+                value = this.max
+            } else if (value < this.min) {
+                value = this.min
             }
-            this.$emit('input', inputValue)
-            this.$emit('change', inputValue)
+            const scale = this._getDecimalScale()
+            this.inputValue = value.toFixed(String(scale).length - 1)
+            this.$emit('change', +this.inputValue)
+            this.$emit('input', +this.inputValue)
+        },
+        _onFocus(event) {
+            this.$emit('focus', event)
         }
     }
 }
 </script>
-
 <style lang="scss" scoped>
-.number-box {
-    width: 148rpx;
-    height: 50rpx;
+$box-height: 48rpx;
+$bg: #fff;
+$br: 4rpx;
+$color: #333;
+
+.cm-number-box {
+    /* #ifndef APP-NVUE */
+    display: flex;
+    /* #endif */
+    flex-direction: row;
+}
+
+.cm-number-box-btns {
+    /* #ifndef APP-NVUE */
+    display: flex;
+    /* #endif */
+    flex-direction: row;
+    align-items: center;
+    justify-content: center;
+    padding: 0 16rpx;
+    background-color: $bg;
+    /* #ifdef H5 */
+    cursor: pointer;
+    /* #endif */
     border: 1rpx solid #e1e1e1;
-    border-radius: 25rpx;
-    @extend .cm-flex-between;
+}
 
-    .add,
-    .sub {
-        @extend .cm-flex-center;
-        flex: 1;
-        font-size: 24rpx;
-        color: #666666;
+.cm-number-box__value {
+    background-color: $bg;
+    width: 48rpx;
+    height: $box-height;
+    text-align: center;
+    font-size: 26rpx;
+    border: 2rpx solid #e1e1e1;
+    border-left-width: 0;
+    border-right-width: 0;
+    color: $color;
+    background-color: #e1e1e1;
+}
 
-        &.disabled {
-            color: #cccccc;
-        }
-    }
+.cm-number-box__minus {
+    border-top-left-radius: $box-height / 2;
+    border-bottom-left-radius: $box-height / 2;
+}
 
-    .add {
-        &::before {
-            margin-bottom: 2rpx;
-            content: '+';
-        }
-    }
+.cm-number-box__plus {
+    border-top-right-radius: $box-height / 2;
+    border-bottom-right-radius: $box-height / 2;
+}
 
-    .sub {
-        &::before {
-            margin-bottom: 2rpx;
-            content: '-';
-        }
-    }
+.cm-number-box--text {
+    // fix nvue
+    line-height: 44rpx;
 
-    .control-input {
-        width: 56rpx;
-        height: 48rpx;
-        border-right: 1rpx solid #e1e1e1;
-        border-left: 1rpx solid #e1e1e1;
-        background-color: #f7f7f7;
-        box-sizing: border-box;
-        text-align: center;
-        font-size: 26rpx;
-        color: #333;
-    }
+    font-size: 32rpx;
+    font-weight: 300;
+    color: $color;
+}
+
+.cm-number-box .cm-number-box--disabled {
+    color: #c0c0c0 !important;
+    /* #ifdef H5 */
+    cursor: not-allowed;
+    /* #endif */
 }
 </style>

+ 1 - 0
components/views/cm-share-popup/cm-share-popup.vue

@@ -315,6 +315,7 @@ export default {
 
             porductNames.forEach((text, index) => {
                 text = index === 1 ? text.slice(0, text.length - 1) + '...' : text
+                // text = index === 1 ? text.slice(0, text.length - 1) + '...' : text
                 ctx.fillText(text, 40 * scale, (732 + 26 + 40 * index) * scale)
             })
             // 绘制商品二维码

+ 1 - 1
pages/authorize/login-custom.vue

@@ -139,7 +139,7 @@ export default {
         },
         // 验证码倒计时
         startCountDown() {
-            this.countDownStatus = 30
+            this.countDownStatus = 60
             if (this.timer) clearInterval(this.timer)
             // 开启定时器
             this.timer = setInterval(() => {

+ 16 - 16
pages/views/cart/cart.vue

@@ -49,22 +49,22 @@
             </tui-no-data>
         </template>
         <template v-else>
-            <!-- 有效商品 -->
-            <view class="supplier-area" v-for="item in shopList" :key="item.shopId">
-                <cm-cart-supplier-area
-                    :shopInfo="item"
-                    @change="checkedProductChange"
-                    @countChange="onCountChange"
-                    ref="supplierArea"
-                ></cm-cart-supplier-area>
-            </view>
-            <!-- 失效商品 -->
-            <view class="supplier-area" v-if="expiredProducts.length > 0">
-                <cm-cart-expired-area :expiredList="expiredProducts" @clear="onClearExp"></cm-cart-expired-area>
-            </view>
-            <view style="height: 100rpx;"></view>
-            <!-- 安全区域 -->
-            <cm-safe-area-bottom></cm-safe-area-bottom>
+            <simple-safe-view>
+                <!-- 有效商品 -->
+                <view class="supplier-area" v-for="item in shopList" :key="item.shopId">
+                    <cm-cart-supplier-area
+                        :shopInfo="item"
+                        @change="checkedProductChange"
+                        @countChange="onCountChange"
+                        ref="supplierArea"
+                    ></cm-cart-supplier-area>
+                </view>
+                <!-- 失效商品 -->
+                <view class="supplier-area" v-if="expiredProducts.length > 0">
+                    <cm-cart-expired-area :expiredList="expiredProducts" @clear="onClearExp"></cm-cart-expired-area>
+                </view>
+                <view style="height: 100rpx;"></view>
+            </simple-safe-view>
             <!-- 购物车导航 -->
             <cm-cart-navbar
                 :safeArea="true"

+ 1 - 1
pages/views/goods/components/goods-coupon-list/goods-coupon-list.vue

@@ -39,7 +39,7 @@ export default {
             border-radius: 4rpx;
             color: #ff457b;
             font-size: 22rpx;
-            width: 200rpx;
+            width: 250rpx;
             overflow: hidden;
             text-overflow: ellipsis;
             white-space: nowrap;

+ 1 - 1
pages/views/goods/components/goods-coupon-section/goods-coupon-section.vue

@@ -51,7 +51,7 @@ export default {
                 border-radius: 4rpx;
                 color: #ff457b;
                 font-size: 22rpx;
-                width: 200rpx;
+                width: 250rpx;
                 overflow: hidden;
                 text-overflow: ellipsis;
                 white-space: nowrap;

+ 107 - 107
pages/views/goods/components/goods-navbar/goods-navbar.vue

@@ -1,130 +1,130 @@
 <template>
-	<view class="goods-navbar">
-		<view class="navbar">
-			<view class="navbar-left">
-				<view class="item" @click="$emit('leftClick', 0)">
-					<!-- 首页 -->
-					<view class="iconfont icon-fanhuishouye"></view>
-					<view class="label">首页</view>
-				</view>
-				<button class="item contact" @click="$emit('leftClick', 1)" open-type="contact">
-					<!-- 客服 -->
-					<view class="iconfont icon-kefu"></view>
-					<view class="label">客服</view>
-				</button>
-				<view class="item cart" @click="$emit('leftClick', 2)">
-					<!-- 购物车 -->
-					<view class="iconfont icon-gouwuche"></view>
-					<view class="label">购物车</view>
-					<view class="badge" v-text="kindCount" v-if="kindCount > 0"></view>
-				</view>
-			</view>
-			<view class="navbar-right">
-				<view class="control" @click="$emit('rightClick', 0)"><slot name="left"></slot></view>
-				<view class="control" @click="$emit('rightClick', 1)"><slot name="right"></slot></view>
-			</view>
-		</view>
-		<!-- 安全区域 -->
-		<cm-safe-area-bottom></cm-safe-area-bottom>
-	</view>
+    <view class="goods-navbar">
+        <simple-safe-view>
+            <view class="navbar">
+                <view class="navbar-left">
+                		  <view class="item" @click="$emit('leftClick', 0)">
+                        <!-- 首页 -->
+                        <view class="iconfont icon-fanhuishouye"></view>
+                			     <view class="label">首页</view>
+                    </view>
+                    <button class="item contact" @click="$emit('leftClick', 1)" open-type="contact">
+                        <!-- 客服 -->
+                        <view class="iconfont icon-kefu"></view>
+                 			    <view class="label">客服</view>
+                    </button>
+                    <view class="item cart" @click="$emit('leftClick', 2)">
+                        <!-- 购物车 -->
+                        <view class="iconfont icon-gouwuche"></view>
+                        <view class="label">购物车</view>
+                        <view class="badge" v-text="kindCount" v-if="kindCount > 0"></view>
+                    </view>
+                </view>
+                <view class="navbar-right">
+                    <view class="control" @click="$emit('rightClick', 0)"><slot name="left"></slot></view>
+                    <view class="control" @click="$emit('rightClick', 1)"><slot name="right"></slot></view>
+                </view>
+            </view>
+        </simple-safe-view>
+    </view>
 </template>
 
 <script>
 import { mapGetters } from 'vuex'
 export default {
-	name: 'goods-navbar',
-	data() {
-		return {}
-	},
-	computed: {
-		...mapGetters(['kindCount'])
-	}
+    name: 'goods-navbar',
+    data() {
+        return {}
+    },
+    computed: {
+        ...mapGetters(['kindCount'])
+    }
 }
 </script>
 
 <style lang="scss" scoped>
 .goods-navbar {
-	@extend .fixed-bottom;
-	background-color: #fff;
-	border-top: 1rpx solid #efefef;
+    @extend .fixed-bottom;
+    background-color: #fff;
+    border-top: 1rpx solid #efefef;
 
-	.navbar {
-		width: 100%;
-		min-height: 100rpx;
-		padding: 0 24rpx;
-		box-sizing: border-box;
-		@extend .cm-flex-between;
+    .navbar {
+        width: 100%;
+        min-height: 100rpx;
+        padding: 0 24rpx;
+        box-sizing: border-box;
+        @extend .cm-flex-between;
 
-		.navbar-left {
-			flex: 1;
-			@extend .cm-flex-around;
-			margin-right: 16rpx;
-			.item {
-				flex: 1;
-				@extend .cm-flex-center;
-				flex-direction: column;
-				color: #333333;
+        .navbar-left {
+            flex: 1;
+            @extend .cm-flex-around;
+            margin-right: 16rpx;
+            .item {
+                flex: 1;
+                @extend .cm-flex-center;
+                flex-direction: column;
+                color: #333333;
 
-				.iconfont {
-					font-size: 36rpx;
-				}
+                .iconfont {
+                    font-size: 36rpx;
+                }
 
-				.label {
-					margin-top: 4rpx;
-					font-size: 22rpx;
-				}
+                .label {
+                    margin-top: 4rpx;
+                    font-size: 22rpx;
+                }
 
-				&.contact {
-					margin: 0;
-					padding: 0;
-					line-height: inherit;
-					background: #fff;
-					&::after {
-						display: none;
-					}
-				}
+                &.contact {
+                    margin: 0;
+                    padding: 0;
+                    line-height: inherit;
+                    background: #fff;
+                    &::after {
+                        display: none;
+                    }
+                }
 
-				&.cart {
-					position: relative;
-					.badge {
-						top: -8rpx;
-						right: 0;
-						position: absolute;
-						width: 36rpx;
-						height: 36rpx;
-						background-color: #ff457b;
-						border-radius: 18rpx;
-						@extend .cm-flex-center;
-						font-size: 22rpx;
-						color: #fff;
-					}
-				}
-			}
-		}
+                &.cart {
+                    position: relative;
+                    .badge {
+                        top: -8rpx;
+                        right: 0;
+                        position: absolute;
+                        width: 36rpx;
+                        height: 36rpx;
+                        background-color: #ff457b;
+                        border-radius: 18rpx;
+                        @extend .cm-flex-center;
+                        font-size: 22rpx;
+                        color: #fff;
+                    }
+                }
+            }
+        }
 
-		.navbar-right {
-			width: 420rpx;
-			@extend .cm-flex-between;
+        .navbar-right {
+            width: 420rpx;
+            @extend .cm-flex-between;
 
-			.control {
-				width: 210rpx;
-				height: 84rpx;
+            .control {
+                width: 210rpx;
+                height: 84rpx;
 
-				&:first-child {
-					@extend .cm-flex-center;
-					flex-direction: column;
-					border-radius: 40rpx 0 0 40rpx;
-					background-color: #ffeff4;
-				}
+                &:first-child {
+                    @extend .cm-flex-center;
+                    flex-direction: column;
+                    border-radius: 40rpx 0 0 40rpx;
+                    background-color: #ffeff4;
+                }
 
-				&:last-child {
-					@extend .cm-flex-center;
-					flex-direction: column;
-					border-radius: 0 40rpx 40rpx 0;
-					background: linear-gradient(92deg, #fc32b4 0%, #f83c6c 100%);
-				}
-			}
-		}
-	}
+                &:last-child {
+                    @extend .cm-flex-center;
+                    flex-direction: column;
+                    border-radius: 0 40rpx 40rpx 0;
+                    background: linear-gradient(92deg, #fc32b4 0%, #f83c6c 100%);
+                }
+            }
+        }
+    }
 }
 </style>

+ 9 - 9
pages/views/goods/goods-coupon-list.vue

@@ -5,16 +5,16 @@
             <!-- 搜索框 -->
             <cm-simple-search @search="onSearch" @cancel="onCancel" v-model="listQuery.productName"></cm-simple-search>
         </view>
-        <!-- 商品列表 -->
-        <view class="product-list">
-            <view class="product-item" v-for="(product, index) in productList" :key="product.productId">
-                <cm-product :data="product"></cm-product>
+        <simple-safe-view>
+            <!-- 商品列表 -->
+            <view class="product-list">
+                <view class="product-item" v-for="(product, index) in productList" :key="product.productId">
+                    <cm-product :data="product"></cm-product>
+                </view>
             </view>
-        </view>
-        <!-- 加载更多 -->
-        <cm-loadmore :hasNextPage="hasNextPage" :isLoading="isLoading" :visiable="!hideLoadmore"></cm-loadmore>
-        <!-- 安全区域 -->
-        <cm-safe-area-bottom v-if="hideLoadmore"></cm-safe-area-bottom>
+            <!-- 加载更多 -->
+            <cm-loadmore :hasNextPage="hasNextPage" :isLoading="isLoading" :visiable="!hideLoadmore"></cm-loadmore>
+        </simple-safe-view>
         <!-- 购物车 -->
         <cm-drag :cartNum="kindCount" @btnClick="toCart"></cm-drag>
     </view>

+ 65 - 66
pages/views/goods/goods-detail.vue

@@ -5,69 +5,71 @@
         <!-- 顶部导航 -->
         <goods-top-tabs @change="onTabChange" :current="currentTab" v-show="scrollTop > 100"></goods-top-tabs>
 
-        <!-- 锚点0 -->
-        <view id="anchor-0" class="anchor"></view>
-
-        <!-- 轮播 -->
-        <goods-image-swiper
-            :list="imageList"
-            @click="onSwiperClick"
-            @change="onSwiperChange"
-            :current="current"
-            :autoplay="autoplay"
-        ></goods-image-swiper>
-        <!-- 价格 -->
-        <goods-price :productData="productInfo"></goods-price>
-
-        <!-- 活动优惠券 -->
-        <goods-coupon-list
-            @click="couponVisiable = true"
-            :couponList="couponList"
-            v-if="couponList.length > 0"
-        ></goods-coupon-list>
-
-        <!-- 商品基本信息:商品名称 && 分享 && 标签 && 备注 && 服务-->
-        <goods-info @share="onShare" :productData="productInfo"></goods-info>
-
-        <!-- 参数 -->
-        <view class="section" v-if="productInfo.parametersList.length > 0">
-            <goods-params-section :paramList="productInfo.parametersList"></goods-params-section>
-        </view>
-
-        <!-- 优惠券 -->
-        <view class="section" v-if="couponList.length > 0">
-            <goods-coupon-section @click="couponVisiable = true" :couponList="couponList"></goods-coupon-section>
-        </view>
-
-        <!-- 锚点1 -->
-        <view id="anchor-1" class="anchor"></view>
-
-        <!-- 商品详情 -->
-        <view class="section detail">
-            <view class="title">商品详情</view>
-            <!-- <view
-                v-if="productDetail.detailInfo"
-                v-html="productDetail.detailInfo"
-                style="overflow-x: hidden;"
-            ></view> -->
-            <template v-if="productDetail && productDetail.detailInfo">
-                <!-- <parser :html="productDetail.detailInfo" :img-mode="widthFix"></parser> -->
-                <uParse :content="productDetail.detailInfo" />
-            </template>
-            <!-- 空 -->
-            <view class="section-empty" v-else>暂无商品详情</view>
-        </view>
-
-        <!-- 锚点2 -->
-        <view id="anchor-2" class="anchor"></view>
-
-        <!-- 服务项目 -->
-        <view class="section service-items">
-            <view class="title">服务项目</view>
-            <view v-if="productDetail && productDetail.serviceInfo" v-html="productDetail.serviceInfo"></view>
-            <!-- 空 -->
-            <view class="section-empty">暂无服务项目</view>
-        </view>
+        <simple-safe-view>
+            <!-- 锚点0 -->
+            <view id="anchor-0" class="anchor"></view>
+
+            <!-- 轮播 -->
+            <goods-image-swiper
+                :list="imageList"
+                @click="onSwiperClick"
+                @change="onSwiperChange"
+                :current="current"
+                :autoplay="autoplay"
+            ></goods-image-swiper>
+            <!-- 价格 -->
+            <goods-price :productData="productInfo"></goods-price>
+
+            <!-- 活动优惠券 -->
+            <goods-coupon-list
+                @click="couponVisiable = true"
+                :couponList="couponList"
+                v-if="couponList.length > 0"
+            ></goods-coupon-list>
+
+            <!-- 商品基本信息:商品名称 && 分享 && 标签 && 备注 && 服务-->
+            <goods-info @share="onShare" :productData="productInfo"></goods-info>
+
+            <!-- 参数 -->
+            <view class="section" v-if="productInfo.parametersList.length > 0">
+                <goods-params-section :paramList="productInfo.parametersList"></goods-params-section>
+            </view>
+
+            <!-- 优惠券 -->
+            <view class="section" v-if="couponList.length > 0">
+                <goods-coupon-section @click="couponVisiable = true" :couponList="couponList"></goods-coupon-section>
+            </view>
+
+            <!-- 锚点1 -->
+            <view id="anchor-1" class="anchor"></view>
+
+            <!-- 商品详情 -->
+            <view class="section detail">
+                <view class="title">商品详情</view>
+                <!-- <view
+                    v-if="productDetail.detailInfo"
+                    v-html="productDetail.detailInfo"
+                    style="overflow-x: hidden;"
+                ></view> -->
+                <template v-if="productDetail && productDetail.detailInfo">
+                    <!-- <parser :html="productDetail.detailInfo" :img-mode="widthFix"></parser> -->
+                    <uParse :content="productDetail.detailInfo" />
+                </template>
+                <!-- 空 -->
+                <view class="section-empty" v-else>暂无商品详情</view>
+            </view>
+
+            <!-- 锚点2 -->
+            <view id="anchor-2" class="anchor"></view>
+
+            <!-- 服务项目 -->
+            <view class="section service-items">
+                <view class="title">服务项目</view>
+                <view v-if="productDetail && productDetail.serviceInfo" v-html="productDetail.serviceInfo"></view>
+                <!-- 空 -->
+                <view class="section-empty">暂无服务项目</view>
+            </view>
+        </simple-safe-view>
 
         <!-- 商品操作导航 -->
         <goods-navbar class="navbar" :class="navbarType" @rightClick="navbarRightClick" @leftClick="navbarLeftClick">
@@ -119,9 +121,6 @@
 
         <!-- 返回顶部 -->
         <tui-scroll-top :scrollTop="scrollTop" :bottom="80"></tui-scroll-top>
-
-        <!-- 安全区域 -->
-        <cm-safe-area-bottom></cm-safe-area-bottom>
     </view>
 </template>
 

+ 13 - 13
pages/views/goods/goods-list.vue

@@ -7,24 +7,24 @@
             <!-- 筛选 -->
             <goods-filter @filter="onFilter"></goods-filter>
         </view>
-        <!-- 商品列表 -->
-        <view class="product-list">
-            <view class="product-item" v-for="(product, index) in productList" :key="index">
-                <cm-product :data="product"></cm-product>
+        <simple-safe-view>
+            <!-- 商品列表 -->
+            <view class="product-list">
+                <view class="product-item" v-for="(product, index) in productList" :key="index">
+                    <cm-product :data="product"></cm-product>
+                </view>
             </view>
-        </view>
-        <!-- 商品列表为空 -->
-        <template v-if="productList.length <= 0 && !isLoading">
-            <tui-no-data :imgUrl="staticUrl + 'icon-empty-address.png'" :imgHeight="230" :imgWidth="290">
-                <view class="empty-tip">暂无商品~~</view>
-            </tui-no-data>
-        </template>
+            <!-- 商品列表为空 -->
+            <template v-if="productList.length <= 0 && !isLoading">
+                <tui-no-data :imgUrl="staticUrl + 'icon-empty-address.png'" :imgHeight="230" :imgWidth="290">
+                    <view class="empty-tip">暂无商品~~</view>
+                </tui-no-data>
+            </template>
+        </simple-safe-view>
         <!-- 加载更多 -->
         <cm-loadmore :hasNextPage="hasNextPage" :isLoading="isLoading" :visiable="!hideLoadmore"></cm-loadmore>
         <!-- 回到顶部 -->
         <tui-scroll-top :scrollTop="scrollTop" :bottom="60"></tui-scroll-top>
-        <!-- 安全区域 -->
-        <cm-safe-area-bottom v-if="hideLoadmore"></cm-safe-area-bottom>
     </view>
 </template>
 

+ 51 - 51
pages/views/goods/goods-search.vue

@@ -13,62 +13,62 @@
                 @search="handleSearch"
             ></cm-search>
         </view>
-        <!-- 订单列表为空 -->
-        <template v-if="list.length <= 0 && !isLoading">
-            <tui-no-data :imgUrl="emptyInfo.image" :imgHeight="230" :imgWidth="290">
-                <view class="empty-tip" v-text="emptyInfo.message"></view>
-            </tui-no-data>
-        </template>
-        <view class="list">
-            <view class="product" v-for="product in list" :key="product.productId" @click="toDetail(product)">
-                <image :src="product.mainImage" mode="widthFix" class="cover"></image>
-                <view class="info">
-                    <view class="title">{{ product.name }}</view>
-                    <view class="unit">规格:{{ product.unit }}</view>
-                    <view class="tags">
-                        <!-- 拼团价  活动价  限时特价  券后价   -->
-                        <!-- 该商品参与了商城活动 -->
-                        <template v-if="isActivityProduct(product)">
-                            <view class="tag pt" v-if="product.collageStatus > 0">拼团价</view>
-                            <view class="tag hd" v-else-if="product.activeStatus > 0">活动价</view>
-                            <view class="tag other" v-else-if="product.discountStatus > 0">限时特价</view>
-                        </template>
-                        <!-- 该商品未参与商城活动 -->
-                        <template v-else>
-                            <view class="tag other" v-if="product.couponStatus > 1">{{ product.couponInfo }}</view>
-                            <view class="tag other" v-else-if="product.couponStatus > 0">券后价</view>
-                        </template>
-                    </view>
-                    <!-- 底部 -->
-                    <view class="footer">
-                        <!-- 价格 -->
-                        <view class="price">
-                            <text>¥{{ showPrice(product) | priceFormat }}</text>
-                            <text class="deleted" v-if="product.normalPrice">
-                                ¥{{ product.normalPrice | priceFormat }}
-                            </text>
+        <simple-safe-view>
+            <!-- 订单列表为空 -->
+            <template v-if="list.length <= 0 && !isLoading">
+                <tui-no-data :imgUrl="emptyInfo.image" :imgHeight="230" :imgWidth="290">
+                    <view class="empty-tip" v-text="emptyInfo.message"></view>
+                </tui-no-data>
+            </template>
+            <view class="list">
+                <view class="product" v-for="product in list" :key="product.productId" @click="toDetail(product)">
+                    <image :src="product.mainImage" mode="widthFix" class="cover"></image>
+                    <view class="info">
+                        <view class="title">{{ product.name }}</view>
+                        <view class="unit">规格:{{ product.unit }}</view>
+                        <view class="tags">
+                            <!-- 拼团价  活动价  限时特价  券后价   -->
+                            <!-- 该商品参与了商城活动 -->
+                            <template v-if="isActivityProduct(product)">
+                                <view class="tag pt" v-if="product.collageStatus > 0">拼团价</view>
+                                <view class="tag hd" v-else-if="product.activeStatus > 0">活动价</view>
+                                <view class="tag other" v-else-if="product.discountStatus > 0">限时特价</view>
+                            </template>
+                            <!-- 该商品未参与商城活动 -->
+                            <template v-else>
+                                <view class="tag other" v-if="product.couponStatus > 1">{{ product.couponInfo }}</view>
+                                <view class="tag other" v-else-if="product.couponStatus > 0">券后价</view>
+                            </template>
+                        </view>
+                        <!-- 底部 -->
+                        <view class="footer">
+                            <!-- 价格 -->
+                            <view class="price">
+                                <text>¥{{ showPrice(product) | priceFormat }}</text>
+                                <text class="deleted" v-if="product.normalPrice">
+                                    ¥{{ product.normalPrice | priceFormat }}
+                                </text>
+                            </view>
+                            <!-- 加入购物车 -->
+                            <view
+                                class="add-cart iconfont icon-gouwuche"
+                                @click.stop="addCart(product)"
+                                v-if="product.collageStatus !== 1"
+                            ></view>
                         </view>
-                        <!-- 加入购物车 -->
-                        <view
-                            class="add-cart iconfont icon-gouwuche"
-                            @click.stop="addCart(product)"
-                            v-if="product.collageStatus !== 1"
-                        ></view>
                     </view>
                 </view>
+                <!-- 没有更多了 -->
+                <cm-loadmore
+                    :hasMore="hasNextPage"
+                    :isLoading="isLoading"
+                    :visiable="visiable"
+                    backgroundColor="#fff"
+                ></cm-loadmore>
             </view>
-            <!-- 没有更多了 -->
-            <cm-loadmore
-                :hasMore="hasNextPage"
-                :isLoading="isLoading"
-                :visiable="visiable"
-                backgroundColor="#fff"
-            ></cm-loadmore>
-        </view>
+        </simple-safe-view>
         <!-- 操作弹窗 -->
         <tui-modal :show="removeKeywordModal" content="确认清空搜索历史记录?" @click="clearAllHistory"></tui-modal>
-        <!-- 安全区域 -->
-        <cm-safe-area-bottom v-if="visiable"></cm-safe-area-bottom>
     </view>
 </template>
 
@@ -136,7 +136,7 @@ export default {
         toDetail(row) {
             this.$router.navigateTo(`goods/goods-detail?jumpState=1&productId=${row.productId}`)
         },
-        // 加入购物车 
+        // 加入购物车
         addCart(row) {
             this.$store.dispatch('cart/addToCart', { productId: row.productId })
         },

+ 15 - 14
pages/views/order/components/order-submit/order-submit.vue

@@ -1,21 +1,22 @@
 <template>
     <view class="order-submit">
-        <view class="control">
-            <view class="count">共{{ orderInfo.allCount }}件商品</view>
-            <view class="price">
-                <view class="total">
-                    总计:
-                    <text class="paymount">¥{{ orderInfo.payAllPrice | priceFormat }}</text>
-                </view>
-                <view class="reduce" v-if="orderInfo.discountedPrice">
-                    共减:¥{{ orderInfo.discountedPrice | priceFormat }}
+        <simple-safe-view>
+            <view class="control">
+                <view class="count">共{{ orderInfo.allCount }}件商品</view>
+                <view class="price">
+                    <view class="total">
+                        总计:
+                        <text class="paymount">¥{{ orderInfo.payAllPrice | priceFormat }}</text>
+                    </view>
+                    <view class="reduce" v-if="orderInfo.discountedPrice">
+                        共减:¥{{ orderInfo.discountedPrice | priceFormat }}
+                    </view>
                 </view>
+                <tui-button type="base" width="210rpx" height="80rpx" shape="circle" @click="$emit('submit')">
+                    提交订单
+                </tui-button>
             </view>
-            <tui-button type="base" width="210rpx" height="80rpx" shape="circle" @click="$emit('submit')">
-                提交订单
-            </tui-button>
-        </view>
-        <cm-safe-area-bottom></cm-safe-area-bottom>
+        </simple-safe-view>
     </view>
 </template>
 

+ 46 - 46
pages/views/order/order-create.vue

@@ -5,52 +5,54 @@
         <view class="sticky-top">
             <order-choose-address class="sticky-top" :addressInfo="addressInfo"></order-choose-address>
         </view>
-        <!-- 供应商商品列表 -->
-        <view class="shop-list">
-            <view class="section" v-for="(shopInfo, index) in shopList" :key="shopInfo.shopId">
-                <order-supplier-area
-                    :shopInfo="shopInfo"
-                    :submitType="submitType"
-                    @countChange="onCountChange"
-                ></order-supplier-area>
-                <view class="comment">
-                    <text>留言:</text>
-                    <input placeholder="请输入内容" placeholder-class="placeholder" v-model="shopInfo.note" />
+        <simple-safe-view>
+            <!-- 供应商商品列表 -->
+            <view class="shop-list">
+                <view class="section" v-for="(shopInfo, index) in shopList" :key="shopInfo.shopId">
+                    <order-supplier-area
+                        :shopInfo="shopInfo"
+                        :submitType="submitType"
+                        @countChange="onCountChange"
+                    ></order-supplier-area>
+                    <view class="comment">
+                        <text>留言:</text>
+                        <input placeholder="请输入内容" placeholder-class="placeholder" v-model="shopInfo.note" />
+                    </view>
+                    <tui-divider :height="48" v-if="index < shopList.length - 1"></tui-divider>
                 </view>
-                <tui-divider :height="48" v-if="index < shopList.length - 1"></tui-divider>
             </view>
-        </view>
-        <!-- 优惠券 -->
-        <view class="cell-section" @click="couponVisiable = true" v-if="receiveCouponList.length > 0">
-            <tui-list-cell :arrow="true" :padding="cellPadding" :unlined="true">
-                <view class="cell-content">
-                    <text class="label">优惠券</text>
-                    <text class="reduce tip">-¥{{ couponAmount | priceFormat }}</text>
-                </view>
-            </tui-list-cell>
-        </view>
-        <!-- 分享减免 -->
-        <view class="cell-section" @click="onShare" v-if="reduction">
-            <tui-list-cell :arrow="false" :padding="cellPadding" :unlined="true">
-                <button class="cell-content share-btn">
-                    <text v-if="!shareStatus" class="active label">
-                        金额满¥{{ reduction.touchPrice }}元,分享可立减¥{{ reduction.reducedAmount }}元
-                    </text>
-                    <text class="label" v-else>分享减免</text>
-                    <text class="reduce tip" v-if="!shareStatus">点击分享</text>
-                    <text class="active" v-else>-¥{{ reduction.reducedAmount | priceFormat }}</text>
-                </button>
-            </tui-list-cell>
-        </view>
-        <!-- 运费 -->
-        <view class="cell-section">
-            <tui-list-cell :arrow="false" :padding="cellPadding" :unlined="true">
-                <view class="cell-content">
-                    <text class="label">运费</text>
-                    <text class="tip postage">免邮</text>
-                </view>
-            </tui-list-cell>
-        </view>
+            <!-- 优惠券 -->
+            <view class="cell-section" @click="couponVisiable = true" v-if="receiveCouponList.length > 0">
+                <tui-list-cell :arrow="true" :padding="cellPadding" :unlined="true">
+                    <view class="cell-content">
+                        <text class="label">优惠券</text>
+                        <text class="reduce tip">-¥{{ couponAmount | priceFormat }}</text>
+                    </view>
+                </tui-list-cell>
+            </view>
+            <!-- 分享减免 -->
+            <view class="cell-section" @click="onShare" v-if="reduction">
+                <tui-list-cell :arrow="false" :padding="cellPadding" :unlined="true">
+                    <button class="cell-content share-btn">
+                        <text v-if="!shareStatus" class="active label">
+                            金额满¥{{ reduction.touchPrice }}元,分享可立减¥{{ reduction.reducedAmount }}元
+                        </text>
+                        <text class="label" v-else>分享减免</text>
+                        <text class="reduce tip" v-if="!shareStatus">点击分享</text>
+                        <text class="active" v-else>-¥{{ reduction.reducedAmount | priceFormat }}</text>
+                    </button>
+                </tui-list-cell>
+            </view>
+            <!-- 运费 -->
+            <view class="cell-section">
+                <tui-list-cell :arrow="false" :padding="cellPadding" :unlined="true">
+                    <view class="cell-content">
+                        <text class="label">运费</text>
+                        <text class="tip postage">免邮</text>
+                    </view>
+                </tui-list-cell>
+            </view>
+        </simple-safe-view>
         <!-- 提交订单 -->
         <order-submit :orderInfo="orderInfo" @submit="onSubmit"></order-submit>
         <!-- 优惠券列表 -->
@@ -78,8 +80,6 @@
         </cm-share-popup>
         <!-- 订单提交拦截 -->
         <tui-modal :show="preventModal" :content="preventText" @click="onPreventModalConfirm"></tui-modal>
-        <!-- 安全区域 -->
-        <cm-safe-area-bottom></cm-safe-area-bottom>
     </view>
 </template>
 

+ 3 - 2
pages/views/order/order-detail.vue

@@ -56,8 +56,9 @@
         <order-information :orderInfo="orderInfo"></order-information>
         <!-- 底部操作按钮 -->
         <view class="control fixed-bottom" v-if="orderInfo.userId == userId">
-            <order-contror :orderInfo="orderInfo" @confirm="handleConfirmClick"></order-contror>
-            <cm-safe-area-bottom></cm-safe-area-bottom>
+            <simple-safe-view>
+                <order-contror :orderInfo="orderInfo" @confirm="handleConfirmClick"></order-contror>
+            </simple-safe-view>
         </view>
         <!-- 操作弹窗 -->
         <tui-modal :show="modal" :content="modalText" @click="handleModalConfirm"></tui-modal>

+ 2 - 2
services/config.env.js

@@ -2,8 +2,8 @@ export let APP_API_URI = ''
 if (process.env.NODE_ENV === 'development') {
     // 开发环境
     // APP_API_URI = 'http://192.168.2.68:8011'	 //本地联调地址
-    // APP_API_URI = 'https://mall2c-b.caimei365.com'
-    APP_API_URI = 'https://mall2c.caimei365.com'
+    APP_API_URI = 'https://mall2c-b.caimei365.com'
+    // APP_API_URI = 'https://mall2c.caimei365.com'
 } else {
     // 生产环境
     APP_API_URI = 'https://mall2c.caimei365.com'

+ 4 - 0
uni_modules/simple-safe-view/changelog.md

@@ -0,0 +1,4 @@
+## 1.0.1(2022-05-20)
+修改组件描述信息
+## 1.0.0(2022-05-20)
+第一次发布

+ 75 - 0
uni_modules/simple-safe-view/components/simple-safe-view/simple-safe-view.vue

@@ -0,0 +1,75 @@
+<template>
+    <!-- #ifndef VUE3  -->
+    <view>
+        <!-- #endif  -->
+        <view><slot></slot></view>
+        <view :style="safeAreaStyle"></view>
+        <!-- #ifndef VUE3  -->
+    </view>
+    <!-- #endif  -->
+</template>
+<!-- #ifdef VUE3  -->
+<script setup>
+import { ref, onMounted, computed } from 'vue'
+const safeFlag = ref(false)
+const props = defineProps({
+    safeStatus: {
+        type: Boolean,
+        default: true
+    },
+    bottom: {
+        type: Number,
+        default: 22
+    },
+    bgColor: {
+        type: String,
+        default: null
+    }
+})
+const safeAreaStyle = computed(() => ({
+    height: `${safeFlag.value ? props.bottom : 0}px`,
+    backgroundColor: props.bgColor
+}))
+onMounted(() => {
+    const sysInfo = uni.getSystemInfoSync()
+    safeFlag.value = props.safeStatus && /^(iphone)\s(x|11|12|13)/i.test(sysInfo.model)
+})
+</script>
+<!-- #endif  -->
+
+<script>
+export default {
+    name: 'simple-safe-view',
+    // #ifndef VUE3
+    props: {
+        safeStatus: {
+            type: Boolean,
+            default: true
+        },
+        bottom: {
+            type: Number,
+            default: 22
+        },
+        bgColor: {
+            type: String,
+            default: null
+        }
+    },
+    data() {
+        return {
+            safeFlag: false
+        }
+    },
+    computed: {
+        safeAreaStyle() {
+            return `height:${this.safeFlag ? this.bottom : 0}px;background-color: ${this.bgColor}`
+        }
+    },
+    created() {
+        const sysInfo = uni.getSystemInfoSync()
+        console.log(sysInfo)
+        this.safeFlag = this.safeStatus && /^(iphone)\s(x|11|12|13)/i.test(sysInfo.model)
+    }
+    // #endif
+}
+</script>

+ 81 - 0
uni_modules/simple-safe-view/package.json

@@ -0,0 +1,81 @@
+{
+    "id": "simple-safe-view",
+    "displayName": "simple-safe-view",
+    "version": "1.0.1",
+    "description": "simple-safe-view",
+    "keywords": [
+        "simple-safe-view"
+    ],
+    "repository": "",
+    "engines": {
+        "HBuilderX": "^3.1.0"
+    },
+    "dcloudext": {
+        "category": [
+            "前端组件",
+            "通用组件"
+        ],
+        "sale": {
+            "regular": {
+                "price": "0.00"
+            },
+            "sourcecode": {
+                "price": "0.00"
+            }
+        },
+        "contact": {
+            "qq": ""
+        },
+        "declaration": {
+            "ads": "无",
+            "data": "插件不采集任何数据",
+            "permissions": "无"
+        },
+        "npmurl": ""
+    },
+    "uni_modules": {
+        "dependencies": [],
+        "encrypt": [],
+        "platforms": {
+            "cloud": {
+                "tcb": "y",
+                "aliyun": "y"
+            },
+            "client": {
+                "Vue": {
+                    "vue2": "y",
+                    "vue3": "y"
+                },
+                "App": {
+                    "app-vue": "u",
+                    "app-nvue": "u"
+        
+     },
+                "H5-mobile": {
+                    "Safari": "u",
+                    "Android Browser": "u",
+                    "微信浏览器(Android)": "u",
+                    "QQ浏览器(Android)": "u"
+                },
+                "H5-pc": {
+                    "Chrome": "n",
+                    "IE": "n",
+                    "Edge": "n",
+                    "Firefox": "n",
+                    "Safari": "n"
+                },
+                "小程序": {
+                    "微信": "y",
+                    "阿里": "u",
+                    "百度": "u",
+                    "字节跳动": "u",
+                    "QQ": "u"
+                },
+                "快应用": {
+                    "华为": "u",
+                    "联盟": "u"
+                }
+            }
+        }
+    }
+}

+ 4 - 0
uni_modules/simple-safe-view/readme.md

@@ -0,0 +1,4 @@
+# simple-safe-view
+
+**该组件作为容器使用**
+- 因部分iphone(iPhone X - iPhone 13)需要适配底部安全区域,该组件可自动获取手机型号并判断是否需要是否开启底部安全距离。