HarmonyKit | 鸿蒙新特性:router 导航 API 从 pushUrl 到 UIContext 的演进

HarmonyKit | 鸿蒙新特性:router 导航 API 从 pushUrl 到 UIContext 的演进

引言:一个全局 API 的谢幕

HarmonyKit 初期使用全局 router.pushUrl() 做页面跳转。后来 DevEco Studio 的编译器开始对 router.pushUrl() 报 deprecated 警告:"推荐使用 this.getUIContext().getRouter().pushUrl()"。从全局函数到 UI 上下文绑定------这个 API 演进背后是鸿蒙多窗口能力的底层架构变化。

这篇文章梳理了 router API 的演进时间线、迁移前后的代码对比、同样受影响的 promptAction.showToast 的迁移路径、以及 NavPathStack 作为下一代导航方案的展望。

项目仓库:https://atomgit.com/VON-/harmony-kit

为什么废弃全局 router

全局 router 的核心问题是:在支持多窗口的 HarmonyOS 设备上,全局 router 不知道"当前应该操作哪个窗口的页面栈"。

场景:应用在分屏模式下有两个窗口,分别是"主页"和"工具页"。用户在主窗口的 ToolCard 上点了一下,跳转到 JSON 格式化工具。全局 router.pushUrl() 应该把页面推入哪个窗口的栈?全局 router 无法判断------它只知道"有一个 pushUrl 调用",但不知道调用来自哪个 UI 上下文。

UIContext 绑定 router 解决了这个问题。this.getUIContext() 返回当前组件所在的 UI 上下文。getRouter() 返回的是这个上下文专属的路由实例。主窗口的点击推入主窗口的栈,副窗口的点击推入副窗口的栈------各走各路。

这个演进不仅是鸿蒙系统的独有趋势。Android 的 startActivity 在分屏模式下同样需要指定 ActivityOptions 来控制在哪个屏幕启动 Activity。iOS 的 UIScene API 也要求场景感知的导航。多窗口是操作系统发展的必然方向,而从全局 API 到上下文绑定 API 的迁移,是所有框架都必须经历的架构调整。

迁移代码对比

typescript 复制代码
// === 旧写法(已废弃)===
import { router } from '@kit.ArkUI';

// 跳转
router.pushUrl({ url: 'pages/tools/JsonFormatter' });

// 返回
router.back();

// === 新写法(推荐)===
// 不需要 import router

// 跳转
this.getUIContext().getRouter().pushUrl({ url: 'pages/tools/JsonFormatter' });

// 返回
this.getUIContext().getRouter().back();

改动的核心:不再依赖全局 router 对象,而是通过当前 UI 上下文获取路由实例。多窗口场景下每个窗口的路由栈独立,但 HarmonyKit 作为手机单窗口应用,新旧写法在功能上没有差异------迁移纯粹是为了消除 compiler warning 和拥抱未来兼容性。

pushUrl 的完整参数

新版本 pushUrl 支持完整的 Options 配置:

typescript 复制代码
this.getUIContext().getRouter().pushUrl({
  url: 'pages/tools/JsonFormatter',
  params: { input: '{"test": true}' }  // 携带参数到目标页面
});

目标页面通过 @State@Prop 接收参数。在之前的 HarmonyKit 版本中,工具页不需要接收参数(所有工具都是从空白状态启动),但这个能力在更复杂的导航场景中至关重要。

promptAction.showToast 的同样命运

typescript 复制代码
// === 旧写法 ===
import { promptAction } from '@kit.ArkUI';
promptAction.showToast({ message: '已复制到剪贴板' });

// === 新写法 ===
this.getUIContext().getPromptAction().showToast({ message: '已复制到剪贴板' });

废弃原因类似------全局 promptAction 在异步场景(setTimeout、Promise 回调)中会丢失 UI 上下文,导致 Toast 无法弹出。UIContext 绑定保证了异步回调中也能正确弹 Toast。

这是一个典型的问题:在 HarmonyKit 的哈希计算工具中,用户输入 → 点击计算 → 结果展示 → 点击复制(CopyButton)→ showToast。这个过程涉及多个异步步骤(哈希计算是 async/await),如果 showToast 是全局调用,在异步链路中可能丢失 UI 上下文。

HarmonyKit 的迁移方案

CopyButton 组件是 HarmonyKit 中唯一调用 showToast 的地方------共 10 个工具页的复制按钮共享此组件。迁移时只改 CopyButton 一个文件,10 个工具自动生效。这是组件化架构的优势------全局 API 迁移的成本被限制在一个组件内部。

此外,每个工具页都有独立的返回按钮(顶部导航栏),调用 router.back()。迁移到 UIContext 后,每个页面的返回按钮代码从:

