@kodaris/krubble-components 1.0.2 → 1.0.4

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.
@@ -85,6 +85,14 @@
85
85
  "module": "./dialog/dialog.js"
86
86
  }
87
87
  },
88
+ {
89
+ "kind": "js",
90
+ "name": "KRSnackbar",
91
+ "declaration": {
92
+ "name": "KRSnackbar",
93
+ "module": "./snackbar/snackbar.js"
94
+ }
95
+ },
88
96
  {
89
97
  "kind": "js",
90
98
  "name": "KRTextField",
@@ -110,19 +118,19 @@
110
118
  {
111
119
  "kind": "variable",
112
120
  "name": "KRAccordion",
113
- "default": "class KRAccordion extends i$1 { constructor() { super(...arguments); /** * Section header text */ this.header = ''; /** * Whether the accordion is expanded */ this.expanded = false; } toggle() { this.expanded = !this.expanded; } render() { return x ` <div class=\"header\" @click=${this.toggle}> <span class=\"header__title\">${this.header}</span> <svg class=\"header__icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"> <path d=\"M6 9l6 6 6-6\"/> </svg> </div> <div class=\"content\"> <div class=\"content__inner\"> <div class=\"content__body\"> <slot></slot> </div> </div> </div> `; } }",
121
+ "default": "class KRAccordion extends i$1 { constructor() { super(...arguments); /** * Section header text */ this.header = ''; /** * Whether the accordion is expanded */ this.expanded = false; } toggle() { this.expanded = !this.expanded; } render() { return b ` <div class=\"header\" @click=${this.toggle}> <span class=\"header__title\">${this.header}</span> <svg class=\"header__icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"> <path d=\"M6 9l6 6 6-6\"/> </svg> </div> <div class=\"content\"> <div class=\"content__inner\"> <div class=\"content__body\"> <slot></slot> </div> </div> </div> `; } }",
114
122
  "description": "Accordion component for collapsible content sections.\n\n## Usage\n```html\n<kr-accordion header=\"Basic Information\" expanded>\n <div>Content here</div>\n</kr-accordion>\n```"
115
123
  },
116
124
  {
117
125
  "kind": "variable",
118
126
  "name": "KRAlert",
119
- "default": "class KRAlert extends i$1 { constructor() { super(...arguments); /** * The alert type/severity */ this.type = 'info'; /** * Whether the alert can be dismissed */ this.dismissible = false; /** * Whether the alert is visible */ this.visible = true; } /** Handles dismiss button click */ _handleDismiss() { this.visible = false; this.dispatchEvent(new CustomEvent('dismiss', { bubbles: true, composed: true })); } render() { const icons = { info: x `<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M18 10a8 8 0 11-16 0 8 8 0 0116 0zm-7-4a1 1 0 11-2 0 1 1 0 012 0zM9 9a1 1 0 000 2v3a1 1 0 001 1h1a1 1 0 100-2v-3a1 1 0 00-1-1H9z\" clip-rule=\"evenodd\"/></svg>`, success: x `<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M10 18a8 8 0 100-16 8 8 0 000 16zm3.707-9.293a1 1 0 00-1.414-1.414L9 10.586 7.707 9.293a1 1 0 00-1.414 1.414l2 2a1 1 0 001.414 0l4-4z\" clip-rule=\"evenodd\"/></svg>`, warning: x `<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M8.257 3.099c.765-1.36 2.722-1.36 3.486 0l5.58 9.92c.75 1.334-.213 2.98-1.742 2.98H4.42c-1.53 0-2.493-1.646-1.743-2.98l5.58-9.92zM11 13a1 1 0 11-2 0 1 1 0 012 0zm-1-8a1 1 0 00-1 1v3a1 1 0 002 0V6a1 1 0 00-1-1z\" clip-rule=\"evenodd\"/></svg>`, error: x `<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M10 18a8 8 0 100-16 8 8 0 000 16zM8.707 7.293a1 1 0 00-1.414 1.414L8.586 10l-1.293 1.293a1 1 0 101.414 1.414L10 11.414l1.293 1.293a1 1 0 001.414-1.414L11.414 10l1.293-1.293a1 1 0 00-1.414-1.414L10 8.586 8.707 7.293z\" clip-rule=\"evenodd\"/></svg>`, }; return x ` <div class=${e$1({ 'alert': true, ['alert--' + this.type]: true, 'alert--hidden': !this.visible })} role=\"alert\" > ${icons[this.type]} <div class=\"content\"> ${this.header ? x `<h4 class=\"header\">${this.header}</h4>` : E} <div class=\"message\"> <slot></slot> </div> </div> ${this.dismissible ? x ` <button class=\"dismiss\" type=\"button\" aria-label=\"Dismiss alert\" @click=${this._handleDismiss} > <svg viewBox=\"0 0 20 20\" fill=\"currentColor\" width=\"16\" height=\"16\"> <path fill-rule=\"evenodd\" d=\"M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z\" clip-rule=\"evenodd\"/> </svg> </button> ` : E} </div> `; } }",
127
+ "default": "class KRAlert extends i$1 { constructor() { super(...arguments); /** * The alert type/severity */ this.type = 'info'; /** * Whether the alert can be dismissed */ this.dismissible = false; /** * Whether the alert is visible */ this.visible = true; } /** Handles dismiss button click */ _handleDismiss() { this.visible = false; this.dispatchEvent(new CustomEvent('dismiss', { bubbles: true, composed: true })); } render() { const icons = { info: b `<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M18 10a8 8 0 11-16 0 8 8 0 0116 0zm-7-4a1 1 0 11-2 0 1 1 0 012 0zM9 9a1 1 0 000 2v3a1 1 0 001 1h1a1 1 0 100-2v-3a1 1 0 00-1-1H9z\" clip-rule=\"evenodd\"/></svg>`, success: b `<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M10 18a8 8 0 100-16 8 8 0 000 16zm3.707-9.293a1 1 0 00-1.414-1.414L9 10.586 7.707 9.293a1 1 0 00-1.414 1.414l2 2a1 1 0 001.414 0l4-4z\" clip-rule=\"evenodd\"/></svg>`, warning: b `<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M8.257 3.099c.765-1.36 2.722-1.36 3.486 0l5.58 9.92c.75 1.334-.213 2.98-1.742 2.98H4.42c-1.53 0-2.493-1.646-1.743-2.98l5.58-9.92zM11 13a1 1 0 11-2 0 1 1 0 012 0zm-1-8a1 1 0 00-1 1v3a1 1 0 002 0V6a1 1 0 00-1-1z\" clip-rule=\"evenodd\"/></svg>`, error: b `<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M10 18a8 8 0 100-16 8 8 0 000 16zM8.707 7.293a1 1 0 00-1.414 1.414L8.586 10l-1.293 1.293a1 1 0 101.414 1.414L10 11.414l1.293 1.293a1 1 0 001.414-1.414L11.414 10l1.293-1.293a1 1 0 00-1.414-1.414L10 8.586 8.707 7.293z\" clip-rule=\"evenodd\"/></svg>`, }; return b ` <div class=${e$1({ 'alert': true, ['alert--' + this.type]: true, 'alert--hidden': !this.visible })} role=\"alert\" > ${icons[this.type]} <div class=\"content\"> ${this.header ? b `<h4 class=\"header\">${this.header}</h4>` : A} <div class=\"message\"> <slot></slot> </div> </div> ${this.dismissible ? b ` <button class=\"dismiss\" type=\"button\" aria-label=\"Dismiss alert\" @click=${this._handleDismiss} > <svg viewBox=\"0 0 20 20\" fill=\"currentColor\" width=\"16\" height=\"16\"> <path fill-rule=\"evenodd\" d=\"M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z\" clip-rule=\"evenodd\"/> </svg> </button> ` : A} </div> `; } }",
120
128
  "description": "A customizable alert component for displaying important information to users."
121
129
  },
122
130
  {
123
131
  "kind": "variable",
124
132
  "name": "KRButton",
125
- "default": "class KRButton extends i$1 { constructor() { super(...arguments); /** * The button variant style */ this.variant = 'primary'; /** * The button size */ this.size = 'medium'; /** * Whether the button is disabled */ this.disabled = false; } render() { const sizeClass = this.size !== 'medium' ? this.size : ''; return x ` <button part=\"button\" class=\"${this.variant} ${sizeClass}\" ?disabled=${this.disabled} > <slot></slot> </button> `; } }",
133
+ "default": "class KRButton extends i$1 { constructor() { super(...arguments); /** * The button variant style */ this.variant = 'primary'; /** * The button size */ this.size = 'medium'; /** * Whether the button is disabled */ this.disabled = false; } render() { const sizeClass = this.size !== 'medium' ? this.size : ''; return b ` <button part=\"button\" class=\"${this.variant} ${sizeClass}\" ?disabled=${this.disabled} > <slot></slot> </button> `; } }",
126
134
  "description": "A customizable button component."
127
135
  },
128
136
  {
@@ -185,13 +193,13 @@
185
193
  {
186
194
  "kind": "variable",
187
195
  "name": "KRCodeDemo",
188
- "default": "class KRCodeDemo extends i$1 { constructor() { super(...arguments); this.language = 'html'; this.code = ''; this.activeTab = 'preview'; this.copied = false; } setTab(tab) { this.activeTab = tab; } getHighlightedCode() { if (!this.code) return ''; if (window.Prism && window.Prism.languages[this.language]) { return window.Prism.highlight(this.code, window.Prism.languages[this.language], this.language); } // Fallback: escape HTML and return plain text return this.escapeHtml(this.code); } escapeHtml(text) { const div = document.createElement('div'); div.textContent = text; return div.innerHTML; } async copyCode() { if (!this.code) return; try { await navigator.clipboard.writeText(this.code); this.copied = true; setTimeout(() => { this.copied = false; }, 2000); } catch (err) { console.error('Failed to copy code:', err); } } render() { return x ` <div class=\"tabs\"> <button class=${e$1({ tab: true, 'tab--active': this.activeTab === 'preview' })} @click=${() => this.setTab('preview')} > Preview </button> <button class=${e$1({ tab: true, 'tab--active': this.activeTab === 'code' })} @click=${() => this.setTab('code')} > Code </button> </div> <div class=${e$1({ panel: true, 'panel--active': this.activeTab === 'preview', preview: true })}> <slot name=\"preview\"></slot> </div> <div class=${e$1({ panel: true, 'panel--active': this.activeTab === 'code', 'code-container': true })}> <button class=${e$1({ 'copy-btn': true, 'copy-btn--copied': this.copied })} @click=${this.copyCode} > ${this.copied ? 'Copied!' : 'Copy'} </button> <pre class=\"code\"><code>${o(this.getHighlightedCode())}</code></pre> </div> `; } }",
196
+ "default": "class KRCodeDemo extends i$1 { constructor() { super(...arguments); this.language = 'html'; this.code = ''; this.activeTab = 'preview'; this.copied = false; } setTab(tab) { this.activeTab = tab; } getHighlightedCode() { if (!this.code) return ''; if (window.Prism && window.Prism.languages[this.language]) { return window.Prism.highlight(this.code, window.Prism.languages[this.language], this.language); } // Fallback: escape HTML and return plain text return this.escapeHtml(this.code); } escapeHtml(text) { const div = document.createElement('div'); div.textContent = text; return div.innerHTML; } async copyCode() { if (!this.code) return; try { await navigator.clipboard.writeText(this.code); this.copied = true; setTimeout(() => { this.copied = false; }, 2000); } catch (err) { console.error('Failed to copy code:', err); } } render() { return b ` <div class=\"tabs\"> <button class=${e$1({ tab: true, 'tab--active': this.activeTab === 'preview' })} @click=${() => this.setTab('preview')} > Preview </button> <button class=${e$1({ tab: true, 'tab--active': this.activeTab === 'code' })} @click=${() => this.setTab('code')} > Code </button> </div> <div class=${e$1({ panel: true, 'panel--active': this.activeTab === 'preview', preview: true })}> <slot name=\"preview\"></slot> </div> <div class=${e$1({ panel: true, 'panel--active': this.activeTab === 'code', 'code-container': true })}> <button class=${e$1({ 'copy-btn': true, 'copy-btn--copied': this.copied })} @click=${this.copyCode} > ${this.copied ? 'Copied!' : 'Copy'} </button> <pre class=\"code\"><code>${o(this.getHighlightedCode())}</code></pre> </div> `; } }",
189
197
  "description": "Code demo component with Preview/Code tabs and syntax highlighting.\n\nUsage:\n```html\n<kr-code-demo language=\"html\">\n <div slot=\"preview\">\n <kr-button>Click me</kr-button>\n </div>\n <script slot=\"code\" type=\"text/plain\">\n <kr-button>Click me</kr-button>\n </script>\n</kr-code-demo>\n```\n\nRequires Prism.js to be loaded globally for syntax highlighting."
190
198
  },
191
199
  {
192
200
  "kind": "variable",
193
201
  "name": "KRContextMenu",
194
- "default": "class KRContextMenu extends i$1 { constructor() { super(...arguments); this.items = []; this.resolvePromise = null; this.boundHandleOutsideClick = this.handleOutsideClick.bind(this); this.boundHandleKeyDown = this.handleKeyDown.bind(this); } static async open(options) { // Remove any existing context menu const existing = document.querySelector('kr-context-menu'); if (existing) { existing.remove(); } // Create and position the menu const menu = document.createElement('kr-context-menu'); document.body.appendChild(menu); return menu.show(options); } async show(options) { this.items = options.items; this.style.left = `${options.x}px`; this.style.top = `${options.y}px`; // Adjust position if menu would go off screen await this.updateComplete; const rect = this.getBoundingClientRect(); if (rect.right > window.innerWidth) { this.style.left = `${options.x - rect.width}px`; } if (rect.bottom > window.innerHeight) { this.style.top = `${options.y - rect.height}px`; } // Add event listeners after a microtask to avoid the current event triggering close requestAnimationFrame(() => { document.addEventListener('click', this.boundHandleOutsideClick); document.addEventListener('contextmenu', this.boundHandleOutsideClick); document.addEventListener('keydown', this.boundHandleKeyDown); }); return new Promise((resolve) => { this.resolvePromise = resolve; }); } handleOutsideClick(e) { if (!this.contains(e.target)) { this.close(null); } } handleKeyDown(e) { if (e.key === 'Escape') { this.close(null); } } handleItemClick(item) { if (!item.disabled && !item.divider) { this.close(item); } } close(result) { document.removeEventListener('click', this.boundHandleOutsideClick); document.removeEventListener('contextmenu', this.boundHandleOutsideClick); document.removeEventListener('keydown', this.boundHandleKeyDown); if (this.resolvePromise) { this.resolvePromise(result); this.resolvePromise = null; } this.remove(); } render() { return x ` <div class=\"menu\"> ${this.items.map(item => item.divider ? x `<div class=\"menu__divider\"></div>` : x ` <button class=\"menu__item\" ?disabled=${item.disabled} @click=${() => this.handleItemClick(item)} > ${item.icon ? x `<span class=\"menu__item-icon\">${item.icon}</span>` : null} ${item.label} </button> `)} </div> `; } }",
202
+ "default": "class KRContextMenu extends i$1 { constructor() { super(...arguments); this.items = []; this.resolvePromise = null; this.boundHandleOutsideClick = this.handleOutsideClick.bind(this); this.boundHandleKeyDown = this.handleKeyDown.bind(this); } static async open(options) { // Remove any existing context menu const existing = document.querySelector('kr-context-menu'); if (existing) { existing.remove(); } // Create and position the menu const menu = document.createElement('kr-context-menu'); document.body.appendChild(menu); return menu.show(options); } async show(options) { this.items = options.items; this.style.left = `${options.x}px`; this.style.top = `${options.y}px`; // Adjust position if menu would go off screen await this.updateComplete; const rect = this.getBoundingClientRect(); if (rect.right > window.innerWidth) { this.style.left = `${options.x - rect.width}px`; } if (rect.bottom > window.innerHeight) { this.style.top = `${options.y - rect.height}px`; } // Add event listeners after a microtask to avoid the current event triggering close requestAnimationFrame(() => { document.addEventListener('click', this.boundHandleOutsideClick); document.addEventListener('contextmenu', this.boundHandleOutsideClick); document.addEventListener('keydown', this.boundHandleKeyDown); }); return new Promise((resolve) => { this.resolvePromise = resolve; }); } handleOutsideClick(e) { if (!this.contains(e.target)) { this.close(null); } } handleKeyDown(e) { if (e.key === 'Escape') { this.close(null); } } handleItemClick(item) { if (!item.disabled && !item.divider) { this.close(item); } } close(result) { document.removeEventListener('click', this.boundHandleOutsideClick); document.removeEventListener('contextmenu', this.boundHandleOutsideClick); document.removeEventListener('keydown', this.boundHandleKeyDown); if (this.resolvePromise) { this.resolvePromise(result); this.resolvePromise = null; } this.remove(); } render() { return b ` <div class=\"menu\"> ${this.items.map(item => item.divider ? b `<div class=\"menu__divider\"></div>` : b ` <button class=\"menu__item\" ?disabled=${item.disabled} @click=${() => this.handleItemClick(item)} > ${item.icon ? b `<span class=\"menu__item-icon\">${item.icon}</span>` : null} ${item.label} </button> `)} </div> `; } }",
195
203
  "description": "Context menu component that can be opened programmatically.\n\nUsage:\n```ts\nconst result = await ContextMenu.open({\n x: event.clientX,\n y: event.clientY,\n items: [\n { id: 'edit', label: 'Edit Item' },\n { id: 'divider', label: '', divider: true },\n { id: 'add-above', label: 'Add Item Above' },\n { id: 'add-below', label: 'Add Item Below' },\n ]\n});\n\nif (result) {\n console.log('Selected:', result.id);\n}\n```"
196
204
  },
197
205
  {
@@ -238,13 +246,18 @@
238
246
  {
239
247
  "kind": "variable",
240
248
  "name": "KRDialog",
241
- "default": "class KRDialog extends i$1 { constructor() { super(...arguments); this.contentElement = null; this.dialogRef = null; this.boundHandleKeyDown = this.handleKeyDown.bind(this); } static open(component, config) { const existing = document.querySelector('kr-dialog'); if (existing) { existing.remove(); } const dialogRef = new DialogRef(); const dialog = document.createElement('kr-dialog'); dialogRef.setDialogElement(dialog); dialog.dialogRef = dialogRef; // Create the content component const content = new component(); content.dialogRef = dialogRef; if (config?.data) { content.data = config.data; } dialog.contentElement = content; document.body.appendChild(dialog); document.addEventListener('keydown', dialog.boundHandleKeyDown); return dialogRef; } handleKeyDown(e) { if (e.key === 'Escape') { this.dialogRef?.close(undefined); } } handleBackdropClick(e) { if (e.target.classList.contains('backdrop')) { this.dialogRef?.close(undefined); } } disconnectedCallback() { super.disconnectedCallback(); document.removeEventListener('keydown', this.boundHandleKeyDown); } render() { return x ` <div class=\"backdrop\" @click=${this.handleBackdropClick}></div> <div class=\"dialog\"> ${this.contentElement} </div> `; } }",
249
+ "default": "class KRDialog extends i$1 { constructor() { super(...arguments); this.contentElement = null; this.dialogRef = null; this.boundHandleKeyDown = this.handleKeyDown.bind(this); } static open(component, config) { const existing = document.querySelector('kr-dialog'); if (existing) { existing.remove(); } const dialogRef = new DialogRef(); const dialog = document.createElement('kr-dialog'); dialogRef.setDialogElement(dialog); dialog.dialogRef = dialogRef; // Create the content component const content = new component(); content.dialogRef = dialogRef; if (config?.data) { content.data = config.data; } dialog.contentElement = content; document.body.appendChild(dialog); document.addEventListener('keydown', dialog.boundHandleKeyDown); return dialogRef; } handleKeyDown(e) { if (e.key === 'Escape') { this.dialogRef?.close(undefined); } } handleBackdropClick(e) { if (e.target.classList.contains('backdrop')) { this.dialogRef?.close(undefined); } } disconnectedCallback() { super.disconnectedCallback(); document.removeEventListener('keydown', this.boundHandleKeyDown); } render() { return b ` <div class=\"backdrop\" @click=${this.handleBackdropClick}></div> <div class=\"dialog\"> ${this.contentElement} </div> `; } }",
242
250
  "description": "Generic dialog component that renders a Lit component inside a dialog shell.\n\nUsage:\n```ts\n// Define your dialog content component\nclass EditItemDialog extends LitElement {\n // Injected by KRDialog\n dialogRef: DialogRef<{ label: string }>;\n data: { label: string };\n\n save() {\n this.dialogRef.close({ label: this.label });\n }\n}\n\n// Open the dialog\nconst dialogRef = KRDialog.open(EditItemDialog, {\n data: { label: 'Dashboard' }\n});\n\nconst result = await dialogRef.afterClosed();\nif (result) {\n console.log('Saved:', result.label);\n}\n```"
243
251
  },
252
+ {
253
+ "kind": "variable",
254
+ "name": "KRSnackbar",
255
+ "description": "A snackbar component for displaying brief notification messages.\n\nSnackbars appear at the bottom-left of the screen and automatically\ndismiss after a configurable duration. Multiple snackbars stack vertically."
256
+ },
244
257
  {
245
258
  "kind": "variable",
246
259
  "name": "KRTextField",
247
- "default": "class KRTextField extends i$1 { constructor() { super(); /** * The input label text */ this.label = ''; /** * The input name for form submission */ this.name = ''; /** * The current value */ this.value = ''; /** * Placeholder text */ this.placeholder = ''; /** * Input type (text, email, password, tel, url, search) */ this.type = 'text'; /** * Whether the field is required */ this.required = false; /** * Whether the field is disabled */ this.disabled = false; /** * Whether the field is readonly */ this.readonly = false; /** * Autocomplete attribute value */ this.autocomplete = ''; /** * Helper text shown below the input */ this.hint = ''; this._touched = false; this._dirty = false; this._internals = this.attachInternals(); } // Form-associated custom element callbacks get form() { return this._internals.form; } get validity() { return this._internals.validity; } get validationMessage() { return this._internals.validationMessage; } get willValidate() { return this._internals.willValidate; } checkValidity() { return this._internals.checkValidity(); } reportValidity() { return this._internals.reportValidity(); } formResetCallback() { this.value = ''; this._touched = false; this._dirty = false; this._internals.setFormValue(''); this._internals.setValidity({}); } formStateRestoreCallback(state) { this.value = state; } _handleInput(e) { this.value = e.target.value; this._dirty = true; this._internals.setFormValue(this.value); this._internals.setValidity(this._input.validity, this._input.validationMessage, this._input); } _handleChange(e) { this.value = e.target.value; this._internals.setFormValue(this.value); } _handleBlur() { this._touched = true; this._internals.setValidity(this._input.validity, this._input.validationMessage, this._input); } render() { let validationMessage = ''; if (this._touched && this._input && !this._input.validity.valid) { validationMessage = this._input.validationMessage; } return x ` <div class=\"wrapper\"> ${this.label ? x ` <label for=\"input\"> ${this.label} ${this.required ? x `<span class=\"required\" aria-hidden=\"true\">*</span>` : ''} </label> ` : ''} <input id=\"input\" type=${this.type} name=${this.name} .value=${l(this.value)} placeholder=${this.placeholder} ?required=${this.required} ?disabled=${this.disabled} ?readonly=${this.readonly} minlength=${this.minlength ?? ''} maxlength=${this.maxlength ?? ''} pattern=${this.pattern ?? ''} autocomplete=${this.autocomplete} @input=${this._handleInput} @change=${this._handleChange} @blur=${this._handleBlur} /> ${validationMessage ? x `<div class=\"validation-message\">${validationMessage}</div>` : this.hint ? x `<div class=\"hint\">${this.hint}</div>` : ''} </div> `; } // Public methods for programmatic control focus() { this._input?.focus(); } blur() { this._input?.blur(); } select() { this._input?.select(); } }",
260
+ "default": "class KRTextField extends i$1 { constructor() { super(); /** * The input label text */ this.label = ''; /** * The input name for form submission */ this.name = ''; /** * The current value */ this.value = ''; /** * Placeholder text */ this.placeholder = ''; /** * Input type (text, email, password, tel, url, search) */ this.type = 'text'; /** * Whether the field is required */ this.required = false; /** * Whether the field is disabled */ this.disabled = false; /** * Whether the field is readonly */ this.readonly = false; /** * Autocomplete attribute value */ this.autocomplete = ''; /** * Helper text shown below the input */ this.hint = ''; this._touched = false; this._dirty = false; this._internals = this.attachInternals(); } // Form-associated custom element callbacks get form() { return this._internals.form; } get validity() { return this._internals.validity; } get validationMessage() { return this._internals.validationMessage; } get willValidate() { return this._internals.willValidate; } checkValidity() { return this._internals.checkValidity(); } reportValidity() { return this._internals.reportValidity(); } formResetCallback() { this.value = ''; this._touched = false; this._dirty = false; this._internals.setFormValue(''); this._internals.setValidity({}); } formStateRestoreCallback(state) { this.value = state; } _handleInput(e) { this.value = e.target.value; this._dirty = true; this._internals.setFormValue(this.value); this._internals.setValidity(this._input.validity, this._input.validationMessage, this._input); } _handleChange(e) { this.value = e.target.value; this._internals.setFormValue(this.value); } _handleBlur() { this._touched = true; this._internals.setValidity(this._input.validity, this._input.validationMessage, this._input); } render() { let validationMessage = ''; if (this._touched && this._input && !this._input.validity.valid) { validationMessage = this._input.validationMessage; } return b ` <div class=\"wrapper\"> ${this.label ? b ` <label for=\"input\"> ${this.label} ${this.required ? b `<span class=\"required\" aria-hidden=\"true\">*</span>` : ''} </label> ` : ''} <input id=\"input\" type=${this.type} name=${this.name} .value=${l(this.value)} placeholder=${this.placeholder} ?required=${this.required} ?disabled=${this.disabled} ?readonly=${this.readonly} minlength=${this.minlength ?? ''} maxlength=${this.maxlength ?? ''} pattern=${this.pattern ?? ''} autocomplete=${this.autocomplete} @input=${this._handleInput} @change=${this._handleChange} @blur=${this._handleBlur} /> ${validationMessage ? b `<div class=\"validation-message\">${validationMessage}</div>` : this.hint ? b `<div class=\"hint\">${this.hint}</div>` : ''} </div> `; } // Public methods for programmatic control focus() { this._input?.focus(); } blur() { this._input?.blur(); } select() { this._input?.select(); } }",
248
261
  "description": "A text field component that works with native browser forms.\n\nUses ElementInternals for form association, allowing the component\nto participate in form submission, validation, and reset.\n\nNative input and change events bubble up from the inner input element."
249
262
  }
250
263
  ],
@@ -321,6 +334,14 @@
321
334
  "module": "dist/krubble.bundled.js"
322
335
  }
323
336
  },
