arkts状态管理使用(@State、@Prop、@Link、@Provide、@Consume、@objectLink和@observed)

一、状态管理

1.在声明式UI中,是以状态驱动视图更新:

①状态(State):指驱动视图更新的数据(被装饰器标记的变量)

②视图(View):基于UI描述渲染得到用户界面

注意:

①@State装饰器标记的变量必须初始化,不能为空值

②@State支持object、class、string、number、boolean、enum类型以及这些类型的数组

③嵌套类型以及数组中的对象属性无法触发视图更新

例子:

TypeScript 复制代码
class Person{
  name:string
  age:number
  friend:Person
  constructor(name:string,age:number,friend?:Person) {
    this.name=name
    this.age=age
    this.friend=friend
  }

}

@Entry
@Component
struct Index {
 @State  message: string = 'Hello World'
@State P:Person=new Person('张三',18,new Person('zz',10))
  build() {
    Row() {
      Column() {
        // 正常发生变化
        Text(`${this.P.name}:${this.P.age}`)
          .fontSize(80)
          .fontWeight(FontWeight.Bold)
          .fontColor("red")
          .onClick(()=>{
            this.P.name="李四"
            this.P.age++
          })
        // 嵌套的对象点击视图不发生变化
        Text(`${this.P.friend.name}:${this.P.friend.age}`)
          .fontSize(80)
          .fontWeight(FontWeight.Bold)
          .fontColor("red")
          .onClick(()=>{
            this.P.friend.name="ss"
            this.P.friend.age++
          })
      }
      .width('100%')
    }
    .height('100%')
  }
}

效果:

2.@State和@Prop单项数据同步(父向子传值)

①父组件

html 复制代码
//2.引入子组件
import { AnLi }from "./AnLi"
@Entry
@Component
struct Index {
//   1.父组件声明变量
@State a:number=0
  build() {
    Stack(){
      Column(){
        // 3.父向子传值
        AnLi({a:this.a})
        Button("点击").onClick(()=>{
          this.a++
        })
      }.height("30%").width("100%").backgroundColor("green")


  }.height("50%").width("100%").backgroundColor("red").alignContent(Alignment.Center)

}}

②子组件

html 复制代码
@Component
export struct AnLi {
  //4.@prop接收父组件传过来的变量
@Prop a:number
  build(){
      Column(){
         Text(  `${this.a}`)
      }

}}

2.@State和@Link数据双向同步

①父组件

html 复制代码
//2.引入子组件
import { AnLi }from "./AnLi"
@Entry
@Component
struct Index {
//   1.父组件声明变量
@State a:number=0
  build() {
    Stack(){
      Column(){
        Text( `${this.a}`)
        // 3.父向子传值
        AnLi({a:this.a})
        Button("点击").onClick(()=>{
          this.a++
        })
      }.height("30%").width("100%").backgroundColor("green")


  }.height("50%").width("100%").backgroundColor("red").alignContent(Alignment.Center)

}}

②子组件

html 复制代码
@Component
export struct AnLi {
  //4.@Link接收父组件传过来的变量
@Link a:number
  build(){
      Column(){
         Text(  `${this.a}`)
      }

}}

效果如下:

3.@Provide和@Consume与后代组件双向同步例子如下:

html 复制代码
//入口组件,根组件
import { AnLi }from "./AnLi"
@Entry
@Component
struct Index {
  @Provide a:number=1
  build() {
    Stack(){
      Column(){
      AnLi()
      }.height("30%").width("100%").backgroundColor("green")

  }.height("50%").width("100%").backgroundColor("red").alignContent(Alignment.Center)

}}

//父组件
import { Consum }from "./Consum"
@Component
export struct AnLi {

  build(){
      Column(){
      Consum()
      }
}}

//子组件
@Component
export struct Consum {
  @Consume a:number
  build(){
    Column(){
     Text(  `${this.a}`)
      Text(  `${this.a}`)
      Button("加以").onClick(()=>{
        this.a++
      })
    }
  }}

效果如下:

4.@objectLink和@observed装饰器用于在涉及嵌套对象或数组元素为对象的场景中进行双向数据同步

  • 被@Observed装饰的类,可以被观察到属性的变化;
  • 子组件中@ObjectLink装饰器装饰的状态变量用于接收@Observed装饰的类的实例,和父组件中对应的状态变量建立双向数据绑定。这个实例可以是数组中的被@Observed装饰的项,或者是class object中的属性,这个属性同样也需要被@Observed装饰。
  • 单独使用@Observed是没有任何作用的,需要搭配@ObjectLink或者@Prop使用。
限制条件
  • 使用@Observed装饰class会改变class原始的原型链,@Observed和其他类装饰器装饰同一个class可能会带来问题。
  • @ObjectLink装饰器不能在@Entry装饰的自定义组件中使用。
html 复制代码
@Observed
class ClassA {
  public c: number;

  constructor(c: number) {
    this.c = c;
  }
}

@Observed
class ClassB {
  public a: ClassA;

  constructor(a: ClassA) {
    this.a = a;
  }
}

@Component
struct ComB{
  @ObjectLink a:ClassA;
  build(){
    Button(`ViewA  this.a.c=${this.a.c} +1`)
      .onClick(() => {
        this.a.c += 1;
      })

  }
}



@Entry
@Component
struct Index {
  @State b: ClassB = new ClassB(new ClassA(0));
  build() {
    Stack(){
      Column(){
        ComB({a:this.b.a})
      }.height("30%").width("100%").backgroundColor("green")

  }.height("50%").width("100%").backgroundColor("red").alignContent(Alignment.Center)

}}

效果如下:

相关推荐
shadowcz0073 分钟前
Live Search API :给大模型装了一个“实时搜索引擎”的插件
linux·服务器·前端·数据库·搜索引擎
一个小白55530 分钟前
nginx 的反向代理 负载均衡 动静分离 重写
linux·运维·前端·nginx·centos·firefox
panrunjun44 分钟前
vue element-plus 集成多语言
前端·javascript·vue.js
蓝莓味的口香糖1 小时前
Vue常用自定义指令-积累的魅力【VUE】
前端·javascript·vue.js
未来之窗软件服务1 小时前
在 Excel 使用macro 常用函数 使用行数 招标专家系统————仙盟创梦IDE
前端·excel·vbs·excel插件·仙盟创梦ide
全马必破三2 小时前
前端性能优化方案
开发语言·前端·javascript
心海资源2 小时前
【心海资源】黄金首饰价格查询单页源码
前端·学习·开源软件
打小就很皮...2 小时前
《从虚拟 DOM 到 Diff 算法:深度解析前端高效更新的核心原理》-简版
前端·javascript·html
神仙别闹2 小时前
基于Java(SSM)+MySQL实现(Web)具有智能推荐功能的图书销售系统
java·前端·mysql
是席木木啊2 小时前
Tomcat:部署前后端分离项目踩坑
前端·javascript·vue.js