文档管理中心
FAQ应用框架开发UI框架组件使用使用promptAction.openCustomDialog创建自定义弹窗闪退

使用promptAction.openCustomDialog创建自定义弹窗闪退

问题现象

使用promptAction.openCustomDialog创建自定义弹窗,将全局Builder构建函数作为自定义弹窗内容构造器。弹窗弹出时应用闪退。错误日志为:

收起
自动换行
深色代码主题
复制
  1. Reason:TypeError Error name:TypeError Error message:Cannot read property observeComponentCreation2 of undefined

问题代码为:

收起
自动换行
深色代码主题
复制
  1. import { promptAction } from '@kit.ArkUI'
  2. @Builder
  3. function customDialogComponent() {
  4. Column() {
  5. Text('customDialogComponent')
  6. }
  7. }
  8. @Entry
  9. @Component
  10. struct Index {
  11. build() {
  12. Column() {
  13. Button('弹窗').onClick(() => {
  14. this.getUIContext().getPromptAction().openCustomDialog({
  15. builder: () => {
  16. customDialogComponent()
  17. },
  18. alignment: DialogAlignment.Center
  19. })
  20. })
  21. }
  22. }
  23. }

背景知识

ArkUI提供了一种轻量的UI元素复用机制@Builder,其内部UI结构固定,仅与使用方进行数据传递,开发者可以将重复使用的UI元素抽象成一个方法,在build方法里调用。

解决方案

自定义构建函数@Builder可以在所属组件的build方法和其他自定义构建函数中调用,但不允许在组件外调用。因此,需要将自定义构建函数@Builder移至结构体内部,示例代码如下:

收起
自动换行
深色代码主题
复制
  1. @Entry
  2. @Component
  3. struct Index55 {
  4. private customDialogComponentId: number = 0;
  5. // 在结构体内构建定义函数
  6. @Builder
  7. customDialogComponent() {
  8. Column() {
  9. Text('温馨提示')
  10. .fontSize(25)
  11. .margin({ top: 10 });
  12. Text('请注意,一旦删除,该数据将从缓存中删除且不可恢复。请谨慎选择。')
  13. .padding({ left: 20, right: 20 });
  14. Row({ space: 50 }) {
  15. Button('确认').onClick(() => {
  16. try {
  17. this.getUIContext().getPromptAction().closeCustomDialog(this.customDialogComponentId);
  18. } catch (error) {
  19. let message = (error as BusinessError).message;
  20. let code = (error as BusinessError).code;
  21. console.error(`closeCustomDialog error code is ${code}, message is ${message}`);
  22. }
  23. });
  24. Button('取消').onClick(() => {
  25. try {
  26. this.getUIContext().getPromptAction().closeCustomDialog(this.customDialogComponentId);
  27. } catch (error) {
  28. let message = (error as BusinessError).message;
  29. let code = (error as BusinessError).code;
  30. console.error(`closeCustomDialog error code is ${code}, message is ${message}`);
  31. }
  32. });
  33. };
  34. }.height(200).padding(5).justifyContent(FlexAlign.SpaceAround);
  35. }
  36. build() {
  37. RelativeContainer() {
  38. Button('弹窗')
  39. .alignRules({
  40. center: { anchor: '__container__', align: VerticalAlign.Center },
  41. middle: { anchor: '__container__', align: HorizontalAlign.Center }
  42. })
  43. .onClick(() => {
  44. this.getUIContext().getPromptAction().openCustomDialog({
  45. builder: () => {
  46. this.customDialogComponent();
  47. },
  48. alignment: DialogAlignment.Center
  49. }).then((dialogId: number) => {
  50. this.customDialogComponentId = dialogId;
  51. });
  52. });
  53. }
  54. .width('100%')
  55. .height('100%');
  56. }
  57. }

效果如下:

在 FAQ 中进行搜索
请输入您想要搜索的关键词