@jungherz-de/glasskit-elements 0.8.3 → 0.9.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/README.md +23 -13
- package/dist/glasskit-elements.esm.js +291 -3
- package/dist/glasskit-elements.js +293 -2
- package/dist/glasskit-elements.min.js +1 -1
- package/package.json +3 -3
- package/src/components/containers/glk-list-item.js +135 -0
- package/src/components/containers/glk-list.js +55 -0
- package/src/components/feedback/glk-popover.js +108 -0
- package/src/index.js +3 -0
|
@@ -0,0 +1,108 @@
|
|
|
1
|
+
import { GlkElement } from '../../base.js';
|
|
2
|
+
|
|
3
|
+
const PLACEMENTS = ['top', 'bottom', 'start', 'end'];
|
|
4
|
+
|
|
5
|
+
class GlkPopover extends GlkElement {
|
|
6
|
+
static get observedAttributes() {
|
|
7
|
+
return ['open', 'placement'];
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
render() {
|
|
11
|
+
this._anchor = this.createElement('div', ['glass-popover-anchor']);
|
|
12
|
+
|
|
13
|
+
const triggerSlot = document.createElement('slot');
|
|
14
|
+
triggerSlot.setAttribute('name', 'trigger');
|
|
15
|
+
this._anchor.appendChild(triggerSlot);
|
|
16
|
+
|
|
17
|
+
this._popover = this.createElement('div', ['glass-popover']);
|
|
18
|
+
this._applyPlacement();
|
|
19
|
+
if (this.getBoolAttr('open')) {
|
|
20
|
+
this._popover.classList.add('is-open');
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
const contentSlot = document.createElement('slot');
|
|
24
|
+
this._popover.appendChild(contentSlot);
|
|
25
|
+
|
|
26
|
+
this._anchor.appendChild(this._popover);
|
|
27
|
+
this._wrapper.appendChild(this._anchor);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
_applyPlacement() {
|
|
31
|
+
if (!this._popover) return;
|
|
32
|
+
PLACEMENTS.forEach(p => this._popover.classList.remove(`glass-popover--${p}`));
|
|
33
|
+
const placement = this.getAttribute('placement') || 'bottom';
|
|
34
|
+
if (placement !== 'bottom' && PLACEMENTS.includes(placement)) {
|
|
35
|
+
this._popover.classList.add(`glass-popover--${placement}`);
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
setupEvents() {
|
|
40
|
+
// Toggle when the slotted trigger is clicked.
|
|
41
|
+
this._onTriggerClick = (e) => {
|
|
42
|
+
const path = e.composedPath();
|
|
43
|
+
const hitTrigger = path.some(node => {
|
|
44
|
+
return node instanceof Element && node.getAttribute && node.getAttribute('slot') === 'trigger';
|
|
45
|
+
});
|
|
46
|
+
if (!hitTrigger) return;
|
|
47
|
+
e.stopPropagation();
|
|
48
|
+
this.toggle();
|
|
49
|
+
};
|
|
50
|
+
this.addEventListener('click', this._onTriggerClick);
|
|
51
|
+
|
|
52
|
+
// Close on outside click.
|
|
53
|
+
this._onDocClick = (e) => {
|
|
54
|
+
if (!this.getBoolAttr('open')) return;
|
|
55
|
+
const path = e.composedPath();
|
|
56
|
+
if (path.includes(this)) return;
|
|
57
|
+
this.close();
|
|
58
|
+
};
|
|
59
|
+
document.addEventListener('click', this._onDocClick);
|
|
60
|
+
|
|
61
|
+
// Close on Escape.
|
|
62
|
+
this._onKeydown = (e) => {
|
|
63
|
+
if (e.key === 'Escape' && this.getBoolAttr('open')) {
|
|
64
|
+
this.close();
|
|
65
|
+
}
|
|
66
|
+
};
|
|
67
|
+
document.addEventListener('keydown', this._onKeydown);
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
teardownEvents() {
|
|
71
|
+
this.removeEventListener('click', this._onTriggerClick);
|
|
72
|
+
document.removeEventListener('click', this._onDocClick);
|
|
73
|
+
document.removeEventListener('keydown', this._onKeydown);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
onAttributeChanged(name) {
|
|
77
|
+
if (!this._popover) return;
|
|
78
|
+
switch (name) {
|
|
79
|
+
case 'open': {
|
|
80
|
+
const isOpen = this.getBoolAttr('open');
|
|
81
|
+
this._popover.classList.toggle('is-open', isOpen);
|
|
82
|
+
this.emit(isOpen ? 'glk-open' : 'glk-close');
|
|
83
|
+
break;
|
|
84
|
+
}
|
|
85
|
+
case 'placement':
|
|
86
|
+
this._applyPlacement();
|
|
87
|
+
break;
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
show() { this.setAttribute('open', ''); }
|
|
92
|
+
close() { this.removeAttribute('open'); }
|
|
93
|
+
toggle() {
|
|
94
|
+
if (this.getBoolAttr('open')) this.close();
|
|
95
|
+
else this.show();
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
get open() { return this.getBoolAttr('open'); }
|
|
99
|
+
set open(v) { this.setBoolAttr('open', v); }
|
|
100
|
+
|
|
101
|
+
get placement() { return this.getAttribute('placement') || 'bottom'; }
|
|
102
|
+
set placement(v) {
|
|
103
|
+
if (PLACEMENTS.includes(v)) this.setAttribute('placement', v);
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
customElements.define('glk-popover', GlkPopover);
|
|
108
|
+
export { GlkPopover };
|
package/src/index.js
CHANGED
|
@@ -32,7 +32,10 @@ export { GlkRange } from './components/forms/glk-range.js';
|
|
|
32
32
|
export { GlkProgress } from './components/feedback/glk-progress.js';
|
|
33
33
|
export { GlkModal } from './components/feedback/glk-modal.js';
|
|
34
34
|
export { GlkToast } from './components/feedback/glk-toast.js';
|
|
35
|
+
export { GlkPopover } from './components/feedback/glk-popover.js';
|
|
35
36
|
|
|
36
37
|
// Containers
|
|
37
38
|
export { GlkAccordion } from './components/containers/glk-accordion.js';
|
|
38
39
|
export { GlkAccordionItem } from './components/containers/glk-accordion-item.js';
|
|
40
|
+
export { GlkList } from './components/containers/glk-list.js';
|
|
41
|
+
export { GlkListItem } from './components/containers/glk-list-item.js';
|