如何改变基于Vue“prop”计算的数组?
Posted
技术标签:
【中文标题】如何改变基于Vue“prop”计算的数组?【英文标题】:How to mutate the array which has been computed based on Vue "prop"? 【发布时间】:2020-08-30 16:51:15 【问题描述】:来自 Vue 文档:
prop 作为需要转换的原始值传入。在 在这种情况下,最好使用 prop 定义一个计算属性 价值。
Source
如果这个“道具”是对象数组怎么办?我试图根据文档将其转换为计算数组。那怎么变异呢?
在下面的示例中,组件接受项目数组Array< ID: string, lettering: string; >
。
组件为每个项目呈现按钮。
-
当我们点击按钮时,它必须改变颜色。
如果我们再次单击相同的按钮,它必须返回到初始状态。
Fiddle
<template>
<div>
<button
v-for="(item, index) in selectableItems"
:key="`BUTTON-$item.ID`"
:class=" selected: item.selected "
@click="() => onButtonClicked(item, index) "
> item.lettering
</button>
</div>
</template>
我从items
计算selectableItems
。除了 item
的属性之外,selectableItems
还具有属性 selected
。
export default
name: "HelloWorld",
props:
items: Array
,
computed:
selectableItems: function ()
const selectableItems = [];
this.items.forEach((item) =>
selectableItems.push(
ID: item.ID,
lettering: item.lettering,
selected: false
);
);
return selectableItems;
,
methods:
onButtonClicked: function(item, index)
if (item.selected)
this.selectableItems[index].selected = false;
else
this.selectableItems[index].selected = true;
console.log(this.selectableItems);
;
目前,Vue 不会重新渲染按钮。
我知道 getter 的 mutate 使用不当。 但是我应该如何改变数组呢?
禁解
不允许通过props
而不是 ID: string, lettering: string;
传递 ID: string, lettering: string; selected: boolean;
。 ID: string, lettering: string;
是纯模型,一定不知道UI。 selected: boolean;
仅用于 UI。
【问题讨论】:
您的解决方案将不起作用,因为您尝试操作计算的道具,该道具在重新计算时将被简单地覆盖。您需要将元素的选定状态存储为数据,以使其正常工作。如果你的数组中有不变的索引,你可以使用这些。或者你在你的 props 上创建一个观察者,并将 props 中给出的所有数据存储为你的本地数据,并在更改时不断更新它 @FrankProvost,感谢您的评论。 “您需要将元素的选定状态存储为数据,以使其正常工作。” - 但如何?从 Vue API 的角度来看,这并不明显。 【参考方案1】:这是 jsfiddle https://jsfiddle.net/hgvajn5t/ 中的一个简单示例
由于时间紧迫,我跳过了创建两个组件,实际上将数据作为道具向下传递。
关键是在数据中定义您选择的按钮
data ()
return
selectedItems: []
,
第二部分是存储哪些项目被选中,哪些没有被选中
onButtonClicked: function(item)
let index = this.selectedItems.indexOf(item.ID)
if (index > -1)
this.selectedItems.splice(index, 1)
else
this.selectedItems.push(item.ID)
onButtonClicked 将项目作为输入接收并检查它是否存在于您的 selectedItems 中 - 如果存在,它将被删除,否则将被添加
最后一部分是改变你的绑定来设置选择的类
:class=" selected: selectedItems.indexOf(item.ID) > -1 "
再次在这里 - 只需检查它是否是 selectItems 的一部分
然后您可以删除计算属性并简单地使用道具循环遍历元素。
重要提示:这仅在您的项目 ID 值是唯一的情况下才有效。
关于这个的一些一般性想法:当你刚接触 vue 时,这个概念可能有点难以理解,因为对于简单的选择状态来说,它似乎非常复杂。这对于我给出的解决方案来说可能是正确的——但总的来说,它在很大程度上取决于你如何构建你的 UI。这一切的主要原因是你不应该直接操纵道具。使用计算道具来增强它们是好的 - 操纵计算道具同样糟糕。如果您需要当前组件之外的选择状态,您将需要考虑使用事件向父级(数据来自哪里)发出对按钮的点击,并直接在那里更改选择状态。然后它将直接通过 props 传递。这是一种更“自然”的方式,因为您可以操纵单一事实来源,而不是在另一个屏幕中保存有关项目的附加信息。
【讨论】:
感谢您的解释!以上是关于如何改变基于Vue“prop”计算的数组?的主要内容,如果未能解决你的问题,请参考以下文章
VueJs 组件的 Prop 相关计算属性对对象数组 Prop 更改没有反应
Vue 2 + TypeScript:避免直接改变 Prop - 在带有 vue-property-decorator 的基于类的组件中