@seamly/web-ui 22.1.0 → 22.3.0-beta.1

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.
Files changed (66) hide show
  1. package/build/dist/lib/components.js +698 -318
  2. package/build/dist/lib/components.js.map +1 -1
  3. package/build/dist/lib/components.min.js +1 -1
  4. package/build/dist/lib/components.min.js.LICENSE.txt +2 -2
  5. package/build/dist/lib/components.min.js.map +1 -1
  6. package/build/dist/lib/hooks.js +301 -60
  7. package/build/dist/lib/hooks.js.map +1 -1
  8. package/build/dist/lib/hooks.min.js +1 -1
  9. package/build/dist/lib/hooks.min.js.map +1 -1
  10. package/build/dist/lib/index.debug.js +80 -58
  11. package/build/dist/lib/index.debug.js.map +1 -1
  12. package/build/dist/lib/index.debug.min.js +1 -1
  13. package/build/dist/lib/index.debug.min.js.LICENSE.txt +12 -4
  14. package/build/dist/lib/index.debug.min.js.map +1 -1
  15. package/build/dist/lib/index.js +718 -325
  16. package/build/dist/lib/index.js.map +1 -1
  17. package/build/dist/lib/index.min.js +1 -1
  18. package/build/dist/lib/index.min.js.LICENSE.txt +2 -2
  19. package/build/dist/lib/index.min.js.map +1 -1
  20. package/build/dist/lib/standalone.js +803 -348
  21. package/build/dist/lib/standalone.js.map +1 -1
  22. package/build/dist/lib/standalone.min.js +1 -1
  23. package/build/dist/lib/standalone.min.js.LICENSE.txt +1 -1
  24. package/build/dist/lib/standalone.min.js.map +1 -1
  25. package/build/dist/lib/style-guide.js +830 -323
  26. package/build/dist/lib/style-guide.js.map +1 -1
  27. package/build/dist/lib/style-guide.min.js +1 -1
  28. package/build/dist/lib/style-guide.min.js.LICENSE.txt +2 -2
  29. package/build/dist/lib/style-guide.min.js.map +1 -1
  30. package/build/dist/lib/styles-default-implementation.js +1 -1
  31. package/build/dist/lib/styles.css +1 -1
  32. package/build/dist/lib/styles.js +1 -1
  33. package/build/dist/lib/utils.js +783 -360
  34. package/build/dist/lib/utils.js.map +1 -1
  35. package/build/dist/lib/utils.min.js +1 -1
  36. package/build/dist/lib/utils.min.js.LICENSE.txt +1 -1
  37. package/build/dist/lib/utils.min.js.map +1 -1
  38. package/package.json +28 -28
  39. package/src/javascripts/api/errors/seamly-api-error.ts +0 -1
  40. package/src/javascripts/api/index.ts +29 -9
  41. package/src/javascripts/domains/app/actions.ts +8 -3
  42. package/src/javascripts/domains/config/slice.ts +2 -1
  43. package/src/javascripts/domains/forms/selectors.ts +6 -8
  44. package/src/javascripts/domains/forms/slice.ts +1 -1
  45. package/src/javascripts/domains/interrupt/selectors.ts +3 -2
  46. package/src/javascripts/domains/interrupt/slice.ts +2 -0
  47. package/src/javascripts/domains/redux/create-debounced-async-thunk.ts +109 -0
  48. package/src/javascripts/domains/redux/redux.types.ts +2 -1
  49. package/src/javascripts/domains/store/actions.ts +38 -0
  50. package/src/javascripts/domains/translations/components/options-dialog/translation-option.tsx +3 -1
  51. package/src/javascripts/domains/translations/components/options-dialog/translation-options.tsx +62 -35
  52. package/src/javascripts/domains/translations/slice.ts +8 -1
  53. package/src/javascripts/domains/visibility/actions.ts +4 -1
  54. package/src/javascripts/lib/engine/index.tsx +3 -1
  55. package/src/javascripts/style-guide/states.js +65 -1
  56. package/src/javascripts/ui/components/conversation/event/{card-component.js → card-component.tsx} +6 -4
  57. package/src/javascripts/ui/components/conversation/event/event-participant.js +1 -1
  58. package/src/javascripts/ui/components/core/seamly-event-subscriber.ts +14 -30
  59. package/src/javascripts/ui/components/entry/text-entry/hooks.ts +2 -2
  60. package/src/javascripts/ui/components/form-controls/wrapper.tsx +13 -3
  61. package/src/javascripts/ui/components/view/window-view/window-open-button.js +8 -3
  62. package/src/javascripts/ui/hooks/use-session-expired-command.ts +31 -2
  63. package/src/stylesheets/5-components/_input.scss +0 -5
  64. package/src/stylesheets/5-components/_message-count.scss +11 -9
  65. package/src/stylesheets/5-components/_options.scss +2 -2
  66. package/src/stylesheets/5-components/_translation-options.scss +23 -3
