vue router动态路由下让每个子路由都是独立组件的解决方案


Posted in Javascript onApril 24, 2018

vue-router 之动态路由

vue-router官网上面是这样说的
// 带查询参数,变成 /register?plan=private
router.push({ path: 'register', query: { plan: 'private' }})
然后,我就这样写了:
this.$router.push({path:'manage', query: {id: 'tasklist'}})1
结果很明显,失败了。然后我就默默的再次看了一下官网,结果发现了这句话
// 命名的路由
router.push({ name: 'user', params: { userId: 123 }})
// 带查询参数,变成 /register?plan=private
router.push({ path: 'register', params: { plan: 'private' }})
注意:如果提供了 path,params 会被忽略,上述例子中的 query 并不属于这种情况。取而代之的是下面例子的做法,你需要提供路由的 name 或手写完整的带有参数的 path:
const userId = 123
router.push({ name: 'user', params: { userId }}) // -> /user/123
router.push({ path: `/user/${userId}` }) // -> /user/123
// 这里的 params 不生效
router.push({ path: '/user', params: { userId }}) // -> /user
谨记啊,动态实现二级路由,需要先用变量保存二级路由名称(let router = 'tasklist'),然后调用this.$router.push({path: `/user/${router}`}).

下面看下vue router动态路由下让每个子路由都是独立组件的解决方案

因为 vue-router 对嵌套路由采用的是组件复用策略,这在大部分场景的确是高效的做法,但是如果遇到这种情况:

vue router动态路由下让每个子路由都是独立组件的解决方案

就是要求多个子路由共活,并且有频繁来回切换需求的话,就很希望能让每个子路由都是独立组件了,虽然可以通过监听路由切换

watch: {
   '$route'(to) {
    if (to.meta.path === '/page/buy-details') {
     this.id = to.params.id;
     this.state()
    }
   }
  },

去实时处理更新的数据,我之前一直都是这么做的,包括上面那副动图的页面,但是这真的很麻烦,要让用户切换中准确的回到切换前页面的显示状态,要考虑的东西太多,于是想出了一个解决方案:

子路由组件不涉及实际业务代码,只维护一个打开过的id列表,路由切换到这边时,判断id,没打开过的添加,通过这个列表循环出实际的子路由组件,v-show当前id的,这样就能实现每个实例都是独立的了
我按这个思路写出一个 mixins

details-page.js

export default {
 watch: {
  '$route'(to, from) {
   this.detailsLeave(from);
   this.detailsOpen(to);
  }
 },
 data() {
  return {
   pagePath: '',
   pageId: 0,
   pages: {}
  }
 },
 methods: {
  /**
   * 子页面打开触发
   * @param route
   */
  detailsOpen(route) {
   if (this.detailsPathGet(route.path) === this.pagePath) {
    if (!this.pages[route.params.id]) {
     this.$set(this.pages, route.params.id, {
      id: route.params.id,
      scrollTop: 0
     })
    }
    //路由打开 跳转滚动条
    this.pageId = route.params.id;
    this.$nextTick(()=>{
     this.$parent.$el.firstChild.scrollTop = this.pages[route.params.id].scrollTop;
    });
   }
  },
  /**
   * 路由切换触发
   * 判断离开的路由是否是当前页面,如果是则记录滚动条高度
   * @param route
   */
  detailsLeave(route) {
   if (this.detailsPathGet(route.path) === this.pagePath) {
    if (this.pages[route.params.id]) {
     //记录滚动条高度 此处针对ea-admin后台 不同的框架要记录的滚动条el不同
     this.pages[route.params.id].scrollTop = this.$parent.$el.firstChild.scrollTop ;
    }
   }
  },
  /**
   * 子页面关闭函数
   * @param id
   */
  detailsClose(id) {
   delete this.pages[id]
  },
  /**
   * 取路由不含最后一项参数的地址
   * @param path
   * @returns {string}
   */
  detailsPathGet(path) {
   const i = path.lastIndexOf('/');
   return path.substr(0, i);
  }
 },
 mounted() {
  //通过当前路由地址创建页面识别地址 注:只对path: '/user/:id' 有效 当 path: /user/:id/profile 失效
  this.pagePath = this.detailsPathGet(this.$route.path);
  //执行第一次子页面打开
  this.detailsOpen(this.$route);
  //监听标签关闭消息 此处针对ea-admin后台 不同框架监听关闭方式不同
  this.$tabs.onRemove((page, next) => {
   //收到标签关闭回调,判断关闭的是否是当前页面
   if (page._path === this.pagePath) {
    //触发子页面删除
    this.detailsClose(page.id)
   }
   next()
  })
 }
}

Details.vue

<template>
 <div>
  <your-component
    v-for="item in pages"
    :id="item.id"
    :key="item.id"
    v-show="item.id === pageId">
  </your-component>
 </div>
