本文是「鸿蒙 6.1 API 23 开发坑系列」第 10 篇(非 UI 系第 4 篇)。本篇讲 @ohos.promptAction namespace(API 9+,鸿蒙 6.1 API 23 基座)—— 弹窗 promptAction.showToast/showDialog/showActionMenu + ToastType/DialogAlignment/BaseDialogOptions/DialogButton 类型。鸿蒙坑根因:① promptAction.showToast/showDialog/showActionMenu 是废弃顶层函数(API 18 废弃,迁移到 UIContext.getPromptAction() 实例方法 promptAction.showToast/showDialog/showActionMenu);② ToastType enum 常量 Default=0/Bottom=1/Center=2/Top=3 不是字符串 'Bottom';③ ShowToastOptionsduration 单位是 10ms(传 3000 显示 30 秒不是 3 秒,要传 300 才 3 秒);④ showDialog 回调 onAccept/onCancel 不是 onConfirm/onAbort(React confirm 命名差异);⑤ DialogButtonaction 是回调函数不是 onClick 字段;⑥ showActionMenuoptions 数组上限 6 个(超过运行错),不是无限。

一、开篇:鸿蒙 promptAction 不是浏览器 confirm/alert,是「namespace 顶层函数 getPromptAction + ToastType enum」

你写 Web 前端时,弹窗用 window.alert/window.confirm/window.prompt(同步阻塞,返回布尔值或字符串):

// Web:window.alert/confirm/prompt 同步阻塞弹窗
window.alert('hello web alert')  // ✅ 同步阻塞 alert
const ok = window.confirm('确认删除?')  // ✅ confirm 返回 boolean 同步
const name = window.prompt('请输入姓名', '张三')  // ✅ prompt 返回 string 同步
// Web confirm 的确认/取消是 confirm 返回值 true/false,不是回调命名

你写鸿蒙 ArkTS 时,弹窗用 promptAction.showToast/showDialog/showActionMenu namespace 顶层函数(全异步 Promise,回调 onAccept/onCancel 不是同步返回):

// ArkTS promptAction.showToast:namespace 顶层函数,ToastType enum 常量不是字符串
import promptAction from '@ohos.promptAction'  // ✅ default import(promptAction 是 namespace)

// ✅ showToast 带 ShowToastOptions + ToastType enum 常量(不是字符串'Bottom',不是同步)
promptAction.showToast({
  message: 'hello harmony toast',
  duration: 300,  // ✅ duration 单位 10ms(传 300 = 3 秒,不是传 3000 = 30 秒)
  bottom: '100px',
  showMode: promptAction.ToastShowMode.DEFAULT  // ✅ ToastShowMode enum 常量不是字符串
})
// 鸿蒙坑根因:showToast 废弃迁移 getPromptAction,duration 单位 10ms 不是 1ms

Web vs 鸿蒙 promptAction 的区别:Web 把弹窗当同步阻塞函数(window.confirm 返回 booleanwindow.prompt 返回 string,阻塞主线程直到用户操作),ArkTS 把弹窗当异步 namespace 顶层函数(promptAction.showToast/showDialog/showActionMenu 全 Promise,回调 onAccept/onCancel 不是同步返回值)。根因不是同步是异步 namespace——鸿蒙 promptAction.showToast/showDialog/showActionMenu 废弃迁移到 UIContext.getPromptAction() 实例方法(API 18 废弃),ToastType enum 常量 Default/Bottom/Center/Top 不是字符串(Web 没有 Toast 位置枚举,鸿蒙 enum 值是数字 0/1/2/3)。

二、根因:鸿蒙 @ohos.promptAction 的六个绑定机制

鸿蒙 @ohos.promptAction namespace(API 9+)核心导出 promptAction.showToast/showDialog/showActionMenu/promptAction.openCustomDialog/promptAction.openCustomDialogWithBuilder 顶层函数(API 18 废弃迁移到 UIContext.getPromptAction() 实例方法)+ ToastType/ToastShowMode/DialogAlignment/DialogButton/DialogOptions/ActionMenuOptions 类型。绑定机制来自六重根因。

机制 1:showToast/showDialog/showActionMenu 废弃顶层函数——迁移到 getPromptAction().showToast

鸿蒙坑根因:promptAction.showToast/showDialog/showActionMenu 是废弃顶层函数,API 18 废弃迁移到 UIContext.getPromptAction() 实例方法:

// ❌ 鸿蒙坑:promptAction.showToast/showDialog/showActionMenu 是废弃顶层函数(API 18 废弃)
import promptAction from '@ohos.promptAction'

// ❌ 废弃 API(API 9~17):顶层函数有 IDE 警告 deprecated
promptAction.showToast({ message: 'hello' })  // ❌ 废弃 deprecated IDE 警告
promptAction.showDialog({ title: '确认', buttons: [{ text: 'ok' }] })  // ❌ 废弃 deprecated
promptAction.showActionMenu({ title: '菜单', buttons: [{ text: '选项1' }] })  // ❌ 废弃 deprecated

