shirkasoft-ui-components 1.2.0 → 1.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/fesm2022/shirkasoft-ui-components-breadcrumb.mjs +199 -0
- package/fesm2022/shirkasoft-ui-components-breadcrumb.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-button.mjs +148 -0
- package/fesm2022/shirkasoft-ui-components-button.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-chart.mjs +153 -0
- package/fesm2022/shirkasoft-ui-components-chart.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-confirm-dialog.mjs +143 -0
- package/fesm2022/shirkasoft-ui-components-confirm-dialog.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-date-picker.mjs +638 -0
- package/fesm2022/shirkasoft-ui-components-date-picker.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-fieldset.mjs +94 -0
- package/fesm2022/shirkasoft-ui-components-fieldset.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-file-upload.mjs +242 -0
- package/fesm2022/shirkasoft-ui-components-file-upload.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-knob.mjs +269 -0
- package/fesm2022/shirkasoft-ui-components-knob.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-loading.mjs +255 -0
- package/fesm2022/shirkasoft-ui-components-loading.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-modal.mjs +290 -0
- package/fesm2022/shirkasoft-ui-components-modal.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-notification.mjs +143 -0
- package/fesm2022/shirkasoft-ui-components-notification.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-price-input.mjs +64 -0
- package/fesm2022/shirkasoft-ui-components-price-input.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-rail-sidebar.mjs +205 -0
- package/fesm2022/shirkasoft-ui-components-rail-sidebar.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-select.mjs +737 -0
- package/fesm2022/shirkasoft-ui-components-select.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-sidebar.mjs +185 -0
- package/fesm2022/shirkasoft-ui-components-sidebar.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-skeleton.mjs +74 -0
- package/fesm2022/shirkasoft-ui-components-skeleton.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-table.mjs +689 -0
- package/fesm2022/shirkasoft-ui-components-table.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-tabs.mjs +249 -0
- package/fesm2022/shirkasoft-ui-components-tabs.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-tag.mjs +70 -0
- package/fesm2022/shirkasoft-ui-components-tag.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-text-field.mjs +370 -0
- package/fesm2022/shirkasoft-ui-components-text-field.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-timeline.mjs +222 -0
- package/fesm2022/shirkasoft-ui-components-timeline.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-toggle.mjs +186 -0
- package/fesm2022/shirkasoft-ui-components-toggle.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-tooltip.mjs +169 -0
- package/fesm2022/shirkasoft-ui-components-tooltip.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-utils.mjs +64 -0
- package/fesm2022/shirkasoft-ui-components-utils.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components-wizard.mjs +167 -0
- package/fesm2022/shirkasoft-ui-components-wizard.mjs.map +1 -0
- package/fesm2022/shirkasoft-ui-components.mjs +0 -5729
- package/fesm2022/shirkasoft-ui-components.mjs.map +1 -1
- package/package.json +101 -1
- package/types/shirkasoft-ui-components-breadcrumb.d.ts +68 -0
- package/types/shirkasoft-ui-components-button.d.ts +59 -0
- package/types/shirkasoft-ui-components-chart.d.ts +65 -0
- package/types/shirkasoft-ui-components-confirm-dialog.d.ts +88 -0
- package/types/shirkasoft-ui-components-date-picker.d.ts +200 -0
- package/types/shirkasoft-ui-components-fieldset.d.ts +72 -0
- package/types/shirkasoft-ui-components-file-upload.d.ts +87 -0
- package/types/shirkasoft-ui-components-knob.d.ts +69 -0
- package/types/shirkasoft-ui-components-loading.d.ts +94 -0
- package/types/shirkasoft-ui-components-modal.d.ts +139 -0
- package/types/shirkasoft-ui-components-notification.d.ts +82 -0
- package/types/shirkasoft-ui-components-price-input.d.ts +41 -0
- package/types/shirkasoft-ui-components-rail-sidebar.d.ts +121 -0
- package/types/shirkasoft-ui-components-select.d.ts +182 -0
- package/types/shirkasoft-ui-components-sidebar.d.ts +106 -0
- package/types/shirkasoft-ui-components-skeleton.d.ts +36 -0
- package/types/shirkasoft-ui-components-table.d.ts +293 -0
- package/types/shirkasoft-ui-components-tabs.d.ts +102 -0
- package/types/shirkasoft-ui-components-tag.d.ts +31 -0
- package/types/shirkasoft-ui-components-text-field.d.ts +120 -0
- package/types/shirkasoft-ui-components-timeline.d.ts +178 -0
- package/types/shirkasoft-ui-components-toggle.d.ts +48 -0
- package/types/shirkasoft-ui-components-tooltip.d.ts +47 -0
- package/types/shirkasoft-ui-components-utils.d.ts +9 -0
- package/types/shirkasoft-ui-components-wizard.d.ts +101 -0
- package/types/shirkasoft-ui-components.d.ts +1 -2333
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"shirkasoft-ui-components-file-upload.mjs","sources":["../../../projects/ui-components/file-upload/file-upload.component.ts","../../../projects/ui-components/file-upload/file-upload.component.html","../../../projects/ui-components/file-upload/shirkasoft-ui-components-file-upload.ts"],"sourcesContent":["import { Component, input, output, signal, computed, ChangeDetectionStrategy, inject } from '@angular/core';\nimport { CommonModule } from '@angular/common';\nimport { TranslocoService } from '@jsverse/transloco';\nimport { LucideDynamicIcon, LucideUpload } from '@lucide/angular';\nimport { getIcon as getIconFromCentral } from 'shirkasoft-ui-components/utils';\n\nexport interface FileUploadError {\n type: 'size' | 'type';\n message: string;\n file: File;\n}\n\n/**\n * Shirkasoft UI Components.\n * Authors: Roberto Valladares Martin (Ansem13), Julio César García García (Sanjuli14).\n * Belongs to Shirkasoft.\n */\n\n/**\n * Drag & drop file uploader with file type/size validation, image previews,\n * multiple files support and localized error messages.\n */\n@Component({\n selector: 'shk-file-upload',\n standalone: true,\n imports: [CommonModule, LucideDynamicIcon],\n templateUrl: './file-upload.component.html',\n changeDetection: ChangeDetectionStrategy.OnPush,\n})\nexport class FileUploadComponent {\n protected getIcon = (name: any) => getIconFromCentral(name, LucideUpload);\n private transloco = inject(TranslocoService);\n\n /** Main label of the uploader. */\n label = input<string>('Cargar archivo');\n /** Accepted MIME types/extensions (e.g. 'image/*', '.pdf'). */\n accept = input<string>('image/*');\n /** Maximum allowed size per file (bytes). */\n maxFileSize = input<number>(2 * 1024 * 1024);\n /** Maximum number of files (0 = unlimited). */\n maxFiles = input<number>(0);\n /** Text of the file picker button. */\n fileUploadText = input<string>('Seleccionar archivo');\n /** Helper text shown next to the label. */\n fileRecommendation = input<string>('');\n /** Text shown when files are already loaded. */\n changeFilesText = input<string>('Cambiar archivos');\n /** Enables selecting more than one file at once. */\n multiple = input<boolean>(false);\n\n /** Emitted with the currently selected files. */\n fileSelected = output<File[]>();\n /** Emitted when the last selected file is removed. */\n fileRemoved = output<void>();\n /** Emitted when a file fails validation (type/size). */\n fileError = output<FileUploadError>();\n /** Emitted when a file is near the size limit. */\n fileWarning = output<FileUploadError>();\n\n /** Currently selected files. */\n selectedFiles = signal<File[]>([]);\n /** Localized error message displayed to the user. */\n errorMessage = signal<string>('');\n /** Whether the user is dragging files over the zone. */\n isDragOver = signal<boolean>(false);\n\n /** Object URLs used for image previews. */\n private previewUrls = new Map<File, string>();\n\n /** Whether another selection is allowed. */\n canAddMore = computed(() => {\n if (!this.multiple()) return this.selectedFiles().length === 0;\n const max = this.maxFiles();\n if (max <= 0) return true;\n return this.selectedFiles().length < max;\n });\n\n /** True when the maximum number of files has been reached. */\n maxReached = computed(() => {\n const max = this.maxFiles();\n if (max <= 0) return false;\n return this.selectedFiles().length >= max;\n });\n\n /** Whether the file is an image (used for previews). */\n isImageFile(file: File): boolean {\n return file.type.startsWith('image/');\n }\n\n /** Returns (creating on demand) the object URL for a file preview. */\n previewUrl(file: File): string {\n if (!this.previewUrls.has(file)) {\n this.previewUrls.set(file, URL.createObjectURL(file));\n }\n return this.previewUrls.get(file) ?? '';\n }\n\n /** Marks the drop zone as active while dragging over it. */\n onDragOver(event: DragEvent): void {\n event.preventDefault();\n event.stopPropagation();\n this.isDragOver.set(true);\n }\n\n /** Clears the drag-over state when the drag leaves the zone. */\n onDragLeave(event: DragEvent): void {\n event.preventDefault();\n event.stopPropagation();\n this.isDragOver.set(false);\n }\n\n /** Processes the files dropped on the zone. */\n onDrop(event: DragEvent): void {\n event.preventDefault();\n event.stopPropagation();\n this.isDragOver.set(false);\n\n const files = event.dataTransfer?.files;\n if (files && files.length > 0) {\n this.processFiles(Array.from(files));\n }\n }\n\n /** Processes the files picked from the native file input. */\n onFileChange(event: Event): void {\n const input = event.target as HTMLInputElement;\n const files = input.files;\n if (files && files.length > 0) {\n this.processFiles(Array.from(files));\n }\n input.value = '';\n }\n\n /** Validates and appends the received files, emitting errors/warnings. */\n private processFiles(files: File[]): void {\n this.errorMessage.set('');\n const validFiles: File[] = [];\n\n for (const file of files) {\n const error = this.validateFile(file);\n if (error) {\n this.fileError.emit(error);\n this.errorMessage.set(error.message);\n return;\n }\n\n const warning = this.checkSizeWarning(file);\n if (warning) {\n this.fileWarning.emit(warning);\n }\n\n validFiles.push(file);\n }\n\n const max = this.maxFiles();\n if (max > 0) {\n const currentCount = this.selectedFiles().length;\n const allowed = max - currentCount;\n if (validFiles.length > allowed) {\n const errorMsg = this.transloco.translate('fileUpload.maxFiles', undefined, `Máximo ${max} archivos permitidos`);\n this.errorMessage.set(errorMsg);\n return;\n }\n }\n\n if (this.multiple()) {\n this.selectedFiles.set([...this.selectedFiles(), ...validFiles]);\n } else {\n this.clearPreviews();\n this.selectedFiles.set(validFiles);\n }\n\n this.fileSelected.emit(this.selectedFiles());\n }\n\n /** Validates a file against `accept` and `maxFileSize`. */\n private validateFile(file: File): FileUploadError | null {\n const acceptStr = this.accept();\n if (acceptStr && acceptStr !== '*') {\n const acceptTypes = acceptStr.split(',').map((t) => t.trim());\n const valid = acceptTypes.some((type) => {\n if (type.endsWith('/*')) {\n const category = type.replace('/*', '');\n return file.type.startsWith(category);\n }\n if (type.startsWith('.')) {\n const ext = type.slice(1).toLowerCase();\n return file.name.toLowerCase().endsWith('.' + ext);\n }\n if (type.includes('/')) {\n return file.type === type;\n }\n return false;\n });\n\n if (!valid) {\n return {\n type: 'type',\n message: this.transloco.translate('fileUpload.invalidType', { accept: acceptStr }, `Tipo de archivo no válido. Formatos aceptados: ${acceptStr}`),\n file,\n };\n }\n }\n\n if (this.maxFileSize() > 0 && file.size > this.maxFileSize()) {\n return {\n type: 'size',\n message: this.transloco.translate('fileUpload.fileTooLarge', { size: this.formatFileSize(this.maxFileSize()) }, `El archivo excede el tamaño máximo de ${this.formatFileSize(this.maxFileSize())}`),\n file,\n };\n }\n\n return null;\n }\n\n /** Emits a warning when the file is close to the size limit (>90%). */\n private checkSizeWarning(file: File): FileUploadError | null {\n if (this.maxFileSize() > 0 && file.size > this.maxFileSize() * 0.9) {\n return {\n type: 'size',\n message: this.transloco.translate('fileUpload.sizeWarning', { size: this.formatFileSize(this.maxFileSize()) }, `El archivo está cerca del límite de tamaño (${this.formatFileSize(this.maxFileSize())})`),\n file,\n };\n }\n return null;\n }\n\n /** Removes a file, revoking its preview URL. */\n removeFile(file: File): void {\n const url = this.previewUrls.get(file);\n if (url) {\n URL.revokeObjectURL(url);\n this.previewUrls.delete(file);\n }\n\n this.selectedFiles.update((files) => files.filter((f) => f !== file));\n this.errorMessage.set('');\n\n if (this.selectedFiles().length === 0) {\n this.fileRemoved.emit();\n }\n }\n\n /** Clears all selected files and previews. */\n changeFiles(): void {\n this.clearPreviews();\n this.selectedFiles.set([]);\n this.errorMessage.set('');\n }\n\n /** Revokes every stored preview object URL. */\n private clearPreviews(): void {\n for (const [file, url] of this.previewUrls) {\n URL.revokeObjectURL(url);\n }\n this.previewUrls.clear();\n }\n\n /** Human readable size (B/KB/MB). */\n private formatFileSize(bytes: number): string {\n if (bytes < 1024) return bytes + ' B';\n if (bytes < 1024 * 1024) return (bytes / 1024).toFixed(1) + ' KB';\n return (bytes / (1024 * 1024)).toFixed(1) + ' MB';\n }\n}","<div class=\"flex flex-col gap-2\">\n @if (label()) {\n <label class=\"text-sm font-medium _shk-text-surface-700 dark:[color:var(--shk-surface-300)]\">\n {{ label() }}\n </label>\n }\n\n @if (canAddMore()) {\n <div\n class=\"relative border-2 border-dashed _shk-border dark:[border-color:var(--shk-surface-700)] rounded-lg p-4 transition-colors hover:[border-color:var(--shk-primary-400)] dark:hover:[border-color:var(--shk-primary-500)]\"\n [class.border-red-400]=\"errorMessage()\"\n (dragover)=\"onDragOver($event)\"\n (dragleave)=\"onDragLeave($event)\"\n (drop)=\"onDrop($event)\"\n >\n <input\n #fileInput\n type=\"file\"\n [accept]=\"accept()\"\n [multiple]=\"multiple()\"\n (change)=\"onFileChange($event)\"\n class=\"hidden\"\n />\n\n <div\n class=\"flex flex-col items-center gap-2 cursor-pointer\"\n (click)=\"fileInput.click()\"\n [class.drag-over]=\"isDragOver()\"\n >\n <svg [lucideIcon]=\"getIcon('upload')\" class=\"w-8 h-8 _shk-icon-subtle dark:[color:var(--shk-surface-600)]\"></svg>\n <span class=\"text-sm _shk-text-surface-700 dark:[color:var(--shk-surface-300)]\">\n {{ fileUploadText() }}\n </span>\n @if (fileRecommendation()) {\n <span class=\"text-xs _shk-text-surface-400 dark:[color:var(--shk-surface-500)]\">\n {{ fileRecommendation() }}\n </span>\n }\n </div>\n </div>\n }\n\n @if (maxReached()) {\n <div class=\"text-xs _shk-text-surface-400 dark:[color:var(--shk-surface-500)] text-center py-2\">\n Máximo {{ maxFiles() }} archivos alcanzado\n </div>\n }\n\n @if (selectedFiles().length > 0) {\n <div class=\"flex flex-wrap gap-3\">\n @for (file of selectedFiles(); track file.name + file.size + file.lastModified) {\n <div class=\"relative group\">\n @if (isImageFile(file)) {\n <img\n [src]=\"previewUrl(file)\"\n [alt]=\"file.name\"\n class=\"w-20 h-20 object-cover rounded-lg _shk-border dark:[border-color:var(--shk-surface-700)]\"\n />\n } @else {\n <div class=\"w-20 h-20 rounded-lg _shk-border dark:[border-color:var(--shk-surface-700)] flex flex-col items-center justify-center _shk-bg-surface-50 dark:[background-color:var(--shk-surface-800)] gap-1\">\n <svg [lucideIcon]=\"getIcon('file')\" class=\"w-6 h-6 _shk-text-surface-400\"></svg>\n <span class=\"text-[10px] _shk-text-surface-400 truncate max-w-[70px] px-1 text-center\">{{ file.name }}</span>\n </div>\n }\n <button\n type=\"button\"\n (click)=\"removeFile(file)\"\n class=\"absolute -top-1.5 -right-1.5 w-5 h-5 bg-red-500 text-white rounded-full text-xs flex items-center justify-center opacity-0 group-hover:opacity-100 transition shadow\"\n >\n <svg [lucideIcon]=\"getIcon('x')\" class=\"w-3 h-3\"></svg>\n </button>\n </div>\n }\n </div>\n @if (!multiple()) {\n <button\n type=\"button\"\n (click)=\"changeFiles()\"\n class=\"text-xs _shk-text-primary hover:[color:var(--shk-primary-700)] dark:[color:var(--shk-primary-400)] dark:hover:[color:var(--shk-primary-300)] underline cursor-pointer bg-transparent border-0\"\n >\n {{ changeFilesText() }}\n </button>\n }\n }\n\n @if (errorMessage()) {\n <p class=\"text-xs _shk-text-red-500\">{{ errorMessage() }}</p>\n }\n</div>","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":["getIconFromCentral"],"mappings":"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"}
|
|
@@ -0,0 +1,269 @@
|
|
|
1
|
+
import * as i0 from '@angular/core';
|
|
2
|
+
import { model, input, output, viewChild, signal, computed, forwardRef, ChangeDetectionStrategy, Component } from '@angular/core';
|
|
3
|
+
import { NG_VALUE_ACCESSOR } from '@angular/forms';
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Shirkasoft UI Components.
|
|
7
|
+
* Authors: Roberto Valladares Martin (Ansem13), Julio César García García (Sanjuli14).
|
|
8
|
+
* Belongs to Shirkasoft.
|
|
9
|
+
*/
|
|
10
|
+
/** SVG radial knob with drag and keyboard support. Implements ControlValueAccessor. */
|
|
11
|
+
class KnobComponent {
|
|
12
|
+
constructor() {
|
|
13
|
+
/** Current value. Two-way bindable with [(value)]. */
|
|
14
|
+
this.value = model(0, ...(ngDevMode ? [{ debugName: "value" }] : /* istanbul ignore next */ []));
|
|
15
|
+
/** Minimum value. */
|
|
16
|
+
this.min = input(0, ...(ngDevMode ? [{ debugName: "min" }] : /* istanbul ignore next */ []));
|
|
17
|
+
/** Maximum value. */
|
|
18
|
+
this.max = input(100, ...(ngDevMode ? [{ debugName: "max" }] : /* istanbul ignore next */ []));
|
|
19
|
+
/** Increment used by arrows and pointer drag rounding. */
|
|
20
|
+
this.step = input(1, ...(ngDevMode ? [{ debugName: "step" }] : /* istanbul ignore next */ []));
|
|
21
|
+
/** Diameter of the knob in px. */
|
|
22
|
+
this.size = input(100, ...(ngDevMode ? [{ debugName: "size" }] : /* istanbul ignore next */ []));
|
|
23
|
+
/** Thickness of the arc stroke. */
|
|
24
|
+
this.strokeWidth = input(14, ...(ngDevMode ? [{ debugName: "strokeWidth" }] : /* istanbul ignore next */ []));
|
|
25
|
+
/** Color of the filled arc. */
|
|
26
|
+
this.valueColor = input('var(--shk-primary-600)', ...(ngDevMode ? [{ debugName: "valueColor" }] : /* istanbul ignore next */ []));
|
|
27
|
+
/** Color of the track arc. */
|
|
28
|
+
this.rangeColor = input('var(--shk-surface-200)', ...(ngDevMode ? [{ debugName: "rangeColor" }] : /* istanbul ignore next */ []));
|
|
29
|
+
/** Whether the current value is shown in the center. */
|
|
30
|
+
this.showValue = input(true, ...(ngDevMode ? [{ debugName: "showValue" }] : /* istanbul ignore next */ []));
|
|
31
|
+
/** Disables user interaction. */
|
|
32
|
+
this.disabled = input(false, ...(ngDevMode ? [{ debugName: "disabled" }] : /* istanbul ignore next */ []));
|
|
33
|
+
/** Blocks editing but keeps the control styled as enabled. */
|
|
34
|
+
this.readonly = input(false, ...(ngDevMode ? [{ debugName: "readonly" }] : /* istanbul ignore next */ []));
|
|
35
|
+
/** Accessible label. */
|
|
36
|
+
this.ariaLabel = input('', ...(ngDevMode ? [{ debugName: "ariaLabel" }] : /* istanbul ignore next */ []));
|
|
37
|
+
/** Emitted when the knob value changes. */
|
|
38
|
+
this.change = output();
|
|
39
|
+
/** Emitted when the user releases the pointer. */
|
|
40
|
+
this.end = output();
|
|
41
|
+
this.knobSvg = viewChild('knobSvg', ...(ngDevMode ? [{ debugName: "knobSvg" }] : /* istanbul ignore next */ []));
|
|
42
|
+
this.onChange = () => { };
|
|
43
|
+
this.onTouched = () => { };
|
|
44
|
+
this.dragging = false;
|
|
45
|
+
this.formDisabled = signal(false, ...(ngDevMode ? [{ debugName: "formDisabled" }] : /* istanbul ignore next */ []));
|
|
46
|
+
/** Effective disabled state combining the `disabled` input and the form binding. */
|
|
47
|
+
this.effectiveDisabled = computed(() => this.disabled() || this.formDisabled(), ...(ngDevMode ? [{ debugName: "effectiveDisabled" }] : /* istanbul ignore next */ []));
|
|
48
|
+
this.r = computed(() => (this.size() - this.strokeWidth()) / 2, ...(ngDevMode ? [{ debugName: "r" }] : /* istanbul ignore next */ []));
|
|
49
|
+
this.center = computed(() => this.size() / 2, ...(ngDevMode ? [{ debugName: "center" }] : /* istanbul ignore next */ []));
|
|
50
|
+
this.fraction = computed(() => {
|
|
51
|
+
const range = this.max() - this.min();
|
|
52
|
+
if (range <= 0)
|
|
53
|
+
return 0;
|
|
54
|
+
return Math.max(0, Math.min(1, (this.value() - this.min()) / range));
|
|
55
|
+
}, ...(ngDevMode ? [{ debugName: "fraction" }] : /* istanbul ignore next */ []));
|
|
56
|
+
this.rangeArc = computed(() => this.getArcPath(135, 405), ...(ngDevMode ? [{ debugName: "rangeArc" }] : /* istanbul ignore next */ []));
|
|
57
|
+
this.valueArc = computed(() => this.getArcPath(135, 135 + 270 * this.fraction()), ...(ngDevMode ? [{ debugName: "valueArc" }] : /* istanbul ignore next */ []));
|
|
58
|
+
}
|
|
59
|
+
writeValue(value) {
|
|
60
|
+
this.value.set(this.clamp(Number(value) || this.min()));
|
|
61
|
+
}
|
|
62
|
+
registerOnChange(fn) {
|
|
63
|
+
this.onChange = fn;
|
|
64
|
+
}
|
|
65
|
+
registerOnTouched(fn) {
|
|
66
|
+
this.onTouched = fn;
|
|
67
|
+
}
|
|
68
|
+
setDisabledState(isDisabled) {
|
|
69
|
+
this.formDisabled.set(isDisabled);
|
|
70
|
+
}
|
|
71
|
+
onPointerDown(event) {
|
|
72
|
+
if (this.effectiveDisabled() || this.readonly())
|
|
73
|
+
return;
|
|
74
|
+
this.dragging = true;
|
|
75
|
+
this.knobSvg()?.nativeElement.setPointerCapture(event.pointerId);
|
|
76
|
+
this.applyEvent(event);
|
|
77
|
+
}
|
|
78
|
+
onPointerMove(event) {
|
|
79
|
+
if (!this.dragging)
|
|
80
|
+
return;
|
|
81
|
+
this.applyEvent(event);
|
|
82
|
+
}
|
|
83
|
+
onPointerUp(event) {
|
|
84
|
+
if (!this.dragging)
|
|
85
|
+
return;
|
|
86
|
+
this.dragging = false;
|
|
87
|
+
try {
|
|
88
|
+
this.knobSvg()?.nativeElement.releasePointerCapture(event.pointerId);
|
|
89
|
+
}
|
|
90
|
+
catch {
|
|
91
|
+
/* noop */
|
|
92
|
+
}
|
|
93
|
+
this.change.emit(this.value());
|
|
94
|
+
this.end.emit(this.value());
|
|
95
|
+
}
|
|
96
|
+
updateByKey(step) {
|
|
97
|
+
if (this.effectiveDisabled() || this.readonly())
|
|
98
|
+
return;
|
|
99
|
+
this.setValue(this.value() + step);
|
|
100
|
+
this.onTouched();
|
|
101
|
+
}
|
|
102
|
+
applyEvent(event) {
|
|
103
|
+
const svg = this.knobSvg()?.nativeElement;
|
|
104
|
+
if (!svg)
|
|
105
|
+
return;
|
|
106
|
+
const rect = svg.getBoundingClientRect();
|
|
107
|
+
const cx = rect.left + rect.width / 2;
|
|
108
|
+
const cy = rect.top + rect.height / 2;
|
|
109
|
+
const angle = Math.atan2(event.clientY - cy, event.clientX - cx);
|
|
110
|
+
const deg = ((angle * 180) / Math.PI + 360) % 360;
|
|
111
|
+
let t = deg - 135;
|
|
112
|
+
if (t < 0)
|
|
113
|
+
t += 360;
|
|
114
|
+
let fraction;
|
|
115
|
+
if (t > 270) {
|
|
116
|
+
fraction = 360 - t < t - 270 ? 0 : 1;
|
|
117
|
+
}
|
|
118
|
+
else {
|
|
119
|
+
fraction = t / 270;
|
|
120
|
+
}
|
|
121
|
+
const raw = this.min() + fraction * (this.max() - this.min());
|
|
122
|
+
this.setValue(raw);
|
|
123
|
+
this.onTouched();
|
|
124
|
+
}
|
|
125
|
+
setValue(raw) {
|
|
126
|
+
const rounded = Math.round(raw / this.step()) * this.step();
|
|
127
|
+
const clamped = this.clamp(rounded);
|
|
128
|
+
this.value.set(clamped);
|
|
129
|
+
this.onChange(clamped);
|
|
130
|
+
}
|
|
131
|
+
clamp(value) {
|
|
132
|
+
return Math.max(this.min(), Math.min(this.max(), value));
|
|
133
|
+
}
|
|
134
|
+
getArcPath(startDeg, endDeg) {
|
|
135
|
+
const cx = this.center();
|
|
136
|
+
const cy = this.center();
|
|
137
|
+
const r = this.r();
|
|
138
|
+
const start = this.anglePoint(cx, cy, r, startDeg);
|
|
139
|
+
const end = this.anglePoint(cx, cy, r, endDeg);
|
|
140
|
+
const largeArc = endDeg - startDeg > 180 ? '1' : '0';
|
|
141
|
+
return `M ${start.x.toFixed(2)} ${start.y.toFixed(2)} A ${r.toFixed(2)} ${r.toFixed(2)} 0 ${largeArc} 1 ${end.x.toFixed(2)} ${end.y.toFixed(2)}`;
|
|
142
|
+
}
|
|
143
|
+
anglePoint(cx, cy, r, angleDeg) {
|
|
144
|
+
const rad = (Math.PI * angleDeg) / 180;
|
|
145
|
+
return {
|
|
146
|
+
x: cx + r * Math.cos(rad),
|
|
147
|
+
y: cy + r * Math.sin(rad),
|
|
148
|
+
};
|
|
149
|
+
}
|
|
150
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: KnobComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
151
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.18", type: KnobComponent, isStandalone: true, selector: "shk-knob", inputs: { value: { classPropertyName: "value", publicName: "value", isSignal: true, isRequired: false, transformFunction: null }, min: { classPropertyName: "min", publicName: "min", isSignal: true, isRequired: false, transformFunction: null }, max: { classPropertyName: "max", publicName: "max", isSignal: true, isRequired: false, transformFunction: null }, step: { classPropertyName: "step", publicName: "step", isSignal: true, isRequired: false, transformFunction: null }, size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, strokeWidth: { classPropertyName: "strokeWidth", publicName: "strokeWidth", isSignal: true, isRequired: false, transformFunction: null }, valueColor: { classPropertyName: "valueColor", publicName: "valueColor", isSignal: true, isRequired: false, transformFunction: null }, rangeColor: { classPropertyName: "rangeColor", publicName: "rangeColor", isSignal: true, isRequired: false, transformFunction: null }, showValue: { classPropertyName: "showValue", publicName: "showValue", isSignal: true, isRequired: false, transformFunction: null }, disabled: { classPropertyName: "disabled", publicName: "disabled", isSignal: true, isRequired: false, transformFunction: null }, readonly: { classPropertyName: "readonly", publicName: "readonly", isSignal: true, isRequired: false, transformFunction: null }, ariaLabel: { classPropertyName: "ariaLabel", publicName: "ariaLabel", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { value: "valueChange", change: "change", end: "end" }, providers: [
|
|
152
|
+
{
|
|
153
|
+
provide: NG_VALUE_ACCESSOR,
|
|
154
|
+
useExisting: forwardRef(() => KnobComponent),
|
|
155
|
+
multi: true,
|
|
156
|
+
},
|
|
157
|
+
], viewQueries: [{ propertyName: "knobSvg", first: true, predicate: ["knobSvg"], descendants: true, isSignal: true }], ngImport: i0, template: `
|
|
158
|
+
<div
|
|
159
|
+
class="shk-knob"
|
|
160
|
+
[class.shk-knob-disabled]="effectiveDisabled()"
|
|
161
|
+
[style]="{ width: size() + 'px', height: size() + 'px' }"
|
|
162
|
+
>
|
|
163
|
+
<svg
|
|
164
|
+
#knobSvg
|
|
165
|
+
class="shk-knob-svg"
|
|
166
|
+
[attr.width]="size()"
|
|
167
|
+
[attr.height]="size()"
|
|
168
|
+
[attr.viewBox]="'0 0 ' + size() + ' ' + size()"
|
|
169
|
+
role="slider"
|
|
170
|
+
tabindex="0"
|
|
171
|
+
[attr.aria-label]="ariaLabel() || 'Valor'"
|
|
172
|
+
[attr.aria-valuemin]="min()"
|
|
173
|
+
[attr.aria-valuemax]="max()"
|
|
174
|
+
[attr.aria-valuenow]="value()"
|
|
175
|
+
[class.shk-knob-svg-focusable]="!effectiveDisabled()"
|
|
176
|
+
(pointerdown)="onPointerDown($event)"
|
|
177
|
+
(pointermove)="onPointerMove($event)"
|
|
178
|
+
(pointerup)="onPointerUp($event)"
|
|
179
|
+
(pointercancel)="onPointerUp($event)"
|
|
180
|
+
(keydown.arrowup)="updateByKey(step())"
|
|
181
|
+
(keydown.arrowright)="updateByKey(step())"
|
|
182
|
+
(keydown.arrowdown)="updateByKey(-step())"
|
|
183
|
+
(keydown.arrowleft)="updateByKey(-step())"
|
|
184
|
+
>
|
|
185
|
+
<path
|
|
186
|
+
[attr.d]="rangeArc()"
|
|
187
|
+
fill="none"
|
|
188
|
+
[style.stroke]="rangeColor()"
|
|
189
|
+
[attr.stroke-width]="strokeWidth()"
|
|
190
|
+
stroke-linecap="round"
|
|
191
|
+
></path>
|
|
192
|
+
<path
|
|
193
|
+
[attr.d]="valueArc()"
|
|
194
|
+
fill="none"
|
|
195
|
+
[style.stroke]="valueColor()"
|
|
196
|
+
[attr.stroke-width]="strokeWidth()"
|
|
197
|
+
stroke-linecap="round"
|
|
198
|
+
></path>
|
|
199
|
+
</svg>
|
|
200
|
+
@if (showValue()) {
|
|
201
|
+
<div class="shk-knob-label">{{ value() }}</div>
|
|
202
|
+
}
|
|
203
|
+
</div>
|
|
204
|
+
`, isInline: true, styles: [".shk-knob{position:relative;display:inline-block}.shk-knob-svg{display:block;touch-action:none}.shk-knob-svg-focusable{cursor:pointer;outline:none}.shk-knob-svg-focusable:focus-visible{border-radius:9999px;outline:2px solid var(--shk-primary-400);outline-offset:2px}.shk-knob-disabled{opacity:.55}.shk-knob-disabled .shk-knob-svg{cursor:not-allowed}.shk-knob-label{position:absolute;top:50%;left:50%;transform:translate(-50%,-50%);font-size:1.125rem;font-weight:600;color:var(--shk-surface-800);pointer-events:none;-webkit-user-select:none;user-select:none}\n"], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
205
|
+
}
|
|
206
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: KnobComponent, decorators: [{
|
|
207
|
+
type: Component,
|
|
208
|
+
args: [{ selector: 'shk-knob', standalone: true, changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
209
|
+
<div
|
|
210
|
+
class="shk-knob"
|
|
211
|
+
[class.shk-knob-disabled]="effectiveDisabled()"
|
|
212
|
+
[style]="{ width: size() + 'px', height: size() + 'px' }"
|
|
213
|
+
>
|
|
214
|
+
<svg
|
|
215
|
+
#knobSvg
|
|
216
|
+
class="shk-knob-svg"
|
|
217
|
+
[attr.width]="size()"
|
|
218
|
+
[attr.height]="size()"
|
|
219
|
+
[attr.viewBox]="'0 0 ' + size() + ' ' + size()"
|
|
220
|
+
role="slider"
|
|
221
|
+
tabindex="0"
|
|
222
|
+
[attr.aria-label]="ariaLabel() || 'Valor'"
|
|
223
|
+
[attr.aria-valuemin]="min()"
|
|
224
|
+
[attr.aria-valuemax]="max()"
|
|
225
|
+
[attr.aria-valuenow]="value()"
|
|
226
|
+
[class.shk-knob-svg-focusable]="!effectiveDisabled()"
|
|
227
|
+
(pointerdown)="onPointerDown($event)"
|
|
228
|
+
(pointermove)="onPointerMove($event)"
|
|
229
|
+
(pointerup)="onPointerUp($event)"
|
|
230
|
+
(pointercancel)="onPointerUp($event)"
|
|
231
|
+
(keydown.arrowup)="updateByKey(step())"
|
|
232
|
+
(keydown.arrowright)="updateByKey(step())"
|
|
233
|
+
(keydown.arrowdown)="updateByKey(-step())"
|
|
234
|
+
(keydown.arrowleft)="updateByKey(-step())"
|
|
235
|
+
>
|
|
236
|
+
<path
|
|
237
|
+
[attr.d]="rangeArc()"
|
|
238
|
+
fill="none"
|
|
239
|
+
[style.stroke]="rangeColor()"
|
|
240
|
+
[attr.stroke-width]="strokeWidth()"
|
|
241
|
+
stroke-linecap="round"
|
|
242
|
+
></path>
|
|
243
|
+
<path
|
|
244
|
+
[attr.d]="valueArc()"
|
|
245
|
+
fill="none"
|
|
246
|
+
[style.stroke]="valueColor()"
|
|
247
|
+
[attr.stroke-width]="strokeWidth()"
|
|
248
|
+
stroke-linecap="round"
|
|
249
|
+
></path>
|
|
250
|
+
</svg>
|
|
251
|
+
@if (showValue()) {
|
|
252
|
+
<div class="shk-knob-label">{{ value() }}</div>
|
|
253
|
+
}
|
|
254
|
+
</div>
|
|
255
|
+
`, providers: [
|
|
256
|
+
{
|
|
257
|
+
provide: NG_VALUE_ACCESSOR,
|
|
258
|
+
useExisting: forwardRef(() => KnobComponent),
|
|
259
|
+
multi: true,
|
|
260
|
+
},
|
|
261
|
+
], styles: [".shk-knob{position:relative;display:inline-block}.shk-knob-svg{display:block;touch-action:none}.shk-knob-svg-focusable{cursor:pointer;outline:none}.shk-knob-svg-focusable:focus-visible{border-radius:9999px;outline:2px solid var(--shk-primary-400);outline-offset:2px}.shk-knob-disabled{opacity:.55}.shk-knob-disabled .shk-knob-svg{cursor:not-allowed}.shk-knob-label{position:absolute;top:50%;left:50%;transform:translate(-50%,-50%);font-size:1.125rem;font-weight:600;color:var(--shk-surface-800);pointer-events:none;-webkit-user-select:none;user-select:none}\n"] }]
|
|
262
|
+
}], propDecorators: { value: [{ type: i0.Input, args: [{ isSignal: true, alias: "value", required: false }] }, { type: i0.Output, args: ["valueChange"] }], min: [{ type: i0.Input, args: [{ isSignal: true, alias: "min", required: false }] }], max: [{ type: i0.Input, args: [{ isSignal: true, alias: "max", required: false }] }], step: [{ type: i0.Input, args: [{ isSignal: true, alias: "step", required: false }] }], size: [{ type: i0.Input, args: [{ isSignal: true, alias: "size", required: false }] }], strokeWidth: [{ type: i0.Input, args: [{ isSignal: true, alias: "strokeWidth", required: false }] }], valueColor: [{ type: i0.Input, args: [{ isSignal: true, alias: "valueColor", required: false }] }], rangeColor: [{ type: i0.Input, args: [{ isSignal: true, alias: "rangeColor", required: false }] }], showValue: [{ type: i0.Input, args: [{ isSignal: true, alias: "showValue", required: false }] }], disabled: [{ type: i0.Input, args: [{ isSignal: true, alias: "disabled", required: false }] }], readonly: [{ type: i0.Input, args: [{ isSignal: true, alias: "readonly", required: false }] }], ariaLabel: [{ type: i0.Input, args: [{ isSignal: true, alias: "ariaLabel", required: false }] }], change: [{ type: i0.Output, args: ["change"] }], end: [{ type: i0.Output, args: ["end"] }], knobSvg: [{ type: i0.ViewChild, args: ['knobSvg', { isSignal: true }] }] } });
|
|
263
|
+
|
|
264
|
+
/**
|
|
265
|
+
* Generated bundle index. Do not edit.
|
|
266
|
+
*/
|
|
267
|
+
|
|
268
|
+
export { KnobComponent };
|
|
269
|
+
//# sourceMappingURL=shirkasoft-ui-components-knob.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"shirkasoft-ui-components-knob.mjs","sources":["../../../projects/ui-components/knob/knob.component.ts","../../../projects/ui-components/knob/shirkasoft-ui-components-knob.ts"],"sourcesContent":["import {\n Component,\n computed,\n forwardRef,\n input,\n model,\n output,\n signal,\n viewChild,\n ElementRef,\n ChangeDetectionStrategy,\n} from '@angular/core';\nimport { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';\n\n/**\n * Shirkasoft UI Components.\n * Authors: Roberto Valladares Martin (Ansem13), Julio César García García (Sanjuli14).\n * Belongs to Shirkasoft.\n */\n\n/** SVG radial knob with drag and keyboard support. Implements ControlValueAccessor. */\n@Component({\n selector: 'shk-knob',\n standalone: true,\n changeDetection: ChangeDetectionStrategy.OnPush,\n template: `\n <div\n class=\"shk-knob\"\n [class.shk-knob-disabled]=\"effectiveDisabled()\"\n [style]=\"{ width: size() + 'px', height: size() + 'px' }\"\n >\n <svg\n #knobSvg\n class=\"shk-knob-svg\"\n [attr.width]=\"size()\"\n [attr.height]=\"size()\"\n [attr.viewBox]=\"'0 0 ' + size() + ' ' + size()\"\n role=\"slider\"\n tabindex=\"0\"\n [attr.aria-label]=\"ariaLabel() || 'Valor'\"\n [attr.aria-valuemin]=\"min()\"\n [attr.aria-valuemax]=\"max()\"\n [attr.aria-valuenow]=\"value()\"\n [class.shk-knob-svg-focusable]=\"!effectiveDisabled()\"\n (pointerdown)=\"onPointerDown($event)\"\n (pointermove)=\"onPointerMove($event)\"\n (pointerup)=\"onPointerUp($event)\"\n (pointercancel)=\"onPointerUp($event)\"\n (keydown.arrowup)=\"updateByKey(step())\"\n (keydown.arrowright)=\"updateByKey(step())\"\n (keydown.arrowdown)=\"updateByKey(-step())\"\n (keydown.arrowleft)=\"updateByKey(-step())\"\n >\n <path\n [attr.d]=\"rangeArc()\"\n fill=\"none\"\n [style.stroke]=\"rangeColor()\"\n [attr.stroke-width]=\"strokeWidth()\"\n stroke-linecap=\"round\"\n ></path>\n <path\n [attr.d]=\"valueArc()\"\n fill=\"none\"\n [style.stroke]=\"valueColor()\"\n [attr.stroke-width]=\"strokeWidth()\"\n stroke-linecap=\"round\"\n ></path>\n </svg>\n @if (showValue()) {\n <div class=\"shk-knob-label\">{{ value() }}</div>\n }\n </div>\n `,\n styles: [\n `\n .shk-knob {\n position: relative;\n display: inline-block;\n }\n .shk-knob-svg {\n display: block;\n touch-action: none;\n }\n .shk-knob-svg-focusable {\n cursor: pointer;\n outline: none;\n }\n .shk-knob-svg-focusable:focus-visible {\n border-radius: 9999px;\n outline: 2px solid var(--shk-primary-400);\n outline-offset: 2px;\n }\n .shk-knob-disabled {\n opacity: 0.55;\n }\n .shk-knob-disabled .shk-knob-svg {\n cursor: not-allowed;\n }\n .shk-knob-label {\n position: absolute;\n top: 50%;\n left: 50%;\n transform: translate(-50%, -50%);\n font-size: 1.125rem;\n font-weight: 600;\n color: var(--shk-surface-800);\n pointer-events: none;\n user-select: none;\n }\n `,\n ],\n providers: [\n {\n provide: NG_VALUE_ACCESSOR,\n useExisting: forwardRef(() => KnobComponent),\n multi: true,\n },\n ],\n})\nexport class KnobComponent implements ControlValueAccessor {\n /** Current value. Two-way bindable with [(value)]. */\n value = model<number>(0);\n /** Minimum value. */\n min = input<number>(0);\n /** Maximum value. */\n max = input<number>(100);\n /** Increment used by arrows and pointer drag rounding. */\n step = input<number>(1);\n /** Diameter of the knob in px. */\n size = input<number>(100);\n /** Thickness of the arc stroke. */\n strokeWidth = input<number>(14);\n /** Color of the filled arc. */\n valueColor = input<string>('var(--shk-primary-600)');\n /** Color of the track arc. */\n rangeColor = input<string>('var(--shk-surface-200)');\n /** Whether the current value is shown in the center. */\n showValue = input<boolean>(true);\n /** Disables user interaction. */\n disabled = input<boolean>(false);\n /** Blocks editing but keeps the control styled as enabled. */\n readonly = input<boolean>(false);\n /** Accessible label. */\n ariaLabel = input<string>('');\n\n /** Emitted when the knob value changes. */\n change = output<number>();\n /** Emitted when the user releases the pointer. */\n end = output<number>();\n\n protected knobSvg = viewChild<ElementRef<SVGElement>>('knobSvg');\n\n private onChange: (value: number) => void = () => {};\n private onTouched: () => void = () => {};\n private dragging = false;\n private formDisabled = signal(false);\n\n /** Effective disabled state combining the `disabled` input and the form binding. */\n protected effectiveDisabled = computed(() => this.disabled() || this.formDisabled());\n\n protected r = computed(() => (this.size() - this.strokeWidth()) / 2);\n protected center = computed(() => this.size() / 2);\n protected fraction = computed(() => {\n const range = this.max() - this.min();\n if (range <= 0) return 0;\n return Math.max(0, Math.min(1, (this.value() - this.min()) / range));\n });\n protected rangeArc = computed(() => this.getArcPath(135, 405));\n protected valueArc = computed(() => this.getArcPath(135, 135 + 270 * this.fraction()));\n\n writeValue(value: any): void {\n this.value.set(this.clamp(Number(value) || this.min()));\n }\n\n registerOnChange(fn: any): void {\n this.onChange = fn;\n }\n\n registerOnTouched(fn: any): void {\n this.onTouched = fn;\n }\n\n setDisabledState(isDisabled: boolean): void {\n this.formDisabled.set(isDisabled);\n }\n\n onPointerDown(event: PointerEvent): void {\n if (this.effectiveDisabled() || this.readonly()) return;\n this.dragging = true;\n this.knobSvg()?.nativeElement.setPointerCapture(event.pointerId);\n this.applyEvent(event);\n }\n\n onPointerMove(event: PointerEvent): void {\n if (!this.dragging) return;\n this.applyEvent(event);\n }\n\n onPointerUp(event: PointerEvent): void {\n if (!this.dragging) return;\n this.dragging = false;\n try {\n this.knobSvg()?.nativeElement.releasePointerCapture(event.pointerId);\n } catch {\n /* noop */\n }\n this.change.emit(this.value());\n this.end.emit(this.value());\n }\n\n updateByKey(step: number): void {\n if (this.effectiveDisabled() || this.readonly()) return;\n this.setValue(this.value() + step);\n this.onTouched();\n }\n\n private applyEvent(event: PointerEvent): void {\n const svg = this.knobSvg()?.nativeElement;\n if (!svg) return;\n const rect = svg.getBoundingClientRect();\n const cx = rect.left + rect.width / 2;\n const cy = rect.top + rect.height / 2;\n const angle = Math.atan2(event.clientY - cy, event.clientX - cx);\n const deg = ((angle * 180) / Math.PI + 360) % 360;\n let t = deg - 135;\n if (t < 0) t += 360;\n let fraction: number;\n if (t > 270) {\n fraction = 360 - t < t - 270 ? 0 : 1;\n } else {\n fraction = t / 270;\n }\n const raw = this.min() + fraction * (this.max() - this.min());\n this.setValue(raw);\n this.onTouched();\n }\n\n private setValue(raw: number): void {\n const rounded = Math.round(raw / this.step()) * this.step();\n const clamped = this.clamp(rounded);\n this.value.set(clamped);\n this.onChange(clamped);\n }\n\n private clamp(value: number): number {\n return Math.max(this.min(), Math.min(this.max(), value));\n }\n\n private getArcPath(startDeg: number, endDeg: number): string {\n const cx = this.center();\n const cy = this.center();\n const r = this.r();\n const start = this.anglePoint(cx, cy, r, startDeg);\n const end = this.anglePoint(cx, cy, r, endDeg);\n const largeArc = endDeg - startDeg > 180 ? '1' : '0';\n return `M ${start.x.toFixed(2)} ${start.y.toFixed(2)} A ${r.toFixed(2)} ${r.toFixed(2)} 0 ${largeArc} 1 ${end.x.toFixed(2)} ${end.y.toFixed(2)}`;\n }\n\n private anglePoint(\n cx: number,\n cy: number,\n r: number,\n angleDeg: number,\n ): { x: number; y: number } {\n const rad = (Math.PI * angleDeg) / 180;\n return {\n x: cx + r * Math.cos(rad),\n y: cy + r * Math.sin(rad),\n };\n }\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,255 @@
|
|
|
1
|
+
import * as i0 from '@angular/core';
|
|
2
|
+
import { input, ChangeDetectionStrategy, Component, computed } from '@angular/core';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Shirkasoft UI Components.
|
|
6
|
+
* Authors: Roberto Valladares Martin (Ansem13), Julio César García García (Sanjuli14).
|
|
7
|
+
* Belongs to Shirkasoft.
|
|
8
|
+
*/
|
|
9
|
+
/** Circular indeterminate spinner. */
|
|
10
|
+
class LoadingSpinnerComponent {
|
|
11
|
+
constructor() {
|
|
12
|
+
/** Diameter of the spinner. */
|
|
13
|
+
this.size = input('2rem', ...(ngDevMode ? [{ debugName: "size" }] : /* istanbul ignore next */ []));
|
|
14
|
+
/** Border thickness in px. */
|
|
15
|
+
this.thickness = input(3, ...(ngDevMode ? [{ debugName: "thickness" }] : /* istanbul ignore next */ []));
|
|
16
|
+
/** Color of the moving arc. Defaults to the primary token. */
|
|
17
|
+
this.color = input('', ...(ngDevMode ? [{ debugName: "color" }] : /* istanbul ignore next */ []));
|
|
18
|
+
/** Optional text shown under the spinner. */
|
|
19
|
+
this.label = input('', ...(ngDevMode ? [{ debugName: "label" }] : /* istanbul ignore next */ []));
|
|
20
|
+
}
|
|
21
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: LoadingSpinnerComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
22
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.18", type: LoadingSpinnerComponent, isStandalone: true, selector: "shk-loading-spinner", inputs: { size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, thickness: { classPropertyName: "thickness", publicName: "thickness", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
23
|
+
<div
|
|
24
|
+
class="shk-loading-spinner"
|
|
25
|
+
[style]="{
|
|
26
|
+
width: size(),
|
|
27
|
+
height: size(),
|
|
28
|
+
}"
|
|
29
|
+
role="status"
|
|
30
|
+
aria-label="Cargando"
|
|
31
|
+
>
|
|
32
|
+
<div
|
|
33
|
+
class="shk-loading-spinner-circle"
|
|
34
|
+
[style]="{
|
|
35
|
+
borderWidth: thickness(),
|
|
36
|
+
borderTopColor: color() || undefined,
|
|
37
|
+
}"
|
|
38
|
+
></div>
|
|
39
|
+
</div>
|
|
40
|
+
@if (label()) {
|
|
41
|
+
<span class="shk-loading-spinner-label">{{ label() }}</span>
|
|
42
|
+
}
|
|
43
|
+
`, isInline: true, styles: [":host{display:inline-flex;flex-direction:column;align-items:center;justify-content:center;gap:.5rem}.shk-loading-spinner{display:inline-block}.shk-loading-spinner-circle{width:100%;height:100%;border-radius:9999px;border-style:solid;border-color:color-mix(in srgb,var(--shk-primary-600) 20%,transparent);border-top-color:var(--shk-primary-600);animation:shk-loading-spin .8s linear infinite}.shk-loading-spinner-label{font-size:.8125rem;color:var(--shk-surface-500)}@keyframes shk-loading-spin{to{transform:rotate(360deg)}}\n"], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
44
|
+
}
|
|
45
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: LoadingSpinnerComponent, decorators: [{
|
|
46
|
+
type: Component,
|
|
47
|
+
args: [{ selector: 'shk-loading-spinner', standalone: true, changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
48
|
+
<div
|
|
49
|
+
class="shk-loading-spinner"
|
|
50
|
+
[style]="{
|
|
51
|
+
width: size(),
|
|
52
|
+
height: size(),
|
|
53
|
+
}"
|
|
54
|
+
role="status"
|
|
55
|
+
aria-label="Cargando"
|
|
56
|
+
>
|
|
57
|
+
<div
|
|
58
|
+
class="shk-loading-spinner-circle"
|
|
59
|
+
[style]="{
|
|
60
|
+
borderWidth: thickness(),
|
|
61
|
+
borderTopColor: color() || undefined,
|
|
62
|
+
}"
|
|
63
|
+
></div>
|
|
64
|
+
</div>
|
|
65
|
+
@if (label()) {
|
|
66
|
+
<span class="shk-loading-spinner-label">{{ label() }}</span>
|
|
67
|
+
}
|
|
68
|
+
`, styles: [":host{display:inline-flex;flex-direction:column;align-items:center;justify-content:center;gap:.5rem}.shk-loading-spinner{display:inline-block}.shk-loading-spinner-circle{width:100%;height:100%;border-radius:9999px;border-style:solid;border-color:color-mix(in srgb,var(--shk-primary-600) 20%,transparent);border-top-color:var(--shk-primary-600);animation:shk-loading-spin .8s linear infinite}.shk-loading-spinner-label{font-size:.8125rem;color:var(--shk-surface-500)}@keyframes shk-loading-spin{to{transform:rotate(360deg)}}\n"] }]
|
|
69
|
+
}], propDecorators: { size: [{ type: i0.Input, args: [{ isSignal: true, alias: "size", required: false }] }], thickness: [{ type: i0.Input, args: [{ isSignal: true, alias: "thickness", required: false }] }], color: [{ type: i0.Input, args: [{ isSignal: true, alias: "color", required: false }] }], label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }] } });
|
|
70
|
+
|
|
71
|
+
/**
|
|
72
|
+
* Shirkasoft UI Components.
|
|
73
|
+
* Authors: Roberto Valladares Martin (Ansem13), Julio César García García (Sanjuli14).
|
|
74
|
+
* Belongs to Shirkasoft.
|
|
75
|
+
*/
|
|
76
|
+
/** Progress bar with an indeterminate sweep or a determinate percentage. */
|
|
77
|
+
class LoadingBarComponent {
|
|
78
|
+
constructor() {
|
|
79
|
+
/** Height of the bar. */
|
|
80
|
+
this.height = input('0.25rem', ...(ngDevMode ? [{ debugName: "height" }] : /* istanbul ignore next */ []));
|
|
81
|
+
/** When true the bar animates without a known percentage. */
|
|
82
|
+
this.indeterminate = input(true, ...(ngDevMode ? [{ debugName: "indeterminate" }] : /* istanbul ignore next */ []));
|
|
83
|
+
/** Current progress 0-100 when `indeterminate` is false. */
|
|
84
|
+
this.progress = input(0, ...(ngDevMode ? [{ debugName: "progress" }] : /* istanbul ignore next */ []));
|
|
85
|
+
/** Fill color. Defaults to the primary token. */
|
|
86
|
+
this.color = input('', ...(ngDevMode ? [{ debugName: "color" }] : /* istanbul ignore next */ []));
|
|
87
|
+
/** Renders fully rounded ends. */
|
|
88
|
+
this.rounded = input(true, ...(ngDevMode ? [{ debugName: "rounded" }] : /* istanbul ignore next */ []));
|
|
89
|
+
/** Fill width/style for the determinate mode, empty for indeterminate. */
|
|
90
|
+
this.fillStyle = computed(() => {
|
|
91
|
+
if (this.indeterminate())
|
|
92
|
+
return {};
|
|
93
|
+
return { width: `${Math.max(0, Math.min(100, this.progress()))}%` };
|
|
94
|
+
}, ...(ngDevMode ? [{ debugName: "fillStyle" }] : /* istanbul ignore next */ []));
|
|
95
|
+
}
|
|
96
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: LoadingBarComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
97
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "21.2.18", type: LoadingBarComponent, isStandalone: true, selector: "shk-loading-bar", inputs: { height: { classPropertyName: "height", publicName: "height", isSignal: true, isRequired: false, transformFunction: null }, indeterminate: { classPropertyName: "indeterminate", publicName: "indeterminate", isSignal: true, isRequired: false, transformFunction: null }, progress: { classPropertyName: "progress", publicName: "progress", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, rounded: { classPropertyName: "rounded", publicName: "rounded", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
98
|
+
<div
|
|
99
|
+
class="shk-loading-bar"
|
|
100
|
+
[class.shk-loading-bar-indeterminate]="indeterminate()"
|
|
101
|
+
[style]="{ height: height(), borderRadius: rounded() ? '9999px' : undefined }"
|
|
102
|
+
role="progressbar"
|
|
103
|
+
[attr.aria-valuenow]="indeterminate() ? undefined : progress()"
|
|
104
|
+
aria-label="Progreso"
|
|
105
|
+
>
|
|
106
|
+
<div
|
|
107
|
+
class="shk-loading-bar-fill"
|
|
108
|
+
[style]="fillStyle()"
|
|
109
|
+
[style.background-color]="color() || undefined"
|
|
110
|
+
[style.border-radius]="rounded() ? '9999px' : undefined"
|
|
111
|
+
></div>
|
|
112
|
+
</div>
|
|
113
|
+
`, isInline: true, styles: [".shk-loading-bar{width:100%;position:relative;overflow:hidden;background-color:var(--shk-surface-200)}.shk-loading-bar-fill{height:100%;background-color:var(--shk-primary-600);transition:width .3s ease-in-out}.shk-loading-bar-indeterminate .shk-loading-bar-fill{width:40%;animation:shk-loading-bar-sweep 1.2s ease-in-out infinite}@keyframes shk-loading-bar-sweep{0%{transform:translate(-100%)}to{transform:translate(350%)}}\n"], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
114
|
+
}
|
|
115
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: LoadingBarComponent, decorators: [{
|
|
116
|
+
type: Component,
|
|
117
|
+
args: [{ selector: 'shk-loading-bar', standalone: true, changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
118
|
+
<div
|
|
119
|
+
class="shk-loading-bar"
|
|
120
|
+
[class.shk-loading-bar-indeterminate]="indeterminate()"
|
|
121
|
+
[style]="{ height: height(), borderRadius: rounded() ? '9999px' : undefined }"
|
|
122
|
+
role="progressbar"
|
|
123
|
+
[attr.aria-valuenow]="indeterminate() ? undefined : progress()"
|
|
124
|
+
aria-label="Progreso"
|
|
125
|
+
>
|
|
126
|
+
<div
|
|
127
|
+
class="shk-loading-bar-fill"
|
|
128
|
+
[style]="fillStyle()"
|
|
129
|
+
[style.background-color]="color() || undefined"
|
|
130
|
+
[style.border-radius]="rounded() ? '9999px' : undefined"
|
|
131
|
+
></div>
|
|
132
|
+
</div>
|
|
133
|
+
`, styles: [".shk-loading-bar{width:100%;position:relative;overflow:hidden;background-color:var(--shk-surface-200)}.shk-loading-bar-fill{height:100%;background-color:var(--shk-primary-600);transition:width .3s ease-in-out}.shk-loading-bar-indeterminate .shk-loading-bar-fill{width:40%;animation:shk-loading-bar-sweep 1.2s ease-in-out infinite}@keyframes shk-loading-bar-sweep{0%{transform:translate(-100%)}to{transform:translate(350%)}}\n"] }]
|
|
134
|
+
}], propDecorators: { height: [{ type: i0.Input, args: [{ isSignal: true, alias: "height", required: false }] }], indeterminate: [{ type: i0.Input, args: [{ isSignal: true, alias: "indeterminate", required: false }] }], progress: [{ type: i0.Input, args: [{ isSignal: true, alias: "progress", required: false }] }], color: [{ type: i0.Input, args: [{ isSignal: true, alias: "color", required: false }] }], rounded: [{ type: i0.Input, args: [{ isSignal: true, alias: "rounded", required: false }] }] } });
|
|
135
|
+
|
|
136
|
+
/**
|
|
137
|
+
* Shirkasoft UI Components.
|
|
138
|
+
* Authors: Roberto Valladares Martin (Ansem13), Julio César García García (Sanjuli14).
|
|
139
|
+
* Belongs to Shirkasoft.
|
|
140
|
+
*/
|
|
141
|
+
/** Wraps content and shows a centered spinner over it while `visible` is true. */
|
|
142
|
+
class LoadingOverlayComponent {
|
|
143
|
+
constructor() {
|
|
144
|
+
/** Controls whether the spinner layer is shown. */
|
|
145
|
+
this.visible = input(false, ...(ngDevMode ? [{ debugName: "visible" }] : /* istanbul ignore next */ []));
|
|
146
|
+
/** Optional text under the spinner. */
|
|
147
|
+
this.message = input('', ...(ngDevMode ? [{ debugName: "message" }] : /* istanbul ignore next */ []));
|
|
148
|
+
/** Diameter of the spinner. */
|
|
149
|
+
this.spinnerSize = input('2.5rem', ...(ngDevMode ? [{ debugName: "spinnerSize" }] : /* istanbul ignore next */ []));
|
|
150
|
+
/** Spinner color. Defaults to the primary token. */
|
|
151
|
+
this.color = input('', ...(ngDevMode ? [{ debugName: "color" }] : /* istanbul ignore next */ []));
|
|
152
|
+
/** Backdrop behind the spinner. */
|
|
153
|
+
this.backdrop = input('transparent', ...(ngDevMode ? [{ debugName: "backdrop" }] : /* istanbul ignore next */ []));
|
|
154
|
+
}
|
|
155
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: LoadingOverlayComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
156
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.18", type: LoadingOverlayComponent, isStandalone: true, selector: "shk-loading-overlay", inputs: { visible: { classPropertyName: "visible", publicName: "visible", isSignal: true, isRequired: false, transformFunction: null }, message: { classPropertyName: "message", publicName: "message", isSignal: true, isRequired: false, transformFunction: null }, spinnerSize: { classPropertyName: "spinnerSize", publicName: "spinnerSize", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, backdrop: { classPropertyName: "backdrop", publicName: "backdrop", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
157
|
+
<div
|
|
158
|
+
class="shk-loading-overlay"
|
|
159
|
+
[class.shk-loading-overlay-light]="backdrop() === 'light'"
|
|
160
|
+
[class.shk-loading-overlay-dark]="backdrop() === 'dark'"
|
|
161
|
+
>
|
|
162
|
+
<ng-content></ng-content>
|
|
163
|
+
@if (visible()) {
|
|
164
|
+
<div class="shk-loading-overlay-layer">
|
|
165
|
+
<shk-loading-spinner [size]="spinnerSize()" [color]="color()" [label]="message()" />
|
|
166
|
+
</div>
|
|
167
|
+
}
|
|
168
|
+
</div>
|
|
169
|
+
`, isInline: true, styles: [":host{display:block}.shk-loading-overlay{position:relative;min-height:1.5rem}.shk-loading-overlay-layer{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;z-index:10}.shk-loading-overlay-light .shk-loading-overlay-layer{background-color:#ffffffa6}.dark .shk-loading-overlay-light .shk-loading-overlay-layer{background-color:#0000008c}.shk-loading-overlay-dark .shk-loading-overlay-layer{background-color:#0006}\n"], dependencies: [{ kind: "component", type: LoadingSpinnerComponent, selector: "shk-loading-spinner", inputs: ["size", "thickness", "color", "label"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
170
|
+
}
|
|
171
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: LoadingOverlayComponent, decorators: [{
|
|
172
|
+
type: Component,
|
|
173
|
+
args: [{ selector: 'shk-loading-overlay', standalone: true, changeDetection: ChangeDetectionStrategy.OnPush, imports: [LoadingSpinnerComponent], template: `
|
|
174
|
+
<div
|
|
175
|
+
class="shk-loading-overlay"
|
|
176
|
+
[class.shk-loading-overlay-light]="backdrop() === 'light'"
|
|
177
|
+
[class.shk-loading-overlay-dark]="backdrop() === 'dark'"
|
|
178
|
+
>
|
|
179
|
+
<ng-content></ng-content>
|
|
180
|
+
@if (visible()) {
|
|
181
|
+
<div class="shk-loading-overlay-layer">
|
|
182
|
+
<shk-loading-spinner [size]="spinnerSize()" [color]="color()" [label]="message()" />
|
|
183
|
+
</div>
|
|
184
|
+
}
|
|
185
|
+
</div>
|
|
186
|
+
`, styles: [":host{display:block}.shk-loading-overlay{position:relative;min-height:1.5rem}.shk-loading-overlay-layer{position:absolute;inset:0;display:flex;align-items:center;justify-content:center;z-index:10}.shk-loading-overlay-light .shk-loading-overlay-layer{background-color:#ffffffa6}.dark .shk-loading-overlay-light .shk-loading-overlay-layer{background-color:#0000008c}.shk-loading-overlay-dark .shk-loading-overlay-layer{background-color:#0006}\n"] }]
|
|
187
|
+
}], propDecorators: { visible: [{ type: i0.Input, args: [{ isSignal: true, alias: "visible", required: false }] }], message: [{ type: i0.Input, args: [{ isSignal: true, alias: "message", required: false }] }], spinnerSize: [{ type: i0.Input, args: [{ isSignal: true, alias: "spinnerSize", required: false }] }], color: [{ type: i0.Input, args: [{ isSignal: true, alias: "color", required: false }] }], backdrop: [{ type: i0.Input, args: [{ isSignal: true, alias: "backdrop", required: false }] }] } });
|
|
188
|
+
|
|
189
|
+
/**
|
|
190
|
+
* Shirkasoft UI Components.
|
|
191
|
+
* Authors: Roberto Valladares Martin (Ansem13), Julio César García García (Sanjuli14).
|
|
192
|
+
* Belongs to Shirkasoft.
|
|
193
|
+
*/
|
|
194
|
+
/** Bouncing dots loading indicator. */
|
|
195
|
+
class LoadingDotsComponent {
|
|
196
|
+
constructor() {
|
|
197
|
+
/** Diameter of each dot. */
|
|
198
|
+
this.size = input('0.5rem', ...(ngDevMode ? [{ debugName: "size" }] : /* istanbul ignore next */ []));
|
|
199
|
+
/** Dot color. Defaults to the primary token. */
|
|
200
|
+
this.color = input('', ...(ngDevMode ? [{ debugName: "color" }] : /* istanbul ignore next */ []));
|
|
201
|
+
/** Number of dots. */
|
|
202
|
+
this.count = input(3, ...(ngDevMode ? [{ debugName: "count" }] : /* istanbul ignore next */ []));
|
|
203
|
+
/** Optional text shown next to the dots. */
|
|
204
|
+
this.label = input('', ...(ngDevMode ? [{ debugName: "label" }] : /* istanbul ignore next */ []));
|
|
205
|
+
/** Array of dot indices to render based on the `count` input. */
|
|
206
|
+
this.dots = computed(() => Array.from({ length: Math.max(1, this.count()) }), ...(ngDevMode ? [{ debugName: "dots" }] : /* istanbul ignore next */ []));
|
|
207
|
+
}
|
|
208
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: LoadingDotsComponent, deps: [], target: i0.ɵɵFactoryTarget.Component }); }
|
|
209
|
+
static { this.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "21.2.18", type: LoadingDotsComponent, isStandalone: true, selector: "shk-loading-dots", inputs: { size: { classPropertyName: "size", publicName: "size", isSignal: true, isRequired: false, transformFunction: null }, color: { classPropertyName: "color", publicName: "color", isSignal: true, isRequired: false, transformFunction: null }, count: { classPropertyName: "count", publicName: "count", isSignal: true, isRequired: false, transformFunction: null }, label: { classPropertyName: "label", publicName: "label", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
210
|
+
<span class="shk-loading-dots" role="status" aria-label="Cargando">
|
|
211
|
+
@for (dot of dots(); track $index) {
|
|
212
|
+
<span
|
|
213
|
+
class="shk-loading-dot"
|
|
214
|
+
[style]="{
|
|
215
|
+
width: size(),
|
|
216
|
+
height: size(),
|
|
217
|
+
backgroundColor: color() || undefined,
|
|
218
|
+
animationDelay: $index * 0.12 + 's',
|
|
219
|
+
}"
|
|
220
|
+
></span>
|
|
221
|
+
}
|
|
222
|
+
</span>
|
|
223
|
+
@if (label()) {
|
|
224
|
+
<span class="shk-loading-dots-label">{{ label() }}</span>
|
|
225
|
+
}
|
|
226
|
+
`, isInline: true, styles: [":host{display:inline-flex;align-items:center;gap:.5rem}.shk-loading-dots{display:inline-flex;align-items:center;gap:.25rem}.shk-loading-dot{border-radius:9999px;background-color:var(--shk-primary-600);animation:shk-loading-dots-bounce 1.4s ease-in-out infinite}.shk-loading-dots-label{font-size:.8125rem;color:var(--shk-surface-500)}@keyframes shk-loading-dots-bounce{0%,80%,to{transform:scale(.6);opacity:.5}40%{transform:scale(1);opacity:1}}\n"], changeDetection: i0.ChangeDetectionStrategy.OnPush }); }
|
|
227
|
+
}
|
|
228
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.18", ngImport: i0, type: LoadingDotsComponent, decorators: [{
|
|
229
|
+
type: Component,
|
|
230
|
+
args: [{ selector: 'shk-loading-dots', standalone: true, changeDetection: ChangeDetectionStrategy.OnPush, template: `
|
|
231
|
+
<span class="shk-loading-dots" role="status" aria-label="Cargando">
|
|
232
|
+
@for (dot of dots(); track $index) {
|
|
233
|
+
<span
|
|
234
|
+
class="shk-loading-dot"
|
|
235
|
+
[style]="{
|
|
236
|
+
width: size(),
|
|
237
|
+
height: size(),
|
|
238
|
+
backgroundColor: color() || undefined,
|
|
239
|
+
animationDelay: $index * 0.12 + 's',
|
|
240
|
+
}"
|
|
241
|
+
></span>
|
|
242
|
+
}
|
|
243
|
+
</span>
|
|
244
|
+
@if (label()) {
|
|
245
|
+
<span class="shk-loading-dots-label">{{ label() }}</span>
|
|
246
|
+
}
|
|
247
|
+
`, styles: [":host{display:inline-flex;align-items:center;gap:.5rem}.shk-loading-dots{display:inline-flex;align-items:center;gap:.25rem}.shk-loading-dot{border-radius:9999px;background-color:var(--shk-primary-600);animation:shk-loading-dots-bounce 1.4s ease-in-out infinite}.shk-loading-dots-label{font-size:.8125rem;color:var(--shk-surface-500)}@keyframes shk-loading-dots-bounce{0%,80%,to{transform:scale(.6);opacity:.5}40%{transform:scale(1);opacity:1}}\n"] }]
|
|
248
|
+
}], propDecorators: { size: [{ type: i0.Input, args: [{ isSignal: true, alias: "size", required: false }] }], color: [{ type: i0.Input, args: [{ isSignal: true, alias: "color", required: false }] }], count: [{ type: i0.Input, args: [{ isSignal: true, alias: "count", required: false }] }], label: [{ type: i0.Input, args: [{ isSignal: true, alias: "label", required: false }] }] } });
|
|
249
|
+
|
|
250
|
+
/**
|
|
251
|
+
* Generated bundle index. Do not edit.
|
|
252
|
+
*/
|
|
253
|
+
|
|
254
|
+
export { LoadingBarComponent, LoadingDotsComponent, LoadingOverlayComponent, LoadingSpinnerComponent };
|
|
255
|
+
//# sourceMappingURL=shirkasoft-ui-components-loading.mjs.map
|