Godot游戏练习01-第14节-Theme,字体,游戏UI

今天来学习游戏中的主题(Theme)和字体调整, 并添加一个能显示轮次和倒计时的游戏UI

看看效果

像素字体加上, 瞬间有那感觉了! 有点那么回事了, 哈哈

实现过程

主题和字体设置

字体我是直接在网上找了一个开源字体, 觉得好看就用了: https://github.com/TakWolf/fusion-pixel-font

下载otf格式, 不带woff/woff2后缀的字体, 导入Godot, 关闭抗锯齿(Antialiasing), Hinting, Subpixel Positioning后重新导入, 像素游戏不需要抗锯齿/高清/子像素等设置, 导入zh_hans(简体中文版本)

新建一个Theme资源, 命名为default.tres, 将Default Font设置为导入的字体, 调整字号为20 (自己在预览中觉得合适的大小)

设置默认主题: Project -> Project Settings -> GUI -> Theme -> Custom, 设置为刚刚新建的Theme资源, 并且可以调整默认字体导入选项

这样, 默认字体和主题都设置完毕

轮次数和轮次倒计时显示

新建一个CanvasLayer为根节点的场景, UI节点树如下

gdscript 复制代码
RoundTimerUI (CanvasLayer)
└── MarginContainer
    └── VBoxContainer
        ├── RoundLabel
        └── TimerLabel

调整对齐, Margin等属性, 让UI在靠顶居中的位置显示

RoundTimerUI脚本如下

gdscript 复制代码
extends CanvasLayer

@export var enemy_spawn_component: EnemySpawnComponent

@onready var round_label: Label = %RoundLabel
@onready var timer_label: Label = %TimerLabel

func _ready() -> void:
	enemy_spawn_component.round_changed.connect(_on_round_changed)


func _process(_delta: float) -> void:
	var time_left := enemy_spawn_component.get_round_time_left()
	timer_label.text = str(ceili(time_left))


func _on_round_changed(round_count: int) -> void:
	round_label.text = "Round %s" % round_count

它监听外部EnemySpawnComponent组件的轮次变化事件, 以及实时获取EnemySpawnComponent组件中的当前轮次剩余时间, 转换为整数显示, 更新UI

之后就是数据的通知与同步, 在这个场景中, 数据的同步显得稍微复杂一点, 它涉及到跨组件的Timer处理

主要把握好两个同步时间点:

  • Round变化
  • 新的Peer加入

同步内容: 主要同步Round计数, 以及当前剩余时间, 倒计时让每个Peer自己的Timer执行, 服务器只在关键点同步, 避免不必要的宽带浪费

这里主要看一下EnemySpawnComponent组件中提供的"同步"接口

gdscript 复制代码
func synchronize(peer_id: int = -1) -> void:
	if not is_multiplayer_authority():
		return
	var data = {
		"round_count": round_count,
		"round_timer_time_left": round_timer.time_left,
		"round_timer_running": not round_timer.is_stopped()
	}
	if peer_id < 0:
		_synchronize.rpc(data)
	elif peer_id > 1:
		_synchronize.rpc_id(peer_id, data)


@rpc("authority", "call_remote", "reliable")
func _synchronize(data: Dictionary) -> void:
	round_count = data.round_count
	round_timer.wait_time = data.round_timer_time_left
	if data.round_timer_running:
		round_timer.start()

同步接口synchronize收集服务端信息, 并同步给其他的peer, 所以peer_id中过滤自身id(1)

synchronize在Round发生变化时与所有peer进行RPC同步; 在新peer加入时, 仅与新peer同步(传入peer_id)

对round_count字段添加getter和setter

gdscript 复制代码
var round_count: int = 0:
	get:
		return round_count
	set(value):
		round_count = value
		round_changed.emit(value)

当每个peer上的round_count发生变化时, 都会触发各自的round_changed信号, 同步到UI界面, 保持数据与UI显示一致

相关推荐
星栈独行24 分钟前
Rust + Makepad 应用怎么打包发布:Windows、macOS、Linux 全平台交付
windows·程序人生·macos·ui·rust
喵星人工作室1 小时前
C++火影忍者1.1.8
开发语言·c++·游戏
Mr..Jackey10 小时前
瑞佑 RUI Builder 图形化 UI 设计工具
arm开发·人工智能·单片机·ui·人机交互·ra8889·lcd控制芯片
狼哥168611 小时前
《新闻资讯》二、公共能力层模块实现指南
ui·华为·harmonyos
挂科边缘13 小时前
MonkeyQt组件库,基于 PySide6 搭建的 UI 组件库,68种主题样式
ui·pyside6·monkeyqt
众乐乐_200814 小时前
用claude Fabel5一句话生成的游戏:三国天命(有资源包)
游戏
namexingyun17 小时前
开源前端生态如何成为 AI UI 生成的“燃料“:shadcn/ui、Tailwind CSS、Storybook 技术价值全解剖
java·前端·人工智能·python·ui·开源·ai编程
LT101579744417 小时前
2026年UI自动化测试平台选型指南:全界面自动化覆盖方案
运维·ui·自动化
德迅--文琪18 小时前
守护数字游戏乐园:解析DDoS攻击与德迅云安全游戏盾防护方案
游戏·ddos
Java知识技术分享18 小时前
opencode安装ui-ux-pro-max和frontend-ui-ux技能
人工智能·ui·个人开发·ai编程·ux