// ✅ 正确用法:getUIContext().getPromptAction() 实例方法(不是废弃顶层函数)
import { getUIContext } from '@kit.ArkUI'  // ✅ getUIContext 从 @kit.ArkUI 不是 @ohos.promptAction
const prompt = getUIContext().getPromptAction()  // ✅ getPromptAction() 造实例
prompt.showToast({ message: 'hello' })  // ✅ 实例方法 showToast 不是废弃顶层函数
prompt.showDialog({ title: '确认', buttons: [{ text: 'ok' }] })  // ✅ 实例方法 showDialog
prompt.showActionMenu({ title: '菜单', buttons: [{ text: '选项1' }] })  // ✅ 实例方法 showActionMenu
// 鸿蒙坑根因:showToast/showDialog/showActionMenu 废弃迁移 getPromptAction(),IDE 警告 deprecated

废弃 showToast/showDialog/showActionMenu 坑根因:鸿蒙 API 9~17 用 promptAction.showToast(options) 顶层函数显示弹窗,API 18 废弃迁移到 getUIContext().getPromptAction() 实例方法(prompt.showToast(options))。鸿蒙坑:用废弃 promptAction.showToast 不会编译错(deprecated 不是 removed),但 IDE 警告 'showToast' has been deprecated,且废弃的顶层函数在某些新 SysCap 上下文失效(如 ComponentV2 里调顶层函数找不到 UI 上下文)。新代码必须 getUIContext().getPromptAction() 造实例后调实例方法。React window.alert 没有 deprecated 版本,鸿蒙 promptAction.showToast deprecated 是因为 API 18 把弹窗统一到 UIContext 实例方法(跟篇 6 animator.create 废弃迁移到 getUIContext().createAnimator()、篇 9 router.push 废弃迁移到 pushUrl 同理)。

机制 2:ToastType enum 常量 Default=0/Bottom=1/Center=2/Top=3 不是字符串’Bottom’

鸿蒙坑根因:ToastType enum 常量 Default=0(默认)/Bottom=1(底部)/Center=2(居中)/Top=3(顶部),不是字符串 'Bottom'

// ❌ 鸿蒙坑:ToastType enum 常量不是字符串'Bottom'(传字符串编译错)
import promptAction from '@ohos.promptAction'

// ❌ 传字符串'Bottom'编译错(ToastType 类型是 enum 不是 string)
promptAction.showToast({ message: 'hello', toastType: 'Bottom' })  // ❌ toastType 类型 enum 不是 string
promptAction.showToast({ message: 'hello', toastType: 'Top' })      // ❌ 传字符串编译错

// ✅ 正确用法:ToastType enum 常量 Default=0 / Bottom=1 / Center=2 / Top=3(不是字符串)
promptAction.showToast({ message: 'hello', toastType: promptAction.ToastType.Bottom })  // ✅ enum 常量 Bottom=1
promptAction.showToast({ message: 'hello', toastType: promptAction.ToastType.Center })  // ✅ enum 常量 Center=2
promptAction.showToast({ message: 'hello', toastType: promptAction.ToastType.Top })     // ✅ enum 常量 Top=3

// ✅ ToastType enum 常量语义:
// Default=0:默认位置(底部偏上,跟随系统配置)
// Bottom=1:底部对齐(距屏幕底部 bottom 参数指定距离)
// Center=2:屏幕居中显示
// Top=3:顶部对齐
const bottomType: promptAction.ToastType = promptAction.ToastType.Bottom  // ✅ Bottom=1
const centerType: promptAction.ToastType = promptAction.ToastType.Center  // ✅ Center=2
// 鸿蒙坑根因:ToastType enum 常量 Default/Bottom/Center/Top 不是字符串,enum 值是数字 0/1/2/3

ToastType enum 坑根因:鸿蒙 ToastType enum 的四个常量是 Default=0(默认位置,底部偏上跟随系统)/Bottom=1(底部对齐,距屏幕底部 bottom 参数指定距离)/Center=2(屏幕居中)/Top=3(顶部对齐)。鸿蒙坑:传字符串 'Bottom' 触发 Type 'string' is not assignable to type 'ToastType' 编译错——必须传 promptAction.ToastType.Bottom enum 常量(enum 值是数字 1 不是字符串)。Web window.alert 没有 toastType 参数(alert 是模态对话框居中),鸿蒙 showToasttoastType enum 控制位置(不是模态对话框,是轻量 toast 提示)。

机制 3:ShowToastOptions.duration 单位是 10ms 不是 1ms——传 3000 显示 30 秒不是 3 秒

鸿蒙坑根因:ShowToastOptions.duration 单位是 10ms,传 3000 显示 30 秒不是 3 秒,要传 300 才 3 秒:

// ❌ 鸿蒙坑:ShowToastOptions.duration 单位是 10ms 不是 1ms(传 3000 显示 30 秒)
import promptAction from '@ohos.promptAction'

