Vue1.0学习总结(4)———Vue1.0自定义组件、Vue1.0组件之间的通信、slot的使用

Vue自定义组件:

组件:就是一个大的对象:new Vue({})就是一个组件
定义一个组件:
1.全局组件:
  <div id="box">
    <aaa></aaa>
  </div>
  var Aaa=Vue.extend({
    template:'<h3>我是一个标题</h3>'
  });
  Vue.component('aaa',Aaa);


a)给自定义的组件添加数据:
  data必须是函数的形式,函数必须返回一个对象(json)
  var Aaa=Vue.extend({
    data(){ //data必须是函数
      return{ //必须return一个对象
        msg:'我是一个标题'
      };
    },
    template:'<h3>{{msg}}</h3>'
  });
  Vue.component('aaa',Aaa);


b)给自定义的组件绑定事件
  var Aaa=Vue.extend({
    data(){ //data必须是函数
      return{ //必须return一个对象
        msg:'我是一个标题'
      };
    },
    methods:{ //给自定义的组件绑定事件
      change(){
        this.msg="change";
      }
    },
    template:'<h3 @click="change">{{msg}}</h3>'
  });
  Vue.component('aaa',Aaa); //component放在外部

 

2.局部组件(子组件)
把自定义的组件放到某一个组件内部
<script type="text/javascript">
  var Aaa=Vue.extend({
    data(){ //data必须是函数
      return{ //必须return一个对象
        msg:'我是一个标题'
      };
    },
    methods:{ //给自定义的组件添加事件
      change(){
        this.msg="change";
      }
    },
    template:'<h3 @click="change">{{msg}}</h3>'
  });

  var vm = new Vue({
    el:'#box',
    data:{
      bsign:true
    },
    components:{ //components放在根组件vue内部,为局部组件
      'aaa':Aaa
    }
  });
</script>
==============================================

定义组件的另一种编写方式:
  <div id="box">
    <my-aaa></my-aaa>
  </div>
1)全局组件:
<script type="text/javascript">
  Vue.component('my-aaa',{
    data(){
      return{
        msg:'标题1111'
      }
    },
    methods:{
      toggle(){
        this.msg="change"
      }
    },
    template:'<strong @click="toggle">{{msg}}</strong>'
  });
  var vm = new Vue({
    el:'#box'
  });
</script>

2)局部组件:
<script type="text/javascript">
  var vm = new Vue({
    el:'#box',
    components:{
      'my-aaa':{
        data(){
          return{
            msg:'标题2233'
          }
        },
        methods:{
          toggle(){
            this.msg="change"
          }
        },
        template:'<strong @click="toggle">{{msg}}</strong>'
      }
    }
  });
</script>
===============================================

配合模板自定义组件:(即template里面的代码)
1.直接放到template里面
  template:'<strong @click="toggle">{{msg}}</strong>'


2.单独放到某一个地方
a)都放到一个script标签里面
<script type="x-template" id="aaa">
  <strong @click="toggle">{{msg}}</strong>
  <ul>
    <li>111</li>
    <li>111</li>
    <li>111</li>
    <li>111</li>
  </ul>
</script>
<script type="text/javascript">
  Vue.component('my-aaa',{
    data(){
      return{
        msg:'标题1111'
      }
    },
    methods:{
      toggle(){
        this.msg="change"
      }
    },
    template:'#aaa' //写的是id属性
  });
  var vm = new Vue({
    el:'#box'
  });
</script>


b)放到template标签里面(*推荐使用)
<template id="aaa">
  <strong @click="toggle">{{msg}}</strong>
  <ul>
    <li v-for="val in arr">{{val}}</li>
  </ul>
</template>

<script type="text/javascript">
  Vue.component('my-aaa',{
    data(){
      return{
        msg:'标题1111',
        arr:['apple','banana','orange']
      }
    },
    methods:{
      toggle(){
        this.msg="change"
      }
    },
    template:'#aaa'
  });
  var vm = new Vue({
    el:'#box'
  });
</script>
===========================================
定义动态组件:
可实现标签切换:
<div id="box">
  <input type="button" value="我是aaa组件" @click="a='aaa'">
  <input type="button" value="我是bbb组件" @click="a='bbb'">
  <component :is="a"></component> //*自定义动态组件
</div>
<script type="text/javascript">
  var vm = new Vue({
    el:'#box',
    data:{
      a:'aaa'
    },
    components:{
      'aaa':{
        template:'<h2>我是标题aaa</h2>'
      },
      'bbb':{
        template:'<h2>我是标题bbb</h2>'
      }
    }
  });
</script>

 

父子组件的定义
<div id="box">
  <aaa></aaa>
</div>

var vm = new Vue({
  el:'#box',
  data:{
    a:'aaa'
  },
  components:{
    'aaa':{
      template:'<h2>我是标题aaa</h2><bbb></bbb>',
      components:{
        'bbb':{
          template:'<h2>我是标题bbb</h2>'
        }
      }
    }
  }
});
----------------------------------------------------------------------------------
vue在默认情况下,子组件没法访问父组件的数据
组件之间数据的传递(推荐使用)
1.子组件想获取父组件的data,通过props方法
props有两种写法:
1)props:['m','myMsg']
2)props:{
  m:String,
  myMsg:Number
 }