@@ -4157,7 +4157,9 @@ module.exports = Object.setPrototypeOf || ('__proto__' in {} ? function () {
4157
4157
  /***/ (function(module, __unused_webpack_exports, __webpack_require__) {
4158
4158
 
4159
4159
  var DESCRIPTORS = __webpack_require__(5746);
4160
+ var fails = __webpack_require__(5981);
4160
4161
  var uncurryThis = __webpack_require__(5329);
4162
+ var objectGetPrototypeOf = __webpack_require__(249);
4161
4163
  var objectKeys = __webpack_require__(4771);
4162
4164
  var toIndexedObject = __webpack_require__(4529);
4163
4165
  var $propertyIsEnumerable = (__webpack_require__(6760).f);
@@ -4165,18 +4167,28 @@ var $propertyIsEnumerable = (__webpack_require__(6760).f);
4165
4167
  var propertyIsEnumerable = uncurryThis($propertyIsEnumerable);
4166
4168
  var push = uncurryThis([].push);
4167
4169
 
4170
+ // in some IE versions, `propertyIsEnumerable` returns incorrect result on integer keys
4171
+ // of `null` prototype objects
4172
+ var IE_BUG = DESCRIPTORS && fails(function () {
4173
+ // eslint-disable-next-line es/no-object-create -- safe
4174
+ var O = Object.create(null);
4175
+ O[2] = 2;
4176
+ return !propertyIsEnumerable(O, 2);
4177
+ });
4178
+
4168
4179
  // `Object.{ entries, values }` methods implementation
4169
4180
  var createMethod = function (TO_ENTRIES) {
4170
4181
  return function (it) {
4171
4182
  var O = toIndexedObject(it);
4172
4183
  var keys = objectKeys(O);
4184
+ var IE_WORKAROUND = IE_BUG && objectGetPrototypeOf(O) === null;
4173
4185
  var length = keys.length;
4174
4186
  var i = 0;
4175
4187
  var result = [];
4176
4188
  var key;
4177
4189
  while (length > i) {
4178
4190
  key = keys[i++];
4179
- if (!DESCRIPTORS || propertyIsEnumerable(O, key)) {
4191
+ if (!DESCRIPTORS || (IE_WORKAROUND ? key in O : propertyIsEnumerable(O, key))) {
4180
4192
  push(result, TO_ENTRIES ? [key, O[key]] : O[key]);
4181
4193
  }
4182
4194
  }
@@ -4553,10 +4565,10 @@ var store = __webpack_require__(3030);
4553
4565
  (module.exports = function (key, value) {
4554
4566
  return store[key] || (store[key] = value !== undefined ? value : {});
4555
4567
  })('versions', []).push({
4556
- version: '3.30.2',
4568
+ version: '3.31.1',
4557
4569
  mode: IS_PURE ? 'pure' : 'global',
4558
4570
  copyright: '© 2014-2023 Denis Pushkarev (zloirock.ru)',
4559
- license: 'https://github.com/zloirock/core-js/blob/v3.30.2/LICENSE',
4571
+ license: 'https://github.com/zloirock/core-js/blob/v3.31.1/LICENSE',
4560
4572
  source: 'https://github.com/zloirock/core-js'
4561
4573
  });
4562
4574
 
@@ -5264,13 +5276,15 @@ module.exports = !fails(function () {
5264
5276
  // eslint-disable-next-line unicorn/relative-url-style -- required for testing
5265
5277
  var url = new URL('b?a=1&b=2&c=3', 'http://a');
5266
5278
  var searchParams = url.searchParams;
5279
+ var searchParams2 = new URLSearchParams('a=1&a=2');
5267
5280
  var result = '';
5268
5281
  url.pathname = 'c%20d';
5269
5282
  searchParams.forEach(function (value, key) {
5270
5283
  searchParams['delete']('b');
5271
5284
  result += key + value;
5272
5285
  });
5273
- return (IS_PURE && !url.toJSON)
5286
+ searchParams2['delete']('a', 2);
5287
+ return (IS_PURE && (!url.toJSON || !searchParams2.has('a', 1) || searchParams2.has('a', 2)))
5274
5288
  || (!searchParams.size && (IS_PURE || !DESCRIPTORS))
5275
5289
  || !searchParams.sort
5276
5290
  || url.href !== 'http://a/c%20d?a=1&c=3'
@@ -7985,7 +7999,7 @@ var URLSearchParamsConstructor = function URLSearchParams(/* init */) {
7985
7999
  anInstance(this, URLSearchParamsPrototype);
7986
8000
  var init = arguments.length > 0 ? arguments[0] : undefined;
7987
8001
  var state = setInternalState(this, new URLSearchParamsState(init));
7988
- if (!DESCRIPTORS) this.length = state.entries.length;
8002
+ if (!DESCRIPTORS) this.size = state.entries.length;
7989
8003
  };
7990
8004
 
7991
8005
  var URLSearchParamsPrototype = URLSearchParamsConstructor.prototype;
@@ -7994,32 +8008,37 @@ defineBuiltIns(URLSearchParamsPrototype, {
7994
8008
  // `URLSearchParams.prototype.append` method
7995
8009
  // https://url.spec.whatwg.org/#dom-urlsearchparams-append
7996
8010
  append: function append(name, value) {
7997
- validateArgumentsLength(arguments.length, 2);
7998
8011
  var state = getInternalParamsState(this);
8012
+ validateArgumentsLength(arguments.length, 2);
7999
8013
  push(state.entries, { key: $toString(name), value: $toString(value) });
8000
8014
  if (!DESCRIPTORS) this.length++;
8001
8015
  state.updateURL();
8002
8016
  },
8003
8017
  // `URLSearchParams.prototype.delete` method
8004
8018
  // https://url.spec.whatwg.org/#dom-urlsearchparams-delete
8005
- 'delete': function (name) {
8006
- validateArgumentsLength(arguments.length, 1);
8019
+ 'delete': function (name /* , value */) {
8007
8020
  var state = getInternalParamsState(this);
8021
+ var length = validateArgumentsLength(arguments.length, 1);
8008
8022
  var entries = state.entries;
8009
8023
  var key = $toString(name);
8024
+ var $value = length < 2 ? undefined : arguments[1];
8025
+ var value = $value === undefined ? $value : $toString($value);
8010
8026
  var index = 0;
8011
8027
  while (index < entries.length) {
8012
- if (entries[index].key === key) splice(entries, index, 1);
8013
- else index++;
8028
+ var entry = entries[index];
8029
+ if (entry.key === key && (value === undefined || entry.value === value)) {
8030
+ splice(entries, index, 1);
8031
+ if (value !== undefined) break;
8032
+ } else index++;
8014
8033
  }
8015
- if (!DESCRIPTORS) this.length = entries.length;
8034
+ if (!DESCRIPTORS) this.size = entries.length;
8016
8035
  state.updateURL();
8017
8036
  },
8018
8037
  // `URLSearchParams.prototype.get` method
8019
8038
  // https://url.spec.whatwg.org/#dom-urlsearchparams-get
8020
8039
  get: function get(name) {
8021
- validateArgumentsLength(arguments.length, 1);
8022
8040
  var entries = getInternalParamsState(this).entries;
8041
+ validateArgumentsLength(arguments.length, 1);
8023
8042
  var key = $toString(name);
8024
8043
  var index = 0;
8025
8044
  for (; index < entries.length; index++) {
@@ -8030,8 +8049,8 @@ defineBuiltIns(URLSearchParamsPrototype, {
8030
8049
  // `URLSearchParams.prototype.getAll` method
8031
8050
  // https://url.spec.whatwg.org/#dom-urlsearchparams-getall
8032
8051
  getAll: function getAll(name) {
8033
- validateArgumentsLength(arguments.length, 1);
8034
8052
  var entries = getInternalParamsState(this).entries;
8053
+ validateArgumentsLength(arguments.length, 1);
8035
8054
  var key = $toString(name);
8036
8055
  var result = [];
8037
8056
  var index = 0;
@@ -8042,21 +8061,24 @@ defineBuiltIns(URLSearchParamsPrototype, {
8042
8061
  },
8043
8062
  // `URLSearchParams.prototype.has` method
8044
8063
  // https://url.spec.whatwg.org/#dom-urlsearchparams-has
8045
- has: function has(name) {
8046
- validateArgumentsLength(arguments.length, 1);
8064
+ has: function has(name /* , value */) {
8047
8065
  var entries = getInternalParamsState(this).entries;
8066
+ var length = validateArgumentsLength(arguments.length, 1);
8048
8067
  var key = $toString(name);
8068
+ var $value = length < 2 ? undefined : arguments[1];
8069
+ var value = $value === undefined ? $value : $toString($value);
8049
8070
  var index = 0;
8050
8071
  while (index < entries.length) {
8051
- if (entries[index++].key === key) return true;
8072
+ var entry = entries[index++];
8073
+ if (entry.key === key && (value === undefined || entry.value === value)) return true;
8052
8074
  }
8053
8075
  return false;
8054
8076
  },
8055
8077
  // `URLSearchParams.prototype.set` method
8056
8078
  // https://url.spec.whatwg.org/#dom-urlsearchparams-set
8057
8079
  set: function set(name, value) {
8058
- validateArgumentsLength(arguments.length, 1);
8059
8080
  var state = getInternalParamsState(this);
8081
+ validateArgumentsLength(arguments.length, 1);
8060
8082
  var entries = state.entries;
8061
8083
  var found = false;
8062
8084
  var key = $toString(name);
@@ -8074,7 +8096,7 @@ defineBuiltIns(URLSearchParamsPrototype, {
8074
8096
  }
8075
8097
  }
8076
8098
  if (!found) push(entries, { key: key, value: val });
8077
- if (!DESCRIPTORS) this.length = entries.length;
8099
+ if (!DESCRIPTORS) this.size = entries.length;
8078
8100
  state.updateURL();
8079
8101
  },
8080
8102
  // `URLSearchParams.prototype.sort` method
@@ -8187,6 +8209,22 @@ module.exports = {
8187
8209
  };
8188
8210
 
8189
8211
 
8212
+ /***/ }),
8213
+
8214
+ /***/ 6454:
8215
+ /***/ (function() {
8216
+
8217
+ // empty
8218
+
8219
+
8220
+ /***/ }),
8221
+
8222
+ /***/ 3305:
8223
+ /***/ (function() {
8224
+
8225
+ // empty
8226
+
8227
+
8190
8228
  /***/ }),
8191
8229
 
8192
8230
  /***/ 5304:
@@ -9699,16 +9737,29 @@ __webpack_require__(7634);
9699
9737
  module.exports = parent;
9700
9738
 
9701
9739
 
9740
+ /***/ }),
9741
+
9742
+ /***/ 7610:
9743
+ /***/ (function(module, __unused_webpack_exports, __webpack_require__) {
9744
+
9745
+ __webpack_require__(5304);
9746
+ __webpack_require__(6454);
9747
+ __webpack_require__(3305);
9748
+ __webpack_require__(2337);
9749
+ var path = __webpack_require__(4058);
9750
+
9751
+ module.exports = path.URLSearchParams;
9752
+
9753
+
9702
9754
  /***/ }),
9703
9755
 
9704
9756
  /***/ 1459:
9705
9757
  /***/ (function(module, __unused_webpack_exports, __webpack_require__) {
9706
9758
 
9759
+ __webpack_require__(7610);
9707
9760
  __webpack_require__(3601);
9708
9761
  __webpack_require__(4630);
9709
9762
  __webpack_require__(8947);
9710
- __webpack_require__(5304);
9711
- __webpack_require__(2337);
9712
9763
  var path = __webpack_require__(4058);
9713
9764
 
9714
9765
  module.exports = path.URL;
@@ -10526,15 +10577,18 @@ var _=0;function o(o,e,n,t,f,l){var s,u,a={};for(u in e)"ref"==u?s=e[u]:a[u]=e[u
10526
10577
  // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/promise.js
10527
10578
  var promise = __webpack_require__(6226);
10528
10579
  var promise_default = /*#__PURE__*/__webpack_require__.n(promise);
10580
+ // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/instance/index-of.js
10581
+ var index_of = __webpack_require__(1882);
10582
+ var index_of_default = /*#__PURE__*/__webpack_require__.n(index_of);
10583
+ // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/object/get-own-property-symbols.js
10584
+ var get_own_property_symbols = __webpack_require__(222);
10585
+ var get_own_property_symbols_default = /*#__PURE__*/__webpack_require__.n(get_own_property_symbols);
10529
10586
  // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/url.js
10530
10587
  var core_js_stable_url = __webpack_require__(3460);
10531
10588
  var url_default = /*#__PURE__*/__webpack_require__.n(core_js_stable_url);
10532
10589
  // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/object/assign.js
10533
10590
  var object_assign = __webpack_require__(6986);
10534
10591
  var assign_default = /*#__PURE__*/__webpack_require__.n(object_assign);
10535
- // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/instance/index-of.js
10536
- var index_of = __webpack_require__(1882);
10537
- var index_of_default = /*#__PURE__*/__webpack_require__.n(index_of);
10538
10592
  // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/json/stringify.js
10539
10593
  var stringify = __webpack_require__(5627);
10540
10594
  var stringify_default = /*#__PURE__*/__webpack_require__.n(stringify);
@@ -12266,6 +12320,7 @@ _ConversationConnector_connectionListeners = new (weak_map_default())(), _Conver
12266
12320
  return !complete;
12267
12321
  }), "f");
12268
12322
  };
12323
+ /* harmony default export */ var conversation_connector = (ConversationConnector);
12269
12324
  ;// CONCATENATED MODULE: ./src/javascripts/api/index.ts
12270
12325
 
12271
12326
 
@@ -12279,6 +12334,7 @@ _ConversationConnector_connectionListeners = new (weak_map_default())(), _Conver
12279
12334
 
12280
12335
 
12281
12336
 
12337
+
12282
12338
  var api_awaiter = undefined && undefined.__awaiter || function (thisArg, _arguments, P, generator) {
12283
12339
  function adopt(value) {
12284
12340
  return value instanceof P ? value : new P(function (resolve) {
@@ -12317,6 +12373,14 @@ var api_classPrivateFieldGet = undefined && undefined.__classPrivateFieldGet ||
12317
12373
  if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
12318
12374
  return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
12319
12375
  };
12376
+ var __rest = undefined && undefined.__rest || function (s, e) {
12377
+ var t = {};
12378
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && index_of_default()(e).call(e, p) < 0) t[p] = s[p];
12379
+ if (s != null && typeof (get_own_property_symbols_default()) === "function") for (var i = 0, p = get_own_property_symbols_default()(s); i < p.length; i++) {
12380
+ if (index_of_default()(e).call(e, p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i])) t[p[i]] = s[p[i]];
12381
+ }
12382
+ return t;
12383
+ };
12320
12384
  var _API_instances, _API_ready, _API_externalId, _API_conversationAuthToken, _API_layoutMode, _API_config, _API_getAccessToken, _API_setAccessToken, _API_setConversationUrl, _API_getChannelTopic, _API_setChannelTopic, _API_getLocale, _API_getUrlPrefix, _API_updateUrls, _API_createConversation, _API_getEnvironment;
12321
12385
 
12322
12386
 
@@ -12405,7 +12469,7 @@ class API {
12405
12469
  _API_conversationAuthToken.set(this, void 0);
12406
12470
  _API_layoutMode.set(this, void 0);
12407
12471
  _API_config.set(this, void 0);
12408
- this.conversation = new ConversationConnector();
12472
+ this.conversation = new conversation_connector();
12409
12473
  _API_getLocale.set(this, locale => locale || this.locale);
12410
12474
  this.store = objectStore(`${namespace}.connection${context.locale ? `.${context.locale}` : ''}`, config.storageProvider || store);
12411
12475
  this.connectionInfo = {
@@ -12435,7 +12499,8 @@ class API {
12435
12499
  });
12436
12500
  }
12437
12501
  getConversationUrl() {
12438
- return this.store.get('conversationUrl');
12502
+ const conversationUrl = this.store.get('conversationUrl');
12503
+ return conversationUrl;
12439
12504
  }
12440
12505
  hasConversation() {
12441
12506
  return !!this.getConversationUrl();
@@ -12544,7 +12609,7 @@ class API {
12544
12609
  if (error.status >= 500) {
12545
12610
  throw new SeamlyGeneralError(error);
12546
12611
  }
12547
- throw error;
12612
+ throw new ApiError(error);
12548
12613
  }
12549
12614
  });
12550
12615
  }
@@ -12654,7 +12719,7 @@ class API {
12654
12719
  if (error.status >= 500) {
12655
12720
  throw new SeamlyGeneralError(error);
12656
12721
  }
12657
- throw error;
12722
+ throw new ApiError(error);
12658
12723
  }
12659
12724
  });
12660
12725
  }
@@ -12682,6 +12747,7 @@ class API {
12682
12747
  this.conversation.pushToChannel(command, buildPayload(command, payload), 10000);
12683
12748
  }
12684
12749
  sendContext(context) {
12750
+ var _a;
12685
12751
  const {
12686
12752
  locale,
12687
12753
  variables
@@ -12703,19 +12769,29 @@ class API {
12703
12769
  if (keys_default()(payload).length === 0 && payload.constructor === Object) {
12704
12770
  return;
12705
12771
  }
12706
- this.send('context', payload, false);
12772
+ // Destructure the server locale from the payload
12773
+ const {
12774
+ locale: _
12775
+ } = payload,
12776
+ restPayload = __rest(payload, ["locale"]);
12777
+ const configLocale = (_a = api_classPrivateFieldGet(this, _API_config, "f").context) === null || _a === void 0 ? void 0 : _a.locale;
12778
+ this.send('context', assign_default()(assign_default()({}, configLocale ? {
12779
+ locale: configLocale
12780
+ } : {}), restPayload), false);
12707
12781
  }
12708
12782
  }
12709
12783
  _API_ready = new (weak_map_default())(), _API_externalId = new (weak_map_default())(), _API_conversationAuthToken = new (weak_map_default())(), _API_layoutMode = new (weak_map_default())(), _API_config = new (weak_map_default())(), _API_getLocale = new (weak_map_default())(), _API_instances = new (weak_set_default())(), _API_getAccessToken = function _API_getAccessToken() {
12710
- return this.store.get('accessToken');
12784
+ const accessToken = this.store.get('accessToken');
12785
+ return accessToken;
12711
12786
  }, _API_setAccessToken = function _API_setAccessToken(accessToken) {
12712
12787
  this.store.set('accessToken', accessToken);
12713
12788
  }, _API_setConversationUrl = function _API_setConversationUrl(url) {
12714
12789
  this.store.set('conversationUrl', url);
12715
12790
  }, _API_getChannelTopic = function _API_getChannelTopic() {
12791
+ const channelTopic = this.store.get('channelTopic') || this.store.get('channelName');
12716
12792
  // The `channelName` fallback is needed for seamless client upgrades.
12717
12793
  // TODO: Remove when all clients have been upgraded past v20.
12718
- return this.store.get('channelTopic') || this.store.get('channelName');
12794
+ return channelTopic;
12719
12795
  }, _API_setChannelTopic = function _API_setChannelTopic(topic) {
12720
12796
  this.store.set('channelTopic', topic);
12721
12797
  }, _API_getUrlPrefix = function _API_getUrlPrefix(protocol) {
@@ -12786,7 +12862,7 @@ _API_ready = new (weak_map_default())(), _API_externalId = new (weak_map_default
12786
12862
  return {
12787
12863
  clientName: "@seamly/web-ui",
12788
12864
  clientVariant: api_classPrivateFieldGet(this, _API_layoutMode, "f"),
12789
- clientVersion: "22.1.0",
12865
+ clientVersion: "22.3.0-beta.1",
12790
12866
  currentUrl: window.location.toString(),
12791
12867
  screenResolution: `${window.screen.width}x${window.screen.height}`,
12792
12868
  timezone: getTimeZone(),
@@ -12820,15 +12896,52 @@ const setBatch = newBatch => batch = newBatch; // Supply a getter just to skip d
12820
12896
  const getBatch = () => batch;
12821
12897
  ;// CONCATENATED MODULE: ./node_modules/react-redux/es/components/Context.js
12822
12898
 
12823
- const Context_ReactReduxContext = /*#__PURE__*/(0,compat_module.createContext)(null);
12899
+ const ContextKey = Symbol.for(`react-redux-context-${compat_module.version}`);
12900
+ const gT = globalThis;
12901
+
12902
+ function getContext() {
12903
+ let realContext = gT[ContextKey];
12904
+
12905
+ if (!realContext) {
12906
+ realContext = (0,compat_module.createContext)(null);
12907
+
12908
+ if (false) {}
12909
+
12910
+ gT[ContextKey] = realContext;
12911
+ }
12912
+
12913
+ return realContext;
12914
+ }
12915
+
12916
+ const Context_ReactReduxContext = /*#__PURE__*/new Proxy({}, /*#__PURE__*/new Proxy({}, {
12917
+ get(_, handler) {
12918
+ const target = getContext(); // @ts-ignore
12824
12919
 
12825
- if (false) {}
12920
+ return (_target, ...args) => Reflect[handler](target, ...args);
12921
+ }
12826
12922
 
12923
+ }));
12827
12924
  /* harmony default export */ var Context = ((/* unused pure expression or super */ null && (Context_ReactReduxContext)));
12828
12925
  ;// CONCATENATED MODULE: ./node_modules/react-redux/es/hooks/useReduxContext.js
12829
12926
 
12830
12927
 
12831
12928
 
12929
+ /**
12930
+ * Hook factory, which creates a `useReduxContext` hook bound to a given context. This is a low-level
12931
+ * hook that you should usually not need to call directly.
12932
+ *
12933
+ * @param {React.Context} [context=ReactReduxContext] Context passed to your `<Provider>`.
12934
+ * @returns {Function} A `useReduxContext` hook bound to the specified context.
12935
+ */
12936
+ function createReduxContextHook(context = Context_ReactReduxContext) {
12937
+ return function useReduxContext() {
12938
+ const contextValue = (0,compat_module.useContext)(context);
12939
+
12940
+ if (false) {}
12941
+
12942
+ return contextValue;
12943
+ };
12944
+ }
12832
12945
  /**
12833
12946
  * A hook to access the value of the `ReactReduxContext`. This is a low-level
12834
12947
  * hook that you should usually not need to call directly.
@@ -12845,13 +12958,8 @@ if (false) {}
12845
12958
  * return <div>{store.getState()}</div>
12846
12959
  * }
12847
12960
  */
12848
- function useReduxContext_useReduxContext() {
12849
- const contextValue = (0,compat_module.useContext)(Context_ReactReduxContext);
12850
-
12851
- if (false) {}
12852
12961
 
12853
- return contextValue;
12854
- }
12962
+ const useReduxContext_useReduxContext = /*#__PURE__*/createReduxContextHook();
12855
12963
  ;// CONCATENATED MODULE: ./node_modules/react-redux/es/utils/useSyncExternalStore.js
12856
12964
  const useSyncExternalStore_notInitialized = () => {
12857
12965
  throw new Error('uSES not initialized!');
@@ -12876,16 +12984,37 @@ const refEquality = (a, b) => a === b;
12876
12984
 
12877
12985
 
12878
12986
  function createSelectorHook(context = Context_ReactReduxContext) {
12879
- const useReduxContext = context === Context_ReactReduxContext ? useReduxContext_useReduxContext : () => (0,compat_module.useContext)(context);
12880
- return function useSelector(selector, equalityFn = refEquality) {
12987
+ const useReduxContext = context === Context_ReactReduxContext ? useReduxContext_useReduxContext : createReduxContextHook(context);
12988
+ return function useSelector(selector, equalityFnOrOptions = {}) {
12989
+ const {
12990
+ equalityFn = refEquality,
12991
+ stabilityCheck = undefined,
12992
+ noopCheck = undefined
12993
+ } = typeof equalityFnOrOptions === 'function' ? {
12994
+ equalityFn: equalityFnOrOptions
12995
+ } : equalityFnOrOptions;
12996
+
12881
12997
  if (false) {}
12882
12998
 
12883
12999
  const {
12884
13000
  store,
12885
13001
  subscription,
12886
- getServerState
13002
+ getServerState,
13003
+ stabilityCheck: globalStabilityCheck,
13004
+ noopCheck: globalNoopCheck
12887
13005
  } = useReduxContext();
12888
- const selectedState = useSyncExternalStoreWithSelector(subscription.addNestedSub, store.getState, getServerState || store.getState, selector, equalityFn);
13006
+ const firstRun = (0,compat_module.useRef)(true);
13007
+ const wrappedSelector = (0,compat_module.useCallback)({
13008
+ [selector.name](state) {
13009
+ const selected = selector(state);
13010
+
13011
+ if (false) {}
13012
+
13013
+ return selected;
13014
+ }
13015
+
13016
+ }[selector.name], [selector, globalStabilityCheck, stabilityCheck]);
13017
+ const selectedState = useSyncExternalStoreWithSelector(subscription.addNestedSub, store.getState, getServerState || store.getState, wrappedSelector, equalityFn);
12889
13018
  (0,compat_module.useDebugValue)(selectedState);
12890
13019
  return selectedState;
12891
13020
  };
@@ -13472,16 +13601,20 @@ function Provider({
13472
13601
  store,
13473
13602
  context,
13474
13603
  children,
13475
- serverState
13604
+ serverState,
13605
+ stabilityCheck = 'once',
13606
+ noopCheck = 'once'
13476
13607
  }) {
13477
13608
  const contextValue = (0,compat_module.useMemo)(() => {
13478
13609
  const subscription = Subscription_createSubscription(store);
13479
13610
  return {
13480
13611
  store,
13481
13612
  subscription,
13482
- getServerState: serverState ? () => serverState : undefined
13613
+ getServerState: serverState ? () => serverState : undefined,
13614
+ stabilityCheck,
13615
+ noopCheck
13483
13616
  };
13484
- }, [store, serverState]);
13617
+ }, [store, serverState, stabilityCheck, noopCheck]);
13485
13618
  const previousState = (0,compat_module.useMemo)(() => store.getState(), [store]);
13486
13619
  useIsomorphicLayoutEffect_useIsomorphicLayoutEffect(() => {
13487
13620
  const {
@@ -13510,7 +13643,6 @@ function Provider({
13510
13643
  ;// CONCATENATED MODULE: ./node_modules/react-redux/es/hooks/useStore.js
13511
13644
 
13512
13645
 
13513
-
13514
13646
  /**
13515
13647
  * Hook factory, which creates a `useStore` hook bound to a given context.
13516
13648
  *
@@ -13520,7 +13652,8 @@ function Provider({
13520
13652
 
13521
13653
  function createStoreHook(context = Context_ReactReduxContext) {
13522
13654
  const useReduxContext = // @ts-ignore
13523
- context === Context_ReactReduxContext ? useReduxContext_useReduxContext : () => (0,compat_module.useContext)(context);
13655
+ context === Context_ReactReduxContext ? useReduxContext_useReduxContext : // @ts-ignore
13656
+ createReduxContextHook(context);
13524
13657
  return function useStore() {
13525
13658
  const {
13526
13659
  store
@@ -16579,6 +16712,64 @@ const setLocale = createAsyncThunk('setLocale', (locale, _ref) => {
16579
16712
  return true;
16580
16713
  }
16581
16714
  });
16715
+ ;// CONCATENATED MODULE: ./src/javascripts/domains/redux/create-debounced-async-thunk.ts
16716
+
16717
+
16718
+
16719
+ /**
16720
+ * A debounced analogue of the `createAsyncThunk` from `@reduxjs/toolkit`
16721
+ * @param typePrefix - a string action type value
16722
+ * @param payloadCreator - a callback function that should return a promise containing the result of some asynchronous logic
16723
+ * @param debounceOptions - the debounce options object
16724
+ */
16725
+ const createDebouncedAsyncThunk = (typePrefix, payloadCreator, debounceOptions) => {
16726
+ const {
16727
+ wait = 300,
16728
+ maxWait = 0,
16729
+ leading = false
16730
+ } = debounceOptions !== null && debounceOptions !== void 0 ? debounceOptions : {};
16731
+ let debounceTimer = null;
16732
+ let maxWaitTimer = null;
16733
+ let resolve;
16734
+ const cancel = () => {
16735
+ if (resolve) {
16736
+ resolve(false);
16737
+ resolve = undefined;
16738
+ }
16739
+ };
16740
+ const invoke = () => {
16741
+ clearTimeout(maxWaitTimer);
16742
+ maxWaitTimer = undefined;
16743
+ if (resolve) {
16744
+ resolve(true);
16745
+ resolve = undefined;
16746
+ }
16747
+ };
16748
+ const debounceExecutionCondition = () => {
16749
+ const immediate = leading && !debounceTimer;
16750
+ // Start debounced condition resolution
16751
+ clearTimeout(debounceTimer);
16752
+ debounceTimer = set_timeout_default()(() => {
16753
+ invoke();
16754
+ debounceTimer = null;
16755
+ }, wait);
16756
+ if (immediate) {
16757
+ return true;
16758
+ }
16759
+ cancel();
16760
+ // Start max wait condition resolution
16761
+ if (maxWait && !maxWaitTimer) {
16762
+ maxWaitTimer = set_timeout_default()(invoke, maxWait);
16763
+ }
16764
+ return new (promise_default())(res => {
16765
+ resolve = res;
16766
+ });
16767
+ };
16768
+ return createAsyncThunk(typePrefix, payloadCreator, {
16769
+ condition: debounceExecutionCondition
16770
+ });
16771
+ };
16772
+ /* harmony default export */ var create_debounced_async_thunk = (createDebouncedAsyncThunk);
16582
16773
  ;// CONCATENATED MODULE: ./node_modules/reselect/es/defaultMemoize.js
16583
16774
  // Cache implementation based on Erik Rasmussen's `lru-memoize`:
16584
16775
  // https://github.com/erikras/lru-memoize
@@ -17164,8 +17355,9 @@ const setVisibility = createAsyncThunk('setVisibility', (requestedVisibility, _r
17164
17355
  if (previousVisibility === calculatedVisibility) {
17165
17356
  return undefined;
17166
17357
  }
17358
+ const visibility = api.store.get(StoreKey);
17167
17359
  // Store the user-requested visibility in order to reinitialize after refresh
17168
- api.store.set(StoreKey, assign_default()(assign_default()({}, api.store.get(StoreKey) || {}), {
17360
+ api.store.set(StoreKey, assign_default()(assign_default()({}, visibility || {}), {
17169
17361
  [layoutMode]: requestedVisibility
17170
17362
  }));
17171
17363
  if (requestedVisibility) {
@@ -17233,6 +17425,7 @@ var app_actions_awaiter = undefined && undefined.__awaiter || function (thisArg,
17233
17425
 
17234
17426
 
17235
17427
 
17428
+
17236
17429
  const initializeApp = createAsyncThunk('initializeApp', (_, _ref) => {
17237
17430
  let {
17238
17431
  extra: {
@@ -17301,7 +17494,7 @@ const initializeApp = createAsyncThunk('initializeApp', (_, _ref) => {
17301
17494
  }
17302
17495
  });
17303
17496
  });
17304
- const resetApp = createAsyncThunk('resetApp', (_, _ref2) => {
17497
+ const resetApp = create_debounced_async_thunk('resetApp', (_, _ref2) => {
17305
17498
  let {
17306
17499
  dispatch,
17307
17500
  extra: {
@@ -17310,7 +17503,7 @@ const resetApp = createAsyncThunk('resetApp', (_, _ref2) => {
17310
17503
  } = _ref2;
17311
17504
  return app_actions_awaiter(void 0, void 0, void 0, function* () {
17312
17505
  yield api.disconnect();
17313
- yield api.clearStore();
17506
+ api.clearStore();
17314
17507
  dispatch(resetConfig());
17315
17508
  yield dispatch(initializeConfig());
17316
17509
  try {
@@ -17318,11 +17511,14 @@ const resetApp = createAsyncThunk('resetApp', (_, _ref2) => {
17318
17511
  locale
17319
17512
  } = yield dispatch(initializeApp()).unwrap();
17320
17513
  yield dispatch(setLocale(locale));
17321
- } catch (rejectedValueOrSerializedError) {
17514
+ } catch (e) {
17322
17515
  // nothing to do
17323
17516
  }
17324
17517
  dispatch(initializeVisibility());
17325
17518
  });
17519
+ }, {
17520
+ wait: 2000,
17521
+ leading: true
17326
17522
  });
17327
17523
  ;// CONCATENATED MODULE: ./src/javascripts/domains/app/hooks.js
17328
17524
 
@@ -17361,12 +17557,80 @@ const {
17361
17557
  setHasResponded
17362
17558
  } = appSlice.actions;
17363
17559
  /* harmony default export */ var app_slice = (appSlice.reducer);
17560
+ ;// CONCATENATED MODULE: ./src/javascripts/domains/store/actions.ts
17561
+
17562
+ var store_actions_awaiter = undefined && undefined.__awaiter || function (thisArg, _arguments, P, generator) {
17563
+ function adopt(value) {
17564
+ return value instanceof P ? value : new P(function (resolve) {
17565
+ resolve(value);
17566
+ });
17567
+ }
17568
+ return new (P || (P = (promise_default())))(function (resolve, reject) {
17569
+ function fulfilled(value) {
17570
+ try {
17571
+ step(generator.next(value));
17572
+ } catch (e) {
17573
+ reject(e);
17574
+ }
17575
+ }
17576
+ function rejected(value) {
17577
+ try {
17578
+ step(generator["throw"](value));
17579
+ } catch (e) {
17580
+ reject(e);
17581
+ }
17582
+ }
17583
+ function step(result) {
17584
+ result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected);
17585
+ }
17586
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
17587
+ });
17588
+ };
17589
+
17590
+ const getConversation = createAsyncThunk('getConversation', (_, _ref) => {
17591
+ let {
17592
+ extra: {
17593
+ api
17594
+ },
17595
+ rejectWithValue
17596
+ } = _ref;
17597
+ return store_actions_awaiter(void 0, void 0, void 0, function* () {
17598
+ try {
17599
+ return api.getConversation();
17600
+ } catch (error) {
17601
+ return rejectWithValue({
17602
+ name: error === null || error === void 0 ? void 0 : error.name,
17603
+ message: error === null || error === void 0 ? void 0 : error.message,
17604
+ langKey: error === null || error === void 0 ? void 0 : error.langKey,
17605
+ action: error === null || error === void 0 ? void 0 : error.action,
17606
+ originalEvent: error === null || error === void 0 ? void 0 : error.originalEvent,
17607
+ originalError: error === null || error === void 0 ? void 0 : error.originalError
17608
+ });
17609
+ }
17610
+ });
17611
+ }, {
17612
+ condition(payload, _ref2) {
17613
+ let {
17614
+ getState
17615
+ } = _ref2;
17616
+ var _a;
17617
+ const {
17618
+ state: {
17619
+ events
17620
+ }
17621
+ } = getState();
17622
+ const lastEvent = events[events.length - 1];
17623
+ const payloadLastEventId = (_a = payload === null || payload === void 0 ? void 0 : payload.lastEvent) === null || _a === void 0 ? void 0 : _a.id;
17624
+ return lastEvent && payloadLastEventId !== lastEvent.payload.id;
17625
+ }
17626
+ });
17364
17627
  ;// CONCATENATED MODULE: ./src/javascripts/domains/interrupt/slice.ts
17365
17628
 
17366
17629
 
17367
17630
 
17368
17631
 
17369
17632
 
17633
+
17370
17634
  const slice_initialState = {
17371
17635
  error: undefined
17372
17636
  };
@@ -17380,7 +17644,7 @@ const interruptSlice = createSlice({
17380
17644
  clearInterrupt: () => slice_initialState
17381
17645
  },
17382
17646
  extraReducers: builder => {
17383
- builder.addCase(initializeConfig.pending, () => slice_initialState).addMatcher(isAnyOf(initializeApp.rejected, initializeConfig.rejected, setLocale.rejected, setVisibility.rejected, initializeVisibility.rejected), (state, _ref) => {
17647
+ builder.addCase(initializeConfig.pending, () => slice_initialState).addMatcher(isAnyOf(initializeApp.rejected, initializeConfig.rejected, setLocale.rejected, setVisibility.rejected, initializeVisibility.rejected, getConversation.rejected), (state, _ref) => {
17384
17648
  let {
17385
17649
  payload
17386
17650
  } = _ref;
@@ -18086,16 +18350,13 @@ const {
18086
18350
  // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/instance/concat.js
18087
18351
  var concat = __webpack_require__(9022);
18088
18352
  var concat_default = /*#__PURE__*/__webpack_require__.n(concat);
18089
- // EXTERNAL MODULE: ./node_modules/@babel/runtime-corejs3/core-js-stable/object/get-own-property-symbols.js
18090
- var get_own_property_symbols = __webpack_require__(222);
18091
- var get_own_property_symbols_default = /*#__PURE__*/__webpack_require__.n(get_own_property_symbols);
18092
18353
  ;// CONCATENATED MODULE: ./src/javascripts/domains/config/slice.ts
18093
18354
 
18094
18355
 
18095
18356
 
18096
18357
 
18097
18358
 
18098
- var __rest = undefined && undefined.__rest || function (s, e) {
18359
+ var slice_rest = undefined && undefined.__rest || function (s, e) {
18099
18360
  var t = {};
18100
18361
  for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && index_of_default()(e).call(e, p) < 0) t[p] = s[p];
18101
18362
  if (s != null && typeof (get_own_property_symbols_default()) === "function") for (var i = 0, p = get_own_property_symbols_default()(s); i < p.length; i++) {
@@ -18138,7 +18399,7 @@ const updateState = (state, config) => {
18138
18399
  {
18139
18400
  messages
18140
18401
  } = _a,
18141
- partialConfig = __rest(_a, ["messages"]);
18402
+ partialConfig = slice_rest(_a, ["messages"]);
18142
18403
  let newState = state;
18143
18404
  if (keys_default()(partialConfig).length > 0) {
18144
18405
  newState = assign_default()(assign_default()({}, newState), partialConfig);
@@ -18180,13 +18441,15 @@ const configSlice = createSlice({
18180
18441
  preChat,
18181
18442
  agentParticipant,
18182
18443
  userParticipant,
18183
- startChatIcon
18444
+ startChatIcon,
18445
+ locale
18184
18446
  }
18185
18447
  } = _ref4;
18186
18448
  state.preChatEvents = map_default()(preChat).call(preChat, payload => ({
18187
18449
  type: 'message',
18188
18450
  payload
18189
18451
  }));
18452
+ state.context.locale = locale;
18190
18453
  state.agentParticipant = agentParticipant;
18191
18454
  state.userParticipant = userParticipant;
18192
18455
  state.startChatIcon = startChatIcon;
@@ -18586,6 +18849,7 @@ var splice_default = /*#__PURE__*/__webpack_require__.n(splice);
18586
18849
 
18587
18850
 
18588
18851
 
18852
+
18589
18853
  const translationsInitialState = {
18590
18854
  isActive: false,
18591
18855
  currentLocale: undefined,
@@ -18685,6 +18949,7 @@ const translationSlice = createSlice({
18685
18949
  },
18686
18950
  extraReducers: builder => {
18687
18951
  builder.addCase(resetApp.pending, () => translationsInitialState).addCase(initializeConfig.fulfilled, (state, _ref6) => {
18952
+ var _context3;
18688
18953
  let {
18689
18954
  payload
18690
18955
  } = _ref6;
@@ -18692,7 +18957,13 @@ const translationSlice = createSlice({
18692
18957
  const feature = (_a = payload === null || payload === void 0 ? void 0 : payload.features) === null || _a === void 0 ? void 0 : _a.translation;
18693
18958
  if (!feature) return;
18694
18959
  state.isAvailable = feature.enabled === true;
18695
- state.languages = feature.languages;
18960
+ state.languages = sort_default()(_context3 = [...feature.languages]).call(_context3, (a, b) => {
18961
+ if (a.locale === payload.locale) return -1;
18962
+ if (b.locale === payload.locale) return 1;
18963
+ return a.nativeName.localeCompare(b.nativeName, undefined, {
18964
+ sensitivity: 'base'
18965
+ });
18966
+ });
18696
18967
  }).addCase(setHistory, (state, _ref7) => {
18697
18968
  let {
18698
18969
  payload
@@ -19956,6 +20227,10 @@ function useInterrupt() {
19956
20227
 
19957
20228
 
19958
20229
 
20230
+
20231
+
20232
+
20233
+
19959
20234
  function useSessionExpiredCommand() {
19960
20235
  const {
19961
20236
  meta: {
@@ -19963,13 +20238,35 @@ function useSessionExpiredCommand() {
19963
20238
  action
19964
20239
  }
19965
20240
  } = useInterrupt();
20241
+ const dispatch = useAppDispatch();
19966
20242
  const seamlyCommands = use_seamly_commands();
19967
20243
  const isExpiredError = (originalError === null || originalError === void 0 ? void 0 : originalError.name) === 'SeamlySessionExpiredError';
20244
+ const limit = (0,hooks_module/* useRef */.sO)(0);
20245
+ const limitTimer = (0,hooks_module/* useRef */.sO)(null);
19968
20246
  (0,hooks_module/* useEffect */.d4)(() => {
19969
20247
  if (isExpiredError && seamlyCommands[action]) {
20248
+ if (limit.current >= 10) {
20249
+ limitTimer.current = set_timeout_default()(() => {
20250
+ limit.current = 0;
20251
+ }, 10000);
20252
+ const error = new SeamlyGeneralError();
20253
+ dispatch(setInterrupt({
20254
+ name: error.name,
20255
+ message: error.message,
20256
+ langKey: error.langKey,
20257
+ originalEvent: error.originalEvent,
20258
+ originalError: error.originalError,
20259
+ action: error.action
20260
+ }));
20261
+ return () => {};
20262
+ }
20263
+ limit.current += 1;
19970
20264
  seamlyCommands[action]();
19971
20265
  }
19972
- }, [action, seamlyCommands, isExpiredError]);
20266
+ return () => {
20267
+ if (limitTimer.current) clearTimeout(limitTimer.current);
20268
+ };
20269
+ }, [action, seamlyCommands, isExpiredError, dispatch]);
19973
20270
  }
19974
20271
  ;// CONCATENATED MODULE: ./src/javascripts/ui/hooks/use-seamly-chat.ts
19975
20272
 
@@ -20850,7 +21147,7 @@ const EventParticipant = _ref => {
20850
21147
  })
20851
21148
  }));
20852
21149
  }
20853
- if (showName) {
21150
+ if (showName && participantName) {
20854
21151
  authorInfo.push(o("span", {
20855
21152
  className: css_className('message__author-name'),
20856
21153
  children: participantName
@@ -20934,109 +21231,61 @@ function MessageContainer(_ref) {
20934
21231
  });
20935
21232
  }
20936
21233
  /* harmony default export */ var message_container = (MessageContainer);
20937
- ;// CONCATENATED MODULE: ./src/javascripts/ui/components/conversation/event/card-component.js
20938
-
21234
+ ;// CONCATENATED MODULE: ./src/javascripts/ui/components/conversation/event/card-component.tsx
20939
21235
 
20940
21236
 
20941
21237
 
20942
21238
 
20943
21239
 
20944
- const CardComponent = _ref => {
20945
- let {
20946
- id,
20947
- action,
20948
- buttonText,
20949
- description,
20950
- hasFocus,
20951
- image,
20952
- title,
20953
- isCarouselItem
20954
- } = _ref;
20955
- const cardRef = (0,hooks_module/* useRef */.sO)(null);
20956
- const {
20957
- sendMessage,
20958
- sendAction,
20959
- emitEvent
20960
- } = use_seamly_commands();
20961
- const descriptionId = useGeneratedId();
20962
- const isMounted = (0,hooks_module/* useRef */.sO)();
20963
- const CardActionComponent = action.type === cardTypes.navigate ? 'a' : 'button';
20964
- const emitCardEvent = (0,hooks_module/* useCallback */.I4)(() => emitEvent(`action.${actionTypes.clickCard}`, {
20965
- type: actionTypes.clickCta,
20966
- originMessage: id,
20967
- action
20968
- }), [emitEvent, id, action]);
20969
- const handleClick = (0,hooks_module/* useCallback */.I4)(() => {
20970
- emitCardEvent();
20971
- if (action.type === cardTypes.ask) {
20972
- sendMessage({
20973
- body: action.ask
20974
- });
20975
- } else if (action.type === cardTypes.topic) {
20976
- const {
20977
- topic: name,
20978
- fallbackMessage
20979
- } = action;
20980
- sendAction({
20981
- type: actionTypes.setTopic,
20982
- body: {
20983
- name,
20984
- fallbackMessage
21240
+ const CardComponent = ({ id, action, buttonText, description, hasFocus, image, title, isCarouselItem, }) => {
21241
+ const cardRef = (0,hooks_module/* useRef */.sO)(null);
21242
+ const { sendMessage, sendAction, emitEvent } = use_seamly_commands();
21243
+ const descriptionId = useGeneratedId();
21244
+ const isMounted = (0,hooks_module/* useRef */.sO)(false);
21245
+ const CardActionComponent = action.type === cardTypes.navigate ? 'a' : 'button';
21246
+ const emitCardEvent = (0,hooks_module/* useCallback */.I4)(() => emitEvent(`action.${actionTypes.clickCard}`, {
21247
+ type: actionTypes.clickCta,
21248
+ originMessage: id,
21249
+ action,
21250
+ }), [emitEvent, id, action]);
21251
+ const handleClick = (0,hooks_module/* useCallback */.I4)(() => {
21252
+ emitCardEvent();
21253
+ if (action.type === cardTypes.ask) {
21254
+ sendMessage({ body: action.ask });
20985
21255
  }
20986
- });
20987
- }
20988
- }, [sendMessage, action, sendAction, emitCardEvent]);
20989
- const actionProps = (0,hooks_module/* useMemo */.Ye)(() => action.type === cardTypes.navigate ? {
20990
- href: action.link,
20991
- rel: 'noopener noreferrer',
20992
- target: action.newTab ? '_blank' : '_self',
20993
- onClick: emitCardEvent
20994
- } : {
20995
- onClick: handleClick
20996
- }, [action, handleClick, emitCardEvent]);
20997
- (0,hooks_module/* useEffect */.d4)(() => {
20998
- if (isCarouselItem) {
20999
- if (hasFocus && isMounted.current) {
21000
- window.requestAnimationFrame(() => cardRef.current.focus());
21001
- } else {
21002
- cardRef.current.blur();
21003
- }
21004
- }
21005
- isMounted.current = true;
21006
- }, [hasFocus, isCarouselItem]);
21007
- return o("div", {
21008
- className: css_className('card__wrapper'),
21009
- id: id,
21010
- tabIndex: "-1" // set tabIndex of -1 so card can be focussed
21011
- ,
21012
- ref: cardRef,
21013
- children: [o("img", {
21014
- className: css_className('card__image'),
21015
- src: image,
21016
- alt: ""
21017
- }), o("div", {
21018
- className: css_className('card__content'),
21019
- id: id,
21020
- children: [title && o("h2", {
21021
- className: css_className('card__title'),
21022
- children: title
21023
- }), description && o("div", {
21024
- className: css_className('card__description'),
21025
- dangerouslySetInnerHTML: {
21026
- __html: description
21256
+ else if (action.type === cardTypes.topic) {
21257
+ const { topic: name, fallbackMessage } = action;
21258
+ sendAction({
21259
+ type: actionTypes.setTopic,
21260
+ body: { name, fallbackMessage },
21261
+ });
21027
21262
  }
21028
- }), o(CardActionComponent, {
21029
- tabIndex: isCarouselItem && !hasFocus ? '-1' : undefined // disable to prevent tabbing through cards
21030
- ,
21031
- className: css_className('button', 'button--primary'),
21032
- "aria-describedby": descriptionId,
21033
- ...actionProps,
21034
- children: buttonText
21035
- })]
21036
- })]
21037
- });
21263
+ }, [sendMessage, action, sendAction, emitCardEvent]);
21264
+ const actionProps = (0,hooks_module/* useMemo */.Ye)(() => action.type === cardTypes.navigate
21265
+ ? {
21266
+ href: action.link,
21267
+ rel: 'noopener noreferrer',
21268
+ target: action.newTab ? '_blank' : '_self',
21269
+ onClick: emitCardEvent,
21270
+ }
21271
+ : {
21272
+ onClick: handleClick,
21273
+ }, [action, handleClick, emitCardEvent]);
21274
+ (0,hooks_module/* useEffect */.d4)(() => {
21275
+ if (isCarouselItem) {
21276
+ if (hasFocus && isMounted.current) {
21277
+ window.requestAnimationFrame(() => cardRef.current.focus());
21278
+ }
21279
+ else {
21280
+ cardRef.current.blur();
21281
+ }
21282
+ }
21283
+ isMounted.current = true;
21284
+ }, [hasFocus, isCarouselItem]);
21285
+ return (o("div", { className: css_className('card__wrapper'), id: id, tabIndex: -1, ref: cardRef, children: [image ? (o("img", { className: css_className('card__image'), src: image, alt: "" })) : null, o("div", { className: css_className('card__content'), id: id, children: [title && o("h2", { className: css_className('card__title'), children: title }), description && (o("div", { className: css_className('card__description'), dangerouslySetInnerHTML: { __html: description } })), o(CardActionComponent, Object.assign({ tabIndex: isCarouselItem && !hasFocus ? -1 : undefined, className: css_className('button', 'button--primary'), "aria-describedby": descriptionId }, actionProps, { children: buttonText }))] })] }));
21038
21286
  };
21039
21287
  /* harmony default export */ var card_component = (CardComponent);
21288
+
21040
21289
  ;// CONCATENATED MODULE: ./src/javascripts/ui/components/conversation/event/card-message.js
21041
21290
 
21042
21291
 
@@ -22095,7 +22344,7 @@ const TimeIndicator = _ref => {
22095
22344
  /* harmony default export */ var time_indicator = (TimeIndicator);
22096
22345
  ;// CONCATENATED MODULE: ./node_modules/tabbable/dist/index.esm.js
22097
22346
  /*!
22098
- * tabbable 6.1.2
22347
+ * tabbable 6.2.0
22099
22348
  * @license MIT, https://github.com/focus-trap/tabbable/blob/master/LICENSE
22100
22349
  */
22101
22350
  // NOTE: separate `:not()` selectors has broader browser support than the newer
@@ -22275,7 +22524,27 @@ var getCandidatesIteratively = function getCandidatesIteratively(elements, inclu
22275
22524
  }
22276
22525
  return candidates;
22277
22526
  };
22278
- var getTabindex = function getTabindex(node, isScope) {
22527
+
22528
+ /**
22529
+ * @private
22530
+ * Determines if the node has an explicitly specified `tabindex` attribute.
22531
+ * @param {HTMLElement} node
22532
+ * @returns {boolean} True if so; false if not.
22533
+ */
22534
+ var hasTabIndex = function hasTabIndex(node) {
22535
+ return !isNaN(parseInt(node.getAttribute('tabindex'), 10));
22536
+ };
22537
+
22538
+ /**
22539
+ * Determine the tab index of a given node.
22540
+ * @param {HTMLElement} node
22541
+ * @returns {number} Tab order (negative, 0, or positive number).
22542
+ * @throws {Error} If `node` is falsy.
22543
+ */
22544
+ var getTabIndex = function getTabIndex(node) {
22545
+ if (!node) {
22546
+ throw new Error('No node provided');
22547
+ }
22279
22548
  if (node.tabIndex < 0) {
22280
22549
  // in Chrome, <details/>, <audio controls/> and <video controls/> elements get a default
22281
22550
  // `tabIndex` of -1 when the 'tabindex' attribute isn't specified in the DOM,
@@ -22284,16 +22553,28 @@ var getTabindex = function getTabindex(node, isScope) {
22284
22553
  // order, consider their tab index to be 0.
22285
22554
  // Also browsers do not return `tabIndex` correctly for contentEditable nodes;
22286
22555
  // so if they don't have a tabindex attribute specifically set, assume it's 0.
22287
- //
22288
- // isScope is positive for custom element with shadow root or slot that by default
22289
- // have tabIndex -1, but need to be sorted by document order in order for their
22290
- // content to be inserted in the correct position
22291
- if ((isScope || /^(AUDIO|VIDEO|DETAILS)$/.test(node.tagName) || isContentEditable(node)) && isNaN(parseInt(node.getAttribute('tabindex'), 10))) {
22556
+ if ((/^(AUDIO|VIDEO|DETAILS)$/.test(node.tagName) || isContentEditable(node)) && !hasTabIndex(node)) {
22292
22557
  return 0;
22293
22558
  }
22294
22559
  }
22295
22560
  return node.tabIndex;
22296
22561
  };
22562
+
22563
+ /**
22564
+ * Determine the tab index of a given node __for sort order purposes__.
22565
+ * @param {HTMLElement} node
22566
+ * @param {boolean} [isScope] True for a custom element with shadow root or slot that, by default,
22567
+ * has tabIndex -1, but needs to be sorted by document order in order for its content to be
22568
+ * inserted into the correct sort position.
22569
+ * @returns {number} Tab order (negative, 0, or positive number).
22570
+ */
22571
+ var getSortOrderTabIndex = function getSortOrderTabIndex(node, isScope) {
22572
+ var tabIndex = getTabIndex(node);
22573
+ if (tabIndex < 0 && isScope && !hasTabIndex(node)) {
22574
+ return 0;
22575
+ }
22576
+ return tabIndex;
22577
+ };
22297
22578
  var sortOrderedTabbables = function sortOrderedTabbables(a, b) {
22298
22579
  return a.tabIndex === b.tabIndex ? a.documentOrder - b.documentOrder : a.tabIndex - b.tabIndex;
22299
22580
  };
@@ -22536,7 +22817,7 @@ var isNodeMatchingSelectorFocusable = function isNodeMatchingSelectorFocusable(o
22536
22817
  return true;
22537
22818
  };
22538
22819
  var isNodeMatchingSelectorTabbable = function isNodeMatchingSelectorTabbable(options, node) {
22539
- if (isNonTabbableRadio(node) || getTabindex(node) < 0 || !isNodeMatchingSelectorFocusable(options, node)) {
22820
+ if (isNonTabbableRadio(node) || getTabIndex(node) < 0 || !isNodeMatchingSelectorFocusable(options, node)) {
22540
22821
  return false;
22541
22822
  }
22542
22823
  return true;
@@ -22561,7 +22842,7 @@ var sortByOrder = function sortByOrder(candidates) {
22561
22842
  candidates.forEach(function (item, i) {
22562
22843
  var isScope = !!item.scopeParent;
22563
22844
  var element = isScope ? item.scopeParent : item;
22564
- var candidateTabindex = getTabindex(element, isScope);
22845
+ var candidateTabindex = getSortOrderTabIndex(element, isScope);
22565
22846
  var elements = isScope ? sortByOrder(item.candidates) : element;
22566
22847
  if (candidateTabindex === 0) {
22567
22848
  isScope ? regularTabbables.push.apply(regularTabbables, elements) : regularTabbables.push(element);
@@ -22580,32 +22861,32 @@ var sortByOrder = function sortByOrder(candidates) {
22580
22861
  return acc;
22581
22862
  }, []).concat(regularTabbables);
22582
22863
  };
22583
- var tabbable = function tabbable(el, options) {
22864
+ var tabbable = function tabbable(container, options) {
22584
22865
  options = options || {};
22585
22866
  var candidates;
22586
22867
  if (options.getShadowRoot) {
22587
- candidates = getCandidatesIteratively([el], options.includeContainer, {
22868
+ candidates = getCandidatesIteratively([container], options.includeContainer, {
22588
22869
  filter: isNodeMatchingSelectorTabbable.bind(null, options),
22589
22870
  flatten: false,
22590
22871
  getShadowRoot: options.getShadowRoot,
22591
22872
  shadowRootFilter: isValidShadowRootTabbable
22592
22873
  });
22593
22874
  } else {
22594
- candidates = getCandidates(el, options.includeContainer, isNodeMatchingSelectorTabbable.bind(null, options));
22875
+ candidates = getCandidates(container, options.includeContainer, isNodeMatchingSelectorTabbable.bind(null, options));
22595
22876
  }
22596
22877
  return sortByOrder(candidates);
22597
22878
  };
22598
- var focusable = function focusable(el, options) {
22879
+ var focusable = function focusable(container, options) {
22599
22880
  options = options || {};
22600
22881
  var candidates;
22601
22882
  if (options.getShadowRoot) {
22602
- candidates = getCandidatesIteratively([el], options.includeContainer, {
22883
+ candidates = getCandidatesIteratively([container], options.includeContainer, {
22603
22884
  filter: isNodeMatchingSelectorFocusable.bind(null, options),
22604
22885
  flatten: true,
22605
22886
  getShadowRoot: options.getShadowRoot
22606
22887
  });
22607
22888
  } else {
22608
- candidates = getCandidates(el, options.includeContainer, isNodeMatchingSelectorFocusable.bind(null, options));
22889
+ candidates = getCandidates(container, options.includeContainer, isNodeMatchingSelectorFocusable.bind(null, options));
22609
22890
  }
22610
22891
  return candidates;
22611
22892
  };
@@ -22636,7 +22917,7 @@ var isFocusable = function isFocusable(node, options) {
22636
22917
 
22637
22918
  ;// CONCATENATED MODULE: ./node_modules/focus-trap/dist/focus-trap.esm.js
22638
22919
  /*!
22639
- * focus-trap 7.4.3
22920
+ * focus-trap 7.5.2
22640
22921
  * @license MIT, https://github.com/focus-trap/focus-trap/blob/master/LICENSE
22641
22922
  */
22642
22923
 
@@ -22722,10 +23003,10 @@ var isSelectableInput = function isSelectableInput(node) {
22722
23003
  return node.tagName && node.tagName.toLowerCase() === 'input' && typeof node.select === 'function';
22723
23004
  };
22724
23005
  var isEscapeEvent = function isEscapeEvent(e) {
22725
- return e.key === 'Escape' || e.key === 'Esc' || e.keyCode === 27;
23006
+ return (e === null || e === void 0 ? void 0 : e.key) === 'Escape' || (e === null || e === void 0 ? void 0 : e.key) === 'Esc' || (e === null || e === void 0 ? void 0 : e.keyCode) === 27;
22726
23007
  };
22727
23008
  var isTabEvent = function isTabEvent(e) {
22728
- return e.key === 'Tab' || e.keyCode === 9;
23009
+ return (e === null || e === void 0 ? void 0 : e.key) === 'Tab' || (e === null || e === void 0 ? void 0 : e.keyCode) === 9;
22729
23010
  };
22730
23011
 
22731
23012
  // checks for TAB by default
@@ -22809,8 +23090,11 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
22809
23090
  // container: HTMLElement,
22810
23091
  // tabbableNodes: Array<HTMLElement>, // empty if none
22811
23092
  // focusableNodes: Array<HTMLElement>, // empty if none
22812
- // firstTabbableNode: HTMLElement|null,
22813
- // lastTabbableNode: HTMLElement|null,
23093
+ // posTabIndexesFound: boolean,
23094
+ // firstTabbableNode: HTMLElement|undefined,
23095
+ // lastTabbableNode: HTMLElement|undefined,
23096
+ // firstDomTabbableNode: HTMLElement|undefined,
23097
+ // lastDomTabbableNode: HTMLElement|undefined,
22814
23098
  // nextTabbableNode: (node: HTMLElement, forward: boolean) => HTMLElement|undefined
22815
23099
  // }>}
22816
23100
  containerGroups: [],
@@ -22827,7 +23111,9 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
22827
23111
  paused: false,
22828
23112
  // timer ID for when delayInitialFocus is true and initial focus in this trap
22829
23113
  // has been delayed during activation
22830
- delayInitialFocusTimer: undefined
23114
+ delayInitialFocusTimer: undefined,
23115
+ // the most recent KeyboardEvent for the configured nav key (typically [SHIFT+]TAB), if any
23116
+ recentNavEvent: undefined
22831
23117
  };
22832
23118
  var trap; // eslint-disable-line prefer-const -- some private functions reference it, and its methods reference private functions, so we must declare here and define later
22833
23119
 
@@ -22846,7 +23132,9 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
22846
23132
  /**
22847
23133
  * Finds the index of the container that contains the element.
22848
23134
  * @param {HTMLElement} element
22849
- * @param {Event} [event]
23135
+ * @param {Event} [event] If available, and `element` isn't directly found in any container,
23136
+ * the event's composed path is used to see if includes any known trap containers in the
23137
+ * case where the element is inside a Shadow DOM.
22850
23138
  * @returns {number} Index of the container in either `state.containers` or
22851
23139
  * `state.containerGroups` (the order/length of these lists are the same); -1
22852
23140
  * if the element isn't found.
@@ -22941,14 +23229,41 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
22941
23229
  var tabbableNodes = tabbable(container, config.tabbableOptions);
22942
23230
 
22943
23231
  // NOTE: if we have tabbable nodes, we must have focusable nodes; focusable nodes
22944
- // are a superset of tabbable nodes
23232
+ // are a superset of tabbable nodes since nodes with negative `tabindex` attributes
23233
+ // are focusable but not tabbable
22945
23234
  var focusableNodes = focusable(container, config.tabbableOptions);
23235
+ var firstTabbableNode = tabbableNodes.length > 0 ? tabbableNodes[0] : undefined;
23236
+ var lastTabbableNode = tabbableNodes.length > 0 ? tabbableNodes[tabbableNodes.length - 1] : undefined;
23237
+ var firstDomTabbableNode = focusableNodes.find(function (node) {
23238
+ return isTabbable(node);
23239
+ });
23240
+ var lastDomTabbableNode = focusableNodes.slice().reverse().find(function (node) {
23241
+ return isTabbable(node);
23242
+ });
23243
+ var posTabIndexesFound = !!tabbableNodes.find(function (node) {
23244
+ return getTabIndex(node) > 0;
23245
+ });
22946
23246
  return {
22947
23247
  container: container,
22948
23248
  tabbableNodes: tabbableNodes,
22949
23249
  focusableNodes: focusableNodes,
22950
- firstTabbableNode: tabbableNodes.length > 0 ? tabbableNodes[0] : null,
22951
- lastTabbableNode: tabbableNodes.length > 0 ? tabbableNodes[tabbableNodes.length - 1] : null,
23250
+ /** True if at least one node with positive `tabindex` was found in this container. */
23251
+ posTabIndexesFound: posTabIndexesFound,
23252
+ /** First tabbable node in container, __tabindex__ order; `undefined` if none. */
23253
+ firstTabbableNode: firstTabbableNode,
23254
+ /** Last tabbable node in container, __tabindex__ order; `undefined` if none. */
23255
+ lastTabbableNode: lastTabbableNode,
23256
+ // NOTE: DOM order is NOT NECESSARILY "document position" order, but figuring that out
23257
+ // would require more than just https://developer.mozilla.org/en-US/docs/Web/API/Node/compareDocumentPosition
23258
+ // because that API doesn't work with Shadow DOM as well as it should (@see
23259
+ // https://github.com/whatwg/dom/issues/320) and since this first/last is only needed, so far,
23260
+ // to address an edge case related to positive tabindex support, this seems like a much easier,
23261
+ // "close enough most of the time" alternative for positive tabindexes which should generally
23262
+ // be avoided anyway...
23263
+ /** First tabbable node in container, __DOM__ order; `undefined` if none. */
23264
+ firstDomTabbableNode: firstDomTabbableNode,
23265
+ /** Last tabbable node in container, __DOM__ order; `undefined` if none. */
23266
+ lastDomTabbableNode: lastDomTabbableNode,
22952
23267
  /**
22953
23268
  * Finds the __tabbable__ node that follows the given node in the specified direction,
22954
23269
  * in this container, if any.
@@ -22959,30 +23274,24 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
22959
23274
  */
22960
23275
  nextTabbableNode: function nextTabbableNode(node) {
22961
23276
  var forward = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : true;
22962
- // NOTE: If tabindex is positive (in order to manipulate the tab order separate
22963
- // from the DOM order), this __will not work__ because the list of focusableNodes,
22964
- // while it contains tabbable nodes, does not sort its nodes in any order other
22965
- // than DOM order, because it can't: Where would you place focusable (but not
22966
- // tabbable) nodes in that order? They have no order, because they aren't tabbale...
22967
- // Support for positive tabindex is already broken and hard to manage (possibly
22968
- // not supportable, TBD), so this isn't going to make things worse than they
22969
- // already are, and at least makes things better for the majority of cases where
22970
- // tabindex is either 0/unset or negative.
22971
- // FYI, positive tabindex issue: https://github.com/focus-trap/focus-trap/issues/375
22972
- var nodeIdx = focusableNodes.findIndex(function (n) {
22973
- return n === node;
22974
- });
23277
+ var nodeIdx = tabbableNodes.indexOf(node);
22975
23278
  if (nodeIdx < 0) {
22976
- return undefined;
22977
- }
22978
- if (forward) {
22979
- return focusableNodes.slice(nodeIdx + 1).find(function (n) {
22980
- return isTabbable(n, config.tabbableOptions);
23279
+ // either not tabbable nor focusable, or was focused but not tabbable (negative tabindex):
23280
+ // since `node` should at least have been focusable, we assume that's the case and mimic
23281
+ // what browsers do, which is set focus to the next node in __document position order__,
23282
+ // regardless of positive tabindexes, if any -- and for reasons explained in the NOTE
23283
+ // above related to `firstDomTabbable` and `lastDomTabbable` properties, we fall back to
23284
+ // basic DOM order
23285
+ if (forward) {
23286
+ return focusableNodes.slice(focusableNodes.indexOf(node) + 1).find(function (el) {
23287
+ return isTabbable(el);
23288
+ });
23289
+ }
23290
+ return focusableNodes.slice(0, focusableNodes.indexOf(node)).reverse().find(function (el) {
23291
+ return isTabbable(el);
22981
23292
  });
22982
23293
  }
22983
- return focusableNodes.slice(0, nodeIdx).reverse().find(function (n) {
22984
- return isTabbable(n, config.tabbableOptions);
22985
- });
23294
+ return tabbableNodes[nodeIdx + (forward ? 1 : -1)];
22986
23295
  }
22987
23296
  };
22988
23297
  });
@@ -22995,6 +23304,19 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
22995
23304
  ) {
22996
23305
  throw new Error('Your focus-trap must have at least one container with at least one tabbable node in it at all times');
22997
23306
  }
23307
+
23308
+ // NOTE: Positive tabindexes are only properly supported in single-container traps because
23309
+ // doing it across multiple containers where tabindexes could be all over the place
23310
+ // would require Tabbable to support multiple containers, would require additional
23311
+ // specialized Shadow DOM support, and would require Tabbable's multi-container support
23312
+ // to look at those containers in document position order rather than user-provided
23313
+ // order (as they are treated in Focus-trap, for legacy reasons). See discussion on
23314
+ // https://github.com/focus-trap/focus-trap/issues/375 for more details.
23315
+ if (state.containerGroups.find(function (g) {
23316
+ return g.posTabIndexesFound;
23317
+ }) && state.containerGroups.length > 1) {
23318
+ throw new Error("At least one node with a positive tabindex was found in one of your focus-trap's multiple containers. Positive tabindexes are only supported in single-container focus-traps.");
23319
+ }
22998
23320
  };
22999
23321
  var tryFocus = function tryFocus(node) {
23000
23322
  if (node === false) {
@@ -23010,6 +23332,7 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
23010
23332
  node.focus({
23011
23333
  preventScroll: !!config.preventScroll
23012
23334
  });
23335
+ // NOTE: focus() API does not trigger focusIn event so set MRU node manually
23013
23336
  state.mostRecentlyFocusedNode = node;
23014
23337
  if (isSelectableInput(node)) {
23015
23338
  node.select();
@@ -23020,64 +23343,23 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
23020
23343
  return node ? node : node === false ? false : previousActiveElement;
23021
23344
  };
23022
23345
 
23023
- // This needs to be done on mousedown and touchstart instead of click
23024
- // so that it precedes the focus event.
23025
- var checkPointerDown = function checkPointerDown(e) {
23026
- var target = getActualTarget(e);
23027
- if (findContainerIndex(target, e) >= 0) {
23028
- // allow the click since it ocurred inside the trap
23029
- return;
23030
- }
23031
- if (valueOrHandler(config.clickOutsideDeactivates, e)) {
23032
- // immediately deactivate the trap
23033
- trap.deactivate({
23034
- // NOTE: by setting `returnFocus: false`, deactivate() will do nothing,
23035
- // which will result in the outside click setting focus to the node
23036
- // that was clicked (and if not focusable, to "nothing"); by setting
23037
- // `returnFocus: true`, we'll attempt to re-focus the node originally-focused
23038
- // on activation (or the configured `setReturnFocus` node), whether the
23039
- // outside click was on a focusable node or not
23040
- returnFocus: config.returnFocusOnDeactivate
23041
- });
23042
- return;
23043
- }
23044
-
23045
- // This is needed for mobile devices.
23046
- // (If we'll only let `click` events through,
23047
- // then on mobile they will be blocked anyways if `touchstart` is blocked.)
23048
- if (valueOrHandler(config.allowOutsideClick, e)) {
23049
- // allow the click outside the trap to take place
23050
- return;
23051
- }
23052
-
23053
- // otherwise, prevent the click
23054
- e.preventDefault();
23055
- };
23056
-
23057
- // In case focus escapes the trap for some strange reason, pull it back in.
23058
- var checkFocusIn = function checkFocusIn(e) {
23059
- var target = getActualTarget(e);
23060
- var targetContained = findContainerIndex(target, e) >= 0;
23061
-
23062
- // In Firefox when you Tab out of an iframe the Document is briefly focused.
23063
- if (targetContained || target instanceof Document) {
23064
- if (targetContained) {
23065
- state.mostRecentlyFocusedNode = target;
23066
- }
23067
- } else {
23068
- // escaped! pull it back in to where it just left
23069
- e.stopImmediatePropagation();
23070
- tryFocus(state.mostRecentlyFocusedNode || getInitialFocusNode());
23071
- }
23072
- };
23073
-
23074
- // Hijack key nav events on the first and last focusable nodes of the trap,
23075
- // in order to prevent focus from escaping. If it escapes for even a
23076
- // moment it can end up scrolling the page and causing confusion so we
23077
- // kind of need to capture the action at the keydown phase.
23078
- var checkKeyNav = function checkKeyNav(event) {
23079
- var isBackward = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false;
23080
- var target = getActualTarget(event);
23346
+ /**
23347
+ * Finds the next node (in either direction) where focus should move according to a
23348
+ * keyboard focus-in event.
23349
+ * @param {Object} params
23350
+ * @param {Node} [params.target] Known target __from which__ to navigate, if any.
23351
+ * @param {KeyboardEvent|FocusEvent} [params.event] Event to use if `target` isn't known (event
23352
+ * will be used to determine the `target`). Ignored if `target` is specified.
23353
+ * @param {boolean} [params.isBackward] True if focus should move backward.
23354
+ * @returns {Node|undefined} The next node, or `undefined` if a next node couldn't be
23355
+ * determined given the current state of the trap.
23356
+ */
23357
+ var findNextNavNode = function findNextNavNode(_ref2) {
23358
+ var target = _ref2.target,
23359
+ event = _ref2.event,
23360
+ _ref2$isBackward = _ref2.isBackward,
23361
+ isBackward = _ref2$isBackward === void 0 ? false : _ref2$isBackward;
23362
+ target = target || getActualTarget(event);
23081
23363
  updateTabbableNodes();
23082
23364
  var destinationNode = null;
23083
23365
  if (state.tabbableGroups.length > 0) {
@@ -23100,8 +23382,8 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
23100
23382
  // REVERSE
23101
23383
 
23102
23384
  // is the target the first tabbable node in a group?
23103
- var startOfGroupIndex = findIndex(state.tabbableGroups, function (_ref2) {
23104
- var firstTabbableNode = _ref2.firstTabbableNode;
23385
+ var startOfGroupIndex = findIndex(state.tabbableGroups, function (_ref3) {
23386
+ var firstTabbableNode = _ref3.firstTabbableNode;
23105
23387
  return target === firstTabbableNode;
23106
23388
  });
23107
23389
  if (startOfGroupIndex < 0 && (containerGroup.container === target || isFocusable(target, config.tabbableOptions) && !isTabbable(target, config.tabbableOptions) && !containerGroup.nextTabbableNode(target, false))) {
@@ -23119,7 +23401,7 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
23119
23401
  // the LAST group if it's the first tabbable node of the FIRST group)
23120
23402
  var destinationGroupIndex = startOfGroupIndex === 0 ? state.tabbableGroups.length - 1 : startOfGroupIndex - 1;
23121
23403
  var destinationGroup = state.tabbableGroups[destinationGroupIndex];
23122
- destinationNode = destinationGroup.lastTabbableNode;
23404
+ destinationNode = getTabIndex(target) >= 0 ? destinationGroup.lastTabbableNode : destinationGroup.lastDomTabbableNode;
23123
23405
  } else if (!isTabEvent(event)) {
23124
23406
  // user must have customized the nav keys so we have to move focus manually _within_
23125
23407
  // the active group: do this based on the order determined by tabbable()
@@ -23129,8 +23411,8 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
23129
23411
  // FORWARD
23130
23412
 
23131
23413
  // is the target the last tabbable node in a group?
23132
- var lastOfGroupIndex = findIndex(state.tabbableGroups, function (_ref3) {
23133
- var lastTabbableNode = _ref3.lastTabbableNode;
23414
+ var lastOfGroupIndex = findIndex(state.tabbableGroups, function (_ref4) {
23415
+ var lastTabbableNode = _ref4.lastTabbableNode;
23134
23416
  return target === lastTabbableNode;
23135
23417
  });
23136
23418
  if (lastOfGroupIndex < 0 && (containerGroup.container === target || isFocusable(target, config.tabbableOptions) && !isTabbable(target, config.tabbableOptions) && !containerGroup.nextTabbableNode(target))) {
@@ -23148,7 +23430,7 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
23148
23430
  // group if it's the last tabbable node of the LAST group)
23149
23431
  var _destinationGroupIndex = lastOfGroupIndex === state.tabbableGroups.length - 1 ? 0 : lastOfGroupIndex + 1;
23150
23432
  var _destinationGroup = state.tabbableGroups[_destinationGroupIndex];
23151
- destinationNode = _destinationGroup.firstTabbableNode;
23433
+ destinationNode = getTabIndex(target) >= 0 ? _destinationGroup.firstTabbableNode : _destinationGroup.firstDomTabbableNode;
23152
23434
  } else if (!isTabEvent(event)) {
23153
23435
  // user must have customized the nav keys so we have to move focus manually _within_
23154
23436
  // the active group: do this based on the order determined by tabbable()
@@ -23160,6 +23442,153 @@ var createFocusTrap = function createFocusTrap(elements, userOptions) {
23160
23442
  // NOTE: the fallbackFocus option does not support returning false to opt-out
23161
23443
  destinationNode = getNodeForOption('fallbackFocus');
23162
23444
  }
23445
+ return destinationNode;
23446
+ };
23447
+
23448
+ // This needs to be done on mousedown and touchstart instead of click
23449
+ // so that it precedes the focus event.
23450
+ var checkPointerDown = function checkPointerDown(e) {
23451
+ var target = getActualTarget(e);
23452
+ if (findContainerIndex(target, e) >= 0) {
23453
+ // allow the click since it ocurred inside the trap
23454
+ return;
23455
+ }
23456
+ if (valueOrHandler(config.clickOutsideDeactivates, e)) {
23457
+ // immediately deactivate the trap
23458
+ trap.deactivate({
23459
+ // NOTE: by setting `returnFocus: false`, deactivate() will do nothing,
23460
+ // which will result in the outside click setting focus to the node
23461
+ // that was clicked (and if not focusable, to "nothing"); by setting
23462
+ // `returnFocus: true`, we'll attempt to re-focus the node originally-focused
23463
+ // on activation (or the configured `setReturnFocus` node), whether the
23464
+ // outside click was on a focusable node or not
23465
+ returnFocus: config.returnFocusOnDeactivate
23466
+ });
23467
+ return;
23468
+ }
23469
+
23470
+ // This is needed for mobile devices.
23471
+ // (If we'll only let `click` events through,
23472
+ // then on mobile they will be blocked anyways if `touchstart` is blocked.)
23473
+ if (valueOrHandler(config.allowOutsideClick, e)) {
23474
+ // allow the click outside the trap to take place
23475
+ return;
23476
+ }
23477
+
23478
+ // otherwise, prevent the click
23479
+ e.preventDefault();
23480
+ };
23481
+
23482
+ // In case focus escapes the trap for some strange reason, pull it back in.
23483
+ // NOTE: the focusIn event is NOT cancelable, so if focus escapes, it may cause unexpected
23484
+ // scrolling if the node that got focused was out of view; there's nothing we can do to
23485
+ // prevent that from happening by the time we discover that focus escaped
23486
+ var checkFocusIn = function checkFocusIn(event) {
23487
+ var target = getActualTarget(event);
23488
+ var targetContained = findContainerIndex(target, event) >= 0;
23489
+
23490
+ // In Firefox when you Tab out of an iframe the Document is briefly focused.
23491
+ if (targetContained || target instanceof Document) {
23492
+ if (targetContained) {
23493
+ state.mostRecentlyFocusedNode = target;
23494
+ }
23495
+ } else {
23496
+ // escaped! pull it back in to where it just left
23497
+ event.stopImmediatePropagation();
23498
+
23499
+ // focus will escape if the MRU node had a positive tab index and user tried to nav forward;
23500
+ // it will also escape if the MRU node had a 0 tab index and user tried to nav backward
23501
+ // toward a node with a positive tab index
23502
+ var nextNode; // next node to focus, if we find one
23503
+ var navAcrossContainers = true;
23504
+ if (state.mostRecentlyFocusedNode) {
23505
+ if (getTabIndex(state.mostRecentlyFocusedNode) > 0) {
23506
+ // MRU container index must be >=0 otherwise we wouldn't have it as an MRU node...
23507
+ var mruContainerIdx = findContainerIndex(state.mostRecentlyFocusedNode);
23508
+ // there MAY not be any tabbable nodes in the container if there are at least 2 containers
23509
+ // and the MRU node is focusable but not tabbable (focus-trap requires at least 1 container
23510
+ // with at least one tabbable node in order to function, so this could be the other container
23511
+ // with nothing tabbable in it)
23512
+ var tabbableNodes = state.containerGroups[mruContainerIdx].tabbableNodes;
23513
+ if (tabbableNodes.length > 0) {
23514
+ // MRU tab index MAY not be found if the MRU node is focusable but not tabbable
23515
+ var mruTabIdx = tabbableNodes.findIndex(function (node) {
23516
+ return node === state.mostRecentlyFocusedNode;
23517
+ });
23518
+ if (mruTabIdx >= 0) {
23519
+ if (config.isKeyForward(state.recentNavEvent)) {
23520
+ if (mruTabIdx + 1 < tabbableNodes.length) {
23521
+ nextNode = tabbableNodes[mruTabIdx + 1];
23522
+ navAcrossContainers = false;
23523
+ }
23524
+ // else, don't wrap within the container as focus should move to next/previous
23525
+ // container
23526
+ } else {
23527
+ if (mruTabIdx - 1 >= 0) {
23528
+ nextNode = tabbableNodes[mruTabIdx - 1];
23529
+ navAcrossContainers = false;
23530
+ }
23531
+ // else, don't wrap within the container as focus should move to next/previous
23532
+ // container
23533
+ }
23534
+ // else, don't find in container order without considering direction too
23535
+ }
23536
+ }
23537
+ // else, no tabbable nodes in that container (which means we must have at least one other
23538
+ // container with at least one tabbable node in it, otherwise focus-trap would've thrown
23539
+ // an error the last time updateTabbableNodes() was run): find next node among all known
23540
+ // containers
23541
+ } else {
23542
+ // check to see if there's at least one tabbable node with a positive tab index inside
23543
+ // the trap because focus seems to escape when navigating backward from a tabbable node
23544
+ // with tabindex=0 when this is the case (instead of wrapping to the tabbable node with
23545
+ // the greatest positive tab index like it should)
23546
+ if (!state.containerGroups.some(function (g) {
23547
+ return g.tabbableNodes.some(function (n) {
23548
+ return getTabIndex(n) > 0;
23549
+ });
23550
+ })) {
23551
+ // no containers with tabbable nodes with positive tab indexes which means the focus
23552
+ // escaped for some other reason and we should just execute the fallback to the
23553
+ // MRU node or initial focus node, if any
23554
+ navAcrossContainers = false;
23555
+ }
23556
+ }
23557
+ } else {
23558
+ // no MRU node means we're likely in some initial condition when the trap has just
23559
+ // been activated and initial focus hasn't been given yet, in which case we should
23560
+ // fall through to trying to focus the initial focus node, which is what should
23561
+ // happen below at this point in the logic
23562
+ navAcrossContainers = false;
23563
+ }
23564
+ if (navAcrossContainers) {
23565
+ nextNode = findNextNavNode({
23566
+ // move FROM the MRU node, not event-related node (which will be the node that is
23567
+ // outside the trap causing the focus escape we're trying to fix)
23568
+ target: state.mostRecentlyFocusedNode,
23569
+ isBackward: config.isKeyBackward(state.recentNavEvent)
23570
+ });
23571
+ }
23572
+ if (nextNode) {
23573
+ tryFocus(nextNode);
23574
+ } else {
23575
+ tryFocus(state.mostRecentlyFocusedNode || getInitialFocusNode());
23576
+ }
23577
+ }
23578
+ state.recentNavEvent = undefined; // clear
23579
+ };
23580
+
23581
+ // Hijack key nav events on the first and last focusable nodes of the trap,
23582
+ // in order to prevent focus from escaping. If it escapes for even a
23583
+ // moment it can end up scrolling the page and causing confusion so we
23584
+ // kind of need to capture the action at the keydown phase.
23585
+ var checkKeyNav = function checkKeyNav(event) {
23586
+ var isBackward = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false;
23587
+ state.recentNavEvent = event;
23588
+ var destinationNode = findNextNavNode({
23589
+ event: event,
23590
+ isBackward: isBackward
23591
+ });
23163
23592
  if (destinationNode) {
23164
23593
  if (isTabEvent(event)) {
23165
23594
  // since tab natively moves focus, we wouldn't have a destination node unless we
@@ -24073,7 +24502,7 @@ const SeamlyActivityMonitor = ({ children }) => {
24073
24502
  // It is important to use keyUp here as focus may be set from outside the
24074
24503
  // chat container via keyboard. In this case the keyDown handler would not
24075
24504
  // be fired inside the container on the initial focus event.
24076
- return (o("div", Object.assign({ className: css_className('activity-monitor'), tabIndex: -1, onMouseDown: onActivityHandler, onKeyUp: onActivityHandler, onTouchStart: onActivityHandler, onMouseMove: onActivityHandler, onWheel: onActivityHandler, onPointerDown: onActivityHandler, onPointerMove: onActivityHandler }, { children: o(seamly_activity_event_context.Provider, Object.assign({ value: onActivityHandler }, { children: children })) })));
24505
+ return (o("div", { className: css_className('activity-monitor'), tabIndex: -1, onMouseDown: onActivityHandler, onKeyUp: onActivityHandler, onTouchStart: onActivityHandler, onMouseMove: onActivityHandler, onWheel: onActivityHandler, onPointerDown: onActivityHandler, onPointerMove: onActivityHandler, children: o(seamly_activity_event_context.Provider, { value: onActivityHandler, children: children }) }));
24077
24506
  };
24078
24507
  /* harmony default export */ var seamly_activity_monitor = (SeamlyActivityMonitor);
24079
24508
 
@@ -24081,6 +24510,34 @@ const SeamlyActivityMonitor = ({ children }) => {
24081
24510
 
24082
24511
 
24083
24512
 
24513
+
24514
+ var seamly_event_subscriber_awaiter = undefined && undefined.__awaiter || function (thisArg, _arguments, P, generator) {
24515
+ function adopt(value) {
24516
+ return value instanceof P ? value : new P(function (resolve) {
24517
+ resolve(value);
24518
+ });
24519
+ }
24520
+ return new (P || (P = (promise_default())))(function (resolve, reject) {
24521
+ function fulfilled(value) {
24522
+ try {
24523
+ step(generator.next(value));
24524
+ } catch (e) {
24525
+ reject(e);
24526
+ }
24527
+ }
24528
+ function rejected(value) {
24529
+ try {
24530
+ step(generator["throw"](value));
24531
+ } catch (e) {
24532
+ reject(e);
24533
+ }
24534
+ }
24535
+ function step(result) {
24536
+ result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected);
24537
+ }
24538
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
24539
+ });
24540
+ };
24084
24541
  var seamly_event_subscriber_rest = undefined && undefined.__rest || function (s, e) {
24085
24542
  var t = {};
24086
24543
  for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && index_of_default()(e).call(e, p) < 0) t[p] = s[p];
@@ -24101,13 +24558,13 @@ var seamly_event_subscriber_rest = undefined && undefined.__rest || function (s,
24101
24558
 
24102
24559
 
24103
24560
 
24561
+
24104
24562
  const EMITTABLE_MESSAGE_TYPES = ['text', 'choice_prompt', 'image', 'video'];
24105
24563
  const SeamlyEventSubscriber = () => {
24106
24564
  const api = useSeamlyApiContext();
24107
24565
  const syncChannelRef = (0,hooks_module/* useRef */.sO)();
24108
24566
  const messageChannelRef = (0,hooks_module/* useRef */.sO)();
24109
- const dispatch = useDispatch();
24110
- const events = useEvents();
24567
+ const dispatch = useAppDispatch();
24111
24568
  const eventBus = (0,hooks_module/* useContext */.qp)(SeamlyEventBusContext);
24112
24569
  const prevEmittedEventId = (0,hooks_module/* useRef */.sO)(null);
24113
24570
  const {
@@ -24356,31 +24813,19 @@ const SeamlyEventSubscriber = () => {
24356
24813
  if (syncChannelRef.current) {
24357
24814
  (_a = api.conversation.channel) === null || _a === void 0 ? void 0 : _a.off('sync', syncChannelRef.current);
24358
24815
  }
24359
- syncChannelRef.current = api.conversation.channel.on('sync', payload => {
24360
- var _a;
24361
- const lastEvent = events[events.length - 1];
24362
- const payloadLastEventId = (_a = payload === null || payload === void 0 ? void 0 : payload.lastEvent) === null || _a === void 0 ? void 0 : _a.id;
24363
- if (lastEvent && payloadLastEventId === lastEvent.payload.id) {
24364
- return payload;
24365
- }
24366
- return api.getConversation().then(history => {
24816
+ syncChannelRef.current = api.conversation.channel.on('sync', payload => seamly_event_subscriber_awaiter(void 0, void 0, void 0, function* () {
24817
+ try {
24818
+ const history = yield dispatch(getConversation(payload)).unwrap();
24367
24819
  if (!history) return;
24368
24820
  dispatch(setHistory(history));
24369
- }).catch(error => {
24370
- dispatch(setInterrupt({
24371
- name: error === null || error === void 0 ? void 0 : error.name,
24372
- message: error === null || error === void 0 ? void 0 : error.message,
24373
- langKey: error === null || error === void 0 ? void 0 : error.langKey,
24374
- action: error === null || error === void 0 ? void 0 : error.action,
24375
- originalEvent: error === null || error === void 0 ? void 0 : error.originalEvent,
24376
- originalError: error === null || error === void 0 ? void 0 : error.originalError
24377
- }));
24378
- });
24379
- });
24821
+ } catch (_e) {
24822
+ // nothing to do, the error is handled in the thunk
24823
+ }
24824
+ }));
24380
24825
  return true;
24381
24826
  });
24382
24827
  }
24383
- }, [api, api.connectionInfo, api.conversation.channel, events, dispatch]);
24828
+ }, [api, api.connectionInfo, api.conversation.channel, dispatch]);
24384
24829
  return null;
24385
24830
  };
24386
24831
  /* harmony default export */ var seamly_event_subscriber = (SeamlyEventSubscriber);
@@ -24487,7 +24932,7 @@ const SeamlyFileUpload = ({ children }) => {
24487
24932
  uploadHandle,
24488
24933
  }));
24489
24934
  }, [addImageToSessionStorage, addUploadBubble, api, dispatch, t]);
24490
- return (o(seamly_file_upload_context.Provider, Object.assign({ value: onUploadFileHandler }, { children: children })));
24935
+ return (o(seamly_file_upload_context.Provider, { value: onUploadFileHandler, children: children }));
24491
24936
  };
24492
24937
  /* harmony default export */ var seamly_file_upload = (SeamlyFileUpload);
24493
24938
 
@@ -24901,7 +25346,7 @@ const SeamlyCore = ({ store, children, eventBus, api }) => {
24901
25346
  (0,hooks_module/* useErrorBoundary */.cO)((error) => {
24902
25347
  store.dispatch(catchError(error));
24903
25348
  });
24904
- return (o(components_Provider, Object.assign({ store: store }, { children: o(SeamlyEventBusContext.Provider, Object.assign({ value: eventBus }, { children: o(SeamlyApiContext.Provider, Object.assign({ value: api }, { children: o(seamly_live_region, { children: o(seamly_chat, { children: o(component_filter, { children: [o(seamly_initializer, {}), o(seamly_event_subscriber, {}), o(seamly_read_state, {}), o(seamly_new_notifications, {}), o(seamly_idle_detach_counter, {}), o(seamly_activity_monitor, { children: [o(seamly_instance_functions_loader, {}), o(seamly_file_upload, { children: children })] })] }) }) }) })) })) })));
25349
+ return (o(components_Provider, { store: store, children: o(SeamlyEventBusContext.Provider, { value: eventBus, children: o(SeamlyApiContext.Provider, { value: api, children: o(seamly_live_region, { children: o(seamly_chat, { children: o(component_filter, { children: [o(seamly_initializer, {}), o(seamly_event_subscriber, {}), o(seamly_read_state, {}), o(seamly_new_notifications, {}), o(seamly_idle_detach_counter, {}), o(seamly_activity_monitor, { children: [o(seamly_instance_functions_loader, {}), o(seamly_file_upload, { children: children })] })] }) }) }) }) }) }));
24905
25350
  };
24906
25351
  /* harmony default export */ var seamly_core = (SeamlyCore);
24907
25352
 
@@ -24969,12 +25414,12 @@ const getState = _ref => {
24969
25414
  } = _ref;
24970
25415
  return forms;
24971
25416
  };
24972
- const getFormById = es_createSelector(getState, (_, _ref2) => {
25417
+ const getFormById = es_createSelector([getState, (_, _ref2) => {
24973
25418
  let {
24974
25419
  formId
24975
25420
  } = _ref2;
24976
25421
  return formId;
24977
- }, (forms, formId) => forms[formId]);
25422
+ }], (forms, formId) => forms[formId]);
24978
25423
  const getFormControlsByFormId = es_createSelector(getFormById, form => (form === null || form === void 0 ? void 0 : form.controls) || {});
24979
25424
  const getFormValuesByFormId = es_createSelector(getFormControlsByFormId, controls => {
24980
25425
  var _context;
@@ -24987,21 +25432,21 @@ const getFormValuesByFormId = es_createSelector(getFormControlsByFormId, control
24987
25432
  });
24988
25433
  return valuesObj;
24989
25434
  });
24990
- const getControlValueByName = es_createSelector(getFormControlsByFormId, (_, _ref4) => {
25435
+ const getControlValueByName = es_createSelector([getFormControlsByFormId, (_, _ref4) => {
24991
25436
  let {
24992
25437
  name
24993
25438
  } = _ref4;
24994
25439
  return name;
24995
- }, (controls, name) => {
25440
+ }], (controls, name) => {
24996
25441
  var _a;
24997
25442
  return (_a = controls[name]) === null || _a === void 0 ? void 0 : _a.value;
24998
25443
  });
24999
- const getControlTouchedByName = es_createSelector(getFormControlsByFormId, (_, _ref5) => {
25444
+ const getControlTouchedByName = es_createSelector([getFormControlsByFormId, (_, _ref5) => {
25000
25445
  let {
25001
25446
  name
25002
25447
  } = _ref5;
25003
25448
  return name;
25004
- }, (controls, name) => {
25449
+ }], (controls, name) => {
25005
25450
  var _a;
25006
25451
  return (_a = controls[name]) === null || _a === void 0 ? void 0 : _a.touched;
25007
25452
  });
@@ -25203,7 +25648,7 @@ const useEntryTextTranslation = controlName => {
25203
25648
  text: (text === null || text === void 0 ? void 0 : text.label) || t('input.inputLabelText'),
25204
25649
  limit: !(text === null || text === void 0 ? void 0 : text.label) && hasCharacterLimit ? characterLimit : null
25205
25650
  }), [t, hasCharacterLimit, characterLimit, text === null || text === void 0 ? void 0 : text.label]);
25206
- const labelClass = (0,hooks_module/* useMemo */.Ye)(() => (text === null || text === void 0 ? void 0 : text.label) ? 'input__label' : 'visually-hidden', [text === null || text === void 0 ? void 0 : text.label]);
25651
+ const labelClass = (0,hooks_module/* useMemo */.Ye)(() => (text === null || text === void 0 ? void 0 : text.label) ? 'label' : 'visually-hidden', [text === null || text === void 0 ? void 0 : text.label]);
25207
25652
  return {
25208
25653
  placeholder,
25209
25654
  label,
@@ -25248,14 +25693,14 @@ function AbortTransactionButton() {
25248
25693
  });
25249
25694
  clearEntryAbortTransaction();
25250
25695
  };
25251
- return (o("li", Object.assign({ className: css_className([
25696
+ return (o("li", { className: css_className([
25252
25697
  'cvco-conversation__item',
25253
25698
  'cvco-conversation__item--abort-transaction',
25254
- ]) }, { children: o("button", Object.assign({ className: css_className([
25699
+ ]), children: o("button", { className: css_className([
25255
25700
  'button',
25256
25701
  'button--secondary',
25257
25702
  'abort-transaction__button',
25258
- ]), type: "button", onClick: handleAbortTransaction }, { children: abortTransaction.label })) })));
25703
+ ]), type: "button", onClick: handleAbortTransaction, children: abortTransaction.label }) }));
25259
25704
  }
25260
25705
 
25261
25706
  ;// CONCATENATED MODULE: ./src/javascripts/ui/components/conversation/event/chat-scroll/chat-scroll-context.ts
@@ -25328,7 +25773,7 @@ const Event = ({ event, newParticipant }) => {
25328
25773
  if (newParticipant) {
25329
25774
  classNames.push('conversation__item--new-participant');
25330
25775
  }
25331
- return (o("li", Object.assign({ className: css_className(classNames), ref: containerRef }, { children: [event.timeIndicator && o(time_indicator, { event: event }), o(Component, Object.assign({ event: event }, { children: o(SubComponent, { event: event }) }))] })));
25776
+ return (o("li", { className: css_className(classNames), ref: containerRef, children: [event.timeIndicator && o(time_indicator, { event: event }), o(Component, { event: event, children: o(SubComponent, { event: event }) })] }));
25332
25777
  };
25333
25778
  /* harmony default export */ var event_event = (Event);
25334
25779
 
@@ -25413,7 +25858,7 @@ const Conversation = () => {
25413
25858
  e.preventDefault();
25414
25859
  focusSkiplinkTarget();
25415
25860
  };
25416
- return (o(preact_module/* Fragment */.HY, { children: [isOpen && (o("a", Object.assign({ className: css_className('skip-link'), href: `#${skiplinkTargetId}`, onClick: onClickHandler }, { children: t('skiplinkText') }))), o("div", Object.assign({ className: css_className('chat__body') }, { children: o("div", Object.assign({ className: css_className('conversation__container') }, { children: [o(privacy_disclaimer, {}), o("ol", Object.assign({ className: css_className('conversation') }, { children: [o(component_filter, { children: o(Events, {}) }), debouncedIsLoading ? o(loader, {}) : null, o(AbortTransactionButton, {})] }))] })) }))] }));
25861
+ return (o(preact_module/* Fragment */.HY, { children: [isOpen && (o("a", { className: css_className('skip-link'), href: `#${skiplinkTargetId}`, onClick: onClickHandler, children: t('skiplinkText') })), o("div", { className: css_className('chat__body'), children: o("div", { className: css_className('conversation__container'), children: [o(privacy_disclaimer, {}), o("ol", { className: css_className('conversation'), children: [o(component_filter, { children: o(Events, {}) }), debouncedIsLoading ? o(loader, {}) : null, o(AbortTransactionButton, {})] })] }) })] }));
25417
25862
  };
25418
25863
  /* harmony default export */ var conversation = (Conversation);
25419
25864
 
@@ -25819,16 +26264,16 @@ const OptionsFrame = ({ className: givenClassName, children, onCancel, headingTe
25819
26264
  (0,hooks_module/* useEffect */.d4)(() => {
25820
26265
  focusElement(container.current);
25821
26266
  }, [container]);
25822
- return (o("section", Object.assign({ className: css_className('options', {
26267
+ return (o("section", { className: css_className('options', {
25823
26268
  'options--right': position.horizontal === 'right',
25824
26269
  'options--left': position.horizontal === 'left',
25825
26270
  'options--top': position.vertical === 'top',
25826
26271
  'options--bottom': position.vertical === 'bottom',
25827
- }, givenClassName), "aria-labelledby": mainHeadingId, tabIndex: -1, ref: container }, { children: o("div", Object.assign({ className: css_className('options__body') }, { children: [o("h2", Object.assign({ id: mainHeadingId, className: css_className('options__title') }, { children: headingText })), o("button", Object.assign({ type: "button", onClick: onCancelHandler, "aria-describedby": mainHeadingId, className: css_className('button', 'options__close'), ref: (btn) => {
26272
+ }, givenClassName), "aria-labelledby": mainHeadingId, tabIndex: -1, ref: container, children: o("div", { className: css_className('options__body'), children: [o("h2", { id: mainHeadingId, className: css_className('options__title'), children: headingText }), o("button", { type: "button", onClick: onCancelHandler, "aria-describedby": mainHeadingId, className: css_className('button', 'options__close'), ref: (btn) => {
25828
26273
  if (cancelButtonRef) {
25829
26274
  cancelButtonRef.current = btn;
25830
26275
  }
25831
- } }, { children: [o(layout_icon, { name: "close", size: "16", alt: "" }), o("span", { children: cancelButtonText })] })), description ? (o("p", Object.assign({ className: css_className('options__description'), id: descriptionId }, { children: description }))) : null, o("div", Object.assign({ className: css_className('options__wrapper') }, { children: children }))] })) })));
26276
+ }, children: [o(layout_icon, { name: "close", size: "16", alt: "" }), o("span", { children: cancelButtonText })] }), description ? (o("p", { className: css_className('options__description'), id: descriptionId, children: description })) : null, o("div", { className: css_className('options__wrapper'), children: children })] }) }));
25832
26277
  };
25833
26278
  /* harmony default export */ var options_frame = (OptionsFrame);
25834
26279
 
@@ -25969,7 +26414,7 @@ function FormProvider(_a) {
25969
26414
  console.error('"onSubmit" is required.');
25970
26415
  return null;
25971
26416
  }
25972
- return (o(context_Provider, Object.assign({}, props, { value: contextValue }, { children: children })));
26417
+ return (o(context_Provider, Object.assign({}, props, { value: contextValue, children: children })));
25973
26418
  }
25974
26419
 
25975
26420
  ;// CONCATENATED MODULE: ./src/javascripts/ui/components/form-controls/form.js
@@ -26038,8 +26483,8 @@ function error_Error(_ref) {
26038
26483
 
26039
26484
 
26040
26485
 
26041
- const FormControlWrapper = ({ contentHint, id, labelText, labelClass = css_className('label'), validity, errorText, children, }) => {
26042
- return (o(preact_module/* Fragment */.HY, { children: [contentHint && (o("span", Object.assign({ id: `${id}-content-hint`, className: css_className('input__content-hint') }, { children: contentHint }))), o(error_Error, { id: `${id}-error`, error: !validity && errorText }), o("div", Object.assign({ className: css_className('form-control__wrapper') }, { children: [o("label", Object.assign({ htmlFor: id, className: labelClass }, { children: labelText })), children] }))] }));
26486
+ const FormControlWrapper = ({ contentHint, id, labelText, labelClass, validity, errorText, children, }) => {
26487
+ return (o(preact_module/* Fragment */.HY, { children: [contentHint && (o("span", { id: `${id}-content-hint`, className: css_className('input__content-hint'), children: contentHint })), o(error_Error, { id: `${id}-error`, error: !validity && errorText }), o("div", { className: css_className('form-control__wrapper'), children: [o("label", { htmlFor: id, className: css_className(labelClass), children: labelText }), children] })] }));
26043
26488
  };
26044
26489
  /* harmony default export */ var wrapper = (FormControlWrapper);
26045
26490
 
@@ -26074,7 +26519,7 @@ function Input(_a) {
26074
26519
  describedByIds.push(`${id}-error`);
26075
26520
  }
26076
26521
  // todo: destructure Field
26077
- return (o(wrapper, Object.assign({ id: id, contentHint: contentHint, validity: !hasError, errorText: error, labelText: labelText, labelClass: labelClass }, { children: o("input", Object.assign({ id: id, name: name, type: type, "aria-invalid": hasError ? 'true' : 'false', "aria-describedby": describedByIds.join(' ') || null }, field, props)) })));
26522
+ return (o(wrapper, { id: id, contentHint: contentHint, validity: !hasError, errorText: error, labelText: labelText, labelClass: labelClass, children: o("input", Object.assign({ id: id, name: name, type: type, "aria-invalid": hasError ? 'true' : 'false', "aria-describedby": describedByIds.join(' ') || null }, field, props)) }));
26078
26523
  }
26079
26524
  /* harmony default export */ var input = (Input);
26080
26525
 
@@ -26433,14 +26878,14 @@ const OptionsButton = () => {
26433
26878
 
26434
26879
 
26435
26880
 
26436
- const TranslationOption = ({ label, checked, description, onChange, id, }) => {
26881
+ const TranslationOption = ({ label, checked, description, onChange, id, itemClassName, }) => {
26437
26882
  const onKeyDown = (e) => {
26438
26883
  if (e.code === 'Space' || e.code === 'Enter') {
26439
26884
  e.preventDefault();
26440
26885
  onChange();
26441
26886
  }
26442
26887
  };
26443
- return (o("li", Object.assign({ className: css_className('translation-options__item'), "aria-selected": checked, role: "option", tabIndex: 0, onClick: onChange, onKeyDown: onKeyDown, id: id }, { children: [o(layout_icon, { alt: "", name: "check", size: "16" }), label, " ", description && o("span", { children: ["(", description, ")"] })] })));
26888
+ return (o("li", { className: css_className([itemClassName, 'translation-options__item']), "aria-selected": checked, role: "option", tabIndex: 0, onClick: onChange, onKeyDown: onKeyDown, id: id, children: [o(layout_icon, { alt: "", name: "check", size: "16" }), label, " ", description && o("span", { children: ["(", description, ")"] })] }));
26444
26889
  };
26445
26890
  /* harmony default export */ var translation_option = (TranslationOption);
26446
26891
 
@@ -26452,12 +26897,13 @@ const TranslationOption = ({ label, checked, description, onChange, id, }) => {
26452
26897
 
26453
26898
 
26454
26899
 
26900
+ const isChecked = (language, currentLocale, isOriginal) => currentLocale === language.locale || (!currentLocale && isOriginal);
26455
26901
  const TranslationOptions = ({ onChange, describedById, }) => {
26456
26902
  const { context: { locale: defaultLocale }, } = useConfig();
26457
26903
  const { t } = useI18n();
26458
26904
  const { focusContainer } = useTranslationsContainer();
26459
26905
  const { languages, currentLocale, enableTranslations, disableTranslations } = useTranslations();
26460
- const handleChange = ({ locale }) => () => {
26906
+ const handleChange = (locale) => () => {
26461
26907
  if (locale === currentLocale || defaultLocale === locale) {
26462
26908
  disableTranslations();
26463
26909
  }
@@ -26467,22 +26913,25 @@ const TranslationOptions = ({ onChange, describedById, }) => {
26467
26913
  onChange();
26468
26914
  focusContainer();
26469
26915
  };
26470
- const sortedLanguages = (0,hooks_module/* useMemo */.Ye)(() => {
26471
- return [...languages].sort((a, b) => {
26472
- if (a.locale === defaultLocale)
26473
- return -1;
26474
- if (b.locale === defaultLocale)
26475
- return 1;
26476
- return a.nativeName.localeCompare(b.nativeName, undefined, {
26477
- sensitivity: 'base',
26478
- });
26479
- });
26480
- }, [languages, defaultLocale]);
26481
- return (o("ul", Object.assign({ "aria-describedby": describedById, role: "listbox", tabIndex: -1, className: css_className('translation-options') }, { children: sortedLanguages.map((language, idx) => {
26482
- const isOriginal = idx === 0;
26483
- const checked = currentLocale === language.locale || (!currentLocale && isOriginal);
26484
- return (o(translation_option, { id: language.locale, label: language.nativeName, checked: checked, description: isOriginal && t('translations.settings.original'), onChange: handleChange(language) }, language.locale));
26485
- }) })));
26916
+ const { primaryLanguages, remainingLanguages } = (0,compat_module.useMemo)(() => languages.reduce((acc, language) => {
26917
+ const isOriginal = language.locale === defaultLocale;
26918
+ const checked = isChecked(language, currentLocale, isOriginal);
26919
+ if (language.locale !== defaultLocale) {
26920
+ acc.remainingLanguages.push(Object.assign(Object.assign({}, language), { checked, isOriginal }));
26921
+ }
26922
+ const selectedIdx = acc.remainingLanguages.findIndex((l) => l.locale === currentLocale);
26923
+ if (isOriginal || (checked && selectedIdx > 4)) {
26924
+ acc.primaryLanguages.push(Object.assign(Object.assign({}, language), { checked, isOriginal }));
26925
+ }
26926
+ return acc;
26927
+ }, {
26928
+ primaryLanguages: [],
26929
+ remainingLanguages: [],
26930
+ }), [currentLocale, defaultLocale, languages]);
26931
+ return (o("ul", { "aria-describedby": describedById, role: "listbox", tabIndex: -1, className: css_className('translation-options'), children: [primaryLanguages.map(({ locale, nativeName, checked, isOriginal }, idx) => (o(translation_option, { id: locale, label: nativeName, checked: checked, description: isOriginal && t('translations.settings.original'), onChange: handleChange(locale), itemClassName: css_className({
26932
+ 'translation-options__item--original': isOriginal,
26933
+ 'translation-options__item--selected': checked && idx !== 0,
26934
+ }) }, locale))), remainingLanguages.map(({ locale, nativeName, checked, isOriginal }) => (o(translation_option, { id: locale, label: nativeName, checked: checked, description: isOriginal && t('translations.settings.original'), onChange: handleChange(locale) }, locale)))] }));
26486
26935
  };
26487
26936
  /* harmony default export */ var translation_options = (TranslationOptions);
26488
26937
 
@@ -26495,7 +26944,7 @@ const TranslationOptions = ({ onChange, describedById, }) => {
26495
26944
  function TranslationsOptionsDialog({ onClose, position, }) {
26496
26945
  const { t } = useI18n();
26497
26946
  const descriptionId = useGeneratedId();
26498
- return (o(options_frame, Object.assign({ onCancel: onClose, headingText: t('translations.menu.title'), cancelButtonText: t('translations.settings.cancelButtonText'), description: t('translations.menu.description'), descriptionId: descriptionId, position: position, disableButtonFocusing: true }, { children: o(translation_options, { describedById: descriptionId, onChange: onClose }) })));
26947
+ return (o(options_frame, { onCancel: onClose, headingText: t('translations.menu.title'), cancelButtonText: t('translations.settings.cancelButtonText'), description: t('translations.menu.description'), descriptionId: descriptionId, position: position, disableButtonFocusing: true, children: o(translation_options, { describedById: descriptionId, onChange: onClose }) }));
26499
26948
  }
26500
26949
  /* harmony default export */ var options_dialog = (TranslationsOptionsDialog);
26501
26950
 
@@ -26535,11 +26984,11 @@ function TranslationsOptionsButton({ children, position = {
26535
26984
  e.preventDefault();
26536
26985
  }
26537
26986
  };
26538
- return (o("div", Object.assign({ className: css_className('translations__container'), onKeyDown: onMainKeyDownHandler }, { children: [o(in_out_transition, Object.assign({ transitionStartState: transitionStartStates.notRendered, isActive: menuIsOpen }, { children: o("div", Object.assign({ className: css_className('options__dialog'), role: "dialog" }, { children: o(options_dialog, { onClose: handleDialogClose, position: position }) })) })), o("button", Object.assign({ type: "button", className: css_className([
26987
+ return (o("div", { className: css_className('translations__container'), onKeyDown: onMainKeyDownHandler, children: [o(in_out_transition, { transitionStartState: transitionStartStates.notRendered, isActive: menuIsOpen, children: o("div", { className: css_className('options__dialog'), role: "dialog", children: o(options_dialog, { onClose: handleDialogClose, position: position }) }) }), o("button", { type: "button", className: css_className([
26539
26988
  'button',
26540
26989
  'chat__options__button',
26541
26990
  ...classNames,
26542
- ]), id: toggleButtonId, onClick: handleToggleClick, onKeyDown: handleToggleKeyDown, ref: toggleButton, "aria-haspopup": "dialog", "aria-expanded": menuIsOpen }, { children: children }))] })));
26991
+ ]), id: toggleButtonId, onClick: handleToggleClick, onKeyDown: handleToggleKeyDown, ref: toggleButton, "aria-haspopup": "dialog", "aria-expanded": menuIsOpen, children: children })] }));
26543
26992
  }
26544
26993
 
26545
26994
  ;// CONCATENATED MODULE: ./src/javascripts/ui/components/app-options/index.js
@@ -26609,7 +27058,7 @@ const UnreadMessagesButton = () => {
26609
27058
  const { scrollToRef, unreadIds } = (0,hooks_module/* useContext */.qp)(chat_scroll_context);
26610
27059
  const { isMinimized } = useVisibility();
26611
27060
  const { t } = useI18n();
26612
- return (o(in_out_transition, Object.assign({ isActive: !!unreadIds.length && !isMinimized }, { children: o("div", Object.assign({ className: css_className('unread-messages') }, { children: o("button", Object.assign({ type: "button", className: css_className('button', 'button--primary'), onClick: scrollToRef }, { children: [t('message.unreadMessagesCount', { unreadCount: unreadIds.length }), o(layout_icon, { name: "chevronDown", size: "32", alt: "" })] })) })) })));
27061
+ return (o(in_out_transition, { isActive: !!unreadIds.length && !isMinimized, children: o("div", { className: css_className('unread-messages'), children: o("button", { type: "button", className: css_className('button', 'button--primary'), onClick: scrollToRef, children: [t('message.unreadMessagesCount', { unreadCount: unreadIds.length }), o(layout_icon, { name: "chevronDown", size: "32", alt: "" })] }) }) }));
26613
27062
  };
26614
27063
  /* harmony default export */ var unread_messages_button = (UnreadMessagesButton);
26615
27064
 
@@ -26764,13 +27213,13 @@ const ChatScrollProvider = ({ children }) => {
26764
27213
  return acc;
26765
27214
  }, {}), [events]);
26766
27215
  const { scrollToRef, scrollToBottom, containerRef, unreadIds } = use_chat_scroll(eventRefs);
26767
- return (o(chat_scroll_context.Provider, Object.assign({ value: {
27216
+ return (o(chat_scroll_context.Provider, { value: {
26768
27217
  eventRefs,
26769
27218
  unreadIds,
26770
27219
  scrollToRef,
26771
27220
  scrollToBottom,
26772
27221
  containerRef,
26773
- } }, { children: o("div", Object.assign({ className: css_className('chat__container') }, { children: [o("div", Object.assign({ className: css_className('chat__container__scroll-area'), ref: containerRef }, { children: children })), o(unread_messages_button, {})] })) })));
27222
+ }, children: o("div", { className: css_className('chat__container'), children: [o("div", { className: css_className('chat__container__scroll-area'), ref: containerRef, children: children }), o(unread_messages_button, {})] }) }));
26774
27223
  };
26775
27224
  /* harmony default export */ var chat_scroll_provider = (ChatScrollProvider);
26776
27225
 
@@ -27064,13 +27513,13 @@ function TextEntryForm({ controlName, skipLinkId }) {
27064
27513
  // When a message is submitted, the keyboard should be prevented from closing on mobile devices
27065
27514
  event.preventDefault();
27066
27515
  };
27067
- return (o(form_controls_form, Object.assign({ className: css_className('entry-form'), disableValidationClasses: true, noValidate: "true" }, { children: [o("div", Object.assign({ className: css_className([
27516
+ return (o(form_controls_form, { className: css_className('entry-form'), disableValidationClasses: true, noValidate: "true", children: [o("div", { className: css_className([
27068
27517
  'input--text__container',
27069
27518
  ...(reachedCharacterWarning && !reachedCharacterLimit
27070
27519
  ? ['character-warning']
27071
27520
  : []),
27072
27521
  ...(reachedCharacterLimit ? ['character-exceeded'] : []),
27073
- ]) }, { children: [o(input, { id: skipLinkId, type: "text", name: controlName, className: css_className('input__text'), autocomplete: "off", placeholder: placeholder, labelText: label, labelClass: css_className(labelClass), "aria-invalid": hasCharacterLimit ? reachedCharacterLimit : null, onKeyUp: handleKeyUp, onFocus: handleFocus }), o("div", Object.assign({ className: css_className('character-count') }, { children: reachedCharacterWarning && o("span", { children: remainingChars }) }))] })), o("button", Object.assign({ className: css_className('button', 'input__submit'), type: "submit", onPointerDown: handlePointerDown, "aria-disabled": !hasValue || reachedCharacterLimit ? 'true' : null }, { children: o(layout_icon, { name: "send", size: "32", alt: t('input.sendMessage') }) }))] })));
27522
+ ]), children: [o(input, { id: skipLinkId, type: "text", name: controlName, className: css_className('input__text'), autocomplete: "off", placeholder: placeholder, labelText: label, labelClass: css_className(labelClass), "aria-invalid": hasCharacterLimit ? reachedCharacterLimit : null, onKeyUp: handleKeyUp, onFocus: handleFocus }), o("div", { className: css_className('character-count'), children: reachedCharacterWarning && o("span", { children: remainingChars }) })] }), o("button", { className: css_className('button', 'input__submit'), type: "submit", onPointerDown: handlePointerDown, "aria-disabled": !hasValue || reachedCharacterLimit ? 'true' : null, children: o(layout_icon, { name: "send", size: "32", alt: t('input.sendMessage') }) })] }));
27074
27523
  }
27075
27524
 
27076
27525
  ;// CONCATENATED MODULE: ./src/javascripts/ui/components/entry/text-entry/index.js
@@ -27738,7 +28187,7 @@ const CollapseButton = () => {
27738
28187
 
27739
28188
  const ChatStatus = ({ children, handleClose, title, closeButtonText, srCloseButtonText, id, }) => {
27740
28189
  const headingId = useGeneratedId();
27741
- return (o("section", Object.assign({ tabIndex: -1, id: id, "aria-labelledby": title ? headingId : undefined, className: css_className('chat-status', !title && 'chat-status--condensed') }, { children: [o("div", Object.assign({ className: css_className('chat-status__body') }, { children: [title ? (o("h2", Object.assign({ className: css_className('chat-status__title'), id: headingId }, { children: title }))) : null, children] })), typeof handleClose === 'function' && (o("button", Object.assign({ type: "button", onClick: handleClose, className: css_className('button', 'button--tertiary', 'chat-status__close') }, { children: [closeButtonText || o(layout_icon, { name: "close", size: "16", alt: "" }), srCloseButtonText && (o("span", Object.assign({ className: css_className('visually-hidden') }, { children: srCloseButtonText })))] })))] })));
28190
+ return (o("section", { tabIndex: -1, id: id, "aria-labelledby": title ? headingId : undefined, className: css_className('chat-status', !title && 'chat-status--condensed'), children: [o("div", { className: css_className('chat-status__body'), children: [title ? (o("h2", { className: css_className('chat-status__title'), id: headingId, children: title })) : null, children] }), typeof handleClose === 'function' && (o("button", { type: "button", onClick: handleClose, className: css_className('button', 'button--tertiary', 'chat-status__close'), children: [closeButtonText || o(layout_icon, { name: "close", size: "16", alt: "" }), srCloseButtonText && (o("span", { className: css_className('visually-hidden'), children: srCloseButtonText }))] }))] }));
27742
28191
  };
27743
28192
  /* harmony default export */ var chat_status = (ChatStatus);
27744
28193
 
@@ -27773,7 +28222,7 @@ function TranslationChatStatus() {
27773
28222
 
27774
28223
 
27775
28224
 
27776
- const ChatStatusAction = ({ handleClick, icon, title, srButtonText, }) => (o("button", Object.assign({ type: "button", onClick: handleClick, className: css_className('button', 'button--primary', 'chat-status__button') }, { children: [o(layout_icon, { name: icon, size: "16", alt: "" }), title, srButtonText && (o("span", Object.assign({ className: css_className('visually-hidden') }, { children: srButtonText })))] })));
28225
+ const ChatStatusAction = ({ handleClick, icon, title, srButtonText, }) => (o("button", { type: "button", onClick: handleClick, className: css_className('button', 'button--primary', 'chat-status__button'), children: [o(layout_icon, { name: icon, size: "16", alt: "" }), title, srButtonText && (o("span", { className: css_className('visually-hidden'), children: srButtonText }))] }));
27777
28226
  /* harmony default export */ var chat_status_action = (ChatStatusAction);
27778
28227
 
27779
28228
  ;// CONCATENATED MODULE: ./src/javascripts/ui/components/translation-proposal/index.tsx
@@ -27787,7 +28236,7 @@ function TranslationProposal() {
27787
28236
  if (!showProposal) {
27788
28237
  return null;
27789
28238
  }
27790
- return (o(chat_status, Object.assign({ handleClose: dismissTranslationProposal, srCloseButtonText: translationProposal.srDismissButtonText, id: id, title: translationProposal.titleLabel }, { children: o(chat_status_action, { handleClick: activateTranslationProposal, icon: "newTranslation", title: translationProposal.buttonLabel }) })));
28239
+ return (o(chat_status, { handleClose: dismissTranslationProposal, srCloseButtonText: translationProposal.srDismissButtonText, id: id, title: translationProposal.titleLabel, children: o(chat_status_action, { handleClick: activateTranslationProposal, icon: "newTranslation", title: translationProposal.buttonLabel }) }));
27791
28240
  }
27792
28241
 
27793
28242
  ;// CONCATENATED MODULE: ./src/javascripts/domains/translations/components/translation-status.tsx
@@ -28059,10 +28508,14 @@ const WindowOpenButton = _ref => {
28059
28508
  "aria-label": ariaLabel,
28060
28509
  "aria-hidden": isOpen,
28061
28510
  onClick: handleClick,
28062
- children: [o("span", {
28063
- className: css_className('message-count'),
28064
- "aria-hidden": "true",
28065
- children: !!count && count
28511
+ children: [o(in_out_transition, {
28512
+ isActive: !!count,
28513
+ transitionStartState: transitionStartStates.notRendered,
28514
+ children: o("span", {
28515
+ className: css_className('message-count'),
28516
+ "aria-hidden": "true",
28517
+ children: count
28518
+ })
28066
28519
  }), o(ButtonIcon, {})]
28067
28520
  })
28068
28521
  });
@@ -28097,7 +28550,7 @@ const WindowView = () => {
28097
28550
  },
28098
28551
  },
28099
28552
  }), [continueChatText]);
28100
- return (o(preact_module/* Fragment */.HY, { children: [o(window_open_button, { onClick: openChat }), o(in_out_transition, Object.assign({ isActive: preChat && !isOpen && !userHasResponded, exitAfter: getDelay(preChat, 'exitAfter'), enterDelay: getDelay(preChat, 'enterDelay'), transitionStartState: transitionStartStates.rendered }, { children: o("div", Object.assign({ className: css_className('unstarted-wrapper', 'unstarted-wrapper--window') }, { children: o(PreChatMessages, {}) })) })), o(in_out_transition, Object.assign({ isActive: continueChat && !isOpen && userHasResponded, exitAfter: getDelay(continueChat, 'exitAfter'), enterDelay: getDelay(continueChat, 'enterDelay'), transitionStartState: transitionStartStates.notRendered }, { children: o("div", Object.assign({ className: css_className('unstarted-wrapper', 'unstarted-wrapper--window', 'unstarted-wrapper--continue') }, { children: o(event_text, { event: continueChatEvent }) })) })), o(in_out_transition, Object.assign({ isActive: isOpen, transitionStartState: transitionStartStates.notRendered }, { children: o(chat, { children: o(chat_frame, { children: o(conversation, {}) }) }) }))] }));
28553
+ return (o(preact_module/* Fragment */.HY, { children: [o(window_open_button, { onClick: openChat }), o(in_out_transition, { isActive: preChat && !isOpen && !userHasResponded, exitAfter: getDelay(preChat, 'exitAfter'), enterDelay: getDelay(preChat, 'enterDelay'), transitionStartState: transitionStartStates.rendered, children: o("div", { className: css_className('unstarted-wrapper', 'unstarted-wrapper--window'), children: o(PreChatMessages, {}) }) }), o(in_out_transition, { isActive: continueChat && !isOpen && userHasResponded, exitAfter: getDelay(continueChat, 'exitAfter'), enterDelay: getDelay(continueChat, 'enterDelay'), transitionStartState: transitionStartStates.notRendered, children: o("div", { className: css_className('unstarted-wrapper', 'unstarted-wrapper--window', 'unstarted-wrapper--continue'), children: o(event_text, { event: continueChatEvent }) }) }), o(in_out_transition, { isActive: isOpen, transitionStartState: transitionStartStates.notRendered, children: o(chat, { children: o(chat_frame, { children: o(conversation, {}) }) }) })] }));
28101
28554
  };
28102
28555
  /* harmony default export */ var window_view = (WindowView);
28103
28556
 
@@ -28313,7 +28766,7 @@ const View = ({ children }) => {
28313
28766
  if (userHasResponded) {
28314
28767
  classNames.push('app--user-responded');
28315
28768
  }
28316
- return (isVisible && (o("div", Object.assign({ className: css_className(classNames), lang: blockLang, tabIndex: -1, "data-nosnippet": true, style: { zIndex }, ref: containerElementRef }, { children: children || o(ViewComponent, {}) }))));
28769
+ return (isVisible && (o("div", { className: css_className(classNames), lang: blockLang, tabIndex: -1, "data-nosnippet": true, style: { zIndex }, ref: containerElementRef, children: children || o(ViewComponent, {}) })));
28317
28770
  };
28318
28771
  /* harmony default export */ var view = (View);
28319
28772
 
@@ -28403,14 +28856,16 @@ class Engine {
28403
28856
  yield store.dispatch(initializeConfig());
28404
28857
  try {
28405
28858
  const { locale } = yield store.dispatch(initializeApp()).unwrap();
28406
- yield store.dispatch(setLocale(locale));
28859
+ if (locale) {
28860
+ yield store.dispatch(setLocale(locale));
28861
+ }
28407
28862
  }
28408
28863
  catch (rejectedValueOrSerializedError) {
28409
28864
  // nothing to do
28410
28865
  }
28411
28866
  store.dispatch(initializeVisibility());
28412
28867
  if (View) {
28413
- (0,preact_module/* render */.sY)(o(seamly_core, Object.assign({ eventBus: this.eventBus, store: store, api: this.api }, { children: o(View, {}) })), this.parentElement);
28868
+ (0,preact_module/* render */.sY)(o(seamly_core, { eventBus: this.eventBus, store: store, api: this.api, children: o(View, {}) }), this.parentElement);
28414
28869
  }
28415
28870
  else {
28416
28871
  (0,preact_module/* render */.sY)(o(chat_app, { config: renderConfig, eventBus: this.eventBus, store: store, api: this.api }), this.parentElement);