| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474 | 
							- <template>
 
-   <view
 
-     class="ui-tab"
 
-     ref="tabRef"
 
-     :id="'tab-' + vm.uid"
 
-     :class="[
 
-       props.ui,
 
-       props.tpl,
 
-       props.bg,
 
-       props.align,
 
-       { 'ui-tab-inline': props.inline },
 
-       { 'ui-tab-scrolls': props.scroll },
 
-     ]"
 
-   >
 
-     <block v-if="scroll">
 
-       <view class="ui-tab-scroll-warp">
 
-         <scroll-view
 
-           scroll-x="true"
 
-           class="ui-tab-scroll"
 
-           :scroll-left="state.curValue > 1 ? state.tabNodeList[state.curValue - 1].left : 0"
 
-           scroll-with-animation
 
-           :style="{ width: `${state.content.width}px` }"
 
-         >
 
-           <view class="ss-flex ss-col-center">
 
-             <su-tab-item
 
-               v-for="(item, index) in props.tab"
 
-               :data="item"
 
-               :index="index"
 
-               :key="index"
 
-               @up="upitem"
 
-               @tap.native="click(index, item)"
 
-             ></su-tab-item>
 
-             <view
 
-               class="ui-tab-mark-warp"
 
-               :class="[{ over: state.over }]"
 
-               :style="[{ left: state.markLeft + 'px' }, { width: state.markWidth + 'px' }]"
 
-             >
 
-               <view
 
-                 class="ui-tab-mark"
 
-                 :class="[props.mark, { 'ui-btn': props.tpl == 'btn' || props.tpl == 'subtitle' }]"
 
-                 :style="[
 
-                   {
 
-                     background:
 
-                       props.tpl == 'btn' || props.tpl == 'subtitle' ? titleStyle.activeBg : 'none',
 
-                   },
 
-                 ]"
 
-               ></view>
 
-             </view>
 
-           </view>
 
-         </scroll-view>
 
-       </view>
 
-     </block>
 
-     <block v-else>
 
-       <su-tab-item
 
-         v-for="(item, index) in props.tab"
 
-         :data="item"
 
-         :index="index"
 
-         :key="index"
 
-         @up="upitem"
 
-         @tap.native="click(index, item)"
 
-       ></su-tab-item>
 
-       <view
 
-         class="ui-tab-mark-warp"
 
-         :class="[{ over: state.over }]"
 
-         :style="[{ left: state.markLeft + 'px' }, { width: state.markWidth + 'px' }]"
 
-       >
 
-         <view
 
-           class="ui-tab-mark"
 
-           :class="[props.mark, { 'ui-btn': props.tpl == 'btn' || props.tpl == 'subtitle' }]"
 
-         ></view>
 
-       </view>
 
-     </block>
 
-   </view>
 
- </template>
 
- <script>
 
-   export default {
 
-     name: 'SuTab',
 
-   };
 
- </script>
 
- <script setup>
 
-   /**
 
-    * 基础组件 - suTab
 
-    */
 
-   import {
 
-     toRef,
 
-     ref,
 
-     reactive,
 
-     unref,
 
-     onMounted,
 
-     nextTick,
 
-     getCurrentInstance,
 
-     provide,
 
-   } from 'vue';
 
-   const vm = getCurrentInstance();
 
-   // 数据
 
-   const state = reactive({
 
-     curValue: 0,
 
-     tabNodeList: [],
 
-     scrollLeft: 0,
 
-     markLeft: 0,
 
-     markWidth: 0,
 
-     content: {
 
-       width: 100,
 
-     },
 
-     over: false,
 
-   });
 
-   const tabRef = ref(null);
 
-   // 参数
 
-   const props = defineProps({
 
-     modelValue: {
 
-       type: Number,
 
-       default: 0,
 
-     },
 
-     ui: {
 
-       type: String,
 
-       default: '',
 
-     },
 
-     bg: {
 
-       type: String,
 
-       default: '',
 
-     },
 
-     tab: {
 
-       type: Array,
 
-       default() {
 
-         return [];
 
-       },
 
-     },
 
-     // line dot long,subtitle,trapezoid
 
-     tpl: {
 
-       type: String,
 
-       default: 'line',
 
-     },
 
-     mark: {
 
-       type: String,
 
-       default: '',
 
-     },
 
-     align: {
 
-       type: String,
 
-       default: '',
 
-     },
 
-     curColor: {
 
-       type: String,
 
-       default: 'ui-TC',
 
-     },
 
-     defaultColor: {
 
-       type: String,
 
-       default: 'ui-TC',
 
-     },
 
-     scroll: {
 
-       type: Boolean,
 
-       default: false,
 
-     },
 
-     inline: {
 
-       type: Boolean,
 
-       default: false,
 
-     },
 
-     titleStyle: {
 
-       type: Object,
 
-       default: () => ({
 
-         activeBg: '#DA2B10',
 
-         activeColor: '#FEFEFE',
 
-         color: '#D70000',
 
-       }),
 
-     },
 
-     subtitleStyle: {
 
-       type: Object,
 
-       default: () => ({
 
-         activeColor: '#333',
 
-         color: '#C42222',
 
-       }),
 
-     },
 
-   });
 