<div id="box">
  <aaa></aaa>
</div>

<template id="aaa">
  <h2>1111111-->{{msg}}</h2>
  <bbb :m="msg" :my-msg="msg1"></bbb>
</template>

<script type="text/javascript">
  var vm = new Vue({
    el:'#box',
    data:{
      a:'aaa'
    },
  components:{
    'aaa':{
      data(){
        return{
          msg:'我是父组件的数据',
          msg1:111
        }
      },
      template:'#aaa',
      components:{
        'bbb':{
          props:['m','myMsg'],//props绑定自定义属性m,进行组件之间的数据传递,
且这里应该是驼峰式写法
          template:'<h2>我是标题bbb-->{{m}}<br/>{{myMsg}}</h2>'
        }
      }
    }
  }
});
</script>

2.父组件想获取子组件的data
*子组件把自己的数据发送到父组件
发送方法:vm.$emit(事件名称,发送的数据)
v-on:接收数据-->@事件名称="函数" (函数写到父组件methods里面,这里没有括号)

<div id="box">
  <aaa></aaa>
</div>

<template id="aaa">
  <h3>父组件-->{{msg}}</h3>
  <bbb @child-msg="get"></bbb> //**这里接收get后面不能有括号
</template>

<template id="bbb">
  <span>子组件-->{{a}}</span>
  <input type="button" value="send数据" @click="send()">
</template>

<script type="text/javascript">
  var vm = new Vue({
    el:'#box',
    data:{

    },
    components:{
      'aaa':{
        data(){
          return{
            msg:'我是父组件的数据',
            msg1:111222
          }
        },
        template:'#aaa',
        methods:{
          get(msg){
            this.msg=msg;
          }
        },
        components:{
          'bbb':{
            data(){
              return{
                a:'我是子组件的数据'
              }
            },
            template:'#bbb',
            methods:{
              send(){
                this.$emit('child-msg',this.a); //数据以名称child-msg发送出去
              }
            }
          }
        }
      }
    }
  });
</script>
-------------------------------------------------------------------------
其他组件之间数据传递方法:
  vm.$dispatch(事件名,数据) -->子组件向父组件发送数据
  vm.$broadcast(事件名,数据) -->父级向子级广播数据
这两个需要配合event:{}使用
不推荐使用,因为在vue2.0中已经淘汰了

-------------------------------------------------------------------------

slot的使用:

slot:位置,槽口
作用:占个位置
类似ng里的transclude(指令)

 

我们在定义一个组建的时候,自己定义的template标签内容会把自定义组件内的内容全部覆盖掉,
如下面aaa组件里的ul列表就不会显示出来,被覆盖掉了,但是我们在实际中是不想被覆盖的,
这时就用到slot,避免被占用。
示例一:没有使用slot,aaa组件里的ul列表不会显示出来
<div id="box">
  <aaa>
    <ul>
      <li>111</li>
      <li>222</li>
      <li>333</li>
    </ul>
  </aaa>
</div>

 

<template id="aaa">
  <h2>标题1:welcome vue</h2>
  <p>段落</p>
</template>

 


var vm = new Vue({
  el:'#box',
  data:{
    a:'aaa'
  },
  components:{
    'aaa':{
      template:'#aaa'
    }
  }
});

 

 

示例2:使用slot,在template标签里预先占一个位置,此时aaa组件里的ul列表显示在h2与p标签的中间
<div id="box">
  <aaa>
    <ul>
      <li>111</li>
      <li>222</li>
      <li>333</li>
    </ul>
  </aaa>
</div>

 

<template id="aaa">
  <h2>标题</h2>
  <slot>这是默认的内容</slot>
  <p>段落</p>
</template>

 


var vm = new Vue({
  el:'#box',
  data:{
    a:'aaa'
  },
  components:{
    'aaa':{
      template:'#aaa'
    }
  }
});

 

 

默认情况下,slot,代表aaa标签里面的所有内容,
有时需要单独代表,

 

<div id="box">
  <aaa>
    <ul slot="ul-slot">
      <li>111</li>
      <li>222</li>
      <li>333</li>
    </ul>
    <ol slot="ol-slot">
      <li>444</li>
      <li>555</li>
      <li>666</li>
    </ol>
  </aaa>
</div>

 

<template id="aaa">
  <h2>标题</h2>
  <slot name="ol-slot">这是默认的内容1</slot>
  <slot name="ul-slot">这是默认的内容2</slot>
  <p>段落</p>
</template>

 

<script type="text/javascript">
  var vm = new Vue({
    el:'#box',
    data:{
      a:'aaa'
    },
    components:{
      'aaa':{
        template:'#aaa'
      }
    }
  });
</script>

 

posted @ 2017-03-11 22:00  夏至未至~  阅读(2963)  评论(0编辑  收藏  举报