vue组件语法及组件之间的通信问题

什么是组件化呢:其实就是对于ui界面的封装,把能够复用的ui元素封装起来

什么是模块化呢:其实就是对于代码的封装,将能够复用的代码封装起来

组件化的优势

1. 便于复用

2. 便于维护

3. 便于分工

在Vue中注册组件的方式:

1、全局注册:

<script>
    Vue.component("my-header", {
        template: "<div class='top'>这是头部</div>"
    })
    const vm = new Vue({
      el: "#app"
    })
</script>

2、局部注册:

<script>
    const vm = new Vue({
      el: "#app",
      components: {
        "my-header": {
          template: "<div class='top'>这是头部</div>"
        }
      }
    })
</script>

如何使用注册的组件:在页面中使用已经注册好的组件,只需要,将组件名作为标签名,书写标签即可

<div id="app">
    <my-header></my-header>
  </div>
  <script src="./node_modules/vue/dist/vue.js"></script>

注意:

组件名中不能包含大写字母,如果需要将多个单词分隔开,需要使用- 中划线进行分割

全局注册的,所有vue实例中都可以使用

局部注册的,只能在当前vue实例中使用

Vue组件其实就是一个特殊的vue实例,传递的参数对象,基本和vue实例的参数对象一致

区别: data 的写法不一样

组件中的data是一个函数,返回一个对象,这个对象就是数据对象!

vue组件中的data必须是个函数的目的:就是为了保证组件实例之间不会相互影响!

模板使用数据的方式,和之前在vue实例中使用数据的方式完全一样!

Vue.component("myheader", {
      template: "<div>这是一个组件{{msg}}</div>",
      data(){
        return {
          msg: "Hello world"
        }
      }
    })
    
    const vm = new Vue({
      el: "#app"
    })

组件中注册事件:

<body>
  <div id="app">

    <myheader></myheader>

  </div>
  <script src="./node_modules/vue/dist/vue.js"></script>

  <script>

    // 组件的模板中必须有一个根元素,否则会报错!

    Vue.component("myheader", {
      template: "<div><div>这是一个组件{{msg}} <button @click='clickHandler'>按钮</button></div><br> <input type='text' v-model='num1'> + <input type='text' v-model='num2'> = <span>{{result}}</span></div>",
      data(){
        return {
          msg: "Hello world",
          num1: 0,
          num2: 0
        }
      },
      methods: {
        clickHandler(){
          alert(123)
        }
      },
      computed: {
        result(){
          return +this.num1 + +this.num2;
        }
      }
    })
    
    const vm = new Vue({
      el: "#app"
    })

  </script>
</body>

组件之间的通信:

1、父 --》子 :将父组件的数据传到子组件

<body>

  <div id="app">
    <father></father>

  </div>
  <script src="./node_modules/vue/dist/vue.js"></script>
  <script>

    //如何把父组件中的数据传递给子组件使用? 父到子的传值(属性传值)

    //1. 在父组件中使用子组件的时候,给子组件的标签中,添加一个属性,这个属性就是用来传递数据的
    //2. 这个属性应该使用动态绑定的方式传递 需要加上:
    //3. 在子组件的参数对象中,添加一个props属性
    //4. 这个属性是一个数组,数组中存放点的,就是父组件传递数据的时候使用的属性名
    //5. 在子组件中,就直接可以使用这个属性了 


    //注意: 父组件中的数据发生变化之后,子组件中接收到的数据也会随之变化

    Vue.component("father", {
      template: `<div>这是父组件:<son :msgfromfather="msg" :numfromfather="num"/></div>`,
      data(){
        return {
          msg: "这是父组件中的数据",
          num: 9999
        }
      }
    })

    Vue.component("son", {
      template: "<div>这是子组件{{msgfromfather}}, {{numfromfather}}</div>",
      props: ["msgfromfather", "numfromfather"]
    })


    const vm = new Vue({
      el: "#app"
    })


    //子组件接收到的数据会随父组件变化

    Vue.component("father", {
      template: `<div>这是父组件:<input type="text" v-model="msg"/><son :msgfromfather="msg" :numfromfather="num"/></div>`,
      data(){
        return {
          msg: "这是父组件中的数据",
          num: 9999
        }
      }
    })

    Vue.component("son", {
      template: "<div>这是子组件{{msgfromfather}}, {{numfromfather}}</div>",
      props: ["msgfromfather", "numfromfather"]
    })


    const vm = new Vue({
      el: "#app"
    })


    //子组件中修改富父组件传递过来的数据,会不会改变父组件中的数据
    //父组件传递给子组件的数据,子组件是不可以进行修改的!

    //单向数据流!

    Vue.component("father", {
      template: `<div>这是父组件:<input type="text" v-model="msg"/><son :msgfromfather="msg" :numfromfather="num"/></div>`,
      data(){
        return {
          msg: "这是父组件中的数据",
          num: 9999
        }
      }
    })

    Vue.component("son", {
      template: `<div>这是子组件 <button @click="clickHandler">修改父组件的数据</button>{{msgfromfather}}, {{numfromfather}}</div>`,
      props: ["msgfromfather", "numfromfather"],
      methods: {
        clickHandler(){
          this.numfromfather = 6666;
        }
      }
    })


    const vm = new Vue({
      el: "#app"
    })

  </script>
