实现tab左右箭头切换及自适应

<template>
  <div>
    <div id="tab1" class="tab">
      <div :class="{scroll:scroll,container:1}">
        <div class="wrapper">
          <header :class="{flex:flex}" :style="{left:left+'px'}">
            <div v-for="(item,index) in tabs" :key="index" :class="{item:1,cur:index==curIndex}" @click="setCur(index,$event)">{{ item }}<b /></div>
            <div class="clear" />
          </header>
        </div>
        <a class="pre" @click="preNext(1)"><</a>
        <a class="next" @click="preNext(-1)">></a>
      </div>
      <div class="tabody">
        <div v-for="(item,index) in tabs" :key="index" :style="{display:index==curIndex?'block':'none'}">{{ item }}</div>
      </div>
    </div>
  </div>
</template>

<script>
export default {
  name: 'Test',
  components: {
  },
  data() {
    return {
      tabs: ['选项卡1', '选项卡2', '选项卡3', '选项卡4', '选项卡5', '选项卡6', '选项卡7', '选项卡8', '选项卡9'],
      curIndex: 0,
      flex: 0,
      scroll: 0,
      left: 0
    }
  },

  mounted() {
    var wrapper = this.$el.querySelector('.wrapper')
    if (wrapper.scrollHeight > wrapper.offsetHeight + 2) {
      var items = wrapper.querySelectorAll('.item')
      var w = 0
      for (var item of items) { item.setAttribute('left', w); w += item.offsetWidth }
      this.header = wrapper.querySelector('header').style.width = w + 'px'
      this.scroll = 1
      this.stepWidth = wrapper.clientWidth - 60
      this.maxLeft = this.stepWidth - w
    } else this.flex = 1
  },

  methods: {
    /* 获取列表数据 */
    setCur(index, e) {
      this.curIndex = index
      if (this.scroll) {
        var el = e.target; var left = parseInt(el.getAttribute('left'))
        this.isInView(left, left + el.offsetWidth)
      }
    },
    preNext(dir) {
      var left = this.left + dir * this.stepWidth
      if (left < this.maxLeft) left = this.maxLeft
      else if (left > 0)left = 0
      this.left = left
    },
    isInView(left, right) {
      var left1 = -1 * this.left; var right1 = -1 * (this.left - this.stepWidth)
      if (left < left1 || left > right1 || right < left1 || right > right1) {
        if (left < left1) this.left = -left + 2
        else this.left = -right + this.stepWidth
      }
    }
  }
}
</script>

<style lang="scss" scoped>
#tab1,#tab2{width:400px;margin:20px auto}
.tab{border:solid 1px #ccc;}
.container{border-bottom:solid 1px #ccc;background:#eee}
.wrapper{height:32px;}
.scroll{padding:0 30px;position:relative}
.scroll .wrapper{overflow:hidden;position:relative;margin-bottom:-1px}
.scroll header{width:999999px;position:absolute;transition:all 0.6s cubic-bezier(0.23,1,0.32,1);}
a.pre,a.next{display:none}
.scroll a.pre,.scroll a.next{position:absolute;left:8px;top:5px;cursor:pointer;background:#eee;display:block}
.scroll a.next{left:auto;right:8px}
.flex{display:flex;justify-content:center;width:auto}
header .item{padding:5px 15px;float:left;cursor:pointer;position:relative;user-select:none}
header .item b{display:none;height:0;border-bottom:solid 2px #fff;width:100%;left:0;bottom:-2px;position:absolute}
header .cur{background:#fff;border-left:solid 1px #ccc;border-right:solid 1px #ccc;color:#007bffb5;border-top-left-radius:5px;border-top-right-radius:5px;}
header .cur b{display:block}
.clear{clear:both}
.tabody{padding:10px}
</style>

  

posted @ 2022-04-29 15:42  李昂唐  阅读(682)  评论(0编辑  收藏  举报