基本上,我有一个名为"AddingMethodComponent"的组件,它希望传递一个HTML元素,我希望将@focus事件和我在"AddingMethodComponent"中创建的v-model添加到这个元素中.

我该怎么做呢?

这是我的实时代码:

https://stackblitz.com/edit/vue-8syygw?file=src%2FApp.vue,src%2FAddingMethodComponent.vue

主要

<AddingMethodComponent>
  <input placeholder="write something.." />
</AddingMethodComponent>

AddingMethodComponent

<template>
  <div>Adding methods</div>
  <slot @focus="clicked" v-model="textModel"></slot>
</template>

<script>
export default {
  name: 'AddingMethodComponent',
  data() {
    return {
      textModel: '',
    };
  },
  mounted() {
    setTimeout(() => {
      this.textModel = 'something';
    }, 2000);
  },
  methods: {
    clicked() {
      console.log('click');
    },
  },
};
</script>

<style></style>

推荐答案

您可以通过将槽props 传递给输入端来执行此操作:

<AddingMethodComponent v-slot="props">
  <input v-bind="props"/>
</AddingMethodComponent>

这是的缩写

<AddingMethodComponent>
  <template v-slot:default="props">
    <input v-bind="props"/>
  </template>
</AddingMethodComponent>

然而,在插槽上使用v-model是危险的.看起来它添加了@update:modelValue监听器,但没有添加:modelValueprops .因此,它可以在Vue组件上工作一半.但它不能与本地输入一起工作,因为本地输入需要:value@input.

我认为不管怎样,通过专门设置props 和Listener而不是速记v-model会更好,即如果您使用本机输入:

<slot
  :value="textModel"
  @input="event => textModel = event.target.value"
></slot>

如果您使用Vue组件:

<slot
  :modelValue="textModel"
  @update:modelValue="value => textModel = value"
></slot>

这是the updated Stackblitz美元.


更新:事实证明你使用的是Vue 2,其中的事件不是attrs的一部分.所以你必须分别提供props 和听众:

<slot
  :props="{value: textValue}" 
  :on="{input: e => textValue = e}"
/>

然后将它们分别与v-bindv-on绑定:

<AddingMethodComponent v-slot="{props, on}">
  <mds-search-field v-bind="props" v-on="on"/>
</AddingMethodComponent>

const SlotComponent = {
  template: `
    <div>
      Here is the slot:
      <slot
        :props="{value: textValue}" 
        :on="{input: e => textValue = e}"
      />
      Value in parent: <i>{{ textValue }}</i>
    </div>
  `,
  
  data(){
    return {
      textValue: 'initial parent value'
    }
  },
}

const InputComponent = {
  template: `
    <div>
      <input :value="value" @input="$emit('input', $event.target.value)">
    </div>
  `,
  props: ['value'],
  emit: ['input']
}


new Vue({
  el: '#app',
  components: {
    SlotComponent,
    InputComponent,
  },
  data() {
    return {
      test: 'value'
    };
  },
})
<div id="app">
  <slot-component v-slot="{props, on}">
    <input-component v-bind="props" v-on="on"/>
  </slot-component>
</div>

<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.7.10/vue.min.js"></script>

Vue.js相关问答推荐

无法在cPanel/SSH上构建 | Laravel + Vue优化

Vuetify 复选框未正确显示值

超出最大调用堆栈大小 - Vue路由

Vuex Mutations 和 Airbnb eslint

VueJS:如何在组件数据属性中引用 this.$store

Vue-router:循环路由以动态创建

Vue:如何将 store 与组件一起使用?

带有 vue.js 的 img 网址

如何在 vuejs 中异步加载图像 src url?

数据更新后触发 Vue.js 事件

如何在 Node.js 服务器上部署 Vue.js 应用程序

使用 Blade/Mustache 模板混合 Laravel 和 Vue.Js

如何禁用 nuxt 默认错误重定向

我在 Nuxt 2.14.0 中运行的是什么版本的 Vue?

如何从 vue.js 捕获 Jquery 事件

异步方法不等待函数

从 ajax 调用填充 Vue.js 中的下拉列表

VueJS错误避免直接改变props

Vue-i18n - 无法读取未定义的属性配置

这个业务逻辑有多少属于 Vuex?