写点什么

HarmonyOS 5.0 应用开发——LazyForEach 数据懒加载

作者:高心星
  • 2024-10-31
    江苏
  • 本文字数:2849 字

    阅读完需:约 9 分钟

HarmonyOS 5.0应用开发——LazyForEach数据懒加载

【高心星出品】

LazyForEach 数据懒加载

LazyForEach 从提供的数据源中按需迭代数据,并在每次迭代过程中创建相应的组件。当在滚动容器中使用了 LazyForEach,框架会根据滚动容器可视区域按需创建组件,当组件滑出可视区域外时,框架会进行组件销毁回收以降低内存占用。

应用场景

  • LazyForEach 必须在容器组件内使用,仅有 List、Grid、Swiper 以及 WaterFlow 组件支持数据懒加载(可配置 cachedCount 属性,即只加载可视部分以及其前后少量数据用于缓冲),其他组件仍然是一次性加载所有的数据。

  • LazyForEach 所使用的数据源必须实现 IDataSource 接口并重写里面的四个方法。

数据源封装

数据源需要自己封装成一个类并实现 IDataSource 接口,重写必备的四个方法。


export class datamodel implements IDataSource{  totalCount(): number { //数据源数据个数    throw new Error("Method not implemented.");  }
getData(index: number) {//根据下标获取数据 throw new Error("Method not implemented."); }
registerDataChangeListener(listener: DataChangeListener): void {//注册数据改变监听 throw new Error("Method not implemented."); }
unregisterDataChangeListener(listener: DataChangeListener): void {//解绑数据改变监听 throw new Error("Method not implemented."); } }
复制代码


除此之外,该类还要有数据源和数据监听数组两个全局变量。并提供数据源改变的相关操作方法,每次更新数据源都要刷新所有的数据监听器。


export class datamodel<T> implements IDataSource {  private datas: T[] = [] //数据源  private listeners: DataChangeListener[] = [] //数据监听  // 数据源构造器  constructor(datas: T[]) {    this.datas = datas;  }
totalCount(): number { //数据源中数据个数 return this.datas.length }
getData(index: number) { //获取下标对应的数据 return this.datas[index] }
registerDataChangeListener(listener: DataChangeListener): void { //注册监听器 if (this.listeners.indexOf(listener) < 0) { //当前监听器数组中没有数据 this.listeners.push(listener) //增加该监听 } }
unregisterDataChangeListener(listener: DataChangeListener): void { let pos = this.listeners.indexOf(listener) if (pos > 0) //当前监听器数组中有数据 { this.listeners.splice(pos, 1) //移除该监听 } }
//_______________________________数据源操作方法 新增数据、插入数据、删除数据、更新数据________________________
addData(item: T) { //尾部增加元素 this.datas.push(item) this.listeners.forEach((listener: DataChangeListener) => { listener.onDataAdd(this.datas.length - 1) }) }
addData1(index: number, item: T) { //某个位置添加元素 this.datas.splice(index, 0, item) this.listeners.forEach((listener: DataChangeListener) => { listener.onDataAdd(index) }) }
delData() { //末尾移除元素 this.datas.pop() this.listeners.forEach((listener: DataChangeListener) => { listener.onDataDelete(this.datas.length - 1) }) }
delData1(index: number) { //移除某个下标对应的元素 this.datas.splice(index, 1) this.listeners.forEach((listener: DataChangeListener) => { listener.onDataDelete(index)
}) }
updData(index: number, Data: T) { //更新某个下标的元素 this.datas.splice(index, 1, Data) this.listeners.forEach((listener: DataChangeListener) => { listener.onDataChange(index) }) }}
复制代码

List 应用

使用懒加载将数据加载到 list 组件中。


import { datamodel } from '../datamodel/datamodel';
@Entry@Componentstruct Test { @State message: string = 'Hello World'; @State datas:string[]=['item1','item2','item3','item4','item5','item6','item7','item8','item9','item10'] @State models:datamodel<string>=new datamodel(this.datas) build() {
Column() { List() { LazyForEach(this.models, (item: string,index:number) => { //数据懒加载 ListItem() { this.genItem(index+1, item) } }, (item: number) => JSON.stringify(item)) } } .height('100%') .width('100%')
} @Builder genItem(index:number,txt:string)//listitem子布局 { Row({space:20}){ Text((index)+'').padding(10).borderRadius(30).backgroundColor(Color.Red).fontWeight(FontWeight.Bold).fontColor(Color.White) Text(txt).padding(10).fontSize(14) }.padding(10).width('100%') }}
复制代码



新增数据、删除数据和更新数据操作。


import { datamodel } from '../datamodel/datamodel';
@Entry@Componentstruct Test { @State message: string = 'Hello World'; @State datas: string[] = ['item1', 'item2', 'item3', 'item4', 'item5', 'item6', 'item7', 'item8', 'item9', 'item10'] @State models: datamodel<string> = new datamodel(this.datas)
build() { Stack() { Column() { List() { LazyForEach(this.models, (item: string, index: number) => { //数据懒加载 ListItem() { this.genItem(index + 1, item) } }, (item: number) => JSON.stringify(item)) } } .height('100%') .width('100%')
Row() { Button('新增元素').onClick(() => { this.models.addData1(1, '新增元素') }) Button('删除元素').onClick(() => { this.models.delData() }) Button('更新元素').onClick(() => { this.models.updData(5,'更新元素') }) }.width('100%').justifyContent(FlexAlign.SpaceEvenly) }.width('100%').height('100%').alignContent(Alignment.Bottom) }
@Builder genItem(index: number, txt: string){ //listitem子布局 Row({ space: 20 }) { Text((index) + '') .padding(10) .borderRadius(30) .backgroundColor(Color.Red) .fontWeight(FontWeight.Bold) .fontColor(Color.White) Text(txt).padding(10).fontSize(14) }.padding(10).width('100%') }}
复制代码


注意


所有的操作都是针对数据的变化,数组下标的变化并不会体现在 UI 刷新上。


注意


所有的操作都是针对数据的变化,数组下标的变化并不会体现在 UI 刷新上。



用户头像

高心星

关注

天将降大任于斯人也,必先苦其心志。 2024-10-17 加入

华为开发者专家(HDE)。 10年教学经验,兼任多家科技公司技术顾问。先后从事JavaEE项目开发、Python爬虫、HarmonyOS移动应用开发等课程的教学工作。参与开发《鸿蒙应用开发基础》和《鸿蒙项目实战》等课程。

评论

发布
暂无评论
HarmonyOS 5.0应用开发——LazyForEach数据懒加载_HarmonyOS_高心星_InfoQ写作社区