formeo 5.0.0 → 5.0.2

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,7 +1,7 @@
1
1
 
2
2
  /**
3
3
  formeo - https://formeo.io
4
- Version: 4.2.5
4
+ Version: 5.0.1
5
5
  Author: Draggable https://draggable.io
6
6
  */
7
7
 
@@ -432,7 +432,7 @@ if (window !== void 0) {
432
432
  window.SmartTooltip = SmartTooltip;
433
433
  }
434
434
  const name$1 = "formeo";
435
- const version$2 = "4.2.5";
435
+ const version$2 = "5.0.1";
436
436
  const pkg = {
437
437
  name: name$1,
438
438
  version: version$2
@@ -1204,9 +1204,9 @@ var hasRequired_cloneBuffer;
1204
1204
  function require_cloneBuffer() {
1205
1205
  if (hasRequired_cloneBuffer) return _cloneBuffer.exports;
1206
1206
  hasRequired_cloneBuffer = 1;
1207
- (function(module, exports) {
1207
+ (function(module, exports$1) {
1208
1208
  var root = require_root();
1209
- var freeExports = exports && !exports.nodeType && exports;
1209
+ var freeExports = exports$1 && !exports$1.nodeType && exports$1;
1210
1210
  var freeModule = freeExports && true && module && !module.nodeType && module;
1211
1211
  var moduleExports = freeModule && freeModule.exports === freeExports;
1212
1212
  var Buffer = moduleExports ? root.Buffer : void 0, allocUnsafe = Buffer ? Buffer.allocUnsafe : void 0;
@@ -1452,9 +1452,9 @@ var hasRequiredIsBuffer;
1452
1452
  function requireIsBuffer() {
1453
1453
  if (hasRequiredIsBuffer) return isBuffer.exports;
1454
1454
  hasRequiredIsBuffer = 1;
1455
- (function(module, exports) {
1455
+ (function(module, exports$1) {
1456
1456
  var root = require_root(), stubFalse = requireStubFalse();
1457
- var freeExports = exports && !exports.nodeType && exports;
1457
+ var freeExports = exports$1 && !exports$1.nodeType && exports$1;
1458
1458
  var freeModule = freeExports && true && module && !module.nodeType && module;
1459
1459
  var moduleExports = freeModule && freeModule.exports === freeExports;
1460
1460
  var Buffer = moduleExports ? root.Buffer : void 0;
@@ -1525,9 +1525,9 @@ var hasRequired_nodeUtil;
1525
1525
  function require_nodeUtil() {
1526
1526
  if (hasRequired_nodeUtil) return _nodeUtil.exports;
1527
1527
  hasRequired_nodeUtil = 1;
1528
- (function(module, exports) {
1528
+ (function(module, exports$1) {
1529
1529
  var freeGlobal = require_freeGlobal();
1530
- var freeExports = exports && !exports.nodeType && exports;
1530
+ var freeExports = exports$1 && !exports$1.nodeType && exports$1;
1531
1531
  var freeModule = freeExports && true && module && !module.nodeType && module;
1532
1532
  var moduleExports = freeModule && freeModule.exports === freeExports;
1533
1533
  var freeProcess = moduleExports && freeGlobal.process;
@@ -10714,11 +10714,25 @@ const Columns2 = columns;
10714
10714
  const Fields2 = fields;
10715
10715
  const Controls2 = Controls$2;
10716
10716
  const getFormData = (formData, useSessionStorage = false) => {
10717
- if (formData) {
10718
- return clone$1(parseData(formData));
10717
+ if (formData !== void 0 && formData !== null) {
10718
+ const parsed = parseData(formData);
10719
+ if (parsed && typeof parsed === "object") {
10720
+ const cloned = clone$1(parsed);
10721
+ return {
10722
+ id: cloned.id || DEFAULT_FORMDATA().id,
10723
+ stages: cloned.stages || DEFAULT_FORMDATA().stages,
10724
+ rows: cloned.rows || {},
10725
+ columns: cloned.columns || {},
10726
+ fields: cloned.fields || {}
10727
+ };
10728
+ }
10729
+ console.warn("Formeo: Invalid formData provided, using default");
10719
10730
  }
10720
10731
  if (useSessionStorage) {
10721
- return sessionStorage.get(SESSION_FORMDATA_KEY) || DEFAULT_FORMDATA();
10732
+ const sessionData = sessionStorage.get(SESSION_FORMDATA_KEY);
10733
+ if (sessionData) {
10734
+ return sessionData;
10735
+ }
10722
10736
  }
10723
10737
  return DEFAULT_FORMDATA();
10724
10738
  };
@@ -10839,6 +10853,8 @@ const defaults$1 = {
10839
10853
  },
10840
10854
  onAdd: () => {
10841
10855
  },
10856
+ onRemove: () => {
10857
+ },
10842
10858
  onChange: (evt) => events.opts?.debug && console.log(evt),
10843
10859
  onUpdate: (evt) => events.opts?.debug && console.log(evt),
10844
10860
  onUpdateStage: (evt) => events.opts?.debug && console.log(evt),
@@ -10931,31 +10947,37 @@ document.addEventListener(EVENT_FORMEO_UPDATED_FIELD, (evt) => {
10931
10947
  document.addEventListener(EVENT_FORMEO_ADDED_ROW, (evt) => {
10932
10948
  const { timeStamp, type, detail } = evt;
10933
10949
  const eventData = { timeStamp, type, detail };
10950
+ events.opts.onAdd(eventData);
10934
10951
  events.opts.onAddRow(eventData);
10935
10952
  });
10936
10953
  document.addEventListener(EVENT_FORMEO_ADDED_COLUMN, (evt) => {
10937
10954
  const { timeStamp, type, detail } = evt;
10938
10955
  const eventData = { timeStamp, type, detail };
10956
+ events.opts.onAdd(eventData);
10939
10957
  events.opts.onAddColumn(eventData);
10940
10958
  });
10941
10959
  document.addEventListener(EVENT_FORMEO_ADDED_FIELD, (evt) => {
10942
10960
  const { timeStamp, type, detail } = evt;
10943
10961
  const eventData = { timeStamp, type, detail };
10962
+ events.opts.onAdd(eventData);
10944
10963
  events.opts.onAddField(eventData);
10945
10964
  });
10946
10965
  document.addEventListener(EVENT_FORMEO_REMOVED_ROW, (evt) => {
10947
10966
  const { timeStamp, type, detail } = evt;
10948
10967
  const eventData = { timeStamp, type, detail };
10968
+ events.opts.onRemove(eventData);
10949
10969
  events.opts.onRemoveRow(eventData);
10950
10970
  });
10951
10971
  document.addEventListener(EVENT_FORMEO_REMOVED_COLUMN, (evt) => {
10952
10972
  const { timeStamp, type, detail } = evt;
10953
10973
  const eventData = { timeStamp, type, detail };
10974
+ events.opts.onRemove(eventData);
10954
10975
  events.opts.onRemoveColumn(eventData);
10955
10976
  });
10956
10977
  document.addEventListener(EVENT_FORMEO_REMOVED_FIELD, (evt) => {
10957
10978
  const { timeStamp, type, detail } = evt;
10958
10979
  const eventData = { timeStamp, type, detail };
10980
+ events.opts.onRemove(eventData);
10959
10981
  events.opts.onRemoveField(eventData);
10960
10982
  });
10961
10983
  document.addEventListener(EVENT_FORMEO_ON_RENDER, (evt) => {
@@ -11122,7 +11144,18 @@ const defaults = {
11122
11144
  };
11123
11145
  }
11124
11146
  };
11147
+ const INIT_STATES = {
11148
+ CREATED: "created",
11149
+ LOADING_RESOURCES: "loading",
11150
+ INITIALIZING: "initializing",
11151
+ READY: "ready",
11152
+ ERROR: "error"
11153
+ };
11125
11154
  let FormeoEditor$1 = class FormeoEditor {
11155
+ #initState = INIT_STATES.CREATED;
11156
+ #initPromise = null;
11157
+ #lockedFormData = null;
11158
+ #dataLoadedOnce = false;
11126
11159
  /**
11127
11160
  * @param {Object} options formeo options
11128
11161
  * @param {String|Object} userFormData loaded formData
@@ -11137,7 +11170,9 @@ let FormeoEditor$1 = class FormeoEditor {
11137
11170
  this.opts = opts;
11138
11171
  dom.setOptions = opts;
11139
11172
  components.config = config;
11140
- this.userFormData = userFormData || formData;
11173
+ const providedData = userFormData || formData;
11174
+ this.#lockedFormData = providedData ? cleanFormData(providedData) : null;
11175
+ this.userFormData = this.#lockedFormData;
11141
11176
  this.Components = components;
11142
11177
  this.dom = dom;
11143
11178
  events.init({ debug, ...events$1 });
@@ -11152,7 +11187,9 @@ let FormeoEditor$1 = class FormeoEditor {
11152
11187
  return this.Components.formData;
11153
11188
  }
11154
11189
  set formData(data = {}) {
11155
- this.userFormData = cleanFormData(data);
11190
+ const cleaned = cleanFormData(data);
11191
+ this.#lockedFormData = cleaned;
11192
+ this.userFormData = cleaned;
11156
11193
  this.load(this.userFormData, this.opts);
11157
11194
  }
11158
11195
  loadData(data = {}) {
@@ -11166,7 +11203,9 @@ let FormeoEditor$1 = class FormeoEditor {
11166
11203
  * @return {void}
11167
11204
  */
11168
11205
  clear() {
11169
- this.userFormData = DEFAULT_FORMDATA();
11206
+ const defaultData = DEFAULT_FORMDATA();
11207
+ this.#lockedFormData = defaultData;
11208
+ this.userFormData = defaultData;
11170
11209
  this.Components.load(this.userFormData, this.opts);
11171
11210
  this.render();
11172
11211
  }
@@ -11176,6 +11215,7 @@ let FormeoEditor$1 = class FormeoEditor {
11176
11215
  */
11177
11216
  async loadResources() {
11178
11217
  document.removeEventListener("DOMContentLoaded", this.loadResources);
11218
+ this.#initState = INIT_STATES.LOADING_RESOURCES;
11179
11219
  const promises = [
11180
11220
  fetchIcons(this.opts.svgSprite),
11181
11221
  fetchFormeoStyle(this.opts.style),
@@ -11185,38 +11225,142 @@ let FormeoEditor$1 = class FormeoEditor {
11185
11225
  locale: globalThis.sessionStorage?.getItem(SESSION_LOCALE_KEY)
11186
11226
  })
11187
11227
  ].filter(Boolean);
11188
- await Promise.all(promises);
11189
- if (this.opts.allowEdit) {
11190
- this.init();
11228
+ try {
11229
+ await Promise.all(promises);
11230
+ if (this.opts.allowEdit) {
11231
+ this.init();
11232
+ }
11233
+ } catch (error) {
11234
+ this.#initState = INIT_STATES.ERROR;
11235
+ console.error("Failed to load resources:", error);
11236
+ throw error;
11191
11237
  }
11192
11238
  }
11193
11239
  /**
11194
11240
  * Formeo initializer
11195
- * @return {Object} References to formeo instance,
11241
+ * @return {Promise} References to formeo instance,
11196
11242
  * dom elements, actions events and more.
11197
11243
  */
11198
11244
  init() {
11199
- return Controls$2.init(this.opts.controls, this.opts.stickyControls).then((controls) => {
11245
+ if (this.#initState === INIT_STATES.INITIALIZING) {
11246
+ return this.#initPromise;
11247
+ }
11248
+ if (this.#initState === INIT_STATES.READY) {
11249
+ return this.#refreshUI();
11250
+ }
11251
+ this.#initState = INIT_STATES.INITIALIZING;
11252
+ this.#initPromise = Controls$2.init(this.opts.controls, this.opts.stickyControls).then((controls) => {
11200
11253
  this.controls = controls;
11201
- this.load(this.userFormData, this.opts);
11254
+ if (!this.#dataLoadedOnce) {
11255
+ this.#loadInitialData();
11256
+ this.#dataLoadedOnce = true;
11257
+ }
11202
11258
  this.formId = components.get("id");
11203
11259
  this.i18n = {
11204
- setLang: (formeoLocale) => {
11205
- globalThis.sessionStorage?.setItem(SESSION_LOCALE_KEY, formeoLocale);
11206
- const loadLang = mi18n.setCurrent(formeoLocale);
11207
- loadLang.then(() => {
11208
- this.init();
11209
- }, console.error);
11210
- }
11260
+ setLang: this.#setLanguage.bind(this)
11211
11261
  };
11262
+ this.render();
11263
+ this.#initState = INIT_STATES.READY;
11212
11264
  this.opts.onLoad?.(this);
11213
11265
  this.tooltipInstance = new SmartTooltip();
11266
+ return this;
11267
+ }).catch((error) => {
11268
+ this.#initState = INIT_STATES.ERROR;
11269
+ console.error("Failed to initialize editor:", error);
11270
+ throw error;
11214
11271
  });
11272
+ return this.#initPromise;
11273
+ }
11274
+ /**
11275
+ * Set language without reloading form data (fixes race condition)
11276
+ * @param {string} formeoLocale - locale code
11277
+ * @return {Promise}
11278
+ */
11279
+ async #setLanguage(formeoLocale) {
11280
+ globalThis.sessionStorage?.setItem(SESSION_LOCALE_KEY, formeoLocale);
11281
+ await mi18n.setCurrent(formeoLocale);
11282
+ await this.#refreshUI();
11283
+ }
11284
+ /**
11285
+ * Refresh UI without reloading data (used for language changes)
11286
+ * @return {Promise}
11287
+ */
11288
+ async #refreshUI() {
11289
+ this.controls = await Controls$2.init(this.opts.controls, this.opts.stickyControls);
11290
+ this.render();
11291
+ return this;
11292
+ }
11293
+ /**
11294
+ * Load initial data with proper priority
11295
+ */
11296
+ #loadInitialData() {
11297
+ const dataToLoad = this.#getDataWithPriority();
11298
+ this.Components.load(dataToLoad, this.opts);
11299
+ }
11300
+ /**
11301
+ * Get form data with proper priority:
11302
+ * 1. User-provided data (locked at construction)
11303
+ * 2. SessionStorage (if enabled)
11304
+ * 3. Default empty form
11305
+ * @return {Object} form data to load
11306
+ */
11307
+ #getDataWithPriority() {
11308
+ if (this.#lockedFormData) {
11309
+ return clone$1(this.#lockedFormData);
11310
+ }
11311
+ if (this.opts.sessionStorage) {
11312
+ const sessionData = sessionStorage.get(SESSION_FORMDATA_KEY);
11313
+ if (sessionData) {
11314
+ return sessionData;
11315
+ }
11316
+ }
11317
+ return DEFAULT_FORMDATA();
11215
11318
  }
11216
11319
  load(formData = this.userFormData, opts = this.opts) {
11217
11320
  this.Components.load(formData, opts);
11218
11321
  this.render();
11219
11322
  }
11323
+ /**
11324
+ * Get current initialization state
11325
+ * @return {string} current state
11326
+ */
11327
+ get initState() {
11328
+ return this.#initState;
11329
+ }
11330
+ /**
11331
+ * Check if the editor is ready
11332
+ * @return {boolean}
11333
+ */
11334
+ get isReady() {
11335
+ return this.#initState === INIT_STATES.READY;
11336
+ }
11337
+ /**
11338
+ * Wait for the editor to be ready
11339
+ * @return {Promise} resolves when editor is ready
11340
+ */
11341
+ async whenReady() {
11342
+ if (this.#initState === INIT_STATES.READY) {
11343
+ return this;
11344
+ }
11345
+ if (this.#initState === INIT_STATES.ERROR) {
11346
+ return Promise.reject(new Error("Editor initialization failed"));
11347
+ }
11348
+ if (this.#initPromise) {
11349
+ return this.#initPromise;
11350
+ }
11351
+ return new Promise((resolve, reject) => {
11352
+ const checkReady = () => {
11353
+ if (this.#initState === INIT_STATES.READY) {
11354
+ resolve(this);
11355
+ } else if (this.#initState === INIT_STATES.ERROR) {
11356
+ reject(new Error("Editor initialization failed"));
11357
+ } else {
11358
+ globalThis.requestAnimationFrame(checkReady);
11359
+ }
11360
+ };
11361
+ checkReady();
11362
+ });
11363
+ }
11220
11364
  /**
11221
11365
  * Render the formeo sections
11222
11366
  * @return {void}