// ❌ 传 3000 期望 3 秒但实际显示 30 秒(duration 单位 10ms,3000 × 10ms = 30 秒)
promptAction.showToast({ message: 'hello', duration: 3000 })  // ❌ 显示 30 秒(不是 3 秒)

// ✅ 正确用法:duration 单位 10ms,传 300 = 3 秒(300 × 10ms = 3000ms = 3 秒)
promptAction.showToast({ message: 'hello', duration: 300 })  // ✅ 显示 3 秒
promptAction.showToast({ message: 'hello', duration: 500 })  // ✅ 显示 5 秒
// ✅ duration 默认值 220(2.2 秒),最小值 10(0.1 秒),最大值 600(6 秒,超过被裁到 600)
promptAction.showToast({ message: 'hello' })  // ✅ duration 默认 220 显示 2.2 秒
// 鸿蒙坑根因:duration 单位 10ms 不是 1ms,传 300 = 3 秒,最大值 600 = 6 秒被裁

duration 10ms 单位坑根因:鸿蒙 ShowToastOptions.duration 的单位是 10ms(不是 1ms,不是 1 秒),值的范围 [10, 600](默认 220 = 2.2 秒,最小 10 = 0.1 秒,最大 600 = 6 秒,超过被裁到 600)。鸿蒙坑:前端开发者习惯 React toast.duration 单位是毫秒(duration: 3000 = 3 秒),鸿蒙 duration 单位是 10ms——传 3000 显示 30 秒(但实际被裁到最大 600 = 6 秒,不会真 30 秒,但语义错),传 300 才 3 秒。Web setTimeout 单位是 1ms,鸿蒙 duration 单位是 10ms(鸿蒙用 10ms 做单位是历史 API 8 遗留,API 9+ 为兼容未改)。

机制 4:showDialog 回调 onAccept/onCancel 不是 onConfirm/onAbort——React confirm 命名差异

鸿蒙坑根因:showDialog 回调 onAccept(确认)/onCancel(取消)不是 onConfirm/onAbort,跟 React confirm 命名差异:

// ❌ 鸿蒙坑:showDialog 回调是 onAccept/onCancel 不是 onConfirm/onAbort(命名差异)
import promptAction from '@ohos.promptAction'

// ❌ 用 onConfirm/onAbort 编译错(ShowDialogOptions 没有这两个字段)
promptAction.showDialog({
  title: '确认删除',
  onConfirm: () => { console.info('确认') },  // ❌ onConfirm 字段不存在(应是 onAccept)
  onAbort: () => { console.info('取消') }      // ❌ onAbort 字段不存在(应是 onCancel)
})

// ✅ 正确用法:onAccept(确认)+ onCancel(取消)+ onChange(多选切换)+ onComplete(完成)
promptAction.showDialog({
  title: '确认删除',
  buttons: [{ text: '取消', color: '#666666' }, { text: '确认', color: '#007dff' }],
  onAccept: () => { console.info('确认') },    // ✅ onAccept 是确认回调(不是 onConfirm)
  onCancel: () => { console.info('取消') }     // ✅ onCancel 是取消回调(不是 onAbort)
})
// 鸿蒙坑根因:showDialog 回调 onAccept/onCancel 不是 onConfirm/onAbort,React confirm 命名差异

showDialog 回调命名坑根因:鸿蒙 promptAction.showDialog(options) 的回调是 onAccept: () => void(用户确认)/onCancel: () => void(用户取消)/onChange: (value: string) => void(多选切换,API 11+)/onComplete: (select: number[]) => void(完成,多选时返回选中索引数组)。鸿蒙坑:前端开发者习惯 React confirmonConfirm/onAbort 命名(或 onOk/onCancel),鸿蒙用 onAccept/onCancel——onConfirm/onAbort 字段在 ShowDialogOptions 里不存在,编译错 Property 'onConfirm' does not exist on type 'ShowDialogOptions'。必须用 onAccept(确认)不是 onConfirmonCancel(取消)不是 onAbort。Web window.confirm 是同步返回 boolean 没有回调,鸿蒙 showDialog 是异步带回调(onAccept/onCancel 分开传)。

机制 5:DialogButton 的 action 是回调函数不是 onClick 字段——button 字段 text/color/bold

鸿蒙坑根因:DialogButtonaction 是回调函数不是 onClick 字段,button 字段是 text/color/bold

// ❌ 鸿蒙坑:DialogButton 的 action 是回调函数不是 onClick 字段
import promptAction from '@ohos.promptAction'

// ❌ 用 onClick 字段编译错(DialogButton 没有 onClick 字段,回调是 action)
promptAction.showDialog({
  title: '确认',
  buttons: [{ text: '确认', onClick: () => { console.info('点击') } }]  // ❌ onClick 字段不存在
})

// ❌ DialogButton 没有 bgColor/background 字段(只能 color 文字颜色,不能背景色)
promptAction.showDialog({
  title: '确认',
  buttons: [{ text: '确认', bgColor: '#007dff' }]  // ❌ bgColor 字段不存在(只能 color 文字色)
})

