kitchen-simulator 5.10.8-react.18 → 5.10.9-react.18

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.
@@ -43,7 +43,6 @@ var LiteKitchenConfigurator = /*#__PURE__*/function (_Component) {
43
43
  var _this;
44
44
  _classCallCheck(this, LiteKitchenConfigurator);
45
45
  _this = _callSuper(this, LiteKitchenConfigurator, [props]);
46
- _this._catalogInitStarted = false;
47
46
  _this.state = {
48
47
  savePopupVisible: false,
49
48
  quotePopupVisible: false,
@@ -290,33 +289,33 @@ var LiteKitchenConfigurator = /*#__PURE__*/function (_Component) {
290
289
  if (el !== null && el !== void 0 && (_el$parentElement0 = el.parentElement) !== null && _el$parentElement0 !== void 0 && _el$parentElement0.parentElement) el.parentElement.parentElement.style.zIndex = 6;
291
290
  }
292
291
  }, {
293
- key: "ensureCatalogReady",
294
- value: function ensureCatalogReady() {
292
+ key: "componentDidMount",
293
+ value: function componentDidMount() {
295
294
  var _extractedState$getIn;
295
+ window.forRedo = [];
296
296
  var _this$props = this.props,
297
297
  catalog = _this$props.catalog,
298
298
  extractedState = _this$props.extractedState,
299
299
  projectActions = _this$props.projectActions;
300
- var ready = extractedState === null || extractedState === void 0 || (_extractedState$getIn = extractedState.getIn) === null || _extractedState$getIn === void 0 ? void 0 : _extractedState$getIn.call(extractedState, ['catalog', 'ready']);
301
- if (ready) return;
302
- if (this._catalogInitStarted) return; // ✅ prevent repeated init storms
303
- this._catalogInitStarted = true;
304
- projectActions.initCatalog(catalog);
305
- }
306
- }, {
307
- key: "componentDidMount",
308
- value: function componentDidMount() {
309
- window.forRedo = [];
310
- if (this.props.externalEvent) handleExternalEvent(this.props);
311
- this.ensureCatalogReady();
300
+ var catalogReady = extractedState === null || extractedState === void 0 || (_extractedState$getIn = extractedState.getIn) === null || _extractedState$getIn === void 0 ? void 0 : _extractedState$getIn.call(extractedState, ['catalog', 'ready']);
301
+ if (!catalogReady) projectActions.initCatalog(catalog);
312
302
  }
313
303
  }, {
314
304
  key: "componentDidUpdate",
315
305
  value: function componentDidUpdate(prevProps) {
316
- if (prevProps.externalEvent !== this.props.externalEvent) {
306
+ var _extractedState$getIn2;
307
+ var _this$props2 = this.props,
308
+ externalEvent = _this$props2.externalEvent,
309
+ extractedState = _this$props2.extractedState,
310
+ projectActions = _this$props2.projectActions,
311
+ catalog = _this$props2.catalog;
312
+
313
+ // same behavior: handle external event when it changes
314
+ if (prevProps.externalEvent !== externalEvent) {
317
315
  handleExternalEvent(this.props);
318
316
  }
319
- this.ensureCatalogReady();
317
+ var catalogReady = extractedState === null || extractedState === void 0 || (_extractedState$getIn2 = extractedState.getIn) === null || _extractedState$getIn2 === void 0 ? void 0 : _extractedState$getIn2.call(extractedState, ['catalog', 'ready']);
318
+ if (!catalogReady) projectActions.initCatalog(catalog);
320
319
  }
321
320
  }, {
322
321
  key: "isProjectEmpty",
@@ -367,11 +366,11 @@ var LiteKitchenConfigurator = /*#__PURE__*/function (_Component) {
367
366
  key: "render",
368
367
  value: function render() {
369
368
  var _this2 = this;
370
- var _this$props2 = this.props,
371
- width = _this$props2.width,
372
- height = _this$props2.height,
373
- extractedState = _this$props2.extractedState,
374
- props = _objectWithoutProperties(_this$props2, _excluded);
369
+ var _this$props3 = this.props,
370
+ width = _this$props3.width,
371
+ height = _this$props3.height,
372
+ extractedState = _this$props3.extractedState,
373
+ props = _objectWithoutProperties(_this$props3, _excluded);
375
374
  var _this$state = this.state,
376
375
  savePopupVisible = _this$state.savePopupVisible,
377
376
  quotePopupVisible = _this$state.quotePopupVisible,
package/es/index.js CHANGED
@@ -1,3 +1,4 @@
1
+ import _defineProperty from "@babel/runtime/helpers/esm/defineProperty";
1
2
  import _extends from "@babel/runtime/helpers/esm/extends";
2
3
  import _classCallCheck from "@babel/runtime/helpers/esm/classCallCheck";
3
4
  import _createClass from "@babel/runtime/helpers/esm/createClass";
@@ -5,6 +6,9 @@ import _possibleConstructorReturn from "@babel/runtime/helpers/esm/possibleConst
5
6
  import _getPrototypeOf from "@babel/runtime/helpers/esm/getPrototypeOf";
6
7
  import _inherits from "@babel/runtime/helpers/esm/inherits";
7
8
  import _asyncToGenerator from "@babel/runtime/helpers/esm/asyncToGenerator";
9
+ import _toConsumableArray from "@babel/runtime/helpers/esm/toConsumableArray";
10
+ function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
11
+ function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
8
12
  function _callSuper(t, o, e) { return o = _getPrototypeOf(o), _possibleConstructorReturn(t, _isNativeReflectConstruct() ? Reflect.construct(o, e || [], _getPrototypeOf(t).constructor) : o.apply(t, e)); }
9
13
  function _isNativeReflectConstruct() { try { var t = !Boolean.prototype.valueOf.call(Reflect.construct(Boolean, [], function () {})); } catch (t) {} return (_isNativeReflectConstruct = function _isNativeReflectConstruct() { return !!t; })(); }
10
14
  function _createForOfIteratorHelper(r, e) { var t = "undefined" != typeof Symbol && r[Symbol.iterator] || r["@@iterator"]; if (!t) { if (Array.isArray(r) || (t = _unsupportedIterableToArray(r)) || e && r && "number" == typeof r.length) { t && (r = t); var _n = 0, F = function F() {}; return { s: F, n: function n() { return _n >= r.length ? { done: !0 } : { done: !1, value: r[_n++] }; }, e: function e(r) { throw r; }, f: F }; } throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } var o, a = !0, u = !1; return { s: function s() { t = t.call(r); }, n: function n() { var r = t.next(); return a = r.done, r; }, e: function e(r) { u = !0, o = r; }, f: function f() { try { a || null == t["return"] || t["return"](); } finally { if (u) throw o; } } }; }
@@ -17,6 +21,66 @@ import LiteRenderer from "./LiteRenderer";
17
21
  import { createRoot } from 'react-dom/client';
18
22
  var ROOT_KEY = '__kitchenSimulatorRoot__';
19
23
  var API_KEY = '__kitchenSimulatorApi__';
24
+
25
+ /**
26
+ * Debug logging
27
+ * - Enable via:
28
+ * - window.__kitchenSimulatorDebug__ = true
29
+ * - or pass props.debug = true to renderKitchenSimulator(container, { debug: true })
30
+ */
31
+ function makeLogger(getEnabled) {
32
+ var prefix = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : '[kitchen-simulator]';
33
+ var now = function now() {
34
+ return (typeof performance !== 'undefined' && performance.now ? performance.now() : Date.now()).toFixed(1);
35
+ };
36
+ var safe = function safe(v) {
37
+ try {
38
+ if (v == null) return v;
39
+ if (typeof v === 'string') return v;
40
+ if (typeof v === 'number' || typeof v === 'boolean') return v;
41
+ // avoid huge logs
42
+ return JSON.stringify(v, function (k, val) {
43
+ if (k === 'children' || k === 'parent') return '[omitted]';
44
+ if (typeof val === 'function') return '[fn]';
45
+ return val;
46
+ });
47
+ } catch (_unused) {
48
+ return '[unserializable]';
49
+ }
50
+ };
51
+ var log = function log() {
52
+ var _console;
53
+ if (!getEnabled()) return;
54
+ // eslint-disable-next-line no-console
55
+ for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
56
+ args[_key] = arguments[_key];
57
+ }
58
+ (_console = console).log.apply(_console, ["".concat(prefix, " ").concat(now(), "ms")].concat(_toConsumableArray(args.map(safe))));
59
+ };
60
+ var warn = function warn() {
61
+ var _console2;
62
+ if (!getEnabled()) return;
63
+ // eslint-disable-next-line no-console
64
+ for (var _len2 = arguments.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
65
+ args[_key2] = arguments[_key2];
66
+ }
67
+ (_console2 = console).warn.apply(_console2, ["".concat(prefix, " ").concat(now(), "ms")].concat(_toConsumableArray(args.map(safe))));
68
+ };
69
+ var error = function error() {
70
+ var _console3;
71
+ if (!getEnabled()) return;
72
+ // eslint-disable-next-line no-console
73
+ for (var _len3 = arguments.length, args = new Array(_len3), _key3 = 0; _key3 < _len3; _key3++) {
74
+ args[_key3] = arguments[_key3];
75
+ }
76
+ (_console3 = console).error.apply(_console3, ["".concat(prefix, " ").concat(now(), "ms")].concat(_toConsumableArray(args.map(safe))));
77
+ };
78
+ return {
79
+ log: log,
80
+ warn: warn,
81
+ error: error
82
+ };
83
+ }
20
84
  function nextFrame() {
21
85
  return new Promise(function (resolve) {
22
86
  return requestAnimationFrame(resolve);
@@ -40,6 +104,7 @@ Three.TextureLoader.prototype.load = function (url, onLoad, onProgress, onError)
40
104
  * Ref-counted global install so multiple instances don't clobber each other.
41
105
  */
42
106
  function installGltfTracker() {
107
+ var debug = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : false;
43
108
  if (typeof window === 'undefined') {
44
109
  var _subscribe = function _subscribe() {
45
110
  return function () {};
@@ -70,6 +135,7 @@ function installGltfTracker() {
70
135
  };
71
136
  }
72
137
  var GLOBAL_KEY = '__kitchenSimulatorGltfTracker__';
138
+ var TRACKER_DEBUG_KEY = '__kitchenSimulatorDebug__';
73
139
  if (!window[GLOBAL_KEY]) {
74
140
  window[GLOBAL_KEY] = {
75
141
  refCount: 0,
@@ -82,13 +148,20 @@ function installGltfTracker() {
82
148
  };
83
149
  }
84
150
  var g = window[GLOBAL_KEY];
151
+ var isDebug = function isDebug() {
152
+ return !!debug || !!window[TRACKER_DEBUG_KEY];
153
+ };
154
+ var _makeLogger = makeLogger(isDebug, '[kitchen-simulator:gltf]'),
155
+ log = _makeLogger.log,
156
+ warn = _makeLogger.warn,
157
+ error = _makeLogger.error;
85
158
  var is3dAssetUrl = function is3dAssetUrl(url) {
86
159
  try {
87
160
  var _url$toString, _url$toString2;
88
161
  var s = typeof url === 'string' ? url : (_url$toString = url === null || url === void 0 || (_url$toString2 = url.toString) === null || _url$toString2 === void 0 ? void 0 : _url$toString2.call(url)) !== null && _url$toString !== void 0 ? _url$toString : '';
89
162
  var u = s.toLowerCase().split('?')[0]; // ignore cache params
90
163
  return u.endsWith('.gltf') || u.endsWith('.glb') || u.endsWith('.bin') || u.endsWith('.ktx2') || u.endsWith('.hdr') || u.endsWith('.exr') || u.endsWith('.png') || u.endsWith('.jpg') || u.endsWith('.jpeg') || u.endsWith('.webp');
91
- } catch (_unused) {
164
+ } catch (_unused2) {
92
165
  return false;
93
166
  }
94
167
  };
@@ -116,6 +189,7 @@ function installGltfTracker() {
116
189
  var installIfNeeded = function installIfNeeded() {
117
190
  var _XHR$prototype, _XHR$prototype2;
118
191
  if (g.installed) return;
192
+ log('Installing GLTF tracker hooks');
119
193
 
120
194
  // ---- XHR hook ----
121
195
  var XHR = window.XMLHttpRequest;
@@ -125,8 +199,14 @@ function installGltfTracker() {
125
199
  XHR.prototype.open = function (method, url) {
126
200
  var _g$originalOpen;
127
201
  this.__is3dAssetRequest = is3dAssetUrl(url);
128
- for (var _len = arguments.length, rest = new Array(_len > 2 ? _len - 2 : 0), _key = 2; _key < _len; _key++) {
129
- rest[_key - 2] = arguments[_key];
202
+ if (this.__is3dAssetRequest) {
203
+ log('XHR open (3D asset)', {
204
+ method: method,
205
+ url: url
206
+ });
207
+ }
208
+ for (var _len4 = arguments.length, rest = new Array(_len4 > 2 ? _len4 - 2 : 0), _key4 = 2; _key4 < _len4; _key4++) {
209
+ rest[_key4 - 2] = arguments[_key4];
130
210
  }
131
211
  return (_g$originalOpen = g.originalOpen).call.apply(_g$originalOpen, [this, method, url].concat(rest));
132
212
  };
@@ -134,39 +214,55 @@ function installGltfTracker() {
134
214
  var _this = this;
135
215
  if (this.__is3dAssetRequest) {
136
216
  g.inFlight += 1;
217
+ log('XHR send -> inFlight++', g.inFlight);
137
218
  notify();
138
219
  var _done = function done() {
139
220
  g.inFlight -= 1;
140
221
  if (g.inFlight < 0) g.inFlight = 0;
222
+ log('XHR done -> inFlight--', g.inFlight);
141
223
  notify();
142
224
  _this.removeEventListener('loadend', _done);
225
+ _this.removeEventListener('error', _done);
226
+ _this.removeEventListener('abort', _done);
227
+ _this.removeEventListener('timeout', _done);
143
228
  };
144
229
  this.addEventListener('loadend', _done);
230
+ this.addEventListener('error', _done);
231
+ this.addEventListener('abort', _done);
232
+ this.addEventListener('timeout', _done);
145
233
  }
146
- for (var _len2 = arguments.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
147
- args[_key2] = arguments[_key2];
234
+ for (var _len5 = arguments.length, args = new Array(_len5), _key5 = 0; _key5 < _len5; _key5++) {
235
+ args[_key5] = arguments[_key5];
148
236
  }
149
237
  return g.originalSend.apply(this, args);
150
238
  };
239
+ } else {
240
+ warn('XHR hooks not installed (missing open/send)');
151
241
  }
152
242
 
153
243
  // ---- fetch hook ----
154
244
  g.originalFetch = window.fetch;
155
245
  if (typeof g.originalFetch === 'function') {
156
246
  window.fetch = /*#__PURE__*/_asyncToGenerator(/*#__PURE__*/_regeneratorRuntime.mark(function _callee2() {
157
- var _len3,
247
+ var _input;
248
+ var _len6,
158
249
  args,
159
- _key3,
250
+ _key6,
160
251
  input,
161
252
  init,
162
253
  newUrl,
163
254
  track,
164
- _args2 = arguments;
255
+ _input2,
256
+ res,
257
+ _input3,
258
+ _e$message,
259
+ _args2 = arguments,
260
+ _t;
165
261
  return _regeneratorRuntime.wrap(function (_context2) {
166
262
  while (1) switch (_context2.prev = _context2.next) {
167
263
  case 0:
168
- for (_len3 = _args2.length, args = new Array(_len3), _key3 = 0; _key3 < _len3; _key3++) {
169
- args[_key3] = _args2[_key3];
264
+ for (_len6 = _args2.length, args = new Array(_len6), _key6 = 0; _key6 < _len6; _key6++) {
265
+ args[_key6] = _args2[_key6];
170
266
  }
171
267
  input = args[0], init = args[1]; // DIY-714 [Temp Fix] Rewrite API URLs
172
268
  if (typeof input === 'string') {
@@ -183,24 +279,44 @@ function installGltfTracker() {
183
279
  return _context2.abrupt("return", g.originalFetch.call(this, input, init));
184
280
  case 1:
185
281
  g.inFlight += 1;
282
+ log('fetch (3D asset) -> inFlight++', g.inFlight, {
283
+ url: typeof input === 'string' ? input : (_input = input) === null || _input === void 0 ? void 0 : _input.url
284
+ });
186
285
  notify();
187
286
  _context2.prev = 2;
188
287
  _context2.next = 3;
189
288
  return g.originalFetch.call(this, input, init);
190
289
  case 3:
191
- return _context2.abrupt("return", _context2.sent);
290
+ res = _context2.sent;
291
+ log('fetch response (3D asset)', {
292
+ url: typeof input === 'string' ? input : (_input2 = input) === null || _input2 === void 0 ? void 0 : _input2.url,
293
+ ok: res === null || res === void 0 ? void 0 : res.ok,
294
+ status: res === null || res === void 0 ? void 0 : res.status
295
+ });
296
+ return _context2.abrupt("return", res);
192
297
  case 4:
193
298
  _context2.prev = 4;
299
+ _t = _context2["catch"](2);
300
+ error('fetch error (3D asset)', {
301
+ url: typeof input === 'string' ? input : (_input3 = input) === null || _input3 === void 0 ? void 0 : _input3.url,
302
+ error: (_e$message = _t === null || _t === void 0 ? void 0 : _t.message) !== null && _e$message !== void 0 ? _e$message : _t
303
+ });
304
+ throw _t;
305
+ case 5:
306
+ _context2.prev = 5;
194
307
  g.inFlight -= 1;
195
308
  if (g.inFlight < 0) g.inFlight = 0;
309
+ log('fetch finally -> inFlight--', g.inFlight);
196
310
  notify();
197
- return _context2.finish(4);
198
- case 5:
311
+ return _context2.finish(5);
312
+ case 6:
199
313
  case "end":
200
314
  return _context2.stop();
201
315
  }
202
- }, _callee2, this, [[2,, 4, 5]]);
316
+ }, _callee2, this, [[2, 4, 5, 6]]);
203
317
  }));
318
+ } else {
319
+ warn('fetch hook not installed (window.fetch not a function)');
204
320
  }
205
321
  g.installed = true;
206
322
  };
@@ -240,13 +356,17 @@ function installGltfTracker() {
240
356
  var _ref3,
241
357
  _ref3$timeoutMs,
242
358
  timeoutMs,
243
- start,
244
359
  _args4 = arguments;
245
360
  return _regeneratorRuntime.wrap(function (_context4) {
246
361
  while (1) switch (_context4.prev = _context4.next) {
247
362
  case 0:
248
363
  _ref3 = _args4.length > 0 && _args4[0] !== undefined ? _args4[0] : {}, _ref3$timeoutMs = _ref3.timeoutMs, timeoutMs = _ref3$timeoutMs === void 0 ? 30000 : _ref3$timeoutMs;
249
- start = Date.now();
364
+ log('waitForIdle start', {
365
+ timeoutMs: timeoutMs,
366
+ inFlight: g.inFlight
367
+ });
368
+
369
+ // Fast path
250
370
  _context4.next = 1;
251
371
  return waitStableIdle2Frames();
252
372
  case 1:
@@ -254,42 +374,62 @@ function installGltfTracker() {
254
374
  _context4.next = 2;
255
375
  break;
256
376
  }
377
+ log('waitForIdle fast-path resolved');
257
378
  return _context4.abrupt("return", true);
258
379
  case 2:
259
380
  return _context4.abrupt("return", new Promise(function (resolve, reject) {
260
381
  var unsub = null;
382
+ var finished = false;
383
+ var finishOk = function finishOk() {
384
+ if (finished) return;
385
+ finished = true;
386
+ if (unsub) unsub();
387
+ clearTimeout(timer);
388
+ log('waitForIdle resolved');
389
+ resolve(true);
390
+ };
391
+ var finishErr = function finishErr(err) {
392
+ var _err$message;
393
+ if (finished) return;
394
+ finished = true;
395
+ if (unsub) unsub();
396
+ clearTimeout(timer);
397
+ error('waitForIdle timeout/reject', (_err$message = err === null || err === void 0 ? void 0 : err.message) !== null && _err$message !== void 0 ? _err$message : err);
398
+ reject(err);
399
+ };
400
+
401
+ // ✅ Real timeout no matter what happens with inFlight changes
402
+ var timer = setTimeout(function () {
403
+ finishErr(new Error('3D assets did not become idle within timeout'));
404
+ }, timeoutMs);
261
405
  var onChange = /*#__PURE__*/function () {
262
406
  var _ref4 = _asyncToGenerator(/*#__PURE__*/_regeneratorRuntime.mark(function _callee3(count) {
263
407
  var stable;
264
408
  return _regeneratorRuntime.wrap(function (_context3) {
265
409
  while (1) switch (_context3.prev = _context3.next) {
266
410
  case 0:
267
- if (!(count !== 0)) {
411
+ if (!finished) {
268
412
  _context3.next = 1;
269
413
  break;
270
414
  }
271
- if (Date.now() - start > timeoutMs) {
272
- if (unsub) unsub();
273
- reject(new Error('3D assets did not become idle within timeout'));
274
- }
275
415
  return _context3.abrupt("return");
276
416
  case 1:
277
- _context3.next = 2;
278
- return waitStableIdle2Frames();
279
- case 2:
280
- stable = _context3.sent;
281
- if (!stable) {
282
- _context3.next = 3;
417
+ log('waitForIdle inFlight change', count);
418
+
419
+ // Only care when it hits zero; otherwise we just wait
420
+ if (!(count !== 0)) {
421
+ _context3.next = 2;
283
422
  break;
284
423
  }
285
- if (unsub) unsub();
286
- resolve(true);
287
424
  return _context3.abrupt("return");
425
+ case 2:
426
+ _context3.next = 3;
427
+ return waitStableIdle2Frames();
288
428
  case 3:
289
- if (Date.now() - start > timeoutMs) {
290
- if (unsub) unsub();
291
- reject(new Error('3D assets did not become idle within timeout'));
292
- }
429
+ stable = _context3.sent;
430
+ log('waitForIdle stable check', stable);
431
+ if (stable) finishOk();
432
+ // else keep waiting
293
433
  case 4:
294
434
  case "end":
295
435
  return _context3.stop();
@@ -315,7 +455,9 @@ function installGltfTracker() {
315
455
  var uninstall = function uninstall() {
316
456
  var _XHR$prototype3, _XHR$prototype4;
317
457
  g.refCount -= 1;
458
+ log('uninstall tracker refCount--', g.refCount);
318
459
  if (g.refCount > 0) return;
460
+ log('uninstall tracker (final) restoring hooks');
319
461
  var XHR = window.XMLHttpRequest;
320
462
  if (XHR !== null && XHR !== void 0 && (_XHR$prototype3 = XHR.prototype) !== null && _XHR$prototype3 !== void 0 && _XHR$prototype3.open && g.originalOpen) XHR.prototype.open = g.originalOpen;
321
463
  if (XHR !== null && XHR !== void 0 && (_XHR$prototype4 = XHR.prototype) !== null && _XHR$prototype4 !== void 0 && _XHR$prototype4.send && g.originalSend) XHR.prototype.send = g.originalSend;
@@ -328,6 +470,7 @@ function installGltfTracker() {
328
470
  g.originalSend = null;
329
471
  };
330
472
  g.refCount += 1;
473
+ log('install tracker refCount++', g.refCount);
331
474
  installIfNeeded();
332
475
  return {
333
476
  getInFlight: function getInFlight() {
@@ -342,10 +485,19 @@ export function renderKitchenSimulator(container) {
342
485
  var _props$framesPerEvent, _props$waitForGltfIdl, _props$gltfTimeoutMs;
343
486
  var props = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
344
487
  if (!container) throw new Error('renderKitchenSimulator: container is required');
488
+ var DEBUG_KEY = '__kitchenSimulatorDebug__';
489
+ var debugEnabled = !!props.debug || typeof window !== 'undefined' && !!window[DEBUG_KEY];
490
+ var _makeLogger2 = makeLogger(function () {
491
+ return debugEnabled;
492
+ }),
493
+ log = _makeLogger2.log,
494
+ warn = _makeLogger2.warn,
495
+ error = _makeLogger2.error;
345
496
 
346
497
  // ✅ Reuse existing API
347
498
  if (container[API_KEY]) {
348
499
  var _container$API_KEY$__, _container$API_KEY;
500
+ log('Reusing existing API; calling __render with new props');
349
501
  (_container$API_KEY$__ = (_container$API_KEY = container[API_KEY]).__render) === null || _container$API_KEY$__ === void 0 || _container$API_KEY$__.call(_container$API_KEY, props);
350
502
  return container[API_KEY];
351
503
  }
@@ -355,38 +507,83 @@ export function renderKitchenSimulator(container) {
355
507
  if (!root) {
356
508
  root = createRoot(container);
357
509
  container[ROOT_KEY] = root;
510
+ log('Created new React root');
511
+ } else {
512
+ log('Reusing existing React root');
358
513
  }
359
514
  var setExternalEventFn = null;
360
515
  var destroyed = false;
361
516
  var queue = [];
362
517
  var pendingMarkers = new Set();
363
518
  var MARKER = Symbol('marker');
364
- var gltfTracker = installGltfTracker();
519
+ var gltfTracker = installGltfTracker(debugEnabled);
365
520
 
366
521
  // FAST defaults (safe)
367
522
  var defaultFramesPerEvent = (_props$framesPerEvent = props.framesPerEvent) !== null && _props$framesPerEvent !== void 0 ? _props$framesPerEvent : 1;
368
523
  var waitForAssets = (_props$waitForGltfIdl = props.waitForGltfIdleAfterEachEvent) !== null && _props$waitForGltfIdl !== void 0 ? _props$waitForGltfIdl : true;
369
524
  var defaultTimeout = (_props$gltfTimeoutMs = props.gltfTimeoutMs) !== null && _props$gltfTimeoutMs !== void 0 ? _props$gltfTimeoutMs : 30000;
370
-
371
- // If you want ultra-fast UI responsiveness, you can disable waiting per-event
372
- // and only wait on “important” events, see comment in settle() below.
373
-
374
525
  var draining = false;
526
+
527
+ // ---- Loop detection / profiling helpers ----
528
+ var drainRunId = 0;
529
+ var eventSeq = 0;
530
+ var lastEvents = [];
531
+ var LAST_N = 40;
532
+ function summarizeEvent(ev) {
533
+ var _ref5, _ref6, _ev$type, _ev$payload, _ref7, _ev$id, _ev$payload2;
534
+ if (!ev) return ev;
535
+ var t = (_ref5 = (_ref6 = (_ev$type = ev === null || ev === void 0 ? void 0 : ev.type) !== null && _ev$type !== void 0 ? _ev$type : ev === null || ev === void 0 || (_ev$payload = ev.payload) === null || _ev$payload === void 0 ? void 0 : _ev$payload.mode) !== null && _ref6 !== void 0 ? _ref6 : ev === null || ev === void 0 ? void 0 : ev.name) !== null && _ref5 !== void 0 ? _ref5 : 'unknown';
536
+ var id = (_ref7 = (_ev$id = ev === null || ev === void 0 ? void 0 : ev.id) !== null && _ev$id !== void 0 ? _ev$id : ev === null || ev === void 0 || (_ev$payload2 = ev.payload) === null || _ev$payload2 === void 0 ? void 0 : _ev$payload2.id) !== null && _ref7 !== void 0 ? _ref7 : null;
537
+ return {
538
+ type: t,
539
+ id: id,
540
+ framesPerEvent: ev === null || ev === void 0 ? void 0 : ev.framesPerEvent,
541
+ waitForGltfIdleAfterEachEvent: ev === null || ev === void 0 ? void 0 : ev.waitForGltfIdleAfterEachEvent,
542
+ gltfTimeoutMs: ev === null || ev === void 0 ? void 0 : ev.gltfTimeoutMs
543
+ };
544
+ }
545
+ function recordEvent(ev) {
546
+ var s = summarizeEvent(ev);
547
+ lastEvents.push(s);
548
+ if (lastEvents.length > LAST_N) lastEvents.shift();
549
+ }
550
+ function dumpLoopHint() {
551
+ var context = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : '';
552
+ warn('Possible infinite loop / stall detected', {
553
+ context: context,
554
+ destroyed: destroyed,
555
+ draining: draining,
556
+ queueLength: queue.length,
557
+ pendingMarkers: pendingMarkers.size,
558
+ gltfInFlight: gltfTracker.getInFlight(),
559
+ lastEvents: lastEvents
560
+ });
561
+ }
375
562
  function isSyncScene(ev) {
376
- var _ev$payload;
377
- return (ev === null || ev === void 0 ? void 0 : ev.type) === 'EXTERNAL_EVENT_SYNC_SCENE' || (ev === null || ev === void 0 || (_ev$payload = ev.payload) === null || _ev$payload === void 0 ? void 0 : _ev$payload.mode) === 'sync-scene' || (ev === null || ev === void 0 ? void 0 : ev.__sync) === true;
563
+ var _ev$payload3;
564
+ return (ev === null || ev === void 0 ? void 0 : ev.type) === 'EXTERNAL_EVENT_SYNC_SCENE' || (ev === null || ev === void 0 || (_ev$payload3 = ev.payload) === null || _ev$payload3 === void 0 ? void 0 : _ev$payload3.mode) === 'sync-scene' || (ev === null || ev === void 0 ? void 0 : ev.__sync) === true;
378
565
  }
379
- function settle(_x2) {
566
+ function settle(_x2, _x3) {
380
567
  return _settle.apply(this, arguments);
381
568
  }
382
569
  function _settle() {
383
- _settle = _asyncToGenerator(/*#__PURE__*/_regeneratorRuntime.mark(function _callee7(ev) {
384
- var _ev$framesPerEvent, _ev$waitForGltfIdleAf;
385
- var frames, i, shouldWait, _ev$gltfTimeoutMs, timeoutMs;
570
+ _settle = _asyncToGenerator(/*#__PURE__*/_regeneratorRuntime.mark(function _callee7(ev, meta) {
571
+ var _ev$framesPerEvent, _ev$waitForGltfIdleAf, _ev$gltfTimeoutMs;
572
+ var frames, shouldWait, timeoutMs, i, start, _e$message2, _t2;
386
573
  return _regeneratorRuntime.wrap(function (_context7) {
387
574
  while (1) switch (_context7.prev = _context7.next) {
388
575
  case 0:
389
- frames = (_ev$framesPerEvent = ev === null || ev === void 0 ? void 0 : ev.framesPerEvent) !== null && _ev$framesPerEvent !== void 0 ? _ev$framesPerEvent : defaultFramesPerEvent; // (1) allow react/reducers to run (fixes “must zoom to see updates”)
576
+ frames = (_ev$framesPerEvent = ev === null || ev === void 0 ? void 0 : ev.framesPerEvent) !== null && _ev$framesPerEvent !== void 0 ? _ev$framesPerEvent : defaultFramesPerEvent;
577
+ shouldWait = (_ev$waitForGltfIdleAf = ev === null || ev === void 0 ? void 0 : ev.waitForGltfIdleAfterEachEvent) !== null && _ev$waitForGltfIdleAf !== void 0 ? _ev$waitForGltfIdleAf : waitForAssets;
578
+ timeoutMs = (_ev$gltfTimeoutMs = ev === null || ev === void 0 ? void 0 : ev.gltfTimeoutMs) !== null && _ev$gltfTimeoutMs !== void 0 ? _ev$gltfTimeoutMs : defaultTimeout;
579
+ log('settle:start', _objectSpread(_objectSpread({}, meta), {}, {
580
+ frames: frames,
581
+ shouldWait: shouldWait,
582
+ timeoutMs: timeoutMs,
583
+ gltfInFlight: gltfTracker.getInFlight()
584
+ }));
585
+
586
+ // (1) allow react/reducers to run (fixes “must zoom to see updates”)
390
587
  i = 0;
391
588
  case 1:
392
589
  if (!(i < frames)) {
@@ -400,34 +597,52 @@ export function renderKitchenSimulator(container) {
400
597
  _context7.next = 1;
401
598
  break;
402
599
  case 3:
403
- // (2) optionally wait for assets
404
- // fastest safe approach: keep ON for events that add/replace/load models
405
- // You can override per-event via ev.waitForGltfIdleAfterEachEvent = false
406
- shouldWait = (_ev$waitForGltfIdleAf = ev === null || ev === void 0 ? void 0 : ev.waitForGltfIdleAfterEachEvent) !== null && _ev$waitForGltfIdleAf !== void 0 ? _ev$waitForGltfIdleAf : waitForAssets;
407
600
  if (!shouldWait) {
408
- _context7.next = 4;
601
+ _context7.next = 8;
409
602
  break;
410
603
  }
411
- timeoutMs = (_ev$gltfTimeoutMs = ev === null || ev === void 0 ? void 0 : ev.gltfTimeoutMs) !== null && _ev$gltfTimeoutMs !== void 0 ? _ev$gltfTimeoutMs : defaultTimeout;
412
- _context7.next = 4;
604
+ start = Date.now();
605
+ _context7.prev = 4;
606
+ _context7.next = 5;
413
607
  return gltfTracker.waitForIdle({
414
608
  timeoutMs: timeoutMs
415
609
  });
416
- case 4:
417
- _context7.next = 5;
418
- return nextFrame();
419
610
  case 5:
611
+ _context7.next = 7;
612
+ break;
613
+ case 6:
614
+ _context7.prev = 6;
615
+ _t2 = _context7["catch"](4);
616
+ error('settle:waitForIdle failed', _objectSpread(_objectSpread({}, meta), {}, {
617
+ err: (_e$message2 = _t2 === null || _t2 === void 0 ? void 0 : _t2.message) !== null && _e$message2 !== void 0 ? _e$message2 : _t2,
618
+ waitedMs: Date.now() - start,
619
+ gltfInFlight: gltfTracker.getInFlight()
620
+ }));
621
+ // Don’t throw unless you want the whole queue to stop.
622
+ // Keeping behavior: let it bubble so caller catches and continues.
623
+ throw _t2;
624
+ case 7:
625
+ log('settle:waitForIdle done', _objectSpread(_objectSpread({}, meta), {}, {
626
+ waitedMs: Date.now() - start,
627
+ gltfInFlight: gltfTracker.getInFlight()
628
+ }));
629
+ case 8:
630
+ _context7.next = 9;
631
+ return nextFrame();
632
+ case 9:
420
633
  if (!isSyncScene(ev)) {
421
- _context7.next = 6;
634
+ _context7.next = 10;
422
635
  break;
423
636
  }
424
- _context7.next = 6;
637
+ _context7.next = 10;
425
638
  return nextFrame();
426
- case 6:
639
+ case 10:
640
+ log('settle:done', _objectSpread({}, meta));
641
+ case 11:
427
642
  case "end":
428
643
  return _context7.stop();
429
644
  }
430
- }, _callee7);
645
+ }, _callee7, null, [[4, 6]]);
431
646
  }));
432
647
  return _settle.apply(this, arguments);
433
648
  }
@@ -436,7 +651,7 @@ export function renderKitchenSimulator(container) {
436
651
  }
437
652
  function _drain() {
438
653
  _drain = _asyncToGenerator(/*#__PURE__*/_regeneratorRuntime.mark(function _callee8() {
439
- var item, _t;
654
+ var myRunId, start, watchdogEveryMs, watchdog, MAX_ITERATIONS, iterations, item, seq, meta, _err$message2, _t3;
440
655
  return _regeneratorRuntime.wrap(function (_context8) {
441
656
  while (1) switch (_context8.prev = _context8.next) {
442
657
  case 0:
@@ -444,55 +659,131 @@ export function renderKitchenSimulator(container) {
444
659
  _context8.next = 1;
445
660
  break;
446
661
  }
662
+ log('drain:skip', {
663
+ draining: draining,
664
+ destroyed: destroyed,
665
+ queueLength: queue.length
666
+ });
447
667
  return _context8.abrupt("return");
448
668
  case 1:
449
669
  draining = true;
670
+ myRunId = drainRunId += 1;
671
+ start = Date.now();
672
+ log('drain:start', {
673
+ runId: myRunId,
674
+ queueLength: queue.length,
675
+ pendingMarkers: pendingMarkers.size,
676
+ gltfInFlight: gltfTracker.getInFlight()
677
+ });
678
+
679
+ // Watchdog: if drain runs too long, dump state (helps spot infinite loops)
680
+ watchdogEveryMs = 4000;
681
+ watchdog = setInterval(function () {
682
+ dumpLoopHint("drain watchdog runId=".concat(myRunId));
683
+ }, watchdogEveryMs); // Hard cap of iterations in one drain call (fail-open) to prevent true infinite loops
684
+ MAX_ITERATIONS = 5000;
685
+ iterations = 0;
450
686
  _context8.prev = 2;
451
687
  case 3:
452
688
  if (!(!destroyed && queue.length)) {
453
- _context8.next = 11;
689
+ _context8.next = 12;
690
+ break;
691
+ }
692
+ iterations += 1;
693
+ if (!(iterations >= MAX_ITERATIONS)) {
694
+ _context8.next = 4;
454
695
  break;
455
696
  }
697
+ dumpLoopHint("MAX_ITERATIONS reached runId=".concat(myRunId));
698
+ // fail-open: stop draining; future drain() calls can continue
699
+ return _context8.abrupt("continue", 12);
700
+ case 4:
456
701
  if (setExternalEventFn) {
457
- _context8.next = 5;
702
+ _context8.next = 6;
458
703
  break;
459
704
  }
460
- _context8.next = 4;
705
+ log('drain:waiting for setExternalEventFn');
706
+ _context8.next = 5;
461
707
  return nextFrame();
462
- case 4:
463
- return _context8.abrupt("continue", 3);
464
708
  case 5:
709
+ return _context8.abrupt("continue", 3);
710
+ case 6:
465
711
  item = queue.shift();
466
712
  if (!(item && item.__marker === MARKER)) {
467
- _context8.next = 6;
713
+ _context8.next = 7;
468
714
  break;
469
715
  }
470
716
  pendingMarkers["delete"](item.token);
717
+ log('drain:marker consumed', {
718
+ runId: myRunId,
719
+ pendingMarkers: pendingMarkers.size,
720
+ queueLength: queue.length
721
+ });
471
722
  return _context8.abrupt("continue", 3);
472
- case 6:
723
+ case 7:
724
+ seq = eventSeq += 1;
725
+ recordEvent(item);
726
+ meta = {
727
+ runId: myRunId,
728
+ seq: seq,
729
+ queueLengthAfterShift: queue.length,
730
+ pendingMarkers: pendingMarkers.size,
731
+ gltfInFlightBefore: gltfTracker.getInFlight(),
732
+ event: summarizeEvent(item)
733
+ };
734
+ log('drain:event begin', meta);
735
+ _context8.prev = 8;
473
736
  setExternalEventFn(item);
474
- _context8.prev = 7;
475
- _context8.next = 8;
476
- return settle(item);
477
- case 8:
478
- _context8.next = 10;
479
- break;
737
+ log('drain:setExternalEventFn called', meta);
738
+ _context8.next = 9;
739
+ return settle(item, meta);
480
740
  case 9:
481
- _context8.prev = 9;
482
- _t = _context8["catch"](7);
483
- console.error('settle failed', _t);
741
+ log('drain:event done', _objectSpread(_objectSpread({}, meta), {}, {
742
+ gltfInFlightAfter: gltfTracker.getInFlight()
743
+ }));
744
+ _context8.next = 11;
745
+ break;
484
746
  case 10:
747
+ _context8.prev = 10;
748
+ _t3 = _context8["catch"](8);
749
+ error('drain:event failed', _objectSpread(_objectSpread({}, meta), {}, {
750
+ err: (_err$message2 = _t3 === null || _t3 === void 0 ? void 0 : _t3.message) !== null && _err$message2 !== void 0 ? _err$message2 : _t3,
751
+ gltfInFlight: gltfTracker.getInFlight()
752
+ }));
753
+ // IMPORTANT: continue so we can eventually consume the marker
754
+ case 11:
755
+ // If queue never drains (e.g. events enqueue more events endlessly),
756
+ // these logs help identify repeating patterns:
757
+ if (debugEnabled && seq % 50 === 0) {
758
+ warn('drain:progress snapshot', {
759
+ runId: myRunId,
760
+ processedEvents: seq,
761
+ queueLength: queue.length,
762
+ pendingMarkers: pendingMarkers.size,
763
+ gltfInFlight: gltfTracker.getInFlight(),
764
+ lastEvents: lastEvents
765
+ });
766
+ }
485
767
  _context8.next = 3;
486
768
  break;
487
- case 11:
488
- _context8.prev = 11;
489
- draining = false;
490
- return _context8.finish(11);
491
769
  case 12:
770
+ _context8.prev = 12;
771
+ clearInterval(watchdog);
772
+ draining = false;
773
+ log('drain:done', {
774
+ runId: myRunId,
775
+ ms: Date.now() - start,
776
+ destroyed: destroyed,
777
+ queueLength: queue.length,
778
+ pendingMarkers: pendingMarkers.size,
779
+ gltfInFlight: gltfTracker.getInFlight()
780
+ });
781
+ return _context8.finish(12);
782
+ case 13:
492
783
  case "end":
493
784
  return _context8.stop();
494
785
  }
495
- }, _callee8, null, [[2,, 11, 12], [7, 9]]);
786
+ }, _callee8, null, [[2,, 12, 13], [8, 10]]);
496
787
  }));
497
788
  return _drain.apply(this, arguments);
498
789
  }
@@ -513,8 +804,14 @@ export function renderKitchenSimulator(container) {
513
804
  value: function componentDidMount() {
514
805
  var _this3 = this;
515
806
  this._mounted = true;
807
+ log('Wrapper mounted');
516
808
  setExternalEventFn = function setExternalEventFn(newEvent) {
517
- if (!_this3._mounted) return;
809
+ if (!_this3._mounted) {
810
+ warn('setExternalEventFn called while unmounted (ignored)');
811
+ return;
812
+ }
813
+ // This is the most important log to see if you’re triggering re-renders endlessly:
814
+ log('Wrapper setState(externalEvent)', summarizeEvent(newEvent));
518
815
  _this3.setState({
519
816
  externalEvent: newEvent
520
817
  });
@@ -523,12 +820,18 @@ export function renderKitchenSimulator(container) {
523
820
  }, {
524
821
  key: "componentWillUnmount",
525
822
  value: function componentWillUnmount() {
823
+ log('Wrapper will unmount');
526
824
  this._mounted = false;
527
825
  setExternalEventFn = null;
528
826
  }
529
827
  }, {
530
828
  key: "render",
531
829
  value: function render() {
830
+ // Render spam can indicate infinite render loop; keep it lightweight
831
+ if (debugEnabled) log('Wrapper render', {
832
+ hasExternalEvent: !!this.state.externalEvent,
833
+ externalEvent: summarizeEvent(this.state.externalEvent)
834
+ });
532
835
  return /*#__PURE__*/React.createElement(LiteRenderer, _extends({}, this.props, {
533
836
  externalEvent: this.state.externalEvent
534
837
  }));
@@ -537,18 +840,40 @@ export function renderKitchenSimulator(container) {
537
840
  }(React.Component);
538
841
  var api = {
539
842
  __render: function __render(nextProps) {
843
+ log('__render called', {
844
+ debug: !!(nextProps !== null && nextProps !== void 0 && nextProps.debug),
845
+ framesPerEvent: nextProps === null || nextProps === void 0 ? void 0 : nextProps.framesPerEvent,
846
+ waitForGltfIdleAfterEachEvent: nextProps === null || nextProps === void 0 ? void 0 : nextProps.waitForGltfIdleAfterEachEvent,
847
+ gltfTimeoutMs: nextProps === null || nextProps === void 0 ? void 0 : nextProps.gltfTimeoutMs
848
+ });
540
849
  root.render(/*#__PURE__*/React.createElement(Wrapper, nextProps));
541
850
  },
542
851
  // ✅ host can query current inFlight
543
852
  getGltfInFlight: function getGltfInFlight() {
544
- return gltfTracker.getInFlight();
853
+ var v = gltfTracker.getInFlight();
854
+ log('getGltfInFlight', v);
855
+ return v;
545
856
  },
546
857
  // ✅ host can subscribe to inFlight changes (loader)
547
858
  subscribeGltfInFlight: function subscribeGltfInFlight(cb) {
548
- return gltfTracker.subscribe(cb);
859
+ log('subscribeGltfInFlight');
860
+ return gltfTracker.subscribe(function (count) {
861
+ if (debugEnabled) log('gltf inFlight changed', count);
862
+ cb(count);
863
+ });
549
864
  },
550
865
  sendExternalEvents: function sendExternalEvents(eventOrEvents) {
866
+ var _ref8 = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {},
867
+ _ref8$timeoutMs = _ref8.timeoutMs,
868
+ timeoutMs = _ref8$timeoutMs === void 0 ? 60000 : _ref8$timeoutMs;
551
869
  var events = Array.isArray(eventOrEvents) ? eventOrEvents : [eventOrEvents];
870
+ var batchId = Math.random().toString(16).slice(2);
871
+ log('sendExternalEvents:enqueue', {
872
+ batchId: batchId,
873
+ count: events.length,
874
+ timeoutMs: timeoutMs,
875
+ events: events.map(summarizeEvent)
876
+ });
552
877
  var _iterator2 = _createForOfIteratorHelper(events),
553
878
  _step2;
554
879
  try {
@@ -567,62 +892,112 @@ export function renderKitchenSimulator(container) {
567
892
  __marker: MARKER,
568
893
  token: token
569
894
  });
895
+ log('sendExternalEvents:marker added', {
896
+ batchId: batchId,
897
+ queueLength: queue.length,
898
+ pendingMarkers: pendingMarkers.size
899
+ });
570
900
  drain();
571
901
 
572
902
  // resolve when marker cleared
573
903
  return new Promise(function (resolve) {
904
+ var start = Date.now();
574
905
  var check = /*#__PURE__*/function () {
575
- var _ref5 = _asyncToGenerator(/*#__PURE__*/_regeneratorRuntime.mark(function _callee6() {
906
+ var _ref9 = _asyncToGenerator(/*#__PURE__*/_regeneratorRuntime.mark(function _callee6() {
907
+ var spins;
576
908
  return _regeneratorRuntime.wrap(function (_context6) {
577
909
  while (1) switch (_context6.prev = _context6.next) {
578
910
  case 0:
911
+ spins = 0;
912
+ case 1:
579
913
  if (destroyed) {
580
- _context6.next = 3;
914
+ _context6.next = 5;
581
915
  break;
582
916
  }
583
- if (!pendingMarkers.has(token)) {
917
+ spins += 1;
918
+ if (pendingMarkers.has(token)) {
584
919
  _context6.next = 2;
585
920
  break;
586
921
  }
587
- _context6.next = 1;
588
- return nextFrame();
589
- case 1:
590
- return _context6.abrupt("continue", 0);
591
- case 2:
922
+ log('sendExternalEvents:resolved', {
923
+ batchId: batchId,
924
+ ms: Date.now() - start,
925
+ spins: spins,
926
+ queueLength: queue.length
927
+ });
592
928
  resolve(true);
593
929
  return _context6.abrupt("return");
594
- case 3:
930
+ case 2:
931
+ if (!(Date.now() - start > timeoutMs)) {
932
+ _context6.next = 3;
933
+ break;
934
+ }
935
+ error('sendExternalEvents timed out', {
936
+ batchId: batchId,
937
+ timeoutMs: timeoutMs,
938
+ ms: Date.now() - start,
939
+ spins: spins,
940
+ queueLength: queue.length,
941
+ pendingMarkers: pendingMarkers.size,
942
+ gltfInFlight: gltfTracker.getInFlight(),
943
+ lastEvents: lastEvents
944
+ });
945
+ pendingMarkers["delete"](token); // fail-open
595
946
  resolve(false);
947
+ return _context6.abrupt("return");
948
+ case 3:
949
+ // Periodic “I might be stuck” hint
950
+ if (debugEnabled && spins % 240 === 0) {
951
+ dumpLoopHint("sendExternalEvents waiting batchId=".concat(batchId));
952
+ }
953
+ _context6.next = 4;
954
+ return nextFrame();
596
955
  case 4:
956
+ _context6.next = 1;
957
+ break;
958
+ case 5:
959
+ warn('sendExternalEvents:destroyed while waiting', {
960
+ batchId: batchId
961
+ });
962
+ resolve(false);
963
+ case 6:
597
964
  case "end":
598
965
  return _context6.stop();
599
966
  }
600
967
  }, _callee6);
601
968
  }));
602
969
  return function check() {
603
- return _ref5.apply(this, arguments);
970
+ return _ref9.apply(this, arguments);
604
971
  };
605
972
  }();
606
973
  check();
607
974
  });
608
975
  },
609
976
  updateExternalEvent: function updateExternalEvent(e) {
977
+ log('updateExternalEvent', summarizeEvent(e));
610
978
  return api.sendExternalEvents(e);
611
979
  },
612
980
  clearQueue: function clearQueue() {
981
+ log('clearQueue', {
982
+ queueLength: queue.length,
983
+ pendingMarkers: pendingMarkers.size
984
+ });
613
985
  queue.length = 0;
614
986
  pendingMarkers.clear();
615
987
  },
616
988
  unmount: function unmount() {
989
+ log('unmount called');
617
990
  destroyed = true;
618
991
  api.clearQueue();
619
992
  gltfTracker.uninstall();
620
993
  var doUnmount = function doUnmount() {
621
994
  try {
995
+ log('root.unmount()');
622
996
  root.unmount();
623
997
  } finally {
624
998
  container[ROOT_KEY] = null;
625
999
  container[API_KEY] = null;
1000
+ log('unmounted + cleared container keys');
626
1001
  }
627
1002
  };
628
1003
  if (typeof queueMicrotask === 'function') queueMicrotask(doUnmount);else setTimeout(doUnmount, 0);
@@ -630,6 +1005,11 @@ export function renderKitchenSimulator(container) {
630
1005
  };
631
1006
  api.__render(props);
632
1007
  container[API_KEY] = api;
1008
+
1009
+ // Helpful: show how to enable debug quickly at runtime
1010
+ if (debugEnabled) {
1011
+ log('Debug enabled. Tip: window.__kitchenSimulatorDebug__ = true (global)');
1012
+ }
633
1013
  return api;
634
1014
  }
635
1015
  export default renderKitchenSimulator;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "kitchen-simulator",
3
- "version": "5.10.8-react.18",
3
+ "version": "5.10.9-react.18",
4
4
  "description": "It is a kitchen simulator (self-contained micro-frontend).",
5
5
  "license": "MIT",
6
6
  "module": "es/index.js",