-   const emits = defineEmits(['update:modelValue', 'change']);
 
-   onMounted(() => {
 
-     state.curValue = props.modelValue;
 
-     setCurValue(props.modelValue);
 
-     nextTick(() => {
 
-       computedQuery();
 
-     });
 
-     uni.onWindowResize((res) => {
 
-       computedQuery();
 
-     });
 
-   });
 
-   const computedQuery = () => {
 
-     uni.createSelectorQuery()
 
-       .in(vm)
 
-       .select('#tab-' + vm.uid)
 
-       .boundingClientRect((data) => {
 
-         if (data != null) {
 
-           if (data.left == 0 && data.right == 0) {
 
-             // setTimeout(() => {
 
-             computedQuery();
 
-             // }, 300);
 
-           } else {
 
-             state.content = data;
 
-             setTimeout(() => {
 
-               state.over = true;
 
-             }, 300);
 
-           }
 
-         } else {
 
-           console.log('tab-' + vm.uid + ' data error');
 
-         }
 
-       })
 
-       .exec();
 
-   };
 
-   const setCurValue = (value) => {
 
-     if (value == state.curValue) return;
 
-     state.curValue = value;
 
-     computedMark();
 
-   };
 
-   const click = (index, item) => {
 
-     setCurValue(index);
 
-     emits('update:modelValue', index);
 
-     emits('change', {
 
-       index: index,
 
-       data: item,
 
-     });
 
-   };
 
-   const upitem = (index, e) => {
 
-     state.tabNodeList[index] = e;
 
-     if (index == state.curValue) {
 
-       computedMark();
 
-     }
 
-   };
 
-   const computedMark = () => {
 
-     if (state.tabNodeList.length == 0) return;
 
-     let left = 0;
 
-     let list = unref(state.tabNodeList);
 
-     let cur = state.curValue;
 
-     state.markLeft = list[cur].left - state.content.left;
 
-     state.markWidth = list[cur].width;
 
-   };
 
-   const computedScroll = () => {
 
-     if (state.curValue == 0 || state.curValue == state.tabNodeList.length - 1) {
 
-       return false;
 
-     }
 
-     let i = 0;
 
-     let left = 0;
 
-     let list = state.tabNodeList;
 
-     for (i in list) {
 
-       if (i == state.curValue && i != 0) {
 
-         left = left - list[i - 1].width;
 
-         break;
 
-       }
 
-       left = left + list[i].width;
 
-     }
 
-     state.scrollLeft = left;
 
-   };
 
-   provide('suTabProvide', {
 
-     props,
 
-     curValue: toRef(state, 'curValue'),
 
-   });
 
- </script>
 
- <style lang="scss">
 
