如何监听我无法控制的嵌套组件发出的事件?

时间:2018-01-17 14:37:42

标签: vue.js vuetify.js

我想在"Autocomplete" version中使用Vuetify 选择组件。

然而,我需要的一件事是查询请求字符串(在表单中是典型的)。它不是直接可用的,但我在DevTools(Vue选项卡)中看到<v-select>发出事件"update:searchInput",其有效负载中包含此请求字符串。

我试图在我的组件中监听此事件(在挂载时:this.$on('update:searchInput', this.querySelections)),但看起来它只是传递给直接父节点而不是上面。

换句话说:我有一个我无法控制的组件向其父级发出一个事件(我也没有控制它),我不知道如何在我的组件中拦截它。这可能吗?

有关信息,示例的代码如下。我相信它并没有那么有用,因为Vue DevTools选项卡不可用。它只显示我可以直接从组件返回的唯一值是a1,这是已经选择的项目(而不是它输入的请求字符串)

new Vue({
  el: '#app',
  data() {
    return {
      a1: null,
      states: [
        'Alabama', 'Alaska', 'American Samoa', 'Arizona',
        'Arkansas', 'California', 'Colorado', 'Connecticut',
        'Delaware', 'District of Columbia', 'Federated States of Micronesia',
        'Florida', 'Georgia', 'Guam', 'Hawaii', 'Idaho',
        'Illinois', 'Indiana', 'Iowa', 'Kansas', 'Kentucky',
        'Louisiana', 'Maine', 'Marshall Islands', 'Maryland',
        'Massachusetts', 'Michigan', 'Minnesota', 'Mississippi',
        'Missouri', 'Montana', 'Nebraska', 'Nevada',
        'New Hampshire', 'New Jersey', 'New Mexico', 'New York',
        'North Carolina', 'North Dakota', 'Northern Mariana Islands', 'Ohio',
        'Oklahoma', 'Oregon', 'Palau', 'Pennsylvania', 'Puerto Rico',
        'Rhode Island', 'South Carolina', 'South Dakota', 'Tennessee',
        'Texas', 'Utah', 'Vermont', 'Virgin Island', 'Virginia',
        'Washington', 'West Virginia', 'Wisconsin', 'Wyoming'
      ]
    }
  }
})
<link href="https://unpkg.com/vuetify@0.17.6/dist/vuetify.min.css" rel="stylesheet"/>
<script src="https://unpkg.com/vue/dist/vue.js"></script>
<script src="https://unpkg.com/vuetify@0.17.6/dist/vuetify.min.js"></script>

<div id="app">
  <v-app id="inspire">
    <v-card color="grey lighten-4" flat>
      <v-card-text>
        <v-container fluid>
          <v-layout row wrap>
            <v-flex xs12 sm6>
              <v-subheader v-text="'Autocomplete'"></v-subheader>
            </v-flex>
            <v-flex xs12 sm6>
              <v-select v-bind:items="states" v-model="a1" label="Select" autocomplete></v-select>
            </v-flex>
          </v-layout>
        </v-container>
      </v-card-text>
    </v-card>
  </v-app>
</div>

1 个答案:

答案 0 :(得分:0)

您可以extend v-select组件来获取公交道具,您可以在其上转发update:searchInput事件,以便您可以在顶层抓住它。

&#13;
&#13;
Vue.component('my-select', {
  extends: Vue.component('v-select'),
  props: ['bus'],
  created() {
    this.$on('update:searchInput', (payload) => this.bus.$emit('update:searchInput', payload));
  }
});

new Vue({
  el: '#app',
  data() {
    return {
      a1: null,
      states: [
        'Alabama', 'Alaska', 'American Samoa', 'Arizona',
        'Arkansas', 'California', 'Colorado', 'Connecticut',
        'Delaware', 'District of Columbia', 'Federated States of Micronesia',
        'Florida', 'Georgia', 'Guam', 'Hawaii', 'Idaho',
        'Illinois', 'Indiana', 'Iowa', 'Kansas', 'Kentucky',
        'Louisiana', 'Maine', 'Marshall Islands', 'Maryland',
        'Massachusetts', 'Michigan', 'Minnesota', 'Mississippi',
        'Missouri', 'Montana', 'Nebraska', 'Nevada',
        'New Hampshire', 'New Jersey', 'New Mexico', 'New York',
        'North Carolina', 'North Dakota', 'Northern Mariana Islands', 'Ohio',
        'Oklahoma', 'Oregon', 'Palau', 'Pennsylvania', 'Puerto Rico',
        'Rhode Island', 'South Carolina', 'South Dakota', 'Tennessee',
        'Texas', 'Utah', 'Vermont', 'Virgin Island', 'Virginia',
        'Washington', 'West Virginia', 'Wisconsin', 'Wyoming'
      ],
      bus: new Vue()
    }
  },
  created() {
    this.bus.$on('update:searchInput', (payload) => console.log("Got", payload));
  }
})
&#13;
<link href="https://unpkg.com/vuetify@0.17.6/dist/vuetify.min.css" rel="stylesheet"/>
<script src="https://unpkg.com/vue/dist/vue.js"></script>
<script src="https://unpkg.com/vuetify@0.17.6/dist/vuetify.min.js"></script>

<div id="app">
  <v-app id="inspire">
    <v-card color="grey lighten-4" flat>
      <v-card-text>
        <v-container fluid>
          <v-layout row wrap>
            <v-flex xs12 sm6>
              <v-subheader v-text="'Autocomplete'"></v-subheader>
            </v-flex>
            <v-flex xs12 sm6>
              <my-select :bus="bus" v-bind:items="states" v-model="a1" label="Select" autocomplete></my-select>
            </v-flex>
          </v-layout>
        </v-container>
      </v-card-text>
    </v-card>
  </v-app>
</div>
&#13;
&#13;
&#13;