anentrypoint-design 0.0.156 → 0.0.157
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/app-shell.css +141 -49
- package/colors_and_type.css +16 -7
- package/dist/247420.css +156 -54
- package/dist/247420.js +12 -12
- package/package.json +1 -1
- package/src/components/chat.js +10 -4
- package/src/components/content.js +2 -2
- package/src/components/shell.js +33 -20
- package/src/kits/os/theme.css +13 -13
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "anentrypoint-design",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.157",
|
|
4
4
|
"description": "247420 design system SDK — webjsx + modified ripple-ui, single-file ESM bundle for reproducible use of the AnEntrypoint design.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/247420.js",
|
package/src/components/chat.js
CHANGED
|
@@ -5,6 +5,7 @@
|
|
|
5
5
|
import * as webjsx from '../../vendor/webjsx/index.js';
|
|
6
6
|
import { renderMarkdownCached, highlightCodeBlockCached, initializeCachesEagerly, getCacheStats } from '../markdown-cache.js';
|
|
7
7
|
import { register } from '../debug.js';
|
|
8
|
+
import { Icon } from './shell.js';
|
|
8
9
|
|
|
9
10
|
const h = webjsx.createElement;
|
|
10
11
|
let _stats = { messages: 0, lastKindCounts: {} };
|
|
@@ -171,10 +172,10 @@ export function ChatComposer({ value, onInput, onSend, onAttach, onEmoji, onMenu
|
|
|
171
172
|
if (e.key === ';' && e.ctrlKey) { e.preventDefault(); onEmoji && onEmoji(e); }
|
|
172
173
|
} }),
|
|
173
174
|
h('div', { class: 'chat-composer-toolbar' },
|
|
174
|
-
onAttach ? h('button', { class: 'composer-btn', onclick: (e) => { e.preventDefault(); onAttach(e); }, 'aria-label': 'attach file', title: 'attach file' }, '
|
|
175
|
-
onEmoji ? h('button', { class: 'composer-btn', onclick: (e) => { e.preventDefault(); onEmoji(e); }, 'aria-label': 'emoji picker', title: 'emoji picker (Ctrl+;)' }, '
|
|
176
|
-
onMenu ? h('button', { class: 'composer-btn', onclick: (e) => { e.preventDefault(); onMenu(e); }, 'aria-label': 'composer menu', title: 'more options' }, '
|
|
177
|
-
h('button', { class: 'send', disabled: disabled || !(value && value.trim()), onclick: send, 'aria-label': 'send message', title: 'send message (Enter)' }, '
|
|
175
|
+
onAttach ? h('button', { type: 'button', class: 'composer-btn', onclick: (e) => { e.preventDefault(); onAttach(e); }, 'aria-label': 'attach file', title: 'attach file' }, Icon('paperclip')) : null,
|
|
176
|
+
onEmoji ? h('button', { type: 'button', class: 'composer-btn', onclick: (e) => { e.preventDefault(); onEmoji(e); }, 'aria-label': 'emoji picker', title: 'emoji picker (Ctrl+;)' }, Icon('smile')) : null,
|
|
177
|
+
onMenu ? h('button', { type: 'button', class: 'composer-btn', onclick: (e) => { e.preventDefault(); onMenu(e); }, 'aria-label': 'composer menu', title: 'more options' }, Icon('more-horizontal')) : null,
|
|
178
|
+
h('button', { type: 'button', class: 'send', disabled: disabled || !(value && value.trim()), onclick: send, 'aria-label': 'send message', title: 'send message (Enter)' }, Icon('arrow-up'))
|
|
178
179
|
)
|
|
179
180
|
);
|
|
180
181
|
}
|
|
@@ -223,6 +224,11 @@ export function Chat({ title = 'chat', sub, messages = [], composer, header } =
|
|
|
223
224
|
h('span', { class: 'sub', 'aria-live': 'polite' }, String(messages.length).padStart(2, '0') + ' msgs')
|
|
224
225
|
),
|
|
225
226
|
h('div', { class: 'chat-thread', ref: threadRef, role: 'log', 'aria-label': 'chat messages' },
|
|
227
|
+
messages.length === 0
|
|
228
|
+
? h('div', { key: '_empty', class: 'chat-empty', role: 'status' },
|
|
229
|
+
h('p', { class: 'chat-empty-title' }, 'no messages yet'),
|
|
230
|
+
h('p', { class: 'chat-empty-sub' }, 'start the conversation'))
|
|
231
|
+
: null,
|
|
226
232
|
...messages.map((m, i) => ChatMessage({ ...m, key: m.key != null ? m.key : i }))
|
|
227
233
|
),
|
|
228
234
|
composer || null
|
|
@@ -274,7 +274,7 @@ export function TextField({ label, value = '', type = 'text', placeholder = '',
|
|
|
274
274
|
label != null ? h('span', { key: 'l', class: 'ds-field-label' }, label) : null,
|
|
275
275
|
input,
|
|
276
276
|
maxLength != null ? h('span', { key: 'c', class: 'ds-field-count' }, String(value.length) + '/' + maxLength) : null,
|
|
277
|
-
hint != null ? h('span', { key: 'h', class: '
|
|
277
|
+
hint != null ? h('span', { key: 'h', class: 'ds-field-hint' }, hint) : null
|
|
278
278
|
);
|
|
279
279
|
}
|
|
280
280
|
|
|
@@ -294,7 +294,7 @@ export function Select({ label, value = '', options = [], onChange, name, key, p
|
|
|
294
294
|
return h('label', { key, class: 'ds-field' },
|
|
295
295
|
label != null ? h('span', { key: 'l', class: 'ds-field-label' }, label) : null,
|
|
296
296
|
select,
|
|
297
|
-
hint != null ? h('span', { key: 'h', class: '
|
|
297
|
+
hint != null ? h('span', { key: 'h', class: 'ds-field-hint' }, hint) : null
|
|
298
298
|
);
|
|
299
299
|
}
|
|
300
300
|
|
package/src/components/shell.js
CHANGED
|
@@ -15,31 +15,35 @@ export function Chip({ tone = '', children }) {
|
|
|
15
15
|
return h('span', { class: 'chip' + (tone ? ' tone-' + tone : '') }, children);
|
|
16
16
|
}
|
|
17
17
|
|
|
18
|
-
export function Btn({ href
|
|
18
|
+
export function Btn({ href, variant = 'default', children, onClick, 'aria-label': ariaLabel, primary, ghost, danger, disabled }) {
|
|
19
19
|
// Support legacy primary/ghost props for backward compatibility, but prefer variant
|
|
20
20
|
const resolvedVariant = variant !== 'default' ? variant : (primary ? 'primary' : (ghost ? 'ghost' : (danger ? 'danger' : 'default')));
|
|
21
21
|
const cls = (resolvedVariant === 'primary' ? 'btn-primary' : (resolvedVariant === 'ghost' ? 'btn-ghost' : (resolvedVariant === 'danger' ? 'btn-primary danger' : 'btn')))
|
|
22
22
|
+ (disabled ? ' is-disabled' : '');
|
|
23
|
-
// Anchor with role=button needs explicit Space/Enter activation for keyboard parity with <button>.
|
|
24
|
-
// Browsers fire click on Enter for anchors with href, but Space does nothing — and href="#"
|
|
25
|
-
// synthesizes navigation if onclick doesn't preventDefault.
|
|
26
|
-
const onkeydown = (e) => {
|
|
27
|
-
if (disabled) { e.preventDefault(); return; }
|
|
28
|
-
if (e.key === ' ' || (e.key === 'Enter' && (!href || href === '#'))) {
|
|
29
|
-
e.preventDefault();
|
|
30
|
-
if (onClick) onClick(e);
|
|
31
|
-
}
|
|
32
|
-
};
|
|
33
23
|
const onclick = (e) => {
|
|
34
24
|
if (disabled) { e.preventDefault(); return; }
|
|
35
25
|
if (onClick) onClick(e);
|
|
36
26
|
};
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
27
|
+
const ariaName = ariaLabel || (typeof children === 'string' ? children : undefined);
|
|
28
|
+
|
|
29
|
+
// A real navigational href renders an anchor; everything else is an action
|
|
30
|
+
// button and renders a native <button> (correct semantics + keyboard
|
|
31
|
+
// activation for free, no role=button / href="#" scroll-jump hack).
|
|
32
|
+
const isLink = href != null && href !== '' && href !== '#';
|
|
33
|
+
if (isLink) {
|
|
34
|
+
return h('a', {
|
|
35
|
+
class: cls, href,
|
|
36
|
+
'aria-label': ariaName,
|
|
37
|
+
'aria-disabled': disabled ? 'true' : null,
|
|
38
|
+
tabindex: disabled ? '-1' : null,
|
|
39
|
+
onclick
|
|
40
|
+
}, children);
|
|
41
|
+
}
|
|
42
|
+
return h('button', {
|
|
43
|
+
type: 'button', class: cls,
|
|
44
|
+
disabled: disabled ? true : null,
|
|
45
|
+
'aria-label': ariaName,
|
|
46
|
+
onclick
|
|
43
47
|
}, children);
|
|
44
48
|
}
|
|
45
49
|
|
|
@@ -59,10 +63,14 @@ export function Badge({ children, variant = 'default', tone = 'neutral' }) {
|
|
|
59
63
|
return h('span', { class: 'ds-badge ds-badge-' + variant + ' tone-' + tone }, children);
|
|
60
64
|
}
|
|
61
65
|
|
|
62
|
-
export function Glyph({ children, color, size = 'base' }) {
|
|
66
|
+
export function Glyph({ children, color, size = 'base', label } = {}) {
|
|
63
67
|
const fontSize = size === 'sm' ? '11px' : (size === 'lg' ? '16px' : '13px');
|
|
64
68
|
const style = `font-size:${fontSize}` + (color ? `;color:${color}` : '');
|
|
65
|
-
|
|
69
|
+
// Decorative by default (screen readers skip the glyph char). Pass `label`
|
|
70
|
+
// to expose an accessible name instead.
|
|
71
|
+
return h('span', label
|
|
72
|
+
? { class: 'glyph', style, role: 'img', 'aria-label': label }
|
|
73
|
+
: { class: 'glyph', style, 'aria-hidden': 'true' }, children);
|
|
66
74
|
}
|
|
67
75
|
|
|
68
76
|
// Monochrome inline-SVG icons (stroke=currentColor) so chrome reads as one
|
|
@@ -77,7 +85,12 @@ const ICON_PATHS = {
|
|
|
77
85
|
phone: '<path d="M5 4h3l2 5-2 1a11 11 0 0 0 5 5l1-2 5 2v3a2 2 0 0 1-2 2A16 16 0 0 1 3 6a2 2 0 0 1 2-2z"/>',
|
|
78
86
|
members: '<circle cx="9" cy="8" r="3"/><path d="M3 20a6 6 0 0 1 12 0M16 6a3 3 0 0 1 0 6M21 20a6 6 0 0 0-4-5.7"/>',
|
|
79
87
|
menu: '<path d="M4 6h16M4 12h16M4 18h16"/>',
|
|
80
|
-
settings: '<circle cx="12" cy="12" r="3"/><path d="M12 2v3M12 19v3M4.9 4.9l2.1 2.1M17 17l2.1 2.1M2 12h3M19 12h3M4.9 19.1 7 17M17 7l2.1-2.1"/>'
|
|
88
|
+
settings: '<circle cx="12" cy="12" r="3"/><path d="M12 2v3M12 19v3M4.9 4.9l2.1 2.1M17 17l2.1 2.1M2 12h3M19 12h3M4.9 19.1 7 17M17 7l2.1-2.1"/>',
|
|
89
|
+
paperclip: '<path d="M21 11.5 12.5 20a5 5 0 0 1-7-7l8-8a3.5 3.5 0 0 1 5 5l-8 8a2 2 0 0 1-3-3l7.5-7.5"/>',
|
|
90
|
+
smile: '<circle cx="12" cy="12" r="9"/><path d="M8 14a4 4 0 0 0 8 0"/><path d="M9 9h.01M15 9h.01"/>',
|
|
91
|
+
'more-horizontal': '<circle cx="5" cy="12" r="1"/><circle cx="12" cy="12" r="1"/><circle cx="19" cy="12" r="1"/>',
|
|
92
|
+
'arrow-up': '<path d="M12 19V5M5 12l7-7 7 7"/>',
|
|
93
|
+
send: '<path d="M22 2 11 13M22 2l-7 20-4-9-9-4z"/>'
|
|
81
94
|
};
|
|
82
95
|
export function Icon(name, { size = 16 } = {}) {
|
|
83
96
|
const inner = ICON_PATHS[name];
|
package/src/kits/os/theme.css
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
@import url('https://fonts.googleapis.com/css2?family=
|
|
1
|
+
@import url('https://fonts.googleapis.com/css2?family=Inter:wght@300;400;500;600;700&display=swap');
|
|
2
2
|
|
|
3
3
|
:root {
|
|
4
|
-
--ff-ui: '
|
|
5
|
-
--ff-display: '
|
|
4
|
+
--ff-ui: 'Inter', system-ui, sans-serif;
|
|
5
|
+
--ff-display: 'Inter', system-ui, sans-serif;
|
|
6
6
|
--ff-mono: 'JetBrains Mono', ui-monospace, monospace;
|
|
7
7
|
--os-accent: var(--panel-accent, #3F8A4A);
|
|
8
8
|
--os-accent-2: var(--panel-accent-2, #2B6B36);
|
|
@@ -23,8 +23,8 @@
|
|
|
23
23
|
--os-bar-h-mobile: 52px;
|
|
24
24
|
--os-rail-w: 64px;
|
|
25
25
|
--os-tap: 44px;
|
|
26
|
-
--os-font: var(--ff-ui, '
|
|
27
|
-
--os-display: var(--ff-display, '
|
|
26
|
+
--os-font: var(--ff-ui, 'Inter', system-ui, sans-serif);
|
|
27
|
+
--os-display: var(--ff-display, 'Inter', system-ui, sans-serif);
|
|
28
28
|
--os-mono: var(--ff-mono, 'JetBrains Mono', ui-monospace, monospace);
|
|
29
29
|
}
|
|
30
30
|
|
|
@@ -464,7 +464,7 @@ html, body {
|
|
|
464
464
|
* thebird theme preset (migrated from thebird's local thebird-brand.css
|
|
465
465
|
* 2026-05-26). thebird ships ZERO design CSS — every rule below lives here
|
|
466
466
|
* upstream and is delivered via the published package. Scoped to .ds-247420
|
|
467
|
-
* (thebird's OS root carries that class). Brand identity:
|
|
467
|
+
* (thebird's OS root carries that class). Brand identity: Inter +
|
|
468
468
|
* --paper #F5F0E4 + green accent #247420 + uniform 34px bars +
|
|
469
469
|
* Windows-style right-side window controls.
|
|
470
470
|
* ============================================================ */
|
|
@@ -472,9 +472,9 @@ html, body {
|
|
|
472
472
|
--paper: #F5F0E4;
|
|
473
473
|
}
|
|
474
474
|
.ds-247420 {
|
|
475
|
-
--ff-ui: '
|
|
476
|
-
--ff-display: '
|
|
477
|
-
--ff-prose: '
|
|
475
|
+
--ff-ui: 'Inter', system-ui, sans-serif !important;
|
|
476
|
+
--ff-display: 'Inter', system-ui, sans-serif !important;
|
|
477
|
+
--ff-prose: 'Inter', system-ui, sans-serif !important;
|
|
478
478
|
--os-accent: #247420;
|
|
479
479
|
/* uniform bar height: 22px button + 6px+6px padding = 34px */
|
|
480
480
|
--os-bar-h: 34px !important;
|
|
@@ -538,7 +538,7 @@ html.ds-247420 { touch-action: pan-x pan-y; overscroll-behavior: none; -webkit-t
|
|
|
538
538
|
border: 1px solid var(--os-accent, #247420);
|
|
539
539
|
border-radius: 8px;
|
|
540
540
|
z-index: 9600;
|
|
541
|
-
font-family: var(--ff-ui, '
|
|
541
|
+
font-family: var(--ff-ui, 'Inter', sans-serif);
|
|
542
542
|
color: var(--os-fg, #fff);
|
|
543
543
|
min-width: 280px;
|
|
544
544
|
box-shadow: 0 12px 40px rgba(0,0,0,0.5);
|
|
@@ -555,19 +555,19 @@ html.ds-247420 { touch-action: pan-x pan-y; overscroll-behavior: none; -webkit-t
|
|
|
555
555
|
color: var(--paper, #fff);
|
|
556
556
|
}
|
|
557
557
|
|
|
558
|
-
/* freddie-chat font family (upstream still ships Nunito; brand is
|
|
558
|
+
/* freddie-chat font family (upstream still ships Nunito; brand is Inter). */
|
|
559
559
|
.ds-247420 freddie-chat,
|
|
560
560
|
.ds-247420 freddie-chat .chat-bubble,
|
|
561
561
|
.ds-247420 freddie-chat .chat-meta,
|
|
562
562
|
.ds-247420 freddie-chat .chat-head {
|
|
563
|
-
font-family: var(--ff-ui, '
|
|
563
|
+
font-family: var(--ff-ui, 'Inter', system-ui, sans-serif);
|
|
564
564
|
}
|
|
565
565
|
.ds-247420 freddie-chat .chat-bubble pre,
|
|
566
566
|
.ds-247420 freddie-chat .chat-bubble code {
|
|
567
567
|
font-family: 'JetBrains Mono', ui-monospace, Menlo, Consolas, monospace;
|
|
568
568
|
}
|
|
569
569
|
.ds-247420 freddie-chat .chat-head {
|
|
570
|
-
font-family: var(--ff-display, '
|
|
570
|
+
font-family: var(--ff-display, 'Inter', system-ui, sans-serif);
|
|
571
571
|
font-weight: 700;
|
|
572
572
|
}
|
|
573
573
|
|