Workers P2: Engine-Requisiten und Branchen-Icons
Möbel und Requisiten aus der Vorlage (Schreibtisch, Monitor mit Schalter an/aus, Aktenschrank, Pflanze, Münze, Pokal, Stempel, Radar, Briefkasten, Tresor, Waage), neu Ablagekorb, Schild und die acht 7x7-Branchen-Icons mit drawIcon. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
This commit is contained in:
1 parent
d44b28368d
commit
514469d93c
2 files changed
+337
No files matched your search
@@ -0,0 +1,255 @@
|
||||
// Möbel, Requisiten und Branchen-Icons des Hustler-Hochhauses.
|
||||
// Portiert aus entwuerfe/sprites.js (Möbel und Requisiten, ohne drawConveyor und drawZone). Neu: drawTray, drawSign,
|
||||
// drawIcon samt ICONS und der Schalter `on` an drawMonitor.
|
||||
// Alle Maße in logischen Einheiten; gezeichnet wird über px() aus sprites.js, es gibt keinen eigenen Zustand.
|
||||
// Kein React, kein Appwrite, kein window/document.
|
||||
|
||||
import { px, label, PAL, TEAM, HAT } from './sprites.js'
|
||||
|
||||
// ---------- Möbel ----------
|
||||
|
||||
export function drawDesk(ctx, x, y, w, accent) {
|
||||
px(ctx, x, y, w, 1, PAL.wood2)
|
||||
px(ctx, x, y + 1, w, 4, PAL.wood)
|
||||
px(ctx, x, y + 5, w, 1, PAL.wood2)
|
||||
if (accent) px(ctx, x, y + 5, w, 1, accent)
|
||||
px(ctx, x + 1, y + 6, 1, 5, PAL.wood2)
|
||||
px(ctx, x + w - 2, y + 6, 1, 5, PAL.wood2)
|
||||
px(ctx, x + 1, y + 11, w - 2, 1, PAL.shadow)
|
||||
}
|
||||
|
||||
// on = false: nur Rahmen, Schirm und Fuß, keine Zeilen und kein Blinken
|
||||
export function drawMonitor(ctx, x, y, t, color, on = true) {
|
||||
const c = color || '#7fb2ff'
|
||||
px(ctx, x, y, 10, 7, PAL.o)
|
||||
px(ctx, x + 1, y + 1, 8, 5, PAL.screen)
|
||||
if (on) {
|
||||
const long = Math.floor((t || 0) * 2) % 2 === 0
|
||||
px(ctx, x + 2, y + 2, 5, 1, c)
|
||||
px(ctx, x + 2, y + 4, long ? 4 : 2, 1, c)
|
||||
}
|
||||
px(ctx, x + 4, y + 7, 2, 2, PAL.o)
|
||||
px(ctx, x + 2, y + 9, 6, 1, PAL.o)
|
||||
}
|
||||
|
||||
export function drawCabinet(ctx, x, y, drawers) {
|
||||
const n = drawers || 3
|
||||
px(ctx, x, y, 12, n * 6 + 1, PAL.metal2)
|
||||
for (let i = 0; i < n; i++) {
|
||||
px(ctx, x + 1, y + 1 + i * 6, 10, 5, PAL.metal)
|
||||
px(ctx, x + 4, y + 3 + i * 6, 4, 1, PAL.metal2)
|
||||
}
|
||||
px(ctx, x, y + n * 6 + 1, 12, 1, PAL.shadow)
|
||||
}
|
||||
|
||||
export function drawPlant(ctx, x, y) {
|
||||
px(ctx, x + 2, y, 2, 2, '#5cbf8a')
|
||||
px(ctx, x, y + 2, 2, 2, '#5cbf8a')
|
||||
px(ctx, x + 4, y + 1, 2, 3, '#3a9466')
|
||||
px(ctx, x + 2, y + 2, 2, 3, '#3a9466')
|
||||
px(ctx, x + 1, y + 5, 4, 4, '#c9714f')
|
||||
px(ctx, x + 1, y + 5, 4, 1, '#a85a3c')
|
||||
}
|
||||
|
||||
// Ablagekorb / Eingangskorb, 10 × 4: voll = Papierstapel ragt über den Rand
|
||||
export function drawTray(ctx, x, y, filled) {
|
||||
px(ctx, x, y + 1, 10, 1, PAL.metal2) // Rand
|
||||
px(ctx, x, y + 2, 10, 1, PAL.metal) // Vorderwand
|
||||
px(ctx, x, y + 3, 10, 1, PAL.metal2) // Boden
|
||||
if (filled) {
|
||||
px(ctx, x + 1, y, 8, 1, PAL.g) // Oberkante des Stapels
|
||||
px(ctx, x + 1, y + 1, 8, 1, PAL.w) // oberstes Blatt in der Öffnung
|
||||
px(ctx, x + 3, y + 1, 4, 1, PAL.p) // eine Textzeile darauf
|
||||
}
|
||||
}
|
||||
|
||||
// ---------- Requisiten ----------
|
||||
|
||||
export function drawCoin(ctx, x, y, t) {
|
||||
const f = Math.floor((t || 0) * 6) % 4
|
||||
const w = [5, 3, 1, 3][f]
|
||||
const ox = (5 - w) / 2
|
||||
px(ctx, x + ox, y, w, 5, PAL.gold2)
|
||||
if (w > 2) px(ctx, x + ox + 1, y + 1, w - 2, 3, PAL.gold)
|
||||
}
|
||||
|
||||
export function drawTrophy(ctx, x, y) {
|
||||
px(ctx, x, y, 7, 1, PAL.gold2)
|
||||
px(ctx, x, y + 1, 7, 3, PAL.gold)
|
||||
px(ctx, x + 1, y + 4, 5, 1, PAL.gold2)
|
||||
px(ctx, x + 3, y + 5, 1, 2, PAL.gold2)
|
||||
px(ctx, x + 1, y + 7, 5, 2, PAL.wood2)
|
||||
px(ctx, x + 1, y + 1, 1, 2, '#fff3c4')
|
||||
}
|
||||
|
||||
export function drawStamp(ctx, x, y, ok) {
|
||||
const c = ok ? PAL.green : PAL.red
|
||||
px(ctx, x, y, 7, 1, c)
|
||||
px(ctx, x, y + 4, 7, 1, c)
|
||||
px(ctx, x, y, 1, 5, c)
|
||||
px(ctx, x + 6, y, 1, 5, c)
|
||||
if (ok) {
|
||||
// Haken
|
||||
px(ctx, x + 2, y + 2, 1, 1, c)
|
||||
px(ctx, x + 3, y + 3, 1, 1, c)
|
||||
px(ctx, x + 4, y + 1, 1, 2, c)
|
||||
} else {
|
||||
// Kreuz
|
||||
px(ctx, x + 2, y + 1, 1, 1, c)
|
||||
px(ctx, x + 4, y + 1, 1, 1, c)
|
||||
px(ctx, x + 3, y + 2, 1, 1, c)
|
||||
px(ctx, x + 2, y + 3, 1, 1, c)
|
||||
px(ctx, x + 4, y + 3, 1, 1, c)
|
||||
}
|
||||
}
|
||||
|
||||
export function drawRadar(ctx, x, y, t) {
|
||||
px(ctx, x + 2, y, 10, 1, PAL.o)
|
||||
px(ctx, x, y + 1, 14, 10, PAL.o)
|
||||
px(ctx, x + 1, y + 2, 12, 8, '#e8f2fc')
|
||||
px(ctx, x + 6, y + 5, 2, 2, TEAM.radar)
|
||||
const a = (t || 0) * 2.2
|
||||
for (let i = 1; i < 6; i++) px(ctx, x + 7 + Math.round(Math.cos(a) * i), y + 6 + Math.round(Math.sin(a) * i * 0.7), 1, 1, TEAM.radar)
|
||||
const blink = Math.floor((t || 0) * 3) % 3
|
||||
if (blink === 0) px(ctx, x + 3, y + 3, 1, 1, PAL.red)
|
||||
if (blink === 1) px(ctx, x + 10, y + 7, 1, 1, PAL.red)
|
||||
px(ctx, x + 6, y + 11, 2, 3, PAL.o)
|
||||
px(ctx, x + 3, y + 14, 8, 1, PAL.o)
|
||||
}
|
||||
|
||||
// Briefkasten des Pults; das rote Abzeichen mit „!“ steht nur bei count > 0
|
||||
export function drawMailbox(ctx, x, y, count) {
|
||||
px(ctx, x, y + 2, 12, 8, TEAM.freigabe)
|
||||
px(ctx, x + 1, y, 10, 2, TEAM.freigabe)
|
||||
px(ctx, x + 2, y + 4, 8, 2, HAT.overseer[1])
|
||||
px(ctx, x + 5, y + 10, 2, 5, PAL.o)
|
||||
if (count > 0) {
|
||||
px(ctx, x + 9, y - 3, 5, 5, PAL.red)
|
||||
px(ctx, x + 11, y - 2, 1, 3, PAL.w)
|
||||
}
|
||||
}
|
||||
|
||||
export function drawVault(ctx, x, y, t) {
|
||||
px(ctx, x, y, 22, 20, PAL.metal2)
|
||||
px(ctx, x + 1, y + 1, 20, 18, PAL.metal)
|
||||
px(ctx, x + 7, y + 6, 8, 8, PAL.metal2)
|
||||
px(ctx, x + 8, y + 7, 6, 6, PAL.metal)
|
||||
const a = (t || 0) * 0.8
|
||||
px(ctx, x + 11 + Math.round(Math.cos(a) * 2), y + 10 + Math.round(Math.sin(a) * 2), 1, 1, PAL.o)
|
||||
px(ctx, x + 18, y + 9, 2, 3, PAL.metal2)
|
||||
px(ctx, x, y + 20, 22, 1, PAL.shadow)
|
||||
}
|
||||
|
||||
export function drawScale(ctx, x, y, tilt) {
|
||||
const d = Math.round(tilt || 0)
|
||||
px(ctx, x + 7, y + 2, 2, 12, PAL.o)
|
||||
px(ctx, x + 3, y + 14, 10, 2, PAL.o)
|
||||
px(ctx, x, y + 2 - d, 16, 1, PAL.o)
|
||||
px(ctx, x - 1, y + 3 - d, 5, 2, TEAM.bewertung)
|
||||
px(ctx, x + 12, y + 3 + d, 5, 2, TEAM.bewertung)
|
||||
}
|
||||
|
||||
// Weißes Schild mit dunklem Rand, 8 hoch; (x, y) = linke obere Ecke, Text zentriert (z. B. „noch nicht angeschlossen“)
|
||||
export function drawSign(ctx, x, y, w, text) {
|
||||
px(ctx, x, y, w, 8, PAL.o)
|
||||
px(ctx, x + 1, y + 1, w - 2, 6, PAL.w)
|
||||
label(ctx, text, x + w / 2, y + 2.5, { size: 9, color: PAL.ink, align: 'center' })
|
||||
}
|
||||
|
||||
// ---------- Branchen-Icons (7 × 7) ----------
|
||||
|
||||
// '.' leer, 'x' Linie in der Teamfarbe, 'a' Akzent in Gold. Schlüssel = die acht Such-Räume (SEARCH_ROOMS)
|
||||
const icon = (...rows) => Object.freeze(rows)
|
||||
export const ICONS = Object.freeze({
|
||||
netz: icon( // Funkwellen
|
||||
'.xxxxx.',
|
||||
'x.....x',
|
||||
'..xxx..',
|
||||
'.x...x.',
|
||||
'.......',
|
||||
'...a...',
|
||||
'...a...',
|
||||
),
|
||||
kleinanzeigen: icon( // Umschlag mit @-Punkt
|
||||
'xxxxxxx',
|
||||
'xx...xx',
|
||||
'x.x.x.x',
|
||||
'x..x..x',
|
||||
'x.....x',
|
||||
'x..a..x',
|
||||
'xxxxxxx',
|
||||
),
|
||||
portale: icon( // Zeilenliste
|
||||
'xxxxxxx',
|
||||
'.......',
|
||||
'a.xxxx.',
|
||||
'.......',
|
||||
'a.xxxx.',
|
||||
'.......',
|
||||
'a.xxxx.',
|
||||
),
|
||||
foren: icon( // Sprechblase
|
||||
'.xxxxx.',
|
||||
'x.....x',
|
||||
'x.a.a.x',
|
||||
'x.....x',
|
||||
'.xxxxx.',
|
||||
'..xx...',
|
||||
'.x.....',
|
||||
),
|
||||
aerzte: icon( // Kreuz
|
||||
'..xxx..',
|
||||
'..xxx..',
|
||||
'xxxxxxx',
|
||||
'xxxxxxx',
|
||||
'xxxxxxx',
|
||||
'..xxx..',
|
||||
'..xxx..',
|
||||
),
|
||||
handwerk: icon( // Hammer
|
||||
'.xxxxx.',
|
||||
'xxxxxxx',
|
||||
'.xxxxx.',
|
||||
'...a...',
|
||||
'...a...',
|
||||
'...a...',
|
||||
'...a...',
|
||||
),
|
||||
selbst: icon( // Person
|
||||
'..xxx..',
|
||||
'.xxxxx.',
|
||||
'..xxx..',
|
||||
'.......',
|
||||
'.xxxxx.',
|
||||
'xxxxxxx',
|
||||
'xxxxxxx',
|
||||
),
|
||||
laden: icon( // Markise
|
||||
'.xxxxx.',
|
||||
'xaxaxax',
|
||||
'xaxaxax',
|
||||
'x.x.x.x',
|
||||
'.......',
|
||||
'x.....x',
|
||||
'xxxxxxx',
|
||||
),
|
||||
})
|
||||
|
||||
// Zeichnet das Icon `name` mit der linken oberen Ecke bei (x, y): 'x' in `color`, 'a' in Gold.
|
||||
// Gleiche Zeichen einer Zeile werden zu einem Rechteck zusammengefasst; ein unbekannter Name zeichnet nichts.
|
||||
export function drawIcon(ctx, name, x, y, color) {
|
||||
const rows = typeof name === 'string' ? ICONS[name] : null
|
||||
if (!Array.isArray(rows)) return
|
||||
for (let r = 0; r < rows.length; r++) {
|
||||
const row = rows[r]
|
||||
let c = 0
|
||||
while (c < row.length) {
|
||||
const ch = row[c]
|
||||
let end = c + 1
|
||||
while (end < row.length && row[end] === ch) end++
|
||||
if (ch === 'x') px(ctx, x + c, y + r, end - c, 1, color)
|
||||
else if (ch === 'a') px(ctx, x + c, y + r, end - c, 1, PAL.gold)
|
||||
c = end
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user