vue2自封装一个锚点导航栏组件

232 阅读1分钟

组件页面

<template>
  <div :class="{'nav-active':isShowPopper}" class="nav-wrapper">
    <slot name='aaa'></slot>
    <el-popover v-model="isShowPopper" :offset="10" :visible-arrow="false" placement="left" popper-class="nav-popper"
                trigger="hover" v-bind="$attrs" width="100" v-on="$listeners">
      <div class="nav-inner">
        <template v-for="(item,index) in navConfigList">
          <div :key="item.id" :class="{active:activeIndex===index}" class="nav-item"
               @click="handleNavItemClick(item,index)">
            <span class="nav-item__index">{{ index + 1 }}</span>
            <span class="nav-item__name">{{ item.name }}</span>
          </div>
        </template>
      </div>
      <div slot="reference" class="nav-button el-button--primary">
      </div>
    </el-popover>
  </div>
</template>

<script>
export default {
  name: "NcNav",
  props: {
    navConfigList: {
      type: Array,
      default: () => []
    }
  },
  data() {
    return {
      activeIndex: 0,
      isShowPopper: false
    };
  },
  methods: {
    handleNavItemClick(item, index) {
      this.activeIndex = index;
      document.getElementById(elementId:`${item.id}`).scrollIntoView(arg:{
        behavior: "smooth"
      });
    }
  }
};
</script>

<style>
.nav-popper {
  padding: 16px 0 !important;
  margin: 0 !important;
}

.nav-popper::after {
  bottom: 0;
}

.nav-popper::before {
  top: 0;
}

.nav-popper::after,
.nav-popper::before {
  content: "";
  position: absolute;
  left: -6px;
  width: 6px;
  height: 6px;
  background-color: white;
  border: 2px solid #d1d1d1;
  border-radius: 6px;
  box-sizing: content-box;
}
</style>
<style lang="less" scoped>
.nav-button {
  width: 24px;
  height: 62px;
  cursor: pointer;
  background: url(~@/assets/img/navbar-left.png) no-repeat;
}

.nav-wrapper {
  position: sticky;
  top: 130px;
  z-index: 99;
  margin-left: calc(100% - 7px);
  transform: translateX(-12px);

  &:hover {
    .nav-button {
      background: url(~@/assets/img/navbar-right.png) no-repeat;
    }
  }
}

.nav-active .nav-button {
  background: url(~@/assets/img/navbar-right.png) no-repeat !important;
}

.nav-inner {
  .nav-item {
    position: relative;
    padding-left: 20px;
    margin-bottom: 7px;
    font-size: 14px;
    color: #000;
    display: flex;
    align-items: center;
    cursor: pointer;

    &:hover {
      background-color: #f5f5f5;
      box-shadow: 1px 1px #d1d1d1;
    }

    &:before {
      content: "";
      box-sizing: content-box;
      position: absolute;
      top: 5px;
      left: -6px;
      width: 6px;
      height: 6px;
      background-color: #d1d1d1;
      border: 2px solid white;
      border-radius: 6px;
      font-size: 48px;
      font-weight: normal;
    }

    .nav-item__name {
      padding-left: 10px;
    }
  }

  .active:before {
    background: url("~@/assets/img/navbar_slider.png");
    left: -7px !important;
    width: 18px !important;
    height: 12px !important;
    top: 2px !important;
  }
}
</style>

如何使用

<NcNav :navConfigList="navConfigList"/>


<div :id="item.id" />

data() {
  return {
    navConfigList: [
      {
        name: "基本信息",
        id: "first"
      },
      {
        name: "专业信息",
        id: "second"
      },
      {
        name: "业绩信息",
        id: "third"
      },
      {
        name: "履历信息",
        id: "fourth"
      },
      {
        name: "个人荣誉",
        id: "fifth"
      },
      {
        name: "发布信息",
        id: "sixth"
      }
    ],
    
    
    }
    }