Vue2 - 23-03-22 自定义v-fbind指令 如果要写一个一上来就能够自动获取焦点的指令,就会涉及到插入页面, 但是默认函数式写法只包括元素与指令绑定时和模板重新解析时
此时就需要时候对象式写法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 <button @click="n++">点我n+1</button> <hr> <input type="text" v-fbind:value="n"> fbind:{ bind(element, binding){ element.value = binding.value; }, inserted(element, binding){ element.focus(); }, update(element, binding){ element.value = binding.value } }
回顾DOM操作顺序
自定义指令容易踩的坑 指令名称多个单词组成 1 2 3 4 5 6 <h2>放大十倍后的n值是<span v-big-number="n"></span></h2> 'big-number'(element, binding){ element.innerText = binding.value*10 }
自定指令的this 指令里面的this都是Windows,需要什么属性通过binding传
定义全局指令 做法与全局过滤器类似
1 2 3 4 5 <h2>放大十倍后的n值是<span v-bigg="n"></span></h2> //定义全局指令 Vue.directive('bigg',function(element, binding){ element.innerText = binding.value*10 });
总结自定义指令
Vue生命周期
生命周期又名生命周期回调函数、生命周期函数、生命周期钩子
是什么:Vue在关键时刻帮我们调用的一些特殊名称的函数
生命周期函数的名字不可更改,但函数的具体内容是程序员根据需求编写的
生命周期函数中的 this 指向是vm或组件实例对象
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 beforeCreate(){ // 生成数据代理前 console.log("beforeCreate"); }, created(){ // 生成数据代理后 console.log("created"); }, beforeMount() { // 虚拟dom覆盖原来dom之前 console.log("beforeMount"); }, mounted(){ // 虚拟dom覆盖原来dom之后 console.log("mounted"); console.log(this.$el); }, beforeUpdate(){ // 数据已经变了,页面更新前 console.log("beforeUpdate"); }, updated(){ // 数据页面同步 console.log("updated"); }, beforeDestroy(){ // 收尾 console.log("beforedestroy"); }, destroyed(){ //对页面残留结果进行操作 console.log("destroyed"); }
生命周期总结
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>总结生命周期</title> <script src="../resources/js/vue.js"></script> </head> <body> <div id="root"> <h2 :style="{opacity}">欢迎学习Vue</h2> <button @click="opacity = 1">透明度变为1</button> <button @click="stop">停止变换</button> </div> <script type="text/javascript"> Vue.config.productionTip = false; const vm = new Vue({ el: '#root', data:{ opacity:1 }, methods:{ stop(){ this.$destroy(); } }, mounted(){ //开发中常用的给当前实例追加属性 this.timer = setInterval(()=>{ this.opacity-=0.01; // if(this.opacity==0) this.opacity=1 js没办法与零比较 if(this.opacity<=0) this.opacity=1 },16) }, beforeDestroy(){ clearInterval(this.timer) } }) </script> </body> </html>
模块化与组件化
模块化 是指将js文件进行拆分组件化 是指一系列代码和资源的集合
组件的基本使用
创建组件(一般包括data、template)
注册组件
使用组件标签
为什么要将data的data写成函数式? 1 2 3 4 5 6 7 8 9 10 11 12 13 let data = {a: 1, b: 2} const d1 = data; const d2 = data; d1.a = 10; console.log(d2)//returns {a: 10, b: 2} ----- let data(){ return {a: 1, b: 2} } const d1 = data; const d2 = data; d1.a = 10; console.log()//returns {a: 1, b: 2}
全局组件 全局组件要放在最开头处,否则容易未被解析出现错误
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 // 全局组件 // 创建组件 const test = Vue.extend({ template:` <div> <h2>{{test}}</h2> </div> `, data(){ return { test:'test successfully! ' } }, }) // 全局注册组件 Vue.component('test',test);
局部组件 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 // 注册局部组件 //第一步:创建组件 const school = Vue.extend({ template:` <div> <h2>学校名称:{{schoolName}}</h2> <h2>学校地址:{{address}}</h2> </div> `, // 只能写成函数式 data(){ return { schoolName: 'gdip', address:'foshan' } } }) const student = Vue.extend({ template:` <div> <h2>学生姓名:{{studentName}}</h2> <h2>学生年龄:{{age}}</h2> <test></test> </div>`, data(){ return { studentName:'linzepore', age:20 } } }) //第二步:创建vm,注册组件 new Vue({ el:'#root', data:{ hello:'hello' }, components:{ school: school, // student: student student } })
组件的使用 1 2 3 4 5 6 7 8 <div id="root"> <!-- 第三步:编写组件标签 --> <h1>{{hello}}</h1> <school></school> <hr> <student></student> <test></test> </div>
组件标签名称大小写
注册组件名称写成以-连接会自动形成大写(如'my-school':school
)
注册的时候用的什么名字,使用标签就要用什么名字;如果组件定义了名字,开发者工具会随之变化,但是使用标签时候还是要用注册的名字
创建组件的时候可以先不写Vue.extend,直接写成对象的形式,注册的时候Vue会进行调用
组件的嵌套以及书写规范 详见->第57集
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 <div id="root"></div> //定义student组件 const student = Vue.extend({ //定义school组件,嵌套了student const school = Vue.extend({ template:` <div> <h2>学校名称:{{schoolname}}</h2> <h2>学校地址: {{address}}</h2> <student></student> </div> `, data(){ return { schoolname:'gdip', address:'foshan' } }, components:{ student } }) //定义了hello组件,与school平级 const hello = Vue.extend({ template:` <h2>欢迎来到Linzepore的博客</h2> ` }) const app = Vue.extend({ template:` <div> <hello></hello> <school></school> </div> `, components:{ hello, school } }) new Vue({ template:`<app></app>`, el: '#root', components:{ app } })
一个bug————忘记把标签包裹成为一个根标签 Vue报错:[Vue warn]: Error compiling template: Component template should contain exactly one root element. If you are using v-if on multiple elements, use v-else-if to chain them instead.