@aparte/core 0.15.1 → 0.16.1
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/dist/client/aparte-client.d.ts +53 -51
- package/dist/client/aparte-client.d.ts.map +1 -1
- package/dist/client/lifecycle-events.d.ts +0 -12
- package/dist/client/lifecycle-events.d.ts.map +1 -1
- package/dist/client/stream-adapter.d.ts +2 -12
- package/dist/client/stream-adapter.d.ts.map +1 -1
- package/dist/components/bubble/aparte-chat-bubble.d.ts +45 -1
- package/dist/components/bubble/aparte-chat-bubble.d.ts.map +1 -1
- package/dist/components/chat/aparte-chat.d.ts +1 -1
- package/dist/components/composer/aparte-composer-action.d.ts +1 -1
- package/dist/components/composer/aparte-composer-add-attachment.d.ts +1 -1
- package/dist/components/composer/aparte-composer-attachments.d.ts +1 -2
- package/dist/components/composer/aparte-composer-attachments.d.ts.map +1 -1
- package/dist/components/composer/aparte-composer-cancel.d.ts +1 -1
- package/dist/components/composer/aparte-composer-input.d.ts +1 -1
- package/dist/components/composer/aparte-composer-send.d.ts +12 -12
- package/dist/components/composer/aparte-composer-send.d.ts.map +1 -1
- package/dist/components/composer/aparte-composer.d.ts +29 -12
- package/dist/components/composer/aparte-composer.d.ts.map +1 -1
- package/dist/components/context/aparte-context.d.ts +31 -8
- package/dist/components/context/aparte-context.d.ts.map +1 -1
- package/dist/components/conversation-list/aparte-conversation-list.d.ts +93 -36
- package/dist/components/conversation-list/aparte-conversation-list.d.ts.map +1 -1
- package/dist/components/conversation-list/index.d.ts +1 -1
- package/dist/components/conversation-list/index.d.ts.map +1 -1
- package/dist/components/elicitation/aparte-elicitation.d.ts +20 -2
- package/dist/components/elicitation/aparte-elicitation.d.ts.map +1 -1
- package/dist/components/index.d.ts +7 -1
- package/dist/components/index.d.ts.map +1 -1
- package/dist/components/scroll-rail/aparte-scroll-rail.d.ts +105 -0
- package/dist/components/scroll-rail/aparte-scroll-rail.d.ts.map +1 -0
- package/dist/components/scroll-rail/index.d.ts +3 -0
- package/dist/components/scroll-rail/index.d.ts.map +1 -0
- package/dist/components/sidebar/aparte-sidebar.d.ts +186 -0
- package/dist/components/sidebar/aparte-sidebar.d.ts.map +1 -0
- package/dist/components/sidebar/index.d.ts +3 -0
- package/dist/components/sidebar/index.d.ts.map +1 -0
- package/dist/components/split/aparte-split.d.ts +354 -0
- package/dist/components/split/aparte-split.d.ts.map +1 -0
- package/dist/components/split/geometry.d.ts +65 -0
- package/dist/components/split/geometry.d.ts.map +1 -0
- package/dist/components/split/index.d.ts +3 -0
- package/dist/components/split/index.d.ts.map +1 -0
- package/dist/components/suggestions/aparte-suggestions.d.ts +7 -1
- package/dist/components/suggestions/aparte-suggestions.d.ts.map +1 -1
- package/dist/components/viewport/aparte-chat-viewport.d.ts +52 -2
- package/dist/components/viewport/aparte-chat-viewport.d.ts.map +1 -1
- package/dist/config/aparte-config.d.ts +95 -33
- package/dist/config/aparte-config.d.ts.map +1 -1
- package/dist/config/icon-provider.d.ts +6 -0
- package/dist/config/icon-provider.d.ts.map +1 -1
- package/dist/config/index.d.ts +2 -2
- package/dist/config/index.d.ts.map +1 -1
- package/dist/config/locale.d.ts +140 -27
- package/dist/config/locale.d.ts.map +1 -1
- package/dist/config/sanitize.d.ts +9 -0
- package/dist/config/sanitize.d.ts.map +1 -1
- package/dist/conversations/conversation-controller.d.ts +13 -1
- package/dist/conversations/conversation-controller.d.ts.map +1 -1
- package/dist/conversations/conversation-manager.d.ts +9 -0
- package/dist/conversations/conversation-manager.d.ts.map +1 -1
- package/dist/custom-elements.json +10278 -7784
- package/dist/{is-awaiting-reply-BZ_iJ3s3.js → dialog-triggers-CVCxqKg3.js} +718 -1182
- package/dist/dialog-triggers-CVCxqKg3.js.map +1 -0
- package/dist/elicitation/approval-panel.d.ts +1 -1
- package/dist/elicitation/approval-panel.d.ts.map +1 -1
- package/dist/elicitation/panel.d.ts +24 -16
- package/dist/elicitation/panel.d.ts.map +1 -1
- package/dist/elicitation/types.d.ts +31 -0
- package/dist/elicitation/types.d.ts.map +1 -1
- package/dist/generated/element-attributes.d.ts +47 -1
- package/dist/generated/element-attributes.d.ts.map +1 -1
- package/dist/{glyphs-B3BZ2TIb.js → glyphs-DQTeOj4w.js} +22 -13
- package/dist/{glyphs-B3BZ2TIb.js.map → glyphs-DQTeOj4w.js.map} +1 -1
- package/dist/host/aparte-chat-host.d.ts +10 -2
- package/dist/host/aparte-chat-host.d.ts.map +1 -1
- package/dist/icons/extended.d.ts +4 -2
- package/dist/icons/extended.d.ts.map +1 -1
- package/dist/icons/glyphs.d.ts +9 -0
- package/dist/icons/glyphs.d.ts.map +1 -1
- package/dist/icons.js +16 -15
- package/dist/icons.js.map +1 -1
- package/dist/index.css +1284 -397
- package/dist/index.d.ts +26 -15
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2099 -296
- package/dist/index.js.map +1 -1
- package/dist/index.node.d.ts +21 -5
- package/dist/index.node.d.ts.map +1 -1
- package/dist/index.node.js +39 -34
- package/dist/index.node.js.map +1 -1
- package/dist/interop/dialog-triggers.d.ts +27 -0
- package/dist/interop/dialog-triggers.d.ts.map +1 -0
- package/dist/interop/element-props.d.ts +16 -8
- package/dist/interop/element-props.d.ts.map +1 -1
- package/dist/parsers/aparte-stream-parser.d.ts +52 -22
- package/dist/parsers/aparte-stream-parser.d.ts.map +1 -1
- package/dist/parsers/index.d.ts +1 -1
- package/dist/parsers/index.d.ts.map +1 -1
- package/dist/primitives/select/aparte-select.d.ts.map +1 -1
- package/dist/renderers/segment-renderers.d.ts.map +1 -1
- package/dist/renderers/segments/code.d.ts.map +1 -1
- package/dist/renderers/segments/tool-call.d.ts.map +1 -1
- package/dist/runtime/message-repository.d.ts.map +1 -1
- package/dist/transport/backend-handler.d.ts.map +1 -1
- package/dist/transport/backend-transport.d.ts +6 -1
- package/dist/transport/backend-transport.d.ts.map +1 -1
- package/dist/types/chat.d.ts +8 -14
- package/dist/types/chat.d.ts.map +1 -1
- package/dist/types/element-map.d.ts +54 -4
- package/dist/types/element-map.d.ts.map +1 -1
- package/dist/types/event-map.d.ts +16 -10
- package/dist/types/event-map.d.ts.map +1 -1
- package/dist/types/events.d.ts +59 -117
- package/dist/types/events.d.ts.map +1 -1
- package/dist/types/imperative-api.d.ts +3 -1
- package/dist/types/imperative-api.d.ts.map +1 -1
- package/dist/types/index.d.ts +5 -4
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/models.d.ts +11 -31
- package/dist/types/models.d.ts.map +1 -1
- package/dist/types/segments.d.ts +11 -47
- package/dist/types/segments.d.ts.map +1 -1
- package/dist/types/stream-blocks.d.ts +57 -0
- package/dist/types/stream-blocks.d.ts.map +1 -0
- package/dist/types/tools.d.ts +57 -0
- package/dist/types/tools.d.ts.map +1 -1
- package/dist/utils/copy-text.d.ts +24 -0
- package/dist/utils/copy-text.d.ts.map +1 -0
- package/dist/utils/css-escape.d.ts +5 -0
- package/dist/utils/css-escape.d.ts.map +1 -1
- package/dist/utils/tool-input.d.ts +20 -0
- package/dist/utils/tool-input.d.ts.map +1 -0
- package/package.json +10 -3
- package/dist/is-awaiting-reply-BZ_iJ3s3.js.map +0 -1
- package/dist/renderers/segments/artifact/binary-file.d.ts +0 -45
- package/dist/renderers/segments/artifact/binary-file.d.ts.map +0 -1
- package/dist/renderers/segments/artifact/card.d.ts +0 -3
- package/dist/renderers/segments/artifact/card.d.ts.map +0 -1
- package/dist/renderers/segments/artifact/preview-document.d.ts +0 -27
- package/dist/renderers/segments/artifact/preview-document.d.ts.map +0 -1
- package/dist/renderers/segments/artifact/shared.d.ts +0 -29
- package/dist/renderers/segments/artifact/shared.d.ts.map +0 -1
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
/** Detail of `aparte-sidebar-toggle`: the state just entered. */
|
|
2
|
+
export interface AparteSidebarToggleDetail {
|
|
3
|
+
collapsed: boolean;
|
|
4
|
+
/** True while the sidebar is a drawer — the window is under the breakpoint. */
|
|
5
|
+
drawer: boolean;
|
|
6
|
+
}
|
|
7
|
+
/**
|
|
8
|
+
* The column beside the chat — conversations, a new-chat button, a search field, an
|
|
9
|
+
* account row — as an element, because it has behaviour: it collapses, it becomes a
|
|
10
|
+
* drawer on a narrow window, and its search field filters the conversation list.
|
|
11
|
+
*
|
|
12
|
+
* What it does NOT own is its content. Children are yours, in the order you want them:
|
|
13
|
+
* a `.aparte-sidebar__header`, a `.aparte-sidebar__search`, a `.aparte-sidebar__body`
|
|
14
|
+
* holding the `<aparte-conversation-list>`, a `.aparte-sidebar__footer`. The
|
|
15
|
+
* stylesheet lays those out and draws nothing you did not put there — the recipe
|
|
16
|
+
* (`.aparte-sidebar`, in `styles/shell/sidebar.css`) is the look, this element is
|
|
17
|
+
* the three behaviours.
|
|
18
|
+
*
|
|
19
|
+
* **Collapse.** `collapsed` is an attribute, reflected, so the host can set it, read
|
|
20
|
+
* it and persist it. Any element carrying `data-aparte-sidebar-toggle` anywhere on
|
|
21
|
+
* the page toggles the nearest sidebar (or the one whose id the attribute names), so
|
|
22
|
+
* a hamburger in the header needs no script. `aparte-sidebar-toggle` fires on every
|
|
23
|
+
* change, whoever caused it.
|
|
24
|
+
*
|
|
25
|
+
* **Drawer.** Under 48rem of window the sidebar leaves the flow and slides over the
|
|
26
|
+
* page (`data-drawer`, set by the element from a media query); open, it draws a
|
|
27
|
+
* scrim, moves the focus to its first focusable child, closes on Escape from anywhere
|
|
28
|
+
* on the page or on a click outside, and hands the focus back to the control that
|
|
29
|
+
* opened it. Nothing here is a portal: the drawer is the same element in the same
|
|
30
|
+
* place, positioned fixed, which is all a sidebar needs and what a dialog would not
|
|
31
|
+
* get away with. Collapsed — folded as a column or slid off as a drawer — it carries
|
|
32
|
+
* `inert` and `aria-hidden`, so nothing invisible keeps a tab stop.
|
|
33
|
+
*
|
|
34
|
+
* **Search.** An input carrying `data-aparte-sidebar-search` filters the conversation
|
|
35
|
+
* list below it by title as the user types — rows that do not match are hidden, and a
|
|
36
|
+
* date group with nothing left hides with them. Client-side, on the titles the list
|
|
37
|
+
* already has: an index over message bodies is the storage adapter's business.
|
|
38
|
+
*
|
|
39
|
+
* @element aparte-sidebar
|
|
40
|
+
*
|
|
41
|
+
* @attr {boolean} collapsed - Hidden (in the flow) or closed (as a drawer). Reflected; set it to start closed.
|
|
42
|
+
* @attr {string} breakpoint - The window width under which the sidebar becomes a drawer: a length (default `48rem`), or `none` for a column that never does.
|
|
43
|
+
* @attr {boolean} data-drawer - Reflected BY the element while the window is under 48rem. Read-only.
|
|
44
|
+
*
|
|
45
|
+
* @fires {CustomEvent<AparteSidebarToggleDetail>} aparte-sidebar-toggle - The sidebar opened or closed, by a toggle, by Escape, by a click on the scrim or by `collapsed` being set. Bubbles.
|
|
46
|
+
*
|
|
47
|
+
* @cssprop [--aparte-sidebar-width=260px] - Width of the column, and of the drawer.
|
|
48
|
+
* @cssprop [--aparte-sidebar-bg=var(--aparte-surface-2)] - Its ground.
|
|
49
|
+
*
|
|
50
|
+
* @example
|
|
51
|
+
* <!-- The sidebar alone, as a column: its header, a search field that filters the list,
|
|
52
|
+
* the list, a footer. The shell it sits in — header, chat — is the app-shell guide's.
|
|
53
|
+
* breakpoint="none" keeps it a column at any width; without it, under 48rem of
|
|
54
|
+
* window it becomes a drawer behind a [data-aparte-sidebar-toggle] control. -->
|
|
55
|
+
* <aparte-sidebar breakpoint="none" style="height: 22rem">
|
|
56
|
+
* <div class="aparte-sidebar__header">
|
|
57
|
+
* <span class="aparte-sidebar__brand">aparté</span>
|
|
58
|
+
* <button class="aparte-btn aparte-btn--icon aparte-btn--sm" type="button" aria-label="New chat">
|
|
59
|
+
* <aparte-icon name="edit"></aparte-icon>
|
|
60
|
+
* </button>
|
|
61
|
+
* </div>
|
|
62
|
+
* <div class="aparte-sidebar__search aparte-field-group">
|
|
63
|
+
* <input class="aparte-field aparte-field--sm" type="search" placeholder="Search conversations" data-aparte-sidebar-search>
|
|
64
|
+
* </div>
|
|
65
|
+
* <div class="aparte-sidebar__body">
|
|
66
|
+
* <aparte-conversation-list active-id="c1"></aparte-conversation-list>
|
|
67
|
+
* </div>
|
|
68
|
+
* <div class="aparte-sidebar__footer">
|
|
69
|
+
* <span class="aparte-avatar aparte-avatar--sm">P</span> Paul
|
|
70
|
+
* </div>
|
|
71
|
+
* </aparte-sidebar>
|
|
72
|
+
* <script>
|
|
73
|
+
* const day = 864e5;
|
|
74
|
+
* document.querySelector('aparte-conversation-list').conversations = [
|
|
75
|
+
* { id: 'c1', title: 'Deploy checklist', updatedAt: Date.now() },
|
|
76
|
+
* { id: 'c2', title: 'Rename the segment types', updatedAt: Date.now() - day },
|
|
77
|
+
* { id: 'c3', title: 'Tokens, not selectors', updatedAt: Date.now() - 4 * day },
|
|
78
|
+
* { id: 'c4', title: 'The first release', updatedAt: Date.now() - 60 * day },
|
|
79
|
+
* ];
|
|
80
|
+
* </script>
|
|
81
|
+
*/
|
|
82
|
+
export declare class AparteSidebar extends HTMLElement {
|
|
83
|
+
static get observedAttributes(): string[];
|
|
84
|
+
private _media;
|
|
85
|
+
private _scrim;
|
|
86
|
+
/** The control that last opened the drawer, to hand the focus back to. */
|
|
87
|
+
private _opener;
|
|
88
|
+
private _lastCollapsed;
|
|
89
|
+
/**
|
|
90
|
+
* `connectedCallback` has run and the element knows what its markup asked for.
|
|
91
|
+
*
|
|
92
|
+
* Not `isConnected`: during an UPGRADE the element is already in the document, so
|
|
93
|
+
* `attributeChangedCallback` fires for every authored attribute — connected, and
|
|
94
|
+
* before `connectedCallback` — which is the ordinary case for a server-rendered
|
|
95
|
+
* `<aparte-sidebar collapsed>` upgraded when the module loads. Announcing there
|
|
96
|
+
* tells the host its sidebar just closed when all that happened is that the markup
|
|
97
|
+
* was read, and says `drawer: false` because the media query has not run yet.
|
|
98
|
+
*/
|
|
99
|
+
private _ready;
|
|
100
|
+
/**
|
|
101
|
+
* The host (or the markup) asked for the column to be folded, so widening the
|
|
102
|
+
* window must not unfold it. Only a collapse taken OUTSIDE the drawer state counts:
|
|
103
|
+
* dismissing an overlay says nothing about what a wide window should show.
|
|
104
|
+
*/
|
|
105
|
+
private _closedByHost;
|
|
106
|
+
/**
|
|
107
|
+
* `_closedByHost` has been taken from the markup once. A re-parent runs
|
|
108
|
+
* `connectedCallback` again, and by then `collapsed` may be the BREAKPOINT's own
|
|
109
|
+
* write — a drawer closes itself on the way in — so reading it back a second time
|
|
110
|
+
* records the element's own doing as the host's word and the column never reopens.
|
|
111
|
+
* Like `_initialCaptured` on `<aparte-split>`, it must survive the move.
|
|
112
|
+
*/
|
|
113
|
+
private _hostIntentSeeded;
|
|
114
|
+
/** Raised around `_applyDrawer`'s own writes, so the breakpoint is never read as a host's intent. */
|
|
115
|
+
private _auto;
|
|
116
|
+
/**
|
|
117
|
+
* The element wrote `inert`/`aria-hidden` and may take them back. A host that inerts
|
|
118
|
+
* the sidebar behind its own modal wrote them itself, and `_syncHidden` runs on every
|
|
119
|
+
* breakpoint re-evaluation: without this it would un-inert the page behind the overlay.
|
|
120
|
+
* Same convention as `_relabel`, which leaves a host-authored `aria-label` alone.
|
|
121
|
+
*/
|
|
122
|
+
private _ownHidden;
|
|
123
|
+
/** Whether the sidebar is collapsed (hidden in the flow, or closed as a drawer). */
|
|
124
|
+
get collapsed(): boolean;
|
|
125
|
+
set collapsed(value: boolean);
|
|
126
|
+
/** True while the window is under the breakpoint and the sidebar is a drawer. */
|
|
127
|
+
get drawer(): boolean;
|
|
128
|
+
connectedCallback(): void;
|
|
129
|
+
/**
|
|
130
|
+
* The drawer's media query, from the `breakpoint` attribute: a length (`48rem`, the
|
|
131
|
+
* default, or `640px`), or `none` for a column that never becomes a drawer — which
|
|
132
|
+
* a narrow host that has room for it wants, and a documentation frame needs.
|
|
133
|
+
*/
|
|
134
|
+
private _watchBreakpoint;
|
|
135
|
+
disconnectedCallback(): void;
|
|
136
|
+
attributeChangedCallback(name: string): void;
|
|
137
|
+
/** Open the sidebar. `opener` is the control to hand the focus back to when it closes. */
|
|
138
|
+
open(opener?: HTMLElement): void;
|
|
139
|
+
close(): void;
|
|
140
|
+
toggle(opener?: HTMLElement): void;
|
|
141
|
+
private _onMediaChange;
|
|
142
|
+
/**
|
|
143
|
+
* Entering the drawer state closes the sidebar: a narrow window that opens on an
|
|
144
|
+
* overlay covering the chat is the wrong first screen. Leaving it reopens, since
|
|
145
|
+
* a wide window has room for the column — unless the host had collapsed it before.
|
|
146
|
+
*/
|
|
147
|
+
private _applyDrawer;
|
|
148
|
+
/**
|
|
149
|
+
* A collapsed sidebar is invisible — folded to nothing in the flow, slid off the
|
|
150
|
+
* screen as a drawer — so it must not keep its tab stops or its place in the
|
|
151
|
+
* accessibility tree. `inert` covers focus and the pointer, `aria-hidden` covers
|
|
152
|
+
* the readers that predate it; a browser without `inert` still gets the second.
|
|
153
|
+
*
|
|
154
|
+
* It removes only what it wrote. Both are standard global attributes a host sets
|
|
155
|
+
* itself — inerting the sidebar behind its own modal is the ordinary pattern — and
|
|
156
|
+
* this runs on every breakpoint re-evaluation, so clearing them unconditionally lets
|
|
157
|
+
* an unrelated resize re-expose the page under an overlay. Same convention as
|
|
158
|
+
* `_relabel`, which leaves a host-authored `aria-label` alone.
|
|
159
|
+
*
|
|
160
|
+
* Neither is declared `@attr`, and `data-drawer` is not the precedent: a `@attr` on a
|
|
161
|
+
* STANDARD name displaces the wrappers' own prop for it — React's JSX props are
|
|
162
|
+
* `Omit<HTMLAttributes, keyof T>`, so declaring `inert` here would retype
|
|
163
|
+
* `<aparte-sidebar inert={busy}>` out of existence. The class docblock says it in prose.
|
|
164
|
+
*/
|
|
165
|
+
private _syncHidden;
|
|
166
|
+
/**
|
|
167
|
+
* The drawer covers the page, so the focus has to follow it in — otherwise the next
|
|
168
|
+
* Tab walks the transcript under the overlay. The host owns the children, so this
|
|
169
|
+
* takes the first thing that can hold focus and leaves the rest alone; a drawer with
|
|
170
|
+
* nothing focusable in it keeps the focus where it was, which is the honest outcome.
|
|
171
|
+
*/
|
|
172
|
+
private _focusFirst;
|
|
173
|
+
private _syncScrim;
|
|
174
|
+
private _onKeydown;
|
|
175
|
+
/** A `[data-aparte-sidebar-toggle]` anywhere toggles this sidebar — no script in the host. */
|
|
176
|
+
private _onDocumentClick;
|
|
177
|
+
private _onInput;
|
|
178
|
+
/**
|
|
179
|
+
* Hide the conversation rows whose title does not contain `query`, and the date
|
|
180
|
+
* groups left empty. Case- and accent-insensitive. An empty query shows everything.
|
|
181
|
+
*/
|
|
182
|
+
filter(query: string): void;
|
|
183
|
+
private _onConfigChange;
|
|
184
|
+
private _relabel;
|
|
185
|
+
}
|
|
186
|
+
//# sourceMappingURL=aparte-sidebar.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"aparte-sidebar.d.ts","sourceRoot":"","sources":["../../../src/components/sidebar/aparte-sidebar.ts"],"names":[],"mappings":"AAEA,iEAAiE;AACjE,MAAM,WAAW,yBAAyB;IACtC,SAAS,EAAE,OAAO,CAAC;IACnB,+EAA+E;IAC/E,MAAM,EAAE,OAAO,CAAC;CACnB;AAKD;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA0EG;AACH,qBAAa,aAAc,SAAQ,WAAW;IAC1C,MAAM,KAAK,kBAAkB,IAAI,MAAM,EAAE,CAExC;IAED,OAAO,CAAC,MAAM,CAA+B;IAC7C,OAAO,CAAC,MAAM,CAA4B;IAC1C,0EAA0E;IAC1E,OAAO,CAAC,OAAO,CAA4B;IAC3C,OAAO,CAAC,cAAc,CAAwB;IAE9C;;;;;;;;;OASG;IACH,OAAO,CAAC,MAAM,CAAS;IAEvB;;;;OAIG;IACH,OAAO,CAAC,aAAa,CAAS;IAE9B;;;;;;OAMG;IACH,OAAO,CAAC,iBAAiB,CAAS;IAElC,qGAAqG;IACrG,OAAO,CAAC,KAAK,CAAS;IAEtB;;;;;OAKG;IACH,OAAO,CAAC,UAAU,CAAS;IAE3B,oFAAoF;IACpF,IAAI,SAAS,IAAI,OAAO,CAEvB;IAED,IAAI,SAAS,CAAC,KAAK,EAAE,OAAO,EAE3B;IAED,iFAAiF;IACjF,IAAI,MAAM,IAAI,OAAO,CAEpB;IAED,iBAAiB,IAAI,IAAI;IAyBzB;;;;OAIG;IACH,OAAO,CAAC,gBAAgB;IAexB,oBAAoB,IAAI,IAAI;IAU5B,wBAAwB,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI;IA8B5C,0FAA0F;IAC1F,IAAI,CAAC,MAAM,CAAC,EAAE,WAAW,GAAG,IAAI;IAKhC,KAAK,IAAI,IAAI;IAIb,MAAM,CAAC,MAAM,CAAC,EAAE,WAAW,GAAG,IAAI;IAOlC,OAAO,CAAC,cAAc,CAAkE;IAExF;;;;OAIG;IACH,OAAO,CAAC,YAAY;IAcpB;;;;;;;;;;;;;;;;OAgBG;IACH,OAAO,CAAC,WAAW;IAYnB;;;;;OAKG;IACH,OAAO,CAAC,WAAW;IAInB,OAAO,CAAC,UAAU;IAclB,OAAO,CAAC,UAAU,CAKhB;IAEF,8FAA8F;IAC9F,OAAO,CAAC,gBAAgB,CAUtB;IAIF,OAAO,CAAC,QAAQ,CAId;IAEF;;;OAGG;IACH,MAAM,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAe3B,OAAO,CAAC,eAAe,CAA+B;IAEtD,OAAO,CAAC,QAAQ;CAMnB"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/sidebar/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,qBAAqB,CAAC;AACpD,YAAY,EAAE,yBAAyB,EAAE,MAAM,qBAAqB,CAAC"}
|
|
@@ -0,0 +1,354 @@
|
|
|
1
|
+
/** Detail of `aparte-split-resize`: the position that settled, and what settled it. */
|
|
2
|
+
export interface AparteSplitResizeDetail {
|
|
3
|
+
/** The achieved size of the primary pane, as a percentage of the container. */
|
|
4
|
+
position: number;
|
|
5
|
+
/** The primary pane is folded to its minimum. */
|
|
6
|
+
collapsed: boolean;
|
|
7
|
+
/** The split is under its breakpoint and showing one pane. */
|
|
8
|
+
stacked: boolean;
|
|
9
|
+
/** Which pane is shown while stacked. */
|
|
10
|
+
pane: 'start' | 'end';
|
|
11
|
+
/** The container's axis, as the `orientation` attribute names it. */
|
|
12
|
+
orientation: 'horizontal' | 'vertical';
|
|
13
|
+
/** What moved it: a drag, a key, or the host setting the property. */
|
|
14
|
+
source: 'pointer' | 'keyboard' | 'api';
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Two panes and a draggable seam — a chat beside a preview, an editor, an artifact card.
|
|
18
|
+
*
|
|
19
|
+
* The grid is the mechanism: `--aparte-split-position` is the primary pane's size and
|
|
20
|
+
* the min/max are CSS clamp bounds, so the browser clamps and nothing here parses a
|
|
21
|
+
* unit. The element adds only what CSS cannot do — the drag, the arrow keys, the ARIA
|
|
22
|
+
* of an APG window splitter, and one pane at a time under a breakpoint. Without the
|
|
23
|
+
* element the `.aparte-split` recipe is still a split; it just does not move.
|
|
24
|
+
*
|
|
25
|
+
* It stores nothing: `position` in, one `aparte-split-resize` out on commit. The
|
|
26
|
+
* attribute is written on COMMIT only — a release, a key up, a double-click, a property
|
|
27
|
+
* set — and the live value during a drag travels on the custom property, so a
|
|
28
|
+
* framework's reconciler is not in the drag loop. Persist from the event; restore by
|
|
29
|
+
* setting `position`.
|
|
30
|
+
*
|
|
31
|
+
* A pane CONTAINS a chat; a chat never contains a split.
|
|
32
|
+
*
|
|
33
|
+
* `aria-orientation` on the handle is the INVERSE of this element's `orientation`: the
|
|
34
|
+
* attribute names the SEPARATOR's own axis, which is what the APG means by "Left Arrow
|
|
35
|
+
* moves a vertical splitter" and what ARIA 1.2 means by the attribute. Do not "fix" it —
|
|
36
|
+
* consumers style against it.
|
|
37
|
+
*
|
|
38
|
+
* Shift + an arrow is ±10%. That is an ecosystem convention, not the APG, which
|
|
39
|
+
* specifies the single step alone.
|
|
40
|
+
*
|
|
41
|
+
* @element aparte-split
|
|
42
|
+
*
|
|
43
|
+
* @attr {number} position - The primary pane's size, as a percentage of the container. Reflected on commit, never per drag frame.
|
|
44
|
+
* @attr {string} orientation - `horizontal` (panes side by side, the default) or `vertical` (stacked). Names the CONTAINER's axis.
|
|
45
|
+
* @attr {string} primary - `start` (default) or `end`: which pane `position` sizes.
|
|
46
|
+
* @attr {boolean} collapsed - The primary pane folded to its minimum. Enter on the seam toggles it; a second Enter restores the size it had.
|
|
47
|
+
* @attr {string} breakpoint - Below this width the split shows one pane at a time. A length (default `48rem`), or `none` to never stack.
|
|
48
|
+
* @attr {string} pane - `start` (default) or `end`: which pane is shown while stacked.
|
|
49
|
+
* @attr {boolean} disabled - No drag, no keys, no tab stop; the seam stays drawn.
|
|
50
|
+
* @attr {string} label - The seam's accessible name. Defaults to the locale's `splitHandleLabel`.
|
|
51
|
+
* @attr {boolean} data-stacked - Written BY the element while one pane is shown. Read-only; style against it.
|
|
52
|
+
*
|
|
53
|
+
* @fires {CustomEvent<AparteSplitResizeDetail>} aparte-split-resize - The position settled: after a drag, a key, a double-click or a property set. Never during a drag — persist from here.
|
|
54
|
+
*
|
|
55
|
+
* @cssprop [--aparte-split-position=38%] - The primary pane's size.
|
|
56
|
+
* @cssprop [--aparte-split-min=20rem] - Floor of the primary pane. Any length or percentage.
|
|
57
|
+
* @cssprop [--aparte-split-max=60%] - Ceiling of the primary pane.
|
|
58
|
+
* @cssprop [--aparte-split-handle-size=4px] - The visible seam.
|
|
59
|
+
* @cssprop [--aparte-split-hit-area=12px] - The invisible grab zone around it. Grows to the touch target on a coarse pointer.
|
|
60
|
+
*
|
|
61
|
+
* @example
|
|
62
|
+
* <!-- The chat in one pane, your own in the other. Drag the seam, or tab to it and use
|
|
63
|
+
* the arrows; double-click resets it. `--aparte-split-min` is a CSS length, so the
|
|
64
|
+
* chat cannot be dragged narrower than 16rem whatever the percentage says. Under
|
|
65
|
+
* 48rem of window the split shows one pane, and the buttons switch it. -->
|
|
66
|
+
* <div class="aparte-app-header">
|
|
67
|
+
* <button class="aparte-btn aparte-btn--sm aparte-btn--surface" type="button" data-aparte-split-pane="start">Chat</button>
|
|
68
|
+
* <button class="aparte-btn aparte-btn--sm aparte-btn--surface" type="button" data-aparte-split-pane="end">Preview</button>
|
|
69
|
+
* </div>
|
|
70
|
+
* <aparte-split position="38" style="height: 22rem; --aparte-split-min: 16rem">
|
|
71
|
+
* <aparte-chat>
|
|
72
|
+
* <aparte-chat-viewport></aparte-chat-viewport>
|
|
73
|
+
* <aparte-composer>
|
|
74
|
+
* <div class="aparte-composer-shell">
|
|
75
|
+
* <div class="aparte-composer-row">
|
|
76
|
+
* <aparte-composer-input></aparte-composer-input>
|
|
77
|
+
* <aparte-composer-send></aparte-composer-send>
|
|
78
|
+
* </div>
|
|
79
|
+
* </div>
|
|
80
|
+
* </aparte-composer>
|
|
81
|
+
* </aparte-chat>
|
|
82
|
+
* <section class="aparte-split__pane">
|
|
83
|
+
* <iframe title="Preview" style="inline-size: 100%; block-size: 100%; border: 0" srcdoc="<h1>Your pane</h1>"></iframe>
|
|
84
|
+
* </section>
|
|
85
|
+
* </aparte-split>
|
|
86
|
+
* <script>
|
|
87
|
+
* document.querySelector('aparte-split').addEventListener('aparte-split-resize', (e) => {
|
|
88
|
+
* localStorage.setItem('split', String(e.detail.position));
|
|
89
|
+
* });
|
|
90
|
+
* </script>
|
|
91
|
+
*/
|
|
92
|
+
export declare class AparteSplit extends HTMLElement {
|
|
93
|
+
static get observedAttributes(): string[];
|
|
94
|
+
private _handle;
|
|
95
|
+
private _scrim;
|
|
96
|
+
private _media;
|
|
97
|
+
private _observer;
|
|
98
|
+
/** The pending `_measureBounds()` from a resize, batched to one per frame. */
|
|
99
|
+
private _measureRafId;
|
|
100
|
+
/** The host size the last resize tick measured, so an unchanged one does nothing. */
|
|
101
|
+
private _observedPx;
|
|
102
|
+
/** Ids for the panes `aria-controls` names — a counter, the way the primitives do it. */
|
|
103
|
+
private static _paneIdSeq;
|
|
104
|
+
/** The live position. The attribute holds it only after a commit. */
|
|
105
|
+
private _position;
|
|
106
|
+
/** What `reset()` — and a double-click on the seam — goes back to. */
|
|
107
|
+
private _initialPosition;
|
|
108
|
+
/**
|
|
109
|
+
* `_initialPosition` has been taken from the markup once. A re-parent runs
|
|
110
|
+
* `connectedCallback` again, and by then the attribute holds the LAST COMMIT, not
|
|
111
|
+
* what the author wrote: capturing a second time makes a framework re-render, a tab
|
|
112
|
+
* switch or a drag-and-drop of the panel redefine what "reset" means.
|
|
113
|
+
*/
|
|
114
|
+
private _initialCaptured;
|
|
115
|
+
/** The size the primary pane had before it was collapsed, for the second Enter. */
|
|
116
|
+
private _preCollapsePosition;
|
|
117
|
+
/** Committed values, so a reflection of our own does not read as a host's change. */
|
|
118
|
+
private _lastPosition;
|
|
119
|
+
private _lastCollapsed;
|
|
120
|
+
private _lastPane;
|
|
121
|
+
/** What an attribute-driven commit blames. Raised around a key that changes state. */
|
|
122
|
+
private _source;
|
|
123
|
+
/**
|
|
124
|
+
* `connectedCallback` has run and the element knows what its markup asked for.
|
|
125
|
+
*
|
|
126
|
+
* Not `isConnected`: during an UPGRADE the element is already in the document, so
|
|
127
|
+
* `attributeChangedCallback` fires for every authored attribute — connected, and
|
|
128
|
+
* before `connectedCallback` — which is the ordinary case for a server-rendered
|
|
129
|
+
* `<aparte-split position="38">` upgraded when the module loads. Committing there
|
|
130
|
+
* measures a layout the element has not set up yet (no `data-stacked`, so on a
|
|
131
|
+
* phone the probe reads the stacked pane and writes `position="84"`), reflects that
|
|
132
|
+
* over the authored number, and sends it to whatever the host persists.
|
|
133
|
+
*/
|
|
134
|
+
private _ready;
|
|
135
|
+
private _dragging;
|
|
136
|
+
private _captured;
|
|
137
|
+
/** The gesture actually moved the seam. A press that did not commits nothing. */
|
|
138
|
+
private _moved;
|
|
139
|
+
private _pointerId;
|
|
140
|
+
private _dragStartPercent;
|
|
141
|
+
private _dragOriginPx;
|
|
142
|
+
private _dragContainerPx;
|
|
143
|
+
/** A key is down and has moved the seam; its keyup is the commit. */
|
|
144
|
+
private _keying;
|
|
145
|
+
/** The primary pane's size, as a percentage of the container. Setting it commits. */
|
|
146
|
+
get position(): number;
|
|
147
|
+
set position(value: number);
|
|
148
|
+
/** The container's axis: `horizontal` (side by side) or `vertical` (stacked). */
|
|
149
|
+
get orientation(): 'horizontal' | 'vertical';
|
|
150
|
+
set orientation(value: 'horizontal' | 'vertical');
|
|
151
|
+
/** Which pane `position` sizes. */
|
|
152
|
+
get primary(): 'start' | 'end';
|
|
153
|
+
set primary(value: 'start' | 'end');
|
|
154
|
+
/** The primary pane is folded to its minimum. */
|
|
155
|
+
get collapsed(): boolean;
|
|
156
|
+
set collapsed(value: boolean);
|
|
157
|
+
/** Which pane is shown while the split is stacked. */
|
|
158
|
+
get pane(): 'start' | 'end';
|
|
159
|
+
set pane(value: 'start' | 'end');
|
|
160
|
+
/** No drag, no keys, no tab stop. The seam stays drawn. */
|
|
161
|
+
get disabled(): boolean;
|
|
162
|
+
set disabled(value: boolean);
|
|
163
|
+
/**
|
|
164
|
+
* True while the split is showing one pane. Read-only.
|
|
165
|
+
*
|
|
166
|
+
* Both routes into that state count. `data-stacked` is the one this element writes
|
|
167
|
+
* from its own breakpoint; `.aparte-split--only-start` / `--only-end` are the CSS
|
|
168
|
+
* route a host takes when it owns its breakpoints and sets `breakpoint="none"`. The
|
|
169
|
+
* sheet gives the two byte-identical rules, so the element has to read them the same
|
|
170
|
+
* way — every guard downstream keys on this getter, and a split stacked by the class
|
|
171
|
+
* alone would measure a one-track grid and commit `position="100"`.
|
|
172
|
+
*/
|
|
173
|
+
get stacked(): boolean;
|
|
174
|
+
/** Fold the primary pane to its minimum, remembering the size it had. */
|
|
175
|
+
collapse(): void;
|
|
176
|
+
/** Unfold it, back to the size it had before it collapsed. */
|
|
177
|
+
expand(): void;
|
|
178
|
+
toggleCollapse(): void;
|
|
179
|
+
/** Show one pane, which only has a visible effect while the split is stacked. */
|
|
180
|
+
showPane(which: 'start' | 'end'): void;
|
|
181
|
+
/**
|
|
182
|
+
* Back to the position the split was FIRST connected with — a re-parent restores
|
|
183
|
+
* that, it does not redefine it. What a double-click on the seam does.
|
|
184
|
+
*/
|
|
185
|
+
reset(): void;
|
|
186
|
+
connectedCallback(): void;
|
|
187
|
+
disconnectedCallback(): void;
|
|
188
|
+
attributeChangedCallback(name: string): void;
|
|
189
|
+
/**
|
|
190
|
+
* The seam. An author-written `.aparte-split__handle` is ADOPTED — a second one
|
|
191
|
+
* would be a second tab stop drawn over the first — otherwise one is inserted
|
|
192
|
+
* between the first two children, which is where a two-pane grid needs it.
|
|
193
|
+
*
|
|
194
|
+
* An adopted one is MOVED there if the author put it elsewhere. The sheet is
|
|
195
|
+
* positional — three tracks with the seam in the middle, and the stacked rules hide
|
|
196
|
+
* `:nth-child(1)` / `:nth-child(3)` — so a handle written first would take the
|
|
197
|
+
* primary pane's track and make stacking hide the wrong child.
|
|
198
|
+
*/
|
|
199
|
+
private _ensureHandle;
|
|
200
|
+
/** The panes: every element child that is not the seam. */
|
|
201
|
+
private _panes;
|
|
202
|
+
private _primaryPane;
|
|
203
|
+
/**
|
|
204
|
+
* The APG's window splitter, plus the two states that take it out of the tab order.
|
|
205
|
+
*
|
|
206
|
+
* `aria-orientation` is the INVERSE of `orientation`: the attribute names the
|
|
207
|
+
* separator's own axis, so a split whose panes sit side by side has a VERTICAL
|
|
208
|
+
* separator between them.
|
|
209
|
+
*/
|
|
210
|
+
private _stampHandle;
|
|
211
|
+
private _measure;
|
|
212
|
+
/**
|
|
213
|
+
* What the pane ACTUALLY got, which is not what was asked for: the CSS clamp between
|
|
214
|
+
* `--aparte-split-min` and `--aparte-split-max` has the last word, and announcing the
|
|
215
|
+
* requested value instead is how a splitter comes to tell a screen reader 5% while
|
|
216
|
+
* the pane sits at 22%. Without layout (jsdom, `display: none`, before first paint)
|
|
217
|
+
* the request is all there is, so it stands.
|
|
218
|
+
*
|
|
219
|
+
* While STACKED there is nothing to read: one pane is `display: none` and the other
|
|
220
|
+
* spans the single track, so the ratio is 0 or 100 whatever the seam was set to.
|
|
221
|
+
* Measuring it there is how tapping "Preview" on a phone used to write `position="0"`
|
|
222
|
+
* into the attribute, the event and the host's storage.
|
|
223
|
+
*/
|
|
224
|
+
private _achievedPercent;
|
|
225
|
+
/**
|
|
226
|
+
* The range the seam can actually reach, written onto the separator: park the pane
|
|
227
|
+
* at 0% and read it, park it at 100% and read it, put the position back. Two forced
|
|
228
|
+
* layouts in one synchronous task, so nothing paints in between.
|
|
229
|
+
*
|
|
230
|
+
* It also reconciles `aria-valuenow`, because the two have to be one story: the
|
|
231
|
+
* requested percentage can sit outside the clamped range the probe just announced —
|
|
232
|
+
* with a `--aparte-split-min` of `20rem`, `position="38"` on a 700px container asks
|
|
233
|
+
* for 38 and gets ~46 — and a separator whose value is below its own minimum is the
|
|
234
|
+
* unclamped-announcement bug this probe exists to prevent, just at rest. `_position`
|
|
235
|
+
* is left alone: it is the REQUESTED value, and `reset()` means it.
|
|
236
|
+
*
|
|
237
|
+
* Gated on `!_dragging`: a ResizeObserver tick mid-gesture would move the pane to
|
|
238
|
+
* both ends under the pointer. Gated on `!stacked` for the reason
|
|
239
|
+
* `_achievedPercent()` is: a pane that spans everything measures the same at 0% and
|
|
240
|
+
* at 100%, which would announce a range of one number.
|
|
241
|
+
*/
|
|
242
|
+
private _measureBounds;
|
|
243
|
+
/**
|
|
244
|
+
* Re-measure when the container's size changes — and only then. The probe writes the
|
|
245
|
+
* host's `style` three times, and the reflection is commit-only precisely because a
|
|
246
|
+
* `MutationObserver({ attributes: true })` (the docs' preview frame has one) reposts
|
|
247
|
+
* a frame height per mutation, which resizes the split, which re-ticks this observer.
|
|
248
|
+
* So: ignore a tick that did not move the size, and batch the rest to one per frame.
|
|
249
|
+
*/
|
|
250
|
+
private _watchSize;
|
|
251
|
+
private _setLive;
|
|
252
|
+
/**
|
|
253
|
+
* The commit: reflect, announce, dispatch — once. Everything downstream reads the
|
|
254
|
+
* ACHIEVED size, so the attribute, `aria-valuenow` and the detail are one number.
|
|
255
|
+
*
|
|
256
|
+
* There is no per-frame event on purpose. A bubbling, composed CustomEvent per
|
|
257
|
+
* pointermove is a reconciler in the drag loop, and no pane in this repo re-lays
|
|
258
|
+
* itself out in JS — they resize in CSS. The trigger for adding
|
|
259
|
+
* `aparte-split-resizing` is a consumer whose pane needs a JS measurement mid-drag.
|
|
260
|
+
*/
|
|
261
|
+
private _commit;
|
|
262
|
+
/** The computed direction, never `document.dir`: a host can flip one subtree. */
|
|
263
|
+
private _rtl;
|
|
264
|
+
private _onPointerDown;
|
|
265
|
+
/**
|
|
266
|
+
* Only the pointer that started the gesture. On a hybrid device a hovering pen or a
|
|
267
|
+
* stray touch delivers a `pointermove` with `buttons === 0`, which would otherwise
|
|
268
|
+
* fall into the release branch below and end someone else's mouse drag.
|
|
269
|
+
*/
|
|
270
|
+
private _isOurPointer;
|
|
271
|
+
private _onPointerMove;
|
|
272
|
+
private _onPointerUp;
|
|
273
|
+
private _onPointerCancel;
|
|
274
|
+
private _endDrag;
|
|
275
|
+
private _releasePointer;
|
|
276
|
+
/**
|
|
277
|
+
* The drag overlay: a fixed, transparent child of the HANDLE, alive for one gesture.
|
|
278
|
+
* Topmost, so it swallows an iframe pane's hit-testing — the case this exists for —
|
|
279
|
+
* and paints the drag cursor across the page. A child of the handle rather than of
|
|
280
|
+
* the body so `click`, and therefore `dblclick`, still dispatches at the handle.
|
|
281
|
+
*/
|
|
282
|
+
private _addScrim;
|
|
283
|
+
/**
|
|
284
|
+
* Take the overlay off.
|
|
285
|
+
*
|
|
286
|
+
* `retire` is the press that never moved — the one a click, and then a double-click,
|
|
287
|
+
* is built from. Its release happened ON the scrim (nothing captured the pointer
|
|
288
|
+
* yet), and WebKit works out what a click hit by walking the pointerup target's LIVE
|
|
289
|
+
* ancestors: take the node out here and that chain is rooted nowhere, so no `click`
|
|
290
|
+
* fires at all, no `dblclick` follows, and the seam never resets. Chromium and Gecko
|
|
291
|
+
* resolve the target before dispatch and do not care.
|
|
292
|
+
*
|
|
293
|
+
* So a retired scrim goes INERT immediately — `pointer-events: none`, which is what
|
|
294
|
+
* actually matters, since a full-page overlay left hit-testable is a page dead to the
|
|
295
|
+
* pointer — and leaves the document a moment later. Not on the next task: a first
|
|
296
|
+
* measurement removed it there and it still raced the click under a loaded machine
|
|
297
|
+
* (the trace is in `e2e/tests/layout.spec.ts`). The reference is dropped either way,
|
|
298
|
+
* so the next press builds its own; an inert one on its way out costs nothing.
|
|
299
|
+
*
|
|
300
|
+
* Teardown never retires: `disconnectedCallback` takes the live one out at once.
|
|
301
|
+
*/
|
|
302
|
+
private _removeScrim;
|
|
303
|
+
private _onDoubleClick;
|
|
304
|
+
private _onKeydown;
|
|
305
|
+
/**
|
|
306
|
+
* The keyup commits, not the keydown: a held arrow repeats, and one release should
|
|
307
|
+
* write one attribute and send one event, not thirty.
|
|
308
|
+
*/
|
|
309
|
+
private _onKeyup;
|
|
310
|
+
/**
|
|
311
|
+
* The other end of a key step. If focus leaves the seam while the key is still down —
|
|
312
|
+
* alt-tab, a click into a pane, a host moving focus — the keyup never arrives, and
|
|
313
|
+
* the pane would stay where the keydown put it while the attribute and
|
|
314
|
+
* `aria-valuenow` kept the old number for good. What is rendered is what commits.
|
|
315
|
+
*/
|
|
316
|
+
private _onFocusOut;
|
|
317
|
+
/**
|
|
318
|
+
* The stacking query, from the `breakpoint` attribute: a length (`48rem`, the
|
|
319
|
+
* default, or `640px`), or `none` for a split that stays two panes at any width —
|
|
320
|
+
* which a documentation frame needs and a host with its own breakpoint wants.
|
|
321
|
+
*/
|
|
322
|
+
private _watchBreakpoint;
|
|
323
|
+
private _onMediaChange;
|
|
324
|
+
/**
|
|
325
|
+
* Entering the stacked state shows the START pane: the chat, never a preview of
|
|
326
|
+
* nothing — the same judgement that makes the sidebar's drawer enter closed. Unless
|
|
327
|
+
* the markup already named one, which is an answer to the same question and a better
|
|
328
|
+
* one. Leaving it restores both panes, and with them the seam and its tab stop.
|
|
329
|
+
*
|
|
330
|
+
* `was` is the ATTRIBUTE, not the `stacked` getter: the getter also counts
|
|
331
|
+
* `.aparte-split--only-*`, the CSS route a host takes when it owns its breakpoints
|
|
332
|
+
* and sets `breakpoint="none"`. Read through the getter, that mount looks like a
|
|
333
|
+
* split leaving a stacked state it never entered — and the `pane` the author wrote
|
|
334
|
+
* is deleted on the way in.
|
|
335
|
+
*/
|
|
336
|
+
private _applyStacked;
|
|
337
|
+
/**
|
|
338
|
+
* A `[data-aparte-split-pane]` anywhere on the page switches a split's pane, so a
|
|
339
|
+
* two-button toggle in a header needs no script.
|
|
340
|
+
*
|
|
341
|
+
* The value is `start` or `end` — the pane to show. Any other non-empty value names
|
|
342
|
+
* a split's `id` and TOGGLES that one; empty toggles the nearest split, else the
|
|
343
|
+
* first on the page. Same shape as `[data-aparte-sidebar-toggle]`.
|
|
344
|
+
*/
|
|
345
|
+
private _onDocumentClick;
|
|
346
|
+
private _onConfigChange;
|
|
347
|
+
/**
|
|
348
|
+
* The seam's accessible name. A host that wrote its own `aria-label` — or an
|
|
349
|
+
* `aria-labelledby` pointing at a heading — keeps it: `data-own-label` marks the
|
|
350
|
+
* one we set, so a language switch replaces ours and never theirs.
|
|
351
|
+
*/
|
|
352
|
+
private _relabel;
|
|
353
|
+
}
|
|
354
|
+
//# sourceMappingURL=aparte-split.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"aparte-split.d.ts","sourceRoot":"","sources":["../../../src/components/split/aparte-split.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The split's arithmetic, with no DOM in it.
|
|
3
|
+
*
|
|
4
|
+
* Separate from the element on purpose: a pointer drag is the path jsdom exercises
|
|
5
|
+
* worst — it has no layout, no `PointerEvent` and no pointer capture — so the numbers
|
|
6
|
+
* are proven here, in plain functions a test can call, and the element is left with
|
|
7
|
+
* the listeners and the attributes.
|
|
8
|
+
*
|
|
9
|
+
* Nothing here parses a CSS unit. `--aparte-split-min` and `--aparte-split-max` are
|
|
10
|
+
* clamp bounds in the grid template, so the browser clamps the pane and this module
|
|
11
|
+
* only ever moves a percentage between 0 and 100.
|
|
12
|
+
*/
|
|
13
|
+
/** One step of a drag: where it started, how far the pointer went, and along which axis. */
|
|
14
|
+
export interface SplitStep {
|
|
15
|
+
/** The primary pane's size when the gesture began, as a percentage of the container. */
|
|
16
|
+
startPercent: number;
|
|
17
|
+
/** How far the pointer has travelled since, in CSS pixels, along the split's axis. */
|
|
18
|
+
deltaPx: number;
|
|
19
|
+
/** The container's size along that same axis. */
|
|
20
|
+
containerPx: number;
|
|
21
|
+
/** The computed reading direction is right-to-left. Ignored on the vertical axis. */
|
|
22
|
+
rtl: boolean;
|
|
23
|
+
/** The split's orientation is `vertical` — the panes are stacked, the axis is the block one. */
|
|
24
|
+
vertical: boolean;
|
|
25
|
+
/**
|
|
26
|
+
* `primary="end"`: the sized track is the LAST one, so the seam's distance from the
|
|
27
|
+
* container's start is `100% - handle - position` and a bigger number moves the seam
|
|
28
|
+
* TOWARD the start. Without this the seam runs away from the pointer.
|
|
29
|
+
*/
|
|
30
|
+
primaryEnd?: boolean;
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* The primary pane's new size, as a percentage of the container, clamped to 0..100.
|
|
34
|
+
*
|
|
35
|
+
* A right-to-left drag moves the other way: in `rtl` the start pane is on the right, so
|
|
36
|
+
* a pointer travelling in +x makes it smaller. The block axis never inverts — `rtl` is a
|
|
37
|
+
* writing direction, not a gravity — so it is ignored when `vertical`.
|
|
38
|
+
*
|
|
39
|
+
* `primaryEnd` inverts it too, and for a different reason: the pane being sized is the
|
|
40
|
+
* one the pointer moves AWAY from. The two inversions compose — an `rtl` split whose
|
|
41
|
+
* primary is the end pane reads like a plain one again — so they are XORed, not summed.
|
|
42
|
+
*
|
|
43
|
+
* A container of zero (measured before layout, or while display:none) yields the
|
|
44
|
+
* starting value rather than `Infinity`: the caller gets a number it can write back.
|
|
45
|
+
*/
|
|
46
|
+
export declare function nextPosition(step: SplitStep): number;
|
|
47
|
+
/**
|
|
48
|
+
* How far a key moves the seam, in percentage points — or `null` for a key that is not
|
|
49
|
+
* ours, so the handler can leave the page's own scrolling alone.
|
|
50
|
+
*
|
|
51
|
+
* Shift is ×10. That is an ecosystem convention (Shoelace's `×10`, Zag's delta of 10),
|
|
52
|
+
* NOT the APG, which specifies only the single step: it is here because a 1% step across
|
|
53
|
+
* a 1600px window is 16px and nobody arrows a pane across a screen one percent at a time.
|
|
54
|
+
*
|
|
55
|
+
* Home and End are the extremes as ±100: the clamp in `nextPosition` — and then the CSS
|
|
56
|
+
* clamp in the grid — decide where that actually lands, so a `--aparte-split-min` of
|
|
57
|
+
* `20rem` means Home stops at 20rem without this function knowing what a rem is.
|
|
58
|
+
*
|
|
59
|
+
* `primaryEnd` mirrors the ARROWS only, for the same reason `nextPosition` mirrors the
|
|
60
|
+
* pointer: an arrow names a direction the SEAM travels in. Home and End name the primary
|
|
61
|
+
* pane's own extremes — its minimum is its minimum whichever end it sits at — so they are
|
|
62
|
+
* left alone.
|
|
63
|
+
*/
|
|
64
|
+
export declare function keyDelta(key: string, shift: boolean, rtl: boolean, vertical: boolean, primaryEnd?: boolean): number | null;
|
|
65
|
+
//# sourceMappingURL=geometry.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"geometry.d.ts","sourceRoot":"","sources":["../../../src/components/split/geometry.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,4FAA4F;AAC5F,MAAM,WAAW,SAAS;IACtB,wFAAwF;IACxF,YAAY,EAAE,MAAM,CAAC;IACrB,sFAAsF;IACtF,OAAO,EAAE,MAAM,CAAC;IAChB,iDAAiD;IACjD,WAAW,EAAE,MAAM,CAAC;IACpB,qFAAqF;IACrF,GAAG,EAAE,OAAO,CAAC;IACb,gGAAgG;IAChG,QAAQ,EAAE,OAAO,CAAC;IAClB;;;;OAIG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;CACxB;AAQD;;;;;;;;;;;;;GAaG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,SAAS,GAAG,MAAM,CAOpD;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,QAAQ,CACpB,GAAG,EAAE,MAAM,EACX,KAAK,EAAE,OAAO,EACd,GAAG,EAAE,OAAO,EACZ,QAAQ,EAAE,OAAO,EACjB,UAAU,UAAQ,GACnB,MAAM,GAAG,IAAI,CAYf"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/split/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,YAAY,EAAE,uBAAuB,EAAE,MAAM,mBAAmB,CAAC"}
|