可触摸滑动具有回弹效果的Vue组件使用总结

发现一个很实用的vue组件,最近做项目遇到一种常见的需要,虽说常见但是自己没有试着写过,然后去网上找了一下。
需求图如下:下面的导航栏内容太多需要做成滑动的
可触摸滑动具有回弹效果的Vue组件使用总结_第1张图片
下面介绍一下我用到的这个组件:
git地址
根据操作引入组件即可,最终达成的效果如下动图所示。
可触摸滑动具有回弹效果的Vue组件使用总结_第2张图片
如果你有去尝试使用这个组件,发现真的是好用极了,不得不说开发这个组件的大佬真的是tql!!!
在试图的切换方面作者也是提供了两种思路:
1.使用Vue-router做router-view的切换
2.使用动态组件(可以配合异步组件使用)
这里我采用的第二种,原因是踩够了router-view的坑了(之前我做类似的导航切换的项目都是采用的router-view),换个坑踩踩,还有就是总觉得使用router-view需要配置一大堆路由,忒麻烦,而且涉及到浏览器回退的坑,so,果断选方案2。
代码:

<template>
    <div>
      <business-search
        :moduleName="refName"
        :isScreen="isScreen"
        @getSearch="getSearch"></business-search>
      <div>
        <ly-tab
          v-model="selectedId"
          :items="items"
          :options="options">
        </ly-tab>
      </div>
      <component :is="name" :ref="refName"/>
    </div>
</template>

<script>
    import BusinessSearch from "../components/businessSharing/BusinessSearch";
    export default {
      name: "businessSharing",
      components: {BusinessSearch},
      data() {
        return {
          isScreen:false,
          refName:'CreativeGroup',//默认值
          selectedId: 0,
          name:'',
          items: [
            {label: '创意施组',name:'CreativeGroup',isScreen:false},
            {label: '开标记录',name:'OpenRecord',isScreen:true},
            {label: '专家库',name:'ExpertBank',isScreen:false},
            {label: '材料价格',name:'MaterialPrice',isScreen:true},
            {label: '成本指导价',name:'CostGuidancePrice',isScreen:true}
          ],
          options: {
            activeColor: '#4f77aa'
            // 可在这里指定labelKey为你数据里文字对应的字段
          },
        }
      },
      created(){
        this.watchRouterFun(this.$route.path);
        let query = this.$route.query
        if(query.selectedId!=undefined){
          this.selectedId = parseInt(query.selectedId)
          localStorage.setItem(this.items[this.selectedId].name,query.form)
        }else {
          this.name = () => import('../components/businessSharing/CreativeGroup')//默认
        }
      },
      watch:{
        selectedId(newValue){
          this.name = () => import('../components/businessSharing/'+this.items[newValue].name)
          this.refName =this.items[newValue].name
          this.isScreen =this.items[newValue].isScreen
        },
        $route(to,from){
          this.watchRouterFun(to.path)
        }
      },
      methods:{
        getSearch(keyword){//接收公共search组件的keyword参数并触发相应子组件的搜索函数
          this.$refs[this.refName].getSearch(keyword);
        },
        lkFun(urlName){
          this.common.linkTo(this,urlName)
        },
        goBack(){
          // this.common.linkTo(this,'Personal')
        },
        watchRouterFun(path){
          if(path == '/Main/BusinessSharing'){
            this.$emit('selectedFun','BusinessSharing');
          }
        }
      }
    }

</script>

<style scoped lang="less">
</style>

监听组件的selectedId,切换导航的时候通过改变中的name来达到切换视图的效果,
记得created的时候加载默认的视图组件。


更新 2019.8.15
今天做项目的时候发现一个问题,之前做的导航,如果点进详情的话,返回列表,又会返回到默认的导航去,这样对用户不太友好,尤其是当用户点击某一导航,翻了很多页的时候,进入详情,再返回该页面,就又跑到第一页去了。就像下图这种情况:
可触摸滑动具有回弹效果的Vue组件使用总结_第3张图片
这个时候,配置一下路由设置meta:{keepAlive:true}即可缓存该页面。
既然都配置路由了,这里还是推荐使用router-view,百度了才发现router-view可以脱离router-link单独使用,还是没仔细看文档啊。
router-view写法

<template>
  <div>
    <data-searchbar @getSearch="searchFun"></data-searchbar>
    <div class="tabWrap">
      <ly-tab
        v-model="selectedId"
        @change="handleChange"
        :items="items"
        :options="options">
      </ly-tab>
    </div>
    <router-view :name="refName" :ref="refName"></router-view>
  </div>
</template>
<script>
    import DataSearchbar from "./DataSearch/DataSearchbar";
    export default {
      name: "DataSearch",
      components: {DataSearchbar},
      data(){
          return{
            routerName:'',
            refName:'Enterprisearch',//默认值
            selectedId: 0,
            id:'',
            items: [],
            options: {
              labelKey:'name',
              activeColor: '#4f77aa'
              // 可在这里指定labelKey为你数据里文字对应的字段
            },
          }
        },
      watch:{
        selectedId(newValue){
          this.refName =this.items[newValue].id
          this.isScreen =this.items[newValue].isScreen
        }
      },
      created(){
        if(localStorage.getItem('allNavTabs')){
          let allTabs = JSON.parse(localStorage.getItem('allNavTabs'))
          allTabs.forEach((v,i)=>{
            if(v.id=='Service'){
              let arr =v.children[1].children
              this.items =[]
              arr.forEach((val,idx) => {
                if(val.active){
                  this.items.push(val)
                }
              })
              console.log(this.items)
            }
          })
        };
      },
      methods:{
        handleChange(item,index){
          console.log(item,index)
        },
        searchFun(keyword){
          console.log(keyword)
          this.$refs[this.refName].getSearch(keyword);
        }
      }
    }
</script>

路由配置

{ path: '/DataSearch', name: 'DataSearch', component: DataSearch,redirect:{name:'Enterprisearch'},
      children:[
        { path: '/Enterprisearch', name: 'Enterprisearch',
          components:{default:Enterprisearch,//注意这里是components
            'Enterprisearch':Enterprisearch,
            'Persearch':Persearch,
            'Performsearch':Performsearch,
            'Financialstate':Financialstate,
            'Legalproce':Legalproce,
            'Prizesearch':Prizesearch},
          meta:{keepAlive:true}},
      ]}

两种方式都能实现下面的效果
可触摸滑动具有回弹效果的Vue组件使用总结_第4张图片
路由配置参考链接https://www.jianshu.com/p/92f61bf9db81

你可能感兴趣的:(vue)