《鸿蒙第一行代码》第十课 @objectLink和@observed

49 阅读2分钟
《鸿蒙第一行代码》第十课 @objectLink和@observed

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

注意: 这里有个坑的地方:状态数组得一个个new进去

简单示例代码:

export  class Student{
  sid:number
  name:string
  age:number
  //宠物
  pet:Pet
  constructor(sid:number,name:string,age:number,pet:Pet) {
    this.sid = sid
    this.name = name
    this.age = age
    this.pet = pet
  }
}

//宠物
@Observed //实现双向数据同步
export  class Pet{
  petName:string
  petAge:number

  constructor(petName:string,petAge:number) {
    this.petName = petName
    this.petAge = petAge
  }
}

@Entry
@Component
struct Observed_objectLink_Page {
  //私有变量的值是一个对象
  @State s:Student = new Student(2301,"马保国", 73, new Pet("大黄",3))

  //准备一个数组
  @State pets:Pet[] = [new Pet("小白",2300), new Pet("小痴", 1100)]

  build() {
    Column({space:20}){
      /**
       * 数组元素为对象,实现数据同步
       * 调用PetInfo, 这里的this.s.pet是属于student对象的pet属性
       */
      // PetInfo({pet:this.s.pet})
      //   .onClick(()=>{
      //     //变量通过@State修饰,点击修改私有变量(点击一次自增1),然后会自动修改刷新UI
      //     this.s.pet.petAge++
      //   })

      //添加宠物
      Button("添加").onClick(()=>{
        this.pets.push(new Pet("小灰"+1, 10))
      })

      Text("---------宠物列表------").fontSize(30).width("100%")
      ForEach(this.pets,(pet:Pet, index)=>{
        /**
         * 嵌套对象,实现数据同步
         * 调用PetList
         */
        PetList({pet:pet})
          .onClick(()=>{
            //变量通过@State修饰,点击修改私有变量(点击一次自增1),然后会自动修改刷新UI
            this.s.pet.petAge++
          })
      })

    }
    .width("100%").height("100%")
    .justifyContent(FlexAlign.Center)//主轴方向对齐
  }
}

/**
 * 嵌套对象,实现数据同步
 */
@Component
struct PetInfo {
  //子组件的变量必须使用@ObjectLink
  @ObjectLink pet:Pet
  build() {
    //修改Student的属性是可以的
    Text(`宠物:${this.pet.petName}${this.pet.petAge}`)
      .fontSize(30)
  }
}

/**
 * 数组元素为对象,实现数据同步
 */
@Component
struct PetList {
  //子组件的变量必须使用@ObjectLink
  @ObjectLink pet:Pet
  build() {
    Row(){
      Text(`${this.pet.petName}:${this.pet.petAge}`).fontSize(20)
      Button("修改年龄").onClick(()=>{
        //点击后发现修改了数据,但是由于属性属于数组的对象,@State无法让修改后自动渲染
        this.pet.petAge++
      })
    }.width("100%").justifyContent(FlexAlign.SpaceAround)
  }
}
《鸿蒙第一行代码》项目代码结构图:

在这里插入图片描述
有需要《鸿蒙第一行代码》项目源码的私信我,我每天都看私信的