</template>
<script>
 import YourComponent from '';
 import detailsPage from '../mixins/details-page'
 export default {
  name: 'DetailsPage',
  components: {YourComponent},
  mixins: [detailsPage],
 }
</script>

这样子组件可以只专注处理自己的固定数据,因为组件唯一,不用再去烦恼为每个id存储视图状态了。

总结

以上所述是小编给大家介绍的vue router动态路由下让每个子路由都是独立组件的解决方案,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
记录几个javascript有关的小细节
Apr 02 Javascript
javascript小组件 原生table排序表格脚本(兼容ie firefox opera chrome)
Jul 25 Javascript
JavaScript定义类的几种方式总结
Jan 06 Javascript
jquery提交form表单时禁止重复提交的方法
Feb 13 Javascript
用javascript关闭本窗口技巧小结
Sep 05 Javascript
Javascript表单验证要注意的事项
Sep 29 Javascript
jQuery实现鼠标经过事件的延时处理效果
Aug 20 Javascript
js学习阶段总结(必看篇)
Jun 16 Javascript
jquery中done和then的区别(详解)
Dec 19 jQuery
使用angularjs.foreach时return的问题解决
Sep 30 Javascript
vue transition 在子组件中失效的解决
Nov 12 Javascript
jQuery弹框插件使用方法详解
May 26 jQuery
vue+webpack实现异步加载三种用法示例详解
Apr 24 #Javascript
vue中$refs的用法及作用详解
Apr 24 #Javascript
vue实现选项卡及选项卡切换效果
Apr 24 #Javascript
Vue手把手教你撸一个 beforeEnter 钩子函数
Apr 24 #Javascript
js 图片转base64的方式(两种)
Apr 24 #Javascript
react配合antd组件实现的管理系统示例代码
Apr 24 #Javascript
详解开发react应用最好用的脚手架 create-react-app
Apr 24 #Javascript
You might like
比较全的PHP 会话(session 时间设定)使用入门代码
2008/06/05 PHP
php ci框架验证码实例分析
2013/06/26 PHP
根据中文裁减字符串函数的php代码
2013/12/03 PHP
浅谈php扩展imagick
2014/06/02 PHP
php实现读取超大文件的方法
2014/07/28 PHP
用PHP写的一个冒泡排序法的函数简单实例
2016/05/26 PHP
ymPrompt的doHandler方法来实现获取子窗口返回值的方法
2010/06/25 Javascript
JavaScript 原型链学习总结
2010/10/29 Javascript
打开新窗口关闭当前页面不弹出关闭提示js代码
2013/03/18 Javascript
JavaScript等比例缩放图片控制超出范围的图片
2013/08/06 Javascript
如何在父窗口中得知window.open()出的子窗口关闭事件
2013/10/15 Javascript
jsPDF生成pdf后在网页展示实例
2014/01/16 Javascript
JavaScript中的document.referrer在各种浏览器测试结果
2014/07/18 Javascript
JavaScript charCodeAt方法入门实例(用于取得指定位置字符的Unicode编码)
2014/10/17 Javascript
利用jquery制作滚动到指定位置触发动画
2016/03/26 Javascript
jQuery事件详解
2017/02/23 Javascript
node.js+express+mySQL+ejs+bootstrop实现网站登录注册功能
2018/01/12 Javascript
详解使用create-react-app快速构建React开发环境
2018/05/16 Javascript
nodejs express配置自签名https服务器的方法
2018/05/22 NodeJs
一个Vue页面的内存泄露分析详解
2018/06/25 Javascript
vue debug 二种方法
2018/09/16 Javascript
vue中使用protobuf的过程记录
2018/10/26 Javascript
微信小程序中的店铺评分组件及vue中用svg实现的评分显示组件
2018/11/16 Javascript
Vue实现购物车详情页面的方法
2019/08/20 Javascript
vue+element-ui+axios实现图片上传
2019/08/20 Javascript
javascript设计模式 ? 组合模式原理与应用实例分析
2020/04/14 Javascript
vue的$http的get请求要加上params操作
2020/11/12 Javascript
Python中使用装饰器时需要注意的一些问题
2015/05/11 Python
Python实现时钟显示效果思路详解
2018/04/11 Python
Django数据库连接丢失问题的解决方法
2018/12/29 Python
django中cookiecutter的使用教程
2020/12/03 Python
奥地利智能家居和智能生活网上商店:tink.at
2019/10/07 全球购物
渡河少年教学反思
2014/02/12 职场文书
淘宝客服工作职责
2014/07/11 职场文书
《多彩的民间艺术》教学反思
2016/02/16 职场文书
python基于scrapy爬取京东笔记本电脑数据并进行简单处理和分析
2021/04/14 Python