// ✅ 正确用法:DialogButton 字段 text/color/bold/action(action 是回调不是 onClick)
promptAction.showDialog({
  title: '确认',
  buttons: [{
    text: '确认',           // ✅ text 按钮文字
    color: '#007dff',       // ✅ color 按钮文字颜色(不是 bgColor 背景色)
    bold: true,             // ✅ bold 是否粗体(可选,默认 false)
    action: () => {         // ✅ action 是回调函数(不是 onClick 字段)
      console.info('确认按钮点击')
    }
  }]
})
// 鸿蒙坑根因:DialogButton 回调是 action 不是 onClick,字段 text/color/bold 不是 bgColor

DialogButton action 坑根因:鸿蒙 DialogButton 的字段是 text: string(按钮文字)/color: ResourceColor(按钮文字颜色,不是背景色)/bold: boolean(是否粗体,可选默认 false)/action: () => void(按钮点击回调函数)。鸿蒙坑:前端开发者习惯 React <Button onClick={...}>onClick 字段,鸿蒙 DialogButtonaction——onClick 字段不存在编译错。且鸿蒙 DialogButton 只有 color(文字色)没有 bgColor/background(背景色,鸿蒙对话框按钮背景跟随系统主题不能自定义),React <Button style={{ background: '...' }}> 能自定义背景色,鸿蒙不能。Web confirm 的确认/取消是返回值,鸿蒙 showDialog 的确认/取消是 DialogButton.action 回调(每个按钮独立的 action)。

机制 6:showActionMenu options 数组上限 6 个——超过运行错不是无限

鸿蒙坑根因:showActionMenuoptions 数组上限 6 个(超过运行错),不是无限:

// ❌ 鸿蒙坑:showActionMenu 的 buttons 数组上限 6 个(超过运行错,不是无限)
import promptAction from '@ohos.promptAction'

// ❌ buttons 数组超过 6 个运行错(ActionMenuOptions 的 buttons 上限 6)
promptAction.showActionMenu({
  title: '菜单',
  buttons: [
    { text: '选项1' }, { text: '选项2' }, { text: '选项3' },
    { text: '选项4' }, { text: '选项5' }, { text: '选项6' },
    { text: '选项7' }  // ❌ 第 7 个超过上限 6 运行错
  ]
})

// ✅ 正确用法:buttons 数组 1~6 个(上限 6,超过运行错弹出失败)
promptAction.showActionMenu({
  title: '菜单',
  buttons: [
    { text: '选项1', action: () => { console.info('选1') } },
    { text: '选项2', action: () => { console.info('选2') } },
    { text: '选项3', action: () => { console.info('选3') } }
  ]  // ✅ 3 个按钮在 1~6 范围内
})
// 鸿蒙坑根因:showActionMenu buttons 上限 6 个,超过运行错不是无限

showActionMenu buttons 上限 6 坑根因:鸿蒙 promptAction.showActionMenu(options)ActionMenuOptions.buttons 数组上限是 6 个按钮(API 9~至今未变),超过 6 个运行错(弹窗不弹出,日志报 buttons count exceeds maximum 6)。鸿蒙坑:前端开发者习惯 React 菜单无限选项(<Menu><MenuItem> 滚动列表),鸿蒙 showActionMenu 硬限 6 个按钮(鸿蒙设计用 6 个按钮上限避免弹窗过长遮挡内容,超过要改用 List 弹窗或自定义 CustomDialog)。且 showActionMenuDialogButtonshowDialog 共用类型(字段 text/color/bold/actionaction 是回调不是 onClick)。Web confirm 没有 6 选项概念(confirm 只 2 个按钮确认/取消),鸿蒙 showActionMenu 多选项但限 6 个。

三、真机配图:鸿蒙 @ohos.promptAction 弹窗坑——ToastType enum 常量 + duration 10ms + onAccept 非 onConfirm

toast 初始态 toast enum+duration 态 showDialog onAccept 态 showActionMenu buttons 态 getPromptAction 不废弃 态

真机配图展示鸿蒙 @ohos.promptAction 弹窗坑:

  • toast 初始态:鸿蒙 6.1 @ohos.promptAction 弹窗坑标题,4 个验证按钮(① ToastType enum+duration 10ms / ② showDialog onAccept 非 onConfirm / ③ showActionMenu buttons 上限 6 / ④ getPromptAction 不废弃),要点说明 7 条
  • toast enum+duration 态:点击「① 验证 ToastType enum+duration」按钮,显示「✅ ToastType enum 常量 Default=0/Bottom=1/Center=2/Top=3 不是字符串,duration 单位 10ms 传 300=3 秒」+ toast 弹出 3 秒——ToastType enum 常量 + duration 10ms 单位验证
  • showDialog onAccept 态:点击「② 验证 showDialog onAccept 非 onConfirm」按钮,显示「✅ showDialog 回调 onAccept/onCancel 不是 onConfirm/onAbort,DialogButton.action 不是 onClick」+ 对话框弹出——onAccept 非 onConfirm + DialogButton.action 非 onClick 验证
  • showActionMenu buttons 态:点击「③ 验证 showActionMenu buttons 上限 6」按钮,显示「✅ showActionMenu buttons 数组上限 6 个不是无限,超过运行错」+ 菜单弹出 3 个选项——buttons 上限 6 验证
  • getPromptAction 不废弃 态:点击「④ 验证 getPromptAction 不废弃」按钮,显示「✅ getUIContext().getPromptAction() 实例方法不是废弃顶层函数 promptAction.showToast」——showToast 废弃迁移 getPromptAction 验证

