1# \@Require装饰器:校验构造传参 2<!--Kit: ArkUI--> 3<!--Subsystem: ArkUI--> 4<!--Owner: @VictorS67--> 5<!--Designer: @lixingchi1--> 6<!--Tester: @TerryTsao--> 7<!--Adviser: @zhang_yixin13--> 8 9\@Require是校验\@Prop、\@State、\@Provide、\@BuilderParam、\@Param和普通变量(无状态装饰器修饰的变量)是否需要构造传参的一个装饰器。 10 11> **说明:** 12> 13> 从API version 11开始对\@Prop/\@BuilderParam进行校验。 14> 15> 从API version 11开始,该装饰器支持在ArkTS卡片中使用。 16> 17> 从API version 11开始,该装饰器支持在原子化服务中使用。 18> 19> 从API version 12开始对\@State/\@Provide/\@Param/普通变量(无状态装饰器修饰的变量)进行校验。 20 21## 概述 22 23当\@Require装饰器和[\@Prop](./arkts-prop.md)、[\@State](./arkts-state.md)、[\@Provide](./arkts-provide-and-consume.md)、[\@Param](./arkts-new-param.md)、[\@BuilderParam](./arkts-builderparam.md)、普通变量(无状态装饰器修饰的变量)结合使用时,在构造该自定义组件时,\@Prop、\@State、\@Provide、\@Param、\@BuilderParam和普通变量(无状态装饰器修饰的变量)必须在构造时传参。 24 25## 限制条件 26 27\@Require装饰器仅用于装饰struct内的\@Prop、\@State、\@Provide、\@BuilderParam、\@Param和普通变量(无状态装饰器修饰的变量)。 28 29预览器的限制场景请参考[PreviewChecker检测规则](https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/ide-previewer-previewchecker-V5)。 30 31## 使用场景 32 33当Child组件内使用\@Require装饰器和\@Prop、\@State、\@Provide、\@BuilderParam、\@Param和普通变量(无状态装饰器修饰的变量)结合使用时,父组件Index在构造Child时必须传参,否则编译不通过。 34 35```ts 36@Entry 37@Component 38struct Index { 39 @State message: string = 'Hello World'; 40 41 @Builder 42 buildTest() { 43 Row() { 44 Text('Hello, world') 45 .fontSize(30) 46 } 47 } 48 49 build() { 50 Row() { 51 // 构造Child时需传入所有@Require对应参数,否则编译失败。 52 Child({ 53 regular_value: this.message, 54 state_value: this.message, 55 provide_value: this.message, 56 initMessage: this.message, 57 message: this.message, 58 buildTest: this.buildTest, 59 initBuildTest: this.buildTest 60 }) 61 } 62 } 63} 64 65@Component 66struct Child { 67 @Builder 68 buildFunction() { 69 Column() { 70 Text('initBuilderParam') 71 .fontSize(30) 72 } 73 } 74 75 @Require regular_value: string = 'Hello'; 76 @Require @State state_value: string = 'Hello'; 77 @Require @Provide provide_value: string = 'Hello'; 78 @Require @BuilderParam buildTest: () => void; 79 @Require @BuilderParam initBuildTest: () => void = this.buildFunction; 80 @Require @Prop initMessage: string = 'Hello'; 81 @Require @Prop message: string; 82 83 build() { 84 Column() { 85 Text(this.initMessage) 86 .fontSize(30) 87 Text(this.message) 88 .fontSize(30) 89 this.initBuildTest(); 90 this.buildTest(); 91 } 92 .width('100%') 93 .height('100%') 94 } 95} 96``` 97 98 99使用\@ComponentV2修饰的自定义组件ChildPage通过父组件ParentPage进行初始化,因为有\@Require装饰\@Param,所以父组件必须进行构造赋值。 100 101```ts 102@ObservedV2 103class Info { 104 @Trace name: string = ''; 105 @Trace age: number = 0; 106} 107 108@ComponentV2 109struct ChildPage { 110 @Require @Param childInfo: Info = new Info(); 111 @Require @Param state_value: string = 'Hello'; 112 113 build() { 114 Column() { 115 Text(`ChildPage childInfo name :${this.childInfo.name}`) 116 .fontSize(20) 117 .fontWeight(FontWeight.Bold) 118 Text(`ChildPage childInfo age :${this.childInfo.age}`) 119 .fontSize(20) 120 .fontWeight(FontWeight.Bold) 121 Text(`ChildPage state_value age :${this.state_value}`) 122 .fontSize(20) 123 .fontWeight(FontWeight.Bold) 124 } 125 } 126} 127 128@Entry 129@ComponentV2 130struct ParentPage { 131 info1: Info = { name: 'Tom', age: 25 }; 132 label1: string = 'Hello World'; 133 @Local info2: Info = { name: 'Tom', age: 25 }; 134 @Local label2: string = 'Hello World'; 135 136 build() { 137 Column() { 138 Text(`info1: ${this.info1.name} ${this.info1.age}`) // Text1 139 .fontSize(30) 140 .fontWeight(FontWeight.Bold) 141 // 父组件ParentPage构造子组件ChildPage时进行了构造赋值。 142 // 为ChildPage中被@Require @Param装饰的childInfo和state_value属性传入了值。 143 ChildPage({ childInfo: this.info1, state_value: this.label1 }) // 创建自定义组件。 144 Line() 145 .width('100%') 146 .height(5) 147 .backgroundColor('#000000').margin(10) 148 Text(`info2: ${this.info2.name} ${this.info2.age}`) // Text2。 149 .fontSize(30) 150 .fontWeight(FontWeight.Bold) 151 // 同上,在父组件创建子组件的过程中进行构造赋值。 152 ChildPage({ childInfo: this.info2, state_value: this.label2 }) // 创建自定义组件。 153 Line() 154 .width('100%') 155 .height(5) 156 .backgroundColor('#000000').margin(10) 157 Button('change info1&info2') 158 .onClick(() => { 159 this.info1 = { name: 'Cat', age: 18 }; // Text1不会刷新,原因是info1没有装饰器装饰,监听不到值的改变。 160 this.info2 = { name: 'Cat', age: 18 }; // Text2会刷新,原因是info2有装饰器装饰,能够监听到值的改变。 161 this.label1 = 'Luck'; // 不会刷新,原因是label1没有装饰器装饰,监听不到值的改变。 162 this.label2 = 'Luck'; // 会刷新,原因是label2有装饰器装饰,可以监听到值的改变。 163 }) 164 } 165 } 166} 167``` 168 169从API version 18开始,使用\@Require装饰\@State、\@Prop、\@Provide装饰的状态变量,可以在无本地初始值的情况下直接在组件内使用,不会编译报错。 170 171```ts 172@Entry 173@Component 174struct Index { 175 message: string = 'Hello World'; 176 177 build() { 178 Column() { 179 Child({ message: this.message }) 180 } 181 } 182} 183 184@Component 185struct Child { 186 @Require @State message: string; 187 188 build() { 189 Column() { 190 Text(this.message) // 从API version 18开始,可以编译通过。 191 } 192 } 193} 194``` 195 196## 常见问题 197 198当Child组件内将\@Require装饰器与\@Prop、\@State、\@Provide、\@BuilderParam、\@Param和普通变量(无状态装饰器修饰的变量)结合使用时,若父组件Index在构造Child时未传递参数,则会导致编译失败。 199 200```ts 201@Entry 202@Component 203struct Index { 204 @State message: string = 'Hello World'; 205 206 @Builder 207 buildTest() { 208 Row() { 209 Text('Hello, world') 210 .fontSize(30) 211 } 212 } 213 214 build() { 215 Row() { 216 //构造Child、ChildV2组件时没有传参,会导致编译不通过。 217 Child() 218 ChildV2() 219 } 220 } 221} 222 223@Component 224struct Child { 225 @Builder 226 buildFunction() { 227 Column() { 228 Text('initBuilderParam') 229 .fontSize(30) 230 } 231 } 232 233 // 使用@Require必须构造时传参。 234 @Require regular_value: string = 'Hello'; 235 @Require @State state_value: string = 'Hello'; 236 @Require @Provide provide_value: string = 'Hello'; 237 @Require @BuilderParam initBuildTest: () => void = this.buildFunction; 238 @Require @Prop initMessage: string = 'Hello'; 239 240 build() { 241 Column() { 242 Text(this.initMessage) 243 .fontSize(30) 244 this.initBuildTest(); 245 } 246 } 247} 248 249@ComponentV2 250struct ChildV2 { 251 // 使用@Require必须构造时传参。 252 @Require @Param message: string; 253 254 build() { 255 Column() { 256 Text(this.message) 257 } 258 } 259} 260```