-   .ui-tab {
 
-     position: relative;
 
-     display: flex;
 
-     height: 4em;
 
-     align-items: center;
 
-     &.ui-tab-scrolls {
 
-       width: 100%;
 
-       /* #ifdef MP-WEIXIN */
 
-       padding-bottom: 10px;
 
-       /* #endif */
 
-       .ui-tab-scroll-warp {
 
-         overflow: hidden;
 
-         height: inherit;
 
-         width: 100%;
 
-         .ui-tab-scroll {
 
-           position: relative;
 
-           display: block;
 
-           white-space: nowrap;
 
-           overflow: auto;
 
-           min-height: 4em;
 
-           line-height: 4em;
 
-           width: 100% !important;
 
-           .ui-tab-mark-warp {
 
-             display: flex;
 
-             align-items: top;
 
-             justify-content: center;
 
-             .ui-tab-mark.ui-btn {
 
-               /* #ifndef MP-WEIXIN */
 
-               height: 2em;
 
-               width: calc(100% - 0.6em);
 
-               margin-top: 4px;
 
-               /* #endif */
 
-               /* #ifdef MP-WEIXIN */
 
-               height: 2em;
 
-               width: calc(100% - 0.6em);
 
-               margin-top: 4px;
 
-               /* #endif */
 
-             }
 
-           }
 
-         }
 
-       }
 
-     }
 
-     .ui-tab-mark-warp {
 
-       color: inherit;
 
-       position: absolute;
 
-       top: 0;
 
-       height: 100%;
 
-       z-index: 0;
 
-       &.over {
 
-         transition: 0.3s;
 
-       }
 
-       .ui-tab-mark {
 
-         color: var(--ui-BG-Main);
 
-         height: 100%;
 
-       }
 
-     }
 
-     &.line {
 
-       .ui-tab-mark {
 
-         border-bottom: 2px solid currentColor;
 
-       }
 
-     }
 
-     &.topline {
 
-       .ui-tab-mark {
 
-         border-top: 2px solid currentColor;
 
-       }
 
-     }
 
-     &.dot {
 
-       .ui-tab-mark::after {
 
-         content: '';
 
-         width: 0.5em;
 
-         height: 0.5em;
 
-         background-color: currentColor;
 
-         border-radius: 50%;
 
-         display: block;
 
-         position: absolute;
 
-         bottom: 0.3em;
 
-         left: 0;
 
-         right: 0;
 
-         margin: auto;
 
-       }
 
-     }
 
-     &.long {
 
-       .ui-tab-mark::after {
 
-         content: '';
 
-         width: 2em;
 
-         height: 0.35em;
 
-         background-color: currentColor;
 
-         border-radius: 5em;
 
-         display: block;
 
-         position: absolute;
 
-         bottom: 0.3em;
 
-         left: 0;
 
-         right: 0;
 
-         margin: auto;
 
-       }
 
-     }
 
-     &.trapezoid {
 
-       .ui-tab-mark::after {
 
-         content: '';
 
-         width: calc(100% - 2em);
 
-         height: 0.35em;
 
-         background-color: currentColor;
 
-         border-radius: 5em 5em 0 0;
 
-         display: block;
 
-         position: absolute;
 
-         bottom: 0;
 
-         left: 0;
 
-         right: 0;
 
-         margin: auto;
 
-       }
 
-     }
 
-     &.btn {
 
-       .ui-tab-mark-warp {
 
-         display: flex;
 
-         align-items: center;
 
-         justify-content: center;
 
-         .ui-tab-mark.ui-btn {
 
-           height: calc(100% - 1.6em);
 
-           width: calc(100% - 0.6em);
 
-         }
 
-       }
 
-       &.sm .ui-tab-mark.ui-btn {
 
-         height: calc(100% - 2px);
 
-         width: calc(100% - 2px);
 
-         border-radius: #{$radius - 2};
 
-       }
 
-     }
 
-     &.subtitle {
 
-       .ui-tab-mark-warp {
 
-         display: flex;
 
-         align-items: top;
 
-         justify-content: center;
 
-         padding-top: 0.6em;
 
-         .ui-tab-mark.ui-btn {
 
-           height: calc(100% - 2.8em);
 
-           width: calc(100% - 0.6em);
 
-         }
 
-       }
 
-     }
 
-     &.ui-tab-inline {
 
-       display: inline-flex;
 
-       height: 3.5em;
 
-       &.ui-tab-scrolls {
 
-         .ui-tab-scroll {
 
-           height: calc(3.5em + 17px);
 
-           line-height: 3.5em;
 
-           .ui-tab-mark-warp {
 
-             height: 3.5em;
 
-           }
 
-         }
 
-       }
 
-       &.btn {
 
-         .ui-tab-mark-warp {
 
-           .ui-tab-mark.ui-btn {
 
-             height: calc(100% - 10px);
 
-             width: calc(100% - 10px);
 
-           }
 
-         }
 
-       }
 
-     }
 
-     &.sm {
 
-       height: 70rpx !important;
 
-       &.ui-tab-inline {
 
-         height: 70rpx;
 
-         &.ui-tab-scrolls {
 
-           .ui-tab-scroll {
 
-             height: calc(70rpx + 17px);
 
-             line-height: 70rpx;
 
-             .ui-tab-mark-warp {
 
-               height: 70rpx;
 
-             }
 
-           }
 
-         }
 
-         &.btn .ui-tab-mark.ui-btn {
 
-           height: calc(100% - 2px);
 
-           width: calc(100% - 2px);
 
-           border-radius: #{$radius - 2};
 
-         }
 
-       }
 
-     }
 
-   }
 
- </style>
 
 
  |