Files
erqiwang_youle/client/js/01_SubGame/codes/config/Layout_Result.js
T
joywayerandClaude Opus 5 92edb6a3f5 二七王:布局求解器补齐显式失败与运行时注入契约,配置补 runtime/targetKind 声明
求解器(ui/LayoutSolver.js):
- 按方向校验 anchor:竖排只收 top/bottom/center、横排只收 left/right/center,
  未知 direction 一并拒绝。框架 AlignmentUtils 的 switch 对写错方向的 anchor 落到
  default(居中),笔误会被静默吞掉——ROOM_CATEGORY_COLUMN 就是这么把前两行摆到画布外的。
- grid 校验合并 ctx 后的 cols/rows 必须是数字:缺 rows 时 capacity=NaN 让超载守卫失效、
  循环一次不跑,静默返回空数组(一个矩形都不产出)。
- line/fan/grid 要求 anchorX/anchorY 必须是数字(框架的 anchorY||0 会把缺失变成 0);
  point 要求 x/y 必须是数字。
- apply() 精灵数与矩形数不等时抛错,不再静默截断:截断会让多余精灵停在上一手牌的旧坐标上。
- 统一运行时注入:ctx 里的 INJECT_KEYS(target/x/y/w/h/anchorX/anchorY/rows/
  itemWidth/itemHeight)覆盖配置同名字段,优先级 ctx > bySeat > base。
- line + items 竖排显式拒绝(只实现了水平)。

配置:
- ROOM_CATEGORY_COLUMN anchor 由 'left' 改为 'top'(竖排语义)。
- ROOM_OPTION_OVERFLOW_GRID 补 rows(runtime)、槽尺寸与 anchor 沿用 ROOM_OPTION_ROW,
  cols 直接引用 ROOM_OPTION_MAX_PER_ROW;ROOM_OPTION_ROW 补上注释里已声明的 itemHeight。
- 所有依赖运行时注入的节点加 runtime 声明,所有 attach 节点加 targetKind
  (sprite / layout / platform),显式区分「忘了写」与「故意延后到运行时」。

守卫(tests/test_constants.js):
- 求解冒烟改为只对 runtime 声明过的键注入假值,没声明却缺字段的照常抛错变红。
- 补矩形数量断言(line/fan/grid 按项数、point/attach 恒 1)——此前只查数组与坐标类型,
  空数组照样通过,「少画了几张牌」对守卫完全不可见。
- attach.target 改为只在 targetKind 指定的那一个命名空间里校验存在。
- 补 runtime 声明自身的合法性检查与布局节点总数(62)钉死。

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-26 22:24:16 +08:00

66 lines
2.4 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
///////////////////////////////////////////////////////////////
////////// EQW_Layout: 结算区配置(清单 §6.9)//////////////////
///////////////////////////////////////////////////////////////
// 【纯数据文件】无函数、无副作用;依赖 LayoutConstants.js 先加载
// (引用其 EQW_Layout.TEXT_STYLE.*,属 EQW_Layout 内部自引用)。
var EQW_Layout = EQW_Layout || {};
EQW_Layout.RESULT_BOTTOM_PANEL = { kind: 'point', x: 430, y: 140, w: 420, h: 148 };
//底牌说明文字:贴面板底部,纯文字,清单未给宽高
EQW_Layout.RESULT_BOTTOM_TEXT = {
kind: 'attach', targetKind: 'layout', target: 'RESULT_BOTTOM_PANEL',
hAlign: 'center', vAlign: 'bottom', offsetY: -14,
runtime: ['w', 'h']
};
//三家分数光晕
EQW_Layout.RESULT_GLOW = {
kind: 'point', w: 225, h: 100,
bySeat: {
LEFT: { x: 175, y: 150 },
RIGHT: { x: 865, y: 150 },
SELF: { x: 490, y: 340 }
}
};
//三家总分大字:贴对应光晕居中。target 直接指向光晕精灵键(固定,非动态)
EQW_Layout.RESULT_SCORE_TEXT = {
kind: 'attach', targetKind: 'sprite', hAlign: 'center', vAlign: 'middle',
textStyle: EQW_Layout.TEXT_STYLE.SCORE_BIG, runtime: ['w', 'h'],
bySeat: {
LEFT: { target: 'RESULT_GLOW_LEFT' },
RIGHT: { target: 'RESULT_GLOW_RIGHT' },
SELF: { target: 'RESULT_GLOW_SELF' }
}
};
//三家『牌局分』:贴对应光晕左下
EQW_Layout.RESULT_JF_TEXT = {
kind: 'attach', targetKind: 'sprite', hAlign: 'left', vAlign: 'bottom', offsetX: -15, offsetY: 24,
runtime: ['w', 'h'],
bySeat: {
LEFT: { target: 'RESULT_GLOW_LEFT' },
RIGHT: { target: 'RESULT_GLOW_RIGHT' },
SELF: { target: 'RESULT_GLOW_SELF' }
}
};
//三家『冲关分』:贴对应光晕右下
EQW_Layout.RESULT_AW_TEXT = {
kind: 'attach', targetKind: 'sprite', hAlign: 'right', vAlign: 'bottom', offsetX: 15, offsetY: 24,
runtime: ['w', 'h'],
bySeat: {
LEFT: { target: 'RESULT_GLOW_LEFT' },
RIGHT: { target: 'RESULT_GLOW_RIGHT' },
SELF: { target: 'RESULT_GLOW_SELF' }
}
};
EQW_Layout.RESULT_BTN_CG = { kind: 'point', x: 535, y: 515, w: 183, h: 63 };
EQW_Layout.RESULT_BTN_NEXT = { kind: 'point', x: 835, y: 518, w: 180, h: 65 };
//冲关遮罩:透明度也是配置项
EQW_Layout.CG_MASK = { kind: 'point', x: 0, y: 0, w: 1280, h: 720, opacity: 0.72 };