</body>

 

2、子 --》父 :将子组件的数据传到父组件

<body>

  <div id="app">
    <father></father>

  </div>
  <script src="./node_modules/vue/dist/vue.js"></script>
  <script>

    // 在实际开发过程中,也会遇到,需要子组件将数据传递给父组件去使用的情况
    // 比如: 日期组件  

    // 父组件给子组件传值,用的是属性传值,而且是在标签中直接书写,代码一运行起来,数据就会传递过去

    // 子组件给父组件传值,是通过事件传值的


    // 在父组件中使用子组件的时候,我们需要给子组件标签,绑定一个函数,这个函数就是用来接收数据的

    // 1. 需要在父组件中先声明一个函数出来,这个函数可以接收一个参数
    // 2. 将这个函数通过@绑定给子组件标签
    // 3. 在子组件中要给父组件传递数据的时候,通过this.$emit("绑定的函数的名称"),调用父组件中的函数,把自己的数据当做参数传递过去
    // 4. 在父组件中,就可以拿到这个数据了
    

    // 子组件给父组件传值(事件传值)

    Vue.component("father", {
      template: `<div>这是父组件:儿子的来信{{msgFromSon}}<son @sendmsg="getMsgFromSon"/></div>`,
      data(){
        return {
          msgFromSon: ""
        }
      },
      methods: {
        getMsgFromSon(value){
          // console.log("儿子来信了:说啥来着,看一下:" + value)
          this.msgFromSon = value;
        }
      }
    })

    Vue.component("son", {
      template: "<div>这是子组件 <button @click='sendMsgToFather'>发消息给父亲</button></div>",
      data(){
        return {
          msg: "想父亲了",
        }
      },
      methods: {
        sendMsgToFather(){
          // 这个点击事件中,我们需要把子组件中的msg发送给父组件去使用

          this.$emit("sendmsg", this.msg)

        }
      }
    })


    const vm = new Vue({
      el: "#app"
    })


  </script>
</body>

3、非父子组件的之间的通信:

非父子组件之间通过一个空的Vue实例来传递数据。

const bus = new Vue();   //bus:公交车  事件总线

核心逻辑 :

组件A给组件B传值:
1. 组件A给bus注册一个事件,监听事件的处理程序
2. 组件B触发bus上对应的事件,把 值当成参数来传递
3. 组件A通过事件处理程序获取数据

<body>

  <div id="app">

    <brother-a></brother-a>
    <brother-b></brother-b>
    
  </div>

  <script src="./node_modules/vue/dist/vue.js"></script>
  <script>


    // globel-event-bus  全局事件总线

    const bus = new Vue();


    Vue.component("brotherA", {
      template: "<div>这是熊大</div>",
      methods: {
        getMsgFromBear2(value){
          console.log("熊二来信了:"+value)
        }
      },
      created(){
        // $on是用来注册事件的
        // bus.$on("事件名", 事件函数)
        bus.$on("getMsg", this.getMsgFromBear2)
      }
    })

    Vue.component("brotherB", {
      template: "<div>这是熊二 <button @click='sendMsgToBearBig'>通知熊大</button></div>",
      data(){
        return {
          msg: "熊大,光头强又来砍树了"
        }
      },
      // 触发bus事件
      methods: {
        sendMsgToBearBig(){
          bus.$emit("getMsg", this.msg);
        }
      }
    })

    const vm = new Vue({
      el: "#app"
    })
  </script>
</body>

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值