vue生命周期和组件间传值

生命周期

new Vue() 初始化一些事件和生命周期 例如:vm.$on, vm.$once, vm.$emit
beforeCreate 初始化之前,会先把一些数据方法放在实例中,还没初始化完,不能操作数据,一般用不到
created 数据,方法初始化完成,可以操作数据,实现响应式绑定,此处一般ajax获取数据
必须有el属性(有编译的元素),才能进行挂载,只能有一个根元素,如果有template属性(内部html),app(外部html)中的内容就会被覆盖掉,就没有意义了
beforeMount 挂载之前,没有什么实际意义,会用vm.$el替换el
mounted 挂载完成,数据和模板挂载好了,真实DOM渲染完了,可以操作DOM
beforeUpdate 更新之前,页面依赖的数据有变化就会开始更新
updated 更新之后,一般用watch方法替代这两个方法
beforeDestory 销毁之前,开始移除一些定时器和事件绑定等操作,方法还没销毁,
destoryed 销毁完成

this.$data:vm上的数据
this.$watch:监控
this.$el:当前el元素
this.$set:后添加的属性实现响应式变化
this.$options:实例上的属性,包括内置的还有自定义的
this.$refs:所有ref的集合,带ref属性的标签,如果不是通过v-for循环出来的DOM元素,只能获取一个
this.$nextTick():异步方法,等待渲染完成后获取vm,数据变化后想获取真实dom,需要等待页面获取完成后再去获取,因此所有dom操作最好都放在this.$nextTick()

mounted(){
  // console.log(document.getElementsByTagName('p')[0].innerHTML);
  console.log(this.$refs.message);
  console.log(this.$refs.wrap);
  this.arr = [1,2,3,4,5]; // dom的渲染是异步的
  this.$nextTick(function () {
  // 数据变化后想获取真实dom,需要等待页面获取完成后再去获取
      console.log(this.$refs.wrap.children.length); // 5
   });
  console.log(this.$refs.wrap.children.length); // 3
}

组件化开发

组件化开发可以提高开发效率,方便重复利用,便与协同开发,更容易被管理和维护。一般根据功能可分为两种:
1、页面级组件,一个页面是一个组件
2、基础组件,将可复用的部分抽离出来
vue中,一个自定义标签就会被看成一个组件
根据用法划分:
全局组件:声明一次可以在任何地方使用,写插件的时候用的多
局部组件:必须要声明这个组件属于哪一部分
声明组件的时候,标签名不要大写,多个单词用- 组件名和定义的名字相同是可以的(首字母可以大写)
html中用-,JS中转驼峰也是可以的
组件中的data必须是函数类型的,返回一个实例作为组件中的数据





局部组件
局部组件使用的三部曲
1、创建组件
2、注册组件
3、引用组件
组件是相互独立的,不能直接跨作用域,vm这个实例也是一个组件,组件中拥有生命周期函数,如果组件共用了数据会导致同时更新,因此要求data必须是函数类型的。
子组件不能直接使用父组件的数据(组件间数据传递),组件理论上可以无限嵌套


组件间的嵌套:
1、被调用的子组件必须先定义,否则就拿不到。
2、哪里要用当前组件,就在哪里通过components注册,
3、需要在调用的组件中通过标签的形式引入
理论上是无限嵌套的,单位了好维护,一般最多嵌套3层

父组件给子组件传值:属性传递,:money=""是传值的,传了一个空值,所以不会用到default,不在子组件定义这个属性,这才算不传值
required: true:表示该值必须传递,不穿就发警告,不能与默认值default同时出现。
校验时不会阻断代码的执行,只会出现警告
还可以自己定义校验信息,用validator方法,里面的参数就是当前传递的值,返回true表示通过反之不通过。(用的8多)


parent: {{money}}

子组件给父组件传值:通过发布订阅的模式,父亲绑定一些事件,儿子触发这个事件,将参数传递过去,单向数据流 父组件数据刷新,子组件就刷新,不能子组件直接改父组件的值,要想这样,就需要子组件先通知父组件要修改值,父组件再去修改
在本例子中,子组件通过点击事件触发($emit)自己的child-msg方法,而该方法又触发了父组件的moreMoney方法执行,这样一来就实现了子组件向父组件传值


parent: {{money}}

sync语法糖的用法


same as

子父组件声明周期
父组件需要等到子组件挂载完成(mounted)之后才会触发挂载

mounted(){
    console.log(this.$refs.child.$el.innerHTML); 
    // 1 2 3
    // 因为存在DOM映射,所以页面上的数据实时变化,
    // 但是DOM渲染是个异步的过程,这里还新的数据还没有渲染完
    this.$nextTick(() => {
          console.log(this.$refs.child.$el.innerHTML); 
          // 4 5 6
    });
},

兄弟组件间相互通信
eventBus一般不用,了解,发布订阅模式失败的原因是因为在不同组件中的this是不一样的,组件2触发,组件1监听,显然是行不通的。发布订阅的执行者应该是同一个才能成功,因此就需要有一个第三方实例eventBus来实现交互。

let brother1 = {
        template: '
{{color}}
', data() { return {color: '绿色', old: '绿色'} }, created() { // 组件1监听 this.$on('changeRed', (val) => { // 页面一加载,组件1长一个耳朵来监听 this.color = val; }) } }; let brother2 = { template: '
{{color}}
', data() { return {color: '红色', old: '红色'} }, methods: { change() { // 组件2发布 this.$emit('changeRed', this.old); } } };

eventBus使用,创建一个Vue实例,在兄弟组件中发布订阅都用这个实例来操作即可,但是触发的方法名不能重复,否则就乱套了

let eventBus = new Vue();
eventBus.$on('changeRed', (val) => { 
      this.color = val;
});
change() {
     eventBus.$emit('changeRed', this.old);
}

你可能感兴趣的:(vue生命周期和组件间传值)