news 2026/7/11 22:57:07

HarmonyOS 小游戏《对战五子棋》开发第31篇 - TwoPlayerPage双人对战(三):结果弹窗与游戏结束处理

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
HarmonyOS 小游戏《对战五子棋》开发第31篇 - TwoPlayerPage双人对战(三):结果弹窗与游戏结束处理

游戏结束时的仪式感——结果弹窗的层叠设计

游戏截图:

Stack层叠布局

build(){Stack({alignContent:Alignment.TopStart}){// 第一层:游戏界面Column(){// 导航栏、状态栏、棋盘、按钮...}.width('100%').height('100%').backgroundColor('#F5F0E8')// 第二层:结果弹窗(条件渲染)if(this.showResultDialog){Column(){// 弹窗内容...}.width('70%').padding(32).backgroundColor('#FFFFFF').borderRadius(16)}}.width('100%').height('100%')}

Stack的层叠原理

Stack ├── Column (游戏界面) ← 底层 └── Column (结果弹窗) ← 上层,覆盖游戏界面

Stack中的子组件按声明顺序层叠——后声明的在上层。弹窗声明在后面,所以覆盖游戏界面。

条件渲染

if(this.showResultDialog){Column(){/* 弹窗内容 */}}

showResultDialogtrue时弹窗渲染,为false时不渲染。ArkUI的条件渲染会完全创建/销毁组件。

弹窗触发时机

privateonCellClick(row:number,col:number):void{if(this.result!==GameResult.PLAYING)return;constsuccess=this.engine.placePiece(row,col,this.currentPlayer);if(success){this.refreshBoardData();if(this.result!==GameResult.PLAYING){this.showResultDialog=true;// 游戏结束时显示弹窗}}}

落子后如果result不再是PLAYING(有人获胜或平局),设置showResultDialog = true

弹窗内容设计

Column(){Text(this.result===GameResult.DRAW?'平局!':'游戏结束').fontSize(24).fontWeight(FontWeight.Bold).fontColor('#333333').margin({bottom:8})Text(this.getStatusText()).fontSize(18).fontColor('#E63946').margin({bottom:4})Text(`${this.moveCount}`).fontSize(14).fontColor('#888888').margin({bottom:24})Row({space:16}){Button('返回首页').fontSize(16).fontColor('#555555').backgroundColor('#E8E0D5').borderRadius(24).height(44).onClick(()=>{router.back();})Button('再来一局').fontSize(16).fontColor('#FFFFFF').backgroundColor('#4A90D9').borderRadius(24).height(44).onClick(()=>{this.restart();})}}.width('70%').padding(32).backgroundColor('#FFFFFF').borderRadius(16).justifyContent(FlexAlign.Center).alignItems(HorizontalAlign.Center)

弹窗信息层级

┌─────────────────────────┐ │ │ │ 游戏结束 │ ← 24px Bold 主标题 │ 黑方获胜! │ ← 18px 红色 结果 │ 共 47 手 │ ← 14px 灰色 统计 │ │ │ [返回首页] [再来一局] │ ← 44px 按钮 │ │ └─────────────────────────┘

弹窗按钮逻辑

返回首页

Button('返回首页').onClick(()=>{router.back();})

调用router.back()返回Index首页。当前页面的组件和引擎实例会被销毁。

再来一局

Button('再来一局').onClick(()=>{this.restart();})
privaterestart():void{this.engine.reset();// 重置引擎this.showResultDialog=false;// 关闭弹窗this.refreshBoardData();// 刷新UI}

restart关闭弹窗并重置游戏——弹窗通过showResultDialog = false消失,棋盘清空。

弹窗样式

.width('70%')// 宽度70%,两侧留边.padding(32)// 内边距32.backgroundColor('#FFFFFF')// 白色背景.borderRadius(16)// 圆角.justifyContent(FlexAlign.Center)// 垂直居中.alignItems(HorizontalAlign.Center)// 水平居中

Stack的alignContent

Stack({alignContent:Alignment.TopStart})

Alignment.TopStart让未指定对齐方式的子组件(弹窗)从左上角开始排列。但弹窗设置了justifyContent(Center)alignItems(Center),所以内容在弹窗内部居中。

注意:Stack默认居中对齐子组件。如果想让弹窗覆盖全屏并居中,可以:

Stack({alignContent:Alignment.Center}){Column(){/* 游戏界面 */}if(this.showResultDialog){Column(){/* 弹窗 */}// 自动居中}}

本项目TwoPlayerPage使用TopStart让游戏界面从顶部开始,弹窗通过Stack默认行为居中显示。

对比AIBattlePage的弹窗

AIBattlePage的弹窗更复杂——有半透明遮罩层:

@BuilderresultDialog(){Stack({alignContent:Alignment.Center}){// 半透明遮罩Column().width('100%').height('100%').backgroundColor('#00000066')// 40%透明黑// 弹窗内容Column(){...}}}

TwoPlayerPage没有遮罩层,AIBattlePage有——设计上的差异。

总结

结果弹窗的设计要点:

  1. Stack层叠:弹窗覆盖在游戏界面上方
  2. 条件渲染if (showResultDialog)控制显示
  3. 信息层级:主标题→结果→统计→按钮
  4. 弹窗样式:70%宽度、32内边距、16圆角
  5. 按钮逻辑:返回首页或再来一局

弹窗是游戏结束的"仪式感"——它让用户感受到对局的完整闭环。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/7/11 22:56:23

Pr 剪辑非线性思维实战:3大视觉技巧+2种叙事模板提升混剪质量

Pr剪辑非线性思维实战:3大视觉技巧2种叙事模板提升混剪质量在数字内容爆炸的时代,一段平庸的剪辑作品很难在信息洪流中脱颖而出。许多掌握了Premiere基础操作的创作者,往往陷入"流水账式剪辑"的困境——素材按时间线机械排列&#…

作者头像 李华
网站建设 2026/7/11 22:55:12

AssetStudio深度解析:Unity资源提取原理与实战指南

1. 项目概述:为什么我们需要AssetStudio? 在Unity游戏开发、逆向分析或者资源复用的圈子里,你肯定不止一次遇到过这样的场景:看到一个游戏里酷炫的模型、一段动人的音乐或者一套精美的UI素材,想拿来学习研究&#xff0…

作者头像 李华
网站建设 2026/7/11 22:51:23

LV3296与STM32F745ZG信号捕获与跟踪系统设计

1. 项目概述:LV3296与STM32F745ZG的信号捕获与跟踪系统在嵌入式信号处理领域,如何高效捕获、跟踪和管理动态信号一直是工程师面临的挑战。LV3296作为一款专业级信号处理芯片,与STM32F745ZG高性能MCU的组合,为解决这一问题提供了理…

作者头像 李华
网站建设 2026/7/11 22:50:47

Python游戏开发入门:Pyglet库核心概念与实战指南

1. 项目概述:为什么选择Pyglet作为你的第一个游戏开发库?如果你正在寻找一个能让你快速上手、不绕弯路、并且能真正理解游戏开发底层逻辑的Python库,Pyglet绝对是一个被低估的宝藏。很多新手一提到Python游戏开发,脑子里蹦出来的第…

作者头像 李华
网站建设 2026/7/11 22:50:16

RocketMQ 消费模式实战:从广播模式切换到集群模式的3步迁移方案

RocketMQ消费模式迁移实战:从广播到集群的平滑过渡方案当业务规模从初创阶段快速扩张时,最初设计的广播消费模式往往会遇到性能瓶颈。我曾亲历一个电商系统在促销期间,由于广播模式导致的消息风暴,整个消息集群几乎瘫痪。本文将分…

作者头像 李华