参考API的链接:https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/arkts-observed-and-objectlink-V5
其中this.arrA[Math.floor(this.arrA.length/2)].c,@State无法观察到第二层的变化,但是ClassA被@Observed装饰,ClassA的属性的变化将被@ObjectLink观察到。
@Observed
export class FilterMaterialModel {
cover: string
id: string
describe: string | null
title: string
fileAddress: string
filterLocalPath: string
downloadProgress: number
constructor(
cover: string,
id: string,
describe: string | null,
title: string,
fileAddress: string
) {
this.cover = cover
this.id = id
this.describe = describe
this.title = title
this.fileAddress = fileAddress
this.filterLocalPath = ''
this.downloadProgress = 0
}
}
List({ space: CommonConstants.MARGIN_16_PX }) {
ForEach(this.curMaterialList, (material: FilterMaterialModel, index) => {
ListItem() {
FilterItemComponent({ material: material, isSelected: this.curMaterialIndex === index })
.onClick(() => {
this.curMaterialIndex = index
this.lastCurMaterialIndex = index
this.lastCurGroupIndex = this.curGroupIndex
this.isSelectedFilter = true
//如果此滤镜没有下载,则进行下载
if (!material.filterLocalPath || material.filterLocalPath.length === 0) {
this.downloadFilter(material, index)
}
})
}
}, (material: FilterMaterialModel) => material.id)
}
.width(CommonConstants.FULL_SIZE)
.height(CommonConstants.MARGIN_64_PX)
.scrollBar(BarState.Off)
.listDirection(Axis.Horizontal)
.alignListItem(ListItemAlign.Center)
@Component
struct FilterItemComponent {
@ObjectLink material: FilterMaterialModel
...
build() {
Column() {
Stack({ alignContent: Alignment.Center }) {
Image(this.material.cover)
.size({ width: CommonConstants.IMAGE_SIZE_44, height: CommonConstants.IMAGE_SIZE_44 })
.borderRadius(4)
if (this.material.downloadProgress > 0 && !this.material.filterLocalPath) {
Progress({
value: this.material.downloadProgress,
total: 100,
type: ProgressType.Ring
})
.color($r('app.color.white'))
.backgroundColor($r('app.color.white_70'))
.style({
strokeWidth: 1.5
})//.size({width: CommonConstants.IMAGE_SIZE_16, height: CommonConstants.IMAGE_SIZE_16})
.size({ width: CommonConstants.IMAGE_SIZE_32, height: CommonConstants.IMAGE_SIZE_32 })
} else if (!this.material.filterLocalPath || this.material.filterLocalPath.length === 0) {
//如果此滤镜未下载
Image($r('[HohemBaseLib].media.ic_download_16'))
.size({ width: CommonConstants.IMAGE_SIZE_16, height: CommonConstants.IMAGE_SIZE_16 })
}
Text(`${this.material.downloadProgress ?? 0}`)
.fontSize(CommonConstants.FONT_TIPS_12)
.fontColor($r('app.color.highlight_deep'))
.width(CommonConstants.IMAGE_SIZE_44)
.textAlign(TextAlign.Center)
.maxLines(1)
.textOverflow({ overflow: TextOverflow.Ellipsis })
}
.size({ width: CommonConstants.IMAGE_SIZE_44, height: CommonConstants.IMAGE_SIZE_44 })
.borderRadius(4)
.borderWidth(this.getBorderWidth())
.borderColor(this.getBorderColor())
.rotate({ angle: ScreenOrientationUtil.getInstance().getRotateAngle(this.screenRotationStatus) }
}
}
}
当变更对象数组数据时无法变更UI。
this.curMaterialList[0].downloadProgress = 100
this.curMaterialList[0].filterLocalPath ='xxxxx'
其中filterLocalPath和downloadProgress是在网络请求中不存在的字段,为了符合需求,新增的为何使用Observe和ObjectLink不能引起UI刷新。
@Observed装饰器和@ObjectLink装饰器:嵌套类对象属性变化失效的主要原因有:
1、@Observed装饰器可以观察到嵌套对象的属性变化,其他装饰器仅能观察到第二层的变化。
2、需要将具有观测能力的类对象绑定组件,来确保当改变这些类对象的内容时,UI能够正常的刷新(New一个继承了Array的对象而不是自定义数组),可以参考文档:https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/arkts-observed-and-objectlink-V5
状态管理使用文档:
https://gitee.com/openharmony/docs/blob/master/zh-cn/application-dev/quick-start/properly-use-state-management-to-develope.md\#%E5%B0%86%E7%AE%80%E5%8D%95%E5%B1%9E%E6%80%A7%E6%95%B0%E7%BB%84%E5%90%88%E5%B9%B6%E6%88%90%E5%AF%B9%E8%B1%A1%E6%95%B0%E7%BB%84
参考示例如下: