Vue IView使用v-for渲染Tabs,数据异常
异常问题如下:
源码:
<Tabs
v-if="equipmentDeviceList.length > 0"
type="card">
<TabPane
v-for="(item,index) in equipmentDeviceList"
:key="index"
:label="item.equipmentName">
<TabPanelTable
ref="tabPanelTableRef"
:equipment-id="item.equipmentId"
:sort-index="item.sortIndex"
:device-list="item.deviceList"></TabPanelTable>
</TabPane>
</Tabs>
使用数组equipmentDeviceList
(vue数组)渲染Tabs数组,效果如下:
从逻辑上讲:父组件使用v-for循环创建[VueComponent]
数组,通过equipmentDeviceList
将设备列表item.deviceList
传入子组件,并用于展示、提供选择功能。自定义子组件TabPanelTable
内,有个vue变量用于存储已选设备。初次渲染没有问题。
问题在于:当在父组件更新/修改equipmentDeviceList
时,根据数组重新渲染[VueComponent]
吗?no。Vue会最小限度修改VueComponent,如何最小化,举个例子,
equipmentDeviceList
:[{a:1}, {b:2}],当我们去掉[0],此时重新渲染,[VueComponent1, VueComponent2]并不是去掉本身的[0],而是对比[VueComponent1, VueComponent2]两个结点,将VueComponent2的用户数据【这里指的数据是父组件传入的内容,即equipmentDeviceList
:[{a:1}, {b:2}]的{b:2},但是不包括:①vue组件id(这个无所谓),②我们在VueComponent2中创建的Vue变量】移植到VueComponent1里,此时渲染出新的Tab:VueComponent1,但是VueComponent1里的变量仍然是未移植之前的变量,于是数据异常。
解决办法:不使用子组件的变量,改为从外层传入:
:select-items="item.selectItems"
@on-selectItems-change="onSelectItemsChange"
传入选择的数组,当父级数组改变时,页面Tab数据也会根据父级传入来渲染。
传入on-selectItems-change方法用于保存子组件提交上来的选中数据。
<Tabs
v-if="equipmentDeviceList.length > 0"
type="card">
<TabPane
v-for="(item,index) in equipmentDeviceList"
:key="index"
:label="item.equipmentName">
<TabPanelTable
ref="tabPanelTableRef"
:equipment-id="item.equipmentId"
:sort-index="item.sortIndex"
:device-list="item.deviceList"
:select-items="item.selectItems"
@on-selectItems-change="onSelectItemsChange"></TabPanelTable>
</TabPane>
</Tabs>