panelset 0.5.0

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.
Files changed (39) hide show
  1. package/dist/index.d.ts +111 -0
  2. package/dist/panelset.css +1 -0
  3. package/dist/panelset.js +317 -0
  4. package/dist/panelset.js.map +1 -0
  5. package/package.json +49 -0
  6. package/src/docs/assets/scripts/copybutton.js +44 -0
  7. package/src/docs/assets/scripts/example-async.js +161 -0
  8. package/src/docs/assets/scripts/example-closable.js +27 -0
  9. package/src/docs/assets/scripts/example-megamenu.js +84 -0
  10. package/src/docs/assets/scripts/example.js +29 -0
  11. package/src/docs/assets/scripts/main.js +7 -0
  12. package/src/docs/assets/styles/_base.scss +13 -0
  13. package/src/docs/assets/styles/_code.scss +121 -0
  14. package/src/docs/assets/styles/_demos.scss +180 -0
  15. package/src/docs/assets/styles/_landingpage.scss +41 -0
  16. package/src/docs/assets/styles/_layout.scss +80 -0
  17. package/src/docs/assets/styles/_sidebar.scss +67 -0
  18. package/src/docs/assets/styles/_typography.scss +116 -0
  19. package/src/docs/assets/styles/_variables.scss +32 -0
  20. package/src/docs/assets/styles/docs.scss +64 -0
  21. package/src/docs/views/api-reference.pug +474 -0
  22. package/src/docs/views/configuration.pug +173 -0
  23. package/src/docs/views/events.pug +222 -0
  24. package/src/docs/views/examples/async.pug +268 -0
  25. package/src/docs/views/examples/basic.pug +155 -0
  26. package/src/docs/views/examples/closable.pug +97 -0
  27. package/src/docs/views/getting-started.pug +99 -0
  28. package/src/docs/views/index.pug +38 -0
  29. package/src/docs/views/templates/includes/_head.pug +11 -0
  30. package/src/docs/views/templates/includes/_mixins.pug +100 -0
  31. package/src/docs/views/templates/includes/_scripts.pug +14 -0
  32. package/src/docs/views/templates/includes/_sidebar.pug +18 -0
  33. package/src/docs/views/templates/layouts/_base.pug +36 -0
  34. package/src/docs/views/transitions.pug +141 -0
  35. package/src/lib/index.ts +685 -0
  36. package/src/lib/styles/_base.scss +99 -0
  37. package/src/lib/styles/_loading.scss +47 -0
  38. package/src/lib/styles/_variables.scss +19 -0
  39. package/src/lib/styles/panelset.scss +3 -0