337
+ {
338
+ "kind": "js",
339
+ "name": "KRSnackbar",
340
+ "declaration": {
341
+ "name": "KRSnackbar",
342
+ "module": "dist/krubble.bundled.js"
343
+ }
344
+ },
324
345
  {
325
346
  "kind": "js",
326
347
  "name": "KRTextField",
@@ -346,33 +367,33 @@
346
367
  },
347
368
  {
348
369
  "kind": "variable",
349
- "name": "ut",
350
- "default": "class extends rt{constructor(){super(...arguments),this.header=\"\",this.expanded=!1}toggle(){this.expanded=!this.expanded}render(){return B` <div class=\"header\" @click=${this.toggle}> <span class=\"header__title\">${this.header}</span> <svg class=\"header__icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"> <path d=\"M6 9l6 6 6-6\"/> </svg> </div> <div class=\"content\"> <div class=\"content__inner\"> <div class=\"content__body\"> <slot></slot> </div> </div> </div> `}}"
370
+ "name": "ft",
371
+ "default": "class extends nt{constructor(){super(...arguments),this.header=\"\",this.expanded=!1}toggle(){this.expanded=!this.expanded}render(){return V` <div class=\"header\" @click=${this.toggle}> <span class=\"header__title\">${this.header}</span> <svg class=\"header__icon\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"> <path d=\"M6 9l6 6 6-6\"/> </svg> </div> <div class=\"content\"> <div class=\"content__inner\"> <div class=\"content__body\"> <slot></slot> </div> </div> </div> `}}"
351
372
  },
