source: Klonkt/src/views/pages/ward.ejs@ 5218863

Last change on this file since 5218863 was 5218863, checked in by Robin <roboburr@โ€ฆ>, 3 months ago

De Ward PWA: het gesprek over de hemel, en de zwaai-hand

Plak 4. Een tik op een gezicht opent nu echt iets.

HET GESPREK is een overlay OVER de levende hemel, geen aparte pagina:
de hemel eronder blijft dezelfde draaiende instantie, en het paneel is
doorschijnend met blur, zoals de glazen bubbels in de app. Dezelfde
bron als de C2S-lezing die Shaer gebruikt (conversationHistory):
inkomend de ap_mentions, uitgaand de eigen directe notes. Openen is
lezen: markRead neemt het maximum, dus een oud toestel kan nooit iets
weer ongelezen maken. Verversen is pollen om de acht seconden zolang
het gesprek open staat; het ritme van een gesprek is geen milliseconde,
en een socket kan later zonder iets te slopen.

DE ZWAAI-HAND hangt in dezelfde hoek als de boei en ze wisselen elkaar
af met de stand: met de kaarten verdwijnt de boei, op de hemel hangt de
hand. Slepen op een gezicht opent het paneel met de drie antwoorden, en
de tekst die je kiest IS het bericht. De treffer is sky.pick(): exact
dezelfde rekensom als een tik, dus mikken gedraagt zich overal gelijk.

Changed files:
src/routes/ward.js

  • /api/thread: beide kanten, cursor, markRead bij openen
  • /api/message: direct bericht of zwaai (shaer:wave reist mee)

src/assets/js/ward-sky.js

  • pick() als publieke mikfunctie

src/assets/js/ward.js

  • thread-overlay met poll, verstuurvak, Escape sluit
  • de hand: slepen, mikken, paneel, versturen

src/views/pages/ward.ejs

  • thread, hand en zwaai-paneel in de schil

src/assets/css/ward.css

  • doorschijnend gesprek, bubbels, hand, paneel

src/services/i18n.js

  • tien sleutels in nl, en, de

test/ward-pwa.test.js

  • het gesprek draagt beide kanten en de zwaai-vlag overleeft; versturen eist een echte ontvanger en echte tekst

remarks: 897 tests groen. Nog niet geport: de (+) voor een nieuw
gesprek, Friends/Orbit-panelen, de composer met media, de mini-speler
en de themakleur; beads volgen. Slepen met een echte vinger is aan
Robin op dev.

-robo
Co-Authored-By: Claude Opus 4.8 <noreply@โ€ฆ>

  • Property mode set to 100644
File size: 4.5 KB
RevLineย 
[303bfc4]1<!DOCTYPE html>
2<html lang="<%= lang %>">
3<head>
4 <meta charset="utf-8">
5 <meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover">
6 <title><%= state.strings.title %></title>
7 <link rel="manifest" href="/ward/manifest.webmanifest">
8 <link rel="icon" href="/ward/icon.svg" type="image/svg+xml">
9 <meta name="theme-color" content="#5a32e6">
10 <link rel="stylesheet" href="/ward/app.css">
11</head>
12<body>
[084b046]13 <!-- De hemel ligt ACHTER alles en draait altijd, ook in kaartenstand: de
14 kaarten vallen straks weg en dan is hij er gewoon nog, precies zoals in
15 Shaer. Aria-hidden want hij is decor tot je hem aanzet. -->
16 <canvas id="sky" aria-hidden="true"></canvas>
17
[303bfc4]18 <main id="app">
[084b046]19 <div class="topbar">
20 <h1><%= state.strings.title %></h1>
21 <button id="mode" type="button" aria-pressed="false"><%= state.strings.toSky %></button>
22 </div>
[303bfc4]23
24 <!-- De hulpknop staat BOVENAAN en niet onderaan bij de instellingen.
25 Als je hem nodig hebt, moet je niet hoeven zoeken. -->
26 <section class="help">
27 <button id="help-btn" type="button"><%= state.strings.help %></button>
28 <p class="hint" id="help-hint"></p>
29 </section>
30
[a5a6249]31 <section id="feed">
32 <h2><%= state.strings.feed %></h2>
33 <div class="cards" id="card-list"></div>
34 <p class="empty" id="feed-empty" hidden><%= state.strings.feedEmpty %></p>
35 </section>
36
[303bfc4]37 <section id="guardians">
38 <h2><%= state.strings.guardians %></h2>
39 <ul class="list" id="guardian-list"></ul>
40 <p class="empty" id="guardians-empty" hidden><%= state.strings.noGuardians %></p>
41 </section>
42
43 <section id="offers" hidden>
44 <h2><%= state.strings.offers %></h2>
45 <ul class="list" id="offer-list"></ul>
46 </section>
47
48 <section id="waiting" hidden>
49 <h2><%= state.strings.waiting %></h2>
50 <ul class="list" id="waiting-list"></ul>
51 </section>
52 </main>
53
[a5a6249]54 <!-- De reddingsboei zweeft boven de pagina en is sleepbaar, net als in
55 Shaer. Een knop, geen plaatje: dan werkt hij ook met een toetsenbord en
56 leest een schermlezer hem voor. -->
57 <button id="buoy" type="button" aria-describedby="buoy-hint">๐Ÿ›Ÿ</button>
58 <p id="buoy-hint" class="sr-only"><%= state.strings.buoyHint %></p>
59
[5218863]60 <!-- De zwaai-hand (ยง5): alleen in berichtenstand, dezelfde hoek als de
61 boei. Ze wisselen elkaar af: met de kaarten verdwijnt de boei, op de
62 hemel hangt de hand. -->
63 <button id="hand" type="button" hidden aria-describedby="hand-hint">๐Ÿ‘‹</button>
64 <p id="hand-hint" class="sr-only"><%= state.strings.handHint %></p>
65
66 <!-- Het gesprek schuift OVER de hemel; die blijft eronder gewoon draaien. -->
67 <section id="thread" hidden>
68 <header>
69 <button id="thread-close" type="button" aria-label="<%= state.strings.close %>">โ†</button>
70 <h2 id="thread-name"></h2>
71 </header>
72 <div id="thread-list"></div>
73 <form id="thread-form">
74 <input id="thread-text" type="text" autocomplete="off" maxlength="2000"
75 placeholder="<%= state.strings.writeHere %>">
76 <button type="submit" class="primary"><%= state.strings.send %></button>
77 </form>
78 </section>
79
80 <!-- Het zwaai-paneel: de tekst die je kiest IS het bericht. -->
81 <dialog id="wave-dialog">
82 <h2 id="wave-title"></h2>
83 <div class="wave-answers">
84 <button data-wave="1">๐Ÿ‘‹ <%= state.strings.wave %></button>
85 <button data-text="<%= state.strings.waveCall %>"><%= state.strings.waveCall %></button>
86 <button data-text="<%= state.strings.waveThanks %>"><%= state.strings.waveThanks %></button>
87 </div>
88 <button id="wave-cancel" type="button"><%= state.strings.notNow %></button>
89 </dialog>
90
[a5a6249]91 <dialog id="help-dialog">
92 <form method="dialog">
93 <h2 id="help-title"></h2>
94 <label for="help-words"><%= state.strings.helpWords %></label>
95 <textarea id="help-words" rows="3" maxlength="500"></textarea>
96 <menu>
97 <button value="cancel"><%= state.strings.cancel %></button>
98 <button id="help-send" value="send" class="primary"><%= state.strings.helpSend %></button>
99 </menu>
100 </form>
101 </dialog>
102
[303bfc4]103 <!-- De begintoestand reist als JSON mee, zodat de pagina meteen compleet is
104 en niet eerst leeg staat te wachten op een fetch. Geen inline script:
105 CSP staat dat niet toe, dus het gaat als data door een script-tag met
106 een type dat de browser niet uitvoert. -->
107 <script type="application/json" id="ward-state"><%- JSON.stringify(state) %></script>
[084b046]108 <!-- Module, zodat app.js het hemelmodel kan importeren. -->
109 <script type="module" src="/ward/app.js"></script>
[303bfc4]110</body>
111</html>
Note: See TracBrowser for help on using the repository browser.