HarmonyOS7 多媒体能力怎么放进一个页面:MediaPanelSwitcher 组合式案例解析
文章目录前言这个案例适合学什么完整代码先看页面骨架一个状态切三块内容切换头部为什么用 ForEachWeb 面板讲的是“控制感”Canvas 面板讲的是“自定义表达”Image 面板讲的是“资源展示效率”这三个组件到底怎么选真实业务里怎么改造成可用页面这类组合页容易踩的坑写在最后前言单独学Web、Canvas、Image都不难真正到了业务里麻烦的是它们往往不会单独出现。一个内容页可能上半部分是图片画廊中间是一块自绘数据区底部还嵌着网页内容。这个时候问题就不再是“某个组件怎么用”而是“多个能力怎么在一个页面里组织得清楚”。这一页案例很适合讲这个问题。它不是某个单组件教程而是一个典型的组合式页面骨架用一个切换面板把三类媒体能力收在同一个交互入口里。这个案例适合学什么它最有价值的地方不是具体内容有多复杂而是把三个能力放在了同一个页面语境里Web适合展示外部内容和页面控制Canvas适合自绘可视化和动态图形Image适合展示视觉资源和图库内容你看完这页至少能建立一个判断框架同一个需求里不同媒体能力应该怎么分工。完整代码import{DEMO_BG_COLOR,DEMO_CARD_COLOR,DEMO_THEME_COLOR,DEMO_SUBTEXT_COLOR}from./typesEntryComponentstruct MediaPanelSwitcher{StateisShow:booleantrueStateactivePanel:number0privatesettings:RenderingContextSettingsnewRenderingContextSettings(true)privatecontext:CanvasRenderingContext2DnewCanvasRenderingContext2D(this.settings)build(){Column(){if(this.isShow){Scroll(){Column({space:16}){Text(Web Canvas Image 综合).fontSize(16).fontColor(DEMO_THEME_COLOR).fontWeight(FontWeight.Bold)Column(){Row({space:0}){ForEach([Web 组件,Canvas 绘图,Image 图片],(label:string,idx:number){Text(label).fontSize(13).fontColor(idxthis.activePanel?#FFFFFF:#666666).padding({left:16,right:16,top:8,bottom:8}).backgroundColor(idxthis.activePanel?DEMO_THEME_COLOR:#E8E8E8).borderRadius(6).margin({right:8}).onClick((){this.activePanelidx})})}.width(100%)}.backgroundColor(DEMO_CARD_COLOR).padding(12).borderRadius(12)if(this.activePanel0){Column(){Column(){Text(Web View 占位).fontSize(14).fontColor(#FFFFFF)}.width(100%).height(180).backgroundColor(#333333).borderRadius(10).justifyContent(FlexAlign.Center)Row({space:6}){ForEach([后退,前进,刷新,首页],(label:string){Text(label).fontSize(11).fontColor(DEMO_THEME_COLOR).backgroundColor(#E8F4FD).borderRadius(4).padding({left:8,right:8,top:4,bottom:4})})}.width(100%).justifyContent(FlexAlign.SpaceEvenly).margin({top:8})}.backgroundColor(DEMO_CARD_COLOR).padding(12).borderRadius(12)}elseif(this.activePanel1){Column(){Column(){Canvas(this.context).onReady((){this.context.fillStyle#4D96FFthis.context.fillRect(10,10,360,50)this.context.fillStyle#6BCB77this.context.fillRect(10,70,360,50)this.context.fillStyle#FFA500this.context.fillRect(10,130,360,50)}).width(100%).height(180).backgroundColor(#FAFAFA).borderRadius(8)}}.backgroundColor(DEMO_CARD_COLOR).padding(12).borderRadius(12)}else{Column(){Row({space:6}){Column(){Text(1).fontSize(14).fontColor(#FFF)}.layoutWeight(1).height(120).backgroundColor(#4D96FF).borderRadius(8).justifyContent(FlexAlign.Center)Column(){Text(2).fontSize(14).fontColor(#FFF)}.layoutWeight(1).height(120).backgroundColor(#FFA500).borderRadius(8).justifyContent(FlexAlign.Center)Column(){Text(3).fontSize(14).fontColor(#FFF)}.layoutWeight(1).height(120).backgroundColor(#6BCB77).borderRadius(8).justifyContent(FlexAlign.Center)}.width(100%)}.backgroundColor(DEMO_CARD_COLOR).padding(12).borderRadius(12)}Column({space:6}){Text(三大组件功能对比).fontSize(14).fontColor(DEMO_THEME_COLOR).fontWeight(FontWeight.Bold)Text(Web: 加载网页 / JS交互 / 前进后退 / Cookie).fontSize(12).fontColor(#333333)Text(Canvas: 绘制图形 / 渐变 / 动画 / 图表).fontSize(12).fontColor(#333333)Text(Image: 显示图片 / 裁剪 / 滤镜 / 填充).fontSize(12).fontColor(#333333)Text(共同场景: 混合布局 / 数据可视化 / 富媒体).fontSize(11).fontColor(DEMO_SUBTEXT_COLOR).margin({top:2})}.width(100%).backgroundColor(#E8F4FD).padding(14).borderRadius(12)}.width(100%)}}Text(MediaPanelSwitcher - Web、Canvas、Image 整合页).fontSize(12).fontColor(DEMO_SUBTEXT_COLOR).margin({top:12})}.width(100%).height(100%).backgroundColor(DEMO_BG_COLOR).padding(16)}}先看页面骨架一个状态切三块内容这个页面最核心的状态其实只有一个StateactivePanel:number0它决定当前显示哪块媒体面板。这个思路非常适合做轻量切换页因为你不用真的跳路由也不用在页面间来回进出所有能力都被折叠在一个统一容器里。切换头部为什么用ForEach顶部按钮区用了这一段ForEach([Web 组件,Canvas 绘图,Image 图片],(label:string,idx:number){Text(label).fontColor(idxthis.activePanel?#FFFFFF:#666666).backgroundColor(idxthis.activePanel?DEMO_THEME_COLOR:#E8E8E8).onClick((){this.activePanelidx})})这段代码的价值不只是少写几个按钮而是把“选项配置”和“当前态样式”绑在了一起。这样后面如果你要扩成 4 个、5 个面板也不需要重构页面结构。说白了这是一种很典型的低成本选项卡写法。Web面板讲的是“控制感”案例里的Web区没有放真实网页而是用了一个占位块加控制按钮ForEach([后退,前进,刷新,首页],(label:string){Text(label)})这其实是在强调Web组件和其他媒体组件最大的不同点之一它除了展示内容还天然带导航和页面控制属性。所以如果你要做帮助中心、嵌入活动页、混合式内容详情Web更适合承载“可浏览、可跳转、可回退”的内容区域。Canvas面板讲的是“自定义表达”中间面板用了三块矩形做占位绘制Canvas(this.context).onReady((){this.context.fillRect(10,10,360,50)this.context.fillRect(10,70,360,50)this.context.fillRect(10,130,360,50)})这一块虽然简单但意思很明确Canvas的优势在于你不受预设组件限制可以自己画图形、图表、动画甚至小游戏元素。所以它最适合承载的是“系统没有现成组件但你又想完全自己控制”的可视区。Image面板讲的是“资源展示效率”第三块内容用三个等宽色块模拟图片卡片Row({space:6}){Column(){Text(1)}.layoutWeight(1)Column(){Text(2)}.layoutWeight(1)Column(){Text(3)}.layoutWeight(1)}这里的重点是layoutWeight(1)。它让三张图天然等比分布很适合做图库、对比展示、商品缩略图和相册入口。相比Canvas和WebImage更偏内容呈现本身而不是行为容器或自绘能力。这三个组件到底怎么选案例最后那块功能对比区方向是对的。你可以把它进一步归纳成一个更实用的判断法。需要嵌网页、承载 H5 内容、做混合页优先Web需要完全自定义图形表现优先Canvas需要稳定展示视觉资源优先Image很多页面不是三选一而是三者组合。关键不是“哪个更强”而是谁负责什么。真实业务里怎么改造成可用页面这个骨架稍微改一下就能变成一个富媒体演示中心。比如第一块接真实WebController做帮助文档浏览页第二块换成设备状态图、订单图表或进度面板第三块接真实图片资源做轮播入口或图库预览一旦内容真实起来这个页面就会从演示页变成一个多能力切换工作台。这类组合页容易踩的坑第一个坑是把所有能力都堆在同一屏里不做切换和分层最后页面极其乱。第二个坑是只关注组件能不能放进去不考虑每类内容的交互节奏。Web、Canvas、Image的操作方式其实完全不同。第三个坑是三块内容高度和样式完全脱节导致页面像三个临时拼接的模块。写在最后这个案例最值得学的不是某个组件 API而是“组合能力”的思维。单个组件学会了只是起点真正能落到业务里的是你怎么让它们在同一个页面里各司其职。把这层理解建立起来后面你看富媒体页面就不会只盯着某一个组件了。

相关新闻