vue.js - 从多个子组件Vue js中获取数据
问题描述
几天来我一直在头疼,试图弄清楚如何从子组件中获取数据。
情况是这样的。
我有一个名为的父组件Post
,用户可以在其中选择日期、标题、描述,并且可以包含多个组件实例Event
。
Event
组件包含标题、描述、与会者等字段。
用户应该能够添加多个Event
组件,这意味着我在组件Event
中有多个Post
组件。
所以,我不知道如何组合我的组件以Event
在我的组件中包含一组对象Post
,稍后我可以将其发送到我的 API。
我需要的对象的结构post
是:
// Post.vue
{
"date": '',
"name": '',
"description": '',
"events": {
{
"title": '',
"description": '',
"attendees": ''
},
{
"title": '',
"description": '',
"attendees": ''
}
}
}
所以,我不知道应该以及如何使用 vuex。我尝试使用 $emit 传递数据,但我找不到适合将数据导入Post
模型的方法。
有人可以指出我应该在哪里寻找它吗?
编辑#1:添加示例代码
组件的代码:
<template>
<v-form>
<v-container>
<v-row>
<v-col
cols="12"
md="4"
>
<v-date-picker v-model="post.date" scrollable>
<v-spacer />
<v-btn text color="primary" @click="modal = false">
Cancel
</v-btn>
<v-btn text color="primary" @click="$refs.dialog.save(date)">
OK
</v-btn>
</v-date-picker>
</v-col>
<v-col
cols="12"
md="4"
>
<v-text-field
v-model="post.name"
label="name"
required
/>
</v-col>
<v-col
cols="12"
md="4"
>
<v-textarea
v-model="post.description"
name="description"
label="Description"
dense
value
rows="4"
hint
/>
</v-col>
</v-row>
<v-row>
<v-btn primary rounded @click="addLine">
Add Event
</v-btn>
<v-expansion-panels accordion>
<UserEvent
v-for="(line, index) in lines"
:key="index"
@addLine="addLine"
@removeLine="removeLine(index)"
/>
</v-expansion-panels>
</v-row>
</v-container>
</v-form>
</template>
<script>
import UserEvent from './partials/event'
export default {
name: 'Post',
components: { UserEvent },
data () {
return {
post: [],
lines: [],
blockRemoval: true
}
},
watch: {
lines () {
this.blockRemoval = this.lines.length <= 1
}
},
mounted () {
},
methods: {
addLine () {
const checkEmptyLines = this.lines.filter(line => line.number === null)
if (checkEmptyLines.length >= 1 && this.lines.length > 0) { return }
this.lines.push({
title: null,
description: null,
attendees: null
})
},
removeLine (lineId) {
if (!this.blockRemoval) { this.lines.splice(lineId, 1) }
}
}
}
</script>
和子组件 UserEvent
// UserEvent.vue
<template>
<v-expansion-panel>
<v-expansion-panel-header>Event details</v-expansion-panel-header>
<v-expansion-panel-content>
<v-row>
<v-col cols="12" md="6">
<v-text-field
v-model="event.title"
label="Title"
required
/>
</v-col>
<v-col
cols="12"
md="6"
>
<v-text-field
v-model="event.atttendees"
label="Atendees"
required
/>
</v-col>
<v-col
cols="12"
md="12"
>
<v-textarea
v-model="event.description"
name="description"
label="Description"
dense
value
rows="4"
hint
/>
</v-col>
<v-col
cols="12"
md="3"
>
<div class="block float-right">
<v-btn @click="removeLine(index)" />
<v-btn v-if="index + 1 === lines.length" @click="addLine" />
</div>
</v-col>
</v-row>
</v-expansion-panel-content>
</v-expansion-panel>
</template>
<script>
export default {
name: 'UserEvent',
props: ['line', 'index'],
data () {
return {
event: []
}
},
methods: {
addLine () {
this.$emit('addLine')
},
removeLine (index) {
this.$emit('removeLine', index)
}
}
}
</script>
解决方案
这是问题中提出的具有类似结构的示例:
{
name: String,
events: [
title: String,
description: String,
],
}
此示例允许用户打开表单以添加新事件。提交该表单时,事件数据将添加到父组件的状态中。
家长
<template>
<div>
<input v-model="name" />
<ul v-if="events.length">
<li v-for="(event, index) in events" :key="index">
<span>{{ event.title }}</span>
<span>{{ event.description }}</span>
</li>
</ul>
<Event v-if="isNewEventFormVisible" @submit="addEvent" />
<button v-else @click="showNewEventForm">add event</button>
</div>
</template>
import Event from '~/components/Event';
export default {
components: { Event },
data() {
return {
name: 'Example Post',
events: [],
isNewEventFormVisible: false,
};
},
methods: {
addEvent({ title, description }) {
this.isNewEventFormVisible = false;
this.events.push({ title, description });
// TODO: call you API here to update
},
showNewEventForm() {
this.isNewEventFormVisible = true;
},
},
};
事件
<template>
<form @submit.prevent="onSubmit">
<input v-model.trim="title" type="text" />
<br />
<textarea v-model.trim="description" />
<button type="submit">submit</button>
</form>
</template>
export default {
data() {
return {
title: '',
description: '',
};
},
methods: {
onSubmit() {
this.$emit('submit', {
title: this.title,
description: this.description,
});
},
},
};
您可以想象一个更复杂的版本,其中事件是可编辑的。在这种情况下,每个都Event
可以使用 props 并将它们作为值绑定到其输入,而不是使用v-model
s。
推荐阅读
- regression - β的岭估计量的偏差和方差计算
- html - 如何减少语音CSS生成气泡的边界框到可见部分?
- kotlin - 我得到一个“类型不匹配:推断的类型是字符串但可编辑!是预期的”我在下面使用了相同的代码,它可以工作吗?
- azure-active-directory - 禁止 Office365 组成员在 Sharepoint Teams 和 Microsoft Teams 上编辑 SharePoint 布局
- python - 比较列表值并选择每天的最大值 - Python
- bots - Discord.js 机器人命令不起作用。怎么解决?
- html - 仅使用负边距而不使用位置上升圈?
- c++ - 我需要在类中的动态数组上调用 delete[] 但它不起作用
- python - 用 pytest 和烧瓶模拟 auth 装饰器
- javascript - 需要帮助将对象添加到我的数组列表中,每当它发生变化时