352
373
  {
353
374
  "kind": "variable",
354
- "name": "xt",
355
- "default": "class extends rt{constructor(){super(...arguments),this.type=\"info\",this.dismissible=!1,this.visible=!0}_handleDismiss(){this.visible=!1,this.dispatchEvent(new CustomEvent(\"dismiss\",{bubbles:!0,composed:!0}))}render(){const t={info:B`<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M18 10a8 8 0 11-16 0 8 8 0 0116 0zm-7-4a1 1 0 11-2 0 1 1 0 012 0zM9 9a1 1 0 000 2v3a1 1 0 001 1h1a1 1 0 100-2v-3a1 1 0 00-1-1H9z\" clip-rule=\"evenodd\"/></svg>`,success:B`<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M10 18a8 8 0 100-16 8 8 0 000 16zm3.707-9.293a1 1 0 00-1.414-1.414L9 10.586 7.707 9.293a1 1 0 00-1.414 1.414l2 2a1 1 0 001.414 0l4-4z\" clip-rule=\"evenodd\"/></svg>`,warning:B`<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M8.257 3.099c.765-1.36 2.722-1.36 3.486 0l5.58 9.92c.75 1.334-.213 2.98-1.742 2.98H4.42c-1.53 0-2.493-1.646-1.743-2.98l5.58-9.92zM11 13a1 1 0 11-2 0 1 1 0 012 0zm-1-8a1 1 0 00-1 1v3a1 1 0 002 0V6a1 1 0 00-1-1z\" clip-rule=\"evenodd\"/></svg>`,error:B`<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M10 18a8 8 0 100-16 8 8 0 000 16zM8.707 7.293a1 1 0 00-1.414 1.414L8.586 10l-1.293 1.293a1 1 0 101.414 1.414L10 11.414l1.293 1.293a1 1 0 001.414-1.414L11.414 10l1.293-1.293a1 1 0 00-1.414-1.414L10 8.586 8.707 7.293z\" clip-rule=\"evenodd\"/></svg>`};return B` <div class=${_t({alert:!0,[\"alert--\"+this.type]:!0,\"alert--hidden\":!this.visible})} role=\"alert\" > ${t[this.type]} <div class=\"content\"> ${this.header?B`<h4 class=\"header\">${this.header}</h4>`:q} <div class=\"message\"> <slot></slot> </div> </div> ${this.dismissible?B` <button class=\"dismiss\" type=\"button\" aria-label=\"Dismiss alert\" @click=${this._handleDismiss} > <svg viewBox=\"0 0 20 20\" fill=\"currentColor\" width=\"16\" height=\"16\"> <path fill-rule=\"evenodd\" d=\"M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z\" clip-rule=\"evenodd\"/> </svg> </button> `:q} </div> `}}"
375
+ "name": "kt",
376
+ "default": "class extends nt{constructor(){super(...arguments),this.type=\"info\",this.dismissible=!1,this.visible=!0}_handleDismiss(){this.visible=!1,this.dispatchEvent(new CustomEvent(\"dismiss\",{bubbles:!0,composed:!0}))}render(){const t={info:V`<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M18 10a8 8 0 11-16 0 8 8 0 0116 0zm-7-4a1 1 0 11-2 0 1 1 0 012 0zM9 9a1 1 0 000 2v3a1 1 0 001 1h1a1 1 0 100-2v-3a1 1 0 00-1-1H9z\" clip-rule=\"evenodd\"/></svg>`,success:V`<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M10 18a8 8 0 100-16 8 8 0 000 16zm3.707-9.293a1 1 0 00-1.414-1.414L9 10.586 7.707 9.293a1 1 0 00-1.414 1.414l2 2a1 1 0 001.414 0l4-4z\" clip-rule=\"evenodd\"/></svg>`,warning:V`<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M8.257 3.099c.765-1.36 2.722-1.36 3.486 0l5.58 9.92c.75 1.334-.213 2.98-1.742 2.98H4.42c-1.53 0-2.493-1.646-1.743-2.98l5.58-9.92zM11 13a1 1 0 11-2 0 1 1 0 012 0zm-1-8a1 1 0 00-1 1v3a1 1 0 002 0V6a1 1 0 00-1-1z\" clip-rule=\"evenodd\"/></svg>`,error:V`<svg class=\"icon\" viewBox=\"0 0 20 20\" fill=\"currentColor\"><path fill-rule=\"evenodd\" d=\"M10 18a8 8 0 100-16 8 8 0 000 16zM8.707 7.293a1 1 0 00-1.414 1.414L8.586 10l-1.293 1.293a1 1 0 101.414 1.414L10 11.414l1.293 1.293a1 1 0 001.414-1.414L11.414 10l1.293-1.293a1 1 0 00-1.414-1.414L10 8.586 8.707 7.293z\" clip-rule=\"evenodd\"/></svg>`};return V` <div class=${$t({alert:!0,[\"alert--\"+this.type]:!0,\"alert--hidden\":!this.visible})} role=\"alert\" > ${t[this.type]} <div class=\"content\"> ${this.header?V`<h4 class=\"header\">${this.header}</h4>`:q} <div class=\"message\"> <slot></slot> </div> </div> ${this.dismissible?V` <button class=\"dismiss\" type=\"button\" aria-label=\"Dismiss alert\" @click=${this._handleDismiss} > <svg viewBox=\"0 0 20 20\" fill=\"currentColor\" width=\"16\" height=\"16\"> <path fill-rule=\"evenodd\" d=\"M4.293 4.293a1 1 0 011.414 0L10 8.586l4.293-4.293a1 1 0 111.414 1.414L11.414 10l4.293 4.293a1 1 0 01-1.414 1.414L10 11.414l-4.293 4.293a1 1 0 01-1.414-1.414L8.586 10 4.293 5.707a1 1 0 010-1.414z\" clip-rule=\"evenodd\"/> </svg> </button> `:q} </div> `}}"
356
377
  },
357
378
  {
358
379
  "kind": "variable",
359
- "name": "kt",
360
- "default": "class extends rt{constructor(){super(...arguments),this.variant=\"primary\",this.size=\"medium\",this.disabled=!1}render(){const t=\"medium\"!==this.size?this.size:\"\";return B` <button part=\"button\" class=\"${this.variant} ${t}\" ?disabled=${this.disabled} > <slot></slot> </button> `}}"
380
+ "name": "At",
381
+ "default": "class extends nt{constructor(){super(...arguments),this.variant=\"primary\",this.size=\"medium\",this.disabled=!1}render(){const t=\"medium\"!==this.size?this.size:\"\";return V` <button part=\"button\" class=\"${this.variant} ${t}\" ?disabled=${this.disabled} > <slot></slot> </button> `}}"
361
382
  },
362
383
  {
363
384
  "kind": "variable",
364
- "name": "Ct",
365
- "default": "class extends rt{constructor(){super(...arguments),this.language=\"html\",this.code=\"\",this.activeTab=\"preview\",this.copied=!1}setTab(t){this.activeTab=t}getHighlightedCode(){return this.code?window.Prism&&window.Prism.languages[this.language]?window.Prism.highlight(this.code,window.Prism.languages[this.language],this.language):this.escapeHtml(this.code):\"\"}escapeHtml(t){const e=document.createElement(\"div\");return e.textContent=t,e.innerHTML}async copyCode(){if(this.code)try{await navigator.clipboard.writeText(this.code),this.copied=!0,setTimeout((()=>{this.copied=!1}),2e3)}catch(t){console.error(\"Failed to copy code:\",t)}}render(){return B` <div class=\"tabs\"> <button class=${_t({tab:!0,\"tab--active\":\"preview\"===this.activeTab})} @click=${()=>this.setTab(\"preview\")} > Preview </button> <button class=${_t({tab:!0,\"tab--active\":\"code\"===this.activeTab})} @click=${()=>this.setTab(\"code\")} > Code </button> </div> <div class=${_t({panel:!0,\"panel--active\":\"preview\"===this.activeTab,preview:!0})}> <slot name=\"preview\"></slot> </div> <div class=${_t({panel:!0,\"panel--active\":\"code\"===this.activeTab,\"code-container\":!0})}> <button class=${_t({\"copy-btn\":!0,\"copy-btn--copied\":this.copied})} @click=${this.copyCode} > ${this.copied?\"Copied!\":\"Copy\"} </button> <pre class=\"code\"><code>${Et(this.getHighlightedCode())}</code></pre> </div> `}}"
385
+ "name": "Pt",
386
+ "default": "class extends nt{constructor(){super(...arguments),this.language=\"html\",this.code=\"\",this.activeTab=\"preview\",this.copied=!1}setTab(t){this.activeTab=t}getHighlightedCode(){return this.code?window.Prism&&window.Prism.languages[this.language]?window.Prism.highlight(this.code,window.Prism.languages[this.language],this.language):this.escapeHtml(this.code):\"\"}escapeHtml(t){const e=document.createElement(\"div\");return e.textContent=t,e.innerHTML}async copyCode(){if(this.code)try{await navigator.clipboard.writeText(this.code),this.copied=!0,setTimeout(()=>{this.copied=!1},2e3)}catch(t){console.error(\"Failed to copy code:\",t)}}render(){return V` <div class=\"tabs\"> <button class=${$t({tab:!0,\"tab--active\":\"preview\"===this.activeTab})} @click=${()=>this.setTab(\"preview\")} > Preview </button> <button class=${$t({tab:!0,\"tab--active\":\"code\"===this.activeTab})} @click=${()=>this.setTab(\"code\")} > Code </button> </div> <div class=${$t({panel:!0,\"panel--active\":\"preview\"===this.activeTab,preview:!0})}> <slot name=\"preview\"></slot> </div> <div class=${$t({panel:!0,\"panel--active\":\"code\"===this.activeTab,\"code-container\":!0})}> <button class=${$t({\"copy-btn\":!0,\"copy-btn--copied\":this.copied})} @click=${this.copyCode} > ${this.copied?\"Copied!\":\"Copy\"} </button> <pre class=\"code\"><code>${St(this.getHighlightedCode())}</code></pre> </div> `}}"
366
387
  },
367
388
  {
368
389
  "kind": "variable",
369
- "name": "Ot",
370
- "default": "class extends rt{constructor(){super(...arguments),this.items=[],this.resolvePromise=null,this.boundHandleOutsideClick=this.handleOutsideClick.bind(this),this.boundHandleKeyDown=this.handleKeyDown.bind(this)}static async open(t){const e=document.querySelector(\"kr-context-menu\");e&&e.remove();const i=document.createElement(\"kr-context-menu\");return document.body.appendChild(i),i.show(t)}async show(t){this.items=t.items,this.style.left=`${t.x}px`,this.style.top=`${t.y}px`,await this.updateComplete;const e=this.getBoundingClientRect();return e.right>window.innerWidth&&(this.style.left=t.x-e.width+\"px\"),e.bottom>window.innerHeight&&(this.style.top=t.y-e.height+\"px\"),requestAnimationFrame((()=>{document.addEventListener(\"click\",this.boundHandleOutsideClick),document.addEventListener(\"contextmenu\",this.boundHandleOutsideClick),document.addEventListener(\"keydown\",this.boundHandleKeyDown)})),new Promise((t=>{this.resolvePromise=t}))}handleOutsideClick(t){this.contains(t.target)||this.close(null)}handleKeyDown(t){\"Escape\"===t.key&&this.close(null)}handleItemClick(t){t.disabled||t.divider||this.close(t)}close(t){document.removeEventListener(\"click\",this.boundHandleOutsideClick),document.removeEventListener(\"contextmenu\",this.boundHandleOutsideClick),document.removeEventListener(\"keydown\",this.boundHandleKeyDown),this.resolvePromise&&(this.resolvePromise(t),this.resolvePromise=null),this.remove()}render(){return B` <div class=\"menu\"> ${this.items.map((t=>t.divider?B`<div class=\"menu__divider\"></div>`:B` <button class=\"menu__item\" ?disabled=${t.disabled} @click=${()=>this.handleItemClick(t)} > ${t.icon?B`<span class=\"menu__item-icon\">${t.icon}</span>`:null} ${t.label} </button> `))} </div> `}}"
390
+ "name": "Mt",
391
+ "default": "class extends nt{constructor(){super(...arguments),this.items=[],this.resolvePromise=null,this.boundHandleOutsideClick=this.handleOutsideClick.bind(this),this.boundHandleKeyDown=this.handleKeyDown.bind(this)}static async open(t){const e=document.querySelector(\"kr-context-menu\");e&&e.remove();const i=document.createElement(\"kr-context-menu\");return document.body.appendChild(i),i.show(t)}async show(t){this.items=t.items,this.style.left=`${t.x}px`,this.style.top=`${t.y}px`,await this.updateComplete;const e=this.getBoundingClientRect();return e.right>window.innerWidth&&(this.style.left=t.x-e.width+\"px\"),e.bottom>window.innerHeight&&(this.style.top=t.y-e.height+\"px\"),requestAnimationFrame(()=>{document.addEventListener(\"click\",this.boundHandleOutsideClick),document.addEventListener(\"contextmenu\",this.boundHandleOutsideClick),document.addEventListener(\"keydown\",this.boundHandleKeyDown)}),new Promise(t=>{this.resolvePromise=t})}handleOutsideClick(t){this.contains(t.target)||this.close(null)}handleKeyDown(t){\"Escape\"===t.key&&this.close(null)}handleItemClick(t){t.disabled||t.divider||this.close(t)}close(t){document.removeEventListener(\"click\",this.boundHandleOutsideClick),document.removeEventListener(\"contextmenu\",this.boundHandleOutsideClick),document.removeEventListener(\"keydown\",this.boundHandleKeyDown),this.resolvePromise&&(this.resolvePromise(t),this.resolvePromise=null),this.remove()}render(){return V` <div class=\"menu\"> ${this.items.map(t=>t.divider?V`<div class=\"menu__divider\"></div>`:V` <button class=\"menu__item\" ?disabled=${t.disabled} @click=${()=>this.handleItemClick(t)} > ${t.icon?V`<span class=\"menu__item-icon\">${t.icon}</span>`:null} ${t.label} </button> `)} </div> `}}"
371
392
  },
372
393
  {
373
394
  "kind": "class",
374
395
  "description": "",
375
- "name": "Mt",
396
+ "name": "Tt",
376
397
  "members": [
377
398
  {
378
399
  "kind": "method",
@@ -415,19 +436,23 @@
415
436
  {
416
437
  "kind": "field",
417
438
  "name": "promise",
418
- "default": "new Promise((t=>{this.resolvePromise=t}))"
439
+ "default": "new Promise(t=>{this.resolvePromise=t})"
419
440
  }
420
441
  ]
421
442
  },
422
443
  {
423
444
  "kind": "variable",
424
- "name": "Ht",
425
- "default": "class extends rt{constructor(){super(...arguments),this.contentElement=null,this.dialogRef=null,this.boundHandleKeyDown=this.handleKeyDown.bind(this)}static open(t,e){const i=document.querySelector(\"kr-dialog\");i&&i.remove();const o=new Mt,s=document.createElement(\"kr-dialog\");o.setDialogElement(s),s.dialogRef=o;const r=new t;return r.dialogRef=o,e?.data&&(r.data=e.data),s.contentElement=r,document.body.appendChild(s),document.addEventListener(\"keydown\",s.boundHandleKeyDown),o}handleKeyDown(t){\"Escape\"===t.key&&this.dialogRef?.close(void 0)}handleBackdropClick(t){t.target.classList.contains(\"backdrop\")&&this.dialogRef?.close(void 0)}disconnectedCallback(){super.disconnectedCallback(),document.removeEventListener(\"keydown\",this.boundHandleKeyDown)}render(){return B` <div class=\"backdrop\" @click=${this.handleBackdropClick}></div> <div class=\"dialog\"> ${this.contentElement} </div> `}}"
445
+ "name": "zt",
446
+ "default": "class extends nt{constructor(){super(...arguments),this.contentElement=null,this.dialogRef=null,this.boundHandleKeyDown=this.handleKeyDown.bind(this)}static open(t,e){const i=document.querySelector(\"kr-dialog\");i&&i.remove();const o=new Tt,s=document.createElement(\"kr-dialog\");o.setDialogElement(s),s.dialogRef=o;const r=new t;return r.dialogRef=o,e?.data&&(r.data=e.data),s.contentElement=r,document.body.appendChild(s),document.addEventListener(\"keydown\",s.boundHandleKeyDown),o}handleKeyDown(t){\"Escape\"===t.key&&this.dialogRef?.close(void 0)}handleBackdropClick(t){t.target.classList.contains(\"backdrop\")&&this.dialogRef?.close(void 0)}disconnectedCallback(){super.disconnectedCallback(),document.removeEventListener(\"keydown\",this.boundHandleKeyDown)}render(){return V` <div class=\"backdrop\" @click=${this.handleBackdropClick}></div> <div class=\"dialog\"> ${this.contentElement} </div> `}}"
426
447
  },
427
448
  {
428
449
  "kind": "variable",
429
- "name": "zt",
430
- "default": "class extends rt{constructor(){super(),this.label=\"\",this.name=\"\",this.value=\"\",this.placeholder=\"\",this.type=\"text\",this.required=!1,this.disabled=!1,this.readonly=!1,this.autocomplete=\"\",this.hint=\"\",this._touched=!1,this._dirty=!1,this._internals=this.attachInternals()}get form(){return this._internals.form}get validity(){return this._internals.validity}get validationMessage(){return this._internals.validationMessage}get willValidate(){return this._internals.willValidate}checkValidity(){return this._internals.checkValidity()}reportValidity(){return this._internals.reportValidity()}formResetCallback(){this.value=\"\",this._touched=!1,this._dirty=!1,this._internals.setFormValue(\"\"),this._internals.setValidity({})}formStateRestoreCallback(t){this.value=t}_handleInput(t){this.value=t.target.value,this._dirty=!0,this._internals.setFormValue(this.value),this._internals.setValidity(this._input.validity,this._input.validationMessage,this._input)}_handleChange(t){this.value=t.target.value,this._internals.setFormValue(this.value)}_handleBlur(){this._touched=!0,this._internals.setValidity(this._input.validity,this._input.validationMessage,this._input)}render(){let t=\"\";return this._touched&&this._input&&!this._input.validity.valid&&(t=this._input.validationMessage),B` <div class=\"wrapper\"> ${this.label?B` <label for=\"input\"> ${this.label} ${this.required?B`<span class=\"required\" aria-hidden=\"true\">*</span>`:\"\"} </label> `:\"\"} <input id=\"input\" type=${this.type} name=${this.name} .value=${jt(this.value)} placeholder=${this.placeholder} ?required=${this.required} ?disabled=${this.disabled} ?readonly=${this.readonly} minlength=${this.minlength??\"\"} maxlength=${this.maxlength??\"\"} pattern=${this.pattern??\"\"} autocomplete=${this.autocomplete} @input=${this._handleInput} @change=${this._handleChange} @blur=${this._handleBlur} /> ${t?B`<div class=\"validation-message\">${t}</div>`:this.hint?B`<div class=\"hint\">${this.hint}</div>`:\"\"} </div> `}focus(){this._input?.focus()}blur(){this._input?.blur()}select(){this._input?.select()}}"
450
+ "name": "Lt"
451
+ },
452
+ {
453
+ "kind": "variable",
454
+ "name": "Bt",
455
+ "default": "class extends nt{constructor(){super(),this.label=\"\",this.name=\"\",this.value=\"\",this.placeholder=\"\",this.type=\"text\",this.required=!1,this.disabled=!1,this.readonly=!1,this.autocomplete=\"\",this.hint=\"\",this._touched=!1,this._dirty=!1,this._internals=this.attachInternals()}get form(){return this._internals.form}get validity(){return this._internals.validity}get validationMessage(){return this._internals.validationMessage}get willValidate(){return this._internals.willValidate}checkValidity(){return this._internals.checkValidity()}reportValidity(){return this._internals.reportValidity()}formResetCallback(){this.value=\"\",this._touched=!1,this._dirty=!1,this._internals.setFormValue(\"\"),this._internals.setValidity({})}formStateRestoreCallback(t){this.value=t}_handleInput(t){this.value=t.target.value,this._dirty=!0,this._internals.setFormValue(this.value),this._internals.setValidity(this._input.validity,this._input.validationMessage,this._input)}_handleChange(t){this.value=t.target.value,this._internals.setFormValue(this.value)}_handleBlur(){this._touched=!0,this._internals.setValidity(this._input.validity,this._input.validationMessage,this._input)}render(){let t=\"\";return this._touched&&this._input&&!this._input.validity.valid&&(t=this._input.validationMessage),V` <div class=\"wrapper\"> ${this.label?V` <label for=\"input\"> ${this.label} ${this.required?V`<span class=\"required\" aria-hidden=\"true\">*</span>`:\"\"} </label> `:\"\"} <input id=\"input\" type=${this.type} name=${this.name} .value=${Dt(this.value)} placeholder=${this.placeholder} ?required=${this.required} ?disabled=${this.disabled} ?readonly=${this.readonly} minlength=${this.minlength??\"\"} maxlength=${this.maxlength??\"\"} pattern=${this.pattern??\"\"} autocomplete=${this.autocomplete} @input=${this._handleInput} @change=${this._handleChange} @blur=${this._handleBlur} /> ${t?V`<div class=\"validation-message\">${t}</div>`:this.hint?V`<div class=\"hint\">${this.hint}</div>`:\"\"} </div> `}focus(){this._input?.focus()}blur(){this._input?.blur()}select(){this._input?.select()}}"
431
456
  }
432
457
  ],
433
458
  "exports": [
@@ -451,7 +476,7 @@
451
476
  "kind": "js",
452
477
  "name": "DialogRef",
453
478
  "declaration": {
454
- "name": "Mt",
479
+ "name": "Tt",
455
480
  "module": "dist/krubble.bundled.min.js"
456
481
  }
457
482
  },
@@ -459,7 +484,7 @@
459
484
  "kind": "js",
460
485
  "name": "KRAccordion",
461
486
  "declaration": {
462
- "name": "ut",
487
+ "name": "ft",
463
488
  "module": "dist/krubble.bundled.min.js"
464
489
  }
465
490
  },
@@ -467,7 +492,7 @@
467
492
  "kind": "js",
468
493
  "name": "KRAlert",
469
494
  "declaration": {
470
- "name": "xt",
495
+ "name": "kt",
471
496
  "module": "dist/krubble.bundled.min.js"
472
497
  }
473
498
  },
@@ -475,7 +500,7 @@
475
500
  "kind": "js",
476
501
  "name": "KRButton",
477
502
  "declaration": {
478
- "name": "kt",
503
+ "name": "At",
479
504
  "module": "dist/krubble.bundled.min.js"
480
505
  }
481
506
  },
@@ -483,7 +508,7 @@
483
508
  "kind": "js",
484
509
  "name": "KRCodeDemo",
485
510
  "declaration": {
486
- "name": "Ct",
511
+ "name": "Pt",
487
512
  "module": "dist/krubble.bundled.min.js"
488
513
  }
489
514
  },
@@ -491,7 +516,7 @@
491
516
  "kind": "js",
492
517
  "name": "KRContextMenu",
493
518
  "declaration": {
494
- "name": "Ot",
519
+ "name": "Mt",
495
520
  "module": "dist/krubble.bundled.min.js"
496
521
  }
497
522
  },
@@ -499,7 +524,15 @@
499
524
  "kind": "js",
500
525
  "name": "KRDialog",
501
526
  "declaration": {
502
- "name": "Ht",
527
+ "name": "zt",
528
+ "module": "dist/krubble.bundled.min.js"
529
+ }
530
+ },
531
+ {
532
+ "kind": "js",
533
+ "name": "KRSnackbar",
534
+ "declaration": {
535
+ "name": "Lt",
503
536
  "module": "dist/krubble.bundled.min.js"
504
537
  }
505
538
  },
@@ -507,7 +540,7 @@
507
540
  "kind": "js",
508
541
  "name": "KRTextField",
509
542
  "declaration": {
510
- "name": "zt",
543
+ "name": "Bt",
511
544
  "module": "dist/krubble.bundled.min.js"
512
545
  }
513
546
  }
@@ -830,6 +863,14 @@
830
863
  "module": "./dialog/dialog.js"
831
864
  }
832
865
  },
866
+ {
867
+ "kind": "js",
868
+ "name": "KRSnackbar",
869
+ "declaration": {
870
+ "name": "KRSnackbar",
871
+ "module": "./snackbar/snackbar.js"
872
+ }
873
+ },
833
874
  {
834
875
  "kind": "js",
835
876
  "name": "KRTextField",
@@ -861,6 +902,14 @@
861
902
  "name": "DialogConfig",
862
903
  "module": "./dialog/dialog.js"
863
904
  }
905
+ },
906
+ {
907
+ "kind": "js",
908
+ "name": "KRSnackbarOptions",
909
+ "declaration": {
910
+ "name": "KRSnackbarOptions",
911
+ "module": "./snackbar/snackbar.js"
912
+ }
864
913
  }
865
914
  ]
866
915
  },
@@ -1038,6 +1087,27 @@
1038
1087
  }
1039
1088
  ]
1040
1089
  },
1090
+ {
1091
+ "kind": "javascript-module",
1092
+ "path": "dist/snackbar/snackbar.js",
1093
+ "declarations": [
1094
+ {
1095
+ "kind": "variable",
1096
+ "name": "KRSnackbar",
1097
+ "description": "A snackbar component for displaying brief notification messages.\n\nSnackbars appear at the bottom-left of the screen and automatically\ndismiss after a configurable duration. Multiple snackbars stack vertically."
1098
+ }
1099
+ ],
1100
+ "exports": [
1101
+ {
1102
+ "kind": "js",
1103
+ "name": "KRSnackbar",
1104
+ "declaration": {
1105
+ "name": "KRSnackbar",
1106
+ "module": "dist/snackbar/snackbar.js"
1107
+ }
1108
+ }
1109
+ ]
1110
+ },
1041
1111
  {
1042
1112
  "kind": "javascript-module",
1043
1113
  "path": "src/accordion/accordion.ts",
@@ -1720,6 +1790,180 @@
1720
1790
  }
1721
1791
  ]
1722
1792
  },
