前端checkbox组件加载对象数组

情景阐述:前端有一个表单,在新增或者编辑时会visible,表单中有一组checkbox,用于记录集群运行节点,这组checkbox的数据源来自集群信息查询,可多选,在前端选中值以数组存储显示,在后端以string存储。在进行新增过程中,通过json对象传值到后端,用RequestBody接收对象,这过程中涉及类型转换。

1、前端选择运行节点的值存储在数组里,保存时需要转换成字符串:

在开发中,若需要将数组转换为字符串,可以利用数组对象的join()和toString()方法实现。

toString()方法会把数组转换为字符串,逗号分隔每一项。

join('分隔符')会将数组的所有元素用指定的分隔符链接成为一个字符串。

join()和toString()方法可将多维数组转为字符串,默认情况下使用逗号连接。不同的是,join()方法可以指定连接数组元素的符号。另外,当数组元素为undefined、null或空数组时,对应的元素会被转换为空字符串。

_this.mdl.runNode = _this.mdl.runNode.toString();

那么在数据库中该字段数据就以字符串存储,每个节点以逗号隔开。

前端显示前先将字符串转换成数组:

let runNodes = _this.item.runNode;

_this.mdl.runNode = runNodes.split(',');

2、点击两次编辑,会报错“runNodes.split is not a function”

得到的runNodes 可能不是一个字符串,可以用 runNodes.toString().split(',')来获取。

3、checkbox已经选中赋值,但是页面上不显示

可能的原因是数据的加载时机不同造成的。当您在组件挂载后,立即使用内联数据初始化选择值时,选择值可以正常显示。但是,当您使用异步接口请求数据时,初始化选择值的代码可能会在数据请求完成之前执行,导致选择值无法正确设置。要解决在组件渲染之前设置选择值的问题,确保选择框正确渲染出来并标记已选项。
下面是一些可能的解决方案:

1)使用 async/await 或 Promise 对数据进行异步加载,并在获取数据之后再初始化选择值: 

async fetchData () {
  const res = await ClusterApi.getClusterNode({"id": clusterId})
  this.nodes = res.data.records.map(item => {
    return {'label': item.name, 'value': item.name}
  })
  this.selectedNodes = ['node-1'] // 初始化选择值
}

 2)在使用异步接口加载数据之前,将 selectedNodes 初始化为空数组,然后在数据请求完成后再更新选择值:

data () {
  return {
    nodes: [],
    selectedNodes: []
  }
},
methods: {
  fetchData () {
    const _this = this
    ClusterApi.getClusterNode({"id": clusterId}).then(function (res) {
      _this.nodes = res.data.records.map(item => {
        return {'label': item.name, 'value': item.name}
      })
      _this.selectedNodes = [] // 将选择值初始化为空数组
    })
  },
  selectNodes () {
    // 处理选择节点的代码
  }
},
mounted () {
  this.fetchData()
},
watch: {
  nodes: function () {
    // 在节点数据变化时,更新选择值
    this.selectedNodes = ['node-1']
  }
}

3)使用 v-if 条件渲染来确保数据加载完成后再显示 v-checkbox-group 组件和其选项:

<template>
  <div>
    <div v-if="nodes.length">
      <v-checkbox-group v-model="selectedNodes">
        <v-checkbox v-for="node in nodes" :key="node.value" :label="node.label" :value="node.value"></v-checkbox>
      </v-checkbox-group>
    </div>
    <div v-else>
      数据正在加载中...
    </div>
  </div>
</template>

4)通过在获取节点信息后使用$nextTick方法来等待DOM渲染完成后再设置选择值。

async showNodes(clusterId) {
  let _this = this;
  _this.nodes = [];
  //获取节点信息
  const res = await ClusterApi.getClusterNode({"id": clusterId});
  _this.nodes = res.data.records.map(item =>{
    return {'label':item.name, 'value': item.name}
  })
  //等待DOM渲染完成后再设置选择值
  this.$nextTick(() => {
    _this.mdl.runNode = ['node-1','node-3'];
  });
}

$nextTick方法用于在下次DOM更新后执行回调函数,确保DOM更新完成后再执行后续逻辑。在上面的代码中,获取节点信息的过程改为异步等待,并使用$nextTick方法等待DOM渲染完成后再设置选择值. 通过这样的方式,可以保证在节点信息获取并且DOM渲染完成后再设置选择值,从而可以确保checkbox组件会正确地显示选项值。 

5)把 _this.mdl.runNode = ['node-1','node-3'] 移到 showNodes 方法之后的 then 回调中,在获取数据完成后再设置选择值。

created () {
  this.showNodes(clusterId).then(() => {
    this.mdl.runNode = ['node-1','node-3'];
  });
},
async showNodes(clusterId) {
  let _this = this;
  _this.nodes = [];
  const res = await ClusterApi.getClusterNode({"id": clusterId});
  _this.nodes = res.data.records.map(item =>{
    return {'label':item.name, 'value': item.name}
  });
}

 将 _this.mdl.runNode = ['node-1','node-3'] 放到 created 钩子函数中,就会在渲染组件和获取数据之前执行,因此 checked 属性在组件渲染时仍然是空数组,所以不能正常勾选选择框。为了解决这个问题,可以执行 showNodes 方法,然后再把 _this.mdl.runNode 设置为选中值。把 _this.mdl.runNode = ['node-1','node-3'] 移到 showNodes 方法之后的 then 回调中,在获取数据完成后再设置选择值。同时,把 showNodes 方法也变为异步函数并使用 async/await 来获取数据。最后,在 created 钩子函数中调用 showNodes 方法,并在方法执行完成后设置选择值。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值