【HarmonyOS】 多层嵌套对象通过@ObjectLink和@Observed实现渲染更新处理!

【HarmonyOS】 多层嵌套对象通过@ObjectLink和@Observed实现渲染更新处理!

一、问题背景:
上文讲过 (【HarmonyOS】List组件多层对象嵌套ForEach渲染更新的处理)对多层嵌套的简单处理,即:深拷贝item数据,该场景适用于简单的数据源处理。

但是若结构对象层级嵌套很多,属性量级大。使用深拷贝的方法就显得得不偿失了。

那应该怎么处理呢?其实还可以拆分大的数据源对象,拆薄。新增@State修饰的状态变量控制刷新。

不过这种方案,对于历史业务逻辑开发是不友好的,因为我们的历史业务数据结构是固定,不方便拆分。

二、解决方案:

花开两朵,各表一枝。在以上方案都不能解决的情况下,官网推荐了一种方式,可以无感知的实现,多层嵌套的对象属性变化,就刷新渲染对应的列表UI。


该方案唯一的缺点就是需要对于item view需进行组件Component申明,需要将list包裹的item UI进行拆分剥离。


实现该方案效果需要以下详细步骤:
1.对嵌套的数据结构类,进行@Observed修饰

2.item UI拆分剥离为组件Component

3.数据源item数据在Component组件中使用@ObjectLink监听变化,以便于通知给父组件的@State修饰的数据源列表数据。

以上步骤完成后,调用item数据对象直接修改任意层级属性值,列表就会同步更新渲染。

三、DEMO示例:

DEMO讲解通过注释的方式表明。若有不清楚的点,可私信我沟通。

import { util } from '@kit.ArkTS';/*** 三级数据结构*/
 // 每一级数据结构都需要用Observed修饰
class GrandsonInfo {content: string = "";}/*** 二级数据结构*/
 // 每一级数据结构都需要用Observed修饰
class ChildInfo {index: number;grandsonInfo: GrandsonInfo;constructor(index: number, content: string) {this.index = index;this.grandsonInfo = new GrandsonInfo();this.grandsonInfo.content = content;}
}/*** 一级数据结构*/
 // 每一级数据结构都需要用Observed修饰
class ItemInfo {key: string = util.generateRandomUUID(true);name: string;icon: Resource;childInfo: ChildInfo;select: boolean;constructor(name: string, icon: Resource, index: number, content: string) {this.name = name;this.icon = icon;this.childInfo = new ChildInfo(index, content);this.select = false;}
}/*** 多层嵌套刷新渲染*/


