koishi-plugin-vsinger-gacha 1.5.0 → 1.5.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/handbook.js +5 -2
- package/lib/render/kit.js +29 -11
- package/package.json +1 -1
package/lib/handbook.js
CHANGED
|
@@ -207,7 +207,10 @@ async function render({ game, store, uid, displayName, outDir, tagsDir, thumbsDi
|
|
|
207
207
|
for (let pi = 0; pi < parts.length; pi++) {
|
|
208
208
|
const part = parts[pi];
|
|
209
209
|
const W = PAD * 2 + part.length * COLW + (part.length - 1) * GAP * 2;
|
|
210
|
-
|
|
210
|
+
// 头部高度随图标自适应(避免标题压到第一个系列条)
|
|
211
|
+
const _R = Math.max(26, Math.min(72, Math.round(W * 0.017)));
|
|
212
|
+
const HEADY = Math.max(HEAD, 34 + _R * 2 + 40);
|
|
213
|
+
const H = HEADY + Math.max(...part.map((c) => c.reduce((a, b) => a + b.h, 0))) + 70;
|
|
211
214
|
const canvas = Canvas.createCanvas(W, H);
|
|
212
215
|
const g = canvas.getContext('2d');
|
|
213
216
|
|
|
@@ -235,7 +238,7 @@ async function render({ game, store, uid, displayName, outDir, tagsDir, thumbsDi
|
|
|
235
238
|
for (let ci = 0; ci < part.length; ci++) {
|
|
236
239
|
const grp = part[ci];
|
|
237
240
|
const x0 = PAD + ci * (COLW + GAP * 2);
|
|
238
|
-
let y =
|
|
241
|
+
let y = HEADY;
|
|
239
242
|
let prevAct = null;
|
|
240
243
|
for (const blk of grp) {
|
|
241
244
|
if (blk.act !== prevAct) {
|
package/lib/render/kit.js
CHANGED
|
@@ -75,8 +75,8 @@ function header(g, o) {
|
|
|
75
75
|
const y = o.y;
|
|
76
76
|
const W = o.W;
|
|
77
77
|
|
|
78
|
-
//
|
|
79
|
-
const R = 24;
|
|
78
|
+
// 圆形图标:圆保持适中,音符用矢量画满圆内(避免字体 ♪ 上标很小)
|
|
79
|
+
const R = Math.max(24, Math.min(40, Math.round(W * 0.011)));
|
|
80
80
|
const cx = x + R;
|
|
81
81
|
const cy = y + R;
|
|
82
82
|
g.save();
|
|
@@ -84,23 +84,41 @@ function header(g, o) {
|
|
|
84
84
|
g.arc(cx, cy, R, 0, Math.PI * 2);
|
|
85
85
|
g.fillStyle = COLOR.accent;
|
|
86
86
|
g.fill();
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
g.
|
|
87
|
+
|
|
88
|
+
// 音符:椭圆头 + 竖杆 + 旗
|
|
89
|
+
const k = R * 0.52; // 音符整体缩放
|
|
90
|
+
const hx = cx - k * 0.34; // 符头中心
|
|
91
|
+
const hy = cy + k * 0.52;
|
|
92
|
+
g.fillStyle = '#ffffff';
|
|
93
|
+
g.beginPath();
|
|
94
|
+
g.ellipse(hx, hy, k * 0.42, k * 0.32, -0.35, 0, Math.PI * 2);
|
|
95
|
+
g.fill();
|
|
96
|
+
|
|
97
|
+
// 竖杆
|
|
98
|
+
const sx = hx + k * 0.36;
|
|
99
|
+
g.fillRect(sx - k * 0.07, cy - k * 0.62, k * 0.14, hy - (cy - k * 0.62));
|
|
100
|
+
|
|
101
|
+
// 旗
|
|
102
|
+
g.beginPath();
|
|
103
|
+
g.moveTo(sx, cy - k * 0.62);
|
|
104
|
+
g.quadraticCurveTo(sx + k * 0.62, cy - k * 0.48, sx + k * 0.46, cy - k * 0.10);
|
|
105
|
+
g.quadraticCurveTo(sx + k * 0.52, cy - k * 0.40, sx, cy - k * 0.34);
|
|
106
|
+
g.closePath();
|
|
107
|
+
g.fill();
|
|
93
108
|
g.restore();
|
|
94
109
|
|
|
95
110
|
g.textBaseline = 'top';
|
|
96
111
|
g.fillStyle = COLOR.text;
|
|
97
112
|
g.font = `bold ${FONT_SIZE.h1}px ${FONT}`;
|
|
98
|
-
|
|
113
|
+
const titleSize = Math.max(FONT_SIZE.h1, Math.round(R * 1.0));
|
|
114
|
+
g.font = `bold ${titleSize}px ${FONT}`;
|
|
115
|
+
g.fillText(fit(g, o.title, `bold ${titleSize}px ${FONT}`, W - 300), x + R * 2 + 18, y + Math.max(0, R - 24));
|
|
99
116
|
|
|
100
117
|
if (o.subtitle) {
|
|
118
|
+
const subSize = Math.max(FONT_SIZE.body, Math.round(R * 0.62));
|
|
101
119
|
g.fillStyle = COLOR.textSub;
|
|
102
|
-
g.font = `${
|
|
103
|
-
g.fillText(o.subtitle, x + R * 2 +
|
|
120
|
+
g.font = `${subSize}px ${FONT}`;
|
|
121
|
+
g.fillText(o.subtitle, x + R * 2 + 18, y + Math.max(40, R * 2 - 8));
|
|
104
122
|
}
|
|
105
123
|
|
|
106
124
|
// 右侧徽章
|