简体   繁体   English

从子表单组件传递和检索数据的最佳方法是什么?

[英]What's the best way to pass and retrieve data from a child form component?

This is my current method: 这是我目前的方法:

Parent.vue: Parent.vue:

// Template

<form-child :schema="schema"><form-child>

// JS

data () {
  return {
    schema: [{ // name: '', value: '', type: '' }, { //etc ... }]
  }
}

FormChild.vue : FormChild.vue

// Template

<div v-for="field in schema">
  <input v-if="field.type === 'text'" @change="updateValue(field.name, field.value)">
  <textarea v-if="field.type === 'textarea'" @change="updateValue(field.name, field.value)">/textarea>
</div>

// JS

props: {
  schema: Arrary
}

methods: {
  updateValue (fieldName, fieldValue) {
    this.schema.forEach(field => {
      // this makes schema update in Parent.vue
      if (field.name === fieldName) field.value = fieldValue
    })
  }
}

Is this the optimal way? 这是最佳方法吗? Or maybe there's a better one using emit and v-model ? 或者,也许有一个使用emitv-model的更好v-model (If so, could you provide a sample code?) (如果是这样,您能否提供示例代码?)

For what you are doing here, there is no need to separate the form into a component. 对于您在这里所做的事情,无需将表单分成一个组件。 Just make it part of the parent and use v-model . 只需使其成为父项的一部分并使用v-model

 new Vue({ el: '#app', data: { schema: [{ type: 'text', name: 'one', value: "1" }, { type: 'textarea', name: 'two', value: "stuff in the textarea" } ] } }); 
 <script src="//cdnjs.cloudflare.com/ajax/libs/vue/2.3.3/vue.min.js"></script> <div id="app"> <div v-for="field in schema"> {{field.name}} = {{field.value}} </div> <div v-for="field in schema"> <input v-if="field.type === 'text'" v-model="field.value"> <textarea v-if="field.type === 'textarea'" v-model="field.value"></textarea> </div> </div> 

If you want the component for reusability and you don't care about insulating the parent from changes (best practice is not to have anything outside a component change its data), you can just wrap the same thing in a component: 如果您希望组件具有可重用性,并且您不关心使父级不受更改的影响(最佳实践是不要让组件外部的任何内容更改其数据),则可以将相同的内容包装在组件中:

 new Vue({ el: '#app', data: { schema: [{ type: 'text', name: 'one', value: "1" }, { type: 'textarea', name: 'two', value: "stuff in the textarea" } ] }, components: { formChild: { props: ['value'] } } }); 
 <script src="//cdnjs.cloudflare.com/ajax/libs/vue/2.3.3/vue.min.js"></script> <div id="app"> <div v-for="field in schema"> {{field.name}} = {{field.value}} </div> <form-child inline-template v-model="schema"> <div> <div v-for="field in value"> <input v-if="field.type === 'text'" v-model="field.value"> <textarea v-if="field.type === 'textarea'" v-model="field.value"></textarea> </div> </div> </form-child> </div> 

A properly encapsulated child component would be decoupled from the parent data structure. 正确封装的子组件将与父数据结构分离。 It would take type and value as separate props, plus an opaque id to tell the parent which value the component is emitting about. 它会将typevalue作为单独的道具,外加一个不透明的id来告诉父组件该组件所发出的值。

By making a settable computed based on the value parameter, the component can use v-model on its form elements. 通过基于value参数计算可设置value ,组件可以在其表单元素上使用v-model The set function emits an input event with the id and the newValue , and the parent takes it from there. set函数发出一个带有idnewValueinput事件,父函数从那里接收它。

Update : I decided I didn't like the id going to the component, so I handled that in the input handler: @input="updateField(index, $event) . 更新 :我决定我不喜欢id转到组件,所以我在输入处理程序中处理了这个问题: @input="updateField(index, $event)

 new Vue({ el: '#app', data: { schema: [{ type: 'text', name: 'one', value: "1" }, { type: 'textarea', name: 'two', value: "stuff in the textarea" } ] }, methods: { updateField(index, newValue) { this.schema[index].value = newValue; } }, components: { formInput: { props: ['type', 'value'], computed: { proxyValue: { get() { return this.value; }, set(newValue) { this.$emit('input', newValue); } } } } } }); 
 <script src="//cdnjs.cloudflare.com/ajax/libs/vue/2.3.3/vue.min.js"></script> <div id="app"> <div v-for="field in schema"> {{field.name}} = {{field.value}} </div> <form-input inline-template v-for="field, index in schema" :type="field.type" :key="index" :value="field.value" @input="updateField(index, $event)"> <div> <input v-if="type === 'text'" v-model="proxyValue"> <textarea v-if="type === 'textarea'" v-model="proxyValue"></textarea> </div> </form-input> </div> 

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 从父组件触发子组件的最佳方式是什么? - What's the best way to trigger a child emit from the parent component? 测试传递给子组件的道具的最佳方式是什么? - What's the best way to test props you pass to child components? 将降价作为道具传递给 Astro 组件的最佳方法是什么 - What's the best way to pass markdown to an Astro component as a prop 无法将 React 表单数据从子组件传递到父组件 - Unable to pass React form data from a Child component to a Parent Component 在子聚合物元素之间通信和传递数据的最佳方法是什么? - What is the best way to communicate and pass data between child polymer elements? React + Redux - 在表单组件中处理CRUD的最佳方法是什么? - React + Redux - What's the best way to handle CRUD in a form component? 从另一个组件有条件地导入组件的最佳方法是什么? - What's the best way to conditionally import a component from another component? 使用$ .ajax会减慢网站速度吗? 什么是从php文件中检索即时数据的最佳方法 - does using $.ajax slows down the website? what's the best way to retrieve instant data from a php file 从服务器获取聊天应用程序消息的最佳方法是什么 - What's the best way to retrieve messages from the server for a chat application 将 django 表单数据传递给 javascript ajax 调用的最佳方法是什么? - What is the best way to pass django form data to javascript ajax call?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM