easy-forms-core 1.1.1 → 1.1.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,6 +1,6 @@
1
- # EasyForms
1
+ # EasyFormsCore
2
2
 
3
- EasyForms es una librería agnóstica de framework para construir formularios dinámicos a partir de JSON usando Web Components.
3
+ EasyFormsCore es una librería agnóstica de framework para construir formularios dinámicos a partir de JSON usando Web Components.
4
4
 
5
5
  Permite crear formularios completos únicamente describiendo un schema JSON.
6
6
 
@@ -229,6 +229,173 @@ form.schema = { fields: [...] }
229
229
  // template ahora es null
230
230
  ```
231
231
 
232
+ ## Personalización de Estilos
233
+
234
+ EasyFormsCore utiliza variables CSS que puedes sobrescribir para personalizar completamente la apariencia de tus formularios. Todas las variables están definidas en el scope del componente (`:host`), lo que permite un control total sobre los colores y estilos.
235
+
236
+ ### Variables CSS Disponibles
237
+
238
+ Puedes sobrescribir estas variables CSS para personalizar los colores de tu formulario:
239
+
240
+ ```css
241
+ easy-form {
242
+ --easy-form-primary: #007bff; /* Color principal (botones, focus, etc.) */
243
+ --easy-form-secondary: #6c757d; /* Color secundario */
244
+ --easy-form-error: #dc3545; /* Color de error */
245
+ --easy-form-success: #28a745; /* Color de éxito */
246
+ --easy-form-text: #212529; /* Color del texto */
247
+ --easy-form-label-color: #212529; /* Color de las etiquetas */
248
+ --easy-form-border: #ddd; /* Color de los bordes */
249
+ --easy-form-background: #ffffff; /* Color de fondo */
250
+ }
251
+ ```
252
+
253
+ ### Ejemplo de Personalización de Colores
254
+
255
+ ```html
256
+ <style>
257
+ easy-form {
258
+ --easy-form-primary: #8b5cf6;
259
+ --easy-form-secondary: #64748b;
260
+ --easy-form-error: #ef4444;
261
+ --easy-form-success: #10b981;
262
+ --easy-form-text: #1e293b;
263
+ --easy-form-label-color: #334155;
264
+ --easy-form-border: #e2e8f0;
265
+ --easy-form-background: #ffffff;
266
+ }
267
+ </style>
268
+
269
+ <easy-form id="form"></easy-form>
270
+ ```
271
+
272
+ ### Sobrescribir Estilos con Clases CSS
273
+
274
+ Puedes sobrescribir cualquier estilo usando las clases CSS del componente. Todas las clases utilizan el prefijo `easy-form-` para evitar conflictos.
275
+
276
+ #### Clases Principales
277
+
278
+ - `.easy-form-field` - Contenedor de cada campo
279
+ - `.easy-form-label` - Etiquetas de los campos
280
+ - `.easy-form-required` - Indicador de campo requerido (asterisco)
281
+ - `.easy-form-input-error` - Input con error
282
+ - `.easy-form-error` - Mensaje de error
283
+ - `.easy-form-description` - Descripción del campo
284
+ - `.easy-form-submit` - Botón de envío
285
+
286
+ #### Clases de Grupos y Filas
287
+
288
+ - `.easy-form-group` - Contenedor de grupo de campos
289
+ - `.easy-form-group-label` - Etiqueta del grupo
290
+ - `.easy-form-row` - Fila horizontal de campos
291
+ - `.easy-form-array` - Contenedor de array dinámico
292
+ - `.easy-form-array-item` - Item individual del array
293
+ - `.easy-form-array-add` - Botón para agregar items
294
+ - `.easy-form-array-remove` - Botón para remover items
295
+
296
+ #### Clases de Wizard/Steps
297
+
298
+ - `.easy-form-wizard` - Contenedor del wizard
299
+ - `.easy-form-wizard-steps` - Contenedor de los pasos
300
+ - `.easy-form-wizard-step` - Paso individual
301
+ - `.easy-form-wizard-step.active` - Paso activo
302
+ - `.easy-form-wizard-step.completed` - Paso completado
303
+ - `.easy-form-wizard-nav` - Navegación del wizard
304
+ - `.easy-form-wizard-prev` - Botón anterior
305
+ - `.easy-form-wizard-next` - Botón siguiente
306
+ - `.easy-form-wizard-fields` - Contenedor de campos del paso actual
307
+
308
+ #### Clases de Inputs Especiales
309
+
310
+ - `.easy-form-radio-group` - Grupo de radio buttons
311
+ - `.easy-form-radio-option` - Opción de radio
312
+ - `.easy-form-radio-label` - Etiqueta de radio
313
+ - `.easy-form-label-checkbox` - Etiqueta de checkbox
314
+ - `.easy-form-label-switch` - Etiqueta de switch
315
+ - `.easy-form-quantity-container` - Contenedor de quantity input
316
+ - `.easy-form-quantity-wrapper` - Wrapper del quantity
317
+ - `.easy-form-quantity-btn` - Botón +/- del quantity
318
+ - `.easy-form-quantity-input` - Input del quantity
319
+ - `.easy-form-accordion-select-container` - Contenedor de accordion select
320
+ - `.easy-form-accordion-item` - Item del accordion
321
+ - `.easy-form-accordion-item.selected` - Item seleccionado
322
+ - `.easy-form-accordion-item.open` - Item abierto
323
+ - `.easy-form-accordion-header` - Header del accordion
324
+ - `.easy-form-accordion-content` - Contenido del accordion
325
+ - `.easy-form-image-grid-container` - Contenedor de image grid
326
+ - `.easy-form-image-grid-item` - Item del grid
327
+ - `.easy-form-image-grid-item.selected` - Item seleccionado
328
+ - `.easy-form-otp-container` - Contenedor de OTP
329
+ - `.easy-form-otp-input` - Input individual de OTP
330
+
331
+ #### Clases de Estado
332
+
333
+ - `.easy-form-field-hidden` - Campo oculto
334
+ - `.easy-form-field-disabled` - Campo deshabilitado
335
+
336
+ ### Ejemplo de Sobrescritura de Estilos
337
+
338
+ ```html
339
+ <style>
340
+ /* Personalizar colores con variables CSS */
341
+ easy-form {
342
+ --easy-form-primary: #6366f1;
343
+ --easy-form-error: #f43f5e;
344
+ }
345
+
346
+ /* Sobrescribir estilos específicos */
347
+ easy-form .easy-form-label {
348
+ font-weight: 700;
349
+ font-size: 0.875rem;
350
+ text-transform: uppercase;
351
+ letter-spacing: 0.05em;
352
+ }
353
+
354
+ easy-form .easy-form-submit {
355
+ border-radius: 12px;
356
+ padding: 0.875rem 2rem;
357
+ font-weight: 600;
358
+ text-transform: uppercase;
359
+ letter-spacing: 0.1em;
360
+ box-shadow: 0 4px 12px rgba(99, 102, 241, 0.3);
361
+ }
362
+
363
+ easy-form .easy-form-submit:hover {
364
+ transform: translateY(-2px);
365
+ box-shadow: 0 6px 16px rgba(99, 102, 241, 0.4);
366
+ }
367
+
368
+ /* Personalizar inputs */
369
+ easy-form input:not([type="checkbox"]):not([type="radio"]),
370
+ easy-form textarea,
371
+ easy-form select {
372
+ border-radius: 8px;
373
+ border-width: 2px;
374
+ padding: 0.75rem 1rem;
375
+ transition: all 0.2s ease;
376
+ }
377
+
378
+ easy-form input:focus,
379
+ easy-form textarea:focus,
380
+ easy-form select:focus {
381
+ outline: none;
382
+ box-shadow: 0 0 0 4px rgba(99, 102, 241, 0.1);
383
+ }
384
+ </style>
385
+
386
+ <easy-form id="form"></easy-form>
387
+ ```
388
+
389
+ ### Notas Importantes
390
+
391
+ 1. **Especificidad**: Los estilos del componente tienen especificidad media. Si necesitas sobrescribir estilos con `!important`, puedes hacerlo, pero se recomienda usar variables CSS cuando sea posible.
392
+
393
+ 2. **Shadow DOM**: El componente utiliza Shadow DOM, por lo que los estilos globales no afectan directamente al contenido interno. Debes usar el selector `easy-form` o las variables CSS.
394
+
395
+ 3. **Variables CSS**: Las variables CSS son la forma recomendada de personalizar colores, ya que se propagan correctamente dentro del Shadow DOM.
396
+
397
+ 4. **Temas**: Los temas predefinidos (plano, tradicional, material, etc.) también respetan las variables CSS que definas, por lo que puedes cambiar los colores manteniendo el estilo del tema.
398
+
232
399
  ## Características
233
400
 
234
401
  - Web Component nativo
@@ -385,6 +385,10 @@ declare class EasyForm extends BrowserHTMLElement {
385
385
  * Renderiza el formulario
386
386
  */
387
387
  private render;
388
+ /**
389
+ * Actualiza el overlay de loading sobre el formulario
390
+ */
391
+ private updateLoadingOverlay;
388
392
  /**
389
393
  * Preserva los valores actuales del DOM antes de re-renderizar
390
394
  * Retorna un objeto con los valores preservados
@@ -527,6 +531,22 @@ declare class EasyForm extends BrowserHTMLElement {
527
531
  * Establece los datos iniciales
528
532
  */
529
533
  set initialData(value: Record<string, any> | null);
534
+ /**
535
+ * Obtiene el estado de loading
536
+ */
537
+ get loading(): boolean;
538
+ /**
539
+ * Establece el estado de loading
540
+ */
541
+ set loading(value: boolean);
542
+ /**
543
+ * Obtiene el estado de disabled
544
+ */
545
+ get disabled(): boolean;
546
+ /**
547
+ * Establece el estado de disabled
548
+ */
549
+ set disabled(value: boolean);
530
550
  /**
531
551
  * Configura estilos básicos
532
552
  */
package/dist/easy-form.js CHANGED
@@ -682,6 +682,53 @@ function getBaseStyles(colors) {
682
682
  .easy-form-otp-input:invalid {
683
683
  border-color: var(--easy-form-error);
684
684
  }
685
+ /* Loading Overlay (sobre el formulario) */
686
+ .easy-form-loading-overlay {
687
+ position: absolute;
688
+ top: 0;
689
+ left: 0;
690
+ right: 0;
691
+ bottom: 0;
692
+ background: rgba(255, 255, 255, 0.8);
693
+ display: flex;
694
+ align-items: center;
695
+ justify-content: center;
696
+ z-index: 1000;
697
+ backdrop-filter: blur(2px);
698
+ border-radius: inherit;
699
+ }
700
+ .easy-form-loading-spinner {
701
+ width: 40px;
702
+ height: 40px;
703
+ border: 4px solid rgba(0, 0, 0, 0.1);
704
+ border-top-color: var(--easy-form-primary);
705
+ border-radius: 50%;
706
+ animation: easy-form-spin 0.8s linear infinite;
707
+ }
708
+ @keyframes easy-form-spin {
709
+ to {
710
+ transform: rotate(360deg);
711
+ }
712
+ }
713
+ /* Disabled State */
714
+ .easy-form-disabled,
715
+ .easy-form-disabled * {
716
+ pointer-events: none;
717
+ opacity: 0.6;
718
+ }
719
+ .easy-form-disabled input,
720
+ .easy-form-disabled textarea,
721
+ .easy-form-disabled select,
722
+ .easy-form-disabled button {
723
+ cursor: not-allowed;
724
+ }
725
+ .easy-form-input-disabled {
726
+ opacity: 0.6;
727
+ cursor: not-allowed !important;
728
+ }
729
+ form {
730
+ position: relative;
731
+ }
685
732
  `;
