HarmonyOS NEXT - Navigation组件封装BaseNavigation
demo 地址: https://github.com/iotjin/JhHarmonyDemo
代码不定时更新,请前往github查看最新代码
在demo中这些组件和工具类都通过module实现了,具体可以参考HarmonyOS NEXT - 通过 module 模块化引用公共组件和utils
官方介绍
组件导航 (Navigation)(推荐)
Navigation是路由容器组件,一般作为首页的根容器,包括单栏(Stack)、分栏(Split)和自适应(Auto)三种显示模式。Navigation组件适用于模块内和跨模块的路由切换,一次开发,多端部署场景。通过组件级路由能力实现更加自然流畅的转场体验,并提供多种标题栏样式来呈现更好的标题和内容联动效果。在不同尺寸的设备上,Navigation组件能够自适应显示大小,自动切换分栏展示效果。
Navigation组件主要包含导航页(NavBar)和子页(NavDestination)。导航页由标题栏(Titlebar,包含菜单栏menu)、内容区(Navigation子组件)和工具栏(Toolbar)组成,其中导航页可以通过hideNavBar属性进行隐藏,导航页不存在页面栈中,导航页和子页,以及子页之间可以通过路由操作进行切换。
在API Version 9上,需要配合NavRouter组件实现页面路由,从API Version 10开始,推荐使用NavPathStack实现页面路由。
这里里封装的只是组件,路由跳转通过 Router切换Navigation 或者 @ohos.route 跳转
demo中都是通过@ohos.router实现的跳转,因为Router需要Navigation 包着页面的内容,多一层嵌套
页面路由 (@ohos.router)(不推荐)
Router切换Navigation
Navigation官方效果图

BaseNavigation效果图

