HarmonyOS 鸿蒙Next 在自定义控件中使用@BuilderParam 定义的变量必须要初始化吗,不能定义为空吗

HarmonyOS 鸿蒙Next 在自定义控件中使用@BuilderParam 定义的变量必须要初始化吗,不能定义为空吗 有很多小模块都有类似的标题本意是想抽取一个ModuleTile控件 中间这一块可选想用@BuilderParam传参动态控制,发现在自定义控件中使用@BuilderParam 定义的变量必须要初始化吗,折中定义了全局的空布局设为默认值

问题:就不能定义为空吗,莫非有这么鸡肋

cke_4436.png

cke_5400.png

写的好纠结 所想的跟所写完全不如预期 还没有明示的错误提示 这里居然不能动态使用数据

cke_1048.png

@Builder function globalEmptyBuilder(){}

@Component
export struct ModuleTitle {
  moreClick: Boolean = true
  moduleName: string | Resource = '模块名'
  moreText: string | Resource = "更多"
  [@BuilderParam](/user/BuilderParam) infoBuilder: () => void = globalEmptyBuilder

  build() {
    Row() {
      Text(this.moduleName)
        .fontSize(18)
        .fontColor('#05131A')
        .fontWeight(FontWeight.Bold)
      Row() {
        this.infoBuilder()
        if (this.moreText)
          Text(this.moreText)
            .fontSize(12)
            .fontColor('#9DA3A6')
        if (this.moreClick)
          Image($r('app.media.ic_right_arrow'))
            .fillColor('#9DA3A6')
            .width(12)
      }
    }.width('100%')
    .justifyContent(FlexAlign.SpaceBetween)
  }
}

更多关于HarmonyOS 鸿蒙Next 在自定义控件中使用@BuilderParam 定义的变量必须要初始化吗,不能定义为空吗的实战教程也可以访问 https://www.itying.com/category-93-b0.html

7 回复
Builder 调用

Component({
slot:()=>{
  this.buildFunction(); //这样写,避免this指向问题
}
})

更多关于HarmonyOS 鸿蒙Next 在自定义控件中使用@BuilderParam 定义的变量必须要初始化吗,不能定义为空吗的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


昨天下午已经使用这种方式 不过是示例中的尾闭包方式调用那个函数而不是指向那种方式,没太整明白两种方式的区别,

很有用,原本代码 xxx,现在改成多套一层箭头函数 () => {xxx},虽然多套了一层 () => { } 确实避免了 this 指向问题,比来回传参要简单直接有效。谢谢,

第一种方式指向当前的函数

第二种/第三种(写法上的不同)都带有括号肯定带有执行的意义

没太整明白更深层的区别

你写的有问题,mBuilder是一个函数组件,它触发的时候实在ModuleTitle组件中触发的,这时候this的指向并不是最上层的AppraisalModule,如果想用AppraisalModule中定义的参数之类的可以进行参数传递,@Build装饰器(https://developer.harmonyos.com/cn/docs/documentation/doc-guides-V3/arkts-builder-0000001524176981-V3)这一节你肯定看过的可以再研究研究。

附demo如下:

interface IParams {
  test?: string
}

@Component
struct ModuleTitle {
  moduleName: ResourceStr = '模块名';
  moreClick: boolean = true;
  moreText: ResourceStr = '更多';
  params: IParams
  @BuilderParam infoBuilder: ( $: IParams ) => void;

  build(){
    Row(){
      Text(this.moduleName)
        .fontSize(18)
        .fontColor('#05131A')
        .fontWeight(FontWeight.Bold)

      Row(){
        this.infoBuilder(this.params)
        if (this.moreText)
          Text(this.moreText)
            .fontSize(12)
            .fontColor('#9DA3A6')
        if (this.moreClick)
          Text('>')
            .fontColor('#9DA3A6')
            .width(12)
      }
    }
    .width('100%')
    .justifyContent(FlexAlign.SpaceBetween)
  }
}

@Entry
@Component
struct Page2 {
  @State message: string = 'Hello World';
  test: string = 'abc';

  @Builder
  mBuilder ($: { test?: string }) {
    Row(){
      Text($?.test).fontSize(18).width(80)
      Image($r('app.media.app_icon'))
        .width(16)
        .borderRadius(16)
        .borderWidth(0.5)
        .borderColor(Color.White)
      Image($r('app.media.app_icon'))
        .width(16)
        .borderRadius(16)
        .borderWidth(0.5)
        .borderColor(Color.White)
    }
    .border({
      width: 1,
      style: BorderStyle.Dashed
    })
  }

  build() {
    Row() {
      ModuleTitle({
        moduleName: '房源特色',
        moreText: '查看更多',
        infoBuilder: this.mBuilder,
        params: {
          test: this.test
        }
      })
    }
    .height('100%')
  }
}

这种方式复杂了点,下面用户的方式是正解。你这种数据传来传去稍显复杂了点,

在HarmonyOS中,@BuilderParam用于定义自定义控件的构建器参数。@BuilderParam定义的变量必须初始化,不能直接定义为空。这是因为@BuilderParam本质上是一个函数类型的参数,需要在声明时提供一个默认的构建器函数,以确保在未传入外部构建器时,控件仍然可以正常渲染。

例如,以下代码展示了如何正确初始化@BuilderParam

@Builder function defaultBuilder() {
  Text('默认构建器')
}

@Component
struct MyComponent {
  @BuilderParam builder: () => void = defaultBuilder

  build() {
    Column() {
      this.builder()
    }
  }
}

在上述代码中,@BuilderParam变量builder被初始化为defaultBuilder,确保即使未传入外部构建器,组件也能正常工作。如果不初始化,编译器会报错,因为未初始化的@BuilderParam会导致控件无法确定默认的构建行为。

总结:@BuilderParam定义的变量必须初始化,不能直接定义为空。

回到顶部