686
733
  }
687
734
  function getThemeSpecificStyles(theme, colors) {
@@ -4483,7 +4530,7 @@ var EasyForm = class extends BrowserHTMLElement {
4483
4530
  this.shadow = this.attachShadow({ mode: "open" });
4484
4531
  }
4485
4532
  static get observedAttributes() {
4486
- return ["schema", "template", "template-extend", "theme", "colors", "initialData"];
4533
+ return ["schema", "template", "template-extend", "theme", "colors", "initialData", "loading", "disabled"];
4487
4534
  }
4488
4535
  /**
4489
4536
  * Obtiene el schema
@@ -4592,6 +4639,21 @@ var EasyForm = class extends BrowserHTMLElement {
4592
4639
  if ((name === "theme" || name === "colors") && newValue !== oldValue) {
4593
4640
  this.setupStyles();
4594
4641
  }
4642
+ if (name === "loading" && newValue !== oldValue) {
4643
+ const form = this.shadow.querySelector("form");
4644
+ this.updateLoadingOverlay(form || void 0);
4645
+ if (form) {
4646
+ const inputs = form.querySelectorAll("input, textarea, select, button");
4647
+ inputs.forEach((input) => {
4648
+ if (input instanceof HTMLElement && "disabled" in input) {
4649
+ input.disabled = this.loading;
4650
+ }
4651
+ });
4652
+ }
4653
+ }
4654
+ if (name === "disabled" && newValue !== oldValue) {
4655
+ this.render();
4656
+ }
4595
4657
  }
4596
4658
  /**
4597
4659
  * Maneja el cambio de schema
@@ -4678,6 +4740,9 @@ var EasyForm = class extends BrowserHTMLElement {
4678
4740
  const finalWizardState = this.stateManager.getWizardState();
4679
4741
  const newFormElement = document.createElement("form");
4680
4742
  newFormElement.addEventListener("submit", (e) => this.handleSubmit(e));
4743
+ if (this.disabled || this.loading) {
4744
+ newFormElement.classList.add("easy-form-disabled");
4745
+ }
4681
4746
  if (finalWizardState) {
4682
4747
  this.renderWizard(newFormElement);
4683
4748
  } else {
@@ -4686,6 +4751,9 @@ var EasyForm = class extends BrowserHTMLElement {
4686
4751
  submitButton.type = "submit";
4687
4752
  submitButton.textContent = "Enviar";
4688
4753
  submitButton.className = "easy-form-submit";
4754
+ if (this.disabled || this.loading) {
4755
+ submitButton.disabled = true;
4756
+ }
4689
4757
  newFormElement.appendChild(submitButton);
4690
4758
  }
4691
4759
  const oldForm = this.shadow.querySelector("form");
@@ -4697,10 +4765,33 @@ var EasyForm = class extends BrowserHTMLElement {
4697
4765
  }
4698
4766
  }
4699
4767
  this.shadow.appendChild(newFormElement);
4768
+ if (this.loading) {
4769
+ this.updateLoadingOverlay(newFormElement);
4770
+ }
4700
4771
  } finally {
4701
4772
  this.isRendering = false;
4702
4773
  }
4703
4774
  }
4775
+ /**
4776
+ * Actualiza el overlay de loading sobre el formulario
4777
+ */
4778
+ updateLoadingOverlay(formElement) {
4779
+ const existingOverlay = this.shadow.querySelector(".easy-form-loading-overlay");
4780
+ if (existingOverlay) {
4781
+ existingOverlay.remove();
4782
+ }
4783
+ if (this.loading) {
4784
+ const form = formElement || this.shadow.querySelector("form");
4785
+ if (form) {
4786
+ const overlay = document.createElement("div");
4787
+ overlay.className = "easy-form-loading-overlay";
4788
+ const spinner = document.createElement("div");
4789
+ spinner.className = "easy-form-loading-spinner";
4790
+ overlay.appendChild(spinner);
4791
+ form.appendChild(overlay);
4792
+ }
4793
+ }
4794
+ }
4704
4795
  /**
4705
4796
  * Preserva los valores actuales del DOM antes de re-renderizar
4706
4797
  * Retorna un objeto con los valores preservados
@@ -4809,9 +4900,10 @@ var EasyForm = class extends BrowserHTMLElement {
4809
4900
  const value = this.stateManager.getValue(field.name);
4810
4901
  const errors = this.stateManager.getErrors(field.name);
4811
4902
  const error = errors.length > 0 ? errors[0] : void 0;
4903
+ const isFormDisabled = this.disabled || this.loading;
4812
4904
  const fieldWithDependencies = {
4813
4905
  ...field,
4814
- disabled: !isEnabled || field.disabled
4906
+ disabled: isFormDisabled || !isEnabled || field.disabled
4815
4907
  };
4816
4908
  const customComponent = getCustomComponent(field.type);
4817
4909
  if (customComponent) {
@@ -4932,11 +5024,15 @@ var EasyForm = class extends BrowserHTMLElement {
4932
5024
  removeButton.type = "button";
4933
5025
  removeButton.textContent = "Eliminar";
4934
5026
  removeButton.className = "easy-form-array-remove";
4935
- removeButton.addEventListener("click", () => {
4936
- const newValues = [...values];
4937
- newValues.splice(i, 1);
4938
- this.handleFieldChange(field.name, newValues);
4939
- });
5027
+ if (this.disabled || this.loading) {
5028
+ removeButton.disabled = true;
5029
+ } else {
5030
+ removeButton.addEventListener("click", () => {
5031
+ const newValues = [...values];
5032
+ newValues.splice(i, 1);
5033
+ this.handleFieldChange(field.name, newValues);
5034
+ });
5035
+ }
4940
5036
  itemContainer.appendChild(removeButton);
4941
5037
  itemsContainer.appendChild(itemContainer);
4942
5038
  }
@@ -4945,10 +5041,14 @@ var EasyForm = class extends BrowserHTMLElement {
4945
5041
  addButton.type = "button";
4946
5042
  addButton.textContent = "Agregar";
4947
5043
  addButton.className = "easy-form-array-add";
4948
- addButton.addEventListener("click", () => {
4949
- const newValues = [...values, {}];
4950
- this.handleFieldChange(field.name, newValues);
4951
- });
5044
+ if (this.disabled || this.loading) {
5045
+ addButton.disabled = true;
5046
+ } else {
5047
+ addButton.addEventListener("click", () => {
5048
+ const newValues = [...values, {}];
5049
+ this.handleFieldChange(field.name, newValues);
5050
+ });
5051
+ }
4952
5052
  arrayContainer.appendChild(addButton);
4953
5053
  return arrayContainer;
4954
5054
  }
@@ -5016,13 +5116,17 @@ var EasyForm = class extends BrowserHTMLElement {
5016
5116
  prevButton.type = "button";
5017
5117
  prevButton.textContent = "Anterior";
5018
5118
  prevButton.className = "easy-form-wizard-prev";
5019
- prevButton.addEventListener("click", () => {
5020
- const currentState = this.stateManager.getWizardState();
5021
- if (currentState && this.stateManager.previousStep()) {
5022
- this.render();
5023
- this.emitStepChange();
5024
- }
5025
- });
5119
+ if (this.disabled || this.loading) {
5120
+ prevButton.disabled = true;
5121
+ } else {
5122
+ prevButton.addEventListener("click", () => {
5123
+ const currentState = this.stateManager.getWizardState();
5124
+ if (currentState && this.stateManager.previousStep()) {
5125
+ this.render();
5126
+ this.emitStepChange();
5127
+ }
5128
+ });
5129
+ }
5026
5130
  navContainer.appendChild(prevButton);
5027
5131
  }
5028
5132
  if (wizardState.currentStep < wizardState.totalSteps - 1) {
@@ -5030,34 +5134,38 @@ var EasyForm = class extends BrowserHTMLElement {
5030
5134
  nextButton.type = "button";
5031
5135
  nextButton.textContent = "Siguiente";
5032
5136
  nextButton.className = "easy-form-wizard-next";
5033
- nextButton.addEventListener("click", async () => {
5034
- const currentState = this.stateManager.getWizardState();
5035
- if (!currentState) return;
5036
- const currentFields2 = this.stateManager.getCurrentStepFields();
5037
- for (const field of currentFields2) {
5038
- if (this.stateManager.getFieldVisibility(field.name)) {
5039
- await this.stateManager.validateField(field.name);
5137
+ if (this.disabled || this.loading) {
5138
+ nextButton.disabled = true;
5139
+ } else {
5140
+ nextButton.addEventListener("click", async () => {
5141
+ const currentState = this.stateManager.getWizardState();
5142
+ if (!currentState) return;
5143
+ const currentFields2 = this.stateManager.getCurrentStepFields();
5144
+ for (const field of currentFields2) {
5145
+ if (this.stateManager.getFieldVisibility(field.name)) {
5146
+ await this.stateManager.validateField(field.name);
5147
+ }
5040
5148
  }
5041
- }
5042
- const allErrors = this.stateManager.getAllErrors();
5043
- const stepErrors = {};
5044
- for (const field of currentFields2) {
5045
- if (allErrors[field.name] && allErrors[field.name].length > 0) {
5046
- stepErrors[field.name] = allErrors[field.name];
5149
+ const allErrors = this.stateManager.getAllErrors();
5150
+ const stepErrors = {};
5151
+ for (const field of currentFields2) {
5152
+ if (allErrors[field.name] && allErrors[field.name].length > 0) {
5153
+ stepErrors[field.name] = allErrors[field.name];
5154
+ }
5047
5155
  }
5048
- }
5049
- const hasErrors = Object.keys(stepErrors).length > 0;
5050
- if (!hasErrors) {
5051
- this.stateManager.completeStep(currentState.currentStep);
5052
- const moved = this.stateManager.nextStep();
5053
- if (moved) {
5054
- this.render();
5055
- this.emitStepChange();
5156
+ const hasErrors = Object.keys(stepErrors).length > 0;
5157
+ if (!hasErrors) {
5158
+ this.stateManager.completeStep(currentState.currentStep);
5159
+ const moved = this.stateManager.nextStep();
5160
+ if (moved) {
5161
+ this.render();
5162
+ this.emitStepChange();
5163
+ }
5164
+ } else {
5165
+ this.emitError(stepErrors);
5056
5166
  }
5057
- } else {
5058
- this.emitError(stepErrors);
5059
- }
5060
- });
5167
+ });
5168
+ }
5061
5169
  navContainer.appendChild(nextButton);
5062
5170
  }
5063
5171
  if (wizardState.currentStep === wizardState.totalSteps - 1) {
@@ -5065,27 +5173,31 @@ var EasyForm = class extends BrowserHTMLElement {
5065
5173
  submitButton.type = "button";
5066
5174
  submitButton.textContent = "Enviar";
5067
5175
  submitButton.className = "easy-form-wizard-next";
5068
- submitButton.addEventListener("click", async () => {
5069
- const currentFields2 = this.stateManager.getCurrentStepFields();
5070
- for (const field of currentFields2) {
5071
- if (this.stateManager.getFieldVisibility(field.name)) {
5072
- await this.stateManager.validateField(field.name);
5176
+ if (this.disabled || this.loading) {
5177
+ submitButton.disabled = true;
5178
+ } else {
5179
+ submitButton.addEventListener("click", async () => {
5180
+ const currentFields2 = this.stateManager.getCurrentStepFields();
5181
+ for (const field of currentFields2) {
5182
+ if (this.stateManager.getFieldVisibility(field.name)) {
5183
+ await this.stateManager.validateField(field.name);
5184
+ }
5073
5185
  }
5074
- }
5075
- const allErrors = this.stateManager.getAllErrors();
5076
- const stepErrors = {};
5077
- for (const field of currentFields2) {
5078
- if (allErrors[field.name] && allErrors[field.name].length > 0) {
5079
- stepErrors[field.name] = allErrors[field.name];
5186
+ const allErrors = this.stateManager.getAllErrors();
5187
+ const stepErrors = {};
5188
+ for (const field of currentFields2) {
5189
+ if (allErrors[field.name] && allErrors[field.name].length > 0) {
5190
+ stepErrors[field.name] = allErrors[field.name];
5191
+ }
5080
5192
  }
5081
- }
5082
- const hasErrors = Object.keys(stepErrors).length > 0;
5083
- if (!hasErrors) {
5084
- await this.handleSubmit(new Event("submit"));
5085
- } else {
5086
- this.emitError(stepErrors);
5087
- }
5088
- });
5193
+ const hasErrors = Object.keys(stepErrors).length > 0;
5194
+ if (!hasErrors) {
5195
+ await this.handleSubmit(new Event("submit"));
5196
+ } else {
5197
+ this.emitError(stepErrors);
5198
+ }
5199
+ });
5200
+ }
5089
5201
  navContainer.appendChild(submitButton);
5090
5202
  }
5091
5203
  wizardContainer.appendChild(navContainer);
@@ -5432,6 +5544,38 @@ var EasyForm = class extends BrowserHTMLElement {
5432
5544
  this.removeAttribute("initialData");
5433
5545
  }
5434
5546
  }
5547
+ /**
5548
+ * Obtiene el estado de loading
5549
+ */
5550
+ get loading() {
5551
+ return this.hasAttribute("loading");
5552
+ }
5553
+ /**
5554
+ * Establece el estado de loading
5555
+ */
5556
+ set loading(value) {
5557
+ if (value) {
5558
+ this.setAttribute("loading", "");
5559
+ } else {
5560
+ this.removeAttribute("loading");
5561
+ }
5562
+ }
5563
+ /**
5564
+ * Obtiene el estado de disabled
5565
+ */
5566
+ get disabled() {
5567
+ return this.hasAttribute("disabled");
5568
+ }
5569
+ /**
5570
+ * Establece el estado de disabled
5571
+ */
5572
+ set disabled(value) {
5573
+ if (value) {
5574
+ this.setAttribute("disabled", "");
5575
+ } else {
5576
+ this.removeAttribute("disabled");
5577
+ }
5578
+ }
5435
5579
  /**
5436
5580
  * Configura estilos básicos
5437
5581
  */