从Vue中的子组件获取输入值

Posted

技术标签:

【中文标题】从Vue中的子组件获取输入值【英文标题】:Get input values from child components in Vue 【发布时间】:2019-11-22 13:30:38 【问题描述】:

我想从我的子组件(clientadvice,见下文)中检索所有输入值,但不知道如何继续。

client.vue

<template>
    <div id="client">
        <input type="text" v-model="client.name" />
        <input type="text" v-model="client.code" />
    </div>
</template>

<script>
    export default 
        data() 
            return 
                client: 
                    name: '',
                    code: '',
                
            
        
    
</script>

advice.vue

<template>
    <div id="advice">
        <input type="text" v-model="advice.foo" />
        <input type="text" v-model="advice.bar" />
        <div v-for="index in 2" :key="index">
            <input type="text" v-model="advice.amount[index]" />
        </div>
    </div>
</template>

<script>
    export default 
        data() 
            return 
                advice: 
                    foo: '',
                    bar: '',
                    amount:[]
                
            
        
    
</script>

每个组件的字段都比上面的例子多。

我的主页(父)看起来很简单:

<template>
    <form id="app" @submit="printForm">
        <clientInfo />
        <advice />
        <input type="submit" value="Print" class="btn" />
    </form>
</template>

<script>
    import clientInfo from "@/components/clientInfo.vue";
    import advice from "@/components/advice.vue";

    export default 
        components: 
            clientInfo,
            advice
        ,
        methods: 
            printForm() 
        
    
</script>

我的第一个想法是$emit,但不确定如何在不将@emitMethod="parentEmitMethod" 附加到每个字段的情况下有效地处理超过 20 个字段。

我的第二个想法是拥有一个 Vuex 存储(如下所示),但我不知道如何一次保存所有状态,也不知道是否应该。

new Vuex.Store(
    state: 
        client: 
            name:'',
            code:''
        ,
        advice: 
            foo:'',
            bar:'',
            amount:[]
        
    
)

【问题讨论】:

【参考方案1】:

您可以使用FormData 来获取具有name 属性的form&lt;input&gt;s 或&lt;textarea&gt;s 的值(匿名的被忽略)。即使表单具有包含 &lt;input&gt;s 的嵌套 Vue 组件,这也有效。

export default 
  methods: 
    printForm(e) 
      const form = e.target
      const formData = new FormData(form) // get all named inputs in form
      for (const [inputName, value] of formData) 
        console.log( inputName, value )
      
    
  

demo

【讨论】:

【参考方案2】:

我认为您可以实现您想要的,当用户使用@change 编写内容时,这将在输入值更改时触发一个方法,您可以使用按钮或任何您想要的东西,如下所示: 子组件

<input type="text" v-model="advice.amount[index]" @change="emitCurrStateToParent ()"/>

您必须在每个输入中添加@change="emitCurrStateToParent ()"

emitCurrStateToParent () 
    this.$emit("emitCurrStateToParent", this.advice)

然后在你的父组件中

<child-component v-on:emitCurrStateToParent="reciveDataFromChild ($event)"></child-component>
reciveDataFromChild (recivedData) 
    // Do something with the data

我会使用按钮而不是@change,比如“保存”按钮idk,vuex也是如此,你可以使用@change事件

saveDataAdviceInStore () 
    this.$store.commit("saveAdvice", this.advice)

然后在商店里

mutations: 
    saveAdvice (state, advice) 
        state.advice = advice
    
    

【讨论】:

那是我一开始就不想做的事情【参考方案3】:

您可以将 v-model 与您的自定义组件一起使用。假设您想像这样使用它们:

<advice v-model="adviceData"/>

为此,您需要观察通知组件中输入元素的值变化,然后发出带有这些值的输入事件。这将更新 adviceData 绑定属性。一种通用的方法是在您的建议组件中包含一个观察者,如下所示:

export default 
  data() 
    return 
      advice: 
        foo: '',
        bar: '',
        amount:[]
      
    
  ,
  watch: 
    advice: 
      handler: function(newValue, oldValue) 
        this.$emit('input', newValue);
      ,
      deep: true,
    
  ,

这样您就不必为每个输入字段添加处理程序。如果我们需要检测通知对象中嵌套数据的变化,则必须包含 deep 选项。

【讨论】:

观察者会在哪里?在组件内部? @Jonathan 在您要使用 v-model 的每个自定义组件中。 能否请您创建一个示例,我不太了解如何使其工作 @Jonathan 我用更完整的例子更新了我的答案。更多关于 vue 观察者的信息:it.vuejs.org/v2/guide/computed.html#Watchers

以上是关于从Vue中的子组件获取输入值的主要内容,如果未能解决你的问题,请参考以下文章

如何将初始表单值传递给 Vue.js 中的子组件?

从服务器获取数据并将值传递给 React 中的子组件(useEffect、useFetch..)

vue中组件之间的传值

如何从 Angular 中的异步输入中获取“就绪”值

从 vue 中的子组件控制一个 prop 类

如何从 vue-fullpage 包装器中的子组件调用 fullpagejs 方法?