struct ObservedPage {private TAG: string = "ObservedPage"; mListData: Array<ItemInfo> = [];aboutToAppear(): void {this.mListData.push(new ItemInfo('游戏', $r("app.media.iconA"), 1, "鹅厂1"));this.mListData.push(new ItemInfo('游戏', $r("app.media.iconB"), 2, "鹅厂2"));this.mListData.push(new ItemInfo('游戏', $r("app.media.iconA"), 3, "鹅厂3"));this.mListData.push(new ItemInfo('游戏', $r("app.media.iconB"), 4, "鹅厂4"));this.mListData.push(new ItemInfo('游戏', $r("app.media.iconA"), 5, "鹅厂5"));this.mListData.push(new ItemInfo('游戏', $r("app.media.iconB"), 6, "鹅厂6"));}build() {List() {ForEach(this.mListData, (item: ItemInfo, index: number) => {ListItem() {// ListItem包裹的ItemView需要抽离成Component组件的形态,参数通过属性赋值传递,即:大括号包裹中,属性值key value形式赋值ItemView({item: item,index: index})}}, (item: ItemInfo) => JSON.stringify(item)) // , (item: ItemInfo) => JSON.stringify(item)// keyGenerator: ArkUI框架会对重复的键值发出警告。在UI更新的场景下,如果出现重复的键值,框架可能无法正常工作. [渲染异常]// 除非必要,否则不推荐将第三个参数KeyGenerator函数处于缺省状态,应尽量避免最终键值生成规则中包含index。[渲染性能降低]}.width("100%").height("100%").padding({ left: px2vp(60), right: px2vp(60) })}
}
struct ItemView {private TAG: string = "ItemView"; index: number = 0;// 列表数据的单个item对象数据,需要使用ObjectLink修饰监听,用于将数据变化传递给外部父组件的mListData item: ItemInfobuild() {Row() {Image(this.item.icon).width(px2vp(200)).height(px2vp(200))Text(this.item.name + "(" + this.item.childInfo.index + ")" + " [ " + this.item.childInfo.grandsonInfo.content + " ] ").fontSize(px2fp(52))Blank()if(this.isLog(this.item, this.index)){if(this.item.select){Image($r("app.media.icon_check")).size({width: px2vp(72),height: px2vp(72)})}}}.width('100%').justifyContent(FlexAlign.Start).onClick(()=>{this.item.select = !this.item.select;if(this.item.select){// 使用很方便,只需要直接改变item数据的任意层级属性值,变化就会同步刷新this.item.childInfo.index = 666;this.item.childInfo.grandsonInfo.content = "鹅厂23333"}else{this.item.childInfo.index = this.index;this.item.childInfo.grandsonInfo.content = "鹅厂" + this.index;}console.log(this.TAG, " ItemView onClick: " + this.index + " item.select: " + this.item.select);})}private isLog(item: ItemInfo, index: number){console.log(this.TAG, " ItemView isLog index: " + index + " item.select: " + item.select);return true;}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/21232.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

C++一个StringBad类

设计一个字符串类,下面的代码是一个不好的设计,起名StringBad。 //stringbad.h #pragma once //一个设计有问题的string类 #include <iostream> using namespace std;class StringBad { public:StringBad();//默认构造函数StringBad(const char* s);//构造函数~StringBa…

计算机毕业设计 | springboot+vue会议室管理系统(附源码)

1&#xff0c;绪论 1.1 项目背景 随着企业规模的不断扩大&#xff0c;会议室管理愈加复杂。传统的手工预约会议室的方式已经无法满足现代企业的需求&#xff0c;因此&#xff0c;开发一套会议室系统方案变得尤为重要。会议室系统可以实现会议室的在线预约、会议室资源的有效利…

每日学习一点:Chatgpt使用shell脚本

前言 本章&#xff0c;需要使用一个会写shell脚本的AI&#xff0c;比如chatgpt 4o&#xff0c;和了解shell脚本并会使用 当然这需要使用linux&#xff0c;其他系统当然也可以做到&#xff0c;就自学吧(๑•̀ㅂ•́)و✧ 使用脚本来完成&#xff0c;一些重复任务的自动化 1.了…

MyBatis二、搭建 MyBatis

MyBatis二、搭建 MyBatis 开发环境MySQL 不同版本的注意事项驱动程序&#xff08;Driver&#xff09;JDBC URL连接参数MyBatis配置文件版本兼容性常见问题与解决方案示例&#xff08;MySQL 8.x与MyBatis连接&#xff09; 创建 Maven 工程打包方式&#xff1a;Jar引入依赖创建数…

rman 备份集没有control file的恢复

rman备份文件&#xff0c;而且是备份的数据文件&#xff0c;没有控制文件没有参数文件的备份&#xff0c;所以普通的 &#xff08;1&#xff09; 先恢复控制文件restore controlfile from ‘…bak’; &#xff08;2&#xff09; 然后catalog start with ‘/data/20…

【TB作品】MSP430 G2553 单片机口袋板,电风扇模拟控制系统设计

功能 电风扇模拟控制系统设计 基本要求: 用LED/LCD 显示电风扇的工作状态 (1,2,3,4 四档风力), 显示风类:“自然风”、“常风”和“睡眠风”。 设计 “自然风”“常风”和“睡眠风” 三个风类键用于设置风类 设计一个“摇头”键用于控制电机摇头。 设计一个“定时”键&#x…

慢SQL的治理思路

慢SQL的治理思路 什么是慢SQL慢SQL产生的原因查看慢 SQL 是否开启开启慢 SQL 记录开启慢查询日志分析慢 SQL解决和优化慢SQL的方法 什么是慢SQL 慢 SQL 指的是 MySQL 中执行比较慢的 SQL&#xff0c;排查慢 SQL 最常用的方法是通过慢查询日志来查找慢 SQL。 MySQL 的慢查询日志…

使用element的过渡效果来做动效

transition来做过渡效果&#xff1a; <transition name"el-zoom-in-bottom"><div></div> </transition> name属性&#xff1a; 属性描述el-fade-in-linear淡入淡出匀速&#xff1b;el-fade-in淡入淡出快速&#xff1b;el-zoom-in-center中…

快速排序与归并排序(非递归)

目录 快速排序&#xff08;双指针法&#xff09; 原理 代码 快速排序&#xff08;非递归&#xff09; 原理 代码 归并排序 介绍 优点 缺点 图片 原理 代码 归并排序&#xff08;非递归&#xff09; 代码 快速排序&#xff08;双指针法&#xff09; 快速排序的精…

2024年06月编程语言流行度排名

点击查看最新编程语言流行度排名&#xff08;每月更新&#xff09; 2024年06月编程语言流行度排名 编程语言流行度排名是通过分析在谷歌上搜索语言教程的频率而创建的 一门语言教程被搜索的次数越多&#xff0c;大家就会认为该语言越受欢迎。这是一个领先指标。原始数据来自…

python中的抽象基类详解

在Python中&#xff0c;抽象基类&#xff08;Abstract Base Classes&#xff0c;简称ABCs&#xff09;是一种特殊的类&#xff0c;主要用于定义接口&#xff0c;即一组方法的规范&#xff0c;但不提供这些方法的实现。抽象基类不能被直接实例化&#xff0c;除非其所有抽象方法都…

【30天精通Prometheus:一站式监控实战指南】第15天:ipmi_exporter从入门到实战:安装、配置详解与生产环境搭建指南,超详细

亲爱的读者们&#x1f44b;   欢迎加入【30天精通Prometheus】专栏&#xff01;&#x1f4da; 在这里&#xff0c;我们将探索Prometheus的强大功能&#xff0c;并将其应用于实际监控中。这个专栏都将为你提供宝贵的实战经验。&#x1f680;   Prometheus是云原生和DevOps的…

(奇幻森林)POLYGON - Enchanted Forest - Nature Biomes - 3D Environment Art by Synty

各种雄伟的树木,装饰着优雅简化的树叶,在头顶形成了一个天堂般的树冠,在苔藓覆盖的森林地面上投下了宁静的咒语。 每一项资产,从引人入胜的环境材料到平缓的波浪状山丘,都经过精心制作,将您带到魔法和自然融合的地方。POLYGON-魔法森林-自然生物技术为数字领域注入真正魔…

60 关于 SegmentFault 的一些场景 (2)

前言 呵呵 此问题主要是来自于 帖子 月经结贴 -- 《Segmentation Fault in Linux》 这里主要也是 结合了作者的相关 case, 来做的一些 调试分享 当然 很多的情况还是 蛮有意思 本文主要问题如下 1. 访问异常堆栈地址1 2. 访问异常堆栈地址2 3. 访问异常堆栈地址3 4. sta…

第三届大湾区算力大会丨暴雨开启数字未来新篇

5月30-31日&#xff0c;韶关市迎来主题为“算启新篇智创未来”的第三届粤港澳大湾区(广东)算力产业大会暨第二届中国算力网大会&#xff0c;活动由广东省人民政府主办&#xff0c;广东省政数局、韶关市人民政府共同承办。暴雨信息作为算力产业发展的重要构建者受邀赴会&#xf…

Java的数据库编程-----JDBC

目录 一.JDBC概念&使用条件&#xff1a; 二.mysql-connector驱动包的下载与导入&#xff1a; 三.JDBC编程&#xff1a; 使用JDBC编程的主要五个步骤&#xff1a; 完整流程1&#xff08;更新update&#xff09;&#xff1a; 完整流程2(查询query)&#xff1a; 一.JDB…

汪小菲直播翻车亲儿子直言麻六记有异味网友热议引爆话题

汪小菲直播翻车&#xff01;亲儿子直言“麻六记”有“异味”&#xff0c;网友热议引爆话题在星光璀璨的娱乐圈&#xff0c;汪小菲一直以家庭幸福、事业有成的形象示人。然而&#xff0c;近日的一场直播让他遭遇了前所未有的尴尬。在直播中&#xff0c;汪小菲兴致勃勃地向观众跨…

链表头部插入结点

Linked List Inserting a node at beginning #include<stdlib.h>//为了用malloc #include<stdio.h> struct node {int data;struct node* next;//在cpp中可以只写 Node *Link&#xff1b;//为了表意明确&#xff0c;Link也经常被命名为next }; struct node* head…

视频搬运的素材网站有哪些?打包好的视频素材在哪找?

短视频创作的朋友们&#xff0c;欢迎进入这个充满创意的世界&#xff01;如果你曾为找不到合适的素材而苦恼&#xff0c;那么今天就让我为你介绍几个能够快速丰富你视频内容的素材平台。无论是为了搬运视频还是寻找灵感&#xff0c;下面这些网站都将是你的强力助手。特别地&…

【软件测试】6.设计测试用例的设计方法

目录 1.基于需求的设计方法 2.具体的设计方法 2.1等价类 2.2边界值 2.3正交法 2.4判定表法 2.5场景法 2.6 错误猜测法 1.基于需求的设计方法 基于需求的设计方法也是总的设计测试用例的方法&#xff0c;在工作中&#xff0c;我们需要参考需求文档/产品规格说明书来设计…