orbiq-neural-ui-kit 1.1.28 → 1.1.29

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.
@@ -8269,222 +8269,954 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImpor
8269
8269
  args: ['popoverContent']
8270
8270
  }] } });
8271
8271
 
8272
- class NeuralBottomSheetComponent {
8272
+ class NeuralDialogComponent {
8273
8273
  dialog;
8274
- title = input('', /* @ts-ignore */
8275
- ...(ngDevMode ? [{ debugName: "title" }] : /* istanbul ignore next */ []));
8274
+ viewContainerRef;
8275
+ openModel = model(false, /* @ts-ignore */
8276
+ ...(ngDevMode ? [{ debugName: "openModel" }] : /* istanbul ignore next */ []));
8277
+ title = input(/* @ts-ignore */
8278
+ ...(ngDevMode ? [undefined, { debugName: "title" }] : /* istanbul ignore next */ []));
8279
+ message = input(/* @ts-ignore */
8280
+ ...(ngDevMode ? [undefined, { debugName: "message" }] : /* istanbul ignore next */ []));
8281
+ icon = input(/* @ts-ignore */
8282
+ ...(ngDevMode ? [undefined, { debugName: "icon" }] : /* istanbul ignore next */ []));
8283
+ size = input('lg', /* @ts-ignore */
8284
+ ...(ngDevMode ? [{ debugName: "size" }] : /* istanbul ignore next */ []));
8285
+ position = input('center', /* @ts-ignore */
8286
+ ...(ngDevMode ? [{ debugName: "position" }] : /* istanbul ignore next */ []));
8287
+ paddingTop = input(/* @ts-ignore */
8288
+ ...(ngDevMode ? [undefined, { debugName: "paddingTop" }] : /* istanbul ignore next */ []));
8289
+ actions = input([], /* @ts-ignore */
8290
+ ...(ngDevMode ? [{ debugName: "actions" }] : /* istanbul ignore next */ []));
8276
8291
  dismissible = input(true, /* @ts-ignore */
8277
8292
  ...(ngDevMode ? [{ debugName: "dismissible" }] : /* istanbul ignore next */ []));
8278
- openChange = new EventEmitter();
8279
- sheetTemplate;
8293
+ showCloseButton = input(true, /* @ts-ignore */
8294
+ ...(ngDevMode ? [{ debugName: "showCloseButton" }] : /* istanbul ignore next */ []));
8295
+ bare = input(false, /* @ts-ignore */
8296
+ ...(ngDevMode ? [{ debugName: "bare" }] : /* istanbul ignore next */ []));
8297
+ hasTitleSlot = input(false, /* @ts-ignore */
8298
+ ...(ngDevMode ? [{ debugName: "hasTitleSlot" }] : /* istanbul ignore next */ []));
8299
+ hasActionsSlot = input(false, /* @ts-ignore */
8300
+ ...(ngDevMode ? [{ debugName: "hasActionsSlot" }] : /* istanbul ignore next */ []));
8301
+ hasDefaultSlot = input(false, /* @ts-ignore */
8302
+ ...(ngDevMode ? [{ debugName: "hasDefaultSlot" }] : /* istanbul ignore next */ []));
8303
+ dialogTemplate;
8280
8304
  dialogRef = null;
8281
- _isOpen = false;
8282
- constructor(dialog) {
8305
+ internalActionsState = {}; // track loading states
8306
+ constructor(dialog, viewContainerRef) {
8283
8307
  this.dialog = dialog;
8308
+ this.viewContainerRef = viewContainerRef;
8309
+ effect(() => {
8310
+ const isOpen = this.openModel();
8311
+ if (isOpen && !this.dialogRef && this.dialogTemplate) {
8312
+ this.openDialog();
8313
+ }
8314
+ else if (!isOpen && this.dialogRef) {
8315
+ this.dialogRef.close();
8316
+ this.dialogRef = null;
8317
+ }
8318
+ });
8284
8319
  }
8285
- set open(value) {
8286
- if (value && !this._isOpen) {
8287
- this.openSheet();
8288
- }
8289
- else if (!value && this._isOpen) {
8290
- this.closeSheet();
8291
- }
8292
- }
8293
- get open() {
8294
- return this._isOpen;
8295
- }
8296
- openSheet() {
8297
- if (this._isOpen)
8298
- return;
8299
- this._isOpen = true;
8300
- this.openChange.emit(true);
8301
- this.dialogRef = this.dialog.open(this.sheetTemplate, {
8302
- panelClass: 'neural-bottom-sheet-panel',
8303
- backdropClass: ['fixed', 'inset-0', 'z-50', 'bg-black-overlay-200', 'dark:bg-black-overlay-700'],
8304
- hasBackdrop: true,
8320
+ openDialog() {
8321
+ this.dialogRef = this.dialog.open(this.dialogTemplate, {
8305
8322
  disableClose: !this.dismissible(),
8323
+ backdropClass: 'bg-black-overlay-200', // To match Frappe UI
8324
+ panelClass: ['w-full', 'h-full', 'bg-transparent', 'shadow-none'],
8325
+ hasBackdrop: true,
8326
+ viewContainerRef: this.viewContainerRef,
8306
8327
  });
8307
8328
  this.dialogRef.closed.subscribe(() => {
8308
- this._isOpen = false;
8309
- this.openChange.emit(false);
8310
8329
  this.dialogRef = null;
8330
+ if (this.openModel()) {
8331
+ this.openModel.set(false);
8332
+ }
8311
8333
  });
8312
8334
  }
8313
- closeSheet() {
8335
+ close() {
8314
8336
  if (this.dialogRef) {
8315
8337
  this.dialogRef.close();
8316
8338
  }
8317
8339
  }
8318
- ngOnDestroy() {
8319
- this.closeSheet();
8320
- }
8321
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralBottomSheetComponent, deps: [{ token: i1$3.Dialog }], target: i0.ɵɵFactoryTarget.Component });
8322
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralBottomSheetComponent, isStandalone: true, selector: "neural-bottom-sheet", inputs: { title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, dismissible: { classPropertyName: "dismissible", publicName: "dismissible", isSignal: true, isRequired: false, transformFunction: null }, open: { classPropertyName: "open", publicName: "open", isSignal: false, isRequired: false, transformFunction: null } }, outputs: { openChange: "openChange" }, viewQueries: [{ propertyName: "sheetTemplate", first: true, predicate: ["sheetTemplate"], descendants: true }], ngImport: i0, template: `
8323
- <!-- We don't render the trigger directly here if we want to use it as a wrapper,
8324
- but typically bottom sheets are opened programmatically or via a button -->
8325
- <ng-template #sheetTemplate>
8326
- <div
8327
- class="fixed inset-x-0 bottom-0 z-50 mx-auto flex max-h-[90dvh] w-full max-w-2xl flex-col rounded-t-[36px] bg-surface-base shadow-lg bottom-sheet-content focus:outline-none after:pointer-events-none after:absolute after:inset-x-0 after:top-full after:h-screen after:bg-surface-base"
8328
- role="dialog"
8329
- [attr.aria-label]="title() || 'Bottom sheet'"
8330
- data-state="open"
8331
- >
8332
- <div class="shrink-0 cursor-grab touch-none select-none active:cursor-grabbing">
8333
- <div class="flex justify-center pb-2 pt-3">
8334
- <div class="h-1.5 w-10 rounded-full bg-surface-gray-3"></div>
8335
- </div>
8336
- @if (title()) {
8337
- <div class="px-2 pb-3 pt-2 text-center text-3xl-semibold text-ink-gray-9">
8338
- {{ title() }}
8339
- </div>
8340
- }
8341
- </div>
8342
- <div class="min-h-0 touch-pan-y overflow-y-auto overscroll-contain">
8343
- <ng-content></ng-content>
8344
- </div>
8345
- </div>
8346
- </ng-template>
8347
- `, isInline: true, styles: ["@keyframes bottom-sheet-content-in{0%{transform:translateY(100%)}to{transform:translateY(0)}}@keyframes bottom-sheet-content-out{0%{transform:translateY(0)}to{transform:translateY(100%)}}.bottom-sheet-content[data-state=open]:not([data-dragged]){animation:bottom-sheet-content-in .3s cubic-bezier(.32,.72,0,1)}.bottom-sheet-content[data-state=closed]{animation:bottom-sheet-content-out .2s ease-in}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: DialogModule }] });
8348
- }
8349
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralBottomSheetComponent, decorators: [{
8350
- type: Component,
8351
- args: [{ selector: 'neural-bottom-sheet', standalone: true, imports: [CommonModule, DialogModule], template: `
8352
- <!-- We don't render the trigger directly here if we want to use it as a wrapper,
8353
- but typically bottom sheets are opened programmatically or via a button -->
8354
- <ng-template #sheetTemplate>
8355
- <div
8356
- class="fixed inset-x-0 bottom-0 z-50 mx-auto flex max-h-[90dvh] w-full max-w-2xl flex-col rounded-t-[36px] bg-surface-base shadow-lg bottom-sheet-content focus:outline-none after:pointer-events-none after:absolute after:inset-x-0 after:top-full after:h-screen after:bg-surface-base"
8357
- role="dialog"
8358
- [attr.aria-label]="title() || 'Bottom sheet'"
8359
- data-state="open"
8360
- >
8361
- <div class="shrink-0 cursor-grab touch-none select-none active:cursor-grabbing">
8362
- <div class="flex justify-center pb-2 pt-3">
8363
- <div class="h-1.5 w-10 rounded-full bg-surface-gray-3"></div>
8364
- </div>
8365
- @if (title()) {
8366
- <div class="px-2 pb-3 pt-2 text-center text-3xl-semibold text-ink-gray-9">
8367
- {{ title() }}
8368
- </div>
8369
- }
8370
- </div>
8371
- <div class="min-h-0 touch-pan-y overflow-y-auto overscroll-contain">
8372
- <ng-content></ng-content>
8373
- </div>
8374
- </div>
8375
- </ng-template>
8376
- `, styles: ["@keyframes bottom-sheet-content-in{0%{transform:translateY(100%)}to{transform:translateY(0)}}@keyframes bottom-sheet-content-out{0%{transform:translateY(0)}to{transform:translateY(100%)}}.bottom-sheet-content[data-state=open]:not([data-dragged]){animation:bottom-sheet-content-in .3s cubic-bezier(.32,.72,0,1)}.bottom-sheet-content[data-state=closed]{animation:bottom-sheet-content-out .2s ease-in}\n"] }]
8377
- }], ctorParameters: () => [{ type: i1$3.Dialog }], propDecorators: { title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: false }] }], dismissible: [{ type: i0.Input, args: [{ isSignal: true, alias: "dismissible", required: false }] }], openChange: [{
8378
- type: Output
8379
- }], sheetTemplate: [{
8380
- type: ViewChild,
8381
- args: ['sheetTemplate']
8382
- }], open: [{
8383
- type: Input
8384
- }] } });
8385
-
8386
- const MONTH_NAMES = ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'];
8387
- const DAY_NAMES = ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'];
8388
- function getCalendarDates(month, year) {
8389
- const firstDay = new Date(year, month, 1);
8390
- const lastDay = new Date(year, month + 1, 0);
8391
- const dates = [];
8392
- // Fill leading days from prev month
8393
- for (let i = firstDay.getDay(); i > 0; i--) {
8394
- dates.push(new Date(year, month, 1 - i));
8395
- }
8396
- // Current month days
8397
- for (let d = 1; d <= lastDay.getDate(); d++) {
8398
- dates.push(new Date(year, month, d));
8399
- }
8400
- // Fill trailing days
8401
- const remaining = 42 - dates.length;
8402
- for (let i = 1; i <= remaining; i++) {
8403
- dates.push(new Date(year, month + 1, i));
8404
- }
8405
- return dates;
8406
- }
8407
- function isSameDay(a, b) {
8408
- return a.getFullYear() === b.getFullYear() && a.getMonth() === b.getMonth() && a.getDate() === b.getDate();
8409
- }
8410
- function dateStr(d) {
8411
- return d.toISOString().slice(0, 10);
8412
- }
8413
- class NeuralCalendarComponent {
8414
- events = input([], /* @ts-ignore */
8415
- ...(ngDevMode ? [{ debugName: "events" }] : /* istanbul ignore next */ []));
8416
- defaultView = input('Month', /* @ts-ignore */
8417
- ...(ngDevMode ? [{ debugName: "defaultView" }] : /* istanbul ignore next */ []));
8418
- disableViews = input([], /* @ts-ignore */
8419
- ...(ngDevMode ? [{ debugName: "disableViews" }] : /* istanbul ignore next */ []));
8420
- eventClick = new EventEmitter();
8421
- dateClick = new EventEmitter();
8422
- create = new EventEmitter();
8423
- update = new EventEmitter();
8424
- delete = new EventEmitter();
8425
- activeView = signal('Month', /* @ts-ignore */
8426
- ...(ngDevMode ? [{ debugName: "activeView" }] : /* istanbul ignore next */ []));
8427
- today = new Date();
8428
- currentYear = signal(this.today.getFullYear(), /* @ts-ignore */
8429
- ...(ngDevMode ? [{ debugName: "currentYear" }] : /* istanbul ignore next */ []));
8430
- currentMonth = signal(this.today.getMonth(), /* @ts-ignore */
8431
- ...(ngDevMode ? [{ debugName: "currentMonth" }] : /* istanbul ignore next */ []));
8432
- selectedDay = signal(new Date(), /* @ts-ignore */
8433
- ...(ngDevMode ? [{ debugName: "selectedDay" }] : /* istanbul ignore next */ []));
8434
- dayNames = DAY_NAMES;
8435
- MONTH_NAMES = MONTH_NAMES;
8436
- keyHandler = this.handleKey.bind(this);
8437
- enabledViews = computed(() => {
8438
- const all = ['Month', 'Week', 'Day'];
8439
- return all.filter(v => !this.disableViews().includes(v));
8440
- }, /* @ts-ignore */
8441
- ...(ngDevMode ? [{ debugName: "enabledViews" }] : /* istanbul ignore next */ []));
8442
- monthDates = computed(() => getCalendarDates(this.currentMonth(), this.currentYear()), /* @ts-ignore */
8443
- ...(ngDevMode ? [{ debugName: "monthDates" }] : /* istanbul ignore next */ []));
8444
- currentWeekDates = computed(() => {
8445
- const d = this.selectedDay();
8446
- const dow = d.getDay();
8447
- const start = new Date(d);
8448
- start.setDate(d.getDate() - dow);
8449
- return Array.from({ length: 7 }, (_, i) => {
8450
- const day = new Date(start);
8451
- day.setDate(start.getDate() + i);
8452
- return day;
8453
- });
8454
- }, /* @ts-ignore */
8455
- ...(ngDevMode ? [{ debugName: "currentWeekDates" }] : /* istanbul ignore next */ []));
8456
- currentMonthYear = computed(() => {
8457
- const v = this.activeView();
8458
- if (v === 'Day') {
8459
- const d = this.selectedDay();
8460
- return `${DAY_NAMES[d.getDay()]}, ${d.getDate()} ${MONTH_NAMES[d.getMonth()]} ${d.getFullYear()}`;
8461
- }
8462
- if (v === 'Week') {
8463
- const dates = this.currentWeekDates();
8464
- const first = dates[0];
8465
- const last = dates[6];
8466
- if (first.getMonth() === last.getMonth()) {
8467
- return `${MONTH_NAMES[first.getMonth()]} ${first.getFullYear()}`;
8340
+ onContainerClick(event) {
8341
+ const target = event.target;
8342
+ // Close if the click is on the scroll container or the flex wrapper (not inside the dialog card)
8343
+ if (target.classList.contains('dialog-scroll-container') || target.classList.contains('min-h-screen')) {
8344
+ if (this.dismissible()) {
8345
+ this.close();
8468
8346
  }
8469
- return `${MONTH_NAMES[first.getMonth()].slice(0, 3)} – ${MONTH_NAMES[last.getMonth()].slice(0, 3)} ${last.getFullYear()}`;
8470
8347
  }
8471
- return `${MONTH_NAMES[this.currentMonth()]} ${this.currentYear()}`;
8472
- }, /* @ts-ignore */
8473
- ...(ngDevMode ? [{ debugName: "currentMonthYear" }] : /* istanbul ignore next */ []));
8474
- ngOnInit() {
8475
- this.activeView.set(this.defaultView());
8476
- window.addEventListener('keydown', this.keyHandler);
8477
8348
  }
8478
8349
  ngOnDestroy() {
8479
- window.removeEventListener('keydown', this.keyHandler);
8350
+ if (this.dialogRef) {
8351
+ this.dialogRef.close();
8352
+ }
8480
8353
  }
8481
- handleKey(e) {
8482
- const target = e.target;
8483
- if (target?.tagName === 'INPUT' || target?.tagName === 'TEXTAREA' || target?.isContentEditable)
8484
- return;
8485
- if (e.key.toLowerCase() === 'm')
8486
- this.activeView.set('Month');
8487
- if (e.key.toLowerCase() === 'w')
8354
+ sizeClass = computed(() => {
8355
+ const map = {
8356
+ xs: 'max-w-xs',
8357
+ sm: 'max-w-sm',
8358
+ md: 'max-w-md',
8359
+ lg: 'max-w-lg',
8360
+ xl: 'max-w-xl',
8361
+ '2xl': 'max-w-2xl',
8362
+ '3xl': 'max-w-3xl',
8363
+ '4xl': 'max-w-4xl',
8364
+ '5xl': 'max-w-5xl',
8365
+ '6xl': 'max-w-6xl',
8366
+ '7xl': 'max-w-7xl',
8367
+ };
8368
+ return map[this.size()] || 'max-w-lg';
8369
+ }, /* @ts-ignore */
8370
+ ...(ngDevMode ? [{ debugName: "sizeClass" }] : /* istanbul ignore next */ []));
8371
+ iconName = computed(() => {
8372
+ const raw = this.icon();
8373
+ if (!raw)
8374
+ return '';
8375
+ return typeof raw === 'string' ? raw : raw.name;
8376
+ }, /* @ts-ignore */
8377
+ ...(ngDevMode ? [{ debugName: "iconName" }] : /* istanbul ignore next */ []));
8378
+ iconTheme = computed(() => {
8379
+ const raw = this.icon();
8380
+ if (typeof raw === 'object' && raw.theme)
8381
+ return raw.theme;
8382
+ return null;
8383
+ }, /* @ts-ignore */
8384
+ ...(ngDevMode ? [{ debugName: "iconTheme" }] : /* istanbul ignore next */ []));
8385
+ dialogIconBgClasses = computed(() => {
8386
+ const theme = this.iconTheme();
8387
+ if (!theme)
8388
+ return 'bg-surface-gray-2';
8389
+ const map = {
8390
+ amber: 'bg-surface-amber-2',
8391
+ blue: 'bg-surface-blue-2',
8392
+ red: 'bg-surface-red-2',
8393
+ green: 'bg-surface-green-2',
8394
+ };
8395
+ return map[theme] || 'bg-surface-gray-2';
8396
+ }, /* @ts-ignore */
8397
+ ...(ngDevMode ? [{ debugName: "dialogIconBgClasses" }] : /* istanbul ignore next */ []));
8398
+ dialogIconClasses = computed(() => {
8399
+ const theme = this.iconTheme();
8400
+ if (!theme)
8401
+ return 'text-ink-gray-5';
8402
+ const map = {
8403
+ amber: 'text-ink-amber-5',
8404
+ blue: 'text-ink-blue-5',
8405
+ red: 'text-ink-red-7',
8406
+ green: 'text-ink-green-5',
8407
+ };
8408
+ return map[theme] || 'text-ink-gray-5';
8409
+ }, /* @ts-ignore */
8410
+ ...(ngDevMode ? [{ debugName: "dialogIconClasses" }] : /* istanbul ignore next */ []));
8411
+ dialogPositionClasses = computed(() => {
8412
+ if (this.paddingTop())
8413
+ return '';
8414
+ return this.position() === 'top' ? 'pt-[20vh]' : 'justify-center';
8415
+ }, /* @ts-ignore */
8416
+ ...(ngDevMode ? [{ debugName: "dialogPositionClasses" }] : /* istanbul ignore next */ []));
8417
+ dialogPositionStyles = computed(() => {
8418
+ const pt = this.paddingTop();
8419
+ return pt ? { paddingTop: pt } : {};
8420
+ }, /* @ts-ignore */
8421
+ ...(ngDevMode ? [{ debugName: "dialogPositionStyles" }] : /* istanbul ignore next */ []));
8422
+ showHeader = computed(() => {
8423
+ if (this.bare())
8424
+ return false;
8425
+ if (this.hasTitleSlot())
8426
+ return true;
8427
+ if (this.title())
8428
+ return true;
8429
+ return false;
8430
+ }, /* @ts-ignore */
8431
+ ...(ngDevMode ? [{ debugName: "showHeader" }] : /* istanbul ignore next */ []));
8432
+ reactiveActions = computed(() => {
8433
+ if (this.bare())
8434
+ return [];
8435
+ return this.actions().map(action => {
8436
+ return {
8437
+ ...action,
8438
+ loading: this.internalActionsState[action.label] || false
8439
+ };
8440
+ });
8441
+ }, /* @ts-ignore */
8442
+ ...(ngDevMode ? [{ debugName: "reactiveActions" }] : /* istanbul ignore next */ []));
8443
+ isSingleActionFullWidth = computed(() => {
8444
+ const smallSizes = ['xs', 'sm', 'md'];
8445
+ return this.actions().length === 1 && smallSizes.includes(this.size());
8446
+ }, /* @ts-ignore */
8447
+ ...(ngDevMode ? [{ debugName: "isSingleActionFullWidth" }] : /* istanbul ignore next */ []));
8448
+ async onActionClick(action) {
8449
+ if (!action.onClick) {
8450
+ this.close();
8451
+ return;
8452
+ }
8453
+ this.internalActionsState[action.label] = true;
8454
+ // trigger change detection by recreating the reference since it's a signal reading internalState
8455
+ // Or we could just use a separate mechanism. Let's mutate and trust Angular template binding if we update state.
8456
+ // In signal components, we might need a signal for internalActionsState
8457
+ // For now, let's just await
8458
+ try {
8459
+ await action.onClick({ close: () => this.close() });
8460
+ }
8461
+ finally {
8462
+ this.internalActionsState[action.label] = false;
8463
+ }
8464
+ }
8465
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralDialogComponent, deps: [{ token: i1$3.Dialog }, { token: i0.ViewContainerRef }], target: i0.ɵɵFactoryTarget.Component });
8466
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralDialogComponent, isStandalone: true, selector: "neural-dialog", inputs: { openModel: { classPropertyName: "openModel", publicName: "openModel", isSignal: true, isRequired: false, transformFunction: null }, title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, message: { classPropertyName: "message", publicName: "message", isSignal: true, isRequired: false, transformFunction: null }, icon: { classPropertyName: "icon", publicName: "icon", isSignal: true, isRequired: false, transformFunction: null }, size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, position: { classPropertyName: "position", publicName: "position", isSignal: true, isRequired: false, transformFunction: null }, paddingTop: { classPropertyName: "paddingTop", publicName: "paddingTop", isSignal: true, isRequired: false, transformFunction: null }, actions: { classPropertyName: "actions", publicName: "actions", isSignal: true, isRequired: false, transformFunction: null }, dismissible: { classPropertyName: "dismissible", publicName: "dismissible", isSignal: true, isRequired: false, transformFunction: null }, showCloseButton: { classPropertyName: "showCloseButton", publicName: "showCloseButton", isSignal: true, isRequired: false, transformFunction: null }, bare: { classPropertyName: "bare", publicName: "bare", isSignal: true, isRequired: false, transformFunction: null }, hasTitleSlot: { classPropertyName: "hasTitleSlot", publicName: "hasTitleSlot", isSignal: true, isRequired: false, transformFunction: null }, hasActionsSlot: { classPropertyName: "hasActionsSlot", publicName: "hasActionsSlot", isSignal: true, isRequired: false, transformFunction: null }, hasDefaultSlot: { classPropertyName: "hasDefaultSlot", publicName: "hasDefaultSlot", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { openModel: "openModelChange" }, viewQueries: [{ propertyName: "dialogTemplate", first: true, predicate: ["dialogTemplate"], descendants: true }], ngImport: i0, template: `
8467
+ <ng-template #dialogTemplate>
8468
+ <div
8469
+ class="fixed inset-0 z-50 overflow-y-auto dialog-scroll-container"
8470
+ (click)="onContainerClick($event)"
8471
+ >
8472
+ <div
8473
+ class="flex min-h-screen flex-col items-center px-4 py-4 text-center"
8474
+ [class]="dialogPositionClasses()"
8475
+ [style]="dialogPositionStyles()"
8476
+ >
8477
+ <div
8478
+ class="my-8 inline-block w-full transform overflow-hidden rounded-7 bg-surface-elevation-1 text-start align-middle shadow-xl dialog-content focus-visible:outline-none"
8479
+ [class]="sizeClass()"
8480
+ >
8481
+ @if (bare()) {
8482
+ <ng-content></ng-content>
8483
+ } @else {
8484
+ <div class="bg-surface-elevation-1 px-4 pb-6 pt-5 sm:px-6">
8485
+ <div class="flex">
8486
+ <div class="w-full flex-1">
8487
+ @if (showHeader()) {
8488
+ <div class="mb-6 flex items-center justify-between">
8489
+ <div class="flex items-center space-x-2 flex-1">
8490
+ @if (icon()) {
8491
+ <div
8492
+ class="flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full"
8493
+ [class]="dialogIconBgClasses()"
8494
+ >
8495
+ <span [class]="iconName() + ' size-4 ' + dialogIconClasses()" aria-hidden="true"></span>
8496
+ </div>
8497
+ }
8498
+ <header class="flex-1">
8499
+ @if (hasTitleSlot()) {
8500
+ <ng-content select="[title]"></ng-content>
8501
+ } @else if (title()) {
8502
+ <h3 class="text-2xl-semibold leading-6 text-ink-gray-8">
8503
+ {{ title() }}
8504
+ </h3>
8505
+ }
8506
+ </header>
8507
+ </div>
8508
+ @if (showCloseButton()) {
8509
+ <neural-button variant="ghost" label="Close" (click)="close()">
8510
+ <span icon class="lucide-x size-4 text-ink-gray-9"></span>
8511
+ </neural-button>
8512
+ }
8513
+ </div>
8514
+ }
8515
+
8516
+ @if (hasDefaultSlot()) {
8517
+ <ng-content></ng-content>
8518
+ } @else if (message()) {
8519
+ <p class="text-p-base text-ink-gray-7">
8520
+ {{ message() }}
8521
+ </p>
8522
+ }
8523
+ </div>
8524
+ </div>
8525
+ </div>
8526
+
8527
+ @if (reactiveActions().length || hasActionsSlot()) {
8528
+ <div class="px-4 pb-7 pt-4 sm:px-6">
8529
+ @if (hasActionsSlot()) {
8530
+ <ng-content select="[actions]"></ng-content>
8531
+ } @else {
8532
+ <div [class]="isSingleActionFullWidth() ? '' : 'flex justify-end gap-2'">
8533
+ @for (action of reactiveActions(); track action.label) {
8534
+ <neural-button
8535
+ class="w-full sm:w-auto"
8536
+ [disabled]="action.disabled || false"
8537
+ [loading]="action.loading || false"
8538
+ [variant]="action.variant || 'solid'"
8539
+ [theme]="action.theme || 'gray'"
8540
+ (click)="onActionClick(action)"
8541
+ >
8542
+ {{ action.label }}
8543
+ @if (action.icon) {
8544
+ <span icon [class]="action.icon + ' size-4'"></span>
8545
+ }
8546
+ </neural-button>
8547
+ }
8548
+ </div>
8549
+ }
8550
+ </div>
8551
+ }
8552
+ }
8553
+
8554
+ @if (showCloseButton() && !showHeader() && !bare()) {
8555
+ <neural-button
8556
+ class="absolute right-4 top-4 z-10"
8557
+ variant="ghost"
8558
+ label="Close"
8559
+ (click)="close()"
8560
+ >
8561
+ <span icon class="lucide-x size-4 text-ink-gray-9"></span>
8562
+ </neural-button>
8563
+ }
8564
+ </div>
8565
+ </div>
8566
+ </div>
8567
+ </ng-template>
8568
+ `, isInline: true, dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: DialogModule }, { kind: "component", type: NeuralButtonComponent, selector: "neural-button", inputs: ["variant", "theme", "size", "type", "disabled", "loading", "icon", "iconLeft", "iconRight", "iconOnly"], outputs: ["clicked"] }] });
8569
+ }
8570
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralDialogComponent, decorators: [{
8571
+ type: Component,
8572
+ args: [{
8573
+ selector: 'neural-dialog',
8574
+ standalone: true,
8575
+ imports: [CommonModule, DialogModule, NeuralButtonComponent],
8576
+ template: `
8577
+ <ng-template #dialogTemplate>
8578
+ <div
8579
+ class="fixed inset-0 z-50 overflow-y-auto dialog-scroll-container"
8580
+ (click)="onContainerClick($event)"
8581
+ >
8582
+ <div
8583
+ class="flex min-h-screen flex-col items-center px-4 py-4 text-center"
8584
+ [class]="dialogPositionClasses()"
8585
+ [style]="dialogPositionStyles()"
8586
+ >
8587
+ <div
8588
+ class="my-8 inline-block w-full transform overflow-hidden rounded-7 bg-surface-elevation-1 text-start align-middle shadow-xl dialog-content focus-visible:outline-none"
8589
+ [class]="sizeClass()"
8590
+ >
8591
+ @if (bare()) {
8592
+ <ng-content></ng-content>
8593
+ } @else {
8594
+ <div class="bg-surface-elevation-1 px-4 pb-6 pt-5 sm:px-6">
8595
+ <div class="flex">
8596
+ <div class="w-full flex-1">
8597
+ @if (showHeader()) {
8598
+ <div class="mb-6 flex items-center justify-between">
8599
+ <div class="flex items-center space-x-2 flex-1">
8600
+ @if (icon()) {
8601
+ <div
8602
+ class="flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full"
8603
+ [class]="dialogIconBgClasses()"
8604
+ >
8605
+ <span [class]="iconName() + ' size-4 ' + dialogIconClasses()" aria-hidden="true"></span>
8606
+ </div>
8607
+ }
8608
+ <header class="flex-1">
8609
+ @if (hasTitleSlot()) {
8610
+ <ng-content select="[title]"></ng-content>
8611
+ } @else if (title()) {
8612
+ <h3 class="text-2xl-semibold leading-6 text-ink-gray-8">
8613
+ {{ title() }}
8614
+ </h3>
8615
+ }
8616
+ </header>
8617
+ </div>
8618
+ @if (showCloseButton()) {
8619
+ <neural-button variant="ghost" label="Close" (click)="close()">
8620
+ <span icon class="lucide-x size-4 text-ink-gray-9"></span>
8621
+ </neural-button>
8622
+ }
8623
+ </div>
8624
+ }
8625
+
8626
+ @if (hasDefaultSlot()) {
8627
+ <ng-content></ng-content>
8628
+ } @else if (message()) {
8629
+ <p class="text-p-base text-ink-gray-7">
8630
+ {{ message() }}
8631
+ </p>
8632
+ }
8633
+ </div>
8634
+ </div>
8635
+ </div>
8636
+
8637
+ @if (reactiveActions().length || hasActionsSlot()) {
8638
+ <div class="px-4 pb-7 pt-4 sm:px-6">
8639
+ @if (hasActionsSlot()) {
8640
+ <ng-content select="[actions]"></ng-content>
8641
+ } @else {
8642
+ <div [class]="isSingleActionFullWidth() ? '' : 'flex justify-end gap-2'">
8643
+ @for (action of reactiveActions(); track action.label) {
8644
+ <neural-button
8645
+ class="w-full sm:w-auto"
8646
+ [disabled]="action.disabled || false"
8647
+ [loading]="action.loading || false"
8648
+ [variant]="action.variant || 'solid'"
8649
+ [theme]="action.theme || 'gray'"
8650
+ (click)="onActionClick(action)"
8651
+ >
8652
+ {{ action.label }}
8653
+ @if (action.icon) {
8654
+ <span icon [class]="action.icon + ' size-4'"></span>
8655
+ }
8656
+ </neural-button>
8657
+ }
8658
+ </div>
8659
+ }
8660
+ </div>
8661
+ }
8662
+ }
8663
+
8664
+ @if (showCloseButton() && !showHeader() && !bare()) {
8665
+ <neural-button
8666
+ class="absolute right-4 top-4 z-10"
8667
+ variant="ghost"
8668
+ label="Close"
8669
+ (click)="close()"
8670
+ >
8671
+ <span icon class="lucide-x size-4 text-ink-gray-9"></span>
8672
+ </neural-button>
8673
+ }
8674
+ </div>
8675
+ </div>
8676
+ </div>
8677
+ </ng-template>
8678
+ `
8679
+ }]
8680
+ }], ctorParameters: () => [{ type: i1$3.Dialog }, { type: i0.ViewContainerRef }], propDecorators: { openModel: [{ type: i0.Input, args: [{ isSignal: true, alias: "openModel", required: false }] }, { type: i0.Output, args: ["openModelChange"] }], title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: false }] }], message: [{ type: i0.Input, args: [{ isSignal: true, alias: "message", required: false }] }], icon: [{ type: i0.Input, args: [{ isSignal: true, alias: "icon", required: false }] }], size: [{ type: i0.Input, args: [{ isSignal: true, alias: "size", required: false }] }], position: [{ type: i0.Input, args: [{ isSignal: true, alias: "position", required: false }] }], paddingTop: [{ type: i0.Input, args: [{ isSignal: true, alias: "paddingTop", required: false }] }], actions: [{ type: i0.Input, args: [{ isSignal: true, alias: "actions", required: false }] }], dismissible: [{ type: i0.Input, args: [{ isSignal: true, alias: "dismissible", required: false }] }], showCloseButton: [{ type: i0.Input, args: [{ isSignal: true, alias: "showCloseButton", required: false }] }], bare: [{ type: i0.Input, args: [{ isSignal: true, alias: "bare", required: false }] }], hasTitleSlot: [{ type: i0.Input, args: [{ isSignal: true, alias: "hasTitleSlot", required: false }] }], hasActionsSlot: [{ type: i0.Input, args: [{ isSignal: true, alias: "hasActionsSlot", required: false }] }], hasDefaultSlot: [{ type: i0.Input, args: [{ isSignal: true, alias: "hasDefaultSlot", required: false }] }], dialogTemplate: [{
8681
+ type: ViewChild,
8682
+ args: ['dialogTemplate']
8683
+ }] } });
8684
+
8685
+ class NeuralAwesomeBarComponent {
8686
+ searchInput;
8687
+ // Two-way binding for dialog visibility
8688
+ openModel = model(false, /* @ts-ignore */
8689
+ ...(ngDevMode ? [{ debugName: "openModel" }] : /* istanbul ignore next */ []));
8690
+ // Search query
8691
+ query = model('', /* @ts-ignore */
8692
+ ...(ngDevMode ? [{ debugName: "query" }] : /* istanbul ignore next */ []));
8693
+ // Filters
8694
+ filters = input([], /* @ts-ignore */
8695
+ ...(ngDevMode ? [{ debugName: "filters" }] : /* istanbul ignore next */ []));
8696
+ activeFilter = model('all', /* @ts-ignore */
8697
+ ...(ngDevMode ? [{ debugName: "activeFilter" }] : /* istanbul ignore next */ []));
8698
+ // Show empty state manually if the parent determines there are no results or it's pristine
8699
+ isEmpty = input(true, /* @ts-ignore */
8700
+ ...(ngDevMode ? [{ debugName: "isEmpty" }] : /* istanbul ignore next */ []));
8701
+ // Outputs
8702
+ onSearch = output();
8703
+ constructor() {
8704
+ effect(() => {
8705
+ // Auto focus input when dialog opens
8706
+ if (this.openModel() && this.searchInput) {
8707
+ setTimeout(() => {
8708
+ this.searchInput.nativeElement.focus();
8709
+ }, 50); // slight delay to allow dialog animation
8710
+ }
8711
+ });
8712
+ }
8713
+ ngAfterViewInit() {
8714
+ if (this.openModel() && this.searchInput) {
8715
+ setTimeout(() => {
8716
+ this.searchInput.nativeElement.focus();
8717
+ }, 50);
8718
+ }
8719
+ }
8720
+ // Computed properties for filters
8721
+ pinnedFilters = computed(() => {
8722
+ return this.filters().filter(f => f.pinned);
8723
+ }, /* @ts-ignore */
8724
+ ...(ngDevMode ? [{ debugName: "pinnedFilters" }] : /* istanbul ignore next */ []));
8725
+ unpinnedFilters = computed(() => {
8726
+ return this.filters().filter(f => !f.pinned);
8727
+ }, /* @ts-ignore */
8728
+ ...(ngDevMode ? [{ debugName: "unpinnedFilters" }] : /* istanbul ignore next */ []));
8729
+ moreFiltersOptions = computed(() => {
8730
+ return this.unpinnedFilters().map(filter => ({
8731
+ label: filter.label,
8732
+ onClick: () => this.selectFilter(filter.id)
8733
+ }));
8734
+ }, /* @ts-ignore */
8735
+ ...(ngDevMode ? [{ debugName: "moreFiltersOptions" }] : /* istanbul ignore next */ []));
8736
+ isUnpinnedFilterActive = computed(() => {
8737
+ const unpinned = this.unpinnedFilters();
8738
+ return unpinned.some(f => f.id === this.activeFilter());
8739
+ }, /* @ts-ignore */
8740
+ ...(ngDevMode ? [{ debugName: "isUnpinnedFilterActive" }] : /* istanbul ignore next */ []));
8741
+ showEmptyState = computed(() => {
8742
+ return this.isEmpty() || this.query().trim() === '';
8743
+ }, /* @ts-ignore */
8744
+ ...(ngDevMode ? [{ debugName: "showEmptyState" }] : /* istanbul ignore next */ []));
8745
+ // Handlers
8746
+ onQueryChange(value) {
8747
+ this.query.set(value);
8748
+ this.onSearch.emit(value);
8749
+ }
8750
+ clearQuery() {
8751
+ this.query.set('');
8752
+ this.onSearch.emit('');
8753
+ this.searchInput.nativeElement.focus();
8754
+ }
8755
+ selectFilter(filterId) {
8756
+ this.activeFilter.set(filterId);
8757
+ this.searchInput.nativeElement.focus();
8758
+ }
8759
+ handleKeydown(event) {
8760
+ if (event.key === 'Escape') {
8761
+ this.openModel.set(false);
8762
+ }
8763
+ // Up, Down, Enter logic is expected to be handled externally since we project results,
8764
+ // or we can emit events so the parent can handle it.
8765
+ }
8766
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralAwesomeBarComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
8767
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralAwesomeBarComponent, isStandalone: true, selector: "neural-awesome-bar", inputs: { openModel: { classPropertyName: "openModel", publicName: "openModel", isSignal: true, isRequired: false, transformFunction: null }, query: { classPropertyName: "query", publicName: "query", isSignal: true, isRequired: false, transformFunction: null }, filters: { classPropertyName: "filters", publicName: "filters", isSignal: true, isRequired: false, transformFunction: null }, activeFilter: { classPropertyName: "activeFilter", publicName: "activeFilter", isSignal: true, isRequired: false, transformFunction: null }, isEmpty: { classPropertyName: "isEmpty", publicName: "isEmpty", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { openModel: "openModelChange", query: "queryChange", activeFilter: "activeFilterChange", onSearch: "onSearch" }, viewQueries: [{ propertyName: "searchInput", first: true, predicate: ["searchInput"], descendants: true }], ngImport: i0, template: `
8768
+ <neural-dialog [(openModel)]="openModel" [bare]="true" size="2xl" position="top" paddingTop="10vh">
8769
+ <div class="flex flex-col bg-surface-base rounded-xl shadow-2xl overflow-hidden ring-1 ring-outline-gray-2 w-full max-h-[85vh]">
8770
+
8771
+ <!-- Search Input Header -->
8772
+ <div class="flex items-center px-4 py-3 border-b border-outline-gray-2 bg-surface-base">
8773
+ <i class="lucide-search size-5 text-ink-gray-5 mr-3"></i>
8774
+ <input
8775
+ #searchInput
8776
+ type="text"
8777
+ class="flex-1 bg-transparent border-none outline-none text-lg text-ink-gray-9 placeholder:text-ink-gray-4 focus:ring-0 p-0"
8778
+ placeholder="Buscar por cualquier cosa..."
8779
+ [ngModel]="query()"
8780
+ (ngModelChange)="onQueryChange($event)"
8781
+ (keydown)="handleKeydown($event)"
8782
+ />
8783
+ @if (query()) {
8784
+ <button
8785
+ class="flex items-center justify-center size-6 rounded-md hover:bg-surface-gray-2 transition-colors ml-2"
8786
+ (click)="clearQuery()"
8787
+ >
8788
+ <i class="lucide-x size-4 text-ink-gray-5"></i>
8789
+ </button>
8790
+ }
8791
+ </div>
8792
+
8793
+ <!-- Filters (Chips) -->
8794
+ @if (filters().length > 0) {
8795
+ <div class="flex items-center gap-2 px-4 py-2 border-b border-outline-gray-2 bg-surface-gray-1 overflow-x-auto no-scrollbar">
8796
+ <!-- Pinned Filters -->
8797
+ @for (filter of pinnedFilters(); track filter.id) {
8798
+ <button
8799
+ class="px-3 py-1 rounded-full text-xs font-medium whitespace-nowrap transition-colors"
8800
+ [class.bg-surface-gray-9]="activeFilter() === filter.id"
8801
+ [class.text-white]="activeFilter() === filter.id"
8802
+ [class.bg-surface-base]="activeFilter() !== filter.id"
8803
+ [class.text-ink-gray-7]="activeFilter() !== filter.id"
8804
+ [class.border]="activeFilter() !== filter.id"
8805
+ [class.border-outline-gray-3]="activeFilter() !== filter.id"
8806
+ [class.hover:bg-surface-gray-2]="activeFilter() !== filter.id"
8807
+ (click)="selectFilter(filter.id)"
8808
+ >
8809
+ {{ filter.label }}
8810
+ </button>
8811
+ }
8812
+
8813
+ <!-- Unpinned Filters (Dropdown) -->
8814
+ @if (unpinnedFilters().length > 0) {
8815
+ <div class="ml-auto">
8816
+ <neural-dropdown
8817
+ [options]="moreFiltersOptions()"
8818
+ [hasTriggerSlot]="true"
8819
+ align="end"
8820
+ >
8821
+ <button
8822
+ trigger
8823
+ class="flex items-center gap-1.5 px-3 py-1 rounded-full text-xs font-medium whitespace-nowrap transition-colors border border-outline-gray-3 bg-surface-base text-ink-gray-7 hover:bg-surface-gray-2"
8824
+ [class.bg-surface-gray-9]="isUnpinnedFilterActive()"
8825
+ [class.text-white]="isUnpinnedFilterActive()"
8826
+ >
8827
+ <i class="lucide-menu size-3.5"></i>
8828
+ Más
8829
+ </button>
8830
+ </neural-dropdown>
8831
+ </div>
8832
+ }
8833
+ </div>
8834
+ }
8835
+
8836
+ <!-- Content Area -->
8837
+ <div class="flex-1 overflow-y-auto">
8838
+ @if (showEmptyState()) {
8839
+ <!-- Empty State -->
8840
+ <div class="flex flex-col items-center justify-center py-16 px-4 text-center">
8841
+ <div class="size-16 rounded-full bg-surface-gray-2 flex items-center justify-center mb-4">
8842
+ <i class="lucide-search size-8 text-ink-gray-4"></i>
8843
+ </div>
8844
+ <h3 class="text-base font-semibold text-ink-gray-9 mb-1">Buscar por cualquier cosa</h3>
8845
+ <p class="text-sm text-ink-gray-5 max-w-sm">
8846
+ Escribe para buscar a través de módulos, clientes, productos y configuraciones.
8847
+ </p>
8848
+ </div>
8849
+ } @else {
8850
+ <!-- Results Projection -->
8851
+ <div class="p-2">
8852
+ <ng-content select="[results]"></ng-content>
8853
+ </div>
8854
+ }
8855
+ </div>
8856
+
8857
+ <!-- Footer Shortcuts -->
8858
+ <div class="flex items-center justify-between px-4 py-2 bg-surface-gray-1 border-t border-outline-gray-2 text-xs text-ink-gray-5">
8859
+ <div class="flex items-center gap-4">
8860
+ <span class="flex items-center gap-1.5">
8861
+ <kbd class="px-1.5 py-0.5 rounded border border-outline-gray-3 bg-surface-base font-sans text-[10px] text-ink-gray-7 shadow-sm">↑</kbd>
8862
+ <kbd class="px-1.5 py-0.5 rounded border border-outline-gray-3 bg-surface-base font-sans text-[10px] text-ink-gray-7 shadow-sm">↓</kbd>
8863
+ Navegar
8864
+ </span>
8865
+ <span class="flex items-center gap-1.5">
8866
+ <kbd class="px-1.5 py-0.5 rounded border border-outline-gray-3 bg-surface-base font-sans text-[10px] text-ink-gray-7 shadow-sm">↵</kbd>
8867
+ Seleccionar
8868
+ </span>
8869
+ </div>
8870
+ <div class="flex items-center gap-1.5 hidden sm:flex">
8871
+ <kbd class="px-1.5 py-0.5 rounded border border-outline-gray-3 bg-surface-base font-sans text-[10px] text-ink-gray-7 shadow-sm">esc</kbd>
8872
+ Cerrar
8873
+ </div>
8874
+ </div>
8875
+
8876
+ </div>
8877
+ </neural-dialog>
8878
+ `, isInline: true, styles: [".no-scrollbar::-webkit-scrollbar{display:none}.no-scrollbar{-ms-overflow-style:none;scrollbar-width:none}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1.DefaultValueAccessor, selector: "input:not([type=checkbox]):not([ngNoCva])[formControlName],textarea:not([ngNoCva])[formControlName],input:not([type=checkbox]):not([ngNoCva])[formControl],textarea:not([ngNoCva])[formControl],input:not([type=checkbox]):not([ngNoCva])[ngModel],textarea:not([ngNoCva])[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: NeuralDialogComponent, selector: "neural-dialog", inputs: ["openModel", "title", "message", "icon", "size", "position", "paddingTop", "actions", "dismissible", "showCloseButton", "bare", "hasTitleSlot", "hasActionsSlot", "hasDefaultSlot"], outputs: ["openModelChange"] }, { kind: "component", type: NeuralDropdownComponent, selector: "neural-dropdown", inputs: ["options", "side", "align", "offset", "buttonLabel", "hasTriggerSlot"] }] });
8879
+ }
8880
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralAwesomeBarComponent, decorators: [{
8881
+ type: Component,
8882
+ args: [{ selector: 'neural-awesome-bar', standalone: true, imports: [
8883
+ CommonModule,
8884
+ FormsModule,
8885
+ NeuralDialogComponent,
8886
+ NeuralDropdownComponent
8887
+ ], template: `
8888
+ <neural-dialog [(openModel)]="openModel" [bare]="true" size="2xl" position="top" paddingTop="10vh">
8889
+ <div class="flex flex-col bg-surface-base rounded-xl shadow-2xl overflow-hidden ring-1 ring-outline-gray-2 w-full max-h-[85vh]">
8890
+
8891
+ <!-- Search Input Header -->
8892
+ <div class="flex items-center px-4 py-3 border-b border-outline-gray-2 bg-surface-base">
8893
+ <i class="lucide-search size-5 text-ink-gray-5 mr-3"></i>
8894
+ <input
8895
+ #searchInput
8896
+ type="text"
8897
+ class="flex-1 bg-transparent border-none outline-none text-lg text-ink-gray-9 placeholder:text-ink-gray-4 focus:ring-0 p-0"
8898
+ placeholder="Buscar por cualquier cosa..."
8899
+ [ngModel]="query()"
8900
+ (ngModelChange)="onQueryChange($event)"
8901
+ (keydown)="handleKeydown($event)"
8902
+ />
8903
+ @if (query()) {
8904
+ <button
8905
+ class="flex items-center justify-center size-6 rounded-md hover:bg-surface-gray-2 transition-colors ml-2"
8906
+ (click)="clearQuery()"
8907
+ >
8908
+ <i class="lucide-x size-4 text-ink-gray-5"></i>
8909
+ </button>
8910
+ }
8911
+ </div>
8912
+
8913
+ <!-- Filters (Chips) -->
8914
+ @if (filters().length > 0) {
8915
+ <div class="flex items-center gap-2 px-4 py-2 border-b border-outline-gray-2 bg-surface-gray-1 overflow-x-auto no-scrollbar">
8916
+ <!-- Pinned Filters -->
8917
+ @for (filter of pinnedFilters(); track filter.id) {
8918
+ <button
8919
+ class="px-3 py-1 rounded-full text-xs font-medium whitespace-nowrap transition-colors"
8920
+ [class.bg-surface-gray-9]="activeFilter() === filter.id"
8921
+ [class.text-white]="activeFilter() === filter.id"
8922
+ [class.bg-surface-base]="activeFilter() !== filter.id"
8923
+ [class.text-ink-gray-7]="activeFilter() !== filter.id"
8924
+ [class.border]="activeFilter() !== filter.id"
8925
+ [class.border-outline-gray-3]="activeFilter() !== filter.id"
8926
+ [class.hover:bg-surface-gray-2]="activeFilter() !== filter.id"
8927
+ (click)="selectFilter(filter.id)"
8928
+ >
8929
+ {{ filter.label }}
8930
+ </button>
8931
+ }
8932
+
8933
+ <!-- Unpinned Filters (Dropdown) -->
8934
+ @if (unpinnedFilters().length > 0) {
8935
+ <div class="ml-auto">
8936
+ <neural-dropdown
8937
+ [options]="moreFiltersOptions()"
8938
+ [hasTriggerSlot]="true"
8939
+ align="end"
8940
+ >
8941
+ <button
8942
+ trigger
8943
+ class="flex items-center gap-1.5 px-3 py-1 rounded-full text-xs font-medium whitespace-nowrap transition-colors border border-outline-gray-3 bg-surface-base text-ink-gray-7 hover:bg-surface-gray-2"
8944
+ [class.bg-surface-gray-9]="isUnpinnedFilterActive()"
8945
+ [class.text-white]="isUnpinnedFilterActive()"
8946
+ >
8947
+ <i class="lucide-menu size-3.5"></i>
8948
+ Más
8949
+ </button>
8950
+ </neural-dropdown>
8951
+ </div>
8952
+ }
8953
+ </div>
8954
+ }
8955
+
8956
+ <!-- Content Area -->
8957
+ <div class="flex-1 overflow-y-auto">
8958
+ @if (showEmptyState()) {
8959
+ <!-- Empty State -->
8960
+ <div class="flex flex-col items-center justify-center py-16 px-4 text-center">
8961
+ <div class="size-16 rounded-full bg-surface-gray-2 flex items-center justify-center mb-4">
8962
+ <i class="lucide-search size-8 text-ink-gray-4"></i>
8963
+ </div>
8964
+ <h3 class="text-base font-semibold text-ink-gray-9 mb-1">Buscar por cualquier cosa</h3>
8965
+ <p class="text-sm text-ink-gray-5 max-w-sm">
8966
+ Escribe para buscar a través de módulos, clientes, productos y configuraciones.
8967
+ </p>
8968
+ </div>
8969
+ } @else {
8970
+ <!-- Results Projection -->
8971
+ <div class="p-2">
8972
+ <ng-content select="[results]"></ng-content>
8973
+ </div>
8974
+ }
8975
+ </div>
8976
+
8977
+ <!-- Footer Shortcuts -->
8978
+ <div class="flex items-center justify-between px-4 py-2 bg-surface-gray-1 border-t border-outline-gray-2 text-xs text-ink-gray-5">
8979
+ <div class="flex items-center gap-4">
8980
+ <span class="flex items-center gap-1.5">
8981
+ <kbd class="px-1.5 py-0.5 rounded border border-outline-gray-3 bg-surface-base font-sans text-[10px] text-ink-gray-7 shadow-sm">↑</kbd>
8982
+ <kbd class="px-1.5 py-0.5 rounded border border-outline-gray-3 bg-surface-base font-sans text-[10px] text-ink-gray-7 shadow-sm">↓</kbd>
8983
+ Navegar
8984
+ </span>
8985
+ <span class="flex items-center gap-1.5">
8986
+ <kbd class="px-1.5 py-0.5 rounded border border-outline-gray-3 bg-surface-base font-sans text-[10px] text-ink-gray-7 shadow-sm">↵</kbd>
8987
+ Seleccionar
8988
+ </span>
8989
+ </div>
8990
+ <div class="flex items-center gap-1.5 hidden sm:flex">
8991
+ <kbd class="px-1.5 py-0.5 rounded border border-outline-gray-3 bg-surface-base font-sans text-[10px] text-ink-gray-7 shadow-sm">esc</kbd>
8992
+ Cerrar
8993
+ </div>
8994
+ </div>
8995
+
8996
+ </div>
8997
+ </neural-dialog>
8998
+ `, styles: [".no-scrollbar::-webkit-scrollbar{display:none}.no-scrollbar{-ms-overflow-style:none;scrollbar-width:none}\n"] }]
8999
+ }], ctorParameters: () => [], propDecorators: { searchInput: [{
9000
+ type: ViewChild,
9001
+ args: ['searchInput']
9002
+ }], openModel: [{ type: i0.Input, args: [{ isSignal: true, alias: "openModel", required: false }] }, { type: i0.Output, args: ["openModelChange"] }], query: [{ type: i0.Input, args: [{ isSignal: true, alias: "query", required: false }] }, { type: i0.Output, args: ["queryChange"] }], filters: [{ type: i0.Input, args: [{ isSignal: true, alias: "filters", required: false }] }], activeFilter: [{ type: i0.Input, args: [{ isSignal: true, alias: "activeFilter", required: false }] }, { type: i0.Output, args: ["activeFilterChange"] }], isEmpty: [{ type: i0.Input, args: [{ isSignal: true, alias: "isEmpty", required: false }] }], onSearch: [{ type: i0.Output, args: ["onSearch"] }] } });
9003
+
9004
+ class NeuralBottomSheetComponent {
9005
+ dialog;
9006
+ title = input('', /* @ts-ignore */
9007
+ ...(ngDevMode ? [{ debugName: "title" }] : /* istanbul ignore next */ []));
9008
+ dismissible = input(true, /* @ts-ignore */
9009
+ ...(ngDevMode ? [{ debugName: "dismissible" }] : /* istanbul ignore next */ []));
9010
+ openChange = new EventEmitter();
9011
+ sheetTemplate;
9012
+ dialogRef = null;
9013
+ _isOpen = false;
9014
+ constructor(dialog) {
9015
+ this.dialog = dialog;
9016
+ }
9017
+ set open(value) {
9018
+ if (value && !this._isOpen) {
9019
+ this.openSheet();
9020
+ }
9021
+ else if (!value && this._isOpen) {
9022
+ this.closeSheet();
9023
+ }
9024
+ }
9025
+ get open() {
9026
+ return this._isOpen;
9027
+ }
9028
+ openSheet() {
9029
+ if (this._isOpen)
9030
+ return;
9031
+ this._isOpen = true;
9032
+ this.openChange.emit(true);
9033
+ this.dialogRef = this.dialog.open(this.sheetTemplate, {
9034
+ panelClass: 'neural-bottom-sheet-panel',
9035
+ backdropClass: ['fixed', 'inset-0', 'z-50', 'bg-black-overlay-200', 'dark:bg-black-overlay-700'],
9036
+ hasBackdrop: true,
9037
+ disableClose: !this.dismissible(),
9038
+ });
9039
+ this.dialogRef.closed.subscribe(() => {
9040
+ this._isOpen = false;
9041
+ this.openChange.emit(false);
9042
+ this.dialogRef = null;
9043
+ });
9044
+ }
9045
+ closeSheet() {
9046
+ if (this.dialogRef) {
9047
+ this.dialogRef.close();
9048
+ }
9049
+ }
9050
+ ngOnDestroy() {
9051
+ this.closeSheet();
9052
+ }
9053
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralBottomSheetComponent, deps: [{ token: i1$3.Dialog }], target: i0.ɵɵFactoryTarget.Component });
9054
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralBottomSheetComponent, isStandalone: true, selector: "neural-bottom-sheet", inputs: { title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, dismissible: { classPropertyName: "dismissible", publicName: "dismissible", isSignal: true, isRequired: false, transformFunction: null }, open: { classPropertyName: "open", publicName: "open", isSignal: false, isRequired: false, transformFunction: null } }, outputs: { openChange: "openChange" }, viewQueries: [{ propertyName: "sheetTemplate", first: true, predicate: ["sheetTemplate"], descendants: true }], ngImport: i0, template: `
9055
+ <!-- We don't render the trigger directly here if we want to use it as a wrapper,
9056
+ but typically bottom sheets are opened programmatically or via a button -->
9057
+ <ng-template #sheetTemplate>
9058
+ <div
9059
+ class="fixed inset-x-0 bottom-0 z-50 mx-auto flex max-h-[90dvh] w-full max-w-2xl flex-col rounded-t-[36px] bg-surface-base shadow-lg bottom-sheet-content focus:outline-none after:pointer-events-none after:absolute after:inset-x-0 after:top-full after:h-screen after:bg-surface-base"
9060
+ role="dialog"
9061
+ [attr.aria-label]="title() || 'Bottom sheet'"
9062
+ data-state="open"
9063
+ >
9064
+ <div class="shrink-0 cursor-grab touch-none select-none active:cursor-grabbing">
9065
+ <div class="flex justify-center pb-2 pt-3">
9066
+ <div class="h-1.5 w-10 rounded-full bg-surface-gray-3"></div>
9067
+ </div>
9068
+ @if (title()) {
9069
+ <div class="px-2 pb-3 pt-2 text-center text-3xl-semibold text-ink-gray-9">
9070
+ {{ title() }}
9071
+ </div>
9072
+ }
9073
+ </div>
9074
+ <div class="min-h-0 touch-pan-y overflow-y-auto overscroll-contain">
9075
+ <ng-content></ng-content>
9076
+ </div>
9077
+ </div>
9078
+ </ng-template>
9079
+ `, isInline: true, styles: ["@keyframes bottom-sheet-content-in{0%{transform:translateY(100%)}to{transform:translateY(0)}}@keyframes bottom-sheet-content-out{0%{transform:translateY(0)}to{transform:translateY(100%)}}.bottom-sheet-content[data-state=open]:not([data-dragged]){animation:bottom-sheet-content-in .3s cubic-bezier(.32,.72,0,1)}.bottom-sheet-content[data-state=closed]{animation:bottom-sheet-content-out .2s ease-in}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: DialogModule }] });
9080
+ }
9081
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralBottomSheetComponent, decorators: [{
9082
+ type: Component,
9083
+ args: [{ selector: 'neural-bottom-sheet', standalone: true, imports: [CommonModule, DialogModule], template: `
9084
+ <!-- We don't render the trigger directly here if we want to use it as a wrapper,
9085
+ but typically bottom sheets are opened programmatically or via a button -->
9086
+ <ng-template #sheetTemplate>
9087
+ <div
9088
+ class="fixed inset-x-0 bottom-0 z-50 mx-auto flex max-h-[90dvh] w-full max-w-2xl flex-col rounded-t-[36px] bg-surface-base shadow-lg bottom-sheet-content focus:outline-none after:pointer-events-none after:absolute after:inset-x-0 after:top-full after:h-screen after:bg-surface-base"
9089
+ role="dialog"
9090
+ [attr.aria-label]="title() || 'Bottom sheet'"
9091
+ data-state="open"
9092
+ >
9093
+ <div class="shrink-0 cursor-grab touch-none select-none active:cursor-grabbing">
9094
+ <div class="flex justify-center pb-2 pt-3">
9095
+ <div class="h-1.5 w-10 rounded-full bg-surface-gray-3"></div>
9096
+ </div>
9097
+ @if (title()) {
9098
+ <div class="px-2 pb-3 pt-2 text-center text-3xl-semibold text-ink-gray-9">
9099
+ {{ title() }}
9100
+ </div>
9101
+ }
9102
+ </div>
9103
+ <div class="min-h-0 touch-pan-y overflow-y-auto overscroll-contain">
9104
+ <ng-content></ng-content>
9105
+ </div>
9106
+ </div>
9107
+ </ng-template>
9108
+ `, styles: ["@keyframes bottom-sheet-content-in{0%{transform:translateY(100%)}to{transform:translateY(0)}}@keyframes bottom-sheet-content-out{0%{transform:translateY(0)}to{transform:translateY(100%)}}.bottom-sheet-content[data-state=open]:not([data-dragged]){animation:bottom-sheet-content-in .3s cubic-bezier(.32,.72,0,1)}.bottom-sheet-content[data-state=closed]{animation:bottom-sheet-content-out .2s ease-in}\n"] }]
9109
+ }], ctorParameters: () => [{ type: i1$3.Dialog }], propDecorators: { title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: false }] }], dismissible: [{ type: i0.Input, args: [{ isSignal: true, alias: "dismissible", required: false }] }], openChange: [{
9110
+ type: Output
9111
+ }], sheetTemplate: [{
9112
+ type: ViewChild,
9113
+ args: ['sheetTemplate']
9114
+ }], open: [{
9115
+ type: Input
9116
+ }] } });
9117
+
9118
+ const MONTH_NAMES = ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'];
9119
+ const DAY_NAMES = ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'];
9120
+ function getCalendarDates(month, year) {
9121
+ const firstDay = new Date(year, month, 1);
9122
+ const lastDay = new Date(year, month + 1, 0);
9123
+ const dates = [];
9124
+ // Fill leading days from prev month
9125
+ for (let i = firstDay.getDay(); i > 0; i--) {
9126
+ dates.push(new Date(year, month, 1 - i));
9127
+ }
9128
+ // Current month days
9129
+ for (let d = 1; d <= lastDay.getDate(); d++) {
9130
+ dates.push(new Date(year, month, d));
9131
+ }
9132
+ // Fill trailing days
9133
+ const remaining = 42 - dates.length;
9134
+ for (let i = 1; i <= remaining; i++) {
9135
+ dates.push(new Date(year, month + 1, i));
9136
+ }
9137
+ return dates;
9138
+ }
9139
+ function isSameDay(a, b) {
9140
+ return a.getFullYear() === b.getFullYear() && a.getMonth() === b.getMonth() && a.getDate() === b.getDate();
9141
+ }
9142
+ function dateStr(d) {
9143
+ return d.toISOString().slice(0, 10);
9144
+ }
9145
+ class NeuralCalendarComponent {
9146
+ events = input([], /* @ts-ignore */
9147
+ ...(ngDevMode ? [{ debugName: "events" }] : /* istanbul ignore next */ []));
9148
+ defaultView = input('Month', /* @ts-ignore */
9149
+ ...(ngDevMode ? [{ debugName: "defaultView" }] : /* istanbul ignore next */ []));
9150
+ disableViews = input([], /* @ts-ignore */
9151
+ ...(ngDevMode ? [{ debugName: "disableViews" }] : /* istanbul ignore next */ []));
9152
+ eventClick = new EventEmitter();
9153
+ dateClick = new EventEmitter();
9154
+ create = new EventEmitter();
9155
+ update = new EventEmitter();
9156
+ delete = new EventEmitter();
9157
+ activeView = signal('Month', /* @ts-ignore */
9158
+ ...(ngDevMode ? [{ debugName: "activeView" }] : /* istanbul ignore next */ []));
9159
+ today = new Date();
9160
+ currentYear = signal(this.today.getFullYear(), /* @ts-ignore */
9161
+ ...(ngDevMode ? [{ debugName: "currentYear" }] : /* istanbul ignore next */ []));
9162
+ currentMonth = signal(this.today.getMonth(), /* @ts-ignore */
9163
+ ...(ngDevMode ? [{ debugName: "currentMonth" }] : /* istanbul ignore next */ []));
9164
+ selectedDay = signal(new Date(), /* @ts-ignore */
9165
+ ...(ngDevMode ? [{ debugName: "selectedDay" }] : /* istanbul ignore next */ []));
9166
+ dayNames = DAY_NAMES;
9167
+ MONTH_NAMES = MONTH_NAMES;
9168
+ keyHandler = this.handleKey.bind(this);
9169
+ enabledViews = computed(() => {
9170
+ const all = ['Month', 'Week', 'Day'];
9171
+ return all.filter(v => !this.disableViews().includes(v));
9172
+ }, /* @ts-ignore */
9173
+ ...(ngDevMode ? [{ debugName: "enabledViews" }] : /* istanbul ignore next */ []));
9174
+ monthDates = computed(() => getCalendarDates(this.currentMonth(), this.currentYear()), /* @ts-ignore */
9175
+ ...(ngDevMode ? [{ debugName: "monthDates" }] : /* istanbul ignore next */ []));
9176
+ currentWeekDates = computed(() => {
9177
+ const d = this.selectedDay();
9178
+ const dow = d.getDay();
9179
+ const start = new Date(d);
9180
+ start.setDate(d.getDate() - dow);
9181
+ return Array.from({ length: 7 }, (_, i) => {
9182
+ const day = new Date(start);
9183
+ day.setDate(start.getDate() + i);
9184
+ return day;
9185
+ });
9186
+ }, /* @ts-ignore */
9187
+ ...(ngDevMode ? [{ debugName: "currentWeekDates" }] : /* istanbul ignore next */ []));
9188
+ currentMonthYear = computed(() => {
9189
+ const v = this.activeView();
9190
+ if (v === 'Day') {
9191
+ const d = this.selectedDay();
9192
+ return `${DAY_NAMES[d.getDay()]}, ${d.getDate()} ${MONTH_NAMES[d.getMonth()]} ${d.getFullYear()}`;
9193
+ }
9194
+ if (v === 'Week') {
9195
+ const dates = this.currentWeekDates();
9196
+ const first = dates[0];
9197
+ const last = dates[6];
9198
+ if (first.getMonth() === last.getMonth()) {
9199
+ return `${MONTH_NAMES[first.getMonth()]} ${first.getFullYear()}`;
9200
+ }
9201
+ return `${MONTH_NAMES[first.getMonth()].slice(0, 3)} – ${MONTH_NAMES[last.getMonth()].slice(0, 3)} ${last.getFullYear()}`;
9202
+ }
9203
+ return `${MONTH_NAMES[this.currentMonth()]} ${this.currentYear()}`;
9204
+ }, /* @ts-ignore */
9205
+ ...(ngDevMode ? [{ debugName: "currentMonthYear" }] : /* istanbul ignore next */ []));
9206
+ ngOnInit() {
9207
+ this.activeView.set(this.defaultView());
9208
+ window.addEventListener('keydown', this.keyHandler);
9209
+ }
9210
+ ngOnDestroy() {
9211
+ window.removeEventListener('keydown', this.keyHandler);
9212
+ }
9213
+ handleKey(e) {
9214
+ const target = e.target;
9215
+ if (target?.tagName === 'INPUT' || target?.tagName === 'TEXTAREA' || target?.isContentEditable)
9216
+ return;
9217
+ if (e.key.toLowerCase() === 'm')
9218
+ this.activeView.set('Month');
9219
+ if (e.key.toLowerCase() === 'w')
8488
9220
  this.activeView.set('Week');
8489
9221
  if (e.key.toLowerCase() === 'd')
8490
9222
  this.activeView.set('Day');
@@ -10360,607 +11092,194 @@ class NeuralCodeEditorComponent {
10360
11092
  this.languageCompartment = new Compartment();
10361
11093
  this.disabledCompartment = new Compartment();
10362
11094
  this.variantCompartment = new Compartment();
10363
- this.sizeCompartment = new Compartment();
10364
- this.placeholderCompartment = new Compartment();
10365
- const theme = buildBaseTheme(this.cmView);
10366
- const highlight = await buildSyntaxHighlight(this.cmState);
10367
- const updateListener = EditorView.updateListener.of((update) => {
10368
- if (update.docChanged && !this.syncingFromProp) {
10369
- this.modelValue.set(update.state.doc.toString());
10370
- }
10371
- if (update.docChanged || update.geometryChanged) {
10372
- this.measureOverflow();
10373
- this.syncGutterShadow();
10374
- }
10375
- });
10376
- const blurHandler = EditorView.domEventHandlers({
10377
- blur: () => {
10378
- if (this.view)
10379
- this.change.emit(this.view.state.doc.toString());
10380
- },
10381
- });
10382
- const escapeHandler = EditorView.domEventHandlers({
10383
- keydown: (e, v) => {
10384
- if (e.key === 'Escape') {
10385
- v.contentDOM.blur();
10386
- return true;
10387
- }
10388
- return false;
10389
- },
10390
- });
10391
- if (!this.editorRoot?.nativeElement)
10392
- return;
10393
- this.view = new EditorView({
10394
- doc: this.modelValue() ?? '',
10395
- extensions: [
10396
- basicSetup,
10397
- this.cmView.keymap.of([indentWithTab]),
10398
- escapeHandler,
10399
- this.languageCompartment.of(await this.buildLanguageExtension(this.language())),
10400
- this.disabledCompartment.of(this.buildDisabled(!!this.disabled())),
10401
- updateListener,
10402
- blurHandler,
10403
- theme,
10404
- this.variantCompartment.of(this.buildVariant(this.variant(), this.disabled())),
10405
- this.sizeCompartment.of(this.buildSize(this.size())),
10406
- this.placeholderCompartment.of(this.buildPlaceholder(this.placeholder())),
10407
- highlight,
10408
- ],
10409
- parent: this.editorRoot.nativeElement,
10410
- });
10411
- this.measureOverflow();
10412
- this.view.scrollDOM.addEventListener('scroll', this.syncGutterShadow, { passive: true });
10413
- this.syncGutterShadow();
10414
- if (typeof ResizeObserver !== 'undefined') {
10415
- this.overflowObserver = new ResizeObserver(() => {
10416
- this.measureOverflow();
10417
- this.syncGutterShadow();
10418
- });
10419
- this.overflowObserver.observe(this.view.scrollDOM);
10420
- }
10421
- }
10422
- ngOnDestroy() {
10423
- this.overflowObserver?.disconnect();
10424
- if (this.view) {
10425
- this.view.scrollDOM.removeEventListener('scroll', this.syncGutterShadow);
10426
- this.view.destroy();
10427
- this.view = null;
10428
- }
10429
- }
10430
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralCodeEditorComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
10431
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralCodeEditorComponent, isStandalone: true, selector: "neural-code-editor", inputs: { modelValue: { classPropertyName: "modelValue", publicName: "modelValue", isSignal: true, isRequired: false, transformFunction: null }, language: { classPropertyName: "language", publicName: "language", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, variant: { classPropertyName: "variant", publicName: "variant", isSignal: true, isRequired: false, transformFunction: null }, size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, description: { classPropertyName: "description", publicName: "description", isSignal: true, isRequired: false, transformFunction: null }, error: { classPropertyName: "error", publicName: "error", isSignal: true, isRequired: false, transformFunction: null }, required: { classPropertyName: "required", publicName: "required", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { modelValue: "modelValueChange", overflow: "overflow", change: "change" }, viewQueries: [{ propertyName: "editorRoot", first: true, predicate: ["editorRoot"], descendants: true }], ngImport: i0, template: `
10432
- <neural-labeling-wrapper [enabled]="hasLabeling()">
10433
- @if (label()) {
10434
- <neural-input-label [id]="labelIdValue" [label]="label()" [required]="required()">
10435
- <ng-content select="[label]"></ng-content>
10436
- </neural-input-label>
10437
- }
10438
-
10439
- <div
10440
- #editorRoot
10441
- class="code-editor"
10442
- data-slot="control"
10443
- ></div>
10444
-
10445
- @if (description()) {
10446
- <neural-input-description [id]="descriptionIdValue" [description]="description()">
10447
- <ng-content select="[description]"></ng-content>
10448
- </neural-input-description>
10449
- }
10450
-
10451
- @if (errorLines().length) {
10452
- <neural-input-error [id]="errorIdValue" [lines]="errorLines()"></neural-input-error>
10453
- }
10454
- </neural-labeling-wrapper>
10455
- `, isInline: true, dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "component", type: NeuralInputLabelComponent, selector: "neural-input-label", inputs: ["id", "forId", "label", "required", "color", "disabled", "hasDefaultSlot"] }, { kind: "component", type: NeuralInputDescriptionComponent, selector: "neural-input-description", inputs: ["id", "description", "disabled", "hasDefaultSlot"] }, { kind: "component", type: NeuralInputErrorComponent, selector: "neural-input-error", inputs: ["id", "lines"] }, { kind: "component", type: NeuralLabelingWrapperComponent, selector: "neural-labeling-wrapper", inputs: ["enabled"] }] });
10456
- }
10457
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralCodeEditorComponent, decorators: [{
10458
- type: Component,
10459
- args: [{
10460
- selector: 'neural-code-editor',
10461
- standalone: true,
10462
- imports: [
10463
- CommonModule,
10464
- NeuralInputLabelComponent,
10465
- NeuralInputDescriptionComponent,
10466
- NeuralInputErrorComponent,
10467
- NeuralLabelingWrapperComponent
10468
- ],
10469
- template: `
10470
- <neural-labeling-wrapper [enabled]="hasLabeling()">
10471
- @if (label()) {
10472
- <neural-input-label [id]="labelIdValue" [label]="label()" [required]="required()">
10473
- <ng-content select="[label]"></ng-content>
10474
- </neural-input-label>
10475
- }
10476
-
10477
- <div
10478
- #editorRoot
10479
- class="code-editor"
10480
- data-slot="control"
10481
- ></div>
10482
-
10483
- @if (description()) {
10484
- <neural-input-description [id]="descriptionIdValue" [description]="description()">
10485
- <ng-content select="[description]"></ng-content>
10486
- </neural-input-description>
10487
- }
10488
-
10489
- @if (errorLines().length) {
10490
- <neural-input-error [id]="errorIdValue" [lines]="errorLines()"></neural-input-error>
10491
- }
10492
- </neural-labeling-wrapper>
10493
- `
10494
- }]
10495
- }], ctorParameters: () => [], propDecorators: { modelValue: [{ type: i0.Input, args: [{ isSignal: true, alias: "modelValue", required: false }] }, { type: i0.Output, args: ["modelValueChange"] }], language: [{ type: i0.Input, args: [{ isSignal: true, alias: "language", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], variant: [{ type: i0.Input, args: [{ isSignal: true, alias: "variant", required: false }] }], size: [{ type: i0.Input, args: [{ isSignal: true, alias: "size", required: false }] }], label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], description: [{ type: i0.Input, args: [{ isSignal: true, alias: "description", required: false }] }], error: [{ type: i0.Input, args: [{ isSignal: true, alias: "error", required: false }] }], required: [{ type: i0.Input, args: [{ isSignal: true, alias: "required", required: false }] }], overflow: [{
10496
- type: Output
10497
- }], change: [{
10498
- type: Output
10499
- }], editorRoot: [{
10500
- type: ViewChild,
10501
- args: ['editorRoot']
10502
- }] } });
10503
-
10504
- class NeuralCodePreviewComponent {
10505
- modelValue = input('', /* @ts-ignore */
10506
- ...(ngDevMode ? [{ debugName: "modelValue" }] : /* istanbul ignore next */ []));
10507
- language = input('plain', /* @ts-ignore */
10508
- ...(ngDevMode ? [{ debugName: "language" }] : /* istanbul ignore next */ []));
10509
- isPreviewLanguage = computed(() => this.language() === 'markdown' || this.language() === 'html', /* @ts-ignore */
10510
- ...(ngDevMode ? [{ debugName: "isPreviewLanguage" }] : /* istanbul ignore next */ []));
10511
- sanitized = computed(() => {
10512
- const src = this.modelValue() ?? '';
10513
- if (!src)
10514
- return '';
10515
- if (this.language() === 'markdown') {
10516
- return DOMPurify.sanitize(marked.parse(src));
10517
- }
10518
- if (this.language() === 'html') {
10519
- return DOMPurify.sanitize(src);
10520
- }
10521
- return '';
10522
- }, /* @ts-ignore */
10523
- ...(ngDevMode ? [{ debugName: "sanitized" }] : /* istanbul ignore next */ []));
10524
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralCodePreviewComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
10525
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralCodePreviewComponent, isStandalone: true, selector: "neural-code-preview", inputs: { modelValue: { classPropertyName: "modelValue", publicName: "modelValue", isSignal: true, isRequired: false, transformFunction: null }, language: { classPropertyName: "language", publicName: "language", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
10526
- @if (isPreviewLanguage()) {
10527
- <div
10528
- class="prose prose-sm max-w-none text-ink-gray-8"
10529
- [innerHTML]="sanitized()"
10530
- ></div>
10531
- }
10532
- `, isInline: true, dependencies: [{ kind: "ngmodule", type: CommonModule }] });
10533
- }
10534
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralCodePreviewComponent, decorators: [{
10535
- type: Component,
10536
- args: [{
10537
- selector: 'neural-code-preview',
10538
- standalone: true,
10539
- imports: [CommonModule],
10540
- template: `
10541
- @if (isPreviewLanguage()) {
10542
- <div
10543
- class="prose prose-sm max-w-none text-ink-gray-8"
10544
- [innerHTML]="sanitized()"
10545
- ></div>
10546
- }
10547
- `
10548
- }]
10549
- }], propDecorators: { modelValue: [{ type: i0.Input, args: [{ isSignal: true, alias: "modelValue", required: false }] }], language: [{ type: i0.Input, args: [{ isSignal: true, alias: "language", required: false }] }] } });
10550
-
10551
- class NeuralDialogComponent {
10552
- dialog;
10553
- viewContainerRef;
10554
- openModel = model(false, /* @ts-ignore */
10555
- ...(ngDevMode ? [{ debugName: "openModel" }] : /* istanbul ignore next */ []));
10556
- title = input(/* @ts-ignore */
10557
- ...(ngDevMode ? [undefined, { debugName: "title" }] : /* istanbul ignore next */ []));
10558
- message = input(/* @ts-ignore */
10559
- ...(ngDevMode ? [undefined, { debugName: "message" }] : /* istanbul ignore next */ []));
10560
- icon = input(/* @ts-ignore */
10561
- ...(ngDevMode ? [undefined, { debugName: "icon" }] : /* istanbul ignore next */ []));
10562
- size = input('lg', /* @ts-ignore */
10563
- ...(ngDevMode ? [{ debugName: "size" }] : /* istanbul ignore next */ []));
10564
- position = input('center', /* @ts-ignore */
10565
- ...(ngDevMode ? [{ debugName: "position" }] : /* istanbul ignore next */ []));
10566
- paddingTop = input(/* @ts-ignore */
10567
- ...(ngDevMode ? [undefined, { debugName: "paddingTop" }] : /* istanbul ignore next */ []));
10568
- actions = input([], /* @ts-ignore */
10569
- ...(ngDevMode ? [{ debugName: "actions" }] : /* istanbul ignore next */ []));
10570
- dismissible = input(true, /* @ts-ignore */
10571
- ...(ngDevMode ? [{ debugName: "dismissible" }] : /* istanbul ignore next */ []));
10572
- showCloseButton = input(true, /* @ts-ignore */
10573
- ...(ngDevMode ? [{ debugName: "showCloseButton" }] : /* istanbul ignore next */ []));
10574
- bare = input(false, /* @ts-ignore */
10575
- ...(ngDevMode ? [{ debugName: "bare" }] : /* istanbul ignore next */ []));
10576
- hasTitleSlot = input(false, /* @ts-ignore */
10577
- ...(ngDevMode ? [{ debugName: "hasTitleSlot" }] : /* istanbul ignore next */ []));
10578
- hasActionsSlot = input(false, /* @ts-ignore */
10579
- ...(ngDevMode ? [{ debugName: "hasActionsSlot" }] : /* istanbul ignore next */ []));
10580
- hasDefaultSlot = input(false, /* @ts-ignore */
10581
- ...(ngDevMode ? [{ debugName: "hasDefaultSlot" }] : /* istanbul ignore next */ []));
10582
- dialogTemplate;
10583
- dialogRef = null;
10584
- internalActionsState = {}; // track loading states
10585
- constructor(dialog, viewContainerRef) {
10586
- this.dialog = dialog;
10587
- this.viewContainerRef = viewContainerRef;
10588
- effect(() => {
10589
- const isOpen = this.openModel();
10590
- if (isOpen && !this.dialogRef && this.dialogTemplate) {
10591
- this.openDialog();
11095
+ this.sizeCompartment = new Compartment();
11096
+ this.placeholderCompartment = new Compartment();
11097
+ const theme = buildBaseTheme(this.cmView);
11098
+ const highlight = await buildSyntaxHighlight(this.cmState);
11099
+ const updateListener = EditorView.updateListener.of((update) => {
11100
+ if (update.docChanged && !this.syncingFromProp) {
11101
+ this.modelValue.set(update.state.doc.toString());
10592
11102
  }
10593
- else if (!isOpen && this.dialogRef) {
10594
- this.dialogRef.close();
10595
- this.dialogRef = null;
11103
+ if (update.docChanged || update.geometryChanged) {
11104
+ this.measureOverflow();
11105
+ this.syncGutterShadow();
10596
11106
  }
10597
11107
  });
10598
- }
10599
- openDialog() {
10600
- this.dialogRef = this.dialog.open(this.dialogTemplate, {
10601
- disableClose: !this.dismissible(),
10602
- backdropClass: 'bg-black-overlay-200', // To match Frappe UI
10603
- panelClass: ['w-full', 'h-full', 'bg-transparent', 'shadow-none'],
10604
- hasBackdrop: true,
10605
- viewContainerRef: this.viewContainerRef,
11108
+ const blurHandler = EditorView.domEventHandlers({
11109
+ blur: () => {
11110
+ if (this.view)
11111
+ this.change.emit(this.view.state.doc.toString());
11112
+ },
10606
11113
  });
10607
- this.dialogRef.closed.subscribe(() => {
10608
- this.dialogRef = null;
10609
- if (this.openModel()) {
10610
- this.openModel.set(false);
10611
- }
11114
+ const escapeHandler = EditorView.domEventHandlers({
11115
+ keydown: (e, v) => {
11116
+ if (e.key === 'Escape') {
11117
+ v.contentDOM.blur();
11118
+ return true;
11119
+ }
11120
+ return false;
11121
+ },
10612
11122
  });
10613
- }
10614
- close() {
10615
- if (this.dialogRef) {
10616
- this.dialogRef.close();
10617
- }
10618
- }
10619
- onContainerClick(event) {
10620
- const target = event.target;
10621
- // Close if the click is on the scroll container or the flex wrapper (not inside the dialog card)
10622
- if (target.classList.contains('dialog-scroll-container') || target.classList.contains('min-h-screen')) {
10623
- if (this.dismissible()) {
10624
- this.close();
10625
- }
11123
+ if (!this.editorRoot?.nativeElement)
11124
+ return;
11125
+ this.view = new EditorView({
11126
+ doc: this.modelValue() ?? '',
11127
+ extensions: [
11128
+ basicSetup,
11129
+ this.cmView.keymap.of([indentWithTab]),
11130
+ escapeHandler,
11131
+ this.languageCompartment.of(await this.buildLanguageExtension(this.language())),
11132
+ this.disabledCompartment.of(this.buildDisabled(!!this.disabled())),
11133
+ updateListener,
11134
+ blurHandler,
11135
+ theme,
11136
+ this.variantCompartment.of(this.buildVariant(this.variant(), this.disabled())),
11137
+ this.sizeCompartment.of(this.buildSize(this.size())),
11138
+ this.placeholderCompartment.of(this.buildPlaceholder(this.placeholder())),
11139
+ highlight,
11140
+ ],
11141
+ parent: this.editorRoot.nativeElement,
11142
+ });
11143
+ this.measureOverflow();
11144
+ this.view.scrollDOM.addEventListener('scroll', this.syncGutterShadow, { passive: true });
11145
+ this.syncGutterShadow();
11146
+ if (typeof ResizeObserver !== 'undefined') {
11147
+ this.overflowObserver = new ResizeObserver(() => {
11148
+ this.measureOverflow();
11149
+ this.syncGutterShadow();
11150
+ });
11151
+ this.overflowObserver.observe(this.view.scrollDOM);
10626
11152
  }
10627
11153
  }
10628
11154
  ngOnDestroy() {
10629
- if (this.dialogRef) {
10630
- this.dialogRef.close();
10631
- }
10632
- }
10633
- sizeClass = computed(() => {
10634
- const map = {
10635
- xs: 'max-w-xs',
10636
- sm: 'max-w-sm',
10637
- md: 'max-w-md',
10638
- lg: 'max-w-lg',
10639
- xl: 'max-w-xl',
10640
- '2xl': 'max-w-2xl',
10641
- '3xl': 'max-w-3xl',
10642
- '4xl': 'max-w-4xl',
10643
- '5xl': 'max-w-5xl',
10644
- '6xl': 'max-w-6xl',
10645
- '7xl': 'max-w-7xl',
10646
- };
10647
- return map[this.size()] || 'max-w-lg';
10648
- }, /* @ts-ignore */
10649
- ...(ngDevMode ? [{ debugName: "sizeClass" }] : /* istanbul ignore next */ []));
10650
- iconName = computed(() => {
10651
- const raw = this.icon();
10652
- if (!raw)
10653
- return '';
10654
- return typeof raw === 'string' ? raw : raw.name;
10655
- }, /* @ts-ignore */
10656
- ...(ngDevMode ? [{ debugName: "iconName" }] : /* istanbul ignore next */ []));
10657
- iconTheme = computed(() => {
10658
- const raw = this.icon();
10659
- if (typeof raw === 'object' && raw.theme)
10660
- return raw.theme;
10661
- return null;
10662
- }, /* @ts-ignore */
10663
- ...(ngDevMode ? [{ debugName: "iconTheme" }] : /* istanbul ignore next */ []));
10664
- dialogIconBgClasses = computed(() => {
10665
- const theme = this.iconTheme();
10666
- if (!theme)
10667
- return 'bg-surface-gray-2';
10668
- const map = {
10669
- amber: 'bg-surface-amber-2',
10670
- blue: 'bg-surface-blue-2',
10671
- red: 'bg-surface-red-2',
10672
- green: 'bg-surface-green-2',
10673
- };
10674
- return map[theme] || 'bg-surface-gray-2';
10675
- }, /* @ts-ignore */
10676
- ...(ngDevMode ? [{ debugName: "dialogIconBgClasses" }] : /* istanbul ignore next */ []));
10677
- dialogIconClasses = computed(() => {
10678
- const theme = this.iconTheme();
10679
- if (!theme)
10680
- return 'text-ink-gray-5';
10681
- const map = {
10682
- amber: 'text-ink-amber-5',
10683
- blue: 'text-ink-blue-5',
10684
- red: 'text-ink-red-7',
10685
- green: 'text-ink-green-5',
10686
- };
10687
- return map[theme] || 'text-ink-gray-5';
10688
- }, /* @ts-ignore */
10689
- ...(ngDevMode ? [{ debugName: "dialogIconClasses" }] : /* istanbul ignore next */ []));
10690
- dialogPositionClasses = computed(() => {
10691
- if (this.paddingTop())
10692
- return '';
10693
- return this.position() === 'top' ? 'pt-[20vh]' : 'justify-center';
10694
- }, /* @ts-ignore */
10695
- ...(ngDevMode ? [{ debugName: "dialogPositionClasses" }] : /* istanbul ignore next */ []));
10696
- dialogPositionStyles = computed(() => {
10697
- const pt = this.paddingTop();
10698
- return pt ? { paddingTop: pt } : {};
10699
- }, /* @ts-ignore */
10700
- ...(ngDevMode ? [{ debugName: "dialogPositionStyles" }] : /* istanbul ignore next */ []));
10701
- showHeader = computed(() => {
10702
- if (this.bare())
10703
- return false;
10704
- if (this.hasTitleSlot())
10705
- return true;
10706
- if (this.title())
10707
- return true;
10708
- return false;
10709
- }, /* @ts-ignore */
10710
- ...(ngDevMode ? [{ debugName: "showHeader" }] : /* istanbul ignore next */ []));
10711
- reactiveActions = computed(() => {
10712
- if (this.bare())
10713
- return [];
10714
- return this.actions().map(action => {
10715
- return {
10716
- ...action,
10717
- loading: this.internalActionsState[action.label] || false
10718
- };
10719
- });
10720
- }, /* @ts-ignore */
10721
- ...(ngDevMode ? [{ debugName: "reactiveActions" }] : /* istanbul ignore next */ []));
10722
- isSingleActionFullWidth = computed(() => {
10723
- const smallSizes = ['xs', 'sm', 'md'];
10724
- return this.actions().length === 1 && smallSizes.includes(this.size());
10725
- }, /* @ts-ignore */
10726
- ...(ngDevMode ? [{ debugName: "isSingleActionFullWidth" }] : /* istanbul ignore next */ []));
10727
- async onActionClick(action) {
10728
- if (!action.onClick) {
10729
- this.close();
10730
- return;
10731
- }
10732
- this.internalActionsState[action.label] = true;
10733
- // trigger change detection by recreating the reference since it's a signal reading internalState
10734
- // Or we could just use a separate mechanism. Let's mutate and trust Angular template binding if we update state.
10735
- // In signal components, we might need a signal for internalActionsState
10736
- // For now, let's just await
10737
- try {
10738
- await action.onClick({ close: () => this.close() });
10739
- }
10740
- finally {
10741
- this.internalActionsState[action.label] = false;
11155
+ this.overflowObserver?.disconnect();
11156
+ if (this.view) {
11157
+ this.view.scrollDOM.removeEventListener('scroll', this.syncGutterShadow);
11158
+ this.view.destroy();
11159
+ this.view = null;
10742
11160
  }
10743
11161
  }
10744
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralDialogComponent, deps: [{ token: i1$3.Dialog }, { token: i0.ViewContainerRef }], target: i0.ɵɵFactoryTarget.Component });
10745
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralDialogComponent, isStandalone: true, selector: "neural-dialog", inputs: { openModel: { classPropertyName: "openModel", publicName: "openModel", isSignal: true, isRequired: false, transformFunction: null }, title: { classPropertyName: "title", publicName: "title", isSignal: true, isRequired: false, transformFunction: null }, message: { classPropertyName: "message", publicName: "message", isSignal: true, isRequired: false, transformFunction: null }, icon: { classPropertyName: "icon", publicName: "icon", isSignal: true, isRequired: false, transformFunction: null }, size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, position: { classPropertyName: "position", publicName: "position", isSignal: true, isRequired: false, transformFunction: null }, paddingTop: { classPropertyName: "paddingTop", publicName: "paddingTop", isSignal: true, isRequired: false, transformFunction: null }, actions: { classPropertyName: "actions", publicName: "actions", isSignal: true, isRequired: false, transformFunction: null }, dismissible: { classPropertyName: "dismissible", publicName: "dismissible", isSignal: true, isRequired: false, transformFunction: null }, showCloseButton: { classPropertyName: "showCloseButton", publicName: "showCloseButton", isSignal: true, isRequired: false, transformFunction: null }, bare: { classPropertyName: "bare", publicName: "bare", isSignal: true, isRequired: false, transformFunction: null }, hasTitleSlot: { classPropertyName: "hasTitleSlot", publicName: "hasTitleSlot", isSignal: true, isRequired: false, transformFunction: null }, hasActionsSlot: { classPropertyName: "hasActionsSlot", publicName: "hasActionsSlot", isSignal: true, isRequired: false, transformFunction: null }, hasDefaultSlot: { classPropertyName: "hasDefaultSlot", publicName: "hasDefaultSlot", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { openModel: "openModelChange" }, viewQueries: [{ propertyName: "dialogTemplate", first: true, predicate: ["dialogTemplate"], descendants: true }], ngImport: i0, template: `
10746
- <ng-template #dialogTemplate>
10747
- <div
10748
- class="fixed inset-0 z-50 overflow-y-auto dialog-scroll-container"
10749
- (click)="onContainerClick($event)"
10750
- >
10751
- <div
10752
- class="flex min-h-screen flex-col items-center px-4 py-4 text-center"
10753
- [class]="dialogPositionClasses()"
10754
- [style]="dialogPositionStyles()"
10755
- >
10756
- <div
10757
- class="my-8 inline-block w-full transform overflow-hidden rounded-7 bg-surface-elevation-1 text-start align-middle shadow-xl dialog-content focus-visible:outline-none"
10758
- [class]="sizeClass()"
10759
- >
10760
- @if (bare()) {
10761
- <ng-content></ng-content>
10762
- } @else {
10763
- <div class="bg-surface-elevation-1 px-4 pb-6 pt-5 sm:px-6">
10764
- <div class="flex">
10765
- <div class="w-full flex-1">
10766
- @if (showHeader()) {
10767
- <div class="mb-6 flex items-center justify-between">
10768
- <div class="flex items-center space-x-2 flex-1">
10769
- @if (icon()) {
10770
- <div
10771
- class="flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full"
10772
- [class]="dialogIconBgClasses()"
10773
- >
10774
- <span [class]="iconName() + ' size-4 ' + dialogIconClasses()" aria-hidden="true"></span>
10775
- </div>
10776
- }
10777
- <header class="flex-1">
10778
- @if (hasTitleSlot()) {
10779
- <ng-content select="[title]"></ng-content>
10780
- } @else if (title()) {
10781
- <h3 class="text-2xl-semibold leading-6 text-ink-gray-8">
10782
- {{ title() }}
10783
- </h3>
10784
- }
10785
- </header>
10786
- </div>
10787
- @if (showCloseButton()) {
10788
- <neural-button variant="ghost" label="Close" (click)="close()">
10789
- <span icon class="lucide-x size-4 text-ink-gray-9"></span>
10790
- </neural-button>
10791
- }
10792
- </div>
10793
- }
11162
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralCodeEditorComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
11163
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralCodeEditorComponent, isStandalone: true, selector: "neural-code-editor", inputs: { modelValue: { classPropertyName: "modelValue", publicName: "modelValue", isSignal: true, isRequired: false, transformFunction: null }, language: { classPropertyName: "language", publicName: "language", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, placeholder: { classPropertyName: "placeholder", publicName: "placeholder", isSignal: true, isRequired: false, transformFunction: null }, variant: { classPropertyName: "variant", publicName: "variant", isSignal: true, isRequired: false, transformFunction: null }, size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null }, description: { classPropertyName: "description", publicName: "description", isSignal: true, isRequired: false, transformFunction: null }, error: { classPropertyName: "error", publicName: "error", isSignal: true, isRequired: false, transformFunction: null }, required: { classPropertyName: "required", publicName: "required", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { modelValue: "modelValueChange", overflow: "overflow", change: "change" }, viewQueries: [{ propertyName: "editorRoot", first: true, predicate: ["editorRoot"], descendants: true }], ngImport: i0, template: `
11164
+ <neural-labeling-wrapper [enabled]="hasLabeling()">
11165
+ @if (label()) {
11166
+ <neural-input-label [id]="labelIdValue" [label]="label()" [required]="required()">
11167
+ <ng-content select="[label]"></ng-content>
11168
+ </neural-input-label>
11169
+ }
10794
11170
 
10795
- @if (hasDefaultSlot()) {
10796
- <ng-content></ng-content>
10797
- } @else if (message()) {
10798
- <p class="text-p-base text-ink-gray-7">
10799
- {{ message() }}
10800
- </p>
10801
- }
10802
- </div>
10803
- </div>
10804
- </div>
11171
+ <div
11172
+ #editorRoot
11173
+ class="code-editor"
11174
+ data-slot="control"
11175
+ ></div>
10805
11176
 
10806
- @if (reactiveActions().length || hasActionsSlot()) {
10807
- <div class="px-4 pb-7 pt-4 sm:px-6">
10808
- @if (hasActionsSlot()) {
10809
- <ng-content select="[actions]"></ng-content>
10810
- } @else {
10811
- <div [class]="isSingleActionFullWidth() ? '' : 'flex justify-end gap-2'">
10812
- @for (action of reactiveActions(); track action.label) {
10813
- <neural-button
10814
- class="w-full sm:w-auto"
10815
- [disabled]="action.disabled || false"
10816
- [loading]="action.loading || false"
10817
- [variant]="action.variant || 'solid'"
10818
- [theme]="action.theme || 'gray'"
10819
- (click)="onActionClick(action)"
10820
- >
10821
- {{ action.label }}
10822
- @if (action.icon) {
10823
- <span icon [class]="action.icon + ' size-4'"></span>
10824
- }
10825
- </neural-button>
10826
- }
10827
- </div>
10828
- }
10829
- </div>
10830
- }
10831
- }
10832
-
10833
- @if (showCloseButton() && !showHeader() && !bare()) {
10834
- <neural-button
10835
- class="absolute right-4 top-4 z-10"
10836
- variant="ghost"
10837
- label="Close"
10838
- (click)="close()"
10839
- >
10840
- <span icon class="lucide-x size-4 text-ink-gray-9"></span>
10841
- </neural-button>
10842
- }
10843
- </div>
10844
- </div>
10845
- </div>
10846
- </ng-template>
10847
- `, isInline: true, dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: DialogModule }, { kind: "component", type: NeuralButtonComponent, selector: "neural-button", inputs: ["variant", "theme", "size", "type", "disabled", "loading", "icon", "iconLeft", "iconRight", "iconOnly"], outputs: ["clicked"] }] });
11177
+ @if (description()) {
11178
+ <neural-input-description [id]="descriptionIdValue" [description]="description()">
11179
+ <ng-content select="[description]"></ng-content>
11180
+ </neural-input-description>
11181
+ }
11182
+
11183
+ @if (errorLines().length) {
11184
+ <neural-input-error [id]="errorIdValue" [lines]="errorLines()"></neural-input-error>
11185
+ }
11186
+ </neural-labeling-wrapper>
11187
+ `, isInline: true, dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "component", type: NeuralInputLabelComponent, selector: "neural-input-label", inputs: ["id", "forId", "label", "required", "color", "disabled", "hasDefaultSlot"] }, { kind: "component", type: NeuralInputDescriptionComponent, selector: "neural-input-description", inputs: ["id", "description", "disabled", "hasDefaultSlot"] }, { kind: "component", type: NeuralInputErrorComponent, selector: "neural-input-error", inputs: ["id", "lines"] }, { kind: "component", type: NeuralLabelingWrapperComponent, selector: "neural-labeling-wrapper", inputs: ["enabled"] }] });
10848
11188
  }
10849
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralDialogComponent, decorators: [{
11189
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralCodeEditorComponent, decorators: [{
10850
11190
  type: Component,
10851
11191
  args: [{
10852
- selector: 'neural-dialog',
11192
+ selector: 'neural-code-editor',
10853
11193
  standalone: true,
10854
- imports: [CommonModule, DialogModule, NeuralButtonComponent],
11194
+ imports: [
11195
+ CommonModule,
11196
+ NeuralInputLabelComponent,
11197
+ NeuralInputDescriptionComponent,
11198
+ NeuralInputErrorComponent,
11199
+ NeuralLabelingWrapperComponent
11200
+ ],
10855
11201
  template: `
10856
- <ng-template #dialogTemplate>
10857
- <div
10858
- class="fixed inset-0 z-50 overflow-y-auto dialog-scroll-container"
10859
- (click)="onContainerClick($event)"
10860
- >
10861
- <div
10862
- class="flex min-h-screen flex-col items-center px-4 py-4 text-center"
10863
- [class]="dialogPositionClasses()"
10864
- [style]="dialogPositionStyles()"
10865
- >
10866
- <div
10867
- class="my-8 inline-block w-full transform overflow-hidden rounded-7 bg-surface-elevation-1 text-start align-middle shadow-xl dialog-content focus-visible:outline-none"
10868
- [class]="sizeClass()"
10869
- >
10870
- @if (bare()) {
10871
- <ng-content></ng-content>
10872
- } @else {
10873
- <div class="bg-surface-elevation-1 px-4 pb-6 pt-5 sm:px-6">
10874
- <div class="flex">
10875
- <div class="w-full flex-1">
10876
- @if (showHeader()) {
10877
- <div class="mb-6 flex items-center justify-between">
10878
- <div class="flex items-center space-x-2 flex-1">
10879
- @if (icon()) {
10880
- <div
10881
- class="flex h-7 w-7 flex-shrink-0 items-center justify-center rounded-full"
10882
- [class]="dialogIconBgClasses()"
10883
- >
10884
- <span [class]="iconName() + ' size-4 ' + dialogIconClasses()" aria-hidden="true"></span>
10885
- </div>
10886
- }
10887
- <header class="flex-1">
10888
- @if (hasTitleSlot()) {
10889
- <ng-content select="[title]"></ng-content>
10890
- } @else if (title()) {
10891
- <h3 class="text-2xl-semibold leading-6 text-ink-gray-8">
10892
- {{ title() }}
10893
- </h3>
10894
- }
10895
- </header>
10896
- </div>
10897
- @if (showCloseButton()) {
10898
- <neural-button variant="ghost" label="Close" (click)="close()">
10899
- <span icon class="lucide-x size-4 text-ink-gray-9"></span>
10900
- </neural-button>
10901
- }
10902
- </div>
10903
- }
11202
+ <neural-labeling-wrapper [enabled]="hasLabeling()">
11203
+ @if (label()) {
11204
+ <neural-input-label [id]="labelIdValue" [label]="label()" [required]="required()">
11205
+ <ng-content select="[label]"></ng-content>
11206
+ </neural-input-label>
11207
+ }
10904
11208
 
10905
- @if (hasDefaultSlot()) {
10906
- <ng-content></ng-content>
10907
- } @else if (message()) {
10908
- <p class="text-p-base text-ink-gray-7">
10909
- {{ message() }}
10910
- </p>
10911
- }
10912
- </div>
10913
- </div>
10914
- </div>
11209
+ <div
11210
+ #editorRoot
11211
+ class="code-editor"
11212
+ data-slot="control"
11213
+ ></div>
10915
11214
 
10916
- @if (reactiveActions().length || hasActionsSlot()) {
10917
- <div class="px-4 pb-7 pt-4 sm:px-6">
10918
- @if (hasActionsSlot()) {
10919
- <ng-content select="[actions]"></ng-content>
10920
- } @else {
10921
- <div [class]="isSingleActionFullWidth() ? '' : 'flex justify-end gap-2'">
10922
- @for (action of reactiveActions(); track action.label) {
10923
- <neural-button
10924
- class="w-full sm:w-auto"
10925
- [disabled]="action.disabled || false"
10926
- [loading]="action.loading || false"
10927
- [variant]="action.variant || 'solid'"
10928
- [theme]="action.theme || 'gray'"
10929
- (click)="onActionClick(action)"
10930
- >
10931
- {{ action.label }}
10932
- @if (action.icon) {
10933
- <span icon [class]="action.icon + ' size-4'"></span>
10934
- }
10935
- </neural-button>
10936
- }
10937
- </div>
10938
- }
10939
- </div>
10940
- }
10941
- }
10942
-
10943
- @if (showCloseButton() && !showHeader() && !bare()) {
10944
- <neural-button
10945
- class="absolute right-4 top-4 z-10"
10946
- variant="ghost"
10947
- label="Close"
10948
- (click)="close()"
10949
- >
10950
- <span icon class="lucide-x size-4 text-ink-gray-9"></span>
10951
- </neural-button>
10952
- }
10953
- </div>
10954
- </div>
10955
- </div>
10956
- </ng-template>
11215
+ @if (description()) {
11216
+ <neural-input-description [id]="descriptionIdValue" [description]="description()">
11217
+ <ng-content select="[description]"></ng-content>
11218
+ </neural-input-description>
11219
+ }
11220
+
11221
+ @if (errorLines().length) {
11222
+ <neural-input-error [id]="errorIdValue" [lines]="errorLines()"></neural-input-error>
11223
+ }
11224
+ </neural-labeling-wrapper>
10957
11225
  `
10958
11226
  }]
10959
- }], ctorParameters: () => [{ type: i1$3.Dialog }, { type: i0.ViewContainerRef }], propDecorators: { openModel: [{ type: i0.Input, args: [{ isSignal: true, alias: "openModel", required: false }] }, { type: i0.Output, args: ["openModelChange"] }], title: [{ type: i0.Input, args: [{ isSignal: true, alias: "title", required: false }] }], message: [{ type: i0.Input, args: [{ isSignal: true, alias: "message", required: false }] }], icon: [{ type: i0.Input, args: [{ isSignal: true, alias: "icon", required: false }] }], size: [{ type: i0.Input, args: [{ isSignal: true, alias: "size", required: false }] }], position: [{ type: i0.Input, args: [{ isSignal: true, alias: "position", required: false }] }], paddingTop: [{ type: i0.Input, args: [{ isSignal: true, alias: "paddingTop", required: false }] }], actions: [{ type: i0.Input, args: [{ isSignal: true, alias: "actions", required: false }] }], dismissible: [{ type: i0.Input, args: [{ isSignal: true, alias: "dismissible", required: false }] }], showCloseButton: [{ type: i0.Input, args: [{ isSignal: true, alias: "showCloseButton", required: false }] }], bare: [{ type: i0.Input, args: [{ isSignal: true, alias: "bare", required: false }] }], hasTitleSlot: [{ type: i0.Input, args: [{ isSignal: true, alias: "hasTitleSlot", required: false }] }], hasActionsSlot: [{ type: i0.Input, args: [{ isSignal: true, alias: "hasActionsSlot", required: false }] }], hasDefaultSlot: [{ type: i0.Input, args: [{ isSignal: true, alias: "hasDefaultSlot", required: false }] }], dialogTemplate: [{
11227
+ }], ctorParameters: () => [], propDecorators: { modelValue: [{ type: i0.Input, args: [{ isSignal: true, alias: "modelValue", required: false }] }, { type: i0.Output, args: ["modelValueChange"] }], language: [{ type: i0.Input, args: [{ isSignal: true, alias: "language", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], placeholder: [{ type: i0.Input, args: [{ isSignal: true, alias: "placeholder", required: false }] }], variant: [{ type: i0.Input, args: [{ isSignal: true, alias: "variant", required: false }] }], size: [{ type: i0.Input, args: [{ isSignal: true, alias: "size", required: false }] }], label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }], description: [{ type: i0.Input, args: [{ isSignal: true, alias: "description", required: false }] }], error: [{ type: i0.Input, args: [{ isSignal: true, alias: "error", required: false }] }], required: [{ type: i0.Input, args: [{ isSignal: true, alias: "required", required: false }] }], overflow: [{
11228
+ type: Output
11229
+ }], change: [{
11230
+ type: Output
11231
+ }], editorRoot: [{
10960
11232
  type: ViewChild,
10961
- args: ['dialogTemplate']
11233
+ args: ['editorRoot']
10962
11234
  }] } });
10963
11235
 
11236
+ class NeuralCodePreviewComponent {
11237
+ modelValue = input('', /* @ts-ignore */
11238
+ ...(ngDevMode ? [{ debugName: "modelValue" }] : /* istanbul ignore next */ []));
11239
+ language = input('plain', /* @ts-ignore */
11240
+ ...(ngDevMode ? [{ debugName: "language" }] : /* istanbul ignore next */ []));
11241
+ isPreviewLanguage = computed(() => this.language() === 'markdown' || this.language() === 'html', /* @ts-ignore */
11242
+ ...(ngDevMode ? [{ debugName: "isPreviewLanguage" }] : /* istanbul ignore next */ []));
11243
+ sanitized = computed(() => {
11244
+ const src = this.modelValue() ?? '';
11245
+ if (!src)
11246
+ return '';
11247
+ if (this.language() === 'markdown') {
11248
+ return DOMPurify.sanitize(marked.parse(src));
11249
+ }
11250
+ if (this.language() === 'html') {
11251
+ return DOMPurify.sanitize(src);
11252
+ }
11253
+ return '';
11254
+ }, /* @ts-ignore */
11255
+ ...(ngDevMode ? [{ debugName: "sanitized" }] : /* istanbul ignore next */ []));
11256
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralCodePreviewComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
11257
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "22.1.4", type: NeuralCodePreviewComponent, isStandalone: true, selector: "neural-code-preview", inputs: { modelValue: { classPropertyName: "modelValue", publicName: "modelValue", isSignal: true, isRequired: false, transformFunction: null }, language: { classPropertyName: "language", publicName: "language", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
11258
+ @if (isPreviewLanguage()) {
11259
+ <div
11260
+ class="prose prose-sm max-w-none text-ink-gray-8"
11261
+ [innerHTML]="sanitized()"
11262
+ ></div>
11263
+ }
11264
+ `, isInline: true, dependencies: [{ kind: "ngmodule", type: CommonModule }] });
11265
+ }
11266
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImport: i0, type: NeuralCodePreviewComponent, decorators: [{
11267
+ type: Component,
11268
+ args: [{
11269
+ selector: 'neural-code-preview',
11270
+ standalone: true,
11271
+ imports: [CommonModule],
11272
+ template: `
11273
+ @if (isPreviewLanguage()) {
11274
+ <div
11275
+ class="prose prose-sm max-w-none text-ink-gray-8"
11276
+ [innerHTML]="sanitized()"
11277
+ ></div>
11278
+ }
11279
+ `
11280
+ }]
11281
+ }], propDecorators: { modelValue: [{ type: i0.Input, args: [{ isSignal: true, alias: "modelValue", required: false }] }], language: [{ type: i0.Input, args: [{ isSignal: true, alias: "language", required: false }] }] } });
11282
+
10964
11283
  class NeuralCommandPaletteComponent {
10965
11284
  open = model(false, /* @ts-ignore */
10966
11285
  ...(ngDevMode ? [{ debugName: "open" }] : /* istanbul ignore next */ []));
@@ -15541,5 +15860,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.1.4", ngImpor
15541
15860
  * Generated bundle index. Do not edit.
15542
15861
  */
15543
15862
 
15544
- export { NeuralAccordionComponent, NeuralAlertComponent, NeuralAvatarComponent, NeuralAxisChartComponent, NeuralBadgeComponent, NeuralBottomSheetComponent, NeuralBreadcrumbsComponent, NeuralButtonComponent, NeuralCalendarComponent, NeuralCheckboxComponent, NeuralCodeEditorComponent, NeuralCodePreviewComponent, NeuralComboboxComponent, NeuralCommandPaletteComponent, NeuralContextMenuComponent, NeuralDataTableComponent, NeuralDatePickerComponent, NeuralDesktopShellComponent, NeuralDialogComponent, NeuralDividerComponent, NeuralDonutChartComponent, NeuralDrawerComponent, NeuralDropdownComponent, NeuralDurationComponent, NeuralEChartsComponent, NeuralEntityFormComponent, NeuralErrorMessageComponent, NeuralFileUploaderComponent, NeuralFilterBuilderComponent, NeuralFloatingWindowComponent, NeuralFooterComponent, NeuralFormControlComponent, NeuralFormLabelComponent, NeuralFunnelChartComponent, NeuralHoverCardComponent, NeuralIconComponent, NeuralInputDescriptionComponent, NeuralInputErrorComponent, NeuralInputLabelComponent, NeuralItemListRowComponent, NeuralKeyboardShortcutComponent, NeuralKeyboardShortcutsDialogComponent, NeuralLabelingWrapperComponent, NeuralListViewComponent, NeuralLoadingIndicatorComponent, NeuralLoadingTextComponent, NeuralMenuComponent, NeuralMobileNavComponent, NeuralMobileNavItemComponent, NeuralMobileShellComponent, NeuralMultiEmailInputComponent, NeuralMultiSelectComponent, NeuralNotificationCenterComponent, NeuralNumberChartComponent, NeuralPageHeaderComponent, NeuralPasswordComponent, NeuralPopoverComponent, NeuralPopoverContentDirective, NeuralPopoverPanelComponent, NeuralPopoverTriggerDirective, NeuralProgressComponent, NeuralRadioComponent, NeuralRadioGroupComponent, NeuralRailComponent, NeuralRailItemComponent, NeuralRatingComponent, NeuralRequiredIndicatorComponent, NeuralScrollAreaComponent, NeuralSearchTriggerComponent, NeuralSelectComponent, NeuralSettingsContentComponent, NeuralSettingsDialogComponent, NeuralSettingsNavItemComponent, NeuralSettingsPanelComponent, NeuralSettingsSidebarComponent, NeuralSidebarComponent, NeuralSidebarItemComponent, NeuralSkeletonComponent, NeuralSliderComponent, NeuralSpinnerComponent, NeuralSubGridComponent, NeuralSwitchComponent, NeuralTabComponent, NeuralTabPanelComponent, NeuralTabsComponent, NeuralTextEditorComponent, NeuralTextInputComponent, NeuralTextareaComponent, NeuralThemeSwitcherComponent, NeuralTimePickerComponent, NeuralToastComponent, NeuralTooltipComponent, NeuralTreeComponent, NeuralTreeItemComponent, RADIO_GROUP, TABS_ROOT, ToastService, formatDuration, parseDuration };
15863
+ export { NeuralAccordionComponent, NeuralAlertComponent, NeuralAvatarComponent, NeuralAwesomeBarComponent, NeuralAxisChartComponent, NeuralBadgeComponent, NeuralBottomSheetComponent, NeuralBreadcrumbsComponent, NeuralButtonComponent, NeuralCalendarComponent, NeuralCheckboxComponent, NeuralCodeEditorComponent, NeuralCodePreviewComponent, NeuralComboboxComponent, NeuralCommandPaletteComponent, NeuralContextMenuComponent, NeuralDataTableComponent, NeuralDatePickerComponent, NeuralDesktopShellComponent, NeuralDialogComponent, NeuralDividerComponent, NeuralDonutChartComponent, NeuralDrawerComponent, NeuralDropdownComponent, NeuralDurationComponent, NeuralEChartsComponent, NeuralEntityFormComponent, NeuralErrorMessageComponent, NeuralFileUploaderComponent, NeuralFilterBuilderComponent, NeuralFloatingWindowComponent, NeuralFooterComponent, NeuralFormControlComponent, NeuralFormLabelComponent, NeuralFunnelChartComponent, NeuralHoverCardComponent, NeuralIconComponent, NeuralInputDescriptionComponent, NeuralInputErrorComponent, NeuralInputLabelComponent, NeuralItemListRowComponent, NeuralKeyboardShortcutComponent, NeuralKeyboardShortcutsDialogComponent, NeuralLabelingWrapperComponent, NeuralListViewComponent, NeuralLoadingIndicatorComponent, NeuralLoadingTextComponent, NeuralMenuComponent, NeuralMobileNavComponent, NeuralMobileNavItemComponent, NeuralMobileShellComponent, NeuralMultiEmailInputComponent, NeuralMultiSelectComponent, NeuralNotificationCenterComponent, NeuralNumberChartComponent, NeuralPageHeaderComponent, NeuralPasswordComponent, NeuralPopoverComponent, NeuralPopoverContentDirective, NeuralPopoverPanelComponent, NeuralPopoverTriggerDirective, NeuralProgressComponent, NeuralRadioComponent, NeuralRadioGroupComponent, NeuralRailComponent, NeuralRailItemComponent, NeuralRatingComponent, NeuralRequiredIndicatorComponent, NeuralScrollAreaComponent, NeuralSearchTriggerComponent, NeuralSelectComponent, NeuralSettingsContentComponent, NeuralSettingsDialogComponent, NeuralSettingsNavItemComponent, NeuralSettingsPanelComponent, NeuralSettingsSidebarComponent, NeuralSidebarComponent, NeuralSidebarItemComponent, NeuralSkeletonComponent, NeuralSliderComponent, NeuralSpinnerComponent, NeuralSubGridComponent, NeuralSwitchComponent, NeuralTabComponent, NeuralTabPanelComponent, NeuralTabsComponent, NeuralTextEditorComponent, NeuralTextInputComponent, NeuralTextareaComponent, NeuralThemeSwitcherComponent, NeuralTimePickerComponent, NeuralToastComponent, NeuralTooltipComponent, NeuralTreeComponent, NeuralTreeItemComponent, RADIO_GROUP, TABS_ROOT, ToastService, formatDuration, parseDuration };
15545
15864
  //# sourceMappingURL=orbiq-neural-ui-kit.mjs.map