多帧图片精灵一次只显示一帧=只能显示一位数,两位数就得两个精灵, 14 个叫分档位(13 档两位数)每档只配一个精灵时根本渲染不出来。 - SpriteManager.drawImageRegion:把 GameABCUtils.Draw.drawImage 的源矩形 能力暴露到业务层(drawImage 只透传了整图版),校验/日志/返回值风格照现有 drawImage 一致;注明必须在精灵绘制回调中调用。 - gameabc-framework/ui/NumberRenderer.js:游戏中立,bind/setValue/clear/unbind, 绘制回调里按字宽逐位裁源矩形画在同一个精灵上;layout 抽为纯函数可脱离引擎单测; 字符映射不到显式抛错,不静默跳过。 - EQW_Layout.NUM_STYLE:5 套数字的字宽/字高/字间距/对齐/绘制区宽集中配置(零裸值), 资源只存键名(与 CARD_SIZE.res 同一约定)。 - client/tests/test_numberrenderer.js:43 checks(多位/单位/正负号/三种对齐/负字间距/ 空值/自定义 charMap/非法字符与非法样式抛错/5 套真实样式画得下)。 Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
62 lines
4.3 KiB
JavaScript
62 lines
4.3 KiB
JavaScript
///////////////////////////////////////////////////////////////
|
||
////////// EQW_Layout: 布局配置总则(清单 §6)/////////////////
|
||
///////////////////////////////////////////////////////////////
|
||
// 设计基准 1280×720,ScreenFitMode 1,30fps(清单 §0.1)。
|
||
// 【纯数据文件】无函数、无副作用、不引用其他模块——
|
||
// fan 的间距算法、bySeat 合并、attach 换算都在 codes/ui/LayoutSolver.js。
|
||
// 数值为参考图目视实测估值(±5px),设计稿到位后只改本层。
|
||
//
|
||
// 本文件须最先加载(其余 5 个 Layout_*.js 会引用本文件的 CARD_SIZE / TEXT_STYLE,
|
||
// 这是 EQW_Layout 内部的自引用,不是跨模块引用)。
|
||
var EQW_Layout = EQW_Layout || {};
|
||
|
||
//座位键(显示位,非服务端座位号;换算见 core/SeatMap.js)
|
||
EQW_Layout.SEAT = { SELF: 'SELF', LEFT: 'LEFT', RIGHT: 'RIGHT' };
|
||
|
||
//三套牌面尺寸档(清单 §6.4)。改牌面尺寸只动这一处,引用它的区域自动跟随
|
||
EQW_Layout.CARD_SIZE = {
|
||
L: { w: 110, h: 190, res: 'CARD_FACE_L' }, //手牌、底牌、冲关牌
|
||
M: { w: 90, h: 155, res: 'CARD_FACE_M' }, //已出牌区
|
||
S: { w: 50, h: 70, res: 'CARD_FACE_S' } //结算埋牌底牌
|
||
};
|
||
|
||
//文字样式预设(清单 §6.3,逐条对应 §6.5–§6.9b 各表出现的 textStyle{...})
|
||
EQW_Layout.TEXT_STYLE = {
|
||
STATUS_BIG: { fontSize: 46, color: '#FFFFFF', align: 'center' }, //玩家位「60分」「不叫」(§6.6)
|
||
CALL_BIG: { fontSize: 52, color: '#FFD24A', align: 'center' }, //自己叫分大字(§6.8)
|
||
SCORE_BIG: { fontSize: 56, color: '#FFFFFF', align: 'center' }, //结算总分大字(§6.9)
|
||
ASET_COUNT: { fontSize: 20, color: '#FFFFFF', align: 'center' }, //底栏「1/4 局」(§6.5)
|
||
ROOM_OPT: { normal: { fontSize: 18, color: '#DDDDDD' }, //建房选项文字(§6.9b)
|
||
selected: { fontSize: 18, color: '#E8873A' } },
|
||
ROOM_CAT: { fontSize: 18, color: '#7FBFB0', bold: true, align: 'right', maxWidth: 60 },
|
||
ROOM_CARD_COST_NOTE: { fontSize: 16, color: '#999999' } //建房房卡消耗附注(§6.9b)
|
||
};
|
||
|
||
//数字样式预设(清单 §3.6 / §6.8,2026-08-26 新增)——图集叠绘数字用,一个精灵画多位美术字。
|
||
//每套对应一张【等宽连续排列】的数字图:字符横向一行排开,第 idx 格的源矩形 = (idx*charWidth, 0, charWidth, charHeight)。
|
||
//渲染由框架的 NumberRenderer 完成(NumberRenderer.bind(spriteId, style) → setValue);
|
||
//本表是【零裸值红线】的落点:charWidth/charHeight/spacing/align/width 只在此定义,业务代码只引用不内联。
|
||
//
|
||
//字段:res —— 图片资源【键名】(与 CARD_SIZE.res 同一约定:纯数据文件不直接引用 EQW_Images,
|
||
// 调用方用 EQW_Images[style.res] 取真实 ID)
|
||
// charWidth/charHeight —— 图集单字符宽高(= 源矩形尺寸,也是原样绘制的目标尺寸)
|
||
// spacing —— 字间距(可为负=字符重叠)
|
||
// align —— 在绘制区内的水平对齐:'left'|'center'|'right'
|
||
// width —— 绘制区宽度(= 承载精灵的宽度;各 Layout_*.js 的对应节点直接引用本值,保持 SSOT)
|
||
EQW_Layout.NUM_STYLE = {
|
||
//倒计时(§2.4):最多两位(秒)
|
||
COUNTDOWN: { res: 'NUM_COUNTDOWN', charWidth: 44, charHeight: 60, spacing: 0, align: 'center', width: 88 },
|
||
|
||
//结算得分 · 赢(§1.8/§6.9):带符号,最多「符号 + 四位」
|
||
RESULT_WIN: { res: 'NUM_RESULT_WIN', charWidth: 46, charHeight: 62, spacing: 0, align: 'center', width: 230 },
|
||
|
||
//结算得分 · 输(§1.8/§6.9):帧序与赢的一致,只是配色不同
|
||
RESULT_LOSE: { res: 'NUM_RESULT_LOSE', charWidth: 46, charHeight: 62, spacing: 0, align: 'center', width: 230 },
|
||
|
||
//叫分档位分数(§1.3/§6.8):14 档中 13 档是两位数;绘制区宽 = 档位按钮宽 74,居中压在按钮上
|
||
CALL_SCORE: { res: 'NUM_CALL_SCORE', charWidth: 30, charHeight: 40, spacing: 0, align: 'center', width: 74 },
|
||
|
||
//选主面板花色张数(§1.5/§6.8):两副牌单花色最多 26 张,最多两位
|
||
MAIN_SUIT_COUNT: { res: 'NUM_MAIN_SUIT_COUNT', charWidth: 24, charHeight: 32, spacing: 0, align: 'center', width: 48 }
|
||
};
|