@nectary/components 0.19.0 → 0.21.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dropdown/index.js CHANGED
@@ -1,7 +1,7 @@
1
1
  import _classPrivateFieldGet from '@babel/runtime/helpers/classPrivateFieldGet';
2
2
  import _classPrivateFieldSet from '@babel/runtime/helpers/classPrivateFieldSet';
3
3
 
4
- var _$button, _$optionSlot, _$listbox, _onButtonClick, _onListboxClick, _onListboxKeyPress, _onListboxKeyDown, _onOptionSlotChange, _setOpen, _onExpand, _onCollapse, _onValueChange, _getFirstOption, _getLastOption, _getNextOption, _getPrevOption, _selectOption, _getOptionWithValue, _getOptionElements, _getEnabledOptionElements, _dispatchChangeEvent;
4
+ var _$target, _$optionSlot, _$listbox, _isConnected, _onListboxClick, _onListboxKeyPress, _onListboxKeyDown, _onOptionSlotChange, _onExpand, _onCollapse, _isOpen, _updateOrientation, _onValueChange, _getFirstOption, _getLastOption, _getNextOption, _getPrevOption, _selectOption, _getOptionWithValue, _getOptionElements, _getEnabledOptionElements, _dispatchChangeEvent, _dispatchCloseEvent, _onCancel, _onCloseReactHandler;
5
5
 
6
6
  function _classPrivateMethodInitSpec(obj, privateSet) { _checkPrivateRedeclaration(obj, privateSet); privateSet.add(obj); }
7
7
 
