@mmlogic/components 0.1.7 → 0.1.9

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.
@@ -1,5 +1,5 @@
1
1
  import { r as registerInstance, c as createEvent, h, H as Host, g as getElement } from './index-_tsCCkAi.js';
2
- import { ClientLayoutItemFieldDataType, ClientLayoutItemType, ClientLayoutItemRelationDisplayType } from './index.js';
2
+ import { ClientLayoutItemFieldDataType, ClientLayoutItemType, ClientLayoutItemRelationDisplayType, ClientLayoutItemRelationEditBehavior } from './index.js';
3
3
  import { p as parseLocalizedNumber, d as formatNumber } from './format-Dt-aHxkM.js';
4
4
 
5
5
  const mrdBooleanFieldScss = () => `.sc-mrd-boolean-field-h{display:block}.mrd-boolean-field.sc-mrd-boolean-field{display:flex;align-items:center;width:100%}.mrd-boolean-field__toggle-label.sc-mrd-boolean-field{display:flex;align-items:center;gap:var(--mrd-space-3);cursor:pointer;user-select:none}.mrd-boolean-field__checkbox.sc-mrd-boolean-field{position:absolute;opacity:0;width:0;height:0;pointer-events:none}.mrd-boolean-field__checkbox.sc-mrd-boolean-field:checked+.mrd-boolean-field__toggle.sc-mrd-boolean-field{background-color:var(--mrd-color-primary)}.mrd-boolean-field__checkbox.sc-mrd-boolean-field:checked+.mrd-boolean-field__toggle.sc-mrd-boolean-field::after{transform:translateX(20px)}.mrd-boolean-field__checkbox.sc-mrd-boolean-field:focus+.mrd-boolean-field__toggle.sc-mrd-boolean-field{box-shadow:var(--mrd-shadow-focus)}.mrd-boolean-field__checkbox.sc-mrd-boolean-field:disabled+.mrd-boolean-field__toggle.sc-mrd-boolean-field{opacity:0.5;cursor:not-allowed}.mrd-boolean-field__toggle.sc-mrd-boolean-field{position:relative;display:inline-block;width:44px;height:24px;background-color:var(--mrd-color-neutral-300);border-radius:var(--mrd-border-radius-full);transition:background-color var(--mrd-transition);flex-shrink:0}.mrd-boolean-field__toggle.sc-mrd-boolean-field::after{content:'';position:absolute;top:2px;left:2px;width:20px;height:20px;background-color:var(--mrd-color-white);border-radius:50%;transition:transform var(--mrd-transition);box-shadow:var(--mrd-shadow-sm)}.mrd-boolean-field__text.sc-mrd-boolean-field{font-family:var(--mrd-font-family);font-size:var(--mrd-font-size-base);color:var(--mrd-color-neutral-800)}.mrd-boolean-field__text--required.sc-mrd-boolean-field::after{content:' *';color:var(--mrd-color-danger)}`;