@@ -0,0 +1,474 @@
1
+ extends /docs/views/templates/layouts/_base
2
+
3
+ append variables
4
+ - pagetitle = "API reference"
5
+
6
+
7
+ block content
8
+ .lane
9
+ .container
10
+ .page-header
11
+ h1 API reference
12
+ p.lead Complete reference for PanelSet Lite methods, properties, and static methods
13
+
14
+
15
+ .lane
16
+ .container
17
+ h2 Constructor
18
+
19
+
20
+ .example.api
21
+ h3.code new PanelSet(selector: string | HTMLElement, options?: PanelSetLiteConfig)
22
+ p Creates a new PanelSet instance.
23
+ h4 Parameters:
24
+ dl
25
+ dt.code selector
26
+ dd CSS selector string or HTMLElement reference to the panelset container
27
+
28
+ dt.code options (optional)
29
+ dd Configuration object (see #[a(href="configuration.html") Configuration] page for details)
30
+ br
31
+ +codeblock('JavaScript').
32
+ // With selector string
33
+ const panelSet = new PanelSet('#my-panelset');
34
+
35
+ // With element reference
36
+ const container = document.getElementById('my-panelset');
37
+ const panelSet = new PanelSet(container, {
38
+ transitions: true,
39
+ closable: false,
40
+ debug: false
41
+ });
42
+ //-
43
+
44
+
45
+
46
+
47
+
48
+
49
+ .lane
50
+ .container
51
+ h2 Instance methods
52
+
53
+
54
+ .example.api
55
+ h3.code show(panelId: string, transition?: boolean, options?: ActivationOptions): Promise<void>
56
+
57
+ p Activates a panel by ID.
58
+
59
+ h4 Parameters:
60
+ dl
61
+ dt.code panelId
62
+ dd ID of the panel to activate
63
+
64
+ dt.code transition (optional)
65
+ dd Whether to animate the transition. Default: <code>true</code>
66
+
67
+ dt.code options (optional)
68
+ dd Object with optional <code>trigger</code> property (HTMLElement that triggered activation)
69
+
70
+ h4 Returns:
71
+ p Promise that resolves when activation completes
72
+
73
+ br
74
+ +codeblock('JavaScript').
75
+ // Basic usage
76
+ panelSet.show('panel-2');
77
+
78
+ // Without transition
79
+ panelSet.show('panel-2', false);
80
+
81
+ // With trigger tracking
82
+ button.addEventListener('click', () => {
83
+ panelSet.show('panel-2', true, { trigger: button });
84
+ });
85
+ //-
86
+
87
+
88
+ .example.api
89
+ h3.code open(transition?: boolean): void
90
+
91
+ p Opens a closable panelset (only works if #[code closable: true]).
92
+
93
+ h4 Parameter:
94
+ dl
95
+ dt.code transition (optional)
96
+ dd Whether to animate the opening. Default: #[code true]
97
+
98
+ br
99
+ +codeblock('JavaScript').
100
+ // Open with animation
101
+ panelSet.open();
102
+
103
+ // Open instantly
104
+ panelSet.open(false);
105
+ //-
106
+
107
+
108
+ .example.api
109
+ h3.code close(transition?: boolean): void
110
+
111
+ p Closes a closable panelset (only works if #[code closable: true]).
112
+
113
+ h4 Parameter:
114
+ dl
115
+ dt.code transition (optional)
116
+ dd Whether to animate the closing. Default: #[code true]
117
+
118
+ br
119
+ +codeblock('JavaScript').
120
+ // Close with animation
121
+ panelSet.close();
122
+
123
+ // Close instantly
124
+ panelSet.close(false);
125
+ //-
126
+
127
+
128
+ .example.api
129
+ h3.code toggle(transition?: boolean): void
130
+
131
+ p Toggles a closable panelset between open and closed (only works if #[code closable: true]).
132
+
133
+ h4 Parameter:
134
+ dl
135
+ dt.code transition (optional)
136
+ dd Whether to animate the toggle. Default: #[code true]
137
+
138
+ br
139
+ +codeblock('JavaScript').
140
+ // Toggle with animation
141
+ panelSet.toggle();
142
+
143
+ // Toggle instantly
144
+ panelSet.toggle(false);
145
+ //-
146
+
147
+
148
+ .example.api
149
+ h3.code getActive(): string | null
150
+
151
+ p Returns the ID of the currently active panel.
152
+
153
+ h4 Returns:
154
+ p Panel ID string, or #[code null] if no panel is active
155
+
156
+ br
157
+ +codeblock('JavaScript').
158
+ const activePanelId = panelSet.getActive();
159
+ console.log('Current panel:', activePanelId);
160
+
161
+ if (panelSet.getActive() === 'panel-3') {
162
+ // Do something when panel 3 is active
163
+ }
164
+ //-
165
+
166
+
167
+
168
+ .example.api
169
+ h3.code onBeforeActivate(handler: Function, options?: { once: boolean }): void
170
+
171
+ p Registers a handler for async content loading before panel activation.
172
+
173
+
174
+ h4 Parameters:
175
+ dl
176
+ dt.code handler
177
+ dd Function #[code (targetPanel: HTMLElement, signal: AbortSignal) => Promise | void]
178
+
179
+ dt.code options (optional)
180
+ dd Object with optional #[code once] property to register a one-time handler. If set to #[code true], the content loads only once and is cached. Otherwise, it reloads every time.
181
+
182
+
183
+ p The handler receives the target panel element and an AbortSignal for cancellation. Return a promise to delay activation until loading completes.
184
+
185
+ br
186
+ +codeblock('JavaScript').
187
+ // Always reload (default)
188
+ panelSet.onBeforeActivate((targetPanel, signal) => {
189
+ return fetch(`/api/panel/${targetPanel.id}`, { signal })
190
+ .then(res => res.text())
191
+ .then(html => targetPanel.innerHTML = html);
192
+ });
193
+
194
+ // Load once, cache forever
195
+ panelSet.onBeforeActivate((targetPanel, signal) => {
196
+ return fetch(`/api/panel/${targetPanel.id}`, { signal })
197
+ .then(res => res.text())
198
+ .then(html => targetPanel.innerHTML = html);
199
+ }, { once: true });
200
+ //-
201
+
202
+
203
+
204
+
205
+
206
+
207
+
208
+
209
+ .lane
210
+ .container
211
+ h2 Instance properties
212
+
213
+ .example.api
214
+ h3.code element: HTMLElement
215
+
216
+ p #[strong Read-only.] Reference to the PanelSet DOM element.
217
+
218
+ +codeblock('JS').
219
+ console.log(panelSet.element.id);
220
+ panelSet.element.classList.add('custom-class');
221
+ //-
222
+ .example.api
223
+ h3.code config: PanelSetConfig
224
+
225
+ p #[strong Read-only.] The merged configuration object.
226
+
227
+ +codeblock('JS').
228
+ console.log(panelSet.config.transitions);
229
+ console.log(panelSet.config.closable);
230
+ //-
231
+
232
+
233
+
234
+
235
+
236
+
237
+
238
+
239
+
240
+ .lane
241
+ .container
242
+ h2 Static methods
243
+
244
+ .example.api
245
+ h3.code PanelSet.init(selector?: string, options?: PanelSetConfig): PanelSet[]
246
+
247
+ p Auto-initializes all panelsets matching the selector.
248
+
249
+ h4 Parameters:
250
+ dl
251
+ dt.code selector (optional)
252
+ dd CSS selector for elements to initialize. Default: <code>'[data-panelset]'</code>
253
+
254
+ dt.code options (optional)
255
+ dd Configuration object applied to all instances
256
+
257
+ h4 Returns:
258
+ p Array of created PanelSet instances
259
+ p Note: Stores instance reference on container as #[code container.panelSet]
260
+
261
+ br
262
+ +codeblock('JavaScript').
263
+ // Initialize all [data-panelset] elements
264
+ const instances = PanelSet.init();
265
+
266
+ // Initialize specific elements
267
+ const instances = PanelSet.init('.my-panelsets');
268
+
269
+ // With global options
270
+ const instances = PanelSet.init('[data-panelset]', {
271
+ transitions: true,
272
+ debug: false
273
+ });
274
+
275
+ // Access via container
276
+ const container = document.getElementById('my-panelset');
277
+ container.panelSet.setActive('panel-2');
278
+ //-
279
+
280
+ .example.api
281
+ h3.code PanelSet.init(options: PanelSetConfig): PanelSet[]
282
+
283
+ p Alternative signature: Pass only options, uses default selector.
284
+
285
+ h4 Parameters:
286
+ dl
287
+ dt.code options (optional)
288
+ dd Configuration object applied to all instances
289
+
290
+ br
291
+ +codeblock('JavaScript').
292
+ const instances = PanelSet.init({
293
+ transitions: false,
294
+ debug: true
295
+ });
296
+ //-
297
+
298
+
299
+
300
+
301
+ .lane
302
+ .container
303
+ h2 Events
304
+ p All events are CustomEvents dispatched from the container element with a #[code detail] object. See the #[a(href="events.html") Events] page for detailed documentation.
305
+
306
+
307
+ .example.white
308
+ table(style="width: 100%; border-collapse: collapse; margin: 0;")
309
+ thead
310
+ tr
311
+ th(style="text-align: left; padding: 0.5rem; border-bottom: 2px solid #e5e7eb;") Event Name
312
+ th(style="text-align: left; padding: 0.5rem; border-bottom: 2px solid #e5e7eb;") When Fired
313
+ th(style="text-align: left; padding: 0.5rem; border-bottom: 2px solid #e5e7eb;") Detail Properties
314
+ tbody
315
+ tr
316
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code ps:ready]
317
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") When instance is initialized
318
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code element]
319
+
320
+ tr
321
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code ps:beforeactivate]
322
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") Before activation begins (for async loading)
323
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code panelId, targetPanel, outgoingPanel, signal, promise]
324
+
325
+ tr
326
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code ps:activationstart]
327
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") When panel activation begins
328
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code panelId, trigger]
329
+ tr
330
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code ps:activationcomplete]
331
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") When activation finishes
332
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code panelId, trigger]
333
+ tr
334
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code ps:activationaborted]
335
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") When activation is interrupted
336
+ td(style="padding: 0.5rem; border-bottom: 1px solid #e5e7eb;") #[code panelId, trigger]
337
+ .lane
338
+ .container
339
+ h2 TypeScript types
340
+ p PanelSet is fully typed. Import types alongside the class:
341
+
342
+
343
+ +codeblock('JS').
344
+ import {
345
+ PanelSet,
346
+ type PanelSetConfig,
347
+ type ActivationStartDetail,
348
+ type ActivationCompleteDetail,
349
+ type ActivationAbortedDetail,
350
+ type ActivationOptions,
351
+ type DebugConfig
352
+ } from 'panelset/lite';
353
+
354
+ // Type-safe configuration
355
+ const config: PanelSetConfig = {
356
+ transitions: { height: true, panels: false },
357
+ closable: true,
358
+ debug: 'verbose'
359
+ };
360
+
361
+ const panelSet = new PanelSet('#my-panelset', config);
362
+
363
+ // Type-safe event handling
364
+ container.addEventListener('ps:activationstart', (e) => {
365
+ const event = e as CustomEvent<ActivationStartDetail>;
366
+ console.log(event.detail.panelId);
367
+ });
368
+
369
+ .lane
370
+ .container
371
+ h2 Complete example
372
+
373
+
374
+ +codeblock('JS').
375
+ import { PanelSet } from 'panelset/lite';
376
+ import 'panelset/lib/panelset-lite.css';
377
+
378
+ // Initialize with options
379
+ const panelSet = new PanelSet('#my-tabs', {
380
+ transitions: true,
381
+ closable: false,
382
+ debug: false
383
+ });
384
+
385
+ // Event listeners
386
+ panelSet.container.addEventListener('ps:activationstart', (e) => {
387
+ console.log('Starting:', e.detail.panelId);
388
+ });
389
+
390
+ panelSet.container.addEventListener('ps:activationcomplete', (e) => {
391
+ console.log('Complete:', e.detail.panelId);
392
+
393
+ // Focus management
394
+ const panel = document.getElementById(e.detail.panelId);
395
+ panel?.querySelector('input, button')?.focus();
396
+ });
397
+
398
+ // Programmatic control
399
+ document.getElementById('next-btn').addEventListener('click', async () => {
400
+ const current = panelSet.getActive();
401
+ if (current === 'step-1') {
402
+ panelSet.setActive('step-2');
403
+ } else if (current === 'step-2') {
404
+ panelSet.setActive('step-3');
405
+ }
406
+ });
407
+
408
+ // Or use init for auto-initialization
409
+ const instances = PanelSet.init('[data-panelset]', {
410
+ transitions: true
411
+ });
412
+
413
+ append scripts
414
+ if isProd
415
+ script(type="module", vite-ignore).
416
+ import { PanelSet } from '/lib/panelset.js';
417
+ PanelSet.init();
418
+ else
419
+ script(type="module").
420
+ import { PanelSet } from '/src/lib/index.js';
421
+ import '/src/lib/styles/panelset.scss';
422
+ PanelSet.init({debug: true});
423
+
424
+ script.
425
+ let transitionsEnabled = true;
426
+
427
+ let closablePanelSet = null;
428
+ document.addEventListener('panelset:ready', (e) => {
429
+ const instance = e.detail.instance;
430
+ const container = e.target;
431
+ if (container.id == 'config-closable-demo') {
432
+ closablePanelSet = instance;
433
+ }
434
+ })
435
+
436
+ document.addEventListener('click', (e) => {
437
+ const button = e.target.closest('button');
438
+ if (!button) return;
439
+
440
+ if (button.dataset.panel) {
441
+ const panelId = button.getAttribute('data-panel');
442
+ const panel = document.getElementById(panelId);
443
+ const container = panel?.closest('[data-panelset]');
444
+
445
+ if (container?.panelSet) {
446
+ container.panelSet.setActive(panelId, true, { trigger: button });
447
+ }
448
+ }
449
+
450
+ if (button.id == "toggle-transitions") {
451
+ const transDemo = document.getElementById('config-transitions-demo');
452
+ if (transDemo?.panelSet.config.transitions == false) {
453
+ transDemo.panelSet.config.transitions = true;
454
+ button.textContent = "Disable Transitions";
455
+ } else {
456
+ transDemo.panelSet.config.transitions = false;
457
+ button.textContent = "Enable Transitions";
458
+ }
459
+ }
460
+ });
461
+
462
+
463
+
464
+ // Log events
465
+ document.addEventListener('activationstart', (e) => {
466
+ console.log('[Demo PanelSet log] Activationstart:', e.detail);
467
+ });
468
+
469
+ document.addEventListener('activationcomplete', (e) => {
470
+ console.log('[Demo PanelsSet log] Activationcomplete:', e.detail);
471
+ });
472
+
473
+
474
+
@@ -0,0 +1,173 @@
1
+ extends /docs/views/templates/layouts/_base
2
+
3
+ append variables
4
+ - pagetitle = "Configuration"
5
+
6
+
7
+ block content
8
+ .lane
9
+ .container
10
+ .page-header
11
+ h1 Configuration
12
+ p.lead Configure PanelSet behavior via constructor options or data attributes
13
+
14
+ .lane
15
+ .container
16
+ h2 Setting the options
17
+ .title-text
18
+ h3 Through JavaScript options
19
+ p You can configure PanelSet when initializing it by passing an options object.
20
+
21
+ +codeblock('JS').
22
+ // Set the options to all PanelSets:
23
+ PanelSet.init({
24
+ transitions: true,
25
+ closable: false,
26
+ emptyPanelHeight: 200,
27
+ debug: false
28
+ });
29
+
30
+ // Set the options to a specific PanelSet:
31
+ PanelSet.init('#my-panelset', {
32
+ transitions: true,
33
+ closable: false,
34
+ emptyPanelHeight: 200,
35
+ debug: false
36
+ });
37
+
38
+ // Or create a named instance directly for later reference:
39
+ const myPanelSet = new PanelSet('#my-panelset', {
40
+ transitions: true,
41
+ closable: false,
42
+ emptyPanelHeight: 200,
43
+ debug: false
44
+ });
45
+
46
+
47
+ .container
48
+ .title-text
49
+ h3 Through data-attributes
50
+ p Or configure via HTML data-attributes on the panelset container:
51
+
52
+
53
+ +codeblock('HTML')
54
+ #my-panelset(data-panelset data-transitions="true" data-closable data-empty-panel-height="300" data-debug="verbose")
55
+ // Panels go here
56
+ //-
57
+
58
+ .lane
59
+ .container
60
+ h2 Available options
61
+
62
+ .example.api
63
+ h3.code.method-signature transitions: boolean | { height: boolean, panels: boolean }
64
+ p Used for setting transitions on or off.
65
+ h4 Default: #[code true]
66
+
67
+ h4 Usage examples:
68
+
69
+ .card-row
70
+ .card
71
+ h4 JavaScript options
72
+ ul
73
+ li #[code {transitions: true}] - Enable all transitions
74
+ li #[code {transitions: false}] - Disable all transitions
75
+ li #[code {transitions: {height: false}}] - Disable height transitions only
76
+ .card
77
+ h4 Data attributes
78
+ ul
79
+ li #[code data-transitions="false"] - Disable all transitions
80
+ li #[code data-transitions='{"height":false}'] - Disable height transitions only
81
+
82
+
83
+
84
+ .example.api
85
+ h3.code.method-signature closable: boolean
86
+ p When enabled, panelsets can be closed (height: 0) and reopened.
87
+ h4 Default: #[code false]
88
+
89
+ h4 Usage examples:
90
+
91
+ .card-row
92
+ .card
93
+ h4 JavaScript options
94
+ ul
95
+ li #[code {closable: true}] - Enable closable panelset
96
+ li #[code {closable: false}] - Disable closable panelset
97
+
98
+ .card
99
+ h4 Data attributes
100
+ ul
101
+ li #[code data-closable] - Enable closable panelset
102
+
103
+ .example.api
104
+ h3.code.method-signature emptyPanelHeight: number
105
+ p Placeholder height in pixels when no panel is active. This is used if there is a delay in loading the panel content, and there is no previous panel to show the spinner on.
106
+ h4 Default: #[code 200]
107
+
108
+ h4 Usage examples:
109
+
110
+ .card-row
111
+ .card
112
+ h4 JavaScript options
113
+ ul
114
+ li #[code {emptyPanelHeight: 200}] - Set placeholder height to 200 pixels
115
+ li #[code {emptyPanelHeight: 300}] - Set placeholder height to 300 pixels
116
+
117
+ .card
118
+ h4 Data attributes
119
+ ul
120
+ li #[code data-empty-panel-height="300"] - Set placeholder height to 300 pixels
121
+
122
+
123
+ .example.api
124
+ h3.code.method-signature loadingDelay: number
125
+ p Delay in milliseconds before showing the loading spinner. Prevents spinner flash on fast connections.
126
+ h4 Default: #[code 300]
127
+
128
+ h4 Usage examples:
129
+
130
+ .card-row
131
+ .card
132
+ h4 JavaScript options
133
+ ul
134
+ li #[code {loadingDelay: 200}] - Set loading delay to 200 milliseconds
135
+ li #[code {loadingDelay: 300}] - Set loading delay to 300 milliseconds
136
+
137
+ .card
138
+ h4 Data attributes
139
+ ul
140
+ li #[code data-loading-delay="300"] - Set loading delay to 300 milliseconds
141
+
142
+ .example.api
143
+ h3.code.method-signature debug: boolean
144
+ p Used for logging and debugging purposes.
145
+ h4 Default: #[code false]
146
+
147
+ h4 Usage examples:
148
+
149
+ .card-row
150
+ .card
151
+ h4 JavaScript options
152
+ ul
153
+ li #[code {debug: true}] - Enable debugging
154
+ li #[code {debug: false}] - Disable debugging
155
+ .card
156
+ h4 Data attributes
157
+ ul
158
+ li #[code data-debug] - Enable debugging
159
+
160
+
161
+
162
+
163
+
164
+ append scripts
165
+ if isProd
166
+ script(type="module", vite-ignore).
167
+ import { PanelSet } from '/lib/panelset.js';
168
+ PanelSet.init();
169
+ else
170
+ script(type="module").
171
+ import { PanelSet } from '/src/lib/index.js';
172
+ import '/src/lib/styles/panelset.scss';
173
+ PanelSet.init({debug: true});