这些vue技巧,你值得拥有

分享我在vue开发中积累的开发技巧总结,有些会结合使用环境或者是个人我的网站(www.cooldream.fun/home)中的使用实例来讲明,毕竟光有技巧也要考虑结合使用环境,这才能作到对于学习状态的加深印象以及实际使用的事半功倍,话很少说,我是想到啥写到啥,不要由于有些可能有点low或者用的很少就看一半就关了,但愿你可以耐心看完,多多少少确定对你仍是有点帮助的,最后,也但愿阅读个人这篇博客能给我一个点赞,大家的赞是我更新的最大动力!

1.动态组件 <component :is='组件名'></component>

结合v-for循环使用

  • 使用环境javascript

    如图,这是一个v-for渲染的列表(只是目前这个版块才刚开始作,目前只有一个),圆圈内的就是一个组件,也就是要v-for动态组件 css

  • 实际使用html

一开始就是基本的组件引入了vue

import ColorIn from '@/components/Magic/ColorIn.vue'
import LineIn from "@/components/Magic/LineIn.vue";
import LineIn from "@/components/Magic/Header.vue";
import LineIn from "@/components/Magic/Footer.vue";

export default{
      components:{
        ColorIn,
        LineIn,
        Header,
        Footer
    }
}
复制代码

接下来就是动态v-for动态组件的使用,componentList:['ColorIn','LineIn','Header','Footer']使用下面的代码便可将代码依次循环java

<component v-for="(item,index) in componentList" :key="index" :is="item"></component>
复制代码

编译之后的效果就是ios

<ColorIn></ColorIn>
<LineIn></LineIn>
<Header></Header>
<Footer></Footer>
复制代码

2.watch进阶使用

当即执行

  • 使用环境

例如场景为页面一进来就调用拉取列表数据getList(),而后监听路由的$route.query.id而后触发列表数据的更新vuex

  • 实际使用

为了让它一开始就执行,咱们须要在created()生命周期中执行一次拉取数据的方法npm

watch:{
    '$route.query.id':{
        handle(){
            this.getList();
        },
    }
},
created(){
    this.getList();
},
复制代码

可是使用immediate便可当即执行,改写之后的代码以下json

watch:{
    '$route.query.id':{
        handle(){
          this.getList();
        },
        immediate:true
    }
},
复制代码

深度监听

  • 使用环境

在监听对象的时候,对象的内部属性发生变化watch没法监听到,这种时候就须要使用深度监听,详情请看个人这一篇博客Vue由浅入深系列(二)详解Watch侦听器axios

  • 实际使用

只须要设置deep:true便可开启深度监听

data(){
    return{
        queryList:{
            count:0,
            name:'',
        }
    }
},
watch:{
    queryList(newValue,oldValue){
        //do something
    }
},
复制代码

计算属性之setter

data(){
    return{
        firstName:'',
        lastName:'',
    }
},
computed:{
    fullName:{
        get(){
            return `${this.firstName} ${this.lastName}`;
        },
        set(newValue){
            let names=newValue.split(' ');
            this.firstName=names[0];
            this.lastName=names[1];
        }
    }
},
复制代码

$on('hook:生命周期')来简化window监听

  • 实际使用

先来看一下日常的使用方法

mounted () {
    window.addEventListener('resize', this.resizeHandler);
},
beforeDestroy () {
    window.removeEventListener('resize', this.resizeHandler);
}
复制代码

改写之后的代码为,相比于上面的写法,这个写法的好处在于能够开启一个事件监听器的同时,就在beforeDestroy生命周期中挂载一个删除事件监听器的事件。比上面的写法会更加安全,更加有助于避免内存泄露并防止事件冲突

mounted () {
  window.addEventListener('resize', this.resizeHandler);
  this.$on("hook:beforeDestroy", () => {
    window.removeEventListener('resize', this.resizeHandler);
  })
}
复制代码

子组件@hook:生命周期监听子组件的生命周期回调

  • 实际使用
<child @hook:mounted="listenChildMounted" />
复制代码

v-pre

  • 使用环境

不须要编译的html代码可使用v-pre,能够提升性能

  • 实际使用
<span v-pre>{{message}}</span>    //就算data里面定义了message,渲染完也是{{message}}
复制代码

v-once

  • 使用环境

只须要渲染一次,适用于渲染完之后就不会更新的内容,下降性能开销

  • 实际使用
<span v-once>{{message}}</span>    //message的值会编译后渲染,可是编译之后再次修改message的值不会触发更新
复制代码
  • v-pre与v-once的区别

v-pre至关于不编译,直接显示,v-once至关于只编译一次,后面的更新不编译了

Vue.set()

  • 使用环境

当你利用索引直接设置一个数组项时或你修改数组的长度时,因为Object.defineprototype()方法限制,数据不响应式更新

  • 实际使用
this.$set(arr,index,item);
复制代码

keep-alive

  • 使用环境