1793
+ {
1794
+ "kind": "javascript-module",
1795
+ "path": "src/snackbar/snackbar.ts",
1796
+ "declarations": [
1797
+ {
1798
+ "kind": "class",
1799
+ "description": "A snackbar component for displaying brief notification messages.\n\nSnackbars appear at the bottom-left of the screen and automatically\ndismiss after a configurable duration. Multiple snackbars stack vertically.",
1800
+ "name": "KRSnackbar",
1801
+ "members": [
1802
+ {
1803
+ "kind": "field",
1804
+ "name": "activeSnackbars",
1805
+ "type": {
1806
+ "text": "KRSnackbar[]"
1807
+ },
1808
+ "privacy": "private",
1809
+ "static": true,
1810
+ "default": "[]",
1811
+ "description": "Track active snackbars for stacking"
1812
+ },
1813
+ {
1814
+ "kind": "method",
1815
+ "name": "show",
1816
+ "static": true,
1817
+ "return": {
1818
+ "type": {
1819
+ "text": ""
1820
+ }
1821
+ },
1822
+ "parameters": [
1823
+ {
1824
+ "name": "options",
1825
+ "type": {
1826
+ "text": "KRSnackbarOptions"
1827
+ },
1828
+ "description": "Configuration including message, optional title, type, and duration"
1829
+ }
1830
+ ],
1831
+ "description": "Show a snackbar with the given options."
1832
+ },
1833
+ {
1834
+ "kind": "field",
1835
+ "name": "dismissTimeout",
1836
+ "type": {
1837
+ "text": "number | null"
1838
+ },
1839
+ "privacy": "private",
1840
+ "default": "null"
1841
+ },
1842
+ {
1843
+ "kind": "field",
1844
+ "name": "type",
1845
+ "type": {
1846
+ "text": "'info' | 'success' | 'warning' | 'error'"
1847
+ },
1848
+ "default": "'info'",
1849
+ "description": "The snackbar type/severity. Controls the color scheme and icon.",
1850
+ "attribute": "type"
1851
+ },
1852
+ {
1853
+ "kind": "field",
1854
+ "name": "title",
1855
+ "type": {
1856
+ "text": "string"
1857
+ },
1858
+ "default": "''",
1859
+ "description": "Optional title to display above the message.",
1860
+ "attribute": "title"
1861
+ },
1862
+ {
1863
+ "kind": "field",
1864
+ "name": "message",
1865
+ "type": {
1866
+ "text": "string"
1867
+ },
1868
+ "default": "''",
1869
+ "description": "The message to display in the snackbar.",
1870
+ "attribute": "message"
1871
+ },
1872
+ {
1873
+ "kind": "field",
1874
+ "name": "duration",
1875
+ "type": {
1876
+ "text": "number"
1877
+ },
1878
+ "default": "5000",
1879
+ "description": "Duration in milliseconds before auto-dismiss. Set to 0 to disable auto-dismiss.",
1880
+ "attribute": "duration"
1881
+ },
1882
+ {
1883
+ "kind": "method",
1884
+ "name": "updatePositions",
1885
+ "privacy": "private"
1886
+ },
1887
+ {
1888
+ "kind": "method",
1889
+ "name": "dismiss",
1890
+ "privacy": "private"
1891
+ }
1892
+ ],
1893
+ "events": [
1894
+ {
1895
+ "name": "dismiss",
1896
+ "type": {
1897
+ "text": "CustomEvent"
1898
+ },
1899
+ "description": "Fired when the snackbar is dismissed (manually or automatically)"
1900
+ }
1901
+ ],
1902
+ "attributes": [
1903
+ {
1904
+ "name": "type",
1905
+ "type": {
1906
+ "text": "'info' | 'success' | 'warning' | 'error'"
1907
+ },
1908
+ "default": "'info'",
1909
+ "description": "The snackbar type/severity. Controls the color scheme and icon.",
1910
+ "fieldName": "type"
1911
+ },
1912
+ {
1913
+ "name": "title",
1914
+ "type": {
1915
+ "text": "string"
1916
+ },
1917
+ "default": "''",
1918
+ "description": "Optional title to display above the message.",
1919
+ "fieldName": "title"
1920
+ },
1921
+ {
1922
+ "name": "message",
1923
+ "type": {
1924
+ "text": "string"
1925
+ },
1926
+ "default": "''",
1927
+ "description": "The message to display in the snackbar.",
1928
+ "fieldName": "message"
1929
+ },
1930
+ {
1931
+ "name": "duration",
1932
+ "type": {
1933
+ "text": "number"
1934
+ },
1935
+ "default": "5000",
1936
+ "description": "Duration in milliseconds before auto-dismiss. Set to 0 to disable auto-dismiss.",
1937
+ "fieldName": "duration"
1938
+ }
1939
+ ],
1940
+ "superclass": {
1941
+ "name": "LitElement",
1942
+ "package": "lit"
1943
+ },
1944
+ "tagName": "kr-snackbar",
1945
+ "customElement": true
1946
+ }
1947
+ ],
1948
+ "exports": [
1949
+ {
1950
+ "kind": "js",
1951
+ "name": "KRSnackbar",
1952
+ "declaration": {
1953
+ "name": "KRSnackbar",
1954
+ "module": "src/snackbar/snackbar.ts"
1955
+ }
1956
+ },
1957
+ {
1958
+ "kind": "custom-element-definition",
1959
+ "name": "kr-snackbar",
1960
+ "declaration": {
1961
+ "name": "KRSnackbar",
1962
+ "module": "src/snackbar/snackbar.ts"
1963
+ }
1964
+ }
1965
+ ]
1966
+ },
1723
1967
  {
1724
1968
  "kind": "javascript-module",
1725
1969
  "path": "dist/form/text-field/text-field.js",
package/dist/index.d.ts CHANGED
@@ -4,7 +4,9 @@ export { KRButton } from './button/button.js';
4
4
  export { KRCodeDemo } from './code-demo/code-demo.js';
5
5
  export { KRContextMenu } from './context-menu/context-menu.js';
6
6
  export { KRDialog, DialogRef } from './dialog/dialog.js';
7
+ export { KRSnackbar } from './snackbar/snackbar.js';
7
8
  export { KRTextField } from './form/index.js';
8
9
  export type { ContextMenuItem, ContextMenuOptions } from './context-menu/context-menu.js';
9
10
  export type { DialogConfig } from './dialog/dialog.js';
11
+ export type { KRSnackbarOptions } from './snackbar/snackbar.js';
10
12
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AACvD,OAAO,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AACrC,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,UAAU,EAAE,MAAM,0BAA0B,CAAC;AACtD,OAAO,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AAC/D,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AAGzD,OAAO,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAC;AAG9C,YAAY,EAAE,eAAe,EAAE,kBAAkB,EAAE,MAAM,gCAAgC,CAAC;AAC1F,YAAY,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AACvD,OAAO,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AACrC,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,UAAU,EAAE,MAAM,0BAA0B,CAAC;AACtD,OAAO,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AAC/D,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAGpD,OAAO,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAC;AAG9C,YAAY,EAAE,eAAe,EAAE,kBAAkB,EAAE,MAAM,gCAAgC,CAAC;AAC1F,YAAY,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AACvD,YAAY,EAAE,iBAAiB,EAAE,MAAM,wBAAwB,CAAC"}
package/dist/index.js CHANGED
@@ -5,6 +5,7 @@ export { KRButton } from './button/button.js';
5
5
  export { KRCodeDemo } from './code-demo/code-demo.js';
6
6
  export { KRContextMenu } from './context-menu/context-menu.js';
7
7
  export { KRDialog, DialogRef } from './dialog/dialog.js';
8
+ export { KRSnackbar } from './snackbar/snackbar.js';
8
9
  // Form components
9
10
  export { KRTextField } from './form/index.js';
10
11
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,aAAa;AACb,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AACvD,OAAO,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AACrC,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,UAAU,EAAE,MAAM,0BAA0B,CAAC;AACtD,OAAO,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AAC/D,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AAEzD,kBAAkB;AAClB,OAAO,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,aAAa;AACb,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AACvD,OAAO,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AACrC,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,UAAU,EAAE,MAAM,0BAA0B,CAAC;AACtD,OAAO,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AAC/D,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAEpD,kBAAkB;AAClB,OAAO,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAC"}