refactor(代码术语): 卡① flag→seal 全族换代+game/ 禁用词清扫(迭代 31 卡①)
标识符面:flag_*→seal_ 族(含 Godot 信号 flag_judged→seal_judged 与连接/回调同名、 FACTS 两键 flags_count→seals_count/dug_under_flag→dug_under_seal 全链、 .tres 键名与 schema .gd 同批同步);显式豁免零改动=size_flags_*(Godot 布局属性)+_fatal_flag。 中文面:金币→GP(金币袋→GP 袋)/插旗→封印/雷格→危险格/惩罚格→危险格/旗→封印·封印印记族, game/ 内 *.gd/.tres/.md/.json 四类禁用词与 flag 双双零命中(V1/V4)。 守卫字面量不动(被检查的禁字不是使用):smoke_all V21 零「雷/旗」检查面、 ui_font_asset_test 字形集攻/雷/旗/封 保持原断言逻辑。 代拍板:板面单字槽 glyph「旗」→「封」(禁字纪律+单字位宽,消费面四处同名随动)。 素材换代(2026-10-18 用户裁案甲):assets/art/board/flag_seal.png→seal_mark.png(素材不入 git, 盘上改名+导入重刷),代码两处 res:// 字符串+COL_FLAG/CURSOR_FLAG 常量同步, 闸件四处随批(run_all_gates.sh/render_gate.sh/golden_baseline_refresh.sh/path_check.py)。 anchor.json 键名手改,重锚与改前改后 diff 随本卡收口(同裁案甲)。 基线读数(改前,主区 ed2dfaf6):冒烟 1151 检查 0 失败/单元 34 套全绿/探针 --click 存量红仅 screen_flow_probe(user:// 断点污染在册已知项)。 改后同批读数(本 worktree):冒烟 1151 检查 0 失败/探针 --click 同一存量红、其余全绿。
This commit is contained in:
1 parent
ed2dfaf66f
commit
32fdf957fd
79 files changed
+899
-899
No files matched your search
@@ -21,7 +21,7 @@ static func rest_line(healed: int, hp: int, max_hp: int) -> String:
|
||||
|
||||
# 商店房行(GP+商店房实施批——到达即开店;购买/离开归玩家意图)
|
||||
static func shop_line(gp: int) -> String:
|
||||
return "[color=#%s]商店房:金币 %d——购买即时生效,离开后选下一跳[/color]" % [UiKit.HEX_LOG_GAIN, gp]
|
||||
return "[color=#%s]商店房:GP %d——购买即时生效,离开后选下一跳[/color]" % [UiKit.HEX_LOG_GAIN, gp]
|
||||
|
||||
|
||||
# 选路口行(零自动推进停点——战斗胜利/兑付确认后出现)
|
||||
@@ -111,7 +111,7 @@ static func bonus_card_text(id: String, tier: String, value: int, treasure_line:
|
||||
"armor":
|
||||
return "护甲等级提升%s\n护甲 +%d" % [ts, value]
|
||||
"gp":
|
||||
return "金币袋%s\n金币 +%d" % [ts, value]
|
||||
return "GP 袋%s\nGP +%d" % [ts, value]
|
||||
"heal":
|
||||
return "恢复药剂\n生命 +%d(当即回复)" % value
|
||||
"treasure_item":
|
||||
|
||||
@@ -177,7 +177,7 @@ func on_shop_buy(product_id: String) -> void:
|
||||
# pool 面:买 1 → 核心全重抽——货架整架重投喂(重抽反馈;余额不足核心拒绝零副作用)
|
||||
if not runner.buy_pool_item(product_id):
|
||||
logger.log_ux("ux_reject", {"source": "wallet", "sub_reason": "insufficient_gp"})
|
||||
toast.show_toast("金币不足——买不起这件商品", "warn")
|
||||
toast.show_toast("GP不足——买不起这件商品", "warn")
|
||||
return
|
||||
shop_overlay.open_shelf(runner.shop_shelf(), int(runner.gp))
|
||||
shop_overlay.set_visit_info(int(runner.shop_bp_visit_buys()), float(db.shop_price_a())) # T6 爬价规则行
|
||||
@@ -187,7 +187,7 @@ func on_shop_buy(product_id: String) -> void:
|
||||
if not runner.buy_product(product_id):
|
||||
# 余额不足(按钮禁用为常态防线——兜底拒绝可见,pattern 1)
|
||||
logger.log_ux("ux_reject", {"source": "wallet", "sub_reason": "insufficient_gp"})
|
||||
toast.show_toast("金币不足——买不起这件商品", "warn")
|
||||
toast.show_toast("GP不足——买不起这件商品", "warn")
|
||||
return
|
||||
shop_overlay.refresh_state(runner.shop_products(), int(runner.gp))
|
||||
_refresh_presentations.call()
|
||||
@@ -199,7 +199,7 @@ func on_shop_refresh() -> void:
|
||||
if runner == null or not runner.is_shop_pool():
|
||||
return
|
||||
if not runner.shop_refresh():
|
||||
toast.show_toast("金币不足——刷新失败", "warn")
|
||||
toast.show_toast("GP不足——刷新失败", "warn")
|
||||
return
|
||||
shop_overlay.open_shelf(runner.shop_shelf(), int(runner.gp))
|
||||
shop_overlay.set_visit_info(int(runner.shop_bp_visit_buys()), float(db.shop_price_a())) # T6 爬价规则行
|
||||
|
||||
@@ -189,7 +189,7 @@ func on_refresh() -> void:
|
||||
# 免费位(X/Y)已穷——GP 付费档(先扣钱包后重抽,余额不足拒绝零副作用)
|
||||
var cost: int = adventure.curio_refresh_gp_cost()
|
||||
if runner == null or not runner.spend_gp(cost):
|
||||
toast.show_toast("金币不足——刷新失败", "warn")
|
||||
toast.show_toast("GP不足——刷新失败", "warn")
|
||||
return
|
||||
refreshed = adventure.refresh_curio_paid()
|
||||
_refresh_presentations.call() # 钱包变化上屏(对齐商店购买后刷新面)
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
## VERTICAL SLICE - NOT FOR PRODUCTION
|
||||
## 呈现装配器:核心状态 → 呈现文案的全部翻译集中于此(战斗屏 B/C/D 区文案与投影),静态无状态。
|
||||
## 核心读取只走 settlement.presentation_snapshot() 成文快照面——禁链式穿透 settlement.enemy_system.* / status_effects 一类内部路径。
|
||||
## 旗/拔/移动反馈与 AP/RAP 无推送信号——组合根每次动作/结算返回后必须重查 refresh,漏调即陈旧呈现。
|
||||
## 封印/拔/移动反馈与 AP/RAP 无推送信号——组合根每次动作/结算返回后必须重查 refresh,漏调即陈旧呈现。
|
||||
class_name HudPresenter
|
||||
extends RefCounted
|
||||
|
||||
@@ -166,7 +166,7 @@ static func outcome_text(outcome: Dictionary) -> String:
|
||||
"not_adjacent": "不能执行:目标与小人不相邻",
|
||||
"target_revealed": "不能执行:目标已开",
|
||||
"target_concealed": "不能移动:目标未开",
|
||||
"flag_present": "不能插旗:此格已有旗(旗为一次性承诺——相邻时左键直接挖开)",
|
||||
"seal_present": "不能封印:此格已有封印印记(封印为一次性承诺——相邻时左键直接挖开)",
|
||||
"no_path": "不能移动:已探明区不连通",
|
||||
"out_of_catalog": "无效目标",
|
||||
}
|
||||
|
||||
@@ -696,7 +696,7 @@ func _on_battle_end_continue() -> void:
|
||||
_refresh_presentations()
|
||||
return
|
||||
# 会话收束(迭代 27 T1 物化):旧手工置空清单(runner/settlement/adventure/_adventure_mode +
|
||||
# _reset_run_scope 三项)整节点 queue_free() 消亡——新闲时会话即建,局态旗/账本/模态挂起全复位
|
||||
# _reset_run_scope 三项)整节点 queue_free() 消亡——新闲时会话即建,局态封印/账本/模态挂起全复位
|
||||
_debug.reset()
|
||||
_begin_session(false)
|
||||
debug_overlay.reset_sliders()
|
||||
@@ -964,7 +964,7 @@ func _on_hover_forbidden(_cell: Vector2i) -> void:
|
||||
|
||||
func _on_chord_attempted(_cell: Vector2i) -> void:
|
||||
if not run_scope.hints_shown.has("chord"):
|
||||
_show_hint("本作无双击快开——插旗后轮末自动判定标中;点数字格可移动小人", "chord")
|
||||
_show_hint("本作无双击快开——封印后轮末自动判定标中;点数字格可移动小人", "chord")
|
||||
|
||||
|
||||
func _show_hint(text: String, hint_id: String) -> void:
|
||||
@@ -1199,7 +1199,7 @@ func _on_board_action(cell: Vector2i, kind: String) -> void:
|
||||
run_scope.locked_click = {"cell": cell, "kind": kind}
|
||||
return
|
||||
# 秘宝选中态劫持(迭代 7 T4——两步交互第二步):点格=使用目标拾取,不落挖格;
|
||||
# 只劫持挖掘点击(move/flag 语义不冲突——选中期玩家仍可移动/插旗)
|
||||
# 只劫持挖掘点击(move/seal 语义不冲突——选中期玩家仍可移动/封印)
|
||||
var treasure_sel: int = _treasure_ui.active_selection()
|
||||
if treasure_sel != 0 and kind == "dig":
|
||||
_treasure_ui.attempt_use(treasure_sel, cell)
|
||||
@@ -1242,7 +1242,7 @@ func _on_stop_pressed() -> void:
|
||||
|
||||
|
||||
func _on_refresh_confirmed() -> void:
|
||||
# 弃图刷新(挖掘期 Active 当场换图继续挖——D4;RAP 按门槛扣费 · 旧板旗作废,每轮上限读表)
|
||||
# 弃图刷新(挖掘期 Active 当场换图继续挖——D4;RAP 按门槛扣费 · 旧板封印作废,每轮上限读表)
|
||||
if _input_locked():
|
||||
return
|
||||
var ok: bool = false
|
||||
@@ -1253,7 +1253,7 @@ func _on_refresh_confirmed() -> void:
|
||||
logger.log_action("refresh", Vector2i(-1, -1), ok)
|
||||
if ok:
|
||||
logger.log_ux("ux_refresh_attempt", {"result": "accepted", "round_refresh_index": _refresh_used_snapshot()})
|
||||
board_zone.toast.show_toast("RAP−%d · 旧板旗作废——新图已就位,AP 保留继续挖" % int(db.action_economy.rap_refresh_cost), "gold")
|
||||
board_zone.toast.show_toast("RAP−%d · 旧板封印作废——新图已就位,AP 保留继续挖" % int(db.action_economy.rap_refresh_cost), "gold")
|
||||
else:
|
||||
# 资源面/上限拒绝(EC13 合法拒绝可见;行动经济 无载荷——客户端按上下文推断)
|
||||
var rap: int = int(run_scope.settlement.presentation_snapshot().get("rap", 0)) if run_scope.settlement != null else 0
|
||||
|
||||
@@ -89,11 +89,11 @@ func _consume_row(row: Dictionary) -> void:
|
||||
stage.on_step_row_fx(row)
|
||||
_play_cross_zone_fx(row) # 跨区因果演出(结算演出链批):开格之因 → 站桩之果
|
||||
_play_settlement_mark(row) # 三轮 #3——逐条标出:Buff/Debuff 色环脉冲 → 伤害/治疗数字浮现
|
||||
# 高光演出(战斗结算×3①② 占位):完美排雷横幅 / 标中旗加重弹道
|
||||
# 高光演出(战斗结算×3①② 占位):完美排雷横幅 / 封印命中加重弹道
|
||||
if String(row.get("type", "")) == "highlight" and String(row.get("highlight", "")) != "skill_unlock":
|
||||
board_zone.fx.play_perfect_sweep()
|
||||
elif String(row.get("highlight", "")) == "flag_hit":
|
||||
board_zone.fx.play_flag_hit_projectile(true)
|
||||
elif String(row.get("highlight", "")) == "seal_hit":
|
||||
board_zone.fx.play_seal_hit_projectile(true)
|
||||
# Boss 半血解锁技提示(迭代14④ T4——D8 呈现面:skill_unlock 行弹一次性技能名 toast,
|
||||
# 轻量非演出零动画资产;行文本 =「XX 解锁了 YY」,只报技能名不报数值——规格=敌人系统 意图呈现节)
|
||||
if String(row.get("highlight", "")) == "skill_unlock":
|
||||
|
||||
@@ -200,7 +200,7 @@ static func build_start_overlay(host: Control, db = null) -> Dictionary:
|
||||
# 故永不被隐藏);右下角 16px(拇指区惯例,与旧三屏角标同域);可见性归组合根(_debug_entry
|
||||
# 门控落定后赋值);地图屏底栏 85px 常驻,offset 抬升本函数不处理(组合根 _sync_status_entry)。
|
||||
static func build_debug_badge(host: Control) -> Button:
|
||||
var badge := UiKit.button("调试", 0.0) # 角落小件豁免宽度基准(0=不设 min/flags——同状态角标)
|
||||
var badge := UiKit.button("调试", 0.0) # 角落小件豁免宽度基准(0=不设 min/seals——同状态角标)
|
||||
badge.add_theme_font_size_override("font_size", UiKit.FS_HINT)
|
||||
badge.tooltip_text = "打开调试浮窗(当局数据/种子/数值调整)"
|
||||
badge.grow_horizontal = Control.GROW_DIRECTION_BEGIN # 向左上生长——尺寸变化向屏内
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
## VERTICAL SLICE - NOT FOR PRODUCTION
|
||||
## D 区 AP 条:AP/RAP 点阵读数与停手、图例、弃图刷新入口(弃图刷新为二段确认——RAP 扣费·旧板旗作废显式代价)。
|
||||
## D 区 AP 条:AP/RAP 点阵读数与停手、图例、弃图刷新入口(弃图刷新为二段确认——RAP 扣费·旧板封印作废显式代价)。
|
||||
## RAP 读数贴弃图刷新消费口(RAP 唯一消费口=弃图刷新);无推送信号——组合根每次核心调用返回后经 setter 重查注入。
|
||||
class_name ApBarView
|
||||
extends PanelContainer
|
||||
@@ -77,7 +77,7 @@ func _init() -> void:
|
||||
_confirm_row.add_theme_constant_override("separation", 4)
|
||||
_confirm_row.visible = false
|
||||
row.add_child(_confirm_row)
|
||||
_confirm_lab = UiKit.label("RAP−%d · 旧板旗作废" % refresh_cost,UiKit.FS_HINT, true, COL_INK)
|
||||
_confirm_lab = UiKit.label("RAP−%d · 旧板封印作废" % refresh_cost,UiKit.FS_HINT, true, COL_INK)
|
||||
_confirm_row.add_child(_confirm_lab)
|
||||
var confirm_btn := UiKit.button("确认弃图", 0.0) # HUD 顶条紧凑钮豁免宽度基准
|
||||
confirm_btn.pressed.connect(_disarm_and_fire)
|
||||
@@ -119,7 +119,7 @@ func set_ap(ap: int, ap_max: int) -> void:
|
||||
|
||||
func set_refresh_cost(cost: int) -> void:
|
||||
refresh_cost = cost
|
||||
_confirm_lab.text = "RAP−%d · 旧板旗作废" % cost
|
||||
_confirm_lab.text = "RAP−%d · 旧板封印作废" % cost
|
||||
|
||||
|
||||
func set_refresh_state(remaining: int, ready: bool) -> void:
|
||||
|
||||
@@ -49,9 +49,9 @@ func _init() -> void:
|
||||
_seal.size_flags_vertical = Control.SIZE_SHRINK_CENTER
|
||||
header.add_child(_seal)
|
||||
var seal_img := TextureRect.new()
|
||||
var flag_tex := UiKit.load_tex("res://assets/art/board/flag_seal.png")
|
||||
if flag_tex != null:
|
||||
seal_img.texture = flag_tex
|
||||
var seal_tex := UiKit.load_tex("res://assets/art/board/seal_mark.png")
|
||||
if seal_tex != null:
|
||||
seal_img.texture = seal_tex
|
||||
seal_img.custom_minimum_size = Vector2(32, 32)
|
||||
seal_img.expand_mode = TextureRect.EXPAND_IGNORE_SIZE
|
||||
seal_img.stretch_mode = TextureRect.STRETCH_KEEP_ASPECT_CENTERED
|
||||
@@ -134,7 +134,7 @@ func open_victory(verdict_line: String, continue_label: String, board_rect: Rect
|
||||
_play_victory_dust() # 尘金粒子(P-C5 两套并存——开关=调试浮窗,会话级)
|
||||
else:
|
||||
_play_crest_assemble() # 碎砖拼纹章(§2.4——样张 v2 冻结批 T3 终稿;默认)
|
||||
_play_flag_recall(0) # 胜利不放旗收回
|
||||
_play_seal_recall(0) # 胜利不放封印收回
|
||||
if gp_gain >= 0:
|
||||
_roll_gp(gp_gain, gp_total)
|
||||
|
||||
@@ -150,7 +150,7 @@ func open_defeat(verdict_line: String, continue_label: String, board_rect: Rect2
|
||||
_cele.visible = false
|
||||
_rows_box.visible = false # P-C4 维持 OQ14:失败侧不呈现账行
|
||||
_play_dust_sadle() # 坐砖掸灰(§2.5——终稿)
|
||||
_play_flag_recall(8)
|
||||
_play_seal_recall(8)
|
||||
|
||||
|
||||
func close() -> void:
|
||||
@@ -211,9 +211,9 @@ func _fx_center() -> Vector2:
|
||||
return get_viewport_rect().size * 0.5
|
||||
|
||||
|
||||
# 旗化光点收回(失败——插过的旗逐面化光点收回占位,§2.5)
|
||||
func _play_flag_recall(count: int) -> void:
|
||||
_fx_flag_dots = count
|
||||
# 封印化光点收回(失败——插过的封印逐面化光点收回占位,§2.5)
|
||||
func _play_seal_recall(count: int) -> void:
|
||||
_fx_seal_dots = count
|
||||
for i in count:
|
||||
var dot := ColorRect.new()
|
||||
dot.color = COL_GOLD
|
||||
@@ -235,7 +235,7 @@ func _play_flag_recall(count: int) -> void:
|
||||
var _crest_bricks: Array[ColorRect] = [] # 纹章碎砖驻留面(close 时回收)
|
||||
var _fx_crest_shards := 0
|
||||
var _fx_dust_motes := 0
|
||||
var _fx_flag_dots := 0
|
||||
var _fx_seal_dots := 0
|
||||
|
||||
|
||||
# 碎砖拼纹章(胜利 §2.4——蜡封落定后十枚碎砖自四周向蜡封外环收拢拼成纹章环,驻留至 close)
|
||||
@@ -323,9 +323,9 @@ func _clear_crest_bricks() -> void:
|
||||
_crest_bricks.clear()
|
||||
|
||||
|
||||
# 演出探针出口(fx_probe——胜利纹章/失败掸灰/旗光收回三断言面)
|
||||
# 演出探针出口(fx_probe——胜利纹章/失败掸灰/封印光收回三断言面)
|
||||
func fx_probe() -> Dictionary:
|
||||
return {"crest_shards": _fx_crest_shards, "dust_motes": _fx_dust_motes, "flag_dots": _fx_flag_dots}
|
||||
return {"crest_shards": _fx_crest_shards, "dust_motes": _fx_dust_motes, "seal_dots": _fx_seal_dots}
|
||||
|
||||
|
||||
func _emit_continue_pressed() -> void:
|
||||
|
||||
@@ -153,7 +153,7 @@ func _format_row(row: Dictionary, agg_count := -1) -> String:
|
||||
var suffix := "(%s)" % src if src != "" else ""
|
||||
match String(row.get("type", "")):
|
||||
"effect":
|
||||
# GP 型效果行(GP+商店房实施批 2026-09-21):「金币袋 +3」兑付反馈——value = 本行 ±power,
|
||||
# GP 型效果行(GP+商店房实施批 2026-09-21):「GP 袋 +3」兑付反馈——value = 本行 ±power,
|
||||
# escrow = 战斗内缓冲现值(入钱包在战斗末一次上抛——呈现语义与增益池分账)
|
||||
if String(row.get("effect_id", "")) in ["gp_gain", "gp_loss"]:
|
||||
var gp_col := UiKit.HEX_LOG_GAIN if v > 0 else UiKit.HEX_LOG_LOSS
|
||||
@@ -190,8 +190,8 @@ func _format_row(row: Dictionary, agg_count := -1) -> String:
|
||||
# 未生效类行:⚠ icon + 划线形状冗余(非色相独载)+ 聚合计数
|
||||
var n := (" ×%d" % agg_count) if agg_count > 1 else ""
|
||||
return prefix + "[s][color=#%s]⚠ %s%s[/color][/s]%s" % [UiKit.HEX_LOG_VOIDED, name_, n, suffix]
|
||||
"flag_miss":
|
||||
var body := "✗ %s%s" % [name_, "(本板完美排雷已破——归因此旗)" if hl == "perfect_broken" else ""]
|
||||
"seal_miss":
|
||||
var body := "✗ %s%s" % [name_, "(本板完美排雷已破——归因此封印)" if hl == "perfect_broken" else ""]
|
||||
return prefix + (_gold_frame(body) if hl == "perfect_broken" else "[color=#%s]%s[/color]" % [UiKit.HEX_LOG_ROUND, body])
|
||||
"cast":
|
||||
# 施放行(敌人技能池批——蓄力行 charge 改型):增益技 0 伤害施放,具名技能
|
||||
|
||||
@@ -32,15 +32,15 @@ var proj_band := 0.0: # 地面投影带宽(像素,0 = 不画
|
||||
set(v):
|
||||
proj_band = v
|
||||
queue_redraw()
|
||||
var glyph := "": # 文字位——数字/雷/旗/人/?(现行视觉旗与数字互斥,同位承载)
|
||||
var glyph := "": # 文字位——数字/雷/封印/人/?(现行视觉封印与数字互斥,同位承载)
|
||||
set(v):
|
||||
glyph = v
|
||||
queue_redraw()
|
||||
var glyph_color := UiKit.INK: # 文字色(墨族/雷朱/旗朱/小人蓝)
|
||||
var glyph_color := UiKit.INK: # 文字色(墨族/雷朱/封印朱/小人蓝)
|
||||
set(v):
|
||||
glyph_color = v
|
||||
queue_redraw()
|
||||
var badge_glyph := "": # 奖励徽章文字(右下角金——旗之下、变异纹之上、不进数字区)
|
||||
var badge_glyph := "": # 奖励徽章文字(右下角金——封印之下、变异纹之上、不进数字区)
|
||||
set(v):
|
||||
badge_glyph = v
|
||||
if _glow_layer != null and is_instance_valid(_glow_layer):
|
||||
@@ -54,7 +54,7 @@ var hl_visible := false: # 焦点高亮(悬停态边框覆盖层)
|
||||
set(v):
|
||||
hl_visible = v
|
||||
queue_redraw()
|
||||
var hl_color := UiKit.GOLD: # 高亮色(金目标/旗朱/禁入灰禁红)
|
||||
var hl_color := UiKit.GOLD: # 高亮色(金目标/封印朱/禁入灰禁红)
|
||||
set(v):
|
||||
hl_color = v
|
||||
queue_redraw()
|
||||
@@ -81,10 +81,10 @@ var tex_base: Texture2D = null # ① 砖面底
|
||||
var tex_mutation: Texture2D = null # ② 变异纹带
|
||||
var tex_glyph: Texture2D = null # ③ 数字
|
||||
var tex_badge: Texture2D = null # ③' 徽章
|
||||
var tex_flag: Texture2D = null: # ④ 旗(T17 修复:槽位可运行时换装〔插旗〕——同族 facade/treasure_mark
|
||||
set(v): # 均 setter 触发重绘;旧普通 var 赋值不重绘=旗插上不显示)
|
||||
if tex_flag != v:
|
||||
tex_flag = v
|
||||
var tex_seal: Texture2D = null: # ④ 封印(T17 修复:槽位可运行时换装〔封印〕——同族 facade/treasure_mark
|
||||
set(v): # 均 setter 触发重绘;旧普通 var 赋值不重绘=封印插上不显示)
|
||||
if tex_seal != v:
|
||||
tex_seal = v
|
||||
queue_redraw()
|
||||
var tex_facade: Texture2D = null # ⑥ E 格墙面材质(v3.5——南邻墙顶 center 瓦片同源,BoardView 注入)
|
||||
var facade_strip := false: # E 格开关(BoardView paint 按「已开格且南邻未开墙」写入——瓦片态专用)
|
||||
@@ -95,7 +95,7 @@ var facade_strip := false: # E 格开关(BoardView paint 按「已开
|
||||
# 变异角标(迭代 6 T6——程序化,tex_mutation 纹带槽留给变异纹带六型自产批):
|
||||
# "flat_damage" = 未开格伤害型变异,左下角危险红三角(开格有代价的策略纹理标记)
|
||||
# 叠加层标记(迭代 7 T4——秘宝板级叠加层的格面呈现;派生信息层零回写):
|
||||
# "mine_reveal" = 真视格(危险红内缩框——「这格是雷」的确定决策标记,插旗照常计费);
|
||||
# "mine_reveal" = 真视格(危险红内缩框——「这格是雷」的确定决策标记,封印照常计费);
|
||||
# "reward_preview" 格不复用本字段——预读徽章走 badge_glyph 注入(board_view refresh 注入 REWARD_BADGE 字形)
|
||||
var treasure_mark := "":
|
||||
set(v):
|
||||
@@ -157,7 +157,7 @@ func _draw() -> void:
|
||||
_draw_e_facade()
|
||||
# 瓦片态描边覆盖层(高墙瓦片接线批 2026-09-26):tex_base 在位时 BoardView 传入的 bg_sb
|
||||
# 已降级为「透明底 + 描边」载体——呼吸微光/主角蓝框画在瓦片之上(art-bible §1.2 叠层序
|
||||
# 不变:底 < 纹带 < 数字 < 旗 < 焦点高亮);素材缺位回退走 elif 程序化原样,零观感变化
|
||||
# 不变:底 < 纹带 < 数字 < 封印 < 焦点高亮);素材缺位回退走 elif 程序化原样,零观感变化
|
||||
if bg_sb != null:
|
||||
draw_style_box(bg_sb, rect)
|
||||
|
||||
@@ -233,7 +233,7 @@ func _draw() -> void:
|
||||
if glyph != "":
|
||||
# 数字色牌后备路径(圣经 v3.5 冻结④ 批 B2 2026-09-30:数字亮墨直画已开格底**退役必垫牌**;
|
||||
# 牌=后备件——雷/「?」维持牌载保读性(牌上深墨族 12:1),复杂格底〔物件纹样/装饰变体格〕
|
||||
# 判定随装饰瓦片自产批扩。牌尺寸 0.60/0.62 格边居中 = 样张 v2 冻结值;旗=未开格不垫牌)
|
||||
# 判定随装饰瓦片自产批扩。牌尺寸 0.60/0.62 格边居中 = 样张 v2 冻结值;封印=未开格不垫牌)
|
||||
if plate:
|
||||
var pw := edge * 0.60
|
||||
var ph := edge * 0.62
|
||||
@@ -249,9 +249,9 @@ func _draw() -> void:
|
||||
draw_texture_rect(tex_badge, rect, false)
|
||||
else:
|
||||
_draw_badge(badge_glyph)
|
||||
# ④ 旗(现行视觉旗文字在 ③ 文字位承载——独立槽位留给终稿旗图)
|
||||
if tex_flag != null:
|
||||
draw_texture_rect(tex_flag, rect, false)
|
||||
# ④ 封印(现行视觉封印文字在 ③ 文字位承载——独立槽位留给终稿封印图)
|
||||
if tex_seal != null:
|
||||
draw_texture_rect(tex_seal, rect, false)
|
||||
# ⑤ 路径点迹 + 焦点高亮(悬停态覆盖层,不参与命中)
|
||||
if dot_visible:
|
||||
var ds := 6.0
|
||||
@@ -260,8 +260,8 @@ func _draw() -> void:
|
||||
# 悬停高亮减淡(2026-09-26 用户反馈:金框太明显——绘制时 55% alpha,hl_color 属性与探针断言面不动)
|
||||
draw_rect(Rect2(1, 1, edge - 2.0, edge - 2.0), Color(hl_color, 0.55), false, 2.0) # 2px 内描边(旧 hl Panel 等价)
|
||||
# ⑥ 视野迷雾层(迭代 11 第④批 T2/T3——最顶遮罩,§6.5 落文):
|
||||
# 全黑=不透明纯黑盖全部叠层(含旗印/徽章/高亮——旗印记随格隐没,§6.5 显式推论);
|
||||
# 记忆态=记忆板素色压平(纹理免疫——色牌/旗印/徽章随板隐没)+数字记忆墨重画(数字可读硬指标 ≥4.5:1)
|
||||
# 全黑=不透明纯黑盖全部叠层(含封印印/徽章/高亮——封印印记随格隐没,§6.5 显式推论);
|
||||
# 记忆态=记忆板素色压平(纹理免疫——色牌/封印印/徽章随板隐没)+数字记忆墨重画(数字可读硬指标 ≥4.5:1)
|
||||
if fog_state == 1:
|
||||
draw_rect(Rect2(Vector2.ZERO, Vector2(edge, edge)), Color(0, 0, 0, 1.0), true)
|
||||
elif fog_state == 2:
|
||||
@@ -274,7 +274,7 @@ func _draw() -> void:
|
||||
if glyph != "":
|
||||
_draw_glyph(glyph, UiKit.FOG_MEMORY_INK, maxi(18, int(ceil(edge * 0.5)))) # 字号下限 18(§7.4 冻结公式同源)
|
||||
# ⑦ 中立移除退色层(迭代 13 T8/D6——P2 甲退色降档:暗幕压顶全层覆盖,暗淡记忆态同族呈现语义;
|
||||
# 顶层于迷雾之上——移除格不再参与迷雾语义。本实现移除集=未揭示雷格(无数字无旗印))
|
||||
# 顶层于迷雾之上——移除格不再参与迷雾语义。本实现移除集=未揭示危险格(无数字无封印印))
|
||||
if removed_dim:
|
||||
draw_rect(Rect2(Vector2.ZERO, Vector2(edge, edge)), Color(0.12, 0.10, 0.09, 0.62), true)
|
||||
|
||||
|
||||
@@ -1,12 +1,12 @@
|
||||
## VERTICAL SLICE - NOT FOR PRODUCTION
|
||||
## D 区演出层:清图喷泉/Boss 影子/完美排雷光带/标中旗弹道/挥铲三帧等一次性占位演出。
|
||||
## D 区演出层:清图喷泉/Boss 影子/完美排雷光带/封印命中弹道/挥铲三帧等一次性占位演出。
|
||||
## 组合根按核心信号直调 play_*;素材缺位静默回退(演出层不设断言面)。
|
||||
class_name BoardFxView
|
||||
extends Control
|
||||
|
||||
const COL_GOLD := UiKit.GOLD
|
||||
const COL_BOSS := UiKit.BOSS_PURPLE # 紫赤 #8F2F6A
|
||||
const COL_FLAG := UiKit.SEAL_BLACK # 封印黑(旗化暴击弹道——旗朱→封印紫→封印黑 2026-09-28)
|
||||
const COL_SEAL := UiKit.SEAL_BLACK # 封印黑(封印化暴击弹道——封印朱→封印紫→封印黑 2026-09-28)
|
||||
const CONFETTI_COLS := [UiKit.GOLD, UiKit.GOLD_LIT, UiKit.HERO_BLUE, UiKit.WARM] # 装饰彩带不涉封印语义——原紫位改亮金(紫赤系 Boss 独占不入装饰)
|
||||
|
||||
var _banner: Label
|
||||
@@ -102,11 +102,11 @@ func play_perfect_sweep() -> void:
|
||||
_show_banner("完美排雷 ×2")
|
||||
|
||||
|
||||
# 标中旗:旗化暴击弹道加重占位(自棋盘上缘飞向 B 区敌人卡方向——越界即收)
|
||||
func play_flag_hit_projectile(heavy: bool) -> void:
|
||||
# 封印命中:封印化暴击弹道加重占位(自棋盘上缘飞向 B 区敌人卡方向——越界即收)
|
||||
func play_seal_hit_projectile(heavy: bool) -> void:
|
||||
var shot := ColorRect.new()
|
||||
var w := 8.0 if heavy else 4.0
|
||||
shot.color = COL_FLAG
|
||||
shot.color = COL_SEAL
|
||||
shot.size = Vector2(w, w * 2.2)
|
||||
shot.position = Vector2(size.x * 0.5, size.y * 0.7)
|
||||
shot.mouse_filter = Control.MOUSE_FILTER_IGNORE
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
class_name BoardView
|
||||
extends Control
|
||||
|
||||
signal action_requested(cell: Vector2i, kind: String) # kind ∈ {dig, move, flag_place, flag_pull}
|
||||
signal action_requested(cell: Vector2i, kind: String) # kind ∈ {dig, move, seal_place, seal_pull}
|
||||
signal hover_forbidden(cell: Vector2i) # 非相邻未开格悬停(首遇 toast 归组合根去重)
|
||||
signal chord_attempted(cell: Vector2i) # 双击快开尝试(chord 肌肉记忆提示锚)
|
||||
|
||||
@@ -15,7 +15,7 @@ const COL_BRICK := UiKit.BRICK # 未开——掩尘完整地砖
|
||||
const COL_FLOOR := UiKit.FLOOR # 已开——裸土 #B39A78(碎裂裸露地面)
|
||||
const COL_DIGIT := UiKit.INK # 数字——墨族 #33261B(对格底 ≥4.5:1 硬指标)
|
||||
const COL_HERO := UiKit.HERO_BLUE # 小人边框——小人蓝 #2E6E8E
|
||||
const COL_FLAG := UiKit.SEAL_BLACK # 封印黑 #000000(旗朱→封印紫→封印黑,2026-09-28 用户拍板)
|
||||
const COL_SEAL := UiKit.SEAL_BLACK # 封印黑 #000000(封印朱→封印紫→封印黑,2026-09-28 用户拍板)
|
||||
const COL_GOLD := UiKit.GOLD # 奖励金 #F0A828
|
||||
const COL_CONTACT := UiKit.CONTACT_GLOW # 接触带微光基色(蓝族浅一档·近白蓝——§3.2 v2.8;旧绿相退役 2026-09-26)
|
||||
const COL_HL_TARGET := UiKit.GOLD # 悬停目标格边框(金)
|
||||
@@ -26,7 +26,7 @@ const REWARD_BADGE := { # 已开格格面资源身份 icon
|
||||
}
|
||||
const BADGE_PLACEHOLDER := "?" # 未知图标键占位纹样(HUD框架:禁静默空图标)
|
||||
const CURSOR_DIG := Input.CURSOR_CROSS # 挖——镐形自绘纹理载体
|
||||
const CURSOR_FLAG := Input.CURSOR_POINTING_HAND # 旗——旗形自绘纹理载体
|
||||
const CURSOR_SEAL := Input.CURSOR_POINTING_HAND # 封印——封印形自绘纹理载体
|
||||
const CURSOR_MOVE_SEM := Input.CURSOR_ARROW # 移动——箭头(命名避开 Control.CURSOR_MOVE 原生成员遮蔽)
|
||||
const CHORD_WINDOW_MS := 350
|
||||
const SEP := 2 # 格间距(旧 GridContainer v/h_separation 同值——格尺寸公式与命中换算共用)
|
||||
@@ -66,7 +66,7 @@ const HERO_SHADOW_PX := Vector2(32, 12) # 脚下椭圆影屏幕尺寸(Godot
|
||||
# dungeon 套(禁同板混渲染);dungeon 套亦缺位 → 程序化平色回退(fresh checkout 冒烟不炸)。
|
||||
const TILE_WALL_NAMES := ["wall_center", "wall_center_crack", "wall_center_speckle", "wall_n", "wall_s", "wall_w", "wall_nw", "wall_sw", "wall_hrun", "wall_vrun", "wall_end_n", "wall_end_s", "wall_end_w", "wall_lone", "wall_in_nw", "wall_in_sw"]
|
||||
const TILE_WALL_FMT := "res://assets/art/board/terrain_%s_%s.png" # %s=件名 %s=board_type
|
||||
const TILE_FLAG_SEAL := "res://assets/art/board/flag_seal.png" # 封印旗纹理(迭代 9 卡⑬——独立可选件)
|
||||
const TILE_SEAL_MARK := "res://assets/art/board/seal_mark.png" # 封印印记纹理(迭代 9 卡⑬——独立可选件)
|
||||
const TILE_FLOOR_FMT := "res://assets/art/board/terrain_floor_%s_%d.png" # %s=board_type 1..%d 变体
|
||||
const TILE_FLOOR_VARIANTS := 5 # 地面瓦片变体数(词表 §一 floor_1..5)
|
||||
|
||||
@@ -112,7 +112,7 @@ var _hero_dig_tw: Tween
|
||||
var _tiles := {} # 词表键 → Texture2D(镜像件已预翻转;装载见 _load_board_tiles)
|
||||
var _floor_tiles: Array[Texture2D] = [] # 地面瓦片五变体(下标 0..4 = floor_1..5)
|
||||
var _tiles_ok := false # false = 素材缺位/未装载——bg_sb 程序化平色原路径
|
||||
var _flag_tex: Texture2D = null # 封印旗纹理(缺盘=null=字形「旗」回退——独立可选件不连瓦片整批)
|
||||
var _seal_tex: Texture2D = null # 封印印记纹理(缺盘=null=字形「封印」回退——独立可选件不连瓦片整批)
|
||||
var _tiles_board_type := "dungeon" # 当前装载瓦片套的 board_type(rebuild 按板切换——T6 换色批)
|
||||
var _digit_dark_ink := true # 数字墨族按板自适应(true=深墨三档)。缺盘平色回退态 #B39A78 裸土
|
||||
# 为中明度底——深墨族 CR 4.96 达标、亮墨族仅 2.2,故缺盘默认深墨;瓦片装载后按实测分位数覆写
|
||||
@@ -452,7 +452,7 @@ func _hero_frame_flash() -> void:
|
||||
|
||||
|
||||
# 受理移动指令回执(组合根 settle 受理后、refresh 前调用)——原地移动经此触发帧闪;
|
||||
# 目标异格时本旗标被 diff 位移路径自然吞掉(置位即清)
|
||||
# 目标异格时本封印标被 diff 位移路径自然吞掉(置位即清)
|
||||
func notify_hero_move() -> void:
|
||||
_hero_bump_pending = true
|
||||
|
||||
@@ -579,10 +579,10 @@ func _on_cell_input(c: Vector2i, ev: InputEvent) -> void:
|
||||
action_requested.emit(c, "dig")
|
||||
_detect_chord(c)
|
||||
elif ev.button_index == MOUSE_BUTTON_RIGHT:
|
||||
if not _minesweeper.has_flag(c):
|
||||
action_requested.emit(c, "flag_place")
|
||||
# 旗 = 一次性承诺(插旗不可逆批 2026-09-19):拔旗退役——旗格右键零动作;
|
||||
# 左键相邻旗格直接挖(四情况②④兑付改判,规则引擎放行)。
|
||||
if not _minesweeper.has_seal(c):
|
||||
action_requested.emit(c, "seal_place")
|
||||
# 封印 = 一次性承诺(封印不可逆批 2026-09-19):撤封印退役——封印格右键零动作;
|
||||
# 左键相邻封印格直接挖(四情况②④兑付改判,规则引擎放行)。
|
||||
|
||||
|
||||
# chord 肌肉记忆首遇锚:同格双左击快开尝试(350ms 窗)——每 run 一次提示由组合根去重
|
||||
@@ -620,7 +620,7 @@ func _apply_hover_visuals(c: Vector2i) -> void:
|
||||
_clear_hover_visuals(c)
|
||||
var u: Node2D = _cells[c]
|
||||
var revealed: bool = _minesweeper.is_revealed(c)
|
||||
var flag: bool = _minesweeper.has_flag(c)
|
||||
var seal: bool = _minesweeper.has_seal(c)
|
||||
var adjacent: bool = _diggable.has(c)
|
||||
if revealed:
|
||||
u.hl_visible = true
|
||||
@@ -629,11 +629,11 @@ func _apply_hover_visuals(c: Vector2i) -> void:
|
||||
_show_path_preview(c)
|
||||
elif adjacent:
|
||||
u.hl_visible = true
|
||||
u.hl_color = COL_HL_TARGET # 挖掘目标格边框(相邻旗格同此——左键直接挖,插旗不可逆批)
|
||||
u.hl_color = COL_HL_TARGET # 挖掘目标格边框(相邻封印格同此——左键直接挖,封印不可逆批)
|
||||
_set_cursor_shape(c, CURSOR_DIG)
|
||||
elif flag:
|
||||
elif seal:
|
||||
u.hl_visible = true
|
||||
u.hl_color = COL_FLAG # 已承诺封印标记(封印黑;无交互可供——拔旗已退役)
|
||||
u.hl_color = COL_SEAL # 已承诺封印标记(封印黑;无交互可供——撤封印已退役)
|
||||
_set_cursor_shape(c, Input.CURSOR_FORBIDDEN)
|
||||
else:
|
||||
u.hl_visible = true
|
||||
@@ -668,7 +668,7 @@ func _hide_path_preview() -> void:
|
||||
_cells[c].dot_visible = false
|
||||
|
||||
|
||||
# ---- 奖励徽章(已开格身份 icon——旗之下、纹带之上、不进数字区) ----
|
||||
# ---- 奖励徽章(已开格身份 icon——封印之下、纹带之上、不进数字区) ----
|
||||
|
||||
func _update_badge(c: Vector2i) -> String:
|
||||
if _minesweeper == null or not _minesweeper.is_revealed(c) or not _identity_cb.is_valid():
|
||||
@@ -717,19 +717,19 @@ func _paint_cell(c: Vector2i, hero: Vector2i) -> void:
|
||||
if u == null:
|
||||
return
|
||||
var revealed: bool = _minesweeper.is_revealed(c)
|
||||
var flag: bool = _minesweeper.has_flag(c)
|
||||
var seal: bool = _minesweeper.has_seal(c)
|
||||
var removed: bool = _minesweeper.is_removed(c) # 迭代 13 T8/D6——中立移除格(P2 甲退色降档)
|
||||
var is_hero: bool = c == hero
|
||||
var glyph := ""
|
||||
var bg: Color
|
||||
var digit_col := COL_DIGIT
|
||||
# 旗槽统一维护(T17 修复):旗格=封印旗纹理;其余格清 null(插旗格挖开后残留在 tex_flag
|
||||
# 会让 _draw 无条件把旗印画在已开格上——tex_flag 绘制无 revealed 条件)。缺盘走字形回退。
|
||||
u.tex_flag = _flag_tex if (flag and not revealed and _flag_tex != null) else null
|
||||
# 封印槽统一维护(T17 修复):封印格=封印印记纹理;其余格清 null(封印格挖开后残留在 tex_seal
|
||||
# 会让 _draw 无条件把封印印画在已开格上——tex_seal 绘制无 revealed 条件)。缺盘走字形回退。
|
||||
u.tex_seal = _seal_tex if (seal and not revealed and _seal_tex != null) else null
|
||||
if removed:
|
||||
revealed = false # 移除格固定未开呈现基座(退色暗幕层承载;雷格本无数字——P1 甲周边数字冻结)
|
||||
flag = false
|
||||
u.tex_flag = null
|
||||
revealed = false # 移除格固定未开呈现基座(退色暗幕层承载;危险格本无数字——P1 甲周边数字冻结)
|
||||
seal = false
|
||||
u.tex_seal = null
|
||||
if revealed:
|
||||
var rec: Dictionary[Variant, Variant] = _minesweeper.reveal_record(c) # E2 收口:已开记录经查询面
|
||||
if rec.get("kind", "") == "mine":
|
||||
@@ -746,11 +746,11 @@ func _paint_cell(c: Vector2i, hero: Vector2i) -> void:
|
||||
glyph = str(d)
|
||||
digit_col = _digit_ink(d) # 数字墨三档色温(样张 v2 冻结批 T4——§4.1)
|
||||
else:
|
||||
if flag:
|
||||
if seal:
|
||||
bg = COL_BRICK
|
||||
if _flag_tex == null:
|
||||
glyph = "旗"
|
||||
digit_col = COL_FLAG
|
||||
if _seal_tex == null:
|
||||
glyph = "封"
|
||||
digit_col = COL_SEAL
|
||||
else:
|
||||
bg = COL_BRICK
|
||||
# 瓦片模式(高墙接线批 2026-09-26):tex_base = 查表瓦片(未开=墙瓦片/已开=地面瓦片),
|
||||
@@ -782,7 +782,7 @@ func _paint_cell(c: Vector2i, hero: Vector2i) -> void:
|
||||
u.glyph_color = digit_col
|
||||
# 色牌后备(v3.5 批 B2——数字直画退牌;雷/「?」维持牌载保读性)+ 2026-10-01 v3.4:双峰纹理板
|
||||
#(_digit_plate——underdark 系亮白筋+近黑斑并存的直画不可救纹理)数字落牌,牌上深墨 12:1
|
||||
var plate_digit := _digit_plate and glyph != "" and glyph != "雷" and glyph != "?" and glyph != "旗" and glyph != "人"
|
||||
var plate_digit := _digit_plate and glyph != "" and glyph != "雷" and glyph != "?" and glyph != "封" and glyph != "人"
|
||||
if plate_digit:
|
||||
digit_col = COL_DIGIT # 牌上深墨族(素牌 12:1——双峰纹理免疫)
|
||||
u.glyph_color = digit_col
|
||||
@@ -792,8 +792,8 @@ func _paint_cell(c: Vector2i, hero: Vector2i) -> void:
|
||||
u.proj_band = 0.0
|
||||
u.tex_facade = null
|
||||
u.facade_strip = false
|
||||
# 旗槽不在此重置(2026-10-02 修复批——T13 批的 paint 尾部 `u.tex_flag = null` 与 L683 的条件
|
||||
# 赋值构成双写踩踏:执行序 683→此处把旗纹理恒清 null=素材在位时插旗不可见;L683 的 else 分支
|
||||
# 封印槽不在此重置(2026-10-02 修复批——T13 批的 paint 尾部 `u.tex_seal = null` 与 L683 的条件
|
||||
# 赋值构成双写踩踏:执行序 683→此处把封印纹理恒清 null=素材在位时封印不可见;L683 的 else 分支
|
||||
# 已是全路径清残留,尾部重置系冗余且有害,删除)
|
||||
var south_n: Vector2i = c + Vector2i(0, 1)
|
||||
var north_n: Vector2i = c + Vector2i(0, -1)
|
||||
@@ -979,8 +979,8 @@ func _load_board_tiles(board_type: String = "dungeon") -> void:
|
||||
_floor_tiles = floors
|
||||
_tiles_board_type = board_type
|
||||
_tiles_ok = true
|
||||
# 封印旗纹理(迭代 9 卡⑬——独立可选件:缺盘=字形回退,不触发瓦片整批回落语义)
|
||||
_flag_tex = UiKit.load_tex(TILE_FLAG_SEAL)
|
||||
# 封印印记纹理(迭代 9 卡⑬——独立可选件:缺盘=字形回退,不触发瓦片整批回落语义)
|
||||
_seal_tex = UiKit.load_tex(TILE_SEAL_MARK)
|
||||
|
||||
|
||||
# 整批回落(T6 换色批):请求套缺位 → 回落 dungeon 套(禁同板混渲染);dungeon 本身缺位 =
|
||||
@@ -1164,7 +1164,7 @@ func _floor_tile_for(c: Vector2i) -> Texture2D:
|
||||
return _floor_tiles[posmod(_cell_hash(c), _floor_tiles.size())]
|
||||
|
||||
|
||||
# ---- 自绘光标纹理(镐/旗——引擎内置光标无此语义;程序化占位,headless 跳过) ----
|
||||
# ---- 自绘光标纹理(镐/封印——引擎内置光标无此语义;程序化占位,headless 跳过) ----
|
||||
|
||||
func _apply_custom_cursors() -> void:
|
||||
if DisplayServer.get_name() == "headless":
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
## VERTICAL SLICE - NOT FOR PRODUCTION
|
||||
## CellTypeGlowLayer——未开格类型微光的独占承载件(挂在 CellUnit 之下、1:1 贴格、不入遮挡栈)。
|
||||
## 为什么单独一件而不画进 CellUnit._draw():
|
||||
## ① 父件 _draw() 命令序列由瓦片/数字/旗/焦点高亮多方共用,插进该序列会随叠层口径错位;
|
||||
## ① 父件 _draw() 命令序列由瓦片/数字/封印/焦点高亮多方共用,插进该序列会随叠层口径错位;
|
||||
## ② 独立子件只在「有组」的格上建(作用集 ≤8),静止态零逐帧成本,且不占父件重绘预算;
|
||||
## ③ 材质归子件独占 ⇒ 不抢世界根去饱和材质挂点(结算相位本层隐藏,无叠加冲突)。
|
||||
## 路线:Q1 丙案主路径 = 每格 canvas_item shader 距离场柔光,兜底 = 程序化渐变底图;
|
||||
@@ -30,7 +30,7 @@ func setup(edge: float, group: int) -> void:
|
||||
queue_redraw()
|
||||
|
||||
|
||||
# 预读徽章位豁免(既有元素——微光不染色其上;叠层序 §1.2:徽章在数字之后、旗之前)
|
||||
# 预读徽章位豁免(既有元素——微光不染色其上;叠层序 §1.2:徽章在数字之后、封印之前)
|
||||
func set_badge_mask(enabled: bool) -> void:
|
||||
if _mat == null:
|
||||
return
|
||||
|
||||
@@ -119,9 +119,9 @@ func set_refresh_display(free_left: int, gp_cost: int, can_afford: bool) -> void
|
||||
_refresh_gp_cost = maxi(0, int(gp_cost))
|
||||
_refresh_btn.visible = _refresh_allowance > 0 or _refresh_gp_cost > 0
|
||||
_refresh_badge.text = str(_refresh_allowance)
|
||||
_refresh_l.text = "免费 · 不消耗 AP" if _refresh_allowance > 0 else ("刷新 %d 金币" % _refresh_gp_cost if _refresh_gp_cost > 0 else "")
|
||||
_refresh_l.text = "免费 · 不消耗 AP" if _refresh_allowance > 0 else ("刷新 %d GP" % _refresh_gp_cost if _refresh_gp_cost > 0 else "")
|
||||
_refresh_l.visible = _refresh_l.text != ""
|
||||
_refresh_btn.tooltip_text = "刷新候选——换一批战利品\n免费 %d 次(刷新件 X 优先 + 冒险池 Y)\nGP 刷新 %d 金币\n池源=共享池,与商店货架同源" % [_refresh_allowance, _refresh_gp_cost]
|
||||
_refresh_btn.tooltip_text = "刷新候选——换一批战利品\n免费 %d 次(刷新件 X 优先 + 冒险池 Y)\nGP 刷新 %d GP\n池源=共享池,与商店货架同源" % [_refresh_allowance, _refresh_gp_cost]
|
||||
_refresh_btn.disabled = _refresh_allowance <= 0 and not can_afford
|
||||
|
||||
|
||||
|
||||
@@ -6,12 +6,12 @@ extends Control
|
||||
signal closed
|
||||
|
||||
const ENTRIES := [
|
||||
["#C9AF83", "完整覆尘地砖", "未开格——左键挖开(1AP,须相邻)· 右键插旗(1AP)"],
|
||||
["#C9AF83", "完整覆尘地砖", "未开格——左键挖开(1AP,须相邻)· 右键封印(1AP)"],
|
||||
["#B39A78", "碎裂裸土", "已开 0 格——可通行,左键移动(免费)"],
|
||||
["#000000", "旗", "封印印记(呈现名·不能拔)——轮末自动判定标中;插错可左键直接挖开(安全格零奖励、雷格吃挖雷惩罚)"],
|
||||
["#000000", "封印", "封印印记(呈现名·不能拔)——轮末自动判定标中;插错可左键直接挖开(安全格零奖励、危险格吃挖雷惩罚)"],
|
||||
["#2e86de", "小人", "探险者——8 向相邻未开格常驻微光 = 可挖域"],
|
||||
["#F0A828", "金徽章", "已开格奖励身份 icon(旗之下、数值之上,不进数字区)"],
|
||||
["#F0A828", "九徽章解码", "攻=攻击 · 守=护甲 · 爆=爆裂 · 医=回复 · 弱=削弱 · 穿=穿刺 · 魔=魔法 · 行=行动点 · 金=金币(打磨包 2026-09-29 入列)"],
|
||||
["#F0A828", "金徽章", "已开格奖励身份 icon(封印之下、数值之上,不进数字区)"],
|
||||
["#F0A828", "九徽章解码", "攻=攻击 · 守=护甲 · 爆=爆裂 · 医=回复 · 弱=削弱 · 穿=穿刺 · 魔=魔法 · 行=行动点 · 金=GP(打磨包 2026-09-29 入列)"],
|
||||
["#33261B", "状态槽空态", "无状态效果时槽位隐藏,数据框上移补位——非异常"],
|
||||
]
|
||||
|
||||
@@ -52,7 +52,7 @@ func _init(rap_cost: int = -1) -> void:
|
||||
rap_chip.custom_minimum_size = Vector2(18, 18)
|
||||
rap_chip.color = UiKit.GOLD # 同 #F0A828——金徽章同源单点(T4 裸色收口)
|
||||
rap_row.add_child(rap_chip)
|
||||
var rap_lab := UiKit.label("RAP 储备行动点 —— 停手时剩余 AP 转存;弃图刷新消耗 RAP−%d(旧板旗作废,AP 保留继续挖)" % _rap_cost,UiKit.FS_HINT, false, UiKit.INK_LABEL)
|
||||
var rap_lab := UiKit.label("RAP 储备行动点 —— 停手时剩余 AP 转存;弃图刷新消耗 RAP−%d(旧板封印作废,AP 保留继续挖)" % _rap_cost,UiKit.FS_HINT, false, UiKit.INK_LABEL)
|
||||
rap_lab.autowrap_mode = TextServer.AUTOWRAP_WORD_SMART
|
||||
rap_lab.custom_minimum_size = Vector2(440, 0)
|
||||
rap_row.add_child(rap_lab)
|
||||
|
||||
@@ -12,7 +12,7 @@ const COL_ROOM_CURRENT := UiKit.GOLD # 当前——奖励金
|
||||
const COL_ROOM_FUTURE := UiKit.DARK_UPCOMING # 未达——暗
|
||||
const COL_PASSAGE := UiKit.STONE # 通道——石灰
|
||||
const COL_PASSAGE_LIT := UiKit.CANDLE # 候选通道/候选描边——烛光黄(M5:金色定岗只留当前位,G4;旧 GOLD_LIT 退役出本屏)
|
||||
const COL_BOSS_BORDER := UiKit.BOSS_PURPLE # Boss 边框——紫赤(色相独占本色;旗朱退役 2026-09-26)
|
||||
const COL_BOSS_BORDER := UiKit.BOSS_PURPLE # Boss 边框——紫赤(色相独占本色;封印朱退役 2026-09-26)
|
||||
const COL_ABANDON := UiKit.RED_MINE # 破坏性动作红(危险红族)
|
||||
const NODE_LABELS := {"battle": "战", "reward": "赏", "rest": "疗", "boss": "王", "shop": "商"} # 商 = GP+商店房实施批 2026-09-21(贴图缺位字形回退用——贴图在位=字形退役惯例)
|
||||
const NODE_TYPE_NAMES := {"battle": "战斗", "reward": "奖励", "rest": "休息", "boss": "Boss", "shop": "商店"} # M5 节点下方类型字(demo ④——三通道可读性;当前位显示「当前位置」)
|
||||
@@ -74,7 +74,7 @@ func _init() -> void:
|
||||
box.add_theme_constant_override("separation", 10)
|
||||
center.add_child(box)
|
||||
# 顶栏语境(spec Layout:左关卡名 / 右 GP 常驻徽章——直角细线数据框;
|
||||
# T5 判官 checkpoint 对齐 demo ④:关卡名入框板(裸文本退役)+GP 徽章=烛光胶囊(同商店金币框)+
|
||||
# T5 判官 checkpoint 对齐 demo ④:关卡名入框板(裸文本退役)+GP 徽章=烛光胶囊(同商店GP框)+
|
||||
# 左右两极排布(原居中悬置))
|
||||
var top := HBoxContainer.new()
|
||||
top.add_theme_constant_override("separation", 12)
|
||||
|
||||
@@ -48,7 +48,7 @@ func _init() -> void:
|
||||
gp_chip.add_theme_stylebox_override("panel",
|
||||
UiKit.panel_flat(UiKit.CANDLE, UiKit.CAMP_HEADER_BAND,UiKit.RADIUS_OBJECT, 1, Vector4(12, 4, 12, 4)))
|
||||
top.add_child(gp_chip)
|
||||
_gp_label = UiKit.label("金币 0",UiKit.FS_BODY, true, UiKit.INK_ON_GOLD)
|
||||
_gp_label = UiKit.label("GP 0",UiKit.FS_BODY, true, UiKit.INK_ON_GOLD)
|
||||
gp_chip.add_child(_gp_label)
|
||||
var box: VBoxContainer = page.box
|
||||
_visit_label = UiKit.label("",UiKit.FS_BODY, false, UiKit.WARM_SOFT)
|
||||
@@ -98,7 +98,7 @@ func open_shop(products: Array, gp: int) -> void:
|
||||
|
||||
# 状态重刷(购买/钱包变化后调用——就地改文案与按钮禁用态,零重建)
|
||||
func refresh_state(products: Array, gp: int) -> void:
|
||||
_gp_label.text = "金币 %d" % gp
|
||||
_gp_label.text = "GP %d" % gp
|
||||
var by_id := {}
|
||||
for p in products:
|
||||
by_id[String(p.product_id)] = p
|
||||
@@ -106,7 +106,7 @@ func refresh_state(products: Array, gp: int) -> void:
|
||||
var p: Dictionary[Variant, Variant] = by_id.get(String(card.product_id), {})
|
||||
if p.is_empty():
|
||||
continue
|
||||
card.price.text = "现价 %d 金币" % int(p.price)
|
||||
card.price.text = "现价 %d GP" % int(p.price)
|
||||
card.bought.text = "已购 %d 档" % int(p.purchased)
|
||||
card.btn.disabled = gp < int(p.price) # 余额不足禁用置灰
|
||||
|
||||
@@ -171,7 +171,7 @@ func open_shelf(cards: Array, gp: int) -> void:
|
||||
|
||||
# 货架余额重刷(就地改禁用态——买后重建路径经 open_shelf 覆盖,本口供 wallet 变化联动)
|
||||
func refresh_shelf_state(gp: int) -> void:
|
||||
_gp_label.text = "金币 %d" % gp
|
||||
_gp_label.text = "GP %d" % gp
|
||||
for card in _shelf_rows:
|
||||
card.btn.disabled = gp < int(card.price)
|
||||
card.card.modulate = Color(1, 1, 1, 1) if gp >= int(card.price) else Color(1, 1, 1, 0.55)
|
||||
@@ -188,7 +188,7 @@ func set_refresh_display(free_left: int, gp_cost: int, can_afford: bool) -> void
|
||||
for lab in _refresh_btn.get_children():
|
||||
if lab is Label:
|
||||
(lab as Label).text = str(free_left)
|
||||
_refresh_btn.tooltip_text = "刷新货架——换一批商品\n免费 %d 次(天赋增益位,基础 0)\nGP 刷新 %d 金币(provisional)\n池源=共享池,与奖励三选一同源" % [free_left, gp_cost]
|
||||
_refresh_btn.tooltip_text = "刷新货架——换一批商品\n免费 %d 次(天赋增益位,基础 0)\nGP 刷新 %d GP(provisional)\n池源=共享池,与奖励三选一同源" % [free_left, gp_cost]
|
||||
_refresh_btn.disabled = not can_afford and free_left <= 0
|
||||
|
||||
|
||||
|
||||
@@ -161,7 +161,7 @@ func set_pending(ptype: String, pid: String) -> void:
|
||||
queue_redraw()
|
||||
return
|
||||
var glyph := "⚔" # 攻击系(damage)
|
||||
var col: Color = UiKit.RED_MINE # 攻击预告红(危险红族——旗朱退役 2026-09-26,预告语义归封印色独占〔现行封印黑〕)
|
||||
var col: Color = UiKit.RED_MINE # 攻击预告红(危险红族——封印朱退役 2026-09-26,预告语义归封印色独占〔现行封印黑〕)
|
||||
if ptype == "buff":
|
||||
glyph = "✦" # 增益系
|
||||
col = UiKit.HERO_BLUE_DEEP # 深档墨(N1-4——浅垫牌上 ≥4.5:1;原 HERO_BLUE 亮档对垫牌 2.5:1)
|
||||
|
||||
@@ -39,7 +39,7 @@ const EFFECT_SEMANTIC := {
|
||||
"empower": "敌方输出 ×2(enemy_output 池加算——蓄力技施放;持续 1 个有效结算)",
|
||||
"fortify": "敌方防御 −50(enemy_defense 池——硬化技施放,主角攻击 ×0.5;持续 1 个有效结算)",
|
||||
}
|
||||
const SOURCE_NAMES := {"safe_cell": "安全格", "flag_hit": "标中旗", "mine_hit": "踩雷", "clear_reward": "清图奖励"}
|
||||
const SOURCE_NAMES := {"safe_cell": "安全格", "seal_hit": "封印命中", "mine_hit": "踩雷", "clear_reward": "清图奖励"}
|
||||
# 未知图标键的占位(HUD框架:占位也要可见,禁静默空图标——debug 断言先行,release 回退槽内 ? 文本)
|
||||
const ICON_PLACEHOLDER := "?"
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@ extends Control
|
||||
const LIFE_SEC := 2.5
|
||||
const MAX_SLOTS := 3
|
||||
const COL_INFO := UiKit.INK
|
||||
const COL_WARN := UiKit.RED_MINE # 危险红族——拒绝/作废(旗朱退役 2026-09-26)
|
||||
const COL_WARN := UiKit.RED_MINE # 危险红族——拒绝/作废(封印朱退役 2026-09-26)
|
||||
const COL_GOLD := UiKit.GOLD_DEEP # 奖励金族——提示/达成(深金档)
|
||||
|
||||
var _slot_box: VBoxContainer
|
||||
|
||||
@@ -30,11 +30,11 @@ const GOLD_LIT := Color8(230, 190, 90) # 亮金(候选高亮)
|
||||
const GOLD_DIM := Color8(140, 116, 60) # 暗金(已过节点)
|
||||
const GOLD_DONE := Color8(104, 86, 44) # 已过节点暗金·关卡画面呈现态(关卡画面样张 v1 冻结新值 #68562C——旧 GOLD_DIM #8C743C 对双色墨均 <4.5:1 对比硬指标逼守;GOLD_DIM 他用不动)
|
||||
|
||||
const SEAL_BLACK := Color8(0, 0, 0) # 封印黑 #000000——封印(插旗)宣告色(2026-09-28
|
||||
# 用户拍板旗朱→封印紫→封印黑:紫色与微光蓝族色相冲突,黑色无色相天然避开禁入带
|
||||
# 妨害紫 281° 各留 12-14° 间距;候选值样张批冻结;旗朱 #C63D22 退役)
|
||||
const SEAL_BLACK := Color8(0, 0, 0) # 封印黑 #000000——封印(封印)宣告色(2026-09-28
|
||||
# 用户拍板封印朱→封印紫→封印黑:紫色与微光蓝族色相冲突,黑色无色相天然避开禁入带
|
||||
# 妨害紫 281° 各留 12-14° 间距;候选值样张批冻结;封印朱 #C63D22 退役)
|
||||
const RED_DEEP := Color8(150, 60, 48) # 深朱(敌卡框/敌像)
|
||||
const RED_MINE := Color8(150, 44, 36) # 引爆雷字朱(已开雷格"雷"字)
|
||||
const RED_MINE := Color8(150, 44, 36) # 引爆雷字朱(已开危险格"雷"字)
|
||||
const RED_FORBID := Color8(120, 60, 50) # 禁止框朱
|
||||
const RED_ALERT := Color8(200, 60, 48) # 报错朱
|
||||
|
||||
@@ -275,7 +275,7 @@ const TEX_ICON_SHOVEL := "res://assets/art/ui/icon_shovel.png" #
|
||||
const TEX_ICON_MEDKIT := "res://assets/art/ui/icon_medkit.png" # 图标·医疗包
|
||||
const TEX_ICON_POUCH := "res://assets/art/ui/icon_pouch.png" # 图标·弹药袋/行动点
|
||||
const TEX_ICON_BLAST := "res://assets/art/ui/icon_blast.png" # 图标·工兵爆破(秘宝)
|
||||
const TEX_ICON_COINBAG := "res://assets/art/ui/icon_coinbag.png" # 图标·金币袋
|
||||
const TEX_ICON_COINBAG := "res://assets/art/ui/icon_coinbag.png" # 图标·GP 袋
|
||||
const TEX_ICON_KEYSHARD := "res://assets/art/ui/icon_keyshard.png" # 图标·钥石残片
|
||||
const TEX_ICON_REFRESH := "res://assets/art/ui/icon_refresh.png" # 图标·刷新(货架/候选)
|
||||
|
||||
|
||||
Reference in new issue
Block a user