四、真解法:鸿蒙 @ohos.promptAction 的四个场景

场景 1:getPromptAction().showToast 带 ToastType.Bottom + duration 300 单位 10ms——90% 场景首选

轻量 toast 提示用 getUIContext().getPromptAction().showToast(options) + ToastType enum 常量 + duration 单位 10ms:

// ✅ 场景 1:getPromptAction().showToast 带 ToastType.Bottom + duration 300 单位 10ms(API 18,90% 场景首选)
import { getUIContext } from '@kit.ArkUI'  // ✅ getUIContext 从 @kit.ArkUI 不是 @ohos.promptAction

@Entry
@Component
struct Index {
  showToastTop() {
    // ✅ getUIContext().getPromptAction() 造实例(不是废弃的 promptAction 顶层 import)
    const prompt = getUIContext().getPromptAction()  // ✅ getPromptAction() 造实例
    prompt.showToast({
      message: '删除成功',
      duration: 300,  // ✅ duration 单位 10ms,传 300 = 3 秒(不是传 3000 = 30 秒)
      toastType: promptAction.ToastType.Bottom,  // ✅ ToastType enum 常量不是字符串'Bottom'
      bottom: '100px'  // ✅ bottom 距底部 100px(toastType=Bottom 时生效)
    })
    // ✅ showToast 不返回 Promise(异步弹出无返回,不像 showDialog 返回 Promise)
  }

  build() { Column({ space: 8 }) { Button('toast').onClick(() => this.showToastTop()) } }
}
// getPromptAction + showToast + ToastType.Bottom:90% 场景首选,duration 300 = 3 秒

鸿蒙 @ohos.promptAction API 真名坑import promptAction from '@ohos.promptAction'(default import,promptAction 是 namespace,但用顶层函数会 deprecated 警告);import { getUIContext } from '@kit.ArkUI'getUIContext@kit.ArkUI 不是 @ohos.promptAction);getUIContext().getPromptAction(): PromptAction(造实例,实例方法 showToast/showDialog/showActionMenu 不废弃);PromptAction.showToast(options: ShowToastOptions): void(不返回 Promise,异步弹出无返回);promptAction.ToastType enum 常量 Default=0/Bottom=1/Center=2/Top=3(不是字符串);ShowToastOptions.duration 单位 10ms(范围 [10, 600],默认 220 = 2.2 秒,传 300 = 3 秒);SysCap SystemCapability.ArkUI.ArkUI.Full@atomicservice 原子化服务(API 11+)。

场景 2:getPromptAction().showDialog 带 onAccept 非 onConfirm + DialogButton.action 非 onClick

确认对话框用 getPromptAction().showDialog(options) + 回调 onAccept/onCancel + DialogButton.action

// ✅ 场景 2:getPromptAction().showDialog 带 onAccept 非 onConfirm + DialogButton.action 非 onClick(API 18)
import { getUIContext } from '@kit.ArkUI'
import promptAction from '@ohos.promptAction'  // ✅ ToastType/DialogButton 类型用

@Entry
@Component
struct Index {
  showConfirmDialog() {
    const prompt = getUIContext().getPromptAction()
    // ✅ showDialog 返回 Promise<void>(带 buttons 时通过 action 回调,不带 buttons 时通过 onAccept/onCancel)
    prompt.showDialog({
      title: '确认删除',
      message: '删除后不可恢复,确认删除该条目?',
      alignment: promptAction.DialogAlignment.Center,  // ✅ DialogAlignment enum 常量不是字符串'Center'
      buttons: [
        {
          text: '取消',
          color: '#666666',  // ✅ DialogButton.color 文字颜色(不是 bgColor 背景色)
          action: () => {  // ✅ DialogButton.action 是回调(不是 onClick 字段)
            console.info('取消按钮点击')
          }
        },
        {
          text: '确认',
          color: '#007dff',
          bold: true,  // ✅ bold 粗体(可选默认 false)
          action: () => {
            console.info('确认按钮点击,执行删除')
            // ✅ 执行删除逻辑(action 回调里)
          }
        }
      ],
      // ✅ onAccept/onCancel 在不带 buttons 时生效(带 buttons 用 button.action 回调)
      onAccept: () => { console.info('确认') },    // ✅ onAccept 不是 onConfirm
      onCancel: () => { console.info('取消') }     // ✅ onCancel 不是 onAbort
    }).then(() => { console.info('对话框关闭') })
  }

