From 729c74932f63b1416f1a62032346582eb804fd9b Mon Sep 17 00:00:00 2001 From: Joywayer Date: Fri, 31 Jul 2026 11:53:16 +0800 Subject: [PATCH] =?UTF-8?q?refactor(attr):=20cpu=5Flimit=20=E5=AE=88?= =?UTF-8?q?=E5=8D=AB=E7=A7=BB=E8=87=B3=E6=8D=A2=E6=9D=96=E5=A4=84=EF=BC=9B?= =?UTF-8?q?cast=5Fdelay=5Fmod=20=E6=94=B9=E5=9C=A8=E5=BC=80=E7=81=AB?= =?UTF-8?q?=E6=97=B6=E7=94=9F=E6=95=88?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 守卫从 execute_compiled 搬到 equip_wand:诊断应放在能导致故障的状态转换处, 而非 2 次/秒的使用点——施法端刷屏会埋掉根因,换杖处每局只跑几次且拿得到杖名。 maxi(..., 1) 保留:错误已在换杖处大声报出,退化不再静默,而去掉它会让法术硬瘫。 订正原注释的事实错误:它声称兜住「attributes.json 缺失」与「attr_id 打错」, 但这两种 player_stats.gd:173/191 早已各自报错,守卫零覆盖。真正无人管的是 「新调用点忘了注入」(正是 combat_test 修前的样子)与「cores.json 某杖配成 0」。 cast_delay_mod 由 equip_wand 快照改为开火时相乘:_cast_timer 语义两种写法一致 (总是从上次写入值倒数),代价仅每次施法一次浮点乘法,但「下一个周期」由下次 换杖变为下次施法——玩家买急速道具期待的是后者。随之删去解释延迟生效的注释。 另在 _rebuild_wand 注入处记下 remove-before-add 为何 load-bearing:漏了会让 cpu_limit 随 install_spell 累积,而 hard: 50 会把它封成一个看起来合理的数字。 Co-Authored-By: Claude Opus 5 --- scripts/domain/combat/combat_manager.gd | 2 ++ scripts/domain/player_manager.gd | 12 ++++++++---- scripts/domain/spell_system/spell_evaluator.gd | 8 ++------ 3 files changed, 12 insertions(+), 10 deletions(-) diff --git a/scripts/domain/combat/combat_manager.gd b/scripts/domain/combat/combat_manager.gd index b1e101d..3a442d7 100644 --- a/scripts/domain/combat/combat_manager.gd +++ b/scripts/domain/combat/combat_manager.gd @@ -270,6 +270,8 @@ func _rebuild_wand() -> void: leech += float(n.meta.get("mana_leech", 0.0)) PlayerStats.mana_leech = leech # 法杖运算力以加成来源接入(非调用点相加),使 hard 上限作用于生效总值 + # remove 必须在 add 之前:本函数每次 install_spell 都会跑,漏了 remove 会让 cpu_limit + # 5→10→15 地累积,而 hard: 50 会把它封成一个看起来合理的数字,不是显眼的异常值 PlayerStats.remove_modifiers_from("core") PlayerStats.add_modifier("cpu_limit", "flat", float(_equipped_core.cpu_limit) if _equipped_core else 0.0, "core") diff --git a/scripts/domain/player_manager.gd b/scripts/domain/player_manager.gd index bc60d5c..1fefc11 100644 --- a/scripts/domain/player_manager.gd +++ b/scripts/domain/player_manager.gd @@ -14,8 +14,7 @@ var _player_node: Node2D = null var _equipped_core: CoreDefinition = null var _equipped_compiled: CompiledDeck = null var _cast_timer: float = 0.0 -var _cast_interval: float = 0.5 # equip_wand 时快照 core.cast_interval × cast_delay_mod; - # 中途改 cast_delay_mod 要到下次 equip_wand(每波开战 _transition_to_battle)才生效 +var _cast_interval: float = 0.5 # 法杖基准间隔(core.cast_interval);实际间隔在开火时 × cast_delay_mod var _is_moving: bool = false var _stationary_time: float = 0.0 @@ -79,19 +78,24 @@ func _handle_auto_cast(delta: float) -> void: return _cast_timer -= delta if _cast_timer <= 0.0: - _cast_timer = _cast_interval + _cast_timer = _cast_interval * PlayerStats.cast_delay_mod SpellEvaluator.execute_compiled(_equipped_compiled, 0, _position) func equip_wand(core: CoreDefinition, compiled: CompiledDeck) -> void: _equipped_core = core _equipped_compiled = compiled - _cast_interval = (core.cast_interval if core else 0.5) * PlayerStats.cast_delay_mod + _cast_interval = core.cast_interval if core else 0.5 _cast_timer = 0.0 if core: PlayerStats.set_mana_pool(core.base_mana_max, core.base_mana_regen) else: PlayerStats.set_mana_pool(100.0, 5.0) PlayerStats.mana_heat = 0.0 + # 0 守卫:cpu_limit=0 → MAX_OPS 退化,法术近乎全静默。放在换杖处而非施法处——施法端 2 次/秒 + # 会刷屏埋掉根因,且此处拿得到杖名。兜的是「新调用点忘了注入」与「cores.json 某杖配成 0」, + # 二者上游无任何报错(缺 attributes.json / attr_id 打错已分别由 player_stats.gd:173/191 报出) + if PlayerStats.cpu_limit <= 0: + push_error("PlayerManager: 装备「%s」后 cpu_limit=0,法术执行预算将退化为 40 步;检查该杖 cores.json 的 cpu_limit 与 source=\"core\" 加成注入" % (core.display_name if core else "—")) func get_position() -> Vector2: return _position diff --git a/scripts/domain/spell_system/spell_evaluator.gd b/scripts/domain/spell_system/spell_evaluator.gd index 2552112..cc72738 100644 --- a/scripts/domain/spell_system/spell_evaluator.gd +++ b/scripts/domain/spell_system/spell_evaluator.gd @@ -329,12 +329,8 @@ func execute_compiled(compiled: CompiledDeck, caster_id: int, spawn_pos: Vector2 var heat_mult: float = 1.0 + PlayerStats.mana_heat var deck: SpellDeck = compiled.make_runtime_deck() var ops_count: int = 0 - # 生效 cpu_limit 已含法杖份额(combat_manager 以 source="core" 的加成接入) - # 0 守卫:cpu_limit=0 意味着所有法术执行零步、全局静默失效。此处是该故障唯一可观测处, - # 能同时兜住上游两种失败(attributes.json 缺失 → 裸字段停在 0;add_modifier 的 attr_id 打错 → - # "core" 份额没注入),而根因处的报错够不到这两种。 - if PlayerStats.cpu_limit <= 0: - push_error("SpellEvaluator: PlayerStats.cpu_limit=%d,法术将无法执行;检查 attributes.json 与 _rebuild_wand 的 core 加成注入" % PlayerStats.cpu_limit) + # 生效 cpu_limit 已含法杖份额(combat_manager._rebuild_wand 以 source="core" 的加成接入) + # 下限 1:注入缺失时不把游戏打成砖(0 会让 while 一步都不走);该异常由 equip_wand 处报出 var max_ops: int = MAX_OPS_PER_CPU * maxi(PlayerStats.cpu_limit, 1) var actions_remaining: int = 1 # 初始为 1,由 multicast_count 加成 while deck.has_next() and ops_count < max_ops: