@spfx-fast/sharepoint-ui 0.4.1 → 0.4.3

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 (57) hide show
  1. package/AGENTS.md +23 -3
  2. package/QUICKSTART.md +133 -0
  3. package/README.md +21 -878
  4. package/components.json +178 -33
  5. package/dist/appearance.js +4 -4
  6. package/dist/elements/alert.js +26 -2
  7. package/dist/elements/avatar.js +1 -1
  8. package/dist/elements/button.js +1 -1
  9. package/dist/elements/carousel.js +5 -2
  10. package/dist/elements/color-picker.js +1 -1
  11. package/dist/elements/combobox.js +5 -5
  12. package/dist/elements/data-grid-model.d.ts +3 -0
  13. package/dist/elements/data-grid.d.ts +2 -1
  14. package/dist/elements/data-grid.js +19 -10
  15. package/dist/elements/date-picker.js +1 -1
  16. package/dist/elements/dialog.js +1 -1
  17. package/dist/elements/file-upload.js +1 -1
  18. package/dist/elements/floating-position.d.ts +10 -0
  19. package/dist/elements/floating-position.js +53 -0
  20. package/dist/elements/info.js +1 -1
  21. package/dist/elements/input.js +2 -2
  22. package/dist/elements/link.js +1 -1
  23. package/dist/elements/message-bar.js +33 -5
  24. package/dist/elements/nav.js +4 -1
  25. package/dist/elements/overflow.d.ts +1 -0
  26. package/dist/elements/overflow.js +2 -2
  27. package/dist/elements/popover.js +1 -1
  28. package/dist/elements/rating.js +3 -3
  29. package/dist/elements/rich-text-editor.d.ts +15 -1
  30. package/dist/elements/rich-text-editor.js +938 -79
  31. package/dist/elements/search.js +3 -10
  32. package/dist/elements/select.js +2 -2
  33. package/dist/elements/shared.d.ts +4 -1
  34. package/dist/elements/shared.js +14 -1
  35. package/dist/elements/sharepoint-field-basic-controls.d.ts +1 -0
  36. package/dist/elements/sharepoint-field-basic-controls.js +14 -0
  37. package/dist/elements/sharepoint-fields.d.ts +29 -0
  38. package/dist/elements/sharepoint-fields.js +460 -0
  39. package/dist/elements/spin-button.js +2 -2
  40. package/dist/elements/tag-picker.js +29 -11
  41. package/dist/elements/textarea.js +2 -2
  42. package/dist/elements/toaster.js +2 -1
  43. package/dist/elements/tooltip.js +18 -1
  44. package/dist/elements/tree.js +1 -1
  45. package/dist/elements.d.ts +3 -2
  46. package/dist/elements.js +4 -1
  47. package/dist/index.d.ts +6 -4
  48. package/dist/index.js +4 -2
  49. package/dist/react.d.ts +188 -19
  50. package/dist/react.js +321 -61
  51. package/dist/sharepoint-fields.d.ts +135 -0
  52. package/dist/sharepoint-fields.js +402 -0
  53. package/dist/theme.d.ts +9 -1
  54. package/dist/theme.js +78 -1
  55. package/package.json +11 -2
  56. package/skills/sharepoint-ui/SKILL.md +1 -1
  57. package/skills/sharepoint-ui/references/sharepoint-patterns.md +1 -1
@@ -1,12 +1,12 @@
1
1
  import { base, syncHostAccessibleName } from "./shared.js";
2
- import { getFloatingPosition } from "./floating-position.js";
2
+ import { getFloatingBoundary, getFloatingPosition } from "./floating-position.js";
3
3
  /** Searchable multi-select picker with native form association and light-DOM options. */
4
4
  export function defineTagPicker() {
5
5
  if (customElements.get("spui-tag-picker"))
6
6
  return;
7
7
  class SpuiTagPicker extends HTMLElement {
8
8
  static formAssociated = true;
9
- static observedAttributes = ["label", "placeholder", "selected-values", "selected-options", "default-selected-options", "input-value", "input-appearance", "input-disabled", "input-aria-label", "input-aria-describedby", "clearable", "selected-label", "inline", "no-popover", "disabled", "required", "name", "no-results", "remove-label", "open", "default-open", "positioning", "disable-auto-focus", "aria-label", "aria-labelledby", "aria-description", "aria-describedby"];
9
+ static observedAttributes = ["label", "placeholder", "selected-values", "selected-options", "default-selected-options", "input-value", "input-appearance", "input-disabled", "input-aria-label", "input-aria-describedby", "clearable", "selected-label", "required-message", "inline", "no-popover", "disabled", "required", "name", "no-results", "remove-label", "open", "default-open", "positioning", "disable-auto-focus", "aria-label", "aria-labelledby", "aria-description", "aria-describedby", "aria-invalid"];
10
10
  internals;
11
11
  observer;
12
12
  resizeObserver;
@@ -261,22 +261,31 @@ export function defineTagPicker() {
261
261
  catch { /* Fixed positioning remains a fallback for browsers without Popover API support. */ }
262
262
  }
263
263
  const rect = anchor.getBoundingClientRect();
264
- const width = Math.min(rect.width, window.innerWidth - 8);
264
+ const view = this.ownerDocument.defaultView ?? window;
265
+ const viewport = { width: view.innerWidth, height: view.innerHeight };
266
+ const config = this.positioningValue ?? this.getAttribute("positioning") ?? undefined;
267
+ const options = typeof config === "object" ? config : undefined;
268
+ const flipBoundary = getFloatingBoundary(options?.flipBoundary === undefined ? "clippingParents" : options.flipBoundary, this, viewport);
269
+ const overflowBoundary = getFloatingBoundary(options?.overflowBoundary === undefined ? "clippingParents" : options.overflowBoundary, this, viewport);
270
+ const bounds = overflowBoundary ?? { left: 0, top: 0, right: viewport.width, bottom: viewport.height };
271
+ const maxWidth = Math.max(0, Math.min(viewport.width - 8, bounds.right - bounds.left - 16));
272
+ const maxHeight = Math.max(0, Math.min(240, bounds.bottom - bounds.top - 16));
273
+ const width = Math.min(rect.width, maxWidth);
265
274
  popup.style.width = `${width}px`;
275
+ popup.style.maxWidth = `${maxWidth}px`;
276
+ popup.style.maxHeight = `${maxHeight}px`;
266
277
  const direction = getComputedStyle(this).direction === "rtl" ? "rtl" : "ltr";
267
- const config = this.positioningValue;
268
278
  const raw = typeof config === "string" ? config : config?.position ?? "below";
269
279
  const [side = "below", suffix] = raw.split("-");
270
280
  const placementMap = { above: "top", below: "bottom", before: "start", after: "end", top: "top", bottom: "bottom", left: "left", right: "right", start: "start", end: "end" };
271
281
  const placement = placementMap[side] ?? "bottom";
272
282
  const align = (typeof config === "object" && config ? config.align : undefined) ?? (suffix === "start" || suffix === "end" || suffix === "top" || suffix === "bottom" ? suffix : "start");
273
- const options = typeof config === "object" && config ? config : undefined;
274
283
  const offset = typeof options?.offset === "number" ? options.offset : typeof options?.offset === "object" ? options.offset.mainAxis : 4;
275
284
  const fallback = (options?.fallbackPositions ?? []).map(value => {
276
285
  const [fallbackSide, fallbackAlign] = value.split("-");
277
286
  return { placement: placementMap[fallbackSide] ?? "bottom", align: fallbackAlign };
278
287
  });
279
- const position = getFloatingPosition(rect, { width: popup.offsetWidth, height: popup.offsetHeight }, placement, direction, offset, undefined, align, fallback, options?.pinned, undefined, undefined, { coverTarget: options?.coverTarget });
288
+ const position = getFloatingPosition(rect, { width: popup.offsetWidth, height: popup.offsetHeight }, placement, direction, offset, viewport, align, fallback, options?.pinned, flipBoundary, overflowBoundary, { coverTarget: options?.coverTarget });
280
289
  popup.dataset.placement = position.placement;
281
290
  popup.style.left = `${position.left}px`;
282
291
  popup.style.top = `${position.top}px`;
@@ -380,7 +389,7 @@ export function defineTagPicker() {
380
389
  this.internals?.setFormValue(values.length && name ? formData : null, JSON.stringify(values));
381
390
  const missing = this.hasAttribute("required") && values.length === 0;
382
391
  try {
383
- this.internals?.setValidity(missing ? { valueMissing: true } : {}, missing ? "Choose at least one option." : "", (this.buttonTrigger() ?? input) ?? undefined);
392
+ this.internals?.setValidity(missing ? { valueMissing: true } : {}, missing ? this.getAttribute("required-message") || "Choose at least one option." : "", (this.buttonTrigger() ?? input) ?? undefined);
384
393
  }
385
394
  catch { /* The input itself retains required semantics as a fallback. */ }
386
395
  }
@@ -391,6 +400,11 @@ export function defineTagPicker() {
391
400
  return;
392
401
  const expanded = this.open || this.hasAttribute("no-popover");
393
402
  input.setAttribute("aria-expanded", String(expanded));
403
+ const invalid = this.getAttribute("aria-invalid");
404
+ if (invalid === null)
405
+ input.removeAttribute("aria-invalid");
406
+ else
407
+ input.setAttribute("aria-invalid", invalid);
394
408
  if (expanded)
395
409
  input.setAttribute("aria-controls", list.id);
396
410
  else
@@ -400,6 +414,10 @@ export function defineTagPicker() {
400
414
  trigger.setAttribute("aria-haspopup", "listbox");
401
415
  trigger.setAttribute("aria-expanded", String(this.open));
402
416
  trigger.setAttribute("aria-required", String(this.hasAttribute("required")));
417
+ if (invalid === null)
418
+ trigger.removeAttribute("aria-invalid");
419
+ else
420
+ trigger.setAttribute("aria-invalid", invalid);
403
421
  if (this.open)
404
422
  trigger.setAttribute("aria-controls", list.id);
405
423
  else
@@ -617,11 +635,11 @@ export function defineTagPicker() {
617
635
  popup.append(list, empty);
618
636
  control.append(selected, buttonSlot, input, popup, secondarySlot, expandSlot);
619
637
  const style = document.createElement("style");
620
- style.textContent = `${base}:host{display:grid;gap:var(--spui-control-gap,6px);min-width:0}label{font-size:14px;font-weight:600;color:var(--spui-ui-muted,var(--spui-semantic-body-text,inherit))}.control{position:relative;display:flex;flex-wrap:wrap;align-items:center;gap:4px;box-sizing:border-box;min-height:var(--spui-control-height,36px);padding:4px 8px;border:1px solid var(--spui-control-border,var(--spui-ui-stroke,var(--spui-semantic-input-border,#8a8886)));border-radius:var(--spui-control-radius,4px);background:var(--spui-control-background,var(--spui-ui-surface,var(--spui-semantic-input-background,#fff)));color:var(--spui-ui-text,inherit)}.control:focus-within{outline:2px solid var(--spui-focus-ring,var(--spui-ui-accent,#0078d4));outline-offset:1px}.selected{display:contents}.chip{display:inline-flex;align-items:center;gap:4px;max-width:100%;padding:2px 5px 2px 8px;border:1px solid var(--spui-base-stroke,var(--spui-ui-stroke,#d1d1d1));border-radius:999px;background:color-mix(in srgb,var(--spui-base-accent,var(--spui-ui-accent,#0078d4)) 12%,var(--spui-base-surface,var(--spui-ui-surface,#fff)));font-size:12px}.chip>span{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.remove{display:grid;place-items:center;flex:none;width:20px;height:20px;padding:0;border:0;border-radius:50%;background:transparent;color:inherit;font:inherit;font-size:16px;cursor:pointer}.remove:hover{background:color-mix(in srgb,currentColor 12%,transparent)}.remove:focus-visible{outline:2px solid var(--spui-focus-ring,var(--spui-ui-accent,#0078d4))}.remove:disabled{opacity:.5;cursor:not-allowed}input{flex:1 1 100px;min-width:72px;width:auto;min-height:28px;padding:2px 4px;border:0;outline:none;background:transparent;color:inherit;font:inherit}input::placeholder{color:var(--spui-ui-muted,#616161)}input:disabled{cursor:not-allowed}ul{position:absolute;z-index:var(--spui-layer-dropdown,20);top:calc(100% + 4px);inset-inline:0;box-sizing:border-box;max-height:240px;overflow:auto;margin:0;padding:4px;list-style:none;border:1px solid var(--spui-ui-stroke,#d1d1d1);border-radius:var(--spui-card-radius,8px);background:var(--spui-ui-surface,#fff);box-shadow:var(--spui-card-shadow,0 4px 14px #0002)}ul[hidden]{display:none}.group-heading{padding:7px 10px 3px;color:var(--spui-ui-muted,inherit);font-size:11px;font-weight:600}li[role=option]{padding:8px 10px;border-radius:var(--spui-control-radius,4px);color:var(--spui-ui-text,inherit);cursor:pointer}li[role=option][data-active=true],li[role=option][aria-selected=true]{background:var(--spui-ui-surface-hover,var(--spui-ui-canvas,#f5f5f5))}li[role=option][aria-disabled=true]{opacity:.5;cursor:not-allowed}.empty{position:absolute;z-index:calc(var(--spui-layer-dropdown,20) + 1);top:calc(100% + 4px);inset-inline:0;box-sizing:border-box;padding:12px;border:1px solid var(--spui-ui-stroke,#d1d1d1);border-radius:var(--spui-card-radius,8px);background:var(--spui-ui-surface,#fff);box-shadow:var(--spui-card-shadow,0 4px 14px #0002);color:var(--spui-ui-muted,inherit)}.empty[hidden]{display:none}:host([disabled]) .control{opacity:.55}@media(forced-colors:active){.control,ul,.empty{border-color:CanvasText}.chip{border-color:CanvasText}li[role=option][data-active=true]{outline:1px solid Highlight}}`;
638
+ style.textContent = `${base}:host{display:grid;gap:var(--spui-control-gap,6px);min-width:0}label{font-size:14px;font-weight:600;color:var(--spui-ui-muted,var(--spui-semantic-body-text,inherit))}.control{position:relative;display:flex;flex-wrap:wrap;align-items:center;gap:4px;box-sizing:border-box;min-height:var(--spui-control-height,36px);padding:4px 8px;border:1px solid var(--spui-control-border,var(--spui-ui-stroke,var(--spui-semantic-input-border,#8a8886)));border-radius:var(--spui-control-radius,4px);background:var(--spui-control-background,var(--spui-ui-surface,var(--spui-semantic-input-background,#fff)));color:var(--spui-ui-text,inherit)}.control:focus-within{border-width:2px;border-color:var(--spui-focus-ring,var(--spui-ui-accent,#0078d4));outline:0;box-shadow:none}.control:has(.remove:focus-visible){border-width:1px;border-color:var(--spui-control-border,var(--spui-ui-stroke,var(--spui-semantic-input-border,#8a8886)))}:host([aria-invalid]:not([aria-invalid=false])) .control{border-color:var(--spui-input-invalid-border,var(--spui-ui-danger,var(--colorPaletteRedBorder2,#c50f1f)))}.selected{display:contents}.chip{display:inline-flex;align-items:center;gap:4px;max-width:100%;padding:2px 5px 2px 8px;border:1px solid var(--spui-base-stroke,var(--spui-ui-stroke,#d1d1d1));border-radius:999px;background:color-mix(in srgb,var(--spui-base-accent,var(--spui-ui-accent,#0078d4)) 12%,var(--spui-base-surface,var(--spui-ui-surface,#fff)));font-size:12px}.chip>span{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.remove{display:grid;place-items:center;flex:none;width:20px;height:20px;padding:0;border:0;border-radius:50%;background:transparent;color:inherit;font:inherit;font-size:16px;cursor:pointer}.remove:hover{background:color-mix(in srgb,currentColor 12%,transparent)}.remove:focus-visible{outline:2px solid var(--spui-focus-ring,var(--spui-ui-accent,#0078d4))}.remove:disabled{opacity:.5;cursor:not-allowed}input{flex:1 1 100px;min-width:72px;width:auto;min-height:28px;padding:2px 4px;border:0;outline:none;background:transparent;color:inherit;font:inherit}input:focus-visible{outline:0}input::placeholder{color:var(--spui-ui-muted,#616161)}input:disabled{cursor:not-allowed}ul{position:absolute;z-index:var(--spui-layer-dropdown,20);top:calc(100% + 4px);inset-inline:0;box-sizing:border-box;max-height:240px;overflow:auto;margin:0;padding:4px;list-style:none;border:1px solid var(--spui-ui-stroke,#d1d1d1);border-radius:var(--spui-card-radius,8px);background:var(--spui-ui-surface,#fff);box-shadow:var(--spui-card-shadow,0 4px 14px #0002)}ul[hidden]{display:none}.group-heading{padding:7px 10px 3px;color:var(--spui-ui-muted,inherit);font-size:11px;font-weight:600}li[role=option]{padding:8px 10px;border-radius:var(--spui-control-radius,4px);color:var(--spui-ui-text,inherit);cursor:pointer}li[role=option][data-active=true],li[role=option][aria-selected=true]{background:var(--spui-ui-surface-hover,var(--spui-ui-canvas,#f5f5f5))}li[role=option][aria-disabled=true]{opacity:.5;cursor:not-allowed}.empty{position:absolute;z-index:calc(var(--spui-layer-dropdown,20) + 1);top:calc(100% + 4px);inset-inline:0;box-sizing:border-box;padding:12px;border:1px solid var(--spui-ui-stroke,#d1d1d1);border-radius:var(--spui-card-radius,8px);background:var(--spui-ui-surface,#fff);box-shadow:var(--spui-card-shadow,0 4px 14px #0002);color:var(--spui-ui-muted,inherit)}.empty[hidden]{display:none}:host([disabled]) .control{opacity:.55}@media(forced-colors:active){.control,ul,.empty{border-color:CanvasText}.control:focus-within{border-color:Highlight}.remove:focus-visible{outline-color:Highlight}:host([aria-invalid]:not([aria-invalid=false])) .control{border-color:CanvasText}:host([aria-invalid]:not([aria-invalid=false])) .control:focus-within{border-color:Highlight}.chip{border-color:CanvasText}li[role=option][data-active=true]{outline:1px solid Highlight}}`;
621
639
  style.textContent += `.option-group{list-style:none;margin:0;padding:0}.option-media{display:inline-flex;align-items:center;justify-content:center;flex:none}.option-media img,.option-media svg{width:24px;height:24px;object-fit:cover}.chip .option-media img,.chip .option-media svg{width:20px;height:20px;border-radius:50%}li[role=option],[role=group] [role=option]{display:flex;align-items:center;gap:8px}.option-group-options [role=option]{padding:8px 10px;border-radius:var(--spui-control-radius,4px);color:var(--spui-ui-text,inherit);cursor:pointer}.option-group-options [role=option][data-active=true],.option-group-options [role=option][aria-selected=true]{background:var(--spui-ui-surface-hover,var(--spui-ui-canvas,#f5f5f5))}.option-group-options [role=option][aria-disabled=true]{opacity:.5;cursor:not-allowed}.option-label{min-width:0;overflow:hidden;text-overflow:ellipsis}.option-secondary{margin-inline-start:auto;color:var(--spui-ui-muted,inherit);font-size:12px;white-space:nowrap}`;
622
- style.textContent += `:host([data-button-trigger]) input{display:none}::slotted(button[slot=button]){align-self:center;display:inline-flex;align-items:center;min-width:32px;min-height:28px;padding:4px 8px;border:1px solid var(--spui-control-border,var(--spui-ui-stroke,#8a8886));border-radius:var(--spui-control-radius,4px);background:var(--spui-control-background,var(--spui-ui-surface,#fff));color:var(--spui-ui-text,inherit);font:inherit;cursor:pointer}::slotted(button[slot=button][data-appearance=filled-darker]){background:var(--spui-ui-surface-sunken,var(--spui-ui-canvas,#f5f5f5))}::slotted(button[slot=button][data-appearance=filled-lighter]){background:var(--spui-ui-surface,var(--spui-semantic-input-background,#fff))}::slotted(button[slot=button][data-appearance=underline]){border:0;border-bottom:1px solid currentColor;border-radius:0;background:transparent}::slotted(button[slot=button][data-size=small]){min-height:24px;padding:2px 6px;font-size:12px}::slotted(button[slot=button][data-size=large]){min-height:40px;padding:6px 12px;font-size:16px}::slotted(button[slot=button]:focus-visible){outline:2px solid var(--spui-focus-ring,var(--spui-ui-accent,#0078d4));outline-offset:1px}:host([disabled])::slotted(button[slot=button]){opacity:.55;cursor:not-allowed}`;
623
- style.textContent += `::slotted(spui-tag-picker-group){display:contents}:host([input-appearance=filled-darker]) .control{background:var(--spui-ui-surface-sunken,var(--spui-ui-canvas,#f5f5f5))}:host([input-appearance=filled-lighter]) .control{background:var(--spui-ui-surface,var(--spui-semantic-input-background,#fff))}:host([input-appearance=underline]) .control{border:0;border-bottom:1px solid var(--spui-control-border,var(--spui-ui-stroke,#8a8886));border-radius:0;background:transparent}`;
624
- style.textContent += `::slotted([slot=secondary-action]){display:inline-flex;align-items:center;flex:none}::slotted([slot=expand-icon]){display:inline-flex;align-items:center;justify-content:center;flex:none}:host([inline]) .popup,:host([no-popover]) .popup{position:absolute;inset-inline:0;top:calc(100% + 4px);left:auto;width:100%!important;max-height:min(240px,calc(100dvh - 8px));z-index:var(--spui-layer-dropdown,20)}`;
640
+ style.textContent += `:host([data-button-trigger]) input{display:none}::slotted(button[slot=button]){align-self:center;display:inline-flex;align-items:center;min-width:32px;min-height:28px;padding:4px 8px;border:1px solid var(--spui-control-border,var(--spui-ui-stroke,#8a8886));border-radius:var(--spui-control-radius,4px);background:var(--spui-control-background,var(--spui-ui-surface,#fff));color:var(--spui-ui-text,inherit);font:inherit;cursor:pointer}::slotted(button[slot=button][data-appearance=filled-darker]){background:var(--spui-ui-surface-sunken,var(--spui-ui-canvas,#f5f5f5))}::slotted(button[slot=button][data-appearance=filled-lighter]){background:var(--spui-ui-surface,var(--spui-semantic-input-background,#fff))}::slotted(button[slot=button][data-appearance=underline]){border:0;border-bottom:1px solid currentColor;border-radius:0;background:transparent}::slotted(button[slot=button][data-size=small]){min-height:24px;padding:2px 6px;font-size:12px}::slotted(button[slot=button][data-size=large]){min-height:40px;padding:6px 12px;font-size:16px}::slotted(button[slot=button]:focus-visible){outline:0!important;outline-offset:0;box-shadow:none!important}:host([disabled])::slotted(button[slot=button]){opacity:.55;cursor:not-allowed}`;
641
+ style.textContent += `::slotted(spui-tag-picker-group){display:contents}:host([input-appearance=filled-darker]) .control{background:var(--spui-ui-surface-sunken,var(--spui-ui-canvas,#f5f5f5))}:host([input-appearance=filled-lighter]) .control{background:var(--spui-ui-surface,var(--spui-semantic-input-background,#fff))}:host([input-appearance=underline]) .control{border:0;border-bottom:1px solid var(--spui-control-border,var(--spui-ui-stroke,#8a8886));border-radius:0;background:transparent}:host([input-appearance=underline]) .control:focus-within{border-bottom-width:2px}:host([input-appearance=underline]) .control:has(.remove:focus-visible){border-bottom-width:1px}`;
642
+ style.textContent += `::slotted([slot=secondary-action]){display:inline-flex;align-items:center;flex:none}::slotted([slot=expand-icon]){display:inline-flex;align-items:center;justify-content:center;flex:none}:host([inline]) .popup,:host([no-popover]) .popup{position:absolute;inset-inline:0;top:calc(100% + 4px);width:100%!important;max-height:min(240px,calc(100dvh - 8px));z-index:var(--spui-layer-dropdown,20)}`;
625
643
  style.textContent += `.popup{position:fixed;inset:auto;z-index:var(--spui-layer-popover,10000);box-sizing:border-box;max-width:calc(100vw - 8px);max-height:min(240px,calc(100dvh - 8px));overflow:auto;margin:0;padding:4px;border:1px solid var(--spui-ui-stroke,#d1d1d1);border-radius:var(--spui-card-radius,8px);background:var(--spui-ui-surface,#fff);color:var(--spui-ui-text,inherit);box-shadow:var(--spui-card-shadow,0 4px 14px #0002)}.popup[hidden]{display:none}.popup ul{position:static;inset:auto;z-index:auto;max-height:none;overflow:visible;margin:0;padding:0;border:0;border-radius:0;background:transparent;box-shadow:none}.popup .empty{position:static;inset:auto;z-index:auto;margin:0;padding:12px;border:0;border-radius:0;background:transparent;box-shadow:none}`;
626
644
  const slot = document.createElement("slot");
627
645
  slot.hidden = true;
@@ -58,8 +58,8 @@ export function defineTextArea() {
58
58
  input.setAttribute(name, value);
59
59
  }
60
60
  const style = document.createElement("style");
61
- style.textContent = `${base}:host{display:grid;gap:var(--spui-control-gap,6px)}label{font-size:14px;font-weight:600;color:var(--spui-ui-muted,var(--spui-semantic-body-text,inherit))}textarea{width:100%;min-height:72px;box-sizing:border-box;padding:var(--spui-control-padding-block,10px) var(--spui-control-padding-inline,12px);border:1px solid var(--spui-control-border,var(--spui-ui-stroke,var(--spui-semantic-input-border,var(--colorNeutralStroke1,#8a8886))));border-radius:var(--spui-control-radius,4px);background:var(--spui-control-background,var(--spui-ui-surface,var(--spui-semantic-input-background,var(--colorNeutralBackground1,#fff))));box-shadow:var(--spui-control-shadow,none);color:var(--spui-ui-text,var(--spui-semantic-body-text,inherit));font:inherit;resize:none}:host([size=small]) textarea{min-height:64px;padding-block:8px;font-size:var(--spui-text-font-size-small,12px)}:host([size=medium]) textarea{min-height:72px}:host([size=large]) textarea{min-height:88px;font-size:var(--spui-text-font-size-large,16px)}:host([appearance=filled-darker]),:host([appearance=filled-darker-shadow]){--spui-control-background:var(--spui-input-filled-darker,var(--spui-ui-surface-hover,var(--colorNeutralBackground3,#f0f0f0)));--spui-control-border:transparent}:host([appearance=filled-lighter]),:host([appearance=filled-lighter-shadow]){--spui-control-background:var(--spui-input-filled-lighter,var(--spui-ui-canvas,var(--colorNeutralBackground2,#fafafa)));--spui-control-border:transparent}:host([appearance=filled-darker-shadow]) textarea,:host([appearance=filled-lighter-shadow]) textarea{box-shadow:var(--spui-input-filled-shadow,var(--shadow2,0 1px 2px rgb(0 0 0 / 20%)))}:host([resize=vertical]) textarea{resize:vertical}:host([resize=horizontal]) textarea{resize:horizontal}:host([resize=both]) textarea{resize:both}textarea:focus-visible{outline:2px solid var(--spui-focus-ring,var(--spui-ui-accent,#0078d4));outline-offset:1px}textarea:disabled{opacity:.55}@media(forced-colors:active){textarea{border-color:FieldText}textarea:focus-visible{outline-color:Highlight}}`;
62
- style.textContent += `textarea[hidden]{display:none}slot[name=textarea]{display:contents}slot[name=textarea]::slotted(textarea){width:100%;min-height:72px;box-sizing:border-box;padding:var(--spui-control-padding-block,10px) var(--spui-control-padding-inline,12px);border:1px solid var(--spui-control-border,var(--spui-ui-stroke,var(--spui-semantic-input-border,var(--colorNeutralStroke1,#8a8886))));border-radius:var(--spui-control-radius,4px);background:var(--spui-control-background,var(--spui-ui-surface,var(--spui-semantic-input-background,var(--colorNeutralBackground1,#fff))));box-shadow:var(--spui-control-shadow,none);color:var(--spui-ui-text,var(--spui-semantic-body-text,inherit));font:inherit;resize:none}:host([size=small]) slot[name=textarea]::slotted(textarea){min-height:64px;padding-block:8px;font-size:var(--spui-text-font-size-small,12px)}:host([size=large]) slot[name=textarea]::slotted(textarea){min-height:88px;font-size:var(--spui-text-font-size-large,16px)}:host([resize=vertical]) slot[name=textarea]::slotted(textarea){resize:vertical}:host([resize=horizontal]) slot[name=textarea]::slotted(textarea){resize:horizontal}:host([resize=both]) slot[name=textarea]::slotted(textarea){resize:both}slot[name=textarea]::slotted(textarea:focus-visible){outline:2px solid var(--spui-focus-ring,var(--spui-ui-accent,#0078d4));outline-offset:1px}`;
61
+ style.textContent = `${base}:host{display:grid;gap:var(--spui-control-gap,6px)}label{font-size:14px;font-weight:600;color:var(--spui-ui-muted,var(--spui-semantic-body-text,inherit))}textarea{width:100%;min-height:72px;box-sizing:border-box;padding:var(--spui-control-padding-block,10px) var(--spui-control-padding-inline,12px);border:1px solid var(--spui-control-border,var(--spui-ui-stroke,var(--spui-semantic-input-border,var(--colorNeutralStroke1,#8a8886))));border-radius:var(--spui-control-radius,4px);background:var(--spui-control-background,var(--spui-ui-surface,var(--spui-semantic-input-background,var(--colorNeutralBackground1,#fff))));box-shadow:var(--spui-control-shadow,none);color:var(--spui-ui-text,var(--spui-semantic-body-text,inherit));font:inherit;resize:none}:host([size=small]) textarea{min-height:64px;padding-block:8px;font-size:var(--spui-text-font-size-small,12px)}:host([size=medium]) textarea{min-height:72px}:host([size=large]) textarea{min-height:88px;font-size:var(--spui-text-font-size-large,16px)}:host([appearance=filled-darker]),:host([appearance=filled-darker-shadow]){--spui-control-background:var(--spui-input-filled-darker,var(--spui-ui-surface-hover,var(--colorNeutralBackground3,#f0f0f0)));--spui-control-border:transparent}:host([appearance=filled-lighter]),:host([appearance=filled-lighter-shadow]){--spui-control-background:var(--spui-input-filled-lighter,var(--spui-ui-canvas,var(--colorNeutralBackground2,#fafafa)));--spui-control-border:transparent}:host([appearance=filled-darker-shadow]) textarea,:host([appearance=filled-lighter-shadow]) textarea{box-shadow:var(--spui-input-filled-shadow,var(--shadow2,0 1px 2px rgb(0 0 0 / 20%)))}:host([resize=vertical]) textarea{resize:vertical}:host([resize=horizontal]) textarea{resize:horizontal}:host([resize=both]) textarea{resize:both}textarea:focus-visible{border-width:2px;border-color:var(--spui-focus-ring,var(--spui-ui-accent,#0078d4));outline:0}textarea[aria-invalid]:not([aria-invalid=false]){border-color:var(--spui-input-invalid-border,var(--spui-ui-danger,var(--colorPaletteRedBorder2,#c50f1f)))}textarea:disabled{opacity:.55}@media(forced-colors:active){textarea{border-color:FieldText}textarea[aria-invalid]:not([aria-invalid=false]){border-color:CanvasText}textarea:focus-visible{border-color:Highlight;outline:0}textarea[aria-invalid]:not([aria-invalid=false]):focus-visible{border-color:Highlight}}`;
62
+ style.textContent += `textarea[hidden]{display:none}slot[name=textarea]{display:contents}slot[name=textarea]::slotted(textarea){width:100%;min-height:72px;box-sizing:border-box;padding:var(--spui-control-padding-block,10px) var(--spui-control-padding-inline,12px);border:1px solid var(--spui-control-border,var(--spui-ui-stroke,var(--spui-semantic-input-border,var(--colorNeutralStroke1,#8a8886))));border-radius:var(--spui-control-radius,4px);background:var(--spui-control-background,var(--spui-ui-surface,var(--spui-semantic-input-background,var(--colorNeutralBackground1,#fff))));box-shadow:var(--spui-control-shadow,none);color:var(--spui-ui-text,var(--spui-semantic-body-text,inherit));font:inherit;resize:none}:host([size=small]) slot[name=textarea]::slotted(textarea){min-height:64px;padding-block:8px;font-size:var(--spui-text-font-size-small,12px)}:host([size=large]) slot[name=textarea]::slotted(textarea){min-height:88px;font-size:var(--spui-text-font-size-large,16px)}:host([resize=vertical]) slot[name=textarea]::slotted(textarea){resize:vertical}:host([resize=horizontal]) slot[name=textarea]::slotted(textarea){resize:horizontal}:host([resize=both]) slot[name=textarea]::slotted(textarea){resize:both}slot[name=textarea]::slotted(textarea:focus-visible){border-width:2px!important;border-color:var(--spui-focus-ring,var(--spui-ui-accent,#0078d4))!important;outline:0!important;outline-offset:0;box-shadow:none!important}slot[name=textarea]::slotted(textarea[aria-invalid]:not([aria-invalid=false])){border-color:var(--spui-input-invalid-border,var(--spui-ui-danger,var(--colorPaletteRedBorder2,#c50f1f)))!important}@media(forced-colors:active){slot[name=textarea]::slotted(textarea){border-color:FieldText}slot[name=textarea]::slotted(textarea:focus-visible){border-color:Highlight!important}slot[name=textarea]::slotted(textarea[aria-invalid]:not([aria-invalid=false]):focus-visible){border-color:Highlight!important}slot[name=textarea]::slotted(textarea[aria-invalid]:not([aria-invalid=false])){border-color:CanvasText!important}}`;
63
63
  style.textContent += `:host([appearance=filled-darker-shadow]) slot[name=textarea]::slotted(textarea),:host([appearance=filled-lighter-shadow]) slot[name=textarea]::slotted(textarea){box-shadow:var(--spui-input-filled-shadow,var(--shadow2,0 1px 2px rgb(0 0 0 / 20%)))}`;
64
64
  const controlSlot = document.createElement("slot");
65
65
  controlSlot.name = "textarea";
@@ -1,3 +1,4 @@
1
+ import { directionByLanguage } from "./shared.js";
1
2
  import { defineToast } from "./toast.js";
2
3
  export function defineToaster() {
3
4
  if (customElements.get("spui-toaster"))
@@ -348,7 +349,7 @@ export function defineToaster() {
348
349
  this.politeRegion.setAttribute("aria-atomic", "true");
349
350
  announcer.append(this.assertiveRegion, this.politeRegion);
350
351
  const style = this.ownerDocument.createElement("style");
351
- style.textContent = `:host{position:fixed;z-index:var(--spui-toaster-z-index,var(--spui-layer-toast,10000));display:flex;flex-direction:column;gap:var(--spui-toaster-gap,10px);box-sizing:border-box;inline-size:min(100vw,460px);max-block-size:calc(100dvh - env(safe-area-inset-top,0px) - env(safe-area-inset-bottom,0px));overflow:auto;overscroll-behavior:contain;padding:calc(16px + env(safe-area-inset-top,0px)) calc(16px + env(safe-area-inset-right,0px)) calc(16px + env(safe-area-inset-bottom,0px)) calc(16px + env(safe-area-inset-left,0px));pointer-events:none}:host([position=top-start]){inset-block-start:0;inset-inline-start:0;align-items:flex-start}:host([position=top-end]){inset-block-start:0;inset-inline-end:0;align-items:flex-end}:host([position=bottom-start]){inset-block-end:0;inset-inline-start:0;align-items:flex-start;flex-direction:column-reverse}:host([position=bottom-end]){inset-block-end:0;inset-inline-end:0;align-items:flex-end;flex-direction:column-reverse}slot{display:contents}::slotted(spui-toast){max-inline-size:100%}.announcer{position:absolute;inline-size:1px;block-size:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);white-space:nowrap;clip-path:inset(50%);border:0}:host([inline]){position:relative;inset:auto;inline-size:100%;max-block-size:none;overflow:visible;padding:0}:host([inline][position^=bottom]){flex-direction:column}`;
352
+ style.textContent = `${directionByLanguage}:host{position:fixed;z-index:var(--spui-toaster-z-index,var(--spui-layer-toast,10000));display:flex;flex-direction:column;gap:var(--spui-toaster-gap,10px);box-sizing:border-box;inline-size:min(100vw,460px);max-block-size:calc(100dvh - env(safe-area-inset-top,0px) - env(safe-area-inset-bottom,0px));overflow:auto;overscroll-behavior:contain;padding:calc(16px + env(safe-area-inset-top,0px)) calc(16px + env(safe-area-inset-right,0px)) calc(16px + env(safe-area-inset-bottom,0px)) calc(16px + env(safe-area-inset-left,0px));pointer-events:none}:host([position=top-start]){inset-block-start:0;inset-inline-start:0;align-items:flex-start}:host([position=top-end]){inset-block-start:0;inset-inline-end:0;align-items:flex-end}:host([position=bottom-start]){inset-block-end:0;inset-inline-start:0;align-items:flex-start;flex-direction:column-reverse}:host([position=bottom-end]){inset-block-end:0;inset-inline-end:0;align-items:flex-end;flex-direction:column-reverse}slot{display:contents}::slotted(spui-toast){max-inline-size:100%}.announcer{position:absolute;inline-size:1px;block-size:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);white-space:nowrap;clip-path:inset(50%);border:0}:host([inline]){position:relative;inset:auto;inline-size:100%;max-block-size:none;overflow:visible;padding:0}:host([inline][position^=bottom]){flex-direction:column}`;
352
353
  shadow.replaceChildren(style, this.toastSlot, announcer);
353
354
  }
354
355
  }
@@ -1,4 +1,5 @@
1
1
  import { getFloatingPosition } from "./floating-position.js";
2
+ import { getDirectionFromLanguage } from "./shared.js";
2
3
  const nextId = (() => { let value = 0; return () => `spui-tooltip-${++value}`; })();
3
4
  let activeTooltip;
4
5
  function rectEdges(rect) {
@@ -12,6 +13,22 @@ function parentElement(element) {
12
13
  const root = element.getRootNode();
13
14
  return root instanceof ShadowRoot ? root.host : null;
14
15
  }
16
+ function getLayoutDirection(element) {
17
+ let explicitDirection;
18
+ let language;
19
+ for (let current = element; current; current = parentElement(current)) {
20
+ if (!explicitDirection && current.hasAttribute("dir"))
21
+ explicitDirection = current;
22
+ if (!language && (current.hasAttribute("lang") || current.hasAttribute("xml:lang")))
23
+ language = current;
24
+ }
25
+ if (explicitDirection)
26
+ return explicitDirection.ownerDocument.defaultView?.getComputedStyle(explicitDirection).direction === "rtl" ? "rtl" : "ltr";
27
+ const derived = getDirectionFromLanguage(language?.getAttribute("lang") ?? language?.getAttribute("xml:lang"));
28
+ if (derived)
29
+ return derived;
30
+ return element.ownerDocument.defaultView?.getComputedStyle(element).direction === "rtl" ? "rtl" : "ltr";
31
+ }
15
32
  function intersectRects(rects) {
16
33
  if (!rects.length)
17
34
  return undefined;
@@ -277,7 +294,7 @@ export function defineTooltip() {
277
294
  const targetContext = target && "contextElement" in target ? target.contextElement : target && "nodeType" in target ? target : undefined;
278
295
  const targetRect = target?.getBoundingClientRect();
279
296
  const anchor = targetRect ?? trigger.getBoundingClientRect();
280
- const direction = (targetContext && getComputedStyle(targetContext).direction) || (trigger && getComputedStyle(trigger).direction) || getComputedStyle(this).direction;
297
+ const direction = getLayoutDirection(targetContext ?? trigger ?? this);
281
298
  const rtl = direction === "rtl";
282
299
  const [requested, align, rawPosition] = this.getRequestedPosition(rtl ? "rtl" : "ltr");
283
300
  const configuredOffset = options?.offset;
@@ -61,7 +61,7 @@ export function defineTree() {
61
61
  if (!rows.some(row => row.key === this.activeKey))
62
62
  this.activeKey = rows[0]?.key ?? "";
63
63
  this.root.replaceChildren();
64
- this.root.setAttribute("aria-label", this.getAttribute("label") || this.getAttribute("aria-label") || "Tree");
64
+ this.root.setAttribute("aria-label", this.getAttribute("aria-label") || this.getAttribute("label") || "Tree");
65
65
  if (this.mode() === "multiple")
66
66
  this.root.setAttribute("aria-multiselectable", "true");
67
67
  else
@@ -7,6 +7,7 @@ export { defineSwatchPicker, defineColorSwatch, defineImageSwatch, defineEmptySw
7
7
  export { createTableColumn, defineTable, defineTableHeader, defineTableBody, defineTableRow, defineTableHeaderCell, defineTableCell, defineTableCellLayout, defineTableCellActions, defineTableResizeHandle, defineTableSelectionCell, type CreateTableColumnOptions, type TableColumnDefinition, type TableColumnId } from "./elements/table.js";
8
8
  export type { TextFont, TextSize, TextTag, TextWeight } from "./elements/text.js";
9
9
  export { defineButton } from "./elements/button.js";
10
+ export { defineSharePointField, type SharePointFieldElement, type SharePointFieldOption, type SharePointFieldValueChangeDetail } from "./elements/sharepoint-fields.js";
10
11
  export { defineButtonGroup } from "./elements/button-group.js";
11
12
  export { defineCompoundButton, defineMenuButton, defineSplitButton, defineToggleButton } from "./elements/button-variants.js";
12
13
  export type { ButtonAppearance, ButtonShape, ButtonSize } from "./elements/button.js";
@@ -34,7 +35,7 @@ export type { SpinButtonAppearance, SpinButtonSize, SpinButtonChangeData } from
34
35
  export { defineSlider } from "./elements/slider.js";
35
36
  export { defineDatePicker } from "./elements/date-picker.js";
36
37
  export { defineCombobox } from "./elements/combobox.js";
37
- export { defineRichTextEditor, type SharePointRichTextEditorElement } from "./elements/rich-text-editor.js";
38
+ export { defineRichTextEditor, getRichTextEditorFieldOptions, type SharePointMultiLineField, type SharePointRichTextEditorElement, type RichTextEditorLink, type RichTextEditorLinkPicker } from "./elements/rich-text-editor.js";
38
39
  export { defineAlert, type AlertAppearance } from "./elements/alert.js";
39
40
  export { defineSkeleton, defineSkeletonItem, type SkeletonAnimation, type SkeletonAppearance, type SkeletonItemSize, type SkeletonShape } from "./elements/skeleton.js";
40
41
  export { defineLink } from "./elements/link.js";
@@ -46,7 +47,7 @@ export { defineAvatarGroupItem, defineAvatarGroupPopover } from "./elements/avat
46
47
  export { definePersona, type PersonaPresence, type PersonaSize } from "./elements/persona.js";
47
48
  export { defineVirtualList, type VirtualListDataSource, type VirtualListItemRenderer, type SharePointVirtualListElement } from "./elements/virtual-list.js";
48
49
  export { defineDataGrid, type DataGridCellRenderer, type DataGridCellsEditHandler, type DataGridRowHeightGetter, type DataGridSourceSelectionHandler, type SharePointDataGridElement } from "./elements/data-grid.js";
49
- export { clampDataGridRowHeight, fitDataGridColumnWidths, formatDataGridClipboard, getDataGridColumnSizing, isDataGridRowSelected, parseDataGridClipboard, parseDataGridClipboardValue, setDataGridRowSelected, writeDataGridClipboardText, type DataGridCellEdit, type DataGridClipboardColumn, type DataGridColumn, type DataGridColumnSizingOption, type DataGridColumnSizingOptions, type DataGridColumnWidths, type DataGridDataSource, type DataGridDataSourceRow, type DataGridSelectionModel, type DataGridEditValue, type DataGridFocusMode, type DataGridSelectionAppearance, type DataGridSort, type DataGridSortDirection } from "./elements/data-grid-model.js";
50
+ export { clampDataGridRowHeight, fitDataGridColumnWidths, formatDataGridClipboard, getDataGridColumnSizing, isDataGridRowSelected, parseDataGridClipboard, parseDataGridClipboardValue, setDataGridRowSelected, writeDataGridClipboardText, type DataGridCellEdit, type DataGridCellEditError, type DataGridClipboardColumn, type DataGridColumn, type DataGridColumnSizingOption, type DataGridColumnSizingOptions, type DataGridColumnWidths, type DataGridDataSource, type DataGridDataSourceRow, type DataGridSelectionModel, type DataGridEditValue, type DataGridFocusMode, type DataGridSelectionAppearance, type DataGridSort, type DataGridSortDirection } from "./elements/data-grid-model.js";
50
51
  export { defineTree, type TreeCheckedItem, type TreeItemRenderer } from "./elements/tree.js";
51
52
  export { type TreeNode, type VisibleTreeNode } from "./elements/tree-model.js";
52
53
  export { defineInteractionTag, defineInteractionTagPrimary, defineInteractionTagSecondary, defineTag, defineTagGroup, type InteractionTagSelectData, type SharePointTagGroupElement, type TagAppearance, type TagGroupSelectData, type TagShape, type TagSize } from "./elements/tags.js";
package/dist/elements.js CHANGED
@@ -57,6 +57,7 @@ import { defineCarousel } from "./elements/carousel.js";
57
57
  import { defineOverflow } from "./elements/overflow.js";
58
58
  import { defineSwatchPicker } from "./elements/swatch-picker.js";
59
59
  import { defineTable } from "./elements/table.js";
60
+ import { defineSharePointField } from "./elements/sharepoint-fields.js";
60
61
  export { createLabel, getLabelStyle } from "./elements/label.js";
61
62
  export { defineInfoButton, createInfoLabel } from "./elements/info.js";
62
63
  export { defineCarousel, defineCarouselCard, defineCarouselNav, defineCarouselNavButton, defineCarouselNavImageButton, defineCarouselButton, defineCarouselAutoplayButton, defineCarouselNavContainer, defineCarouselSlider, defineCarouselViewport } from "./elements/carousel.js";
@@ -64,6 +65,7 @@ export { defineOverflow, defineOverflowItem, defineOverflowDivider } from "./ele
64
65
  export { defineSwatchPicker, defineColorSwatch, defineImageSwatch, defineEmptySwatch, defineSwatchPickerRow } from "./elements/swatch-picker.js";
65
66
  export { createTableColumn, defineTable, defineTableHeader, defineTableBody, defineTableRow, defineTableHeaderCell, defineTableCell, defineTableCellLayout, defineTableCellActions, defineTableResizeHandle, defineTableSelectionCell } from "./elements/table.js";
66
67
  export { defineButton } from "./elements/button.js";
68
+ export { defineSharePointField } from "./elements/sharepoint-fields.js";
67
69
  export { defineButtonGroup } from "./elements/button-group.js";
68
70
  export { defineCompoundButton, defineMenuButton, defineSplitButton, defineToggleButton } from "./elements/button-variants.js";
69
71
  export { defineInput } from "./elements/input.js";
@@ -88,7 +90,7 @@ export { defineSpinButton } from "./elements/spin-button.js";
88
90
  export { defineSlider } from "./elements/slider.js";
89
91
  export { defineDatePicker } from "./elements/date-picker.js";
90
92
  export { defineCombobox } from "./elements/combobox.js";
91
- export { defineRichTextEditor } from "./elements/rich-text-editor.js";
93
+ export { defineRichTextEditor, getRichTextEditorFieldOptions } from "./elements/rich-text-editor.js";
92
94
  export { defineAlert } from "./elements/alert.js";
93
95
  export { defineSkeleton, defineSkeletonItem } from "./elements/skeleton.js";
94
96
  export { defineLink } from "./elements/link.js";
@@ -155,6 +157,7 @@ export function defineSharePointUIElements() {
155
157
  defineDatePicker();
156
158
  defineCombobox();
157
159
  defineRichTextEditor();
160
+ defineSharePointField();
158
161
  defineAlert();
159
162
  defineSkeleton();
160
163
  defineLink();
package/dist/index.d.ts CHANGED
@@ -1,5 +1,6 @@
1
1
  export { defineSharePointUIElements } from "./elements.js";
2
2
  export { defineButton } from "./elements/button.js";
3
+ export { defineSharePointField, type SharePointFieldElement, type SharePointFieldOption, type SharePointFieldValueChangeDetail } from "./elements/sharepoint-fields.js";
3
4
  export { defineButtonGroup } from "./elements/button-group.js";
4
5
  export { defineCompoundButton, defineMenuButton, defineSplitButton, defineToggleButton } from "./elements/button-variants.js";
5
6
  export type { ButtonAppearance, ButtonShape, ButtonSize } from "./elements/button.js";
@@ -16,7 +17,7 @@ export { defineToolbar, defineToolbarGroup, defineToolbarSeparator, defineToolba
16
17
  export { defineCarousel, defineCarouselCard, defineCarouselNav, defineCarouselNavButton, defineCarouselNavImageButton, defineCarouselButton, defineCarouselAutoplayButton, defineCarouselNavContainer, defineCarouselSlider, defineCarouselViewport } from "./elements/carousel.js";
17
18
  export type { CarouselIndexChangeData, CarouselIndexChangeSource } from "./elements/carousel.js";
18
19
  export type { CarouselAlign, CarouselAppearance, CarouselMotion, CarouselAnnouncerFunction, SharePointCarouselElement, SharePointCarouselCardElement, SharePointCarouselNavButtonElement, SharePointCarouselButtonElement, SharePointCarouselAutoplayButtonElement, SharePointCarouselSliderElement } from "./elements/carousel.js";
19
- export { defineOverflow, defineOverflowItem, defineOverflowDivider, type OverflowAxis, type OverflowState } from "./elements/overflow.js";
20
+ export { defineOverflow, defineOverflowItem, defineOverflowDivider, type OverflowAxis, type OverflowDensity, type OverflowState } from "./elements/overflow.js";
20
21
  export { defineSwatchPicker, defineColorSwatch, defineImageSwatch, defineEmptySwatch, defineSwatchPickerRow } from "./elements/swatch-picker.js";
21
22
  export { createTableColumn, defineTable, defineTableHeader, defineTableBody, defineTableRow, defineTableHeaderCell, defineTableCell, defineTableCellLayout, defineTableCellActions, defineTableResizeHandle, defineTableSelectionCell, type CreateTableColumnOptions, type TableColumnDefinition, type TableColumnId } from "./elements/table.js";
22
23
  export { defineNav, defineNavItem, defineAppItem, defineAppItemStatic, defineHamburger, defineNavDrawer, defineNavDrawerBody, defineNavDrawerFooter, defineNavDrawerHeader, defineSplitNavItem, defineNavCategory, defineNavCategoryItem, defineNavSubItemGroup, defineNavSubItem, defineNavDivider, defineNavSectionHeader, type NavItemSelectData, type NavCategoryToggleData } from "./elements/nav.js";
@@ -43,11 +44,12 @@ export type { SpinButtonAppearance, SpinButtonSize, SpinButtonChangeData } from
43
44
  export { defineSlider } from "./elements/slider.js";
44
45
  export { defineDatePicker } from "./elements/date-picker.js";
45
46
  export { defineCombobox } from "./elements/combobox.js";
46
- export { defineRichTextEditor, type SharePointRichTextEditorElement } from "./elements/rich-text-editor.js";
47
+ export { defineRichTextEditor, getRichTextEditorFieldOptions, type SharePointMultiLineField, type SharePointRichTextEditorElement, type RichTextEditorImageUploadResult, type RichTextEditorImageUploader, type RichTextEditorLink, type RichTextEditorLinkPicker } from "./elements/rich-text-editor.js";
47
48
  export { defineAlert, type AlertAppearance } from "./elements/alert.js";
48
49
  export { defineSkeleton, defineSkeletonItem, type SkeletonAnimation, type SkeletonAppearance, type SkeletonItemSize, type SkeletonShape } from "./elements/skeleton.js";
49
50
  export { DEFAULT_ACCENT, getSharePointUIStyleTokens, type SharePointUIAppearance, type SharePointUIBaseAppearance, type SharePointUIDensity, type SharePointUIStyleTokens } from "./appearance.js";
50
- export { applySharePointTheme, composeSharePointUIDesignThemes, getSharePointUIDesignTokens, type SharePointTheme, type FluentThemeTokens, type SharePointUIDesignTheme, type SharePointUIThemeOptions } from "./theme.js";
51
+ export { applySharePointTheme, composeSharePointUIDesignThemes, getSharePointUIDesignTokens, getSharePointThemeColorPresets, type SharePointThemeColorPreset, type SharePointTheme, type FluentThemeTokens, type SharePointUIDesignTheme, type SharePointUIThemeOptions } from "./theme.js";
52
+ export { getSharePointFieldAdapter, getSharePointFieldMetadataUrl, getSharePointListItemUrl, getSharePointLookupOptionsUrl, getSharePointNextPageUrl, serializeSharePointLookupValue, serializeSharePointChoiceValue, serializeSharePointFieldValue, serializeSharePointFieldValues, type SharePointFieldAdapter, type SharePointFieldControl, type SharePointFieldMetadata, type SharePointLookupId, type SharePointLookupUpdate, type SharePointLookupValue, type SharePointChoiceValue, type SharePointChoiceUpdate, type SharePointFieldValue, type SharePointFieldValues, type SharePointFieldUpdate, type SharePointFieldUpdateValue, type SharePointUrlValue } from "./sharepoint-fields.js";
51
53
  export { defineLink } from "./elements/link.js";
52
54
  export { defineDivider, type DividerAppearance } from "./elements/divider.js";
53
55
  export { defineAccordion, defineAccordionHeader, defineAccordionPanel, type AccordionItemValue, type AccordionNavigation, type AccordionToggleData } from "./elements/accordion.js";
@@ -57,7 +59,7 @@ export { defineAvatarGroupItem, defineAvatarGroupPopover } from "./elements/avat
57
59
  export { definePersona, type PersonaPresence, type PersonaSize } from "./elements/persona.js";
58
60
  export { defineVirtualList, type VirtualListDataSource, type VirtualListItemRenderer, type SharePointVirtualListElement } from "./elements/virtual-list.js";
59
61
  export { defineDataGrid, type DataGridCellRenderer, type DataGridCellsEditHandler, type DataGridRowHeightGetter, type DataGridSourceSelectionHandler, type SharePointDataGridElement } from "./elements/data-grid.js";
60
- export { clampDataGridRowHeight, fitDataGridColumnWidths, formatDataGridClipboard, getDataGridColumnSizing, getDataGridGroupKey, isDataGridRowSelected, parseDataGridClipboard, parseDataGridClipboardValue, setDataGridRowSelected, writeDataGridClipboardText, type DataGridCellEdit, type DataGridClipboardColumn, type DataGridColumn, type DataGridColumnSizingOption, type DataGridColumnSizingOptions, type DataGridColumnWidths, type DataGridDataSource, type DataGridDataSourceRow, type DataGridSelectionModel, type DataGridEditValue, type DataGridFocusMode, type DataGridGroup, type DataGridSelectionAppearance, type DataGridSort, type DataGridSortDirection, type DataGridSortState } from "./elements/data-grid-model.js";
62
+ export { clampDataGridRowHeight, fitDataGridColumnWidths, formatDataGridClipboard, getDataGridColumnSizing, getDataGridGroupKey, isDataGridRowSelected, parseDataGridClipboard, parseDataGridClipboardValue, setDataGridRowSelected, writeDataGridClipboardText, type DataGridCellEdit, type DataGridCellEditError, type DataGridClipboardColumn, type DataGridColumn, type DataGridColumnSizingOption, type DataGridColumnSizingOptions, type DataGridColumnWidths, type DataGridDataSource, type DataGridDataSourceRow, type DataGridSelectionModel, type DataGridEditValue, type DataGridFocusMode, type DataGridGroup, type DataGridSelectionAppearance, type DataGridSort, type DataGridSortDirection, type DataGridSortState } from "./elements/data-grid-model.js";
61
63
  export { defineTree, type TreeCheckedItem, type TreeItemRenderer } from "./elements/tree.js";
62
64
  export { type TreeNode, type VisibleTreeNode } from "./elements/tree-model.js";
63
65
  export { defineInteractionTag, defineInteractionTagPrimary, defineInteractionTagSecondary, defineTag, defineTagGroup, type InteractionTagSelectData, type SharePointTagGroupElement, type TagAppearance, type TagGroupSelectData, type TagShape, type TagSize } from "./elements/tags.js";
package/dist/index.js CHANGED
@@ -1,5 +1,6 @@
1
1
  export { defineSharePointUIElements } from "./elements.js";
2
2
  export { defineButton } from "./elements/button.js";
3
+ export { defineSharePointField } from "./elements/sharepoint-fields.js";
3
4
  export { defineButtonGroup } from "./elements/button-group.js";
4
5
  export { defineCompoundButton, defineMenuButton, defineSplitButton, defineToggleButton } from "./elements/button-variants.js";
5
6
  export { defineInput } from "./elements/input.js";
@@ -37,11 +38,12 @@ export { defineSpinButton } from "./elements/spin-button.js";
37
38
  export { defineSlider } from "./elements/slider.js";
38
39
  export { defineDatePicker } from "./elements/date-picker.js";
39
40
  export { defineCombobox } from "./elements/combobox.js";
40
- export { defineRichTextEditor } from "./elements/rich-text-editor.js";
41
+ export { defineRichTextEditor, getRichTextEditorFieldOptions } from "./elements/rich-text-editor.js";
41
42
  export { defineAlert } from "./elements/alert.js";
42
43
  export { defineSkeleton, defineSkeletonItem } from "./elements/skeleton.js";
43
44
  export { DEFAULT_ACCENT, getSharePointUIStyleTokens } from "./appearance.js";
44
- export { applySharePointTheme, composeSharePointUIDesignThemes, getSharePointUIDesignTokens } from "./theme.js";
45
+ export { applySharePointTheme, composeSharePointUIDesignThemes, getSharePointUIDesignTokens, getSharePointThemeColorPresets } from "./theme.js";
46
+ export { getSharePointFieldAdapter, getSharePointFieldMetadataUrl, getSharePointListItemUrl, getSharePointLookupOptionsUrl, getSharePointNextPageUrl, serializeSharePointLookupValue, serializeSharePointChoiceValue, serializeSharePointFieldValue, serializeSharePointFieldValues } from "./sharepoint-fields.js";
45
47
  export { defineLink } from "./elements/link.js";
46
48
  export { defineDivider } from "./elements/divider.js";
47
49
  export { defineAccordion, defineAccordionHeader, defineAccordionPanel } from "./elements/accordion.js";