  build() { Column({ space: 8 }) { Button('删除').onClick(() => this.showConfirmDialog()) } }
}
// showDialog + onAccept + DialogButton.action:onAccept 非 onConfirm,action 非 onClick,color 非 bgColor

鸿蒙 showDialog + DialogButton API 真名坑promptAction.showDialog(options: ShowDialogOptions): Promise<void>(返回 Promise,关闭时 resolve);ShowDialogOptions 字段 title/message/alignment: DialogAlignment/buttons: DialogButton[]/onAccept/onCancel/onChange/onComplete(不是 onConfirm/onAbort);DialogButton 字段 text/color: ResourceColor/bold: boolean/action: () => void(不是 onClick,没有 bgColor/background);promptAction.DialogAlignment enum 常量 Top=0/Center=1/Bottom=2/Default=3(不是字符串 'Center');鸿蒙坑:React confirmonConfirm/onAbort,鸿蒙 showDialogonAccept/onCancel(命名差异编译错);React <Button onClick>onClick,鸿蒙 DialogButtonaction(字段差异编译错);鸿蒙 DialogButton 没有 bgColor(只能 color 文字色,背景色跟系统主题)。

场景 3:getPromptAction().showActionMenu 带 buttons 上限 6 个 + action 回调非 onClick

操作菜单用 getPromptAction().showActionMenu(options) + buttons 数组上限 6 个 + DialogButton.action

// ✅ 场景 3:getPromptAction().showActionMenu 带 buttons 上限 6 个 + action 回调非 onClick(API 18)
import { getUIContext } from '@kit.ArkUI'

@Entry
@Component
struct Index {
  showShareMenu() {
    const prompt = getUIContext().getPromptAction()
    // ✅ showActionMenu 的 buttons 数组上限 6 个(超过运行错,不是无限)
    prompt.showActionMenu({
      title: '分享到',
      // ✅ buttons 1~6 个(上限 6,超过运行错 buttons count exceeds maximum 6)
      buttons: [
        { text: '微信', color: '#07C160', action: () => { console.info('分享微信') } },
        { text: '朋友圈', color: '#07C160', action: () => { console.info('分享朋友圈') } },
        { text: 'QQ', color: '#12B7F5', action: () => { console.info('分享QQ') } },
        { text: '微博', color: '#E6162D', action: () => { console.info('分享微博') } },
        { text: '复制链接', color: '#666666', action: () => { console.info('复制链接') } }
        // ✅ 5 个按钮在 1~6 范围内(第 7 个会运行错)
      ]
    }).then(() => { console.info('菜单关闭') })
  }

  build() { Column({ space: 8 }) { Button('分享').onClick(() => this.showShareMenu()) } }
}
// showActionMenu + buttons 上限 6 + action:buttons 超 6 运行错,action 非 onClick

鸿蒙 showActionMenu API 真名坑promptAction.showActionMenu(options: ActionMenuOptions): Promise<void>(返回 Promise,关闭时 resolve);ActionMenuOptions 字段 title: ResourceStr/buttons: DialogButton[](上限 6 个,超过运行错)/showInSubWindow: boolean(API 12+,是否在子窗口显示);DialogButton 字段同 showDialogtext/color/bold/action,不是 onClick,没有 bgColor);鸿蒙坑:React <Menu> 菜单无限选项(滚动列表),鸿蒙 showActionMenu 硬限 6 个按钮(超过运行错 buttons count exceeds maximum 6,弹窗不弹出);超过 6 个要改用 List 弹窗或 CustomDialog@CustomDialog 装饰器自定义弹窗,无按钮上限)。

场景 4:getPromptAction().openCustomDialogWithBuilder 自定义弹窗——@CustomBuilder 装饰器无按钮上限

自定义弹窗用 getPromptAction().openCustomDialogWithBuilder(builder, options) + @CustomBuilder 装饰器(无按钮上限):

// ✅ 场景 4:openCustomDialogWithBuilder 自定义弹窗 + @CustomBuilder 装饰器无按钮上限(API 11+)
import { getUIContext } from '@kit.ArkUI'
import promptAction from '@ohos.promptAction'

// ✅ @CustomBuilder 装饰器定义自定义弹窗内容(无按钮上限,自由布局)
@CustomBuilder
function myCustomDialogBuilder() {
  Column({ space: 12 }) {
    Text('自定义弹窗标题').fontSize(18).fontWeight(FontWeight.Bold)
    Text('这是自定义弹窗内容,可以放任意组件,按钮无上限').fontSize(14)
    // ✅ 自定义弹窗里按钮无上限(不像 showActionMenu 限 6 个)
    Row({ space: 8 }) {
      Button('选项1').onClick(() => { console.info('选1') })
      Button('选项2').onClick(() => { console.info('选2') })
      Button('选项3').onClick(() => { console.info('选3') })
      Button('选项4').onClick(() => { console.info('选4') })
      Button('选项5').onClick(() => { console.info('选5') })
      Button('选项6').onClick(() => { console.info('选6') })
      Button('选项7').onClick(() => { console.info('选7') })  // ✅ 自定义弹窗第 7 个不超限
    }
  }.padding(20).backgroundColor('#FFFFFF').borderRadius(12)
}