@@ -334,6 +334,7 @@ const MrdField = class {
334
334
  this.mrdChange = createEvent(this, "mrdChange");
335
335
  this.mrdBlur = createEvent(this, "mrdBlur");
336
336
  this.mrdSearch = createEvent(this, "mrdSearch");
337
+ this.mrdFetchAll = createEvent(this, "mrdFetchAll");
337
338
  this.locale = navigator.language;
338
339
  this.handleChange = (e) => {
339
340
  e.stopPropagation();
@@ -347,13 +348,17 @@ const MrdField = class {
347
348
  e.stopPropagation();
348
349
  this.mrdSearch.emit(e.detail);
349
350
  };
351
+ this.handleFetchAll = (e) => {
352
+ e.stopPropagation();
353
+ this.mrdFetchAll.emit(e.detail);
354
+ };
350
355
  }
351
356
  render() {
352
- var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _0, _1, _2, _3, _4, _5;
357
+ var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _0, _1, _2, _3, _4, _5, _6;
353
358
  const { item, locale, value } = this;
354
359
  if (item.type === ClientLayoutItemType.RELATION && item.relation) {
355
360
  const rel = item.relation;
356
- return (h(Host, null, h("mrd-relation-field", { name: rel.name, label: rel.label, required: rel.required, disabled: (_a = rel.disabled) !== null && _a !== void 0 ? _a : false, locale: locale, relatedClass: rel.relatedClass, mostSignificantClass: (_b = rel.mostSignificantClass) !== null && _b !== void 0 ? _b : '', displayType: (_c = rel.displayType) !== null && _c !== void 0 ? _c : ClientLayoutItemRelationDisplayType.SEARCH, multiple: (_d = rel.multiple) !== null && _d !== void 0 ? _d : false, dropdownValues: (_e = rel.dropdownValues) !== null && _e !== void 0 ? _e : [], value: value, onMrdChange: this.handleChange, onMrdBlur: this.handleBlur, onMrdSearch: this.handleSearch })));
361
+ return (h(Host, null, h("mrd-relation-field", { name: rel.name, label: rel.label, required: rel.required, disabled: (_a = rel.disabled) !== null && _a !== void 0 ? _a : false, locale: locale, relatedClass: rel.relatedClass, mostSignificantClass: (_b = rel.mostSignificantClass) !== null && _b !== void 0 ? _b : '', displayType: (_c = rel.displayType) !== null && _c !== void 0 ? _c : ClientLayoutItemRelationDisplayType.SEARCH, editBehavior: (_d = rel.editBehavior) !== null && _d !== void 0 ? _d : null, commonRelation: rel.commonRelation, multiple: (_e = rel.multiple) !== null && _e !== void 0 ? _e : false, dropdownValues: (_f = rel.dropdownValues) !== null && _f !== void 0 ? _f : [], value: value, onMrdChange: this.handleChange, onMrdBlur: this.handleBlur, onMrdSearch: this.handleSearch, onMrdFetchAll: this.handleFetchAll })));
357
362
  }
358
363
  if (item.type !== ClientLayoutItemType.FIELD || !item.field) {
359
364
  return h(Host, null);
@@ -363,40 +368,40 @@ const MrdField = class {
363
368
  name: field.name,
364
369
  label: field.label,
365
370
  required: field.required,
366
- disabled: (_f = field.disabled) !== null && _f !== void 0 ? _f : false,
371
+ disabled: (_g = field.disabled) !== null && _g !== void 0 ? _g : false,
367
372
  locale,
368
373
  onMrdChange: this.handleChange,
369
374
  onMrdBlur: this.handleBlur,
370
375
  };
371
376
  switch (field.dataType) {
372
377
  case ClientLayoutItemFieldDataType.TEXT:
373
- return (h(Host, null, h("mrd-text-field", Object.assign({}, commonProps, { value: (_g = value) !== null && _g !== void 0 ? _g : '', placeholder: (_h = field.placeholder) !== null && _h !== void 0 ? _h : '' }))));
378
+ return (h(Host, null, h("mrd-text-field", Object.assign({}, commonProps, { value: (_h = value) !== null && _h !== void 0 ? _h : '', placeholder: (_j = field.placeholder) !== null && _j !== void 0 ? _j : '' }))));
374
379
  case ClientLayoutItemFieldDataType.TEXTBLOCK:
375
- return (h(Host, null, h("mrd-textarea-field", Object.assign({}, commonProps, { value: (_j = value) !== null && _j !== void 0 ? _j : '', placeholder: (_k = field.placeholder) !== null && _k !== void 0 ? _k : '' }))));
380
+ return (h(Host, null, h("mrd-textarea-field", Object.assign({}, commonProps, { value: (_k = value) !== null && _k !== void 0 ? _k : '', placeholder: (_l = field.placeholder) !== null && _l !== void 0 ? _l : '' }))));
376
381
  case ClientLayoutItemFieldDataType.INTEGER:
377
382
  case ClientLayoutItemFieldDataType.DECIMAL:
378
383
  case ClientLayoutItemFieldDataType.PERCENTAGE:
379
- return (h(Host, null, h("mrd-number-field", Object.assign({}, commonProps, { value: (_l = value) !== null && _l !== void 0 ? _l : null, dataType: field.dataType, decimalPrecision: (_m = field.decimalPrecision) !== null && _m !== void 0 ? _m : 2, placeholder: (_o = field.placeholder) !== null && _o !== void 0 ? _o : '' }))));
384
+ return (h(Host, null, h("mrd-number-field", Object.assign({}, commonProps, { value: (_m = value) !== null && _m !== void 0 ? _m : null, dataType: field.dataType, decimalPrecision: (_o = field.decimalPrecision) !== null && _o !== void 0 ? _o : 2, placeholder: (_p = field.placeholder) !== null && _p !== void 0 ? _p : '' }))));
380
385
  case ClientLayoutItemFieldDataType.CURRENCY:
381
- return (h(Host, null, h("mrd-currency-field", Object.assign({}, commonProps, { value: (_p = value) !== null && _p !== void 0 ? _p : { amount: null, currency: (_q = field.currencyCode) !== null && _q !== void 0 ? _q : 'EUR' } }))));
386
+ return (h(Host, null, h("mrd-currency-field", Object.assign({}, commonProps, { value: (_q = value) !== null && _q !== void 0 ? _q : { amount: null, currency: (_r = field.currencyCode) !== null && _r !== void 0 ? _r : 'EUR' } }))));
382
387
  case ClientLayoutItemFieldDataType.BOOLEAN:
383
- return (h(Host, null, h("mrd-boolean-field", Object.assign({}, commonProps, { value: (_r = value) !== null && _r !== void 0 ? _r : false }))));
388
+ return (h(Host, null, h("mrd-boolean-field", Object.assign({}, commonProps, { value: (_s = value) !== null && _s !== void 0 ? _s : false }))));
384
389
  case ClientLayoutItemFieldDataType.DATE:
385
- return (h(Host, null, h("mrd-date-field", Object.assign({}, commonProps, { value: (_s = value) !== null && _s !== void 0 ? _s : '' }))));
390
+ return (h(Host, null, h("mrd-date-field", Object.assign({}, commonProps, { value: (_t = value) !== null && _t !== void 0 ? _t : '' }))));
386
391
  case ClientLayoutItemFieldDataType.DATETIME:
387
- return (h(Host, null, h("mrd-datetime-field", Object.assign({}, commonProps, { value: (_t = value) !== null && _t !== void 0 ? _t : '' }))));
392
+ return (h(Host, null, h("mrd-datetime-field", Object.assign({}, commonProps, { value: (_u = value) !== null && _u !== void 0 ? _u : '' }))));
388
393
  case ClientLayoutItemFieldDataType.TIME:
389
- return (h(Host, null, h("mrd-time-field", Object.assign({}, commonProps, { value: (_u = value) !== null && _u !== void 0 ? _u : '' }))));
394
+ return (h(Host, null, h("mrd-time-field", Object.assign({}, commonProps, { value: (_v = value) !== null && _v !== void 0 ? _v : '' }))));
390
395
  case ClientLayoutItemFieldDataType.EMAIL:
391
- return (h(Host, null, h("mrd-email-field", Object.assign({}, commonProps, { value: (_v = value) !== null && _v !== void 0 ? _v : '', placeholder: (_w = field.placeholder) !== null && _w !== void 0 ? _w : '' }))));
396
+ return (h(Host, null, h("mrd-email-field", Object.assign({}, commonProps, { value: (_w = value) !== null && _w !== void 0 ? _w : '', placeholder: (_x = field.placeholder) !== null && _x !== void 0 ? _x : '' }))));
392
397
  case ClientLayoutItemFieldDataType.HYPERLINK:
393
- return (h(Host, null, h("mrd-hyperlink-field", Object.assign({}, commonProps, { value: (_x = value) !== null && _x !== void 0 ? _x : '', placeholder: (_y = field.placeholder) !== null && _y !== void 0 ? _y : '' }))));
398
+ return (h(Host, null, h("mrd-hyperlink-field", Object.assign({}, commonProps, { value: (_y = value) !== null && _y !== void 0 ? _y : '', placeholder: (_z = field.placeholder) !== null && _z !== void 0 ? _z : '' }))));
394
399
  case ClientLayoutItemFieldDataType.LIST:
395
- return (h(Host, null, h("mrd-list-field", Object.assign({}, commonProps, { value: (_z = value) !== null && _z !== void 0 ? _z : '', multiple: (_0 = field.multiple) !== null && _0 !== void 0 ? _0 : false, listItems: (_1 = field.listItems) !== null && _1 !== void 0 ? _1 : [] }))));
400
+ return (h(Host, null, h("mrd-list-field", Object.assign({}, commonProps, { value: (_0 = value) !== null && _0 !== void 0 ? _0 : '', multiple: (_1 = field.multiple) !== null && _1 !== void 0 ? _1 : false, listItems: (_2 = field.listItems) !== null && _2 !== void 0 ? _2 : [] }))));
396
401
  case ClientLayoutItemFieldDataType.FILE:
397
- return (h(Host, null, h("mrd-file-field", Object.assign({}, commonProps, { accept: (_2 = field.accept) !== null && _2 !== void 0 ? _2 : '', maxSize: (_3 = field.maxSize) !== null && _3 !== void 0 ? _3 : 0 }))));
402
+ return (h(Host, null, h("mrd-file-field", Object.assign({}, commonProps, { accept: (_3 = field.accept) !== null && _3 !== void 0 ? _3 : '', maxSize: (_4 = field.maxSize) !== null && _4 !== void 0 ? _4 : 0 }))));
398
403
  case ClientLayoutItemFieldDataType.IMAGE:
399
- return (h(Host, null, h("mrd-image-field", Object.assign({}, commonProps, { accept: (_4 = field.accept) !== null && _4 !== void 0 ? _4 : 'image/*', maxSize: (_5 = field.maxSize) !== null && _5 !== void 0 ? _5 : 0 }))));
404
+ return (h(Host, null, h("mrd-image-field", Object.assign({}, commonProps, { accept: (_5 = field.accept) !== null && _5 !== void 0 ? _5 : 'image/*', maxSize: (_6 = field.maxSize) !== null && _6 !== void 0 ? _6 : 0 }))));
400
405
  default:
401
406
  return h(Host, null);
402
407
  }
@@ -475,29 +480,78 @@ const MrdFileField = class {
475
480
  };
476
481
  MrdFileField.style = mrdFileFieldScss();
477
482
 
478
- const mrdFormScss = () => `.sc-mrd-form-h{display:block}.mrd-form.sc-mrd-form{font-family:var(--mrd-font-family);width:100%}.mrd-form__title.sc-mrd-form{font-size:var(--mrd-font-size-2xl);font-weight:var(--mrd-font-weight-bold);color:var(--mrd-color-neutral-900);margin:0 0 var(--mrd-space-6) 0}.mrd-form__body.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-5)}.mrd-form__field.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-1)}.mrd-form__field-error.sc-mrd-form{font-family:var(--mrd-font-family);font-size:var(--mrd-error-font-size);color:var(--mrd-error-color)}.mrd-form__section.sc-mrd-form{border:var(--mrd-border-width) solid var(--mrd-border-color);border-radius:var(--mrd-border-radius-md);padding:var(--mrd-space-4) var(--mrd-space-5);margin:0}.mrd-form__section-legend.sc-mrd-form{font-family:var(--mrd-font-family);font-size:var(--mrd-font-size-base);font-weight:var(--mrd-font-weight-semibold);color:var(--mrd-color-neutral-700);padding:0 var(--mrd-space-2)}.mrd-form__section-body.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-4);margin-top:var(--mrd-space-2)}.mrd-form__group.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-2)}.mrd-form__group-label.sc-mrd-form{font-family:var(--mrd-font-family);font-size:var(--mrd-font-size-sm);font-weight:var(--mrd-font-weight-semibold);color:var(--mrd-color-neutral-500);text-transform:uppercase;letter-spacing:0.05em}.mrd-form__group-body.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-4);padding-left:var(--mrd-space-4);border-left:3px solid var(--mrd-color-neutral-200)}.mrd-form__footer.sc-mrd-form{margin-top:var(--mrd-space-8);padding-top:var(--mrd-space-5);border-top:var(--mrd-border-width) solid var(--mrd-border-color);display:flex;justify-content:flex-end}.mrd-form__submit.sc-mrd-form{display:inline-flex;align-items:center;justify-content:center;height:var(--mrd-input-height);padding:0 var(--mrd-space-6);background-color:var(--mrd-color-primary);color:var(--mrd-color-white);font-family:var(--mrd-font-family);font-size:var(--mrd-font-size-base);font-weight:var(--mrd-font-weight-medium);border:none;border-radius:var(--mrd-border-radius);cursor:pointer;transition:background-color var(--mrd-transition)}.mrd-form__submit.sc-mrd-form:hover{background-color:var(--mrd-color-primary-hover)}.mrd-form__submit.sc-mrd-form:focus{outline:none;box-shadow:var(--mrd-shadow-focus)}.mrd-form__submit.sc-mrd-form:active{background-color:var(--mrd-color-primary-dark)}`;
483
+ const mrdFormScss = () => `.sc-mrd-form-h{display:block}.mrd-form.sc-mrd-form{font-family:var(--mrd-font-family);width:100%}.mrd-form__title.sc-mrd-form{font-size:var(--mrd-font-size-2xl);font-weight:var(--mrd-font-weight-bold);color:var(--mrd-color-neutral-900);margin:0 0 var(--mrd-space-6) 0}.mrd-form__body.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-5)}.mrd-form__field.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-1)}.mrd-form__field-error.sc-mrd-form{font-family:var(--mrd-font-family);font-size:var(--mrd-error-font-size);color:var(--mrd-error-color)}.mrd-form__section.sc-mrd-form{border:var(--mrd-border-width) solid var(--mrd-border-color);border-radius:var(--mrd-border-radius-md);padding:var(--mrd-space-4) var(--mrd-space-5);margin:0}.mrd-form__section-legend.sc-mrd-form{font-family:var(--mrd-font-family);font-size:var(--mrd-font-size-base);font-weight:var(--mrd-font-weight-semibold);color:var(--mrd-color-neutral-700);padding:0 var(--mrd-space-2)}.mrd-form__section-body.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-4);margin-top:var(--mrd-space-2)}.mrd-form__group.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-2)}.mrd-form__group-label.sc-mrd-form{font-family:var(--mrd-font-family);font-size:var(--mrd-font-size-sm);font-weight:var(--mrd-font-weight-semibold);color:var(--mrd-color-neutral-500);text-transform:uppercase;letter-spacing:0.05em}.mrd-form__group-body.sc-mrd-form{display:flex;flex-direction:column;gap:var(--mrd-space-4);padding-left:var(--mrd-space-4);border-left:3px solid var(--mrd-color-neutral-200)}.mrd-form__footer.sc-mrd-form{margin-top:var(--mrd-space-8);padding-top:var(--mrd-space-5);border-top:var(--mrd-border-width) solid var(--mrd-border-color);display:flex;justify-content:flex-end;gap:var(--mrd-space-3)}.mrd-form__submit.sc-mrd-form{display:inline-flex;align-items:center;justify-content:center;height:var(--mrd-input-height);padding:0 var(--mrd-space-6);background-color:var(--mrd-color-primary);color:var(--mrd-color-white);font-family:var(--mrd-font-family);font-size:var(--mrd-font-size-base);font-weight:var(--mrd-font-weight-medium);border:none;border-radius:var(--mrd-border-radius);cursor:pointer;transition:background-color var(--mrd-transition)}.mrd-form__submit.sc-mrd-form:hover{background-color:var(--mrd-color-primary-hover)}.mrd-form__submit.sc-mrd-form:focus{outline:none;box-shadow:var(--mrd-shadow-focus)}.mrd-form__submit.sc-mrd-form:active{background-color:var(--mrd-color-primary-dark)}.mrd-form__cancel.sc-mrd-form{display:inline-flex;align-items:center;justify-content:center;height:var(--mrd-input-height);padding:0 var(--mrd-space-6);background-color:transparent;color:var(--mrd-color-neutral-600);font-family:var(--mrd-font-family);font-size:var(--mrd-font-size-base);font-weight:var(--mrd-font-weight-medium);border:var(--mrd-border-width) solid var(--mrd-border-color);border-radius:var(--mrd-border-radius);cursor:pointer;transition:background-color var(--mrd-transition), color var(--mrd-transition)}.mrd-form__cancel.sc-mrd-form:hover{background-color:var(--mrd-color-neutral-100);color:var(--mrd-color-neutral-800)}.mrd-form__cancel.sc-mrd-form:focus{outline:none;box-shadow:var(--mrd-shadow-focus)}.mrd-form__cancel.sc-mrd-form:active{background-color:var(--mrd-color-neutral-200)}`;
479
484
 
480
485
  const MrdForm = class {
481
486
  constructor(hostRef) {
482
487
  registerInstance(this, hostRef);
483
488
  this.mrdSubmit = createEvent(this, "mrdSubmit");
489
+ this.mrdCancel = createEvent(this, "mrdCancel");
484
490
  this.mrdSearch = createEvent(this, "mrdSearch");
491
+ this.mrdFetchAll = createEvent(this, "mrdFetchAll");
485
492
  this.locale = navigator.language;
486
493
  this.values = {};
494
+ /**
495
+ * Absolute href of the parent/reference object (e.g. the clientAgreement href
496
+ * when creating an invoice from within a client agreement).
497
+ * Combined with `referenceClass`, mrd-form will automatically pre-fill the
498
+ * matching relation field so dependent DROPDOWN fields can be fetched on load
499
+ * — without the host app needing to know anything about the form layout.
500
+ */
501
+ /**
502
+ * Absolute href of the parent/reference object (e.g. the clientAgreement href
503
+ * when creating an invoice from within a client agreement).
504
+ * Combined with `referenceClass`, mrd-form will automatically pre-fill the
505
+ * matching relation field so dependent DROPDOWN fields can be fetched on load.
506
+ */
507
+ this.referenceHref = '';
508
+ /**
509
+ * The `mostSignificantClass` of the parent/reference object
510
+ * (e.g. `'clientAgreements'`). Used to locate the matching RELATION field.
511
+ */
512
+ this.referenceClass = '';
513
+ /** When true, a cancel button is shown next to the submit button. */
514
+ this.showCancel = false;
487
515
  this.formValues = {};
488
516
  this.errors = {};
489
517
  this.submitted = false;
490
518
  this.handleFieldChange = (e) => {
491
519
  const { name, value } = e.detail;
520
+ const prevHref = this.getHref(this.formValues[name]);
492
521
  this.formValues = Object.assign(Object.assign({}, this.formValues), { [name]: value });
493
522
  if (this.errors[name]) {
494
523
  this.errors = Object.assign(Object.assign({}, this.errors), { [name]: '' });
495
524
  }
525
+ // When a field changes, check if it is the commonRelation dependency for any
526
+ // DROPDOWN relation. If so, reset the dependent field and re-fetch its options.
527
+ // Skip when the effective href did not change (e.g. mrdBlur fires after mrdChange
528
+ // with the same value, which would otherwise trigger a duplicate fetch).
529
+ const newHref = this.getHref(value);
530
+ if (newHref === prevHref)
531
+ return;
532
+ for (const rel of this.collectDependentDropdowns()) {
533
+ if (rel.commonRelation !== name)
534
+ continue;
535
+ // Clear the dependent field's current selection (options have changed)
536
+ this.formValues = Object.assign(Object.assign({}, this.formValues), { [rel.name]: null });
537
+ this.mrdFetchAll.emit({
538
+ name: rel.name,
539
+ relatedClass: rel.relatedClass,
540
+ mostSignificantClass: rel.mostSignificantClass,
541
+ commonRelation: rel.commonRelation,
542
+ filter: rel.commonRelation,
543
+ filterValue: newHref, // empty string when dependency was cleared → host should clear the list
544
+ });
545
+ }
496
546
  };
497
547
  this.handleSearch = (e) => {
498
548
  e.stopPropagation();
499
549
  this.mrdSearch.emit(e.detail);
500
550
  };
551
+ this.handleFetchAll = (e) => {
552
+ e.stopPropagation();
553
+ this.mrdFetchAll.emit(e.detail);
554
+ };
501
555
  this.handleSubmit = (e) => {
502
556
  e.preventDefault();
503
557
  this.submitted = true;
@@ -510,12 +564,71 @@ const MrdForm = class {
510
564
  var _a;
511
565
  this.formValues = Object.assign({}, ((_a = this.values) !== null && _a !== void 0 ? _a : {}));
512
566
  }
567
+ componentDidLoad() {
568
+ // Apply reference pre-fill and emit mrdFetchAll for dependent DROPDOWN fields.
569
+ // Deferred so Angular/host prop bindings are settled before we read them.
570
+ setTimeout(() => {
571
+ this.applyReferenceValue();
572
+ this.emitDependentFetchAll();
573
+ }, 0);
574
+ }
513
575
  /** Sync formValues when the values prop is set from outside after mount
514
576
  * (e.g. when pre-filling an existing record in edit mode). */
515
577
  valuesChanged(newValues) {
516
578
  this.formValues = Object.assign({}, (newValues !== null && newValues !== void 0 ? newValues : {}));
579
+ this.applyReferenceValue();
517
580
  this.errors = {};
518
581
  this.submitted = false;
582
+ // Re-check DROPDOWN dependencies now that formValues are updated
583
+ setTimeout(() => this.emitDependentFetchAll(), 0);
584
+ }
585
+ /**
586
+ * When referenceHref + referenceClass are set, find the matching layout field
587
+ * and inject its value into formValues. This allows dependent DROPDOWN fields
588
+ * (those with commonRelation pointing to that field) to be fetched on load
589
+ * without the host app doing any form-domain logic.
590
+ *
591
+ * Two lookup strategies:
592
+ * 1. Find a RELATION whose mostSignificantClass matches referenceClass.
593
+ * 2. Fallback: find a DROPDOWN whose commonRelation field is absent from the
594
+ * layout (API omitted it because it is implied by the reference context).
595
+ */
596
+ applyReferenceValue() {
597
+ if (!this.referenceHref || !this.referenceClass)
598
+ return;
599
+ const fieldName = this.resolveReferenceFieldName();
600
+ if (!fieldName)
601
+ return;
602
+ // Only set when not already present (don't overwrite an explicit value)
603
+ if (!this.formValues[fieldName]) {
604
+ this.formValues = Object.assign(Object.assign({}, this.formValues), { [fieldName]: this.referenceHref });
605
+ }
606
+ }
607
+ resolveReferenceFieldName() {
608
+ var _a, _b;
609
+ const allItems = this.collectFields((_b = (_a = this.layout) === null || _a === void 0 ? void 0 : _a.items) !== null && _b !== void 0 ? _b : []);
610
+ // Strategy 1: direct match on mostSignificantClass
611
+ const direct = allItems.find(item => {
612
+ var _a;
613
+ return item.type === ClientLayoutItemType.RELATION &&
614
+ ((_a = item.relation) === null || _a === void 0 ? void 0 : _a.mostSignificantClass) === this.referenceClass;
615
+ });
616
+ if (direct === null || direct === void 0 ? void 0 : direct.relation)
617
+ return direct.relation.name;
618
+ // Strategy 2: a DROPDOWN whose commonRelation field was omitted from the layout
619
+ const layoutRelationNames = new Set(allItems
620
+ .filter(item => item.type === ClientLayoutItemType.RELATION)
621
+ .map(item => item.relation.name));
622
+ for (const item of allItems) {
623
+ const rel = item.relation;
624
+ if (item.type === ClientLayoutItemType.RELATION &&
625
+ (rel === null || rel === void 0 ? void 0 : rel.editBehavior) === ClientLayoutItemRelationEditBehavior.DROPDOWN &&
626
+ rel.commonRelation &&
627
+ !layoutRelationNames.has(rel.commonRelation)) {
628
+ return rel.commonRelation;
629
+ }
630
+ }
631
+ return null;
519
632
  }
520
633
  async setFieldValue(name, value) {
521
634
  this.formValues = Object.assign(Object.assign({}, this.formValues), { [name]: value });
@@ -523,6 +636,45 @@ const MrdForm = class {
523
636
  this.errors = Object.assign(Object.assign({}, this.errors), { [name]: '' });
524
637
  }
525
638
  }
639
+ /** Collect all RELATION items that use editBehavior=DROPDOWN with a commonRelation. */
640
+ collectDependentDropdowns() {
641
+ var _a, _b;
642
+ return this.collectFields((_b = (_a = this.layout) === null || _a === void 0 ? void 0 : _a.items) !== null && _b !== void 0 ? _b : [])
643
+ .filter(item => {
644
+ var _a;
645
+ return item.type === ClientLayoutItemType.RELATION &&
646
+ ((_a = item.relation) === null || _a === void 0 ? void 0 : _a.editBehavior) === ClientLayoutItemRelationEditBehavior.DROPDOWN &&
647
+ !!item.relation.commonRelation;
648
+ })
649
+ .map(item => item.relation);
650
+ }
651
+ /** Emit mrdFetchAll for every dependent DROPDOWN whose filter value is currently set. */
652
+ emitDependentFetchAll() {
653
+ for (const rel of this.collectDependentDropdowns()) {
654
+ const filterValue = this.getHref(this.formValues[rel.commonRelation]);
655
+ if (filterValue) {
656
+ this.mrdFetchAll.emit({
657
+ name: rel.name,
658
+ relatedClass: rel.relatedClass,
659
+ mostSignificantClass: rel.mostSignificantClass,
660
+ commonRelation: rel.commonRelation,
661
+ filter: rel.commonRelation,
662
+ filterValue,
663
+ });
664
+ }
665
+ }
666
+ }
667
+ /** Extract a plain href string from a form value, which can be a string or
668
+ * a RelationSearchResult-like object with an `id` field. */
669
+ getHref(value) {
670
+ if (!value)
671
+ return '';
672
+ if (typeof value === 'string')
673
+ return value;
674
+ if (typeof value === 'object' && 'id' in value)
675
+ return value.id;
676
+ return '';
677
+ }
526
678
  collectFields(items) {
527
679
  const fields = [];
528
680
  for (const item of items) {
@@ -592,7 +744,7 @@ const MrdForm = class {
592
744
  }
593
745
  const fieldName = (_d = (_b = (_a = item.field) === null || _a === void 0 ? void 0 : _a.name) !== null && _b !== void 0 ? _b : (_c = item.relation) === null || _c === void 0 ? void 0 : _c.name) !== null && _d !== void 0 ? _d : '';
594
746
  const fieldValue = this.formValues[fieldName];
595
- return (h("div", { class: "mrd-form__field" }, h("mrd-field", { item: item, locale: this.locale, value: fieldValue, onMrdChange: this.handleFieldChange, onMrdBlur: this.handleFieldChange, onMrdSearch: this.handleSearch }), this.errors[fieldName] && (h("span", { class: "mrd-form__field-error" }, this.errors[fieldName]))));
747
+ return (h("div", { class: "mrd-form__field" }, h("mrd-field", { item: item, locale: this.locale, value: fieldValue, onMrdChange: this.handleFieldChange, onMrdBlur: this.handleFieldChange, onMrdSearch: this.handleSearch, onMrdFetchAll: this.handleFetchAll }), this.errors[fieldName] && (h("span", { class: "mrd-form__field-error" }, this.errors[fieldName]))));
596
748
  });
597
749
  }
598
750
  render() {
@@ -600,7 +752,7 @@ const MrdForm = class {
600
752
  return h(Host, null);
601
753
  }
602
754
  const dir = this.locale.startsWith('ar') ? 'rtl' : 'ltr';
603
- return (h(Host, null, h("form", { class: "mrd-form", dir: dir, onSubmit: this.handleSubmit, noValidate: true }, this.layout.title && h("h2", { class: "mrd-form__title" }, this.layout.title), h("div", { class: "mrd-form__body" }, this.renderItems(this.layout.items)), h("div", { class: "mrd-form__footer" }, h("button", { type: "submit", class: "mrd-form__submit" }, t('submit', this.locale))))));
755
+ return (h(Host, null, h("form", { class: "mrd-form", dir: dir, onSubmit: this.handleSubmit, noValidate: true }, this.layout.title && h("h2", { class: "mrd-form__title" }, this.layout.title), h("div", { class: "mrd-form__body" }, this.renderItems(this.layout.items)), h("div", { class: "mrd-form__footer" }, h("button", { type: "submit", class: "mrd-form__submit" }, t('submit', this.locale)), this.showCancel && (h("button", { type: "button", class: "mrd-form__cancel", onClick: () => this.mrdCancel.emit() }, t('cancel', this.locale)))))));
604
756
  }
605
757
  static get watchers() { return {
606
758
  "values": [{
@@ -916,6 +1068,7 @@ const MrdRelationField = class {
916
1068
  this.mrdChange = createEvent(this, "mrdChange");
917
1069
  this.mrdBlur = createEvent(this, "mrdBlur");
918
1070
  this.mrdSearch = createEvent(this, "mrdSearch");
1071
+ this.mrdFetchAll = createEvent(this, "mrdFetchAll");
919
1072
  this.name = '';
920
1073
  this.label = '';
921
1074
  this.required = false;
@@ -931,6 +1084,7 @@ const MrdRelationField = class {
931
1084
  this.value = null;
932
1085
  this.searchQuery = '';
933
1086
  this.searchResults = [];
1087
+ this.allRecords = [];
934
1088
  this.isLoading = false;
935
1089
  this.selectedItems = [];
936
1090
  this.showResults = false;
@@ -1039,6 +1193,9 @@ const MrdRelationField = class {
1039
1193
  this.mrdBlur.emit({ name: this.name, value: val });
1040
1194
  };
1041
1195
  }
1196
+ async setAllRecords(records) {
1197
+ this.allRecords = records;
1198
+ }
1042
1199
  async setSearchResults(results) {
1043
1200
  this.searchResults = results;
1044
1201
  this.isLoading = false;
@@ -1052,24 +1209,41 @@ const MrdRelationField = class {
1052
1209
  var _a;
1053
1210
  // Pre-fill selectedItems when value is passed as { id, label } objects
1054
1211
  // (e.g. when editing an existing record fetched from the API).
1055
- if (!this.value)
1056
- return;
1057
- if (Array.isArray(this.value)) {
1058
- if (this.value.length > 0 && typeof this.value[0] === 'object') {
1059
- this.selectedItems = this.value;
1060
- this.searchQuery = '';
1212
+ if (this.value) {
1213
+ if (Array.isArray(this.value)) {
1214
+ if (this.value.length > 0 && typeof this.value[0] === 'object') {
1215
+ this.selectedItems = this.value;
1216
+ this.searchQuery = '';
1217
+ }
1218
+ }
1219
+ else if (typeof this.value === 'object') {
1220
+ this.selectedItems = [this.value];
1221
+ this.searchQuery = (_a = this.value.label) !== null && _a !== void 0 ? _a : '';
1061
1222
  }
1062
1223
  }
1063
- else if (typeof this.value === 'object') {
1064
- this.selectedItems = [this.value];
1065
- this.searchQuery = (_a = this.value.label) !== null && _a !== void 0 ? _a : '';
1224
+ }
1225
+ componentDidLoad() {
1226
+ // Only emit when there is no commonRelation dependency the form orchestrates those.
1227
+ if (this.editBehavior === ClientLayoutItemRelationEditBehavior.DROPDOWN && !this.commonRelation) {
1228
+ // Defer to next tick so parent event listeners are registered after DOM patching
1229
+ setTimeout(() => {
1230
+ this.mrdFetchAll.emit({
1231
+ name: this.name,
1232
+ relatedClass: this.relatedClass,
1233
+ mostSignificantClass: this.mostSignificantClass || undefined,
1234
+ });
1235
+ }, 0);
1066
1236
  }
1067
1237
  }
1068
1238
  render() {
1069
- var _a, _b;
1239
+ var _a, _b, _c, _d;
1070
1240
  const hasError = !!this.error;
1071
- if (this.displayType === ClientLayoutItemRelationDisplayType.DROPDOWN) {
1241
+ if (this.editBehavior === ClientLayoutItemRelationEditBehavior.DROPDOWN) {
1072
1242
  const currentValue = Array.isArray(this.value) ? ((_a = this.value[0]) !== null && _a !== void 0 ? _a : '') : ((_b = this.value) !== null && _b !== void 0 ? _b : '');
1243
+ return (h(Host, null, h("div", { class: "mrd-relation-field" }, this.label && (h("label", { class: `mrd-relation-field__label${this.required ? ' mrd-relation-field__label--required' : ''}` }, this.label)), h("select", { class: `mrd-relation-field__select${hasError ? ' mrd-relation-field__select--error' : ''}`, name: this.name, required: this.required, disabled: this.disabled, onChange: this.handleDropdownChange }, h("option", { value: "" }, t('select_placeholder', this.locale)), this.allRecords.map(record => (h("option", { key: record.id, value: record.id, selected: record.id === currentValue }, record.label)))), hasError && h("span", { class: "mrd-relation-field__error" }, this.error))));
1244
+ }
1245
+ if (this.displayType === ClientLayoutItemRelationDisplayType.DROPDOWN) {
1246
+ const currentValue = Array.isArray(this.value) ? ((_c = this.value[0]) !== null && _c !== void 0 ? _c : '') : ((_d = this.value) !== null && _d !== void 0 ? _d : '');
1073
1247
  return (h(Host, null, h("div", { class: "mrd-relation-field" }, this.label && (h("label", { class: `mrd-relation-field__label${this.required ? ' mrd-relation-field__label--required' : ''}` }, this.label)), h("select", { class: `mrd-relation-field__select${hasError ? ' mrd-relation-field__select--error' : ''}`, name: this.name, required: this.required, disabled: this.disabled, onChange: this.handleDropdownChange }, h("option", { value: "" }, t('select_placeholder', this.locale)), this.dropdownValues.map(dv => (h("option", { key: dv.key, value: dv.key, selected: dv.key === currentValue }, dv.label)))), hasError && h("span", { class: "mrd-relation-field__error" }, this.error))));
1074
1248
  }
1075
1249
  // SEARCH mode
@@ -1 +1 @@
1
- import{p as e,b as l}from"./p-_tsCCkAi.js";export{s as setNonce}from"./p-_tsCCkAi.js";import{g as a}from"./p-DQuL1Twl.js";(()=>{const l=import.meta.url,a={};return""!==l&&(a.resourcesUrl=new URL(".",l).href),e(a)})().then((async e=>(await a(),l([["p-baf08615",[[2,"mrd-table",{columns:[16],rows:[16],locale:[1],totalElements:[2,"total-elements"],pageSize:[2,"page-size"],rowHeight:[2,"row-height"],tableHeight:[2,"table-height"],defaultSort:[1,"default-sort"],loadedPages:[32],requestedPages:[32],renderStart:[32],renderEnd:[32],colWidths:[32],sortField:[32],sortDir:[32],init:[64],setPage:[64]}]]],["p-45c40269",[[2,"mrd-form",{layout:[16],locale:[1],values:[16],formValues:[32],errors:[32],submitted:[32],setFieldValue:[64]},null,{values:[{valuesChanged:0}]}],[2,"mrd-field",{item:[16],locale:[1],value:[16]}],[2,"mrd-boolean-field",{name:[1],label:[1],value:[4],required:[4],disabled:[4],locale:[1],checked:[32]}],[2,"mrd-currency-field",{name:[1],label:[1],value:[16],required:[4],disabled:[4],locale:[1],amountDisplay:[32],currency:[32],error:[32]}],[2,"mrd-date-field",{name:[1],label:[1],value:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-datetime-field",{name:[1],label:[1],value:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-email-field",{name:[1],label:[1],value:[1],placeholder:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-file-field",{name:[1],label:[1],required:[4],disabled:[4],locale:[1],accept:[1],maxSize:[2,"max-size"],fileName:[32],isDragging:[32],error:[32]}],[2,"mrd-hyperlink-field",{name:[1],label:[1],value:[1],placeholder:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-image-field",{name:[1],label:[1],required:[4],disabled:[4],locale:[1],accept:[1],maxSize:[2,"max-size"],previewUrl:[32],fileName:[32],isDragging:[32],error:[32]}],[2,"mrd-list-field",{name:[1],label:[1],value:[1],required:[4],disabled:[4],multiple:[4],locale:[1],listItems:[16],error:[32],selected:[32]}],[2,"mrd-number-field",{name:[1],label:[1],value:[2],placeholder:[1],required:[4],disabled:[4],locale:[1],dataType:[1,"data-type"],decimalPrecision:[2,"decimal-precision"],displayValue:[32],error:[32]}],[2,"mrd-relation-field",{name:[1],label:[1],required:[4],disabled:[4],locale:[1],relatedClass:[1,"related-class"],mostSignificantClass:[1,"most-significant-class"],displayType:[1,"display-type"],multiple:[4],dropdownValues:[16],value:[1],searchQuery:[32],searchResults:[32],isLoading:[32],selectedItems:[32],showResults:[32],error:[32],highlightedIndex:[32],setSearchResults:[64],setLoading:[64]}],[2,"mrd-text-field",{name:[1],label:[1],value:[1],placeholder:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-textarea-field",{name:[1],label:[1],value:[1],placeholder:[1],required:[4],disabled:[4],locale:[1],error:[32],editorReady:[32]}],[2,"mrd-time-field",{name:[1],label:[1],value:[1],required:[4],disabled:[4],locale:[1],error:[32]}]]]],e))));
1
+ import{p as e,b as l}from"./p-_tsCCkAi.js";export{s as setNonce}from"./p-_tsCCkAi.js";import{g as a}from"./p-DQuL1Twl.js";(()=>{const l=import.meta.url,a={};return""!==l&&(a.resourcesUrl=new URL(".",l).href),e(a)})().then((async e=>(await a(),l([["p-baf08615",[[2,"mrd-table",{columns:[16],rows:[16],locale:[1],totalElements:[2,"total-elements"],pageSize:[2,"page-size"],rowHeight:[2,"row-height"],tableHeight:[2,"table-height"],defaultSort:[1,"default-sort"],loadedPages:[32],requestedPages:[32],renderStart:[32],renderEnd:[32],colWidths:[32],sortField:[32],sortDir:[32],init:[64],setPage:[64]}]]],["p-2a8cb2eb",[[2,"mrd-form",{layout:[16],locale:[1],values:[16],referenceHref:[1,"reference-href"],referenceClass:[1,"reference-class"],showCancel:[4,"show-cancel"],formValues:[32],errors:[32],submitted:[32],setFieldValue:[64]},null,{values:[{valuesChanged:0}]}],[2,"mrd-field",{item:[16],locale:[1],value:[16]}],[2,"mrd-boolean-field",{name:[1],label:[1],value:[4],required:[4],disabled:[4],locale:[1],checked:[32]}],[2,"mrd-currency-field",{name:[1],label:[1],value:[16],required:[4],disabled:[4],locale:[1],amountDisplay:[32],currency:[32],error:[32]}],[2,"mrd-date-field",{name:[1],label:[1],value:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-datetime-field",{name:[1],label:[1],value:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-email-field",{name:[1],label:[1],value:[1],placeholder:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-file-field",{name:[1],label:[1],required:[4],disabled:[4],locale:[1],accept:[1],maxSize:[2,"max-size"],fileName:[32],isDragging:[32],error:[32]}],[2,"mrd-hyperlink-field",{name:[1],label:[1],value:[1],placeholder:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-image-field",{name:[1],label:[1],required:[4],disabled:[4],locale:[1],accept:[1],maxSize:[2,"max-size"],previewUrl:[32],fileName:[32],isDragging:[32],error:[32]}],[2,"mrd-list-field",{name:[1],label:[1],value:[1],required:[4],disabled:[4],multiple:[4],locale:[1],listItems:[16],error:[32],selected:[32]}],[2,"mrd-number-field",{name:[1],label:[1],value:[2],placeholder:[1],required:[4],disabled:[4],locale:[1],dataType:[1,"data-type"],decimalPrecision:[2,"decimal-precision"],displayValue:[32],error:[32]}],[2,"mrd-relation-field",{name:[1],label:[1],required:[4],disabled:[4],locale:[1],relatedClass:[1,"related-class"],mostSignificantClass:[1,"most-significant-class"],displayType:[1,"display-type"],editBehavior:[1,"edit-behavior"],commonRelation:[1,"common-relation"],multiple:[4],dropdownValues:[16],value:[1],searchQuery:[32],searchResults:[32],allRecords:[32],isLoading:[32],selectedItems:[32],showResults:[32],error:[32],highlightedIndex:[32],setAllRecords:[64],setSearchResults:[64],setLoading:[64]}],[2,"mrd-text-field",{name:[1],label:[1],value:[1],placeholder:[1],required:[4],disabled:[4],locale:[1],error:[32]}],[2,"mrd-textarea-field",{name:[1],label:[1],value:[1],placeholder:[1],required:[4],disabled:[4],locale:[1],error:[32],editorReady:[32]}],[2,"mrd-time-field",{name:[1],label:[1],value:[1],required:[4],disabled:[4],locale:[1],error:[32]}]]]],e))));