当这个页面没有数据更新,或者是想保存状态,下次进来仍是这样子的时候,例如淘宝查看列表页,点进去查看详情以后,返回列表页依旧到上次浏览到的地方,均可以使用keep-alive

$route路由信息

  • $route.query.id

用来拿取路由传值的信息,好比路由的后缀?id=1,$route.query.id拿到的值为1

  • $route.meta.flag

用来拿取路由meta中的信息,路由信息里的meta是能够自定义属性的,我通常导航栏当前选中的nav用来和$route.meta.flag进行匹配,来拿到当前页面应该激活哪个选项卡

  • base路由

比方说百度的全部路由前缀要加/baidu,那么能够设置路由的base为/baidu

export const router = new Router({
  base:'/baidu/',
}
复制代码

此外,打包的时候,请修改config/index.jsbuild块中的assetsPublicPath为 '/baidu/',否则打包之后是找不到资源文件路径的

module.exports = {
    build:{
        assetsPublicPath: '/baidu/',
    }
}
复制代码
  • 全局路由钩子

使用场景通常为用户的登陆鉴权

router.beforeEach((to, from, next) => {
  //必定要调用next()才能到下一个页面
  if (path === '/login') {
    next()
  }else{
    if(token){
      next();
    }else{
      next('/login');
    }  
  }
})
复制代码
  • 组件路由钩子中访问this

组件路由的钩子一开始还未初始化,不能访问到vue实例 beforeRouteEnter (to, from, next) { // 这里还没法访问到组件实例,this === undefined next( vm => { // 经过 vm 访问组件实例 }) }

样式穿透

  • 使用环境

通常在修改插件样式的时候使用的比较多

  • 实际使用

分为两种,通常stylus中使用>>>less中使用/deep/sass没有使用经验,不予说明

>>>.el-dialog .el-dialog__body{
  padding 0
  text-align center
  border-radius 0 0 4px 4px
}
/deep/.el-dialog .el-dialog__body{
  padding 0
  text-align center
  border-radius 0 0 4px 4px
}
复制代码

Object.freeze()

  • 使用环境

咱们都知道vue是使用Object.defineProperty对数据进行双向绑定,而对于只作展现使用的长列表,可使用Object.freeze()进行冻结,使它没法被修改,从而提升性能

  • 实际使用
getList().then(res=>{
    this.list=Object.freeze(res.data.result);
})
复制代码

值得注意的是,改变list的值不会更新,但改变引用会触发更新

组件通讯技巧

  • props
  • $emit
  • $attrs & $listeners
  • provide & inject
  • vuex
  • Observable
  • eventBus
  • $refs
  • slot-scope & v-slot
  • scopedSlots
  • $parent & $children & $root

详细使用能够查看个人这一篇博客一篇文章看懂Vue.js的11种传值通讯方式

mixins混入的使用

  • 使用环境

通常获取验证码,收藏,点赞等公用且逻辑同样(有些逻辑是根据页面的不一样而不一样的不建议使用混入)等场景均可以使用混入

  • 实际使用

这里我直接封装了一个vue新开窗口的混入方法,引入了之后,混入中的全部data,methods,以及生命周期都会共享

//openWindow.js
export default {
  methods:{
    openUrl(url){
      const link= this.$router.resolve({path: url});
      window.open(link.href,'_blank');
    },
  }
}

//其余页面使用
import openWindow from "../../mixins/openWindow";

export default{
    mixins:[openWindow],
}
复制代码
  • 注意点(使用的页面统称为组件)

① 混入比组件优先执行

② 当混入中的属性或者方法与组件中的属性或者方法名称相同时,以组件中的值为准(结合上一条规则,由于混入先执行,因此组件会将混入覆盖)

③ 比方说A页面和B页面都使用了同一个混入,A页面与B页面的状态一样是独立的

qs

  • 使用场景,get传输的时候都是路由拼接方式(?a=1&b=2),而不是json方式

  • 实际使用

//安装依赖
npm install qs --save

//页面中或者直接api.js中直接序列化使用
import qs from 'qs'
qs.stringify(params)

//axios拦截器中直接使用
import qs from 'qs'
axios.interceptors.request.use(
  config => {
    if (config.method === 'get') {
      config.data = qs.stringify(config.data)
    }
)
复制代码

v-for绑定key不建议使用index,建议使用另外的而且值惟一的变量,例如后台给你的id

  • 主要缘由

有的时候v-for列表可能存有删除,交换位置等操做,这种时候index的顺序变换会致使同一条数据,在此刻的index置换,因此,不建议v-for的key绑定index

v-for不建议配合v-if

  • 主要缘由

v-for的优先级比v-if高,也就是说,假设总计50条数据,即便通过v-if之后,只剩下25条显示,可是v-for早就循环了一遍50条数据,解决办法就是用一个计算属性先将数据过滤了之后,v-for循环过滤了以后的数据

document.body.contentEditable

  • 操做方法

打开控制台,输入document.body.contentEditable=true,而后敲回车,网页能够像word同样编辑,很方便对于页面的布局抗压能力作测试