@bongos/core 1.21.7 → 1.21.8
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/.bongos-core.json +56 -21
- package/docs/copy-inventory.md +20 -5
- package/docs/copy-registry.json +163 -16
- package/docs/module-api-changelog.md +2 -0
- package/docs/page-inventory.json +33 -4
- package/docs/page-readings.json +44 -2
- package/modules/hall-ui/public/city-draw.js +11 -2
- package/modules/hall-ui/public/street-draw.js +585 -0
- package/modules/hall-ui/public/street.css +188 -0
- package/modules/hall-ui/public/street.html +118 -0
- package/modules/hall-ui/public/street.js +364 -0
- package/modules/hall-ui/public/street.states.json +43 -0
- package/modules/hall-ui/records/governor-street.md +14 -0
- package/package-lock.json +2 -2
- package/package.json +1 -1
- package/release-notes.json +10 -0
- package/src/bongos/serve-internal.js +12 -0
- package/src/module-api.js +1 -1
- package/tests/hall_audit.mjs +9 -1
- package/tests/hall_page_gate_map.mjs +3 -0
- package/tests/hall_street.mjs +521 -0
|
@@ -0,0 +1,188 @@
|
|
|
1
|
+
/* modules/hall-ui/public/street.css — THE STREET (task 1004525, goal 1000125,
|
|
2
|
+
R03). The street branch of the <style> and template of
|
|
3
|
+
docs/design/mocks/governor-city/Street.dc.html: the same header strip, names
|
|
4
|
+
and state lines, group brackets, pins with their labels, crates, doors, six
|
|
5
|
+
readings and card, at the same sizes, and the same keyframes (ring, enter,
|
|
6
|
+
bob). What changed is where the colours come from: the prototype wrote its
|
|
7
|
+
theme() values inline; here every colour is one of the hall's tokens
|
|
8
|
+
(style.css + the branding pack), whose values ARE the prototype's (bg #000 /
|
|
9
|
+
#edecee, ink, ink-soft, ink-faint, the rules, the accent #fb9569 and its
|
|
10
|
+
dark ink #2a1305). The drawing's own faces are drawing data in
|
|
11
|
+
street-draw.js (the prototype's front-on palette).
|
|
12
|
+
Nothing else is on the page, as on the city (task 1004524): no hall
|
|
13
|
+
sidebar, no top bar; the stage is the window.
|
|
14
|
+
No :root here (tests/hall_reading_world.mjs): page tokens live on the body.
|
|
15
|
+
The two dark blocks below are byte-identical twins. */
|
|
16
|
+
|
|
17
|
+
body[data-page="street"] {
|
|
18
|
+
/* the hall's ground plate and its veil are the hall chrome's; the street is its own ground */
|
|
19
|
+
--plate: none;
|
|
20
|
+
--plate-veil: none;
|
|
21
|
+
margin: 0;
|
|
22
|
+
height: 100%;
|
|
23
|
+
overflow: hidden;
|
|
24
|
+
background: var(--bg);
|
|
25
|
+
color: var(--ink);
|
|
26
|
+
font-family: var(--font-body);
|
|
27
|
+
--street-rule: var(--rule-soft);
|
|
28
|
+
--street-rule-strong: var(--rule);
|
|
29
|
+
--street-accent-text: var(--accent-deep);
|
|
30
|
+
--street-glow: none;
|
|
31
|
+
--street-wash: color-mix(in srgb, var(--ink) 4.5%, transparent);
|
|
32
|
+
--street-crate: color-mix(in srgb, var(--ink) 55%, transparent);
|
|
33
|
+
--street-crate-fill: color-mix(in srgb, var(--ink) 4%, transparent);
|
|
34
|
+
}
|
|
35
|
+
html[data-theme="dark"] body[data-page="street"] {
|
|
36
|
+
--street-rule: color-mix(in srgb, var(--ink) 12%, transparent);
|
|
37
|
+
--street-rule-strong: color-mix(in srgb, var(--ink) 18%, transparent);
|
|
38
|
+
--street-accent-text: color-mix(in srgb, var(--accent) 70%, #ffffff);
|
|
39
|
+
--street-glow: 0 0 20px color-mix(in srgb, var(--accent) 50%, transparent);
|
|
40
|
+
--street-crate: color-mix(in srgb, var(--ink) 60%, transparent);
|
|
41
|
+
}
|
|
42
|
+
@media (prefers-color-scheme: dark) {
|
|
43
|
+
html:not([data-theme]) body[data-page="street"] {
|
|
44
|
+
--street-rule: color-mix(in srgb, var(--ink) 12%, transparent);
|
|
45
|
+
--street-rule-strong: color-mix(in srgb, var(--ink) 18%, transparent);
|
|
46
|
+
--street-accent-text: color-mix(in srgb, var(--accent) 70%, #ffffff);
|
|
47
|
+
--street-glow: 0 0 20px color-mix(in srgb, var(--accent) 50%, transparent);
|
|
48
|
+
--street-crate: color-mix(in srgb, var(--ink) 60%, transparent);
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
html:has(body[data-page="street"]) { height: 100%; }
|
|
53
|
+
|
|
54
|
+
/* the stage: the window */
|
|
55
|
+
.street-stage { position: fixed; inset: 0; margin: 0; padding: 0; display: flex; flex-direction: column; background: var(--bg); color: var(--ink); font-family: var(--font-body); overflow: hidden; }
|
|
56
|
+
|
|
57
|
+
.street-label { font-size: 11.5px; letter-spacing: 0.12em; text-transform: uppercase; color: var(--ink-faint); white-space: nowrap; }
|
|
58
|
+
|
|
59
|
+
/* the header strip: wordmark and kicker left; needs you, moving, your share and the switch right */
|
|
60
|
+
.street-top { flex: none; height: 64px; box-sizing: border-box; display: flex; align-items: center; gap: 16px; padding: 0 32px; border-bottom: 1px solid var(--street-rule); background: var(--bg); position: relative; z-index: 9; }
|
|
61
|
+
.street-top__brand { display: flex; align-items: baseline; gap: 16px; min-width: 0; }
|
|
62
|
+
.street-mark { font-weight: 500; font-size: 17px; letter-spacing: -0.015em; text-transform: lowercase; color: var(--ink); text-decoration: none; display: inline-flex; align-items: center; min-height: 24px; }
|
|
63
|
+
.street-kicker { margin: 0; font-size: 11.5px; font-weight: 400; letter-spacing: 0.12em; text-transform: uppercase; color: var(--ink-faint); white-space: nowrap; }
|
|
64
|
+
.street-hud { display: flex; align-items: center; gap: 36px; margin-left: auto; }
|
|
65
|
+
.street-hud__item { display: flex; align-items: center; gap: 12px; }
|
|
66
|
+
.street-hud__dot { width: 8px; height: 8px; border-radius: 999px; background: var(--street-rule-strong); }
|
|
67
|
+
.street-hud__dot--hot { background: var(--accent); }
|
|
68
|
+
.street-hud__n { font-size: 24px; font-weight: 300; font-variant-numeric: tabular-nums; }
|
|
69
|
+
.street-mode { margin-left: 36px; flex: none; background: none; border: 1px solid var(--street-rule-strong); border-radius: 999px; height: 36px; padding: 0 14px; display: flex; align-items: center; gap: 8px; cursor: pointer; color: var(--ink); font-family: var(--font-body); font-size: 13px; text-transform: lowercase; }
|
|
70
|
+
.street-mode svg { display: block; stroke-width: 1.4; }
|
|
71
|
+
|
|
72
|
+
/* the street band: the prototype's 1440-wide artboard, scaled by street.js */
|
|
73
|
+
.street-window { flex: 1 1 auto; min-height: 0; width: 100%; max-width: none; margin: 0; padding: 0; box-sizing: border-box; display: flex; overflow-x: auto; overflow-y: hidden; position: relative; }
|
|
74
|
+
.street-sizer { position: relative; margin: auto; flex: none; overflow: hidden; }
|
|
75
|
+
.street-board { position: absolute; left: 0; top: 0; width: 1440px; height: 900px; transform-origin: 0 0; transform: scale(var(--street-scale, 1)) translateY(-64px); }
|
|
76
|
+
.street-svg { position: absolute; left: 0; top: 0; pointer-events: none; overflow: visible; }
|
|
77
|
+
.street-layer { position: absolute; left: 0; top: 0; width: 100%; height: 900px; pointer-events: none; }
|
|
78
|
+
.street-layer > * { pointer-events: auto; }
|
|
79
|
+
|
|
80
|
+
.street-hint { position: absolute; left: 0; right: 0; top: 84px; margin: 0; text-align: center; font-size: 11.5px; letter-spacing: 0.12em; text-transform: uppercase; color: var(--ink-faint); pointer-events: none; z-index: 2; }
|
|
81
|
+
.street-evening { position: absolute; left: 0; right: 0; top: 104px; display: flex; flex-direction: column; align-items: center; gap: 10px; pointer-events: none; z-index: 2; }
|
|
82
|
+
.street-evening[hidden] { display: none; }
|
|
83
|
+
.street-evening__h { margin: 0; font-size: 46px; font-weight: 300; letter-spacing: -0.042em; line-height: 1; }
|
|
84
|
+
.street-evening__line { margin: 0; font-size: 16px; color: var(--ink-soft); font-variant-numeric: tabular-nums; }
|
|
85
|
+
|
|
86
|
+
/* work waiting at Review: dashed crates by its door */
|
|
87
|
+
.street-crate { position: absolute; width: 15px; height: 13px; box-sizing: border-box; border: 1px dashed var(--street-crate); background: var(--street-crate-fill); border-radius: 2px; pointer-events: none !important; }
|
|
88
|
+
|
|
89
|
+
/* a name and one line of state under every building */
|
|
90
|
+
.street-col { position: absolute; display: flex; flex-direction: column; align-items: center; gap: 3px; text-align: center; pointer-events: none !important; }
|
|
91
|
+
.street-col__name { max-width: 100%; overflow: hidden; text-overflow: ellipsis; font-size: 11px; letter-spacing: 0.11em; text-transform: uppercase; color: var(--ink-faint); white-space: nowrap; }
|
|
92
|
+
.street-col__name--strong { color: var(--ink); }
|
|
93
|
+
.street-col__state { font-size: 12.5px; color: var(--ink-soft); line-height: 1.3; }
|
|
94
|
+
|
|
95
|
+
/* the group brackets */
|
|
96
|
+
.street-group { position: absolute; display: flex; flex-direction: column; align-items: center; gap: 8px; pointer-events: none !important; }
|
|
97
|
+
.street-group__bracket { width: 100%; height: 6px; box-sizing: border-box; border: 1px solid var(--street-rule-strong); border-top: 0; }
|
|
98
|
+
|
|
99
|
+
/* doors: every building and district */
|
|
100
|
+
.street-door { position: absolute; z-index: 1; border-radius: 8px; }
|
|
101
|
+
.street-door:hover { background: color-mix(in srgb, var(--accent) 7%, transparent); }
|
|
102
|
+
.street-door--here { outline: 1px solid color-mix(in srgb, var(--accent) 55%, transparent); outline-offset: -3px; }
|
|
103
|
+
|
|
104
|
+
/* pins: orange and pulsing waits on you; ink is moving; grey is settled; dashed is the queue */
|
|
105
|
+
.street-pin { position: absolute; z-index: 3; display: flex; flex-direction: column; align-items: center; gap: 6px; background: transparent; border: 0; padding: 0; cursor: pointer; font-family: var(--font-body); color: var(--ink); }
|
|
106
|
+
.street-pin__label { max-width: 110px; overflow: hidden; text-overflow: ellipsis; font-size: 12px; line-height: 1.2; white-space: nowrap; }
|
|
107
|
+
.street-pin__head { position: relative; width: 28px; height: 28px; flex-shrink: 0; border-radius: 999px; box-sizing: border-box; display: flex; align-items: center; justify-content: center; transition: transform 200ms cubic-bezier(.2,.7,.3,1); }
|
|
108
|
+
.street-pin:hover .street-pin__head { transform: scale(1.12); }
|
|
109
|
+
.street-pin__head svg { display: block; }
|
|
110
|
+
.street-pin__head path { fill: currentColor; }
|
|
111
|
+
.street-pin__head path + path { fill: none; stroke: currentColor; stroke-width: 1.4; }
|
|
112
|
+
.street-pin__stem { width: 0; flex-grow: 1; border-left: 1px solid transparent; }
|
|
113
|
+
.street-pin__ring { position: absolute; inset: -1px; border-radius: 999px; border: 1px solid var(--accent); }
|
|
114
|
+
.street-pin__count { font-size: 12.5px; font-weight: 500; font-variant-numeric: tabular-nums; }
|
|
115
|
+
.street-pin--needs .street-pin__label { color: var(--street-accent-text); }
|
|
116
|
+
.street-pin--needs .street-pin__head { background: var(--accent); color: var(--accent-on); box-shadow: var(--street-glow); }
|
|
117
|
+
.street-pin--needs .street-pin__stem { border-left-color: color-mix(in srgb, var(--accent) 65%, transparent); }
|
|
118
|
+
.street-pin--moving .street-pin__head { background: var(--ink); color: var(--bg-card); }
|
|
119
|
+
.street-pin--moving .street-pin__stem { border-left-color: color-mix(in srgb, var(--ink) 45%, transparent); }
|
|
120
|
+
.street-pin--settled .street-pin__label { color: var(--ink-faint); }
|
|
121
|
+
.street-pin--settled .street-pin__head { background: color-mix(in srgb, var(--ink) 10%, var(--bg)); border: 1px solid color-mix(in srgb, var(--ink) 22%, transparent); color: var(--ink-faint); }
|
|
122
|
+
.street-pin--settled .street-pin__stem { border-left-color: color-mix(in srgb, var(--ink) 22%, transparent); }
|
|
123
|
+
.street-pin--queue .street-pin__head { background: transparent; border: 1px dashed var(--street-crate); color: var(--ink); }
|
|
124
|
+
.street-pin--queue .street-pin__stem { border-left-color: color-mix(in srgb, var(--ink) 22%, transparent); }
|
|
125
|
+
|
|
126
|
+
/* the six readings */
|
|
127
|
+
.street-signs { flex: none; height: 128px; box-sizing: border-box; margin: 0 32px; border-top: 1px solid var(--street-rule); background: var(--bg); display: grid; grid-template-columns: repeat(6, minmax(0, 1fr)); position: relative; z-index: 5; }
|
|
128
|
+
.street-sign { display: flex; flex-direction: column; gap: 5px; padding: 12px 16px 0; text-align: left; color: var(--ink); text-decoration: none; border-left: 1px solid var(--street-rule); transition: transform 200ms cubic-bezier(.2,.7,.3,1); min-width: 0; }
|
|
129
|
+
.street-sign:hover { transform: translateY(-2px); }
|
|
130
|
+
.street-sign--here { background: var(--street-wash); }
|
|
131
|
+
.street-sign__top { display: flex; align-items: center; gap: 8px; }
|
|
132
|
+
.street-sign__top .street-label { font-size: 11px; }
|
|
133
|
+
.street-sign__dot { width: 7px; height: 7px; border-radius: 999px; background: var(--street-rule-strong); flex: none; }
|
|
134
|
+
.street-sign--hot .street-sign__dot { background: var(--accent); }
|
|
135
|
+
.street-sign__figure { font-size: 26px; font-weight: 300; letter-spacing: -0.03em; font-variant-numeric: tabular-nums; }
|
|
136
|
+
.street-sign__line { font-size: 12.5px; line-height: 1.35; color: var(--ink-soft); }
|
|
137
|
+
|
|
138
|
+
/* the matter card, over the street (short form until task 1004528) */
|
|
139
|
+
.street-card { position: absolute; left: var(--street-card-x, 32px); bottom: 16px; width: 390px; max-height: 300px; overflow-y: auto; box-sizing: border-box; background: var(--bg-card); border: 1px solid var(--street-rule-strong); border-radius: 16px; z-index: 8; padding: 14px 20px 18px; display: flex; flex-direction: column; gap: 11px; }
|
|
140
|
+
.street-card[hidden] { display: none; }
|
|
141
|
+
.street-card__head { display: flex; align-items: center; gap: 10px; }
|
|
142
|
+
.street-card__head .street-label { font-size: 11px; }
|
|
143
|
+
.street-card__fill { flex-grow: 1; }
|
|
144
|
+
.street-card__close { background: none; border: 0; width: 34px; height: 34px; border-radius: 999px; cursor: pointer; display: flex; align-items: center; justify-content: center; flex-shrink: 0; color: var(--ink-faint); }
|
|
145
|
+
.street-card__close svg { stroke-width: 1.5; }
|
|
146
|
+
.street-card__title { margin: 0; font-size: 21px; font-weight: 300; letter-spacing: -0.025em; line-height: 1.2; }
|
|
147
|
+
.street-card__meta { margin: 0; font-size: 13px; color: var(--ink-soft); font-variant-numeric: tabular-nums; }
|
|
148
|
+
.street-card__lines { margin: 0; padding: 0; list-style: none; display: flex; flex-direction: column; }
|
|
149
|
+
.street-card__lines li { padding: 8px 0; border-top: 1px solid var(--street-rule); font-size: 14px; line-height: 1.4; }
|
|
150
|
+
.street-card__result { margin: 0; font-size: 15px; line-height: 1.45; }
|
|
151
|
+
.street-card__open { align-self: flex-start; display: inline-flex; align-items: center; min-height: 24px; padding: 6px 0; font-size: 14px; color: var(--street-accent-text); text-decoration: underline; text-underline-offset: 4px; }
|
|
152
|
+
.street-card__open[hidden] { display: none; }
|
|
153
|
+
|
|
154
|
+
.street-mark:focus-visible, .street-mode:focus-visible, .street-pin:focus-visible, .street-door:focus-visible, .street-sign:focus-visible, .street-card__close:focus-visible, .street-card__open:focus-visible { outline: 2px solid var(--accent); outline-offset: 3px; }
|
|
155
|
+
|
|
156
|
+
/* narrower: the strip tightens, then wraps; the readings scroll sideways */
|
|
157
|
+
@media (max-width: 1180px) {
|
|
158
|
+
.street-hud { gap: 20px; }
|
|
159
|
+
.street-hud__n { font-size: 20px; }
|
|
160
|
+
.street-mode { margin-left: 20px; }
|
|
161
|
+
}
|
|
162
|
+
/* narrow: two rows inside the 80 px top-bar floor, the wordmark and the switch
|
|
163
|
+
on the first, the three figures on the second as their own sideways strip */
|
|
164
|
+
@media (max-width: 900px) {
|
|
165
|
+
.street-top { height: auto; max-height: 80px; display: grid; grid-template-columns: minmax(0, 1fr) auto; grid-template-areas: "brand mode" "hud hud"; row-gap: 2px; padding: 5px 16px; }
|
|
166
|
+
.street-top__brand { grid-area: brand; }
|
|
167
|
+
.street-mode { grid-area: mode; margin-left: 0; height: 34px; }
|
|
168
|
+
.street-hud { grid-area: hud; margin-left: 0; gap: 18px; min-width: 0; overflow-x: auto; overflow-y: hidden; white-space: nowrap; height: 30px; }
|
|
169
|
+
.street-hud__item { gap: 6px; flex: none; }
|
|
170
|
+
.street-hud .street-label { font-size: 11px; }
|
|
171
|
+
.street-hud__n { font-size: 16px; }
|
|
172
|
+
.street-signs { margin: 0 16px; grid-template-columns: none; grid-auto-flow: column; grid-auto-columns: 180px; overflow-x: auto; overflow-y: hidden; }
|
|
173
|
+
}
|
|
174
|
+
@media (max-width: 560px) {
|
|
175
|
+
.street-card { left: 16px; right: 16px; width: auto; }
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
/* the prototype's motion, verbatim */
|
|
179
|
+
@keyframes street-ring { 0% { transform: scale(.8); opacity: .9; } 100% { transform: scale(2.3); opacity: 0; } }
|
|
180
|
+
@keyframes street-enter { from { opacity: 0; transform: translateY(8px); } to { opacity: 1; transform: none; } }
|
|
181
|
+
.street-pin__ring { animation: street-ring 2.8s cubic-bezier(.2,.7,.3,1) infinite; }
|
|
182
|
+
.street-card, .street-evening { animation: street-enter 320ms cubic-bezier(.16,1,.3,1) both; }
|
|
183
|
+
|
|
184
|
+
/* The Kill Switch: under reduced motion nothing moves. The rest frame is the
|
|
185
|
+
whole street with its pins standing still. */
|
|
186
|
+
@media (prefers-reduced-motion: reduce) {
|
|
187
|
+
body[data-page="street"] *, body[data-page="street"] *::before, body[data-page="street"] *::after { animation: none !important; transition: none !important; }
|
|
188
|
+
}
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
<!doctype html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="utf-8">
|
|
5
|
+
<meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover">
|
|
6
|
+
<title>The street — {{worldName}}</title>
|
|
7
|
+
<meta name="description" content="The governor's street: every part of the project's government as a building, in the order work moves, a pin over every matter, and six readings along the bottom.">
|
|
8
|
+
<link rel="preconnect" href="https://fonts.googleapis.com">
|
|
9
|
+
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
|
10
|
+
<!-- The faces (Manrope, JetBrains Mono) come from the branding pack's font
|
|
11
|
+
links, injected into this head by the server like every hall page's
|
|
12
|
+
(tests/hall_tokens.mjs: no hall page hardcodes a web-font stylesheet). -->
|
|
13
|
+
<link rel="stylesheet" href="/builders/style.css?v=2026-07-02-shell1">
|
|
14
|
+
<link rel="stylesheet" href="/builders/street.css?v=2026-10-02-street1">
|
|
15
|
+
</head>
|
|
16
|
+
<!-- THE STREET (task 1004525, goal 1000125, R03). The street view of
|
|
17
|
+
docs/design/mocks/governor-city/Street.dc.html (renderVals' street branch,
|
|
18
|
+
signsOf and the street half of its template), built over the governor
|
|
19
|
+
docket (GET /api/bongos/government/docket, task 1004523), the open goals
|
|
20
|
+
with their task rollups, and the viewer's earnings this month.
|
|
21
|
+
|
|
22
|
+
Nothing else is on the page, on purpose, as on the city (task 1004524):
|
|
23
|
+
no hall sidebar, no top bar. It has no menu link of its own: the way in is
|
|
24
|
+
the city's start governing, and the wordmark is the way back.
|
|
25
|
+
|
|
26
|
+
The markup is the prototype's: its header (the wordmark back to the city,
|
|
27
|
+
the kicker, needs you, moving, your share, the light/dark switch), the
|
|
28
|
+
street drawn on its 1440-wide artboard (street.js scales it to the
|
|
29
|
+
window), and the six readings along the bottom. Every
|
|
30
|
+
building and district is a door (an <a>) to where its interior lives —
|
|
31
|
+
/builders/street#building=<key> and #district=<goal id> (README "Where the
|
|
32
|
+
screens live"; task 1004526 builds them). A pin opens the matter's short
|
|
33
|
+
card (task 1004528 makes it act).
|
|
34
|
+
|
|
35
|
+
The drawing is street-draw.js (the prototype's front-on kit, verbatim, as
|
|
36
|
+
pure data) over city-draw.js (the glyphs and the seeded random, shared with
|
|
37
|
+
the city); street.js reads the feeds and builds the nodes; street.css is
|
|
38
|
+
the template's <style> on the hall's tokens.
|
|
39
|
+
|
|
40
|
+
The page is gated on board.vote.cast (src/bongos/serve-internal.js), the
|
|
41
|
+
same atom the docket read checks, so whoever reaches the street can read
|
|
42
|
+
what it draws. -->
|
|
43
|
+
<body data-page="street" class="street">
|
|
44
|
+
|
|
45
|
+
<div class="street-stage">
|
|
46
|
+
|
|
47
|
+
<header class="street-top">
|
|
48
|
+
<div class="street-top__brand">
|
|
49
|
+
<a class="street-mark" id="streetHome" href="/builders/city" aria-label="Back to the city overview">{{productName}}</a>
|
|
50
|
+
<h1 class="street-kicker">the street</h1>
|
|
51
|
+
</div>
|
|
52
|
+
<div class="street-hud">
|
|
53
|
+
<div class="street-hud__item">
|
|
54
|
+
<span class="street-hud__dot" id="hudDot"></span>
|
|
55
|
+
<span class="street-label">needs you</span>
|
|
56
|
+
<span class="street-hud__n" id="hudNeeds">—</span>
|
|
57
|
+
</div>
|
|
58
|
+
<div class="street-hud__item">
|
|
59
|
+
<span class="street-label">moving</span>
|
|
60
|
+
<span class="street-hud__n" id="hudMoving">—</span>
|
|
61
|
+
</div>
|
|
62
|
+
<div class="street-hud__item">
|
|
63
|
+
<span class="street-label">your share this month</span>
|
|
64
|
+
<span class="street-hud__n" id="hudShare">—</span>
|
|
65
|
+
</div>
|
|
66
|
+
</div>
|
|
67
|
+
<button type="button" class="street-mode" id="streetMode" aria-label="Switch to light mode" title="Switch to light mode">
|
|
68
|
+
<svg width="14" height="14" viewBox="0 0 14 14" fill="none" stroke="currentColor" aria-hidden="true"><path id="streetModeIcon" d=""></path></svg>
|
|
69
|
+
<span id="streetModeWord">light</span>
|
|
70
|
+
</button>
|
|
71
|
+
</header>
|
|
72
|
+
|
|
73
|
+
<main class="street-window" id="streetWindow">
|
|
74
|
+
<div class="street-sizer" id="streetSizer">
|
|
75
|
+
<div class="street-board" id="streetBoard" role="group" aria-label="The street">
|
|
76
|
+
<p class="street-hint" id="streetHint"></p>
|
|
77
|
+
<div class="street-evening" id="streetEvening" hidden>
|
|
78
|
+
<p class="street-evening__h">nothing waits on you.</p>
|
|
79
|
+
<p class="street-evening__line" id="streetEveningLine"></p>
|
|
80
|
+
</div>
|
|
81
|
+
<svg class="street-svg" id="streetSvg" width="1440" height="900" viewBox="0 0 1440 900" aria-hidden="true" focusable="false">
|
|
82
|
+
<g id="streetFlat"></g>
|
|
83
|
+
<g id="streetBlds" class="street-blds"></g>
|
|
84
|
+
</svg>
|
|
85
|
+
<div class="street-layer" id="streetCrates" aria-hidden="true"></div>
|
|
86
|
+
<div class="street-layer" id="streetCols"></div>
|
|
87
|
+
<div class="street-layer" id="streetGroups" aria-hidden="true"></div>
|
|
88
|
+
<div class="street-layer" id="streetDoors"></div>
|
|
89
|
+
<div class="street-layer" id="streetPins"></div>
|
|
90
|
+
</div>
|
|
91
|
+
</div>
|
|
92
|
+
</main>
|
|
93
|
+
|
|
94
|
+
<nav class="street-signs" id="streetSigns" aria-label="The six readings"></nav>
|
|
95
|
+
|
|
96
|
+
<div class="street-card" id="streetCard" role="dialog" aria-modal="false" aria-labelledby="streetCardTitle" hidden>
|
|
97
|
+
<div class="street-card__head">
|
|
98
|
+
<span class="street-label" id="streetCardWhere"></span>
|
|
99
|
+
<span class="street-card__fill"></span>
|
|
100
|
+
<span class="street-label" id="streetCardWhen"></span>
|
|
101
|
+
<button type="button" class="street-card__close" id="streetCardClose" aria-label="Close">
|
|
102
|
+
<svg width="13" height="13" viewBox="0 0 14 14" fill="none" stroke="currentColor" aria-hidden="true"><path d="M2 2L12 12M12 2L2 12"></path></svg>
|
|
103
|
+
</button>
|
|
104
|
+
</div>
|
|
105
|
+
<h2 class="street-card__title" id="streetCardTitle"></h2>
|
|
106
|
+
<p class="street-card__meta" id="streetCardMeta" hidden></p>
|
|
107
|
+
<ul class="street-card__lines" id="streetCardLines" hidden></ul>
|
|
108
|
+
<p class="street-card__result" id="streetCardResult"></p>
|
|
109
|
+
<a class="street-card__open" id="streetCardOpen" href="/builders/street" hidden>open it where it lives</a>
|
|
110
|
+
</div>
|
|
111
|
+
|
|
112
|
+
</div>
|
|
113
|
+
|
|
114
|
+
<script src="/builders/city-draw.js?v=2026-10-02-street1"></script>
|
|
115
|
+
<script src="/builders/street-draw.js?v=2026-10-02-street1"></script>
|
|
116
|
+
<script src="/builders/street.js?v=2026-10-02-street1"></script>
|
|
117
|
+
</body>
|
|
118
|
+
</html>
|