@ixfx/components 0.6.0 → 0.6.2

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 (50) hide show
  1. package/bundle/index.d.ts +176 -1
  2. package/bundle/index.d.ts.map +1 -1
  3. package/bundle/index.js +810 -1
  4. package/bundle/index.js.map +1 -1
  5. package/dist/ac-text.d.ts +1 -1
  6. package/dist/{ac-token-DVbmHmky.d.ts → ac-token-BAa6ke09.d.ts} +2 -2
  7. package/dist/{ac-token-DVbmHmky.d.ts.map → ac-token-BAa6ke09.d.ts.map} +1 -1
  8. package/dist/ac-token.d.ts +1 -1
  9. package/dist/colour-picker.d.ts +1 -1
  10. package/dist/crumbs.d.ts +1 -1
  11. package/dist/{data-grid-BeAkORz2.d.ts → data-grid-C8qIo1-u.d.ts} +2 -2
  12. package/dist/{data-grid-BeAkORz2.d.ts.map → data-grid-C8qIo1-u.d.ts.map} +1 -1
  13. package/dist/data-grid.d.ts +1 -1
  14. package/dist/{grouped-item-lister-CNLMgdIr.d.ts → grouped-item-lister-_pMDwIo1.d.ts} +2 -2
  15. package/dist/{grouped-item-lister-CNLMgdIr.d.ts.map → grouped-item-lister-_pMDwIo1.d.ts.map} +1 -1
  16. package/dist/grouped-item-lister.d.ts +1 -1
  17. package/dist/{icon-BUwP1CZ1.d.ts → icon-DpA9x2Ve.d.ts} +2 -2
  18. package/dist/icon-DpA9x2Ve.d.ts.map +1 -0
  19. package/dist/icons.d.ts +2 -2
  20. package/dist/{index-RqMh1i-O.d.ts → index-BtGFYfaK.d.ts} +2 -2
  21. package/dist/{index-RqMh1i-O.d.ts.map → index-BtGFYfaK.d.ts.map} +1 -1
  22. package/dist/{index-ovq_GTdl.d.ts → index-CKtLhgYj.d.ts} +3 -3
  23. package/dist/{index-ovq_GTdl.d.ts.map → index-CKtLhgYj.d.ts.map} +1 -1
  24. package/dist/{index-BUB5SICW.d.ts → index-CoqtMSd9.d.ts} +2 -2
  25. package/dist/{index-BUB5SICW.d.ts.map → index-CoqtMSd9.d.ts.map} +1 -1
  26. package/dist/{index-BOUaDIW-.d.ts → index-tq6f8007.d.ts} +2 -2
  27. package/dist/{index-BOUaDIW-.d.ts.map → index-tq6f8007.d.ts.map} +1 -1
  28. package/dist/index.d.ts +186 -11
  29. package/dist/index.d.ts.map +1 -1
  30. package/dist/index.js +811 -1
  31. package/dist/index.js.map +1 -1
  32. package/dist/{labelled-input-base-Dp_9KP0G.d.ts → labelled-input-base-DiTme1JO.d.ts} +2 -2
  33. package/dist/{labelled-input-base-Dp_9KP0G.d.ts.map → labelled-input-base-DiTme1JO.d.ts.map} +1 -1
  34. package/dist/labelled-radial-input.d.ts +2 -2
  35. package/dist/labelled-radial-input.d.ts.map +1 -1
  36. package/dist/labelled-range-input.d.ts +1 -1
  37. package/dist/{menu-item-BG5w7fi4.d.ts → menu-item-Bs2MYyHq.d.ts} +2 -2
  38. package/dist/{menu-item-BG5w7fi4.d.ts.map → menu-item-Bs2MYyHq.d.ts.map} +1 -1
  39. package/dist/menu.d.ts +2 -2
  40. package/dist/panel.d.ts +1 -1
  41. package/dist/{tab-list-Beuh2nom.d.ts → tab-list-D_1cYhB_.d.ts} +2 -2
  42. package/dist/{tab-list-Beuh2nom.d.ts.map → tab-list-D_1cYhB_.d.ts.map} +1 -1
  43. package/dist/tabs.d.ts +1 -1
  44. package/docs-user/README.md +1 -0
  45. package/docs-user/index.json +7 -2
  46. package/docs-user/llms.txt +1 -0
  47. package/docs-user/toolbar.md +135 -0
  48. package/llms.txt +1 -0
  49. package/package.json +2 -1
  50. package/dist/icon-BUwP1CZ1.d.ts.map +0 -1
package/bundle/index.js CHANGED
@@ -25228,6 +25228,431 @@ __decorate([property({
25228
25228
  })], SliderInputElement.prototype, "disabled", void 0);
25229
25229
  SliderInputElement = __decorate([safeCustomElement(`ixfx-slider-input`)], SliderInputElement);
25230
25230
  //#endregion
25231
+ //#region src/sliding-number/sliding-number.ts
25232
+ const REEL_DIGITS = Array.from({ length: 30 }, (_, index) => index % 10);
25233
+ const SECTION_RANK = {
25234
+ lead: 0,
25235
+ integer: 1,
25236
+ decimal: 2,
25237
+ fraction: 3,
25238
+ trail: 4
25239
+ };
25240
+ function mod(n, m) {
25241
+ return (n % m + m) % m;
25242
+ }
25243
+ /** Parse a CSS time token (`0.7s`, `700ms`, `0`) to milliseconds. */
25244
+ function millis(value) {
25245
+ const s = value.trim();
25246
+ if (s === ``) return 0;
25247
+ if (s.endsWith(`ms`)) return Number.parseFloat(s) || 0;
25248
+ if (s.endsWith(`s`)) return (Number.parseFloat(s) || 0) * 1e3;
25249
+ return Number.parseFloat(s) || 0;
25250
+ }
25251
+ let SlidingNumberElement = class SlidingNumberElement extends i {
25252
+ constructor(..._args) {
25253
+ super(..._args);
25254
+ this.value = 0;
25255
+ this.prefix = ``;
25256
+ this.suffix = ``;
25257
+ this.trend = `auto`;
25258
+ this.noAnimate = false;
25259
+ this.respectMotionPreference = true;
25260
+ this._cells = [];
25261
+ this._formatted = ``;
25262
+ this._ready = false;
25263
+ this._pendingSpins = [];
25264
+ this._pendingDir = `none`;
25265
+ this._reelAnims = /* @__PURE__ */ new Map();
25266
+ this._reapTimer = 0;
25267
+ }
25268
+ connectedCallback() {
25269
+ super.connectedCallback();
25270
+ if (!this.hasAttribute(`role`)) this.setAttribute(`role`, `img`);
25271
+ }
25272
+ disconnectedCallback() {
25273
+ super.disconnectedCallback();
25274
+ for (const anim of this._reelAnims.values()) anim.cancel();
25275
+ this._reelAnims.clear();
25276
+ if (this._reapTimer) clearTimeout(this._reapTimer);
25277
+ }
25278
+ _motionOK() {
25279
+ if (this.noAnimate) return false;
25280
+ if (this.respectMotionPreference && typeof window !== `undefined` && window.matchMedia?.(`(prefers-reduced-motion: reduce)`).matches) return false;
25281
+ return true;
25282
+ }
25283
+ _timing(kind) {
25284
+ const cs = getComputedStyle(this);
25285
+ return {
25286
+ duration: this._motionOK() ? millis(cs.getPropertyValue(`--sliding-number-${kind}-duration`)) : 0,
25287
+ easing: cs.getPropertyValue(`--sliding-number-${kind}-easing`).trim() || `ease`
25288
+ };
25289
+ }
25290
+ _numberFormat() {
25291
+ try {
25292
+ return new Intl.NumberFormat(this.locales || void 0, this.format || void 0);
25293
+ } catch {
25294
+ return new Intl.NumberFormat(this.locales || void 0);
25295
+ }
25296
+ }
25297
+ _resolveDir(first) {
25298
+ switch (this.trend) {
25299
+ case `up`:
25300
+ case `increasing`: return `up`;
25301
+ case `down`:
25302
+ case `decreasing`: return `down`;
25303
+ case `none`: return `none`;
25304
+ default:
25305
+ if (first || this._prevValue === void 0 || this.value === this._prevValue) return `none`;
25306
+ return this.value > this._prevValue ? `up` : `down`;
25307
+ }
25308
+ }
25309
+ /** Split the formatted value into positioned cells. */
25310
+ _buildCells(parts) {
25311
+ const intRaw = [];
25312
+ const fractionChars = [];
25313
+ const lead = [];
25314
+ const trail = [];
25315
+ let decimalChar = ``;
25316
+ let sawInteger = false;
25317
+ let sawDecimal = false;
25318
+ for (const part of parts) switch (part.type) {
25319
+ case `integer`:
25320
+ sawInteger = true;
25321
+ for (const c of part.value) intRaw.push({
25322
+ digit: true,
25323
+ char: c
25324
+ });
25325
+ break;
25326
+ case `group`:
25327
+ intRaw.push({
25328
+ digit: false,
25329
+ char: part.value
25330
+ });
25331
+ break;
25332
+ case `decimal`:
25333
+ sawDecimal = true;
25334
+ decimalChar = part.value;
25335
+ break;
25336
+ case `fraction`:
25337
+ for (const c of part.value) fractionChars.push(c);
25338
+ break;
25339
+ default: (sawInteger || sawDecimal ? trail : lead).push(part.value);
25340
+ }
25341
+ const cells = [];
25342
+ const totalIntDigits = intRaw.filter((x) => x.digit).length;
25343
+ lead.forEach((char, index) => {
25344
+ cells.push({
25345
+ key: `lead:${index}`,
25346
+ kind: `symbol`,
25347
+ section: `lead`,
25348
+ char,
25349
+ pos: index - 100,
25350
+ phase: `active`
25351
+ });
25352
+ });
25353
+ let seen = 0;
25354
+ for (const item of intRaw) if (item.digit) {
25355
+ const place = totalIntDigits - 1 - seen;
25356
+ seen++;
25357
+ cells.push({
25358
+ key: `int:${place}`,
25359
+ kind: `digit`,
25360
+ section: `integer`,
25361
+ char: item.char,
25362
+ pos: -place,
25363
+ phase: `active`
25364
+ });
25365
+ } else {
25366
+ const place = totalIntDigits - seen;
25367
+ cells.push({
25368
+ key: `grp:${place}`,
25369
+ kind: `symbol`,
25370
+ section: `integer`,
25371
+ char: item.char,
25372
+ pos: -place + .5,
25373
+ phase: `active`
25374
+ });
25375
+ }
25376
+ if (sawDecimal) cells.push({
25377
+ key: `decimal`,
25378
+ kind: `symbol`,
25379
+ section: `decimal`,
25380
+ char: decimalChar,
25381
+ pos: 0,
25382
+ phase: `active`
25383
+ });
25384
+ fractionChars.forEach((char, index) => {
25385
+ cells.push({
25386
+ key: `frac:${index}`,
25387
+ kind: `digit`,
25388
+ section: `fraction`,
25389
+ char,
25390
+ pos: index + 1,
25391
+ phase: `active`
25392
+ });
25393
+ });
25394
+ trail.forEach((char, index) => {
25395
+ cells.push({
25396
+ key: `trail:${index}`,
25397
+ kind: `symbol`,
25398
+ section: `trail`,
25399
+ char,
25400
+ pos: index + 100,
25401
+ phase: `active`
25402
+ });
25403
+ });
25404
+ return cells;
25405
+ }
25406
+ willUpdate(changed) {
25407
+ if (![
25408
+ `value`,
25409
+ `format`,
25410
+ `locales`,
25411
+ `prefix`,
25412
+ `suffix`,
25413
+ `noAnimate`
25414
+ ].some((p) => changed.has(p)) && this._ready) return;
25415
+ const nf = this._numberFormat();
25416
+ this._formatted = `${this.prefix}${nf.format(this.value)}${this.suffix}`;
25417
+ this.setAttribute(`aria-label`, this._formatted);
25418
+ this.toggleAttribute(`data-static`, !this._motionOK());
25419
+ const first = !this._ready;
25420
+ const motionOK = this._motionOK() && !first;
25421
+ const next = this._buildCells(nf.formatToParts(this.value));
25422
+ const nextKeys = new Set(next.map((c) => c.key));
25423
+ const prev = this._cells.filter((c) => c.phase !== `leave`);
25424
+ const prevByKey = new Map(prev.map((c) => [c.key, c]));
25425
+ const dir = this._resolveDir(first);
25426
+ const spins = [];
25427
+ const merged = [];
25428
+ for (const cell of next) {
25429
+ const before = prevByKey.get(cell.key);
25430
+ if (before) {
25431
+ if (motionOK && cell.kind === `digit` && before.char !== cell.char) spins.push({
25432
+ key: cell.key,
25433
+ from: Number(before.char),
25434
+ to: Number(cell.char)
25435
+ });
25436
+ merged.push({
25437
+ ...cell,
25438
+ phase: `active`
25439
+ });
25440
+ } else merged.push({
25441
+ ...cell,
25442
+ phase: motionOK ? `enter` : `active`
25443
+ });
25444
+ }
25445
+ if (motionOK) {
25446
+ for (const cell of prev) if (!nextKeys.has(cell.key)) merged.push({
25447
+ ...cell,
25448
+ phase: `leave`
25449
+ });
25450
+ }
25451
+ merged.sort((a, b) => SECTION_RANK[a.section] - SECTION_RANK[b.section] || a.pos - b.pos);
25452
+ this._cells = merged;
25453
+ this._pendingSpins = spins;
25454
+ this._pendingDir = dir;
25455
+ }
25456
+ updated() {
25457
+ for (const spin of this._pendingSpins) this._spin(spin.key, spin.from, spin.to, this._pendingDir);
25458
+ this._pendingSpins = [];
25459
+ if (this._cells.some((c) => c.phase === `enter`)) requestAnimationFrame(() => requestAnimationFrame(() => {
25460
+ let changed = false;
25461
+ for (const cell of this._cells) if (cell.phase === `enter`) {
25462
+ cell.phase = `active`;
25463
+ changed = true;
25464
+ }
25465
+ if (changed) {
25466
+ this._cells = [...this._cells];
25467
+ this.requestUpdate();
25468
+ }
25469
+ }));
25470
+ if (this._cells.some((c) => c.phase === `leave`)) {
25471
+ if (this._reapTimer) clearTimeout(this._reapTimer);
25472
+ this._reapTimer = window.setTimeout(() => {
25473
+ this._reapTimer = 0;
25474
+ const kept = this._cells.filter((c) => c.phase !== `leave`);
25475
+ if (kept.length !== this._cells.length) {
25476
+ this._cells = kept;
25477
+ this.requestUpdate();
25478
+ }
25479
+ }, this._timing(`transform`).duration + 120);
25480
+ }
25481
+ this._prevValue = this.value;
25482
+ this._ready = true;
25483
+ }
25484
+ _spin(key, fromDigit, toDigit, dir) {
25485
+ const reel = this.renderRoot.querySelector(`[data-key="${key}"] .reel`);
25486
+ if (!reel) return;
25487
+ const fromOffset = 10 + fromDigit;
25488
+ let toOffset;
25489
+ if (dir === `up`) toOffset = fromOffset + mod(toDigit - fromDigit, 10);
25490
+ else if (dir === `down`) toOffset = fromOffset - mod(fromDigit - toDigit, 10);
25491
+ else toOffset = [
25492
+ toDigit,
25493
+ 10 + toDigit,
25494
+ 20 + toDigit
25495
+ ].reduce((best, candidate) => Math.abs(candidate - fromOffset) < Math.abs(best - fromOffset) ? candidate : best);
25496
+ const { duration, easing } = this._timing(`spin`);
25497
+ this._reelAnims.get(key)?.cancel();
25498
+ if (duration === 0) {
25499
+ reel.style.setProperty(`--o`, String(10 + toDigit));
25500
+ return;
25501
+ }
25502
+ const anim = reel.animate([{ transform: `translateY(calc(-1em * ${fromOffset}))` }, { transform: `translateY(calc(-1em * ${toOffset}))` }], {
25503
+ duration,
25504
+ easing,
25505
+ fill: `both`
25506
+ });
25507
+ this._reelAnims.set(key, anim);
25508
+ anim.finished.then(() => {
25509
+ reel.style.setProperty(`--o`, String(10 + toDigit));
25510
+ anim.cancel();
25511
+ this._reelAnims.delete(key);
25512
+ }).catch(() => {});
25513
+ }
25514
+ _renderCell(cell) {
25515
+ if (cell.kind === `digit`) return b`
25516
+ <span class="cell digit" part="digit" data-key=${cell.key} data-phase=${cell.phase}>
25517
+ <span class="reel" style=${`--o:${10 + Number(cell.char)}`}>
25518
+ ${REEL_DIGITS.map((d) => b`<span>${d}</span>`)}
25519
+ </span>
25520
+ </span>
25521
+ `;
25522
+ return b`
25523
+ <span class="cell symbol" part="symbol" data-key=${cell.key} data-phase=${cell.phase}>${cell.char}</span>
25524
+ `;
25525
+ }
25526
+ render() {
25527
+ const section = (name) => this._cells.filter((c) => c.section === name);
25528
+ const integer = [...section(`integer`)].reverse();
25529
+ return b`
25530
+ ${this.prefix ? b`<span class="affix" part="prefix">${this.prefix}</span>` : A}
25531
+ <span class="number" part="number" aria-hidden="true">
25532
+ <span class="run lead">${section(`lead`).map((c) => this._renderCell(c))}</span>
25533
+ <span class="run integer" part="integer">
25534
+ ${repeat(integer, (c) => c.key, (c) => this._renderCell(c))}
25535
+ </span>
25536
+ ${section(`decimal`).map((c) => this._renderCell(c))}
25537
+ <span class="run fraction" part="fraction">
25538
+ ${repeat(section(`fraction`), (c) => c.key, (c) => this._renderCell(c))}
25539
+ </span>
25540
+ <span class="run trail">${section(`trail`).map((c) => this._renderCell(c))}</span>
25541
+ </span>
25542
+ ${this.suffix ? b`<span class="affix" part="suffix">${this.suffix}</span>` : A}
25543
+ `;
25544
+ }
25545
+ static {
25546
+ this.styles = i$3`
25547
+ :host {
25548
+ --sliding-number-spin-duration: 0.7s;
25549
+ --sliding-number-spin-easing: cubic-bezier(0.16, 1, 0.3, 1);
25550
+ --sliding-number-transform-duration: 0.5s;
25551
+ --sliding-number-transform-easing: cubic-bezier(0.16, 1, 0.3, 1);
25552
+ --sliding-number-opacity-duration: 0.35s;
25553
+ --sliding-number-digit-width: 1ch;
25554
+
25555
+ display: inline-flex;
25556
+ align-items: flex-end;
25557
+ line-height: 1;
25558
+ font-variant-numeric: tabular-nums;
25559
+ }
25560
+
25561
+ .number,
25562
+ .run {
25563
+ display: inline-flex;
25564
+ /* Every cell is exactly 1em tall, so aligning bottom edges keeps
25565
+ every glyph on the same line without relying on synthesised
25566
+ flex baselines (which break under overflow: hidden). */
25567
+ align-items: flex-end;
25568
+ white-space: nowrap;
25569
+ }
25570
+
25571
+ .affix {
25572
+ line-height: 1;
25573
+ }
25574
+
25575
+ /* Integer digits stack right-to-left so the units column (next to the
25576
+ decimal point) stays put while higher places grow outward. */
25577
+ .run.integer {
25578
+ flex-direction: row-reverse;
25579
+ }
25580
+
25581
+ .cell {
25582
+ display: block;
25583
+ height: 1em;
25584
+ line-height: 1;
25585
+ text-align: center;
25586
+ overflow: hidden;
25587
+ transition:
25588
+ width var(--sliding-number-transform-duration) var(--sliding-number-transform-easing),
25589
+ max-width var(--sliding-number-transform-duration) var(--sliding-number-transform-easing),
25590
+ opacity var(--sliding-number-opacity-duration) var(--sliding-number-transform-easing);
25591
+ }
25592
+
25593
+ .cell.digit {
25594
+ position: relative;
25595
+ width: var(--sliding-number-digit-width);
25596
+ }
25597
+
25598
+ .cell.symbol {
25599
+ max-width: 4ch;
25600
+ }
25601
+
25602
+ .cell[data-phase='enter'],
25603
+ .cell[data-phase='leave'] {
25604
+ opacity: 0;
25605
+ }
25606
+
25607
+ .cell.digit[data-phase='enter'],
25608
+ .cell.digit[data-phase='leave'] {
25609
+ width: 0;
25610
+ }
25611
+
25612
+ .cell.symbol[data-phase='enter'],
25613
+ .cell.symbol[data-phase='leave'] {
25614
+ max-width: 0;
25615
+ }
25616
+
25617
+ .reel {
25618
+ position: absolute;
25619
+ inset: 0 0 auto 0;
25620
+ display: flex;
25621
+ flex-direction: column;
25622
+ will-change: transform;
25623
+ transform: translateY(calc(-1em * var(--o, 10)));
25624
+ }
25625
+
25626
+ .reel > span {
25627
+ display: block;
25628
+ height: 1em;
25629
+ line-height: 1;
25630
+ text-align: center;
25631
+ }
25632
+
25633
+ :host([data-static]) .cell {
25634
+ transition: none;
25635
+ }
25636
+ `;
25637
+ }
25638
+ };
25639
+ __decorate([property({ type: Number })], SlidingNumberElement.prototype, "value", void 0);
25640
+ __decorate([property({ type: String })], SlidingNumberElement.prototype, "locales", void 0);
25641
+ __decorate([property({ type: Object })], SlidingNumberElement.prototype, "format", void 0);
25642
+ __decorate([property({ type: String })], SlidingNumberElement.prototype, "prefix", void 0);
25643
+ __decorate([property({ type: String })], SlidingNumberElement.prototype, "suffix", void 0);
25644
+ __decorate([property({ type: String })], SlidingNumberElement.prototype, "trend", void 0);
25645
+ __decorate([property({
25646
+ type: Boolean,
25647
+ attribute: `no-animate`
25648
+ })], SlidingNumberElement.prototype, "noAnimate", void 0);
25649
+ __decorate([property({
25650
+ type: Boolean,
25651
+ attribute: false
25652
+ })], SlidingNumberElement.prototype, "respectMotionPreference", void 0);
25653
+ __decorate([state()], SlidingNumberElement.prototype, "_cells", void 0);
25654
+ SlidingNumberElement = __decorate([safeCustomElement(`ixfx-sliding-number`)], SlidingNumberElement);
25655
+ //#endregion
25231
25656
  //#region src/snackbar/snackbar.ts
25232
25657
  let _instanceCounter = 0;
25233
25658
  let SnackbarElement = class SnackbarElement extends i {
@@ -27778,6 +28203,83 @@ let TabPanelsElement = class TabPanelsElement extends i {
27778
28203
  __decorate([queryAssignedElements()], TabPanelsElement.prototype, "_listItems", void 0);
27779
28204
  TabPanelsElement = __decorate([safeCustomElement(`ixfx-tab-panels`)], TabPanelsElement);
27780
28205
  //#endregion
28206
+ //#region src/text-shimmer/text-shimmer.ts
28207
+ let TextShimmerElement = class TextShimmerElement extends i {
28208
+ constructor(..._args) {
28209
+ super(..._args);
28210
+ this.text = ``;
28211
+ this.paused = false;
28212
+ }
28213
+ render() {
28214
+ return b`<span class="shimmer" part="text"
28215
+ >${this.text === `` ? b`<slot></slot>` : this.text}</span
28216
+ >`;
28217
+ }
28218
+ static {
28219
+ this.styles = i$3`
28220
+ :host {
28221
+ --text-shimmer-color: var(--surface-3-text, #888);
28222
+ --text-shimmer-gradient-color: var(--surface-2-text, #fff);
28223
+ --text-shimmer-duration: 2s;
28224
+ --text-shimmer-spread: 15%;
28225
+
28226
+ display: inline-block;
28227
+ color: var(--text-shimmer-color);
28228
+ }
28229
+
28230
+ .shimmer {
28231
+ background-image: linear-gradient(
28232
+ 90deg,
28233
+ var(--text-shimmer-color) 0%,
28234
+ var(--text-shimmer-color) calc(50% - var(--text-shimmer-spread)),
28235
+ var(--text-shimmer-gradient-color) 50%,
28236
+ var(--text-shimmer-color) calc(50% + var(--text-shimmer-spread)),
28237
+ var(--text-shimmer-color) 100%
28238
+ );
28239
+ background-size: 250% 100%;
28240
+ background-repeat: no-repeat;
28241
+ -webkit-background-clip: text;
28242
+ background-clip: text;
28243
+ color: transparent;
28244
+ -webkit-text-fill-color: transparent;
28245
+ animation: ixfx-text-shimmer-sweep var(--text-shimmer-duration) linear infinite;
28246
+ }
28247
+
28248
+ /* Sweep the highlight band from the right edge to the left edge. */
28249
+ @keyframes ixfx-text-shimmer-sweep {
28250
+ from {
28251
+ background-position: 100% center;
28252
+ }
28253
+ to {
28254
+ background-position: 0% center;
28255
+ }
28256
+ }
28257
+
28258
+ :host([paused]) .shimmer {
28259
+ animation: none;
28260
+ background-image: none;
28261
+ color: var(--text-shimmer-color);
28262
+ -webkit-text-fill-color: var(--text-shimmer-color);
28263
+ }
28264
+
28265
+ @media (prefers-reduced-motion: reduce) {
28266
+ .shimmer {
28267
+ animation: none;
28268
+ background-image: none;
28269
+ color: var(--text-shimmer-color);
28270
+ -webkit-text-fill-color: var(--text-shimmer-color);
28271
+ }
28272
+ }
28273
+ `;
28274
+ }
28275
+ };
28276
+ __decorate([property({ type: String })], TextShimmerElement.prototype, "text", void 0);
28277
+ __decorate([property({
28278
+ type: Boolean,
28279
+ reflect: true
28280
+ })], TextShimmerElement.prototype, "paused", void 0);
28281
+ TextShimmerElement = __decorate([safeCustomElement(`ixfx-text-shimmer`)], TextShimmerElement);
28282
+ //#endregion
27781
28283
  //#region src/timeline/timeline-controller.ts
27782
28284
  /**
27783
28285
  * External adapter class that can configure a timeline element
@@ -29523,6 +30025,313 @@ __decorate([state()], IxfxTimelineElement.prototype, "_internalEvents", void 0);
29523
30025
  __decorate([state()], IxfxTimelineElement.prototype, "_internalTracks", void 0);
29524
30026
  IxfxTimelineElement = __decorate([safeCustomElement(`ixfx-timeline`)], IxfxTimelineElement);
29525
30027
  //#endregion
30028
+ //#region src/toolbar/toolbar-group.ts
30029
+ let ToolbarGroupElement = class ToolbarGroupElement extends i {
30030
+ constructor(..._args) {
30031
+ super(..._args);
30032
+ this.label = ``;
30033
+ this.grow = false;
30034
+ }
30035
+ static {
30036
+ this.styles = [themeFallbacks, i$3`
30037
+ :host {
30038
+ display: flex;
30039
+ flex-direction: column;
30040
+ align-items: var(--toolbar-group-align-items, center);
30041
+ justify-content: var(--toolbar-group-justify-content, flex-start);
30042
+ gap: var(--toolbar-gap, var(--space-s));
30043
+ padding: var(--space-xs);
30044
+ border: 1px solid var(--border-subtle, var(--border));
30045
+ border-radius: var(--radius-s);
30046
+ background: var(--surface-3);
30047
+ min-width: 0;
30048
+ }
30049
+ :host(:not([label])) {
30050
+ border: none;
30051
+ background: transparent;
30052
+ padding: 0;
30053
+ }
30054
+ .label-row {
30055
+ display: none;
30056
+ font-size: var(--text-s, 12px);
30057
+ color: var(--surface-muted-text);
30058
+ padding-inline: var(--space-xs);
30059
+ white-space: nowrap;
30060
+ border-bottom: 1px solid var(--border-subtle);
30061
+ margin-bottom: var(--space-xs);
30062
+ }
30063
+ :host([label][show-label]) .label-row { display: block; }
30064
+ :host(:not([label])) .label-row { display: none; }
30065
+ :host([grow]) { flex: 1 1 auto; min-width: 0; }
30066
+ :host([hidden]) { display: none !important; }
30067
+ .components { display: flex; }
30068
+ ::slotted(*) { flex: 0 0 auto; }
30069
+ ::slotted([grow]) { flex: 1 1 auto; }
30070
+ `];
30071
+ }
30072
+ render() {
30073
+ return b`
30074
+ <div class="label-row">${this.label}</div>
30075
+ <div class="components">
30076
+ <slot></slot>
30077
+ </div>
30078
+ `;
30079
+ }
30080
+ };
30081
+ __decorate([property({ type: String })], ToolbarGroupElement.prototype, "label", void 0);
30082
+ __decorate([property({
30083
+ type: Boolean,
30084
+ reflect: true
30085
+ })], ToolbarGroupElement.prototype, "grow", void 0);
30086
+ ToolbarGroupElement = __decorate([safeCustomElement(`ixfx-toolbar-group`)], ToolbarGroupElement);
30087
+ //#endregion
30088
+ //#region src/toolbar/toolbar.ts
30089
+ var _ToolbarElement;
30090
+ let ToolbarElement = class ToolbarElement extends i {
30091
+ static {
30092
+ _ToolbarElement = this;
30093
+ }
30094
+ constructor(..._args) {
30095
+ super(..._args);
30096
+ this.orientation = `horizontal`;
30097
+ this.layout = `one-line`;
30098
+ this.verticalWriting = `auto`;
30099
+ this.showGroupLabels = false;
30100
+ this.invisibleGroups = false;
30101
+ this._overflowCount = 0;
30102
+ this._ro = null;
30103
+ this._anchor = `--toolbar-${_ToolbarElement._cnt++}`;
30104
+ this._sizes = /* @__PURE__ */ new WeakMap();
30105
+ this._measureQueued = false;
30106
+ }
30107
+ static {
30108
+ this._cnt = 0;
30109
+ }
30110
+ static {
30111
+ this.styles = [
30112
+ themeFallbacks,
30113
+ popupSurfaceStyles,
30114
+ i$3`
30115
+ :host {
30116
+ --toolbar-gap: var(--space-s);
30117
+ --toolbar-group-gap: var(--space-m);
30118
+ display: block;
30119
+ container-type: inline-size;
30120
+ }
30121
+ :host([orientation="vertical-left"]),
30122
+ :host([orientation="vertical-right"]) {
30123
+ container-type: normal;
30124
+ width: max-content;
30125
+ }
30126
+ :host([orientation="vertical-left"]),
30127
+ :host([orientation="vertical-right"]) { height: 100%; }
30128
+ :host([orientation="vertical-left"]) .inner,
30129
+ :host([orientation="vertical-right"]) .inner { height: 100%; box-sizing: border-box; width: max-content; }
30130
+ .inner {
30131
+ display: flex;
30132
+ gap: var(--toolbar-gap);
30133
+ background: var(--toolbar-bg, var(--surface-2));
30134
+ padding: var(--toolbar-padding, var(--space-s));
30135
+ border: var(--toolbar-border, var(--border-subtle));
30136
+ border-radius: var(--radius-s);
30137
+ align-items: center;
30138
+ }
30139
+ :host([orientation="horizontal"]) .inner { flex-direction: row; justify-content: flex-start; }
30140
+ :host([orientation="vertical-left"]) .inner { flex-direction: column-reverse; align-items: stretch; }
30141
+ :host([orientation="vertical-right"]) .inner { flex-direction: column; align-items: stretch; }
30142
+ :host([layout="wrap"]) .inner { flex-wrap: wrap; }
30143
+ :host([layout="one-line"]) .inner { flex-wrap: nowrap; overflow: hidden; }
30144
+ :host([orientation="vertical-left"][vertical-writing="auto"]) ::slotted(*) { writing-mode: sideways-lr; }
30145
+ :host([orientation="vertical-right"][vertical-writing="auto"]) ::slotted(*) { writing-mode: vertical-lr; }
30146
+ :host([vertical-writing="up"]) ::slotted(*) { writing-mode: vertical-rl; text-orientation: upright; }
30147
+ :host([vertical-writing="down"]) ::slotted(*) { writing-mode: vertical-lr; }
30148
+ :host([vertical-writing="none"]) ::slotted(*) { writing-mode: horizontal-tb; }
30149
+ ::slotted(*) { flex: 0 0 auto; }
30150
+ ::slotted([grow]), ::slotted(ixfx-toolbar-group[grow]) { flex: 1 1 auto; }
30151
+ ::slotted([hidden]) { display: none !important; }
30152
+ :host([invisible-groups]) ::slotted(ixfx-toolbar-group) { --toolbar-group-border: none; }
30153
+ .overflow-btn {
30154
+ anchor-name: var(--anchor-name);
30155
+ flex-shrink: 0;
30156
+ background: var(--surface-3);
30157
+ border: var(--border);
30158
+ border-radius: var(--radius-s);
30159
+ padding: var(--space-xs) var(--space-s);
30160
+ cursor: pointer;
30161
+ display: none;
30162
+ }
30163
+ .overflow-btn[visible] { display: inline-flex; }
30164
+ .overflow-popover {
30165
+ position: fixed;
30166
+ top: anchor(bottom);
30167
+ left: anchor(right);
30168
+ position-anchor: var(--anchor-name);
30169
+ position-try-fallbacks: flip-block, flip-inline, flip-block flip-inline;
30170
+ margin: 8px;
30171
+ max-height: min(60vh, 400px);
30172
+ max-width: min(90vw, 320px);
30173
+ overflow: auto;
30174
+ overscroll-behavior: contain;
30175
+ z-index: 100;
30176
+ padding: var(--space-s);
30177
+ flex-direction: column;
30178
+ gap: var(--space-s);
30179
+ }
30180
+ .overflow-popover:popover-open { display: flex; }
30181
+ .overflow-popover ::slotted(*) { writing-mode: horizontal-tb; text-orientation: mixed; }
30182
+ `
30183
+ ];
30184
+ }
30185
+ connectedCallback() {
30186
+ super.connectedCallback();
30187
+ this.style.setProperty(`--anchor-name`, this._anchor);
30188
+ }
30189
+ firstUpdated() {
30190
+ this._slot.addEventListener(`slotchange`, () => this._scheduleMeasure());
30191
+ this._ro = new ResizeObserver(() => this._scheduleMeasure());
30192
+ this._ro.observe(this._inner);
30193
+ this._scheduleMeasure();
30194
+ this._updateGroupLabels();
30195
+ }
30196
+ updated(changed) {
30197
+ if (changed.has(`showGroupLabels`)) this._updateGroupLabels();
30198
+ }
30199
+ _updateGroupLabels() {
30200
+ for (const child of Array.from(this.children)) if (child.tagName === `IXFX-TOOLBAR-GROUP`) {
30201
+ if (this.showGroupLabels) child.setAttribute(`show-label`, ``);
30202
+ else child.removeAttribute(`show-label`);
30203
+ }
30204
+ }
30205
+ disconnectedCallback() {
30206
+ super.disconnectedCallback();
30207
+ this._ro?.disconnect();
30208
+ }
30209
+ /** Coalesce measure passes into one per frame; prevents slotchange feedback loops. */
30210
+ _scheduleMeasure() {
30211
+ if (this._measureQueued) return;
30212
+ this._measureQueued = true;
30213
+ requestAnimationFrame(() => {
30214
+ this._measureQueued = false;
30215
+ this._measure();
30216
+ });
30217
+ }
30218
+ _measure() {
30219
+ const children = Array.from(this.children);
30220
+ const isGrow = (el) => el.hasAttribute(`grow`) || el.matches(`[grow]`);
30221
+ const overflowable = children.filter((el) => !isGrow(el));
30222
+ const isHoriz = this.orientation === `horizontal`;
30223
+ if (this.layout !== `one-line`) {
30224
+ let mutated = false;
30225
+ for (const el of children) {
30226
+ if (el.getAttribute(`slot`) === `overflow`) {
30227
+ el.removeAttribute(`slot`);
30228
+ mutated = true;
30229
+ }
30230
+ if (el.hasAttribute(`hidden`)) {
30231
+ el.removeAttribute(`hidden`);
30232
+ mutated = true;
30233
+ }
30234
+ }
30235
+ if (this._overflowCount !== 0) {
30236
+ this._overflowCount = 0;
30237
+ mutated = true;
30238
+ }
30239
+ if (mutated) this.requestUpdate();
30240
+ return;
30241
+ }
30242
+ if (!this._inner) return;
30243
+ const cs = getComputedStyle(this._inner);
30244
+ const gap = (isHoriz ? Number.parseFloat(cs.columnGap) : Number.parseFloat(cs.rowGap)) || 0;
30245
+ const available = isHoriz ? this._inner.clientWidth : this._inner.clientHeight;
30246
+ const btnSize = 36;
30247
+ const inMain = overflowable.filter((el) => el.getAttribute(`slot`) !== `overflow`);
30248
+ const inOverflow = overflowable.filter((el) => el.getAttribute(`slot`) === `overflow`);
30249
+ let cum = 0;
30250
+ inMain.forEach((el, i) => {
30251
+ const s = isHoriz ? el.offsetWidth : el.offsetHeight;
30252
+ if (s > 0) this._sizes.set(el, s);
30253
+ cum += (i ? gap : 0) + (this._sizes.get(el) ?? s);
30254
+ });
30255
+ const btnAllowance = inOverflow.length > 0 ? gap + btnSize : 0;
30256
+ let mutated = false;
30257
+ while (inMain.length > 0 && cum + btnAllowance > available) {
30258
+ const last = inMain[inMain.length - 1];
30259
+ const s = this._sizes.get(last) ?? 0;
30260
+ last.setAttribute(`slot`, `overflow`);
30261
+ inMain.pop();
30262
+ inOverflow.unshift(last);
30263
+ cum -= (inMain.length ? gap : 0) + s;
30264
+ mutated = true;
30265
+ }
30266
+ while (inOverflow.length > 0) {
30267
+ const first = inOverflow[0];
30268
+ const s = this._sizes.get(first);
30269
+ if (s === void 0) break;
30270
+ const addGap = inMain.length ? gap : 0;
30271
+ const nextBtnAllowance = inOverflow.length > 1 ? gap + btnSize : 0;
30272
+ if (cum + addGap + s + nextBtnAllowance > available) break;
30273
+ first.removeAttribute(`slot`);
30274
+ inOverflow.shift();
30275
+ inMain.push(first);
30276
+ cum += addGap + s;
30277
+ mutated = true;
30278
+ }
30279
+ const newCount = inOverflow.length;
30280
+ if (newCount !== this._overflowCount) {
30281
+ this._overflowCount = newCount;
30282
+ mutated = true;
30283
+ }
30284
+ if (mutated) this.requestUpdate();
30285
+ }
30286
+ _toggleOverflow() {
30287
+ try {
30288
+ this._popover.togglePopover();
30289
+ } catch {
30290
+ this._popover.showPopover();
30291
+ }
30292
+ }
30293
+ render() {
30294
+ const hasOverflow = this._overflowCount > 0;
30295
+ return b`
30296
+ <div class="inner" role="toolbar" aria-orientation=${this.orientation}>
30297
+ <slot></slot>
30298
+ <button class="overflow-btn" ?visible=${hasOverflow} @click=${this._toggleOverflow} aria-label="More" aria-haspopup="true" aria-expanded=${this._popover?.matches(`:popover-open`) ?? false}>⋯</button>
30299
+ </div>
30300
+ <div class="overflow-popover popup-surface" popover="auto" @click=${(e) => e.stopPropagation()}>
30301
+ <slot name="overflow"></slot>
30302
+ </div>
30303
+ `;
30304
+ }
30305
+ };
30306
+ __decorate([property({
30307
+ type: String,
30308
+ reflect: true
30309
+ })], ToolbarElement.prototype, "orientation", void 0);
30310
+ __decorate([property({
30311
+ type: String,
30312
+ reflect: true
30313
+ })], ToolbarElement.prototype, "layout", void 0);
30314
+ __decorate([property({
30315
+ type: String,
30316
+ attribute: `vertical-writing`,
30317
+ reflect: true
30318
+ })], ToolbarElement.prototype, "verticalWriting", void 0);
30319
+ __decorate([property({
30320
+ type: Boolean,
30321
+ attribute: `show-group-labels`,
30322
+ reflect: true
30323
+ })], ToolbarElement.prototype, "showGroupLabels", void 0);
30324
+ __decorate([property({
30325
+ type: Boolean,
30326
+ attribute: `invisible-groups`,
30327
+ reflect: true
30328
+ })], ToolbarElement.prototype, "invisibleGroups", void 0);
30329
+ __decorate([state()], ToolbarElement.prototype, "_overflowCount", void 0);
30330
+ __decorate([query(`.inner`)], ToolbarElement.prototype, "_inner", void 0);
30331
+ __decorate([query(`.overflow-popover`)], ToolbarElement.prototype, "_popover", void 0);
30332
+ __decorate([query(`slot`)], ToolbarElement.prototype, "_slot", void 0);
30333
+ ToolbarElement = _ToolbarElement = __decorate([safeCustomElement(`ixfx-toolbar`)], ToolbarElement);
30334
+ //#endregion
29526
30335
  //#region src/transitory-label/transitory-label.ts
29527
30336
  let TransitoryLabelElement = class TransitoryLabelElement extends i {
29528
30337
  constructor(..._args) {
@@ -30382,6 +31191,6 @@ function init() {
30382
31191
  console.log(`Init`);
30383
31192
  }
30384
31193
  //#endregion
30385
- export { AcTextElement, AcTokenElement, ButtonElement, Checkbox, ColourPicker, ColourPickerPopup, CrumbNavigationElement, CrumbPathController, CrumbPathElement, DataController, DataDisplayComponent, DataGridElement, EditableLabel, EditableNumber, FormElement, FormGroupElement, FormPartElement, GroupedItemListerElement, ICON_CARET_RIGHT, ICON_CHECK, ICON_CHEVRON_DOWN, ICON_CLOSE, IncrSearchTreeController as IncrSearchMillerController, IncrSearchTreeController, IxfxHexEditorElement, IxfxIconElement, IxfxTimelineElement, LabelledRadialInput, LabelledRangeInput, LedElement, menu_exports as Menu, MillerBaseElement, MillerListElement, MillerTreeController, NarrowedTextElement, NotificationManager, NotificationPillElement, PanelElement, PanelGroupElement, PlotDataSeries, PlotHistogram, PlotMultiAxis, PlotSingleAxis, PlotXyAxis, PolarPad, RadialInputElement, RadioGroup, RangeElement, RangeInput, RangeMultiElement, RatingElement, SelectHorizElement, SliderInputElement, SnackbarElement, SnapContainer, SplitButton, SplitLayoutElement, SwipeElement, TabController, TabListElement, TabListItemElement, TabPanelElement, TabPanelsElement, TimelineController, TimelineTrackTabElement, TooltipElement, TransitoryLabelElement, TreeBaseElement, TreeController, TreeDataModel, TreeListElement, VerticalListElement, XyPad, applyAgeModification, applyHighlights, attachTimelineInteractions, buildHighlightTargets, clearHighlights, collectDataResult, computeColour, createAcCompletionProvider, createElementIncrSearch, createFuzzySearch, createIncrSearch, createPillRenderer, createTreeListAdapter, createVerticalListAdapter, getIcon, hasIcon, iconBus, init, monitorIndeterminate, parseColourScaleAttr, readBaseColour, registerIcon, resolveCssVars, resolveGrid, svgToDataUri, timelineStyles };
31194
+ export { AcTextElement, AcTokenElement, ButtonElement, Checkbox, ColourPicker, ColourPickerPopup, CrumbNavigationElement, CrumbPathController, CrumbPathElement, DataController, DataDisplayComponent, DataGridElement, EditableLabel, EditableNumber, FormElement, FormGroupElement, FormPartElement, GroupedItemListerElement, ICON_CARET_RIGHT, ICON_CHECK, ICON_CHEVRON_DOWN, ICON_CLOSE, IncrSearchTreeController as IncrSearchMillerController, IncrSearchTreeController, IxfxHexEditorElement, IxfxIconElement, IxfxTimelineElement, LabelledRadialInput, LabelledRangeInput, LedElement, menu_exports as Menu, MillerBaseElement, MillerListElement, MillerTreeController, NarrowedTextElement, NotificationManager, NotificationPillElement, PanelElement, PanelGroupElement, PlotDataSeries, PlotHistogram, PlotMultiAxis, PlotSingleAxis, PlotXyAxis, PolarPad, RadialInputElement, RadioGroup, RangeElement, RangeInput, RangeMultiElement, RatingElement, SelectHorizElement, SliderInputElement, SlidingNumberElement, SnackbarElement, SnapContainer, SplitButton, SplitLayoutElement, SwipeElement, TabController, TabListElement, TabListItemElement, TabPanelElement, TabPanelsElement, TextShimmerElement, TimelineController, TimelineTrackTabElement, ToolbarElement, ToolbarGroupElement, TooltipElement, TransitoryLabelElement, TreeBaseElement, TreeController, TreeDataModel, TreeListElement, VerticalListElement, XyPad, applyAgeModification, applyHighlights, attachTimelineInteractions, buildHighlightTargets, clearHighlights, collectDataResult, computeColour, createAcCompletionProvider, createElementIncrSearch, createFuzzySearch, createIncrSearch, createPillRenderer, createTreeListAdapter, createVerticalListAdapter, getIcon, hasIcon, iconBus, init, monitorIndeterminate, parseColourScaleAttr, readBaseColour, registerIcon, resolveCssVars, resolveGrid, svgToDataUri, timelineStyles };
30386
31195
 
30387
31196
  //# sourceMappingURL=index.js.map