typescript 复制代码
router.back();

改为:

typescript 复制代码
this.getUIContext().getRouter().back();

同样是"每页面改一行"的工作量。10 个工具页共 10 行修改,没有遗漏风险。

鸿蒙 API 废弃策略

鸿蒙的 API 废弃遵循"标记 → 警告 → 移除"的渐进策略。@deprecated 标记的 API 仍然可用,但编译器输出 warning。开发者有充分的时间窗口进行迁移。HarmonyKit 在收到 warning 后统一迁移------改动量不大(每个受影响的方法只改一行)。

从实际体验来看,这个策略的设计是合理的:

  • 标记阶段 :API 新增替代方法,旧方法标记为 @deprecated,文档同步更新。开发者可以选择立即迁移或等更成熟。
  • 警告阶段:编译器开始输出 warning,但功能不受影响。开发者收到 warning 后安排迁移时间。
  • 移除阶段:API 真正被移除,调用导致编译错误。通常跨越 3-5 个 API 版本,给开发者充分的迁移时间。

HarmonyKit 遇到的废弃 API 都处于警告阶段------编译不报错,只是输出 warning。但"warning 也是技术债",尽早迁移是合理的工程实践。

NavPathStack 配合 HdsNavigationnavDestination builder 是官方推荐的长期导航方案。它提供了声明式的路由映射、类型安全的路由参数、以及页面的自动释放和重建。

typescript 复制代码
// NavPathStack 的基本用法
@State pathStack: NavPathStack = new NavPathStack();

build() {
  HdsNavigation(this.pathStack) {
    // 声明路由表
    HdsNavDestination() {
      if (name === 'JsonFormatter') {
        JsonFormatterPage();
      }
      // 更多路由...
    }
    .title(...)
  }
}

// 跳转
this.pathStack.pushPath({ name: 'JsonFormatter' });

NavPathStack 相比 router 的核心优势:

  1. 声明式路由映射:路由表集中管理,一目了然
  2. 类型安全:路由参数的类型在编译期检查
  3. 自动释放:页面出栈后自动销毁,减少内存占用
  4. 生命周期集成:与 HdsNavigation 的 titleBar、toolbar 无缝集成

HarmonyKit 目前的页面栈深度不超过 2 层(主页 → 工具页),router 够用。对于更复杂的应用(多级导航、嵌套 Tab、动态路由注册),NavPathStack 是值得考虑的迁移目标。

维度 router NavPathStack
API 形式 全局函数 实例方法
多窗口支持 不支持(废弃原因) 原生支持
参数类型安全 运行时检查 编译期检查
路由声明 独立 JSON 文件 集中式 builder
页面释放 手动管理 自动管理
与 HDS 集成 需要手动适配 原生集成
学习成本

对于新项目,建议直接使用 NavPathStack。对于已有项目如 HarmonyKit,迁移需要权衡:当前的 router 方案在所有设备上都能正常运行,迁移到 NavPathStack 需要重写主页的导航逻辑和所有工具页的路由声明。在没有实际痛点的情况下,这是一个"可以做但不是必须做"的改进项。

项目仓库:https://atomgit.com/VON-/harmony-kit

相关推荐
星释1 小时前
鸿蒙智能体开发实战:31.鸿蒙壁纸大师 - 环境搭建与基础配置
算法·华为·ai·harmonyos·鸿蒙
ysa0510301 小时前
【板子】树上启发式合并
数据结构·c++·笔记·算法
特立独行的猫a1 小时前
鸿蒙PC开源软件迁移与多语言三方库移植实战课程讲稿(三、命令行工具移植实战——以OpenSSH为主线)
华为·harmonyos·三方库移植·鸿蒙pc
学究天人2 小时前
数学公理体系大全:第一章 命题逻辑:真值之舞
人工智能·算法·机器学习·数学建模·动态规划·图论·抽象代数
小O的算法实验室2 小时前
2025年Neurocomputing,基于LLM的进化优化器:结合精英策略推理
算法
程序员黑豆2 小时前
鸿蒙应用开发之全局状态管理:AppStorageV2轻松实现登录到个人中心数据共享
华为·harmonyos·鸿蒙
进击的前栈2 小时前
鸿蒙实战:全栈回顾——Kit API 全景、架构总结与未来演进
华为·架构·harmonyos
在书中成长2 小时前
HarmonyOS 小游戏《对战五子棋》开发第33篇 - AI异步落子与setTimeout
人工智能·harmonyos
listening7772 小时前
HarmonyOS 6.1 分布式文件服务实战:跨设备商品图片/视频秒开方案
wpf·harmonyos