@@ -11,9 +11,10 @@ function _checkPrivateRedeclaration(obj, privateCollection) { if (privateCollect
11
11
 
12
12
  function _classPrivateMethodGet(receiver, privateSet, fn) { if (!privateSet.has(receiver)) { throw new TypeError("attempted to get private field on non-instance"); } return fn; }
13
13
 
14
+ import dialogPolyfill from 'dialog-polyfill';
14
15
  import { isDropdownOptionElement } from '../dropdown-option';
15
- import { attrValueToPixels, defineCustomElement, getAttribute, getBooleanAttribute, getIntegerAttribute, getLiteralAttribute, getRect, updateAttribute, updateBooleanAttribute, updateIntegerAttribute, updateLiteralAttribute } from '../utils';
16
- const templateHTML = '<style>:host{display:inline-block;vertical-align:middle;outline:0}#wrapper{position:relative;width:100%;box-sizing:border-box}dialog{outline:0;border:none;font:var(--sinch-font-body);color:var(--sinch-color-text-default);background-color:var(--sinch-color-snow-100);box-shadow:1px 2px 4px rgb(0 0 0 / 15%);overflow-y:auto;contain:content;padding:0;border-radius:4px;cursor:pointer}dialog::backdrop{background-color:transparent}dialog+.backdrop{position:fixed;top:0;right:0;bottom:0;left:0;background-color:transparent}dialog.fixed{position:fixed;top:50%;transform:translate(0,-50%)}._dialog_overlay{position:fixed;top:0;right:0;bottom:0;left:0}::slotted(*){display:block}</style><div id="wrapper"><div id="button" aria-haspopup="listbox" aria-expanded="false"><slot name="target"></slot></div><dialog id="listbox" tabindex="-1"><slot name="option"></slot></dialog></div>';
16
+ import { attrValueToPixels, defineCustomElement, getAttribute, getBooleanAttribute, getIntegerAttribute, getLiteralAttribute, getReactEventHandler, getRect, isAttrTrue, updateAttribute, updateBooleanAttribute, updateIntegerAttribute, updateLiteralAttribute } from '../utils';
17
+ const templateHTML = '<style>:host{display:inline-block;vertical-align:middle;outline:0}#wrapper{position:relative;width:100%;box-sizing:border-box}dialog{outline:0;border:none;font:var(--sinch-font-body);color:var(--sinch-color-text-default);background-color:var(--sinch-color-snow-100);box-shadow:1px 2px 4px rgba(0,0,0,.15);overflow-y:auto;contain:content;padding:0;border-radius:4px;cursor:pointer}dialog::backdrop{background-color:transparent}dialog+.backdrop{position:fixed;top:0;right:0;bottom:0;left:0;background-color:transparent}dialog.fixed{position:fixed;top:50%;transform:translate(0,-50%)}._dialog_overlay{position:fixed;top:0;right:0;bottom:0;left:0}::slotted(*){display:block}</style><div id="wrapper"><div id="target" aria-haspopup="listbox" aria-expanded="false"><slot name="target"></slot></div><dialog id="listbox" tabindex="-1"><slot name="option"></slot></dialog></div>';
17
18
  const orientationValues = ['top-left', 'top-right', 'bottom-left', 'bottom-right'];
18
19
  const ITEM_HEIGHT = 40;
19
20
 
@@ -29,10 +30,12 @@ const findSelectedOption = elements => {
29
30
 
30
31
  const template = document.createElement('template');
31
32
  template.innerHTML = templateHTML;
32
- defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot = new WeakMap(), _$listbox = new WeakMap(), _onButtonClick = new WeakMap(), _onListboxClick = new WeakMap(), _onListboxKeyPress = new WeakMap(), _onListboxKeyDown = new WeakMap(), _onOptionSlotChange = new WeakMap(), _setOpen = new WeakSet(), _onExpand = new WeakSet(), _onCollapse = new WeakSet(), _onValueChange = new WeakSet(), _getFirstOption = new WeakSet(), _getLastOption = new WeakSet(), _getNextOption = new WeakSet(), _getPrevOption = new WeakSet(), _selectOption = new WeakSet(), _getOptionWithValue = new WeakSet(), _getOptionElements = new WeakSet(), _getEnabledOptionElements = new WeakSet(), _dispatchChangeEvent = new WeakSet(), class extends HTMLElement {
33
+ defineCustomElement('sinch-dropdown', (_$target = new WeakMap(), _$optionSlot = new WeakMap(), _$listbox = new WeakMap(), _isConnected = new WeakMap(), _onListboxClick = new WeakMap(), _onListboxKeyPress = new WeakMap(), _onListboxKeyDown = new WeakMap(), _onOptionSlotChange = new WeakMap(), _onExpand = new WeakSet(), _onCollapse = new WeakSet(), _isOpen = new WeakSet(), _updateOrientation = new WeakSet(), _onValueChange = new WeakSet(), _getFirstOption = new WeakSet(), _getLastOption = new WeakSet(), _getNextOption = new WeakSet(), _getPrevOption = new WeakSet(), _selectOption = new WeakSet(), _getOptionWithValue = new WeakSet(), _getOptionElements = new WeakSet(), _getEnabledOptionElements = new WeakSet(), _dispatchChangeEvent = new WeakSet(), _dispatchCloseEvent = new WeakSet(), _onCancel = new WeakMap(), _onCloseReactHandler = new WeakMap(), class extends HTMLElement {
33
34
  constructor() {
34
35
  super();
35
36
 
37
+ _classPrivateMethodInitSpec(this, _dispatchCloseEvent);
38
+
36
39
  _classPrivateMethodInitSpec(this, _dispatchChangeEvent);
37
40
 
38
41
  _classPrivateMethodInitSpec(this, _getEnabledOptionElements);
@@ -53,13 +56,15 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
53
56
 
54
57
  _classPrivateMethodInitSpec(this, _onValueChange);
55
58
 
59
+ _classPrivateMethodInitSpec(this, _updateOrientation);
60
+
61
+ _classPrivateMethodInitSpec(this, _isOpen);
62
+
56
63
  _classPrivateMethodInitSpec(this, _onCollapse);
57
64
 
58
65
  _classPrivateMethodInitSpec(this, _onExpand);
59
66
 
60
- _classPrivateMethodInitSpec(this, _setOpen);
61
-
62
- _classPrivateFieldInitSpec(this, _$button, {
67
+ _classPrivateFieldInitSpec(this, _$target, {
63
68
  writable: true,
64
69
  value: void 0
65
70
  });
@@ -74,32 +79,30 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
74
79
  value: void 0
75
80
  });
76
81
 
77
- _classPrivateFieldInitSpec(this, _onButtonClick, {
82
+ _classPrivateFieldInitSpec(this, _isConnected, {
78
83
  writable: true,
79
- value: e => {
80
- e.stopPropagation();
81
-
82
- if (this.disabled) {
83
- return;
84
- }
85
-
86
- if (_classPrivateFieldGet(this, _$button).getAttribute('aria-expanded') !== 'true') {
87
- _classPrivateMethodGet(this, _onExpand, _onExpand2).call(this);
88
- }
89
- }
84
+ value: false
90
85
  });
91
86
 
92
87
  _classPrivateFieldInitSpec(this, _onListboxClick, {
93
88
  writable: true,
94
89
  value: e => {
95
- e.stopPropagation();
90
+ const rect = this.dropdownRect;
91
+ const isInside = e.x >= rect.x && e.x < rect.x + rect.width && e.y >= rect.y && e.y < rect.y + rect.height;
92
+
93
+ if (!isInside) {
94
+ _classPrivateMethodGet(this, _dispatchCloseEvent, _dispatchCloseEvent2).call(this);
95
+
96
+ return;
97
+ }
98
+
96
99
  const $elem = e.target;
97
100
 
98
- if ($elem !== _classPrivateFieldGet(this, _$listbox) && isDropdownOptionElement($elem) && $elem.disabled !== true) {
101
+ if ($elem !== _classPrivateFieldGet(this, _$listbox) && isDropdownOptionElement($elem)) {
102
+ e.stopPropagation();
103
+
99
104
  _classPrivateMethodGet(this, _dispatchChangeEvent, _dispatchChangeEvent2).call(this, $elem);
100
105
  }
101
-
102
- _classPrivateMethodGet(this, _onCollapse, _onCollapse2).call(this);
103
106
  }
104
107
  });
105
108
 
@@ -114,8 +117,6 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
114
117
 
115
118
  _classPrivateMethodGet(this, _dispatchChangeEvent, _dispatchChangeEvent2).call(this, findSelectedOption(_classPrivateMethodGet(this, _getEnabledOptionElements, _getEnabledOptionElements2).call(this)));
116
119
 
117
- _classPrivateMethodGet(this, _onCollapse, _onCollapse2).call(this);
118
-
119
120
  break;
120
121
  }
121
122
  }
@@ -143,15 +144,6 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
143
144
 
144
145
  _classPrivateMethodGet(this, _selectOption, _selectOption2).call(this, _classPrivateMethodGet(this, _getNextOption, _getNextOption2).call(this));
145
146
 
146
- break;
147
- }
148
-
149
- case 'Escape':
150
- {
151
- e.preventDefault();
152
-
153
- _classPrivateMethodGet(this, _onCollapse, _onCollapse2).call(this);
154
-
155
147
  break;
156
148
  }
157
149
  }
@@ -161,29 +153,47 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
161
153
  _classPrivateFieldInitSpec(this, _onOptionSlotChange, {
162
154
  writable: true,
163
155
  value: () => {
164
- _classPrivateMethodGet(this, _onCollapse, _onCollapse2).call(this);
165
-
166
156
  _classPrivateMethodGet(this, _onValueChange, _onValueChange2).call(this, this.value);
167
157
  }
168
158
  });
169
159
 
160
+ _classPrivateFieldInitSpec(this, _onCancel, {
161
+ writable: true,
162
+ value: e => {
163
+ e.preventDefault();
164
+
165
+ _classPrivateMethodGet(this, _dispatchCloseEvent, _dispatchCloseEvent2).call(this);
166
+ }
167
+ });
168
+
169
+ _classPrivateFieldInitSpec(this, _onCloseReactHandler, {
170
+ writable: true,
171
+ value: () => {
172
+ getReactEventHandler(this, 'onClose')?.();
173
+ }
174
+ });
175
+
170
176
  const shadowRoot = this.attachShadow({
171
177
  mode: 'closed',
172
178
  delegatesFocus: true
173
179
  });
174
180
  shadowRoot.appendChild(template.content.cloneNode(true));
175
181
 
176
- _classPrivateFieldSet(this, _$button, shadowRoot.querySelector('#button'));
182
+ _classPrivateFieldSet(this, _$target, shadowRoot.querySelector('#target'));
177
183
 
178
184
  _classPrivateFieldSet(this, _$listbox, shadowRoot.querySelector('#listbox'));
179
185
 
180
186
  _classPrivateFieldSet(this, _$optionSlot, shadowRoot.querySelector('slot[name="option"]'));
187
+
188
+ dialogPolyfill.registerDialog(_classPrivateFieldGet(this, _$listbox));
181
189
  }
182
190
 
183
191
  connectedCallback() {
192
+ _classPrivateFieldSet(this, _isConnected, true);
193
+
184
194
  this.setAttribute('role', 'listbox');
185
195
 
186
- _classPrivateFieldGet(this, _$button).addEventListener('click', _classPrivateFieldGet(this, _onButtonClick));
196
+ _classPrivateFieldGet(this, _$listbox).addEventListener('cancel', _classPrivateFieldGet(this, _onCancel));
187
197
 
188
198
  _classPrivateFieldGet(this, _$listbox).addEventListener('click', _classPrivateFieldGet(this, _onListboxClick));
189
199
 
@@ -192,10 +202,20 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
192
202
  _classPrivateFieldGet(this, _$listbox).addEventListener('keypress', _classPrivateFieldGet(this, _onListboxKeyPress));
193
203
 
194
204
  _classPrivateFieldGet(this, _$optionSlot).addEventListener('slotchange', _classPrivateFieldGet(this, _onOptionSlotChange));
205
+
206
+ this.addEventListener('close', _classPrivateFieldGet(this, _onCloseReactHandler));
207
+
208
+ if (getBooleanAttribute(this, 'open')) {
209
+ _classPrivateMethodGet(this, _onExpand, _onExpand2).call(this);
210
+ } else {
211
+ _classPrivateMethodGet(this, _onCollapse, _onCollapse2).call(this);
212
+ }
195
213
  }
196
214
 
197
215
  disconnectedCallback() {
198
- _classPrivateFieldGet(this, _$button).removeEventListener('click', _classPrivateFieldGet(this, _onButtonClick));
216
+ _classPrivateFieldSet(this, _isConnected, false);
217
+
218
+ _classPrivateFieldGet(this, _$listbox).removeEventListener('cancel', _classPrivateFieldGet(this, _onCancel));
199
219
 
200
220
  _classPrivateFieldGet(this, _$listbox).removeEventListener('click', _classPrivateFieldGet(this, _onListboxClick));
201
221
 
@@ -204,10 +224,12 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
204
224
  _classPrivateFieldGet(this, _$listbox).removeEventListener('keypress', _classPrivateFieldGet(this, _onListboxKeyPress));
205
225
 
206
226
  _classPrivateFieldGet(this, _$optionSlot).removeEventListener('slotchange', _classPrivateFieldGet(this, _onOptionSlotChange));
227
+
228
+ this.removeEventListener('close', _classPrivateFieldGet(this, _onCloseReactHandler));
207
229
  }
208
230
 
209
231
  static get observedAttributes() {
210
- return ['value', 'maxvisibleitems'];
232
+ return ['value', 'maxvisibleitems', 'open', 'orientation'];
211
233
  }
212
234
 
213
235
  get nodeName() {
@@ -238,12 +260,12 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
238
260
  updateLiteralAttribute(this, orientationValues, 'orientation', value);
239
261
  }
240
262
 
241
- set disabled(isDisabled) {
242
- updateBooleanAttribute(this, 'disabled', isDisabled);
263
+ set open(isOpen) {
264
+ updateBooleanAttribute(this, 'open', isOpen);
243
265
  }
244
266
 
245
- get disabled() {
246
- return getBooleanAttribute(this, 'disabled');
267
+ get open() {
268
+ return getBooleanAttribute(this, 'open');
247
269
  }
248
270
 
249
271
  get dropdownRect() {
@@ -252,6 +274,28 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
252
274
 
253
275
  attributeChangedCallback(name, oldVal, newVal) {
254
276
  switch (name) {
277
+ case 'open':
278
+ {
279
+ if (_classPrivateFieldGet(this, _isConnected)) {
280
+ if (isAttrTrue(newVal)) {
281
+ _classPrivateMethodGet(this, _onExpand, _onExpand2).call(this);
282
+ } else {
283
+ _classPrivateMethodGet(this, _onCollapse, _onCollapse2).call(this);
284
+ }
285
+ }
286
+
287
+ break;
288
+ }
289
+
290
+ case 'orientation':
291
+ {
292
+ if (_classPrivateMethodGet(this, _isOpen, _isOpen2).call(this)) {
293
+ _classPrivateMethodGet(this, _updateOrientation, _updateOrientation2).call(this);
294
+ }
295
+
296
+ break;
297
+ }
298
+
255
299
  case 'value':
256
300
  {
257
301
  _classPrivateMethodGet(this, _onValueChange, _onValueChange2).call(this, newVal ?? '');
@@ -283,22 +327,35 @@ defineCustomElement('sinch-dropdown', (_$button = new WeakMap(), _$optionSlot =
283
327
 
284
328
  }));
285
329
 
286
- function _setOpen2(isOpen) {
287
- if (isOpen) {
288
- if (!getBooleanAttribute(_classPrivateFieldGet(this, _$listbox), 'open')) {
289
- _classPrivateFieldGet(this, _$listbox).showModal();
290
- }
291
- } else {
292
- _classPrivateFieldGet(this, _$listbox).close();
330
+ function _onExpand2() {
331
+ _classPrivateFieldGet(this, _$target).setAttribute('aria-expanded', 'true');
332
+
333
+ if (!_classPrivateMethodGet(this, _isOpen, _isOpen2).call(this)) {
334
+ _classPrivateFieldGet(this, _$listbox).showModal();
293
335
  }
336
+
337
+ _classPrivateMethodGet(this, _updateOrientation, _updateOrientation2).call(this);
338
+
339
+ _classPrivateMethodGet(this, _selectOption, _selectOption2).call(this, _classPrivateMethodGet(this, _getOptionWithValue, _getOptionWithValue2).call(this, this.value) ?? _classPrivateMethodGet(this, _getFirstOption, _getFirstOption2).call(this));
294
340
  }
295
341
 
296
- function _onExpand2() {
297
- _classPrivateFieldGet(this, _$button).setAttribute('aria-expanded', 'true');
342
+ function _onCollapse2() {
343
+ _classPrivateFieldGet(this, _$target).setAttribute('aria-expanded', 'false');
298
344
 
299
- _classPrivateMethodGet(this, _setOpen, _setOpen2).call(this, true);
345
+ if (_classPrivateMethodGet(this, _isOpen, _isOpen2).call(this)) {
346
+ _classPrivateFieldGet(this, _$listbox).close?.();
347
+ }
348
+ }
300
349
 
301
- const buttonRect = _classPrivateFieldGet(this, _$button).getBoundingClientRect();
350
+ function _isOpen2() {
351
+ return _classPrivateFieldGet(this, _isConnected) && getBooleanAttribute(_classPrivateFieldGet(this, _$listbox), 'open');
352
+ }
353
+
354
+ function _updateOrientation2() {
355
+ _classPrivateFieldGet(this, _$listbox).style.transform = `initial`;
356
+ _classPrivateFieldGet(this, _$listbox).style.width = `max-content`;
357
+
358
+ const buttonRect = _classPrivateFieldGet(this, _$target).getBoundingClientRect();
302
359
 
303
360
  const modalRect = _classPrivateFieldGet(this, _$listbox).getBoundingClientRect();
304
361
 
@@ -326,17 +383,6 @@ function _onExpand2() {
326
383
 
327
384
  _classPrivateFieldGet(this, _$listbox).style.transform = `translateX(${leftOffset}px) translateY(${topOffset}px)`;
328
385
  _classPrivateFieldGet(this, _$listbox).style.width = `${width}px`;
329
-
330
- _classPrivateMethodGet(this, _selectOption, _selectOption2).call(this, _classPrivateMethodGet(this, _getOptionWithValue, _getOptionWithValue2).call(this, this.value) ?? _classPrivateMethodGet(this, _getFirstOption, _getFirstOption2).call(this));
331
- }
332
-
333
- function _onCollapse2() {
334
- _classPrivateFieldGet(this, _$button).setAttribute('aria-expanded', 'false');
335
-
336
- _classPrivateMethodGet(this, _setOpen, _setOpen2).call(this, false);
337
-
338
- _classPrivateFieldGet(this, _$listbox).style.transform = `initial`;
339
- _classPrivateFieldGet(this, _$listbox).style.width = `max-content`;
340
386
  }
341
387
 
342
388
  function _onValueChange2(value) {
@@ -430,4 +476,10 @@ function _dispatchChangeEvent2($opt) {
430
476
  bubbles: true
431
477
  }));
432
478
  }
479
+ }
480
+
481
+ function _dispatchCloseEvent2() {
482
+ this.dispatchEvent(new CustomEvent('close', {
483
+ bubbles: true
484
+ }));
433
485
  }
package/index.d.ts CHANGED
@@ -8,6 +8,7 @@ import './button';
8
8
  import './card';
9
9
  import './card-button';
10
10
  import './card-link';
11
+ import './card-container';
11
12
  import './checkbox';
12
13
  import './input';
13
14
  import './help-tooltip';
@@ -139,7 +140,11 @@ import './search-option';
139
140
  import './segment';
140
141
  import './segment-collapse';
141
142
  import './avatar';
143
+ import './avatar-badge';
144
+ import './avatar-status';
142
145
  import './chat-avatar';
143
146
  import './chat-bubble';
144
147
  import './chat-block';
145
148
  import './chat';
149
+ import './title';
150
+ import './popover';
package/index.js CHANGED
@@ -8,6 +8,7 @@ import './button';
8
8
  import './card';
9
9
  import './card-button';
10
10
  import './card-link';
11
+ import './card-container';
11
12
  import './checkbox';
12
13
  import './input';
13
14
  import './help-tooltip';
@@ -139,7 +140,11 @@ import './search-option';
139
140
  import './segment';
140
141
  import './segment-collapse';
141
142
  import './avatar';
143
+ import './avatar-badge';
144
+ import './avatar-status';
142
145
  import './chat-avatar';
143
146
  import './chat-bubble';
144
147
  import './chat-block';
145
- import './chat';
148
+ import './chat';
149
+ import './title';
150
+ import './popover';
package/input/index.js CHANGED
@@ -8,7 +8,7 @@ function _classPrivateFieldInitSpec(obj, privateMap, value) { _checkPrivateRedec
8
8
  function _checkPrivateRedeclaration(obj, privateCollection) { if (privateCollection.has(obj)) { throw new TypeError("Cannot initialize the same private elements twice on an object"); } }
9
9
 
10
10
  import { defineCustomElement, getAttribute, getBooleanAttribute, getLiteralAttribute, isAttrTrue, updateAttribute, updateBooleanAttribute, updateLiteralAttribute } from '../utils';
11
- const templateHTML = '<style>:host{display:inline-block;vertical-align:middle;outline:0;--sinch-color-icon:var(--sinch-color-stormy-500)}#wrapper{width:100%;box-sizing:border-box}#input{all:initial;border:1px solid var(--sinch-color-stormy-200);box-sizing:border-box;border-radius:4px;width:100%;height:48px;margin:2px 0;padding:0 12px;font:var(--sinch-font-body);color:var(--sinch-color-text-default);caret-color:var(--sinch-caret-color,auto)}#input::placeholder{font:var(--sinch-font-body);color:var(--sinch-color-text-muted)}#input:disabled{border-color:var(--sinch-color-snow-500);color:var(--sinch-color-stormy-100)}#input:disabled::placeholder{color:var(--sinch-color-snow-500)}#input:focus{border-color:var(--sinch-color-stormy-600)}#input[type=password]{font-size:1.5em;letter-spacing:.1em}:host([invalidtext]:not([invalidtext=""])) #input:not(:disabled){border-color:var(--sinch-color-text-invalid)}#bottom,#top{display:flex;align-items:baseline}#top{height:24px}#bottom{height:20px}#additional,#invalid,#label,#optional{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}#label{font:var(--sinch-font-title-4);color:var(--sinch-color-text-default)}#optional{flex:1;text-align:right;font:var(--sinch-font-small-text);color:var(--sinch-color-text-muted)}#additional{flex:1;text-align:right;font:var(--sinch-font-extra-small-text);color:var(--sinch-color-text-muted)}#invalid{font:var(--sinch-font-extra-small-text);color:var(--sinch-color-text-invalid)}::slotted(sinch-help-tooltip){align-self:center;margin:0 8px}:host([disabled]:not([disabled=false])) :is(#label,#additional,#optional,#invalid){color:var(--sinch-color-stormy-100)}:host([disabled]:not([disabled=false])){--sinch-color-icon:var(--sinch-color-stormy-100)}</style><div id="wrapper"><div id="top"><label id="label" for="input"></label><slot name="tooltip"></slot><span id="optional"></span></div><input id="input" type="text"/><div id="bottom"><span id="invalid"></span> <span id="additional"></span></div></div>';
11
+ const templateHTML = '<style>:host{display:inline-block;vertical-align:middle;outline:0;--sinch-color-icon:var(--sinch-color-stormy-500)}#wrapper{width:100%;box-sizing:border-box}#input{all:initial;border:1px solid var(--sinch-color-stormy-200);box-sizing:border-box;border-radius:4px;width:100%;height:48px;margin:2px 0;padding:0 12px;font:var(--sinch-font-body);color:var(--sinch-color-text-default);caret-color:var(--sinch-caret-color,auto)}#input::placeholder{font:var(--sinch-font-body);color:var(--sinch-color-text-muted)}#input:disabled{border-color:var(--sinch-color-snow-500);color:var(--sinch-color-stormy-100)}#input:disabled::placeholder{color:var(--sinch-color-snow-500)}#input:focus{border-color:var(--sinch-color-stormy-600)}#input[type=password]{font-size:1.5em;letter-spacing:.1em}:host([invalidtext]:not([invalidtext=""])) #input:not(:disabled){border-color:var(--sinch-color-text-invalid)}#bottom,#top{display:flex;align-items:baseline}#top{height:24px}#bottom{height:20px}#additional,#invalid,#label,#optional{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}#label{font:var(--sinch-font-title-s);color:var(--sinch-color-text-default)}#optional{flex:1;text-align:right;font:var(--sinch-font-small-text);color:var(--sinch-color-text-muted)}#additional{flex:1;text-align:right;font:var(--sinch-font-extra-small-text);color:var(--sinch-color-text-muted)}#invalid{font:var(--sinch-font-extra-small-text);color:var(--sinch-color-text-invalid)}::slotted(sinch-help-tooltip){align-self:center;margin:0 8px}:host([disabled]:not([disabled=false])) :is(#label,#additional,#optional,#invalid){color:var(--sinch-color-stormy-100)}:host([disabled]:not([disabled=false])){--sinch-color-icon:var(--sinch-color-stormy-100)}</style><div id="wrapper"><div id="top"><label id="label" for="input"></label><slot name="tooltip"></slot><span id="optional"></span></div><input id="input" type="text"/><div id="bottom"><span id="invalid"></span> <span id="additional"></span></div></div>';
12
12
  const inputTypes = ['text', 'password'];
13
13
  const template = document.createElement('template');
14
14
  template.innerHTML = templateHTML;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nectary/components",
3
- "version": "0.19.0",
3
+ "version": "0.21.0",
4
4
  "files": [
5
5
  "theme.css",
6
6
  "**/*/*.js",
@@ -0,0 +1,26 @@
1
+ import type { TRect, TSinchElementReact } from '../types';
2
+ import type { SyntheticEvent } from 'react';
3
+ declare const orientationValues: readonly ["top-left", "top-right", "bottom-left", "bottom-right"];
4
+ export declare type TSinchPopoverOrientation = typeof orientationValues[number];
5
+ export declare type TSinchPopoverElement = HTMLElement & {
6
+ open: boolean;
7
+ orientation: TSinchPopoverOrientation;
8
+ readonly popoverRect: TRect;
9
+ };
10
+ export declare type TSinchPopoverReact = TSinchElementReact<TSinchPopoverElement> & {
11
+ open: boolean;
12
+ orientation?: TSinchPopoverOrientation;
13
+ 'aria-label': string;
14
+ onClose: (event: SyntheticEvent<TSinchPopoverElement, CustomEvent<void>>) => void;
15
+ };
16
+ declare global {
17
+ namespace JSX {
18
+ interface IntrinsicElements {
19
+ 'sinch-popover': TSinchPopoverReact;
20
+ }
21
+ }
22
+ interface HTMLElementTagNameMap {
23
+ 'sinch-popover': TSinchPopoverElement;
24
+ }
25
+ }
26
+ export {};
@@ -0,0 +1,230 @@
1
+ import _classPrivateFieldGet from '@babel/runtime/helpers/classPrivateFieldGet';
2
+ import _classPrivateFieldSet from '@babel/runtime/helpers/classPrivateFieldSet';
3
+
4
+ var _$target, _$dialog, _isConnected, _onExpand, _onCollapse, _isOpen, _updateOrientation, _onBackdropClick, _onCancel, _onCloseReactHandler, _dispatchCloseEvent;
5
+
6
+ function _classPrivateMethodInitSpec(obj, privateSet) { _checkPrivateRedeclaration(obj, privateSet); privateSet.add(obj); }
7
+
8
+ function _classPrivateFieldInitSpec(obj, privateMap, value) { _checkPrivateRedeclaration(obj, privateMap); privateMap.set(obj, value); }
9
+
10
+ function _checkPrivateRedeclaration(obj, privateCollection) { if (privateCollection.has(obj)) { throw new TypeError("Cannot initialize the same private elements twice on an object"); } }
11
+
12
+ function _classPrivateMethodGet(receiver, privateSet, fn) { if (!privateSet.has(receiver)) { throw new TypeError("attempted to get private field on non-instance"); } return fn; }
13
+
14
+ import dialogPolyfill from 'dialog-polyfill';
15
+ import { defineCustomElement, getBooleanAttribute, getLiteralAttribute, getRect, isAttrTrue, updateLiteralAttribute, getReactEventHandler, updateBooleanAttribute } from '../utils';
16
+ const templateHTML = '<style>:host{display:inline-block;vertical-align:middle;outline:0}#wrapper{position:relative}dialog{outline:0;font:var(--sinch-font-body);color:var(--sinch-color-text-default);background-color:var(--sinch-color-snow-100);box-shadow:1px 2px 6px rgba(0,0,0,.15);border:1px solid var(--sinch-color-snow-500);border-radius:4px;overflow-y:auto;contain:content;padding:12px;box-sizing:border-box}dialog:not([open]){display:none}dialog::backdrop{background-color:transparent}dialog+.backdrop{position:fixed;top:0;right:0;bottom:0;left:0;background-color:transparent}dialog.fixed{position:fixed;top:50%;transform:translate(0,-50%)}._dialog_overlay{position:fixed;top:0;right:0;bottom:0;left:0}</style><div id="wrapper"><div id="target" aria-haspopup="dialog" aria-expanded="false"><slot name="target"></slot></div><dialog id="dialog" tabindex="-1"><slot name="content"></slot></dialog></div>';
17
+ const orientationValues = ['top-left', 'top-right', 'bottom-left', 'bottom-right'];
18
+ const template = document.createElement('template');
19
+ template.innerHTML = templateHTML;
20
+ defineCustomElement('sinch-popover', (_$target = new WeakMap(), _$dialog = new WeakMap(), _isConnected = new WeakMap(), _onExpand = new WeakSet(), _onCollapse = new WeakSet(), _isOpen = new WeakSet(), _updateOrientation = new WeakSet(), _onBackdropClick = new WeakMap(), _onCancel = new WeakMap(), _onCloseReactHandler = new WeakMap(), _dispatchCloseEvent = new WeakSet(), class extends HTMLElement {
21
+ constructor() {
22
+ super();
23
+
24
+ _classPrivateMethodInitSpec(this, _dispatchCloseEvent);
25
+
26
+ _classPrivateMethodInitSpec(this, _updateOrientation);
27
+
28
+ _classPrivateMethodInitSpec(this, _isOpen);
29
+
30
+ _classPrivateMethodInitSpec(this, _onCollapse);
31
+
32
+ _classPrivateMethodInitSpec(this, _onExpand);
33
+
34
+ _classPrivateFieldInitSpec(this, _$target, {
35
+ writable: true,
36
+ value: void 0
37
+ });
38
+
39
+ _classPrivateFieldInitSpec(this, _$dialog, {
40
+ writable: true,
41
+ value: void 0
42
+ });
43
+
44
+ _classPrivateFieldInitSpec(this, _isConnected, {
45
+ writable: true,
46
+ value: false
47
+ });
48
+
49
+ _classPrivateFieldInitSpec(this, _onBackdropClick, {
50
+ writable: true,
51
+ value: e => {
52
+ const rect = this.popoverRect;
53
+ const isInside = e.x >= rect.x && e.x < rect.x + rect.width && e.y >= rect.y && e.y < rect.y + rect.height;
54
+
55
+ if (!isInside) {
56
+ _classPrivateMethodGet(this, _dispatchCloseEvent, _dispatchCloseEvent2).call(this);
57
+ }
58
+ }
59
+ });
60
+
61
+ _classPrivateFieldInitSpec(this, _onCancel, {
62
+ writable: true,
63
+ value: e => {
64
+ e.preventDefault();
65
+
66
+ _classPrivateMethodGet(this, _dispatchCloseEvent, _dispatchCloseEvent2).call(this);
67
+ }
68
+ });
69
+
70
+ _classPrivateFieldInitSpec(this, _onCloseReactHandler, {
71
+ writable: true,
72
+ value: () => {
73
+ getReactEventHandler(this, 'onClose')?.();
74
+ }
75
+ });
76
+
77
+ const shadowRoot = this.attachShadow({
78
+ mode: 'closed',
79
+ delegatesFocus: true
80
+ });
81
+ shadowRoot.appendChild(template.content.cloneNode(true));
82
+
83
+ _classPrivateFieldSet(this, _$target, shadowRoot.querySelector('#target'));
84
+
85
+ _classPrivateFieldSet(this, _$dialog, shadowRoot.querySelector('#dialog'));
86
+
87
+ dialogPolyfill.registerDialog(_classPrivateFieldGet(this, _$dialog));
88
+ }
89
+
90
+ connectedCallback() {
91
+ this.setAttribute('role', 'dialog');
92
+
93
+ _classPrivateFieldGet(this, _$dialog).addEventListener('cancel', _classPrivateFieldGet(this, _onCancel));
94
+
95
+ _classPrivateFieldGet(this, _$dialog).addEventListener('click', _classPrivateFieldGet(this, _onBackdropClick));
96
+
97
+ this.addEventListener('close', _classPrivateFieldGet(this, _onCloseReactHandler));
98
+
99
+ _classPrivateFieldSet(this, _isConnected, true);
100
+
101
+ if (getBooleanAttribute(this, 'open')) {
102
+ _classPrivateMethodGet(this, _onExpand, _onExpand2).call(this);
103
+ } else {
104
+ _classPrivateMethodGet(this, _onCollapse, _onCollapse2).call(this);
105
+ }
106
+ }
107
+
108
+ disconnectedCallback() {
109
+ _classPrivateFieldGet(this, _$dialog).removeEventListener('cancel', _classPrivateFieldGet(this, _onCancel));
110
+
111
+ _classPrivateFieldGet(this, _$dialog).removeEventListener('click', _classPrivateFieldGet(this, _onBackdropClick));
112
+
113
+ this.removeEventListener('close', _classPrivateFieldGet(this, _onCloseReactHandler));
114
+
115
+ _classPrivateFieldSet(this, _isConnected, false);
116
+ }
117
+
118
+ static get observedAttributes() {
119
+ return ['open', 'orientation'];
120
+ }
121
+
122
+ set open(isOpen) {
123
+ updateBooleanAttribute(this, 'open', isOpen);
124
+ }
125
+
126
+ get open() {
127
+ return getBooleanAttribute(this, 'open');
128
+ }
129
+
130
+ get orientation() {
131
+ return getLiteralAttribute(this, orientationValues, 'orientation', 'bottom-right');
132
+ }
133
+
134
+ set orientation(value) {
135
+ updateLiteralAttribute(this, orientationValues, 'orientation', value);
136
+ }
137
+
138
+ get popoverRect() {
139
+ return getRect(_classPrivateFieldGet(this, _$dialog));
140
+ }
141
+
142
+ attributeChangedCallback(name, oldVal, newVal) {
143
+ switch (name) {
144
+ case 'open':
145
+ {
146
+ if (_classPrivateFieldGet(this, _isConnected)) {
147
+ if (isAttrTrue(newVal)) {
148
+ _classPrivateMethodGet(this, _onExpand, _onExpand2).call(this);
149
+ } else {
150
+ _classPrivateMethodGet(this, _onCollapse, _onCollapse2).call(this);
151
+ }
152
+ }
153
+
154
+ break;
155
+ }
156
+
157
+ case 'orientation':
158
+ {
159
+ if (_classPrivateMethodGet(this, _isOpen, _isOpen2).call(this)) {
160
+ _classPrivateMethodGet(this, _updateOrientation, _updateOrientation2).call(this);
161
+ }
162
+
163
+ break;
164
+ }
165
+ }
166
+ }
167
+
168
+ }));
169
+
170
+ function _onExpand2() {
171
+ _classPrivateFieldGet(this, _$target).setAttribute('aria-expanded', 'true');
172
+
173
+ if (!_classPrivateMethodGet(this, _isOpen, _isOpen2).call(this)) {
174
+ _classPrivateFieldGet(this, _$dialog).showModal();
175
+ }
176
+
177
+ _classPrivateMethodGet(this, _updateOrientation, _updateOrientation2).call(this);
178
+ }
179
+
180
+ function _onCollapse2() {
181
+ _classPrivateFieldGet(this, _$target).setAttribute('aria-expanded', 'false');
182
+
183
+ if (_classPrivateMethodGet(this, _isOpen, _isOpen2).call(this)) {
184
+ _classPrivateFieldGet(this, _$dialog).close?.();
185
+ }
186
+ }
187
+
188
+ function _isOpen2() {
189
+ return _classPrivateFieldGet(this, _isConnected) && getBooleanAttribute(_classPrivateFieldGet(this, _$dialog), 'open');
190
+ }
191
+
192
+ function _updateOrientation2() {
193
+ _classPrivateFieldGet(this, _$dialog).style.transform = `initial`;
194
+ _classPrivateFieldGet(this, _$dialog).style.width = `max-content`;
195
+
196
+ const buttonRect = _classPrivateFieldGet(this, _$target).getBoundingClientRect();
197
+
198
+ const modalRect = _classPrivateFieldGet(this, _$dialog).getBoundingClientRect();
199
+
200
+ const width = Math.max(modalRect.width, buttonRect.width);
201
+ const widthDiff = Math.max(buttonRect.width - modalRect.width, 0);
202
+ let leftOffset = 0;
203
+ let topOffset = 0;
204
+ const orient = this.orientation;
205
+
206
+ if (orient === 'bottom-right' || orient === 'top-right') {
207
+ leftOffset = Math.min(modalRect.x, Math.max(-modalRect.x, buttonRect.x - modalRect.x + widthDiff * 0.5));
208
+ }
209
+
210
+ if (orient === 'bottom-left' || orient === 'top-left') {
211
+ leftOffset = Math.min(modalRect.x, Math.max(-modalRect.x, buttonRect.x + buttonRect.width - modalRect.x - modalRect.width - widthDiff * 0.5));
212
+ }
213
+
214
+ if (orient === 'bottom-left' || orient === 'bottom-right') {
215
+ topOffset = Math.min(modalRect.y, Math.max(-modalRect.y, buttonRect.y + buttonRect.height - modalRect.y + 8));
216
+ }
217
+
218
+ if (orient === 'top-left' || orient === 'top-right') {
219
+ topOffset = Math.min(modalRect.y, Math.max(-modalRect.y, buttonRect.y - modalRect.y - modalRect.height - 8));
220
+ }
221
+
222
+ _classPrivateFieldGet(this, _$dialog).style.transform = `translateX(${leftOffset}px) translateY(${topOffset}px)`;
223
+ _classPrivateFieldGet(this, _$dialog).style.width = `${width}px`;
224
+ }
225
+
226
+ function _dispatchCloseEvent2() {
227
+ this.dispatchEvent(new CustomEvent('close', {
228
+ bubbles: true
229
+ }));
230
+ }
package/search/index.d.ts CHANGED
@@ -8,6 +8,9 @@ export declare type TSinchSearchElement = HTMLElement & {
8
8
  label: string | null;
9
9
  placeholder: string | null;
10
10
  maxVisibleItems: number | null;
11
+ selectionStart: HTMLInputElement['selectionStart'];
12
+ selectionEnd: HTMLInputElement['selectionEnd'];
13
+ selectionDirection: HTMLInputElement['selectionDirection'];
11
14
  readonly dropdownRect: TRect;
12
15
  focus(): void;
13
16
  blur(): void;