@Entry
@Component
struct Index {
  @State customDialogId: number = -1  // ✅ openCustomDialogWithBuilder 返回 dialogId(关闭用)

  showCustomDialog() {
    const prompt = getUIContext().getPromptAction()
    // ✅ openCustomDialogWithBuilder 带 @CustomBuilder 装饰器函数 + options(不是 builder 字符串)
    this.customDialogId = prompt.openCustomDialogWithBuilder(myCustomDialogBuilder, {
      alignment: promptAction.DialogAlignment.Center,  // ✅ DialogAlignment enum 常量不是字符串
      isModal: true  // ✅ isModal 模态(点击外部不关闭)
    })
    // ✅ 返回 dialogId(number),关闭用 promptAction.closeCustomDialog(dialogId)
  }

  closeCustomDialog() {
    const prompt = getUIContext().getPromptAction()
    if (this.customDialogId >= 0) {
      // ✅ closeCustomDialog 带 dialogId 关闭(不是 closeCustomDialogWithBuilder)
      prompt.closeCustomDialog(this.customDialogId)
      this.customDialogId = -1
    }
  }

  build() {
    Column({ space: 8 }) {
      Button('弹自定义').onClick(() => this.showCustomDialog())
      Button('关自定义').onClick(() => this.closeCustomDialog())
    }
  }
}
// openCustomDialogWithBuilder + @CustomBuilder:无按钮上限,返回 dialogId 关闭用 closeCustomDialog

鸿蒙 openCustomDialogWithBuilder API 真名坑PromptAction.openCustomDialogWithBuilder(builder: CustomBuilder, options?: CustomDialogOptions): number(带 @CustomBuilder 装饰器函数,返回 dialogId);PromptAction.closeCustomDialog(dialogId: number): void(带 dialogId 关闭,不是 closeCustomDialogWithBuilder);CustomDialogOptions 字段 alignment: DialogAlignment/isModal: boolean/offset: Dimension/autoCancel: boolean(点击外部是否关闭,默认 true);鸿蒙坑@CustomBuilder 装饰器定义弹窗内容(不是 @Builder@CustomBuilder 专用于自定义弹窗),自定义弹窗里按钮无上限(不像 showActionMenu 限 6 个);openCustomDialogWithBuilder 返回 dialogId 用于 closeCustomDialog 关闭(不是返回 Promise);React 自定义弹窗用 <Modal> 组件控制 open 属性,鸿蒙 openCustomDialogWithBuilder 返回 dialogId + closeCustomDialog 关闭(命令式 API 不是声明式)。

五、一句话哲学

写鸿蒙 ArkTS 记住:promptAction 不是浏览器 confirm/alert 是「namespace 顶层函数 getPromptAction + ToastType enum」——鸿蒙 6.1 API 23 @ohos.promptAction namespace(API 9+,鸿蒙 6.1 API 23 基座,promptAction.showToast/showDialog/showActionMenu/openCustomDialog/openCustomDialogWithBuilder 顶层函数 + ToastType/ToastShowMode/DialogAlignment/DialogButton/ShowToastOptions/ShowDialogOptions/ActionMenuOptions/CustomDialogOptions 类型,SysCap SystemCapability.ArkUI.ArkUI.Full,@atomicservice,API 18 废弃迁移到 UIContext.getPromptAction() 实例方法)。根因不是同步是异步 namespace——promptAction.showToast/showDialog/showActionMenu 废弃迁移到 getUIContext().getPromptAction() 实例方法(✅ getUIContext().getPromptAction().showToast(options) 不是废弃的 promptAction.showToast,❌ promptAction.showToast deprecated 有 IDE 警告 'showToast' has been deprecated,API 18 废弃迁移到 UIContext.getPromptAction() 实例方法,getUIContext@kit.ArkUI import 不是 @ohos.promptAction),ToastType enum 常量 Default=0/Bottom=1/Center=2/Top=3 不是字符串 'Bottom'(✅ promptAction.ToastType.Bottom/promptAction.ToastType.Center enum 常量,❌ 传字符串 'Bottom' 触发 Type 'string' is not assignable to type 'ToastType' 编译错,enum 值是数字 0/1/2/3 不是字符串),ShowToastOptions.duration 单位是 10ms 不是 1ms 不是 1 秒(✅ duration: 300 = 3 秒(300 × 10ms),❌ duration: 3000 期望 3 秒但实际 30 秒被裁到最大 600 = 6 秒,范围 [10, 600] 默认 220 = 2.2 秒,鸿蒙 API 8 历史遗留 10ms 单位),showDialog 回调 onAccept/onCancel 不是 onConfirm/onAbort(✅ onAccept(确认)+ onCancel(取消)+ onChange(多选切换)+ onComplete(完成),❌ onConfirm/onAbort 触发 Property does not exist on type 'ShowDialogOptions' 编译错,React confirmonConfirm/onAbort 命名差异),DialogButtonaction 是回调函数不是 onClick 字段(✅ action: () => void 回调,❌ onClick 触发 Property 'onClick' does not exist on type 'DialogButton' 编译错,React <Button onClick> 命名差异),DialogButton 字段 text/color(文字色)/bold 没有 bgColor/background(背景色跟系统主题不能自定义,React <Button style={{ background }}> 能自定义背景色),showActionMenubuttons 数组上限 6 个(超过运行错 buttons count exceeds maximum 6,弹窗不弹出,React <Menu> 无限选项差异,超过要改用 openCustomDialogWithBuilder + @CustomBuilder 自定义弹窗无按钮上限),openCustomDialogWithBuilder 返回 dialogId: number 不是 Promise(✅ prompt.closeCustomDialog(dialogId) 关闭,不是 closeCustomDialogWithBuilder),@CustomBuilder 装饰器(不是 @Builder)定义弹窗内容。showToast/showDialog/showActionMenu 废弃迁移 getPromptAction + ToastType enum 常量不是字符串 + duration 单位 10ms 不是 1ms + onAccept 非 onConfirm + DialogButton.action 非 onClick 无 bgColor + showActionMenu buttons 上限 6 是鸿蒙 6.1 @ohos.promptAction 弹窗坑核心!

