@bongos/core 1.19.404 → 1.19.405
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 +13 -13
- package/docs/copy-inventory.md +78 -79
- package/docs/copy-registry.json +94 -103
- package/docs/design/landing-page-direction-v2.md +2 -0
- package/package-lock.json +2 -2
- package/package.json +1 -1
- package/public-landing/index.html +18 -41
- package/src/module-api.js +3 -1
- package/tests/landing_page.mjs +16 -4
|
@@ -58,6 +58,8 @@ What the pick settles: the settled constraint (dark-first with a real, tested li
|
|
|
58
58
|
|
|
59
59
|
**2026-08-28: the owner's review of the shipped hero (task 1003333).** Three corrections to the pick, each overriding this record and `DESIGN.md` where they conflicted: the doors sit in the blob's lower half (stage 73% dark / 75% light, from 53 / 60), not at its centre; the three leader-line figures leave the landing (they read as "random lines" there; the poster card on `/projects` keeps the grammar, task 1003301); and the small bead's orbit is replaced by the big plates themselves drifting like a lava lamp (v1's "drift" of §3, built: `drift-form` 74s, `drift-orb` 58s, transform only, dead under reduced motion; the pointer parallax stays out, no motion in JavaScript). The bead left the hero and survives as the third project orb below the fold. The two feeds that fed only the figures (`/public/cost-summary`, `/public/leaderboard`) leave the page with them.
|
|
60
60
|
|
|
61
|
+
**2026-08-28, the second note (task 1003334).** Seeing the before/after of task 1003333, the owner found the chrome bongo pair sitting on the top-right sweeping form did not fit ("the random bongos on the blobs background"). Offered three treatments (remove it from the hero; keep it off the blob on plain black or paper; phones only), the owner picked **remove it from the hero**. The pair is no longer a hero object: `.mark`, its arrival and its tokens leave; it stays as the closing figure, the second project orb and the bar's mark. The sweeping form stays as a bare backdrop. Under 900 the masthead is the big blob alone, with the words keeping the 56vw the pair used to hold above them.
|
|
62
|
+
|
|
61
63
|
## 7. Shot list: real imagery still owed
|
|
62
64
|
|
|
63
65
|
No version left a placeholder slot: every image on the three pages is a real plate (the round-2 chrome set, the single blob, the two bongo pairs, the two new blob cutouts) or the real Verro Labs medallion, and the proof is the ledger rendered as page content, so no hall or hub capture is used. What the build will still owe:
|
package/package-lock.json
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@bongos/core",
|
|
3
|
-
"version": "1.19.
|
|
3
|
+
"version": "1.19.405",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "@bongos/core",
|
|
9
|
-
"version": "1.19.
|
|
9
|
+
"version": "1.19.405",
|
|
10
10
|
"license": "AGPL-3.0-or-later",
|
|
11
11
|
"dependencies": {
|
|
12
12
|
"express": "^4.21.2",
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@bongos/core",
|
|
3
|
-
"version": "1.19.
|
|
3
|
+
"version": "1.19.405",
|
|
4
4
|
"description": "Cloud Bongos — the AI-first build platform core (GDS + platform surfaces + module system), installed as a versioned dependency (ADR 0108).",
|
|
5
5
|
"license": "AGPL-3.0-or-later",
|
|
6
6
|
"main": "src/platform-server.js",
|
|
@@ -112,7 +112,6 @@ main:focus{outline:none;box-shadow:none}
|
|
|
112
112
|
/* the authored moment: the forms arrive from slightly apart and converge into place */
|
|
113
113
|
@keyframes arrive-form{from{translate:3.4vw -2.2vh;opacity:.36}to{translate:0 0;opacity:1}}
|
|
114
114
|
@keyframes arrive-orb{from{translate:-2.8vw 2.4vh;opacity:.36}to{translate:0 0;opacity:1}}
|
|
115
|
-
@keyframes arrive-mark{from{translate:2.6vw 1.8vh;opacity:.36}to{translate:0 0;opacity:1}}
|
|
116
115
|
/* the breath: a 32s swell, and a 40s hue drift so the iridescence keeps moving */
|
|
117
116
|
@keyframes breathe{0%{scale:1}50%{scale:1.035}100%{scale:1}}
|
|
118
117
|
@keyframes sheen{0%{filter:var(--sky-shadow) hue-rotate(0deg)}
|
|
@@ -124,8 +123,11 @@ main:focus{outline:none;box-shadow:none}
|
|
|
124
123
|
the transform property alone, so it composes with the arrival (translate), the breath (scale)
|
|
125
124
|
and the sheen (filter) instead of fighting them; a translate in percent is a fraction of the
|
|
126
125
|
plate's own box, and it stays inside 5% with rotation inside 1.5deg, so the type over the plate
|
|
127
|
-
keeps its ground. 0% is the graded frame: the rest frame is the composition.
|
|
128
|
-
|
|
126
|
+
keeps its ground. 0% is the graded frame: the rest frame is the composition. Only the plates
|
|
127
|
+
move; the type and the doors sit still in their own layer, which is what the moving ground is
|
|
128
|
+
read against. (The chrome bongo pair that sat still on the sweeping form left the hero with the
|
|
129
|
+
owner's second note, task 1003334; it stays as the closing figure, a project orb and the bar's
|
|
130
|
+
mark.) */
|
|
129
131
|
@keyframes drift-form{
|
|
130
132
|
0%{transform:translate(0,0) rotate(0deg)}
|
|
131
133
|
27%{transform:translate(-2.4%,2.6%) rotate(-.9deg)}
|
|
@@ -224,12 +226,6 @@ h1 .whole{white-space:normal;margin-left:0}
|
|
|
224
226
|
.lede{position:var(--float2);left:var(--lede-x);top:var(--lede-y);width:var(--lede-w);max-width:100%;
|
|
225
227
|
font-size:18.5px;line-height:1.42;color:var(--ink-soft);text-shadow:var(--type-halo)}
|
|
226
228
|
|
|
227
|
-
/* the hero object: the three-quarter chrome pair, an alpha cutout with its own contact shadow */
|
|
228
|
-
.mark{position:var(--float2);left:var(--mark-x);top:var(--mark-y);width:var(--mark-w);aspect-ratio:1;
|
|
229
|
-
background-image:var(--sky-bongos);background-repeat:no-repeat;background-size:100% auto;
|
|
230
|
-
filter:var(--sky-shadow);
|
|
231
|
-
pointer-events:none;animation:arrive-mark 700ms cubic-bezier(.16,1,.3,1) 210ms both}
|
|
232
|
-
|
|
233
229
|
/* the two doors, one joined pill, floating in the lower half of the big blob: below its centre so
|
|
234
230
|
the choice is not the centre of the composition (owner, 2026-08-28; task 1003333). The pair sits
|
|
235
231
|
in its own layer and never moves with the plate that drifts under it. */
|
|
@@ -395,9 +391,6 @@ body{
|
|
|
395
391
|
--orb-w:48vw;
|
|
396
392
|
--orb-x:32vw;
|
|
397
393
|
--orb-y:calc(var(--vh) * 32);
|
|
398
|
-
--mark-w:22vw;
|
|
399
|
-
--mark-x:78vw;
|
|
400
|
-
--mark-y:calc(var(--vh) * 13);
|
|
401
394
|
--doors-cx:56vw;
|
|
402
395
|
--doors-cy:calc(var(--vh) * 75);
|
|
403
396
|
}
|
|
@@ -440,9 +433,6 @@ body{
|
|
|
440
433
|
--orb-w:54vw;
|
|
441
434
|
--orb-x:5vw;
|
|
442
435
|
--orb-y:calc(var(--vh) * 24);
|
|
443
|
-
--mark-w:27vw;
|
|
444
|
-
--mark-x:71vw;
|
|
445
|
-
--mark-y:calc(var(--vh) * 12);
|
|
446
436
|
--doors-cx:32vw;
|
|
447
437
|
--doors-cy:calc(var(--vh) * 73);
|
|
448
438
|
}
|
|
@@ -486,9 +476,6 @@ body{
|
|
|
486
476
|
--orb-w:54vw;
|
|
487
477
|
--orb-x:5vw;
|
|
488
478
|
--orb-y:calc(var(--vh) * 24);
|
|
489
|
-
--mark-w:27vw;
|
|
490
|
-
--mark-x:71vw;
|
|
491
|
-
--mark-y:calc(var(--vh) * 12);
|
|
492
479
|
--doors-cx:32vw;
|
|
493
480
|
--doors-cy:calc(var(--vh) * 73);
|
|
494
481
|
}
|
|
@@ -516,9 +503,10 @@ body{
|
|
|
516
503
|
.bandProfile .bandCell,.bandProfile .bandSlot{flex:none;text-align:left}
|
|
517
504
|
.bandWho{padding-bottom:14px}
|
|
518
505
|
.hero{min-height:0;padding-bottom:36px}
|
|
506
|
+
/* the masthead is the big blob alone (task 1003334): the words start where they did when the
|
|
507
|
+
bongo pair stood above them, so the blob's crown stays the first thing on a phone */
|
|
519
508
|
.layer{display:flex;flex-direction:column;align-items:center;text-align:center;
|
|
520
|
-
top:0;left:auto;right:auto;bottom:auto;padding-top:12px;pointer-events:auto}
|
|
521
|
-
.mark{order:1;margin:0 auto}
|
|
509
|
+
top:0;left:auto;right:auto;bottom:auto;padding-top:calc(12px + 56vw);pointer-events:auto}
|
|
522
510
|
h1{order:2;margin-top:14px}
|
|
523
511
|
h1 .l2{margin-left:0}
|
|
524
512
|
.lede{order:3;margin:16px auto 0}
|
|
@@ -559,9 +547,6 @@ body{
|
|
|
559
547
|
--orb-w:92vw;
|
|
560
548
|
--orb-x:4vw;
|
|
561
549
|
--orb-y:-6vh;
|
|
562
|
-
--mark-w:56vw;
|
|
563
|
-
--mark-x:0;
|
|
564
|
-
--mark-y:0;
|
|
565
550
|
--doors-cx:0;--doors-cy:0;
|
|
566
551
|
}
|
|
567
552
|
:root[data-mode="dark"] body{
|
|
@@ -583,9 +568,6 @@ body{
|
|
|
583
568
|
--orb-w:150vw;
|
|
584
569
|
--orb-x:-25vw;
|
|
585
570
|
--orb-y:22vh;
|
|
586
|
-
--mark-w:56vw;
|
|
587
|
-
--mark-x:0;
|
|
588
|
-
--mark-y:0;
|
|
589
571
|
--doors-cx:0;--doors-cy:0;
|
|
590
572
|
}
|
|
591
573
|
}
|
|
@@ -610,9 +592,6 @@ body{
|
|
|
610
592
|
--orb-w:150vw;
|
|
611
593
|
--orb-x:-25vw;
|
|
612
594
|
--orb-y:22vh;
|
|
613
|
-
--mark-w:56vw;
|
|
614
|
-
--mark-x:0;
|
|
615
|
-
--mark-y:0;
|
|
616
595
|
--doors-cx:0;--doors-cy:0;
|
|
617
596
|
}
|
|
618
597
|
}
|
|
@@ -624,12 +603,13 @@ THESIS: the owner's template, built as a working front door. One chrome sculptur
|
|
|
624
603
|
first viewport, the headline crosses it in two lines, and the only thing on the big blob is the
|
|
625
604
|
choice: the two doors, joined, floating in its lower half.
|
|
626
605
|
FIRST VIEWPORT (1440, dark): the big round blob 54vw at the centre-left, its top crossed by the
|
|
627
|
-
h1's second line; the sweeping form across the upper right
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
606
|
+
h1's second line; the sweeping form across the upper right as a bare backdrop; the lede top-left
|
|
607
|
+
under the first line; the joined door pill in the blob's lower half, below its centre, primary
|
|
608
|
+
carrying the one warm accent, its ground half black so the sculpture still reads through it;
|
|
609
|
+
nothing else sits on the sculpture. The owner's review of 2026-08-28 took the three leader-line
|
|
610
|
+
figures off the landing (task 1003333; the poster card on /projects keeps that grammar) and then
|
|
611
|
+
the chrome bongo pair that sat on the sweeping form (task 1003334; it stays as the closing figure,
|
|
612
|
+
the second project orb and the bar's mark). The pipeline rail lives below the fold.
|
|
633
613
|
STAGE: every vertical token in the hero is a percentage of a FLOORED stage, max(100dvh, 900px),
|
|
634
614
|
not of the raw viewport. At 900 and taller the frame above is reproduced exactly; a shorter laptop
|
|
635
615
|
viewport (1536x730, 1440x760) scrolls the last of the hero instead of recomposing it, which is what
|
|
@@ -648,13 +628,13 @@ under a slow hue drift (plus or minus 12 degrees, 40s) so the iridescence keeps
|
|
|
648
628
|
big plates float like a lava lamp on their own long loops (the sweeping form 74s, the blob 58s;
|
|
649
629
|
translate inside 5% of each plate's own box, rotation inside 1.5deg, on the transform property
|
|
650
630
|
alone). The authored moment is the arrival: the forms converge from slightly apart into place in
|
|
651
|
-
700ms. All CSS, all on the plates themselves so the lighten group is never broken; the
|
|
652
|
-
|
|
631
|
+
700ms. All CSS, all on the plates themselves so the lighten group is never broken; the type and the
|
|
632
|
+
doors sit in their own layer and never move with a plate. The world layer's reduced-motion
|
|
653
633
|
kill switch stops every one of them, and the still frame (every plate at 0%, blob at rest, no hue
|
|
654
634
|
shift) is the composition.
|
|
655
635
|
LIGHT ANSWER, "the rebuilt light mode": no black panel anywhere. The same sculpture, cut out with
|
|
656
636
|
real alpha, sits directly on the pale ground with a soft contact shadow so it reads as objects on
|
|
657
|
-
paper. The blob
|
|
637
|
+
paper. The blob is whole; the sweeping form is deliberately not, it carries a
|
|
658
638
|
gradient mask that dissolves its left edge and it bleeds off the right of the viewport, which is how
|
|
659
639
|
a form that wide stays a backdrop and not a fourth object. The type moves off the chrome onto clean
|
|
660
640
|
paper at the left. The doors keep their place in the blob's lower half on a near opaque pale
|
|
@@ -765,9 +745,6 @@ composition A; landing composition v3, picked by the owner 2026-08-27. No roll,
|
|
|
765
745
|
|
|
766
746
|
<p class="lede">AI agents claim tasks and ship the code. You set the direction and the gates.</p>
|
|
767
747
|
|
|
768
|
-
<div class="mark" role="img"
|
|
769
|
-
aria-label="A pair of bongo drums in mirror-polished chrome, seen from three quarters"></div>
|
|
770
|
-
|
|
771
748
|
<div class="doors">
|
|
772
749
|
<div class="doorbar">
|
|
773
750
|
<a class="door" href="/projects">Find a project to join</a>
|
package/src/module-api.js
CHANGED
|
@@ -1248,8 +1248,10 @@ const { validateOrRespond, LIMITS, parseId, asyncHandler, corsPublicGet, parsePa
|
|
|
1248
1248
|
// landed since 1.19.402 with no explicit bump. run 33208825538. (task 1002620)
|
|
1249
1249
|
// 1.19.404 — CI auto-patch (publish-on-merge, ADR 0161): carrier for merges
|
|
1250
1250
|
// landed since 1.19.403 with no explicit bump. run 33211074633. (task 1002620)
|
|
1251
|
+
// 1.19.405 — CI auto-patch (publish-on-merge, ADR 0161): carrier for merges
|
|
1252
|
+
// landed since 1.19.404 with no explicit bump. run 33212035244. (task 1002620)
|
|
1251
1253
|
// ---------------------------------------------------------------------------
|
|
1252
|
-
const CORE_VERSION = '1.19.
|
|
1254
|
+
const CORE_VERSION = '1.19.405'; // CI auto-patch carrier (ADR 0161); see changelog above
|
|
1253
1255
|
|
|
1254
1256
|
// A namespaced logger so a module's log lines are attributable + consistent.
|
|
1255
1257
|
// Usage: const log = api.logger('dev-box'); log.info('mounted');
|
package/tests/landing_page.mjs
CHANGED
|
@@ -317,7 +317,7 @@ test('the signature animations are plain declarations, so the switch reaches the
|
|
|
317
317
|
for (const name of [
|
|
318
318
|
'breathe', 'sheen', // the breath
|
|
319
319
|
'drift-form', 'drift-orb', // the drift (task 1003333)
|
|
320
|
-
'arrive-form', 'arrive-orb',
|
|
320
|
+
'arrive-form', 'arrive-orb', // the authored moment
|
|
321
321
|
]) {
|
|
322
322
|
assert.match(PAGE_CSS, new RegExp(`@keyframes\\s+${name}\\s*\\{`), `@keyframes ${name} is gone`);
|
|
323
323
|
assert.match(PAGE_CSS, new RegExp(`animation:[^;}]*\\b${name}\\b`), `nothing runs ${name}`);
|
|
@@ -343,7 +343,7 @@ test('the breath stays slow and the arrival stays brief', () => {
|
|
|
343
343
|
assert.ok(form >= 30, 'the sweeping form drifts over 74s; under 30s it paddles');
|
|
344
344
|
assert.ok(orb >= 30, 'the blob drifts over 58s; under 30s it paddles');
|
|
345
345
|
assert.notEqual(form, orb, 'equal periods would make the two plates read as one animation');
|
|
346
|
-
for (const arrive of ['arrive-form', 'arrive-orb'
|
|
346
|
+
for (const arrive of ['arrive-form', 'arrive-orb']) {
|
|
347
347
|
assert.ok(period(arrive, 'ms') <= 800, `${arrive} holds the first paint too long`);
|
|
348
348
|
}
|
|
349
349
|
});
|
|
@@ -398,13 +398,25 @@ test('the big plates drift on transform alone, and the still object never does (
|
|
|
398
398
|
}
|
|
399
399
|
const form = PAGE_CSS.match(/\n\.form\{[^}]*\}/);
|
|
400
400
|
const orb = PAGE_CSS.match(/\n\.orb\{[^}]*\}/);
|
|
401
|
-
const mark = PAGE_CSS.match(/\n\.mark\{[^}]*\}/);
|
|
402
401
|
assert.match(form[0], /animation:[^}]*\bdrift-form\b/, 'the sweeping form drifts');
|
|
403
402
|
assert.match(orb[0], /animation:[^}]*\bdrift-orb\b/, 'the big blob drifts');
|
|
404
|
-
assert.doesNotMatch(mark[0], /drift/, 'the bongo pair is the still object the moving ground is read against');
|
|
405
403
|
assert.doesNotMatch(PAGE_CSS, /\.doors\{[^}]*animation/, 'the doors never move with a plate');
|
|
406
404
|
});
|
|
407
405
|
|
|
406
|
+
test('the chrome bongo pair is not a hero object; it keeps the closing figure, the orb and the bar (task 1003334)', () => {
|
|
407
|
+
// the owner's second note: the pair sitting on the top-right blob did not fit. It leaves the hero
|
|
408
|
+
// at every width; the phone masthead is the big blob alone, with the words starting where they
|
|
409
|
+
// did when the pair stood above them.
|
|
410
|
+
const hero = HTML.split('<section class="hero">')[1].split('</section>')[0];
|
|
411
|
+
assert.doesNotMatch(hero, /class="mark"|role="img"|bongo drums/, 'a hero object came back');
|
|
412
|
+
assert.doesNotMatch(PAGE_CSS, /\n\.mark\{|--mark-[wxy]|@keyframes\s+arrive-mark\b/, 'the hero object\'s CSS survived');
|
|
413
|
+
assert.match(PAGE_CSS, /\.layer\{[^}]*padding-top:calc\(12px \+ 56vw\)/, 'under 900 the words keep the height the object held');
|
|
414
|
+
// the pair is still the world's object elsewhere on the page
|
|
415
|
+
assert.match(PAGE_CSS, /\.close \.closemark\{[^}]*--sky-bongos/, 'the closing figure is the pair');
|
|
416
|
+
assert.match(PAGE_CSS, /\.o2\{[^}]*--bead-src:var\(--sky-bongos\)/, 'the second project orb is the pair');
|
|
417
|
+
assert.match(HTML, /<a class="barMark" href="\/"[^>]*>\s*<svg viewBox="0 0 26 20"/, 'the bar keeps the mark');
|
|
418
|
+
});
|
|
419
|
+
|
|
408
420
|
// ── the live-data contract ─────────────────────────────────────────────────
|
|
409
421
|
// Five public feeds fill the page after it has already rendered a real, baked
|
|
410
422
|
// state. Everything here is invisible to a passing render: a feed renamed, an
|