Files
gplan-2/game/presentation/views/settings_overlay.gd
T

135 lines
5.4 KiB
GDScript

# VERTICAL SLICE - NOT FOR PRODUCTION
# Date: 2026-09-29(迭代 8 卡④ 最小设置面)
# 设置覆盖层(纯视图边界规范 1.3 同款):音量滑杆/全屏/减动效三件+返回(退出游戏已提级开始菜单)。
# 生效与持久化全经 SettingsStore 单点(实时应用+即改即存);本类零核心触碰。
# 减动效转正承载(测试调整板旧开关退役——设置面唯一入口,卡④ AC③)。
# 探针接缝:retarget(store) = 隔离存档换注口(同 camp 换注先例);控件引用公有只读供断言。
class_name SettingsOverlay
extends Control
signal closed
var _store
var _volume: HSlider
var _volume_val: Label
var _fs_btn: Button # M4 换 SwitchToggle 拨杆(仍 Button 子类——探针接缝保持)
var _motion_btn: Button # M4 同上
var _fs_st: Label # M4 状态字随行(开/关)
var _motion_st: Label # M4 状态字(完整/快速)
func _init(store) -> void:
_store = store
_build()
_sync()
visible = false
# 探针隔离换注(冒烟/探针禁碰真实 user://settings.cfg——换注后按新 store 重挂控件态)
func retarget(store) -> void:
_store = store
_sync()
func _build() -> void:
# M4(UI 落码批):石板面板化(demo ③)+行牌化(标签+拨杆+状态字+后果说明行);
# 设置项零增减(P-C6:只有主音量——demo 音效音量行系原型发明已撤);
# 减动效与结算演出动画=同一设置(语义命名批合并),一行承载
var shell: Dictionary = UiKit.modal_shell(self, UiKit.BG_BRIGHT, Vector2(560, 0), 8, true,
UiKit.panel_skinned(Vector4(20, 16, 20, 16)))
var box: VBoxContainer = shell.box
var title := UiKit.label("设置", 24, true, UiKit.INK_TITLE)
title.horizontal_alignment = HORIZONTAL_ALIGNMENT_CENTER
box.add_child(title)
var hint := UiKit.label("系统级设置——独立存储不随存档(一安装一份,删游戏才消失)", 13, false, Color8(110, 69, 52))
hint.horizontal_alignment = HORIZONTAL_ALIGNMENT_CENTER
box.add_child(hint)
box.add_child(HSeparator.new())
# 音量(master bus 实时生效——入口归设置、生效口径归 音频.md)
var vol_row := HBoxContainer.new()
vol_row.add_theme_constant_override("separation", 14)
box.add_child(vol_row)
vol_row.add_child(UiKit.label("主音量", 15, false, UiKit.INK_LABEL))
_volume = UiKit.styled_slider(100.0, 0.0, 100.0)
_volume.step = 1
_volume.value_changed.connect(_on_volume_changed)
vol_row.add_child(_volume)
_volume_val = UiKit.label("100%", 15, true, UiKit.INK_TITLE)
_volume_val.custom_minimum_size = Vector2(60, 0)
vol_row.add_child(_volume_val)
# 全屏(拨杆形——M10 SwitchToggle;状态字随行)
var fs_row := HBoxContainer.new()
fs_row.add_theme_constant_override("separation", 14)
box.add_child(fs_row)
fs_row.add_child(UiKit.label("全屏", 15, false, UiKit.INK_LABEL))
_fs_btn = UiKit.switch_toggle(false)
_fs_btn.toggled.connect(_on_fullscreen_toggled)
fs_row.add_child(_fs_btn)
_fs_st = UiKit.label("关", 14, true, UiKit.INK_LABEL)
fs_row.add_child(_fs_st)
# 结算演出动画(=减动效实称——语义命名批 T17;拨杆 on=完整,off=快速时长减半)
var motion_row := HBoxContainer.new()
motion_row.add_theme_constant_override("separation", 14)
box.add_child(motion_row)
motion_row.add_child(UiKit.label("结算演出动画", 15, false, UiKit.INK_LABEL))
_motion_btn = UiKit.switch_toggle(true)
_motion_btn.toggled.connect(_on_motion_toggled)
motion_row.add_child(_motion_btn)
_motion_st = UiKit.label("完整", 14, true, UiKit.INK_LABEL)
motion_row.add_child(_motion_st)
var why := UiKit.label("快速 = 时长减半(运动敏感 / 演示用)", 12, false, Color8(110, 69, 52))
why.position.y = 0
box.add_child(why)
box.add_child(HSeparator.new())
# 退出游戏已提级开始菜单(D1——设置面不再承载,用户裁决「退出只在一级菜单出现」)
var close_row := HBoxContainer.new()
close_row.alignment = BoxContainer.ALIGNMENT_CENTER
box.add_child(close_row)
var close_btn := UiKit.button("返回")
close_btn.pressed.connect(_emit_closed)
close_row.add_child(close_btn)
func _sync() -> void:
_volume.set_value_no_signal(roundf(_store.volume_linear * 100.0))
_volume_val.text = "%d%%" % roundi(_store.volume_linear * 100.0)
_fs_btn.set_pressed_no_signal(_store.fullscreen)
_fs_st.text = "开" if _store.fullscreen else "关"
_motion_btn.set_pressed_no_signal(not _store.reduced_motion) # 拨杆 on=完整
_sync_motion_text()
# T17 修复:文案随状态即时刷新(旧 bug=切换后文案恒「开」,玩家无法得知当前态)+语义命名
# (「减动效」玩家读不懂——实称「结算演出动画」速度档)+操作提示内联(所见即所得)。
func _sync_motion_text() -> void:
_motion_st.text = "快速" if _store.reduced_motion else "完整"
func _on_volume_changed(v: float) -> void:
_store.volume_linear = v / 100.0
_store.apply()
_store.save_settings()
_volume_val.text = "%d%%" % int(v)
func _on_fullscreen_toggled(on: bool) -> void:
_store.fullscreen = on
_store.apply()
_store.save_settings()
func _on_motion_toggled(on: bool) -> void:
_store.reduced_motion = not on # M4 拨杆语义翻转:on=完整(off=快速)
_store.apply()
_store.save_settings()
_sync_motion_text() # T17 修复:切换即时刷新文案(旧版漏刷新=状态文字恒「开」)
func _emit_closed() -> void:
closed.emit()