Navigation使用
@Entry
@Component
struct TestNav {// menus(value: Array<NavigationMenuItem> | CustomBuilder): NavigationAttributeaboutToAppear() {console.log('CustomComponent: aboutToAppear called. Component is about to appear.')// 在这里执行初始化数据的操作}build() {Column() {this.NavigationTest()}}TooTmp: NavigationMenuItem = {'value': "1",'action': () => {},'icon': "resources/rawfile/tab/nav_tab_1.png",}TooBar: ToolbarItem[] = [this.TooTmp, this.TooTmp, this.TooTmp]@BuilderNavigationTest() {Navigation() {RelativeContainer() {Text('Content').fontSize(50).fontWeight(FontWeight.Bold).alignRules({center: { anchor: '__container__', align: VerticalAlign.Center },middle: { anchor: '__container__', align: HorizontalAlign.Center }})}.height('100%').width('100%')}.titleMode(NavigationTitleMode.Mini).title("标题栏") // 设置title,此时不支持修改文字大小,颜色等样式.hideBackButton(false).menus([this.TooTmp, this.TooTmp, this.TooTmp]).toolbarConfiguration(this.TooBar)// .size({ width: '100%', height: '100%' })// .backgroundColor(Color.Orange)// .toolbarConfiguration(this.TooBar)}
}
BaseNavigation使用
demo里的弹框在这里 HarmonyOS NEXT - Toast和Loading使用
- 左侧返回,右侧文字
BaseNavigation({title: '标题标题标题标题标题标题标题标题标题标题',rightText: '设置',rightItemCallBack: () => {console.log("点击了设置")JhProgressHUD.showText("点击了设置")}})
- 左侧返回(拦截点击事件),右侧图片
BaseNavigation({title: '标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题',titleTextAlign: TextAlign.Start,// rightImgPath: 'resources/rawfile/images/ic_more_white.png',rightImgPath: $rawfile("images/ic_nav_add.png"),rightItemCallBack: () => {JhProgressHUD.showText("点击了右侧图标")},leftItemCallBack: () => {JhProgressHUD.showText("点击左侧")}})
- 左侧自定义右侧文字
BaseNavigation({title: '标题',titleTextAlign: TextAlign.Start,leftItem: {text: '设置1',icon: $rawfile("images/ic_nav_add.png"),itemCallBack: () => {JhProgressHUD.showText("点击了左侧")}},rightText: '发布',rightItemCallBack: () => {console.log("点击了设置")JhProgressHUD.showText("点击了发布")}})
- 渐变导航条
BaseNavigation({isGradient: true,title: '标题',// rightImgPath: 'resources/rawfile/images/ic_more_white.png',rightImgPath: $rawfile("images/ic_nav_add.png"),rightItemCallBack: () => {JhProgressHUD.showText("点击了右侧图标")}})
- 右侧自定义1
BaseNavigation({title: '标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题标题',titleTextAlign: TextAlign.Start,rightItems: [{text: '设置1',itemCallBack: () => {JhProgressHUD.showText("点击了设置1")}},{text: '设置2',itemCallBack: () => {JhProgressHUD.showText("点击了设置2")}}]})
- 内部包裹child内容
BaseNavigation({title: '自定义child',child: () => {this.childBuilder()}})@BuilderchildBuilder() {Scroll() {Column() {Text('111111111').width('100%').height(600).backgroundColor(Color.Orange)Text('222222222').width('100%').height(500).backgroundColor(Color.Yellow)}}}
JhProgressHud.ets 完整代码
/// BaseNavigation.ets
///
/// Created by iotjin on 2024/08/01.
/// description: 导航条import { router } from '@kit.ArkUI';
import { KColors } from '../configs/Colors';type imageType = string | Resource | PixelMapinterface ItemType {icon?: imageType // icon优先级高于texttext?: stringitemCallBack?: () => void
}const _titleFontSize = 18.0
const _textFontSize = 16.0
const _itemSpace = 15.0 // 右侧item内间距
const _imgWH = 22.0 // 右侧图片宽高
const _rate = 16 // 左右item占比const _bgColor: ResourceColor = KColors.kThemeColor
const _bgDarkColor: ResourceColor = KColors.kNavBgDarkColor
const _titleColor: ResourceColor = KColors.kNavTitleColorconst _appbarStartColor = KColors.kGradientStartColor // 默认appBar 渐变开始色
const _appbarEndColor = KColors.kGradientEndColor // 默认appBar 渐变结束色@Preview
@Component
export struct BaseNavigation {@Prop public title: string = '' // 标题文字private isCenterTitle: boolean = true@Prop public titleFontSize: number = _titleFontSize@Prop public titleTextAlign: TextAlign = this.isCenterTitle ? TextAlign.Center : TextAlign.Start@Prop public bgColor: ResourceColor = _bgColor@Prop public leftItem?: ItemType | null = null // 左侧Widget,为空显示返回按钮public leftItemCallBack?: () => void@Prop public rightText: string = '' // 右侧按钮文字@Prop public rightImgPath: imageType = '' // 右侧按钮图片路径,优先级高于text ,eg: $rawfile("images/ic_nav_add.png") | 'resources/rawfile/images/ic_nav_add.png'public rightItemCallBack?: () => void@Prop public rightItems: [] | [ItemType] | [ItemType, ItemType] = [] // 优先级高于rightText和rightImgPath@Prop public isGradient: boolean = false // 是否渐变背景色@Prop public navHeight: number = 56 // 传入child为100%,否则为navHeight@BuilderParam child?: () => void // 子组件//private backImage: imageType = $rawfile("common/ic_nav_back_white.png")private titleAndIconColor: ResourceColor = _titleColoraboutToAppear() {// 如果背景透明或者是白色,设置字体和图标、状态栏字体为黑色let isTransparent = this.bgColor == Color.Transparent || this.bgColor == Color.White || this.bgColor == KColors.kNavWhiteBgColorif (isTransparent) {this.titleAndIconColor = Color.Blackthis.backImage = $rawfile("common/ic_nav_back_black.png")}}build() {Navigation() {if (this.child) {this.child()}}.titleMode(NavigationTitleMode.Mini).title(this.NavigationTitle()).hideBackButton(true).height(this.child ? '100%' : this.navHeight)}@BuilderNavigationTitle() {Row() {this.navBuilder()}.width('100%').height('100%').backgroundColor(this.bgColor).linearGradient(this.isGradient ? {direction: GradientDirection.Right, // 从左向右colors: [[_appbarStartColor, 0.0], [_appbarEndColor, 1.0]]} : null)}@BuildernavBuilder() {Row() {if (this.leftItem) {Row() {this.itemBuilder({ icon: this.leftItem.icon, text: this.leftItem.text })}.onClick(this.leftItem.itemCallBack)} else {this.backBuilder()}}.layoutWeight(_rate).width('100%')Row() {this.titleBuilder()}.layoutWeight(this.rightItems.length ? (100 - _rate - this.rightItems.length * _rate) : (100 - _rate * 2)).width('100%')if (this.rightItems.length) {Row() {ForEach(this.rightItems, (item: ItemType) => {Row() {this.itemBuilder({ icon: item.icon, text: item.text })}.onClick(item.itemCallBack).layoutWeight(1).width('100%')})}.margin({ left: this.rightItems.length == 2 ? 15 : 0, right: this.rightItems.length == 2 ? 5 : 0 }).layoutWeight(_rate * this.rightItems.length).width('100%')} else {Row() {this.itemBuilder({ icon: this.rightImgPath, text: this.rightText })}.onClick(this.rightItemCallBack).layoutWeight(_rate).width('100%')}}@BuilderbackBuilder() {Row() {Image(this.backImage).width(18).height(18).margin({ left: 15 })}.size({ width: '100%', height: '100%' }).onClick(() => {if (this.leftItemCallBack) {this.leftItemCallBack()} else {this.goBack()}})}@BuildertitleBuilder() {Row() {Text(this.title).padding({left: 10,top: 5,right: 10,bottom: 5}).fontSize(this.titleFontSize).fontColor(this.titleAndIconColor).textAlign(this.titleTextAlign).maxLines(2).textOverflow({ overflow: TextOverflow.Ellipsis })// 文本超长显示省略号.wordBreak(WordBreak.BREAK_WORD)}.justifyContent(FlexAlign.Center).alignItems(VerticalAlign.Center).size({ width: '100%', height: '100%' })}@BuilderitemBuilder(item: ItemType) {Row() {if (item.icon) {Image(item.icon).width(_imgWH).height(_imgWH).margin({ left: _itemSpace, right: _itemSpace })} else if (item.text) {Text(item.text).fontSize(_textFontSize).fontColor(this.titleAndIconColor)}}.size({ width: '100%', height: '100%' }).justifyContent(FlexAlign.Center).alignItems(VerticalAlign.Center)}goBack() {router.back()}
}
里面用到的颜色
export class KColors {// 主题色(导航条背景、提交按钮背景、弹框确认文字、表单图标录入光标)// 暗黑模式高亮显示颜色按kThemeColor设置,如tabBar选中文字图标、提交按钮背景色、指示器选中下划线、光标等static readonly kThemeColor: ResourceColor = '#3BB815'static readonly kThemeDarkColor: ResourceColor = '#0A0A0A' // (10, 10, 10)static readonly kThemeBlueColor: ResourceColor = '#4688FA'static readonly kThemePurpleColor: ResourceColor = '#9C27B0'// 渐变色(appBar和按钮)static readonly kGradientStartColor: ResourceColor = '#2683BE' // 渐变开始色static readonly kGradientEndColor: ResourceColor = '#34CABE' // 渐变结束色static readonly kNavTitleColor: Color = Color.White
}
相关文章:
HarmonyOS NEXT - Navigation组件封装BaseNavigation
demo 地址: https://github.com/iotjin/JhHarmonyDemo 代码不定时更新,请前往github查看最新代码 在demo中这些组件和工具类都通过module实现了,具体可以参考HarmonyOS NEXT - 通过 module 模块化引用公共组件和utils 官方介绍 组件导航 (Navigation)(推…...
浅看MySQL数据库
有这么一句话:“一个不会数据库的程序员不是合格的程序员”。有点夸张,但是确是如此。透彻学习数据库是要学习好多知识,需要学的东西也是偏难的。我们今天来看数据库MySQL的一些简单基础东西,跟着小编一起来看一下吧。 什么是数据…...
Pytorch常用训练套路框架(CPU)
文章目录 1. 数据准备示例:加载 CIFAR-10 数据集 2. 模型定义示例:定义一个简单的卷积神经网络 3. 损失函数和优化器示例:定义损失函数和优化器 4. 训练循环示例:训练循环 5. 评估和测试示例:评估模型 6. 保存和加载模…...
C++ | Leetcode C++题解之第338题比特位计数
题目: 题解: class Solution { public:vector<int> countBits(int n) {vector<int> bits(n 1);for (int i 1; i < n; i) {bits[i] bits[i & (i - 1)] 1;}return bits;} };...
智慧校园云平台电子班牌系统源码,智慧教育一体化云解决方案
智慧校园云平台电子班牌系统,利用先进的云计算技术,将教育信息化资源和教学管理系统进行有效整合,实现生态基础数据共享、应用生态统一管理,为智慧教育建设的统一性,稳定性,可扩展性,互通性提供…...
数据库系统 第17节 数据仓库 案例赏析
下面我将通过几个具体的案例来说明数据仓库如何在不同的行业中发挥作用,并解决实际业务问题。 案例 1: 零售业 背景: 一家大型零售商希望改进其库存管理和市场营销策略,以提高销售额和顾客满意度。 解决方案: 数据仓库: 构建一个数据仓库࿰…...
硬件面试经典 100 题(71~90 题)
71、请问下图电路的作用是什么? 该电路实现 IIC 信号的电平转换(3.3V 和 5V 电平转换),并且是双向通信的。 上下两路是一样的,只分析 SDA 一路: 1) 从左到右通信(SDA2 为输入状态&…...
【git】代理相关
问题: 开启了翻墙代理工具,拉取代码时报错:fatal: 无法访问 xxxx : Failed to connect to github.com port 443: 连接超时 解决: 0,取消代理仍然无法拉取 1,查看控制面板-网络与Internet-代理ÿ…...
golang gin框架中创建自定义中间件的2种方式总结 - func(*gin.Context)方式和闭包函数方式定义gin中间件
在gin框架中,我们可以通过2种方式创建自定义中间件: 1. 直接定义一个类型为 func(*gin.Context)的函数或者方法 这种方式是我们常用的方式,也就是定义一个参数为*gin.Context的函数或者方法。定义的方法就是创建一个 参数类型为 gin.Handler…...
Linux高级编程 8.13 文件IO
一、文件IO 操作系统为了方便用户使用系统功能而对外提供的一组系统函数。称之为 系统调用(unistd.h) 其中有个 文件IO,一般都是对设备文件操作,当然也可以对普通文件进行操作。 这是一个基于Linux内核的没有缓存的IO机制 文件IO特性&…...
【k8s】ubuntu18.04 containerd 手动从1.7.15 换为1.7.20
ubutnu18.04之前手动安装了1.7.15现在下载1.7.20containerd-1.7.20-linux-amd64.tar.gz root@k8s-worker-i58265u:/home/zhangbin# root@k8s-worker-i58265u:/home/zhangbin# https://github.com/containerd/containerd/releases/download/v1.7.20/containerd-1.7.20-linux-am…...
常用浮动方式
目录 一、标准流 二、float浮动 三、 flex浮动 3.1flex组成 3.2 主轴对齐方式 3.3侧轴对齐方式 3.4修改主轴方向 3.5弹性盒子换行 3.6行对齐方式 一、标准流 标签在网页中的默认排布规则 例如: 块元素独占一行、行内元素可以一行显示多个 二、float浮动 让块…...
设计模式反模式:UML常见误用案例分析
文章目录 设计模式反模式:UML常见误用案例分析1. 反模式概述2. 反模式的 UML 图示误用2.1 God Object 反模式2.2 Spaghetti Code 反模式2.3 Golden Hammer 反模式2.4 Poltergeist 反模式 3. 总结 设计模式反模式:UML常见误用案例分析 在软件工程领域&am…...
Python编码系列—Python SQL与NoSQL数据库交互:深入探索与实战应用
🌟🌟 欢迎来到我的技术小筑,一个专为技术探索者打造的交流空间。在这里,我们不仅分享代码的智慧,还探讨技术的深度与广度。无论您是资深开发者还是技术新手,这里都有一片属于您的天空。让我们在知识的海洋中…...
贪心算法---跳跃游戏
题目: 给你一个非负整数数组 nums ,你最初位于数组的 第一个下标 。数组中的每个元素代表你在该位置可以跳跃的最大长度。 判断你是否能够到达最后一个下标,如果可以,返回 true ;否则,返回 false 。 思路…...
利用EditPlus进行Json数据格式化
利用EditPlus进行Json数据格式化 git下载地址:https://github.com/michael-deve/CommonData-EditPlusTools.git (安装过editplus的直接将里面的json.js文件复制走就行) 命令:Cscript.exe /nologo “D:\Program Files (x86)\EditPlus 3\json.js” D:\P…...
xss.function靶场(easy)
文章目录 第一关Ma Spaghet!第二关Jefff第三关Ugandan Knuckles第四关Ricardo Milos第五关Ah Thats Hawt第六关Ligma第七关Mafia第八关Ok, Boomer 网址:https://xss.pwnfunction.com/ 第一关Ma Spaghet! 源码 <!-- Challenge --> <h2 id"spaghet&qu…...
【LLM入门】Let‘s reproduce GPT-2 (124M)【完结,重新回顾一下,伟大!】
文章目录 03:43:05 SECTION 4: results in the morning! GPT-2, GPT-3 repro03:56:21 shoutout to llm.c, equivalent but faster code in raw C/CUDA【太牛了ba】03:59:39 summary, phew, build-nanogpt github repo 03:43:05 SECTION 4: results in the morning! GPT-2, GPT-…...
c语言----取反用什么符号
目录 前言 一、逻辑取反 二、按位取反 三、应用场景 前言 在C编程语言中,取反使用符号!表示逻辑取反,而使用~表示按位取反。 其中,逻辑取反!是将表达式的真值(非0值)转换为假(0),…...
【html+css 绚丽Loading】 - 000003 乾坤阴阳轮
前言:哈喽,大家好,今天给大家分享htmlcss 绚丽Loading!并提供具体代码帮助大家深入理解,彻底掌握!创作不易,如果能帮助到大家或者给大家一些灵感和启发,欢迎收藏关注哦 💕…...
vscode里如何用git
打开vs终端执行如下: 1 初始化 Git 仓库(如果尚未初始化) git init 2 添加文件到 Git 仓库 git add . 3 使用 git commit 命令来提交你的更改。确保在提交时加上一个有用的消息。 git commit -m "备注信息" 4 …...
java_网络服务相关_gateway_nacos_feign区别联系
1. spring-cloud-starter-gateway 作用:作为微服务架构的网关,统一入口,处理所有外部请求。 核心能力: 路由转发(基于路径、服务名等)过滤器(鉴权、限流、日志、Header 处理)支持负…...
成都鼎讯硬核科技!雷达目标与干扰模拟器,以卓越性能制胜电磁频谱战
在现代战争中,电磁频谱已成为继陆、海、空、天之后的 “第五维战场”,雷达作为电磁频谱领域的关键装备,其干扰与抗干扰能力的较量,直接影响着战争的胜负走向。由成都鼎讯科技匠心打造的雷达目标与干扰模拟器,凭借数字射…...
(转)什么是DockerCompose?它有什么作用?
一、什么是DockerCompose? DockerCompose可以基于Compose文件帮我们快速的部署分布式应用,而无需手动一个个创建和运行容器。 Compose文件是一个文本文件,通过指令定义集群中的每个容器如何运行。 DockerCompose就是把DockerFile转换成指令去运行。 …...
Xen Server服务器释放磁盘空间
disk.sh #!/bin/bashcd /run/sr-mount/e54f0646-ae11-0457-b64f-eba4673b824c # 全部虚拟机物理磁盘文件存储 a$(ls -l | awk {print $NF} | cut -d. -f1) # 使用中的虚拟机物理磁盘文件 b$(xe vm-disk-list --multiple | grep uuid | awk {print $NF})printf "%s\n"…...
初探Service服务发现机制
1.Service简介 Service是将运行在一组Pod上的应用程序发布为网络服务的抽象方法。 主要功能:服务发现和负载均衡。 Service类型的包括ClusterIP类型、NodePort类型、LoadBalancer类型、ExternalName类型 2.Endpoints简介 Endpoints是一种Kubernetes资源…...
Kafka入门-生产者
生产者 生产者发送流程: 延迟时间为0ms时,也就意味着每当有数据就会直接发送 异步发送API 异步发送和同步发送的不同在于:异步发送不需要等待结果,同步发送必须等待结果才能进行下一步发送。 普通异步发送 首先导入所需的k…...
力扣热题100 k个一组反转链表题解
题目: 代码: func reverseKGroup(head *ListNode, k int) *ListNode {cur : headfor i : 0; i < k; i {if cur nil {return head}cur cur.Next}newHead : reverse(head, cur)head.Next reverseKGroup(cur, k)return newHead }func reverse(start, end *ListNode) *ListN…...
Unity UGUI Button事件流程
场景结构 测试代码 public class TestBtn : MonoBehaviour {void Start(){var btn GetComponent<Button>();btn.onClick.AddListener(OnClick);}private void OnClick(){Debug.Log("666");}}当添加事件时 // 实例化一个ButtonClickedEvent的事件 [Formerl…...
算法打卡第18天
从中序与后序遍历序列构造二叉树 (力扣106题) 给定两个整数数组 inorder 和 postorder ,其中 inorder 是二叉树的中序遍历, postorder 是同一棵树的后序遍历,请你构造并返回这颗 二叉树 。 示例 1: 输入:inorder [9,3,15,20,7…...