能力系列回链

  • 鸿蒙 7.0 新特性篇 1~17(沉浸式毛玻璃/Component3D/智能体框架/方舟引擎/星盾安全/星河互联/空间音频/可变字体/游戏快启/分布式数据盾/LTPO 可变帧率/AI 文档识别/多形态服务窗口/AI 反诈/机密计算/空间计算/小艺全面进化)
  • 鸿蒙 6.1 API 23 开发坑系列篇 1「ArkUI.modifier 装饰器坑」——attributeModifier + AttributeModifier 状态化节点修改器
  • 鸿蒙 6.1 API 23 开发坑系列篇 2「arkui.componentSnapshot 组件截图坑」——get/getSync/createFromBuilder 返回 image.PixelMap 像素图
  • 鸿蒙 6.1 API 23 开发坑系列篇 3「arkui.node 节点坑」——NodeController abstract class makeNode override + BuilderNode WrappedBuilder
  • 鸿蒙 6.1 API 23 开发坑系列篇 4「arkui.UIContext UI 上下文坑」——runScopedTask 不是 runScopedOnUiThread + 11 个子管理器
  • 鸿蒙 6.1 API 23 开发坑系列篇 5「arkui.observer UI 观察器坑」——uiObserver namespace 真名不是 observer + on type string literal
  • 鸿蒙 6.1 API 23 开发坑系列篇 6「@ohos.animator 动画器坑」——import @kit.ArkUI 不是 @ohos.animator + onFrame 驼峰不是废弃 onframe + getUIContext().createAnimator 不是废弃 animator.create + 持引用 + aboutToDisappear cancel
  • 鸿蒙 6.1 API 23 开发坑系列篇 7「@ohos.net.http HTTP 请求坑」——HttpDataType 常量是 STRING 不是 STRING_TYPE + HttpRequest 是 interface 不能 new + http.createHttp() 工厂造实例 + on/off 监听不是 addEventListener + header Record 不是 Headers + RequestMethod enum 不是字符串
  • 鸿蒙 6.1 API 23 开发坑系列篇 8「@ohos.file.fs 文件管理坑」——writeSync/readSync 是 namespace 顶层函数不是 File 实例方法 + 第一参传 file.fd 文件描述符 + ReadOptions 无 encoding 读 ArrayBuffer 原字节 + WriteOptions 带 encoding 写字符串指定编码 + closeSync(file) 传 File 不是 fd + OpenMode enum 不是 flags 数字
  • 鸿蒙 6.1 API 23 开发坑系列篇 9「@ohos.router 页面路由坑」——router.push/replace 废弃迁移 pushUrl/replaceUrl + RouterMode enum 常量 Standard/Single 不是字符串 + RouterOptions.url 绝对路径不是相对路径 + getParams 返回 Object 要 as Record 转型 + RouterState 真属性 index/name 不是 stackLength + getLength 返回 string 不是 number
  • 鸿蒙 6.1 API 23 开发坑系列篇 10「@ohos.promptAction 弹窗坑」——showToast/showDialog/showActionMenu 废弃迁移 getPromptAction + ToastType enum 常量 Default/Bottom/Center/Top 不是字符串 + ShowToastOptions.duration 单位 10ms 不是 1ms + showDialog 回调 onAccept/onCancel 不是 onConfirm/onAbort + DialogButton.action 不是 onClick 无 bgColor + showActionMenu buttons 上限 6 不是无限(本文)
Logo

讨论HarmonyOS开发技术,专注于API与组件、DevEco Studio、测试、元服务和应用上架分发等。

更多推荐