状态管理
@State、@Prop、@Link、@Provide、Consume、@ObjectLink、@Observed和@Watch用于管理页面级变量的状态。
装饰器 | 装饰内容 | 说明 |
---|---|---|
@State | 基本数据类型,类,数组 | 修饰的状态数据被修改时会触发组件的build方法进行UI界面更新。 |
@Prop | 基本数据类型 | 修改后的状态数据用于在父组件和子组件之间建立单向数据依赖关系。修改父组件关联数据时,当前组件会重新渲染。 |
@Link | 基本数据类型,类,数组 | 父子组件之间的双向数据绑定,父组件的内部状态数据作为数据源,任何一方所做的修改都会反映给另一方。 |
@Observed | 类 | @Observed应用于类,表示该类中的数据变更被UI页面管理。 |
@ObjectLink | 被@Observed所装饰类的对象 | @ObjectLink装饰的状态数据被修改时,在父组件或者其他兄弟组件内与它关联的状态数据所在的组件都会重新渲染。 |
@Consume | 基本数据类型,类,数组 | @Consume装饰的变量在感知到@Provide装饰的变量更新后,会触发当前自定义组件的重新渲染。 |
@Provide | 基本数据类型,类,数组 | @Provide作为数据的提供方,可以更新其子孙节点的数据,并触发页面重新渲染。 |
@State
@State装饰的变量是组件内部的状态数据,当这些状态数据被修改时,将会调用所在组件的build方法进行UI刷新。
@State状态数据具有以下特征:
支持多种类型数据:支持class、number、boolean、string强类型数据的值类型和引用类型,以及这些强类型构成的数组,即Array、Array、Array、Array。不支持object和any。
支持多实例:组件不同实例的内部状态数据独立。
内部私有:标记为@State的属性是私有变量,只能在组件内访问。
需要本地初始化:必须为所有@State变量分配初始值,变量未初始化可能导致未定义的框架异常行为。
创建自定义组件时支持通过状态变量名设置初始值:在创建组件实例时,可以通过变量名显式指定@State状态变量的初始值。
@Prop
@Prop与@State有相同的语义,但初始化方式不同。@Prop装饰的变量必须使用其父组件提供的@State变量进行初始化,允许组件内部修改@Prop变量,但变量的更改不会通知给父组件,即@Prop属于单向数据绑定。
@Prop状态数据具有以下特征:
支持简单类型:仅支持number、string、boolean等简单数据类型;
私有:仅支持组件内访问;
支持多个实例:一个组件中可以定义多个标有@Prop的属性;
创建自定义组件时将值传递给@Prop变量进行初始化:在创建组件的新实例时,必须初始化所有@Prop变量,不支持在组件内部进行初始化
@Link
@Link装饰的变量可以和父组件的@State变量建立双向数据绑定:
支持多种类型:@Link支持的数据类型与@State相同,即class、number、string、boolean或这些类型的数组;
私有:仅支持组件内访问;
单个数据源:父组件中用于初始化子组件@Link变量的必须是@State变量;
双向通信:子组件对@Link变量的更改将同步修改父组件中的@State变量;
创建自定义组件时需要将变量的引用传递给@Link变量,在创建组件的新实例时,必须使用命名参数初始化所有@Link变量。@Link变量可以使用@State变量或@Link变量的引用进行初始化,@State变量可以通过'$'操作符创建引用。
@Observed和ObjectLink数据管理
开发者只想针对父组件中某个数据对象的部分信息进行同步时,如果这些部分信息是一个类对象,就可以使用@ObjectLink配合@Observed来实现,如下图所示。
@Observed用于类,@ObjectLink用于变量。
@ObjectLink装饰的变量类型必须为类(class type)。
类要被@Observed装饰器所装饰。
不支持简单类型参数,可以使用@Prop进行单向同步。
@ObjectLink装饰的变量是不可变的。
属性的改动是被允许的,当改动发生时,如果同一个对象被多个@ObjectLink变量所引用,那么所有拥有这些变量的自定义组件都会被通知进行重新渲染。
@ObjectLink装饰的变量不可设置默认值。
必须让父组件中有一个由@State、@Link、@StorageLink、@Provide或@Consume装饰的变量所参与的TS表达式进行初始化。
@ObjectLink装饰的变量是私有变量,只能在组件内访问
@Consume和@Provide
@Provide作为数据的提供方,可以更新其子孙节点的数据,并触发页面渲染。@Consume在感知到@Provide数据的更新后,会触发当前自定义组件的重新渲染。
@Provide
名称 | 说明 |
---|---|
装饰器参数 | 是一个string类型的常量,用于给装饰的变量起别名。如果规定别名,则提供对应别名的数据更新。如果没有,则使用变量名作为别名。推荐使用@Provide('alias')这种形式。 |
同步机制 | @Provide的变量类似@State,可以修改对应变量进行页面重新渲染。也可以修改@Consume装饰的变量,反向修改@State变量。 |
初始值 | 必须设置初始值。 |
页面重渲染场景 | 触发页面渲染的修改:- 基础类型(boolean,string,number)变量的改变;- @Observed class类型变量及其属性的修改;- 添加,删除,更新数组中的元素。 |
@Consume
类型 | 说明 |
---|---|
初始值 | 不可设置默认初始值。 |
@Watch
@Watch用于监听状态变量的变化
具体允许哪种方式取决于状态变量的装饰器:
装饰器类型 | 本地初始化 | 通过构造函数参数初始化 |
---|---|---|
@State | 必须 | 可选 |
@Prop | 禁止 | 必须 |
@Link | 禁止 | 必须 |
@StorageLink | 必须 | 禁止 |
@StorageProp | 必须 | 禁止 |
@Provide | 必须 | 可选 |
@Consume | 禁止 | 禁止 |
@ObjectLink | 禁止 | 必须 |
常规成员变量 | 推荐 | 可选 |
从上表中可以看出:
@State变量需要本地初始化,初始化的值可以被构造参数覆盖。
@Prop和@Link变量必须且仅通过构造函数参数进行初始化。
通过构造函数方法初始化成员变量,需要遵循如下规则:
从父组件中的变量(下)到子组件中的变量(右) | @State | @Link | @Prop | 常规变量 |
---|---|---|---|---|
@State | 不允许 | 允许 | 允许 | 允许 |
@Link | 不允许 | 允许 | 不推荐 | 允许 |
@Prop | 不允许 | 不允许 | 允许 | 允许 |
@StorageLink | 不允许 | 允许 | 不允许 | 允许 |
@StorageProp | 不允许 | 不允许 | 不允许 | 允许 |
常规变量 | 允许 | 不允许 | 不允许 | 允许 |
从上表中可以看出:
父组件的常规变量可以用于初始化子组件的@State变量,但不能用于初始化@Link或@Prop变量。
父组件的@State变量可以初始化子组件的@Prop、@Link(通过$)或常规变量,但不能初始化子组件的@State变量。
父组件的@Link变量可以初始化子组件的@Link或常规变量。但是初始化子组件的@State成员是语法错误,此外不建议初始化@Prop。
父组件的@Prop变量可以初始化子组件的常规变量或@Prop变量,但不能初始化子组件的@State或@Link变量。
@StorageLink和@StorageProp不允许由父组件中传递到子组件。
除了上述规则外,还需要遵循TS的强类型规则。
审核编辑:汤梓红
-
变量
+关注
关注
0文章
613浏览量
28369 -
OpenHarmony
+关注
关注
25文章
3722浏览量
16317
发布评论请先 登录
相关推荐
评论