为什么$ emit在我的vue组件中不起作用

时间:2018-05-10 17:58:13

标签: vuejs2

我几个小时来一直在反对这个问题。我无法看到问题,据我所知,我正在遵循此处的文档:https://vuejs.org/v2/guide/components-custom-events.html

下面的代码



<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<div id="wrap">
  <test-listen>
    <test-emit></test-emit>
  </test-listen>
</div>
<script>
Vue.component('test-listen', {
  data: function(){
    return {};
  },
  methods: {
    customHandler : function(e){
      console.log(e);
      console.log("works");
    }
  },
  template: `
    <div class='test_listen' v-on:custom="customHandler">
      <slot></slot>
    </div>
  `
});

Vue.component('test-emit',{
  data: function(){
    return {};
  },
  methods: {
    clickHandler : function(){
      this.$emit('custom');
    }
  },
  template : `
    <div class='test_emit' v-on:click="clickHandler">
      test
    </div>
  `
});

new Vue({
  el:"#wrap"
});
</script>
<style>
.test_listen{
  display:block;
  padding:20px;
  border:1px solid #000;
}
.test_emit{
  display:block;
  width:100px;
  height:100px;
  background-color:#f0f;
  color:#fff;
  font-weight:700;
  font-size:20px;
}
</style>
&#13;
&#13;
&#13;

但是监听器肯定绑定到了元素,因为如果我调度一个vanillaJS CustomEvent,它就会触发控制台日志。我错过了什么?

3 个答案:

答案 0 :(得分:3)

我在这里只看到一个错误。你应该在子组件上添加v-on。 当你从内部发出(&#39; custom&#39;)时,它会调用&#34; customHandler&#34;在parrent上 成分

Working jsfiddle

    <test-listen>
        <test-emit v-on:custom="customHandler"></test-emit>
    </test-listen>

答案 1 :(得分:1)

使用this.$emit()可以告诉父组件嘿我创建了一个事件,现在你可以听这个事件了

你做得很好,但你不会在父母组件中听孩子发出的事件。 I made it to work.Click here to see it in action

因此,为了使代码正常工作,在test-listen组件中,将test-emit组件用作子代。

然后在div #wrap内使用test-listen组件

您的问题是您没有在父组件中收听该事件。

答案 2 :(得分:1)

这里有两件事不对。

  1. Vue事件只能绑定到组件我猜[在这里讨论vue事件]
  2. 对于事件作者批准,不合理。 [来源:https://github.com/vuejs/vue/issues/4332]
  3. 如果您确实希望无限制地传输数据,请更好地使用Global Event Bus Approach

      

    您的代码的工作示例,稍作修正。

    <script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
    <div id="wrap">
      <test-listen>
      </test-listen>
    </div>
    <script>
    Vue.component('test-listen', {
      data: function(){
        return {};
      },
      methods: {
        customHandler : function(e){
          console.log(e);
          console.log("works");
        }
      },
      template: `
        <div class='test_listen' >
          <test-emit v-on:custom="customHandler"></test-emit>
        </div>
      `
    });
    
    Vue.component('test-emit',{
      data: function(){
        return {};
      },
      methods: {
        clickHandler : function(e){
          // e => event : didnt pass here as console will stuck so
          this.$emit('custom', 'somedata');
        }
      },
      template : `
        <div class='test_emit' v-on:click="clickHandler">
          test
        </div>
      `
    });
    
    new Vue({
      el:"#wrap"
    });
    </script>
    <style>
    .test_listen{
      display:block;
      padding:20px;
      border:1px solid #000;
    }
    .test_emit{
      display:block;
      width:100px;
      height:100px;
      background-color:#f0f;
      color:#fff;
      font-weight:700;
      font-size:20px;
    }
    </style>