kempo-ui 0.0.2 → 0.0.3
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/.github/copilot-instructions.md +149 -149
- package/.github/workflows/publish-npm.yml +44 -44
- package/CONTRIBUTING.md +149 -149
- package/README.md +0 -0
- package/dist/kempo-vars.css +0 -0
- package/dist/src/components/FocusCapture.js +7 -0
- package/dist/src/components/Icon.js +10 -0
- package/dist/src/components/Import.js +1 -0
- package/dist/src/components/ShadowComponent.js +1 -0
- package/dist/src/components/SideMenu.js +97 -0
- package/dist/src/lit-all.min.js +120 -0
- package/docs/components/accordion.html +122 -0
- package/docs/components/card.html +91 -0
- package/docs/components/component.html +90 -0
- package/docs/components/content-slider.html +193 -0
- package/docs/components/dialog.html +245 -0
- package/docs/components/directory-viewer.html +90 -0
- package/docs/components/focus-capture.html +68 -0
- package/docs/components/icon.html +161 -0
- package/docs/components/import.html +78 -0
- package/docs/components/lazy-component.html +84 -0
- package/docs/components/reactive-component.html +69 -0
- package/docs/components/reactive-lazy-component.html +69 -0
- package/docs/components/resize.html +152 -0
- package/docs/components/search.html +102 -0
- package/docs/components/show-more.html +123 -0
- package/docs/components/side-menu.html +168 -0
- package/docs/components/sortable.html +96 -0
- package/docs/components/split.html +126 -0
- package/docs/components/table.html +312 -0
- package/docs/components/tableControls.html +77 -0
- package/docs/components/tableCustomFields.html +113 -0
- package/docs/components/tableFetchRecords.html +114 -0
- package/docs/components/tableFieldSortHide.html +75 -0
- package/docs/components/tablePagination.html +100 -0
- package/docs/components/tableRecordEditing.html +144 -0
- package/docs/components/tableRecordFiltering.html +75 -0
- package/docs/components/tableRecordHiding.html +80 -0
- package/docs/components/tableRecordSearching.html +75 -0
- package/docs/components/tableRecordSelection.html +75 -0
- package/docs/components/tableRowControls.html +78 -0
- package/docs/components/tableSorting.html +73 -0
- package/docs/components/tabs.html +163 -0
- package/docs/components/tags.html +94 -0
- package/docs/components/theme-switcher.html +129 -0
- package/docs/components/timestamp.html +86 -0
- package/docs/components/toast.html +328 -0
- package/docs/components/toggle.html +155 -0
- package/docs/dev.config.json +20 -0
- package/docs/icons/add.svg +1 -0
- package/docs/icons/arrow-back.svg +1 -0
- package/docs/icons/arrow-down-double.svg +1 -0
- package/docs/icons/arrow-down.svg +1 -0
- package/docs/icons/arrow-forward.svg +1 -0
- package/docs/icons/arrow-up-double.svg +1 -0
- package/docs/icons/arrow-up.svg +1 -0
- package/docs/icons/cards.svg +1 -0
- package/docs/icons/check.svg +1 -0
- package/docs/icons/chevron-left.svg +1 -0
- package/docs/icons/chevron-right.svg +1 -0
- package/docs/icons/close.svg +2 -0
- package/docs/icons/compare.svg +1 -0
- package/docs/icons/delete.svg +1 -0
- package/docs/icons/drag-handle.svg +1 -0
- package/docs/icons/drawing2.svg +124 -0
- package/docs/icons/edit.svg +1 -0
- package/docs/icons/error.svg +1 -0
- package/docs/icons/export-file.svg +1 -0
- package/docs/icons/file-text.svg +1 -0
- package/docs/icons/file.svg +1 -0
- package/docs/icons/filter-off.svg +1 -0
- package/docs/icons/filter.svg +1 -0
- package/docs/icons/first.svg +1 -0
- package/docs/icons/folder-clear.svg +1 -0
- package/docs/icons/folder-create.svg +1 -0
- package/docs/icons/folder-open.svg +1 -0
- package/docs/icons/folder.svg +1 -0
- package/docs/icons/hide.svg +1 -0
- package/docs/icons/image.svg +1 -0
- package/docs/icons/label-add.svg +1 -0
- package/docs/icons/label.svg +1 -0
- package/docs/icons/last.svg +1 -0
- package/docs/icons/menu.svg +1 -0
- package/docs/icons/mode-auto.svg +1 -0
- package/docs/icons/mode-dark.svg +1 -0
- package/docs/icons/mode-light.svg +1 -0
- package/docs/icons/open-in-browser.svg +1 -0
- package/docs/icons/pause.svg +1 -0
- package/docs/icons/play.svg +1 -0
- package/docs/icons/refresh.svg +1 -0
- package/docs/icons/remove.svg +1 -0
- package/docs/icons/save.svg +1 -0
- package/docs/icons/search.svg +1 -0
- package/docs/icons/settings.svg +1 -0
- package/docs/icons/show.svg +1 -0
- package/docs/icons/storage.svg +1 -0
- package/docs/icons/table-visibility.svg +1 -0
- package/docs/icons/tag.svg +1 -0
- package/docs/icons/tools.svg +1 -0
- package/docs/icons/trash-x.svg +1 -0
- package/docs/icons/warning.svg +1 -0
- package/docs/index.html +28 -21
- package/docs/nav.inc.html +73 -0
- package/docs/nav.inc.js +4 -0
- package/{config/production.json → docs/prod.config.json} +20 -16
- package/docs/src/components/FocusCapture.js +7 -0
- package/docs/src/components/HybridComponent.js +1 -0
- package/docs/src/components/Icon.js +10 -0
- package/docs/src/components/Import.js +1 -0
- package/docs/src/components/LightComponent.js +1 -0
- package/docs/src/components/ShadowComponent.js +1 -0
- package/docs/src/components/SideMenu.js +97 -0
- package/docs/src/lit-all.min.js +120 -0
- package/docs/src/utils/cli.js +1 -0
- package/docs/src/utils/fs-utils.js +1 -0
- package/docs/styles.css +6 -0
- package/icons/add.svg +1 -0
- package/icons/arrow-back.svg +1 -0
- package/icons/arrow-down-double.svg +1 -0
- package/icons/arrow-down.svg +1 -0
- package/icons/arrow-forward.svg +1 -0
- package/icons/arrow-up-double.svg +1 -0
- package/icons/arrow-up.svg +1 -0
- package/icons/cards.svg +1 -0
- package/icons/check.svg +1 -0
- package/icons/chevron-left.svg +1 -0
- package/icons/chevron-right.svg +1 -0
- package/icons/close.svg +2 -0
- package/icons/compare.svg +1 -0
- package/icons/delete.svg +1 -0
- package/icons/drag-handle.svg +1 -0
- package/icons/drawing2.svg +124 -0
- package/icons/edit.svg +1 -0
- package/icons/error.svg +1 -0
- package/icons/export-file.svg +1 -0
- package/icons/file-text.svg +1 -0
- package/icons/file.svg +1 -0
- package/icons/filter-off.svg +1 -0
- package/icons/filter.svg +1 -0
- package/icons/first.svg +1 -0
- package/icons/folder-clear.svg +1 -0
- package/icons/folder-create.svg +1 -0
- package/icons/folder-open.svg +1 -0
- package/icons/folder.svg +1 -0
- package/icons/hide.svg +1 -0
- package/icons/image.svg +1 -0
- package/icons/label-add.svg +1 -0
- package/icons/label.svg +1 -0
- package/icons/last.svg +1 -0
- package/icons/menu.svg +1 -0
- package/icons/mode-auto.svg +1 -0
- package/icons/mode-dark.svg +1 -0
- package/icons/mode-light.svg +1 -0
- package/icons/open-in-browser.svg +1 -0
- package/icons/pause.svg +1 -0
- package/icons/play.svg +1 -0
- package/icons/refresh.svg +1 -0
- package/icons/remove.svg +1 -0
- package/icons/save.svg +1 -0
- package/icons/search.svg +1 -0
- package/icons/settings.svg +1 -0
- package/icons/show.svg +1 -0
- package/icons/storage.svg +1 -0
- package/icons/table-visibility.svg +1 -0
- package/icons/tag.svg +1 -0
- package/icons/tools.svg +1 -0
- package/icons/trash-x.svg +1 -0
- package/icons/warning.svg +1 -0
- package/package.json +2 -2
- package/scripts/build.js +109 -138
- package/scripts/docs.js +60 -60
- package/src/components/Card.js +66 -0
- package/src/components/FocusCapture.js +23 -0
- package/src/components/HybridComponent.js +40 -40
- package/src/components/Icon.js +155 -0
- package/src/components/Import.js +104 -0
- package/src/components/LightComponent.js +32 -32
- package/src/components/ShadowComponent.js +30 -17
- package/src/components/SideMenu.js +167 -0
- package/src/components/ThemeSwitcher.js +108 -0
- package/src/kempo-hljs.css +146 -0
- package/src/utils/cli.js +43 -43
- package/src/utils/fs-utils.js +41 -41
- package/src/utils/propConverters.js +11 -0
- package/tests/HybridComponent.browser-test.js +214 -214
- package/tests/LightComponent.browser-test.js +169 -169
- package/tests/ShadowComponent.browser-test.js +130 -130
- package/config/development.json +0 -14
- package/docs/components/ShadowComponent.js +0 -1
- /package/{docs → dist/src}/components/HybridComponent.js +0 -0
- /package/{docs → dist/src}/components/LightComponent.js +0 -0
- /package/{docs → dist/src}/utils/cli.js +0 -0
- /package/{docs → dist/src}/utils/fs-utils.js +0 -0
|
@@ -1,40 +1,40 @@
|
|
|
1
|
-
import { html, render } from '../lit-all.min.js';
|
|
2
|
-
import ShadowComponent from './ShadowComponent.js';
|
|
3
|
-
|
|
4
|
-
export default class HybridComponent extends ShadowComponent {
|
|
5
|
-
|
|
6
|
-
/*
|
|
7
|
-
Shadow DOM Setup
|
|
8
|
-
*/
|
|
9
|
-
|
|
10
|
-
createRenderRoot() {
|
|
11
|
-
const renderContainer = super.createRenderRoot();
|
|
12
|
-
|
|
13
|
-
this.lightRoot = document.createElement('div');
|
|
14
|
-
this.lightRoot.style.display = 'contents';
|
|
15
|
-
this.lightRoot.slot = 'lightRoot';
|
|
16
|
-
this.appendChild(this.lightRoot);
|
|
17
|
-
|
|
18
|
-
return renderContainer;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
/*
|
|
22
|
-
Lifecycle Callbacks
|
|
23
|
-
*/
|
|
24
|
-
|
|
25
|
-
updated() {
|
|
26
|
-
render(this.renderLightDom(), this.lightRoot);
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
/*
|
|
30
|
-
Rendering
|
|
31
|
-
*/
|
|
32
|
-
|
|
33
|
-
renderLightDom() {
|
|
34
|
-
return html``;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
render() {
|
|
38
|
-
return html`<slot name="lightRoot"></slot>`;
|
|
39
|
-
}
|
|
40
|
-
}
|
|
1
|
+
import { html, render } from '../lit-all.min.js';
|
|
2
|
+
import ShadowComponent from './ShadowComponent.js';
|
|
3
|
+
|
|
4
|
+
export default class HybridComponent extends ShadowComponent {
|
|
5
|
+
|
|
6
|
+
/*
|
|
7
|
+
Shadow DOM Setup
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
createRenderRoot() {
|
|
11
|
+
const renderContainer = super.createRenderRoot();
|
|
12
|
+
|
|
13
|
+
this.lightRoot = document.createElement('div');
|
|
14
|
+
this.lightRoot.style.display = 'contents';
|
|
15
|
+
this.lightRoot.slot = 'lightRoot';
|
|
16
|
+
this.appendChild(this.lightRoot);
|
|
17
|
+
|
|
18
|
+
return renderContainer;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
/*
|
|
22
|
+
Lifecycle Callbacks
|
|
23
|
+
*/
|
|
24
|
+
|
|
25
|
+
updated() {
|
|
26
|
+
render(this.renderLightDom(), this.lightRoot);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
/*
|
|
30
|
+
Rendering
|
|
31
|
+
*/
|
|
32
|
+
|
|
33
|
+
renderLightDom() {
|
|
34
|
+
return html``;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
render() {
|
|
38
|
+
return html`<slot name="lightRoot"></slot>`;
|
|
39
|
+
}
|
|
40
|
+
}
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
import ShadowComponent from './ShadowComponent.js';
|
|
2
|
+
import { html, css, unsafeHTML } from '../lit-all.min.js';
|
|
3
|
+
|
|
4
|
+
const cache = {};
|
|
5
|
+
|
|
6
|
+
const getIconByPath = async (path) => {
|
|
7
|
+
if (!cache[path]) {
|
|
8
|
+
cache[path] = new Promise(async (resolve, reject) => {
|
|
9
|
+
const controller = new AbortController();
|
|
10
|
+
const signal = controller.signal;
|
|
11
|
+
try {
|
|
12
|
+
const response = await fetch(path, { signal });
|
|
13
|
+
if (response.status === 200) {
|
|
14
|
+
resolve(await response.text());
|
|
15
|
+
} else if (response.status === 404) {
|
|
16
|
+
resolve(null);
|
|
17
|
+
}
|
|
18
|
+
} catch (e) {
|
|
19
|
+
if (e.name !== 'AbortError') {
|
|
20
|
+
reject(e);
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
}).catch(() => null);
|
|
24
|
+
}
|
|
25
|
+
return await cache[path];
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
const getIconByName = (name) => {
|
|
29
|
+
const tryDir = async (dir) => getIconByPath(`${dir}/${name}.svg`);
|
|
30
|
+
|
|
31
|
+
return new Promise(async (resolve, reject) => {
|
|
32
|
+
let svg;
|
|
33
|
+
for(let i = 0; i < Icon.pathToIcons.length && !svg; i++){
|
|
34
|
+
try {
|
|
35
|
+
svg = await tryDir(Icon.pathToIcons[i]);
|
|
36
|
+
} catch(e){}
|
|
37
|
+
}
|
|
38
|
+
if(svg){
|
|
39
|
+
resolve(svg);
|
|
40
|
+
} else {
|
|
41
|
+
resolve(null);
|
|
42
|
+
}
|
|
43
|
+
});
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
export default class Icon extends ShadowComponent {
|
|
47
|
+
/*
|
|
48
|
+
Properties
|
|
49
|
+
*/
|
|
50
|
+
static properties = {
|
|
51
|
+
src: { type: String, reflect: true },
|
|
52
|
+
name: { type: String, reflect: true },
|
|
53
|
+
iconContent: { type: String }
|
|
54
|
+
};
|
|
55
|
+
|
|
56
|
+
constructor(name = '') {
|
|
57
|
+
super();
|
|
58
|
+
this.src = '';
|
|
59
|
+
this.name = name;
|
|
60
|
+
this.iconContent = '';
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
/*
|
|
64
|
+
Lifecycle Callbacks
|
|
65
|
+
*/
|
|
66
|
+
updated(changedProperties) {
|
|
67
|
+
super.updated();
|
|
68
|
+
|
|
69
|
+
if (changedProperties.has('src') || changedProperties.has('name')) {
|
|
70
|
+
this.loadIcon();
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
if (changedProperties.has('iconContent')) {
|
|
74
|
+
this.fixSVG();
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
/*
|
|
79
|
+
Methods
|
|
80
|
+
*/
|
|
81
|
+
async loadIcon() {
|
|
82
|
+
let svg;
|
|
83
|
+
|
|
84
|
+
if (this.src) {
|
|
85
|
+
svg = await getIconByPath(this.src);
|
|
86
|
+
} else if (this.name) {
|
|
87
|
+
svg = await getIconByName(this.name);
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
if (svg) {
|
|
91
|
+
this.iconContent = svg;
|
|
92
|
+
} else {
|
|
93
|
+
// Check for slotted fallback content first
|
|
94
|
+
const slottedContent = this.innerHTML.trim();
|
|
95
|
+
if (slottedContent) {
|
|
96
|
+
this.iconContent = slottedContent;
|
|
97
|
+
} else {
|
|
98
|
+
this.iconContent = Icon.fallback;
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
fixSVG() {
|
|
104
|
+
// Use setTimeout to ensure DOM is updated
|
|
105
|
+
setTimeout(() => {
|
|
106
|
+
const $svg = this.querySelector('svg');
|
|
107
|
+
if ($svg) {
|
|
108
|
+
$svg.removeAttribute('width');
|
|
109
|
+
$svg.removeAttribute('height');
|
|
110
|
+
$svg.querySelectorAll('path, rect, circle').forEach($path => {
|
|
111
|
+
$path.setAttribute('fill', 'currentColor');
|
|
112
|
+
});
|
|
113
|
+
}
|
|
114
|
+
}, 0);
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
/*
|
|
118
|
+
Styles
|
|
119
|
+
*/
|
|
120
|
+
static styles = css`
|
|
121
|
+
:host {
|
|
122
|
+
display: inline-block;
|
|
123
|
+
vertical-align: bottom;
|
|
124
|
+
}
|
|
125
|
+
::slotted(svg), svg {
|
|
126
|
+
height: 1.35em;
|
|
127
|
+
vertical-align: middle;
|
|
128
|
+
}
|
|
129
|
+
`;
|
|
130
|
+
|
|
131
|
+
/*
|
|
132
|
+
Rendering
|
|
133
|
+
*/
|
|
134
|
+
render() {
|
|
135
|
+
if (!this.iconContent) {
|
|
136
|
+
// Show slotted content while loading
|
|
137
|
+
return html`<slot></slot>`;
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
return html`${unsafeHTML(this.iconContent)}`;
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
/*
|
|
144
|
+
Static Properties
|
|
145
|
+
*/
|
|
146
|
+
static pathToIcons = [
|
|
147
|
+
'/icons'
|
|
148
|
+
];
|
|
149
|
+
|
|
150
|
+
static fallback = `
|
|
151
|
+
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960"><path fill="currentColor" d="M480-79q-16 0-30.5-6T423-102L102-423q-11-12-17-26.5T79-480q0-16 6-31t17-26l321-321q12-12 26.5-17.5T480-881q16 0 31 5.5t26 17.5l321 321q12 11 17.5 26t5.5 31q0 16-5.5 30.5T858-423L537-102q-11 11-26 17t-31 6Zm0-80 321-321-321-321-321 321 321 321Zm-40-281h80v-240h-80v240Zm40 120q17 0 28.5-11.5T520-360q0-17-11.5-28.5T480-400q-17 0-28.5 11.5T440-360q0 17 11.5 28.5T480-320Zm0-160Z"/></svg>
|
|
152
|
+
`;
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
window.customElements.define('k-icon', Icon);
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
import LightComponent from './LightComponent.js';
|
|
2
|
+
import { html, render, unsafeHTML } from '../lit-all.min.js';
|
|
3
|
+
|
|
4
|
+
export default class Import extends LightComponent {
|
|
5
|
+
/*
|
|
6
|
+
Properties
|
|
7
|
+
*/
|
|
8
|
+
static properties = {
|
|
9
|
+
src: {
|
|
10
|
+
type: String,
|
|
11
|
+
reflect: true
|
|
12
|
+
},
|
|
13
|
+
content: {
|
|
14
|
+
type: String
|
|
15
|
+
},
|
|
16
|
+
scripts: {
|
|
17
|
+
type: Array
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
static replacements = {}
|
|
22
|
+
constructor(){
|
|
23
|
+
super();
|
|
24
|
+
this.src = '';
|
|
25
|
+
this.content = '';
|
|
26
|
+
this.scripts = [];
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
/*
|
|
30
|
+
Lifecycle Callbacks
|
|
31
|
+
*/
|
|
32
|
+
updated(changedProperties){
|
|
33
|
+
super.updated(); // Important: call super for LightComponent
|
|
34
|
+
|
|
35
|
+
if(changedProperties.has('src')){
|
|
36
|
+
this.fetch();
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
if(changedProperties.has('content') && this.scripts.length > 0){
|
|
40
|
+
// Execute scripts after DOM content is rendered
|
|
41
|
+
setTimeout(() => this.executeScripts(), 0);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
/*
|
|
46
|
+
Methods
|
|
47
|
+
*/
|
|
48
|
+
async fetch(){
|
|
49
|
+
let contents = await (await fetch(this.src)).text();
|
|
50
|
+
for (const [name, value] of Object.entries(Import.replacements)) {
|
|
51
|
+
contents = contents.replace(new RegExp(`%%${name}%%`, 'g'), value);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
// Parse the HTML to extract scripts
|
|
55
|
+
const parser = new DOMParser();
|
|
56
|
+
const doc = parser.parseFromString(contents, 'text/html');
|
|
57
|
+
const scriptElements = doc.querySelectorAll('script');
|
|
58
|
+
|
|
59
|
+
// Extract script sources and inline code
|
|
60
|
+
this.scripts = Array.from(scriptElements).map(script => ({
|
|
61
|
+
src: script.src,
|
|
62
|
+
text: script.textContent,
|
|
63
|
+
type: script.type || 'text/javascript'
|
|
64
|
+
}));
|
|
65
|
+
|
|
66
|
+
// Remove script tags from the content
|
|
67
|
+
scriptElements.forEach(script => script.remove());
|
|
68
|
+
|
|
69
|
+
// Serialize back to string without scripts - use the entire body content
|
|
70
|
+
this.content = doc.body ? doc.body.innerHTML : contents;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
executeScripts(){
|
|
74
|
+
this.scripts.forEach(script => {
|
|
75
|
+
const scriptElement = document.createElement('script');
|
|
76
|
+
scriptElement.type = script.type;
|
|
77
|
+
|
|
78
|
+
if (script.src) {
|
|
79
|
+
scriptElement.src = script.src;
|
|
80
|
+
} else if (script.text) {
|
|
81
|
+
scriptElement.textContent = script.text;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
// Append to head to execute
|
|
85
|
+
document.head.appendChild(scriptElement);
|
|
86
|
+
});
|
|
87
|
+
|
|
88
|
+
// Clear scripts after execution to avoid re-execution
|
|
89
|
+
this.scripts = [];
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
/*
|
|
93
|
+
Rendering
|
|
94
|
+
*/
|
|
95
|
+
renderLightDom() {
|
|
96
|
+
if (!this.content) {
|
|
97
|
+
return html``;
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
// Use unsafeHTML to render the actual HTML content
|
|
101
|
+
return html`${unsafeHTML(this.content)}`;
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
window.customElements.define('k-import', Import);
|
|
@@ -1,32 +1,32 @@
|
|
|
1
|
-
import { LitElement, html, render } from '../lit-all.min.js';
|
|
2
|
-
|
|
3
|
-
export default class LightComponent extends LitElement {
|
|
4
|
-
|
|
5
|
-
/*
|
|
6
|
-
Light DOM Setup
|
|
7
|
-
*/
|
|
8
|
-
|
|
9
|
-
createRenderRoot() {
|
|
10
|
-
this.lightRoot = document.createElement('div');
|
|
11
|
-
this.lightRoot.style.display = 'contents';
|
|
12
|
-
this.appendChild(this.lightRoot);
|
|
13
|
-
|
|
14
|
-
return this;
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
/*
|
|
18
|
-
Lifecycle Callbacks
|
|
19
|
-
*/
|
|
20
|
-
|
|
21
|
-
updated() {
|
|
22
|
-
render(this.renderLightDom(), this.lightRoot);
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
/*
|
|
26
|
-
Rendering
|
|
27
|
-
*/
|
|
28
|
-
|
|
29
|
-
renderLightDom() {
|
|
30
|
-
return html``;
|
|
31
|
-
}
|
|
32
|
-
}
|
|
1
|
+
import { LitElement, html, render } from '../lit-all.min.js';
|
|
2
|
+
|
|
3
|
+
export default class LightComponent extends LitElement {
|
|
4
|
+
|
|
5
|
+
/*
|
|
6
|
+
Light DOM Setup
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
createRenderRoot() {
|
|
10
|
+
this.lightRoot = document.createElement('div');
|
|
11
|
+
this.lightRoot.style.display = 'contents';
|
|
12
|
+
this.appendChild(this.lightRoot);
|
|
13
|
+
|
|
14
|
+
return this;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
/*
|
|
18
|
+
Lifecycle Callbacks
|
|
19
|
+
*/
|
|
20
|
+
|
|
21
|
+
updated() {
|
|
22
|
+
render(this.renderLightDom(), this.lightRoot);
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
/*
|
|
26
|
+
Rendering
|
|
27
|
+
*/
|
|
28
|
+
|
|
29
|
+
renderLightDom() {
|
|
30
|
+
return html``;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
@@ -1,17 +1,30 @@
|
|
|
1
|
-
import { LitElement } from '../lit-all.min.js';
|
|
2
|
-
|
|
3
|
-
export default class ShadowComponent extends LitElement {
|
|
4
|
-
createRenderRoot() {
|
|
5
|
-
const shadowRoot = this.attachShadow({ mode: 'open' });
|
|
6
|
-
|
|
7
|
-
const link = document.createElement('link');
|
|
8
|
-
link.rel = 'stylesheet';
|
|
9
|
-
link.href = '/kempo.min.css';
|
|
10
|
-
shadowRoot.appendChild(link);
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
1
|
+
import { LitElement } from '../lit-all.min.js';
|
|
2
|
+
|
|
3
|
+
export default class ShadowComponent extends LitElement {
|
|
4
|
+
createRenderRoot() {
|
|
5
|
+
const shadowRoot = this.attachShadow({ mode: 'open' });
|
|
6
|
+
|
|
7
|
+
const link = document.createElement('link');
|
|
8
|
+
link.rel = 'stylesheet';
|
|
9
|
+
link.href = '/kempo.min.css';
|
|
10
|
+
shadowRoot.appendChild(link);
|
|
11
|
+
|
|
12
|
+
// Inject component styles if they exist
|
|
13
|
+
const styles = this.constructor.styles;
|
|
14
|
+
if (styles) {
|
|
15
|
+
const styleEl = document.createElement('style');
|
|
16
|
+
if (Array.isArray(styles)) {
|
|
17
|
+
styleEl.textContent = styles.map(s => s.cssText || s).join('\n');
|
|
18
|
+
} else {
|
|
19
|
+
styleEl.textContent = styles.cssText || styles;
|
|
20
|
+
}
|
|
21
|
+
shadowRoot.appendChild(styleEl);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
const renderContainer = document.createElement('div');
|
|
25
|
+
renderContainer.style.display = 'contents';
|
|
26
|
+
shadowRoot.appendChild(renderContainer);
|
|
27
|
+
|
|
28
|
+
return renderContainer;
|
|
29
|
+
}
|
|
30
|
+
}
|
|
@@ -0,0 +1,167 @@
|
|
|
1
|
+
import ShadowComponent from './ShadowComponent.js';
|
|
2
|
+
import { html, css } from '../lit-all.min.js';
|
|
3
|
+
import { boolTrueFalse } from '../utils/propConverters.js';
|
|
4
|
+
import './FocusCapture.js';
|
|
5
|
+
|
|
6
|
+
export default class SideMenu extends ShadowComponent {
|
|
7
|
+
/*
|
|
8
|
+
Properties
|
|
9
|
+
*/
|
|
10
|
+
static properties = {
|
|
11
|
+
opened: { type: Boolean, reflect: true },
|
|
12
|
+
overlayClose: { type: Boolean, reflect: true, attribute: 'overlay-close', converter: boolTrueFalse },
|
|
13
|
+
side: { type: String, reflect: true }
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
constructor() {
|
|
17
|
+
super();
|
|
18
|
+
this.opened = false;
|
|
19
|
+
this.overlayClose = true;
|
|
20
|
+
this.side = 'left';
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
/*
|
|
24
|
+
Event Handlers
|
|
25
|
+
*/
|
|
26
|
+
overlayClick = () => {
|
|
27
|
+
if(this.overlayClose) this.close();
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/*
|
|
31
|
+
Lifecycle Callbacks
|
|
32
|
+
*/
|
|
33
|
+
updated(changedProperties) {
|
|
34
|
+
super.updated(changedProperties);
|
|
35
|
+
|
|
36
|
+
if(changedProperties.has('opened')) {
|
|
37
|
+
if(this.opened) {
|
|
38
|
+
this.dispatchEvent(new CustomEvent('change', { detail: 'open' }));
|
|
39
|
+
this.dispatchEvent(new CustomEvent('open'));
|
|
40
|
+
} else {
|
|
41
|
+
this.dispatchEvent(new CustomEvent('change', { detail: 'close' }));
|
|
42
|
+
this.dispatchEvent(new CustomEvent('close'));
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
/*
|
|
48
|
+
Methods
|
|
49
|
+
*/
|
|
50
|
+
open() {
|
|
51
|
+
this.opened = true;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
close() {
|
|
55
|
+
this.opened = false;
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
toggle() {
|
|
59
|
+
this.opened ? this.close() : this.open();
|
|
60
|
+
this.dispatchEvent(new CustomEvent('toggle'));
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
/*
|
|
64
|
+
Rendering
|
|
65
|
+
*/
|
|
66
|
+
render() {
|
|
67
|
+
return html`
|
|
68
|
+
<k-focus-capture>
|
|
69
|
+
<div id="container">
|
|
70
|
+
<button id="overlay" @click=${this.overlayClick}>
|
|
71
|
+
<div id="overlay-x">✕</div>
|
|
72
|
+
</button>
|
|
73
|
+
<div id="menu">
|
|
74
|
+
<slot></slot>
|
|
75
|
+
</div>
|
|
76
|
+
</div>
|
|
77
|
+
</k-focus-capture>
|
|
78
|
+
`;
|
|
79
|
+
}
|
|
80
|
+
static styles = css`
|
|
81
|
+
:host {
|
|
82
|
+
--bg: var(--c_bg);
|
|
83
|
+
--width: 20rem;
|
|
84
|
+
|
|
85
|
+
position: fixed;
|
|
86
|
+
top: 0;
|
|
87
|
+
left: 0;
|
|
88
|
+
width: 100vw;
|
|
89
|
+
max-width: 100%;
|
|
90
|
+
height: 100vh;
|
|
91
|
+
z-index: 100;
|
|
92
|
+
pointer-events: none;
|
|
93
|
+
}
|
|
94
|
+
:host([opened]) {
|
|
95
|
+
pointer-events: auto;
|
|
96
|
+
}
|
|
97
|
+
k-focus-capture {
|
|
98
|
+
width: 100%;
|
|
99
|
+
height: 100%;
|
|
100
|
+
}
|
|
101
|
+
#container {
|
|
102
|
+
position: relative;
|
|
103
|
+
width: 100%;
|
|
104
|
+
height: 100%;
|
|
105
|
+
opacity: 0;
|
|
106
|
+
transition: opacity var(--animation_ms, 256ms);
|
|
107
|
+
}
|
|
108
|
+
:host([opened]) #container {
|
|
109
|
+
opacity: 1;
|
|
110
|
+
}
|
|
111
|
+
#overlay {
|
|
112
|
+
position: absolute;
|
|
113
|
+
width: 100%;
|
|
114
|
+
height: 100%;
|
|
115
|
+
left: 0;
|
|
116
|
+
top: 0;
|
|
117
|
+
background: var(--overlay, rgba(0, 0, 0, 0.5));
|
|
118
|
+
border: none;
|
|
119
|
+
padding: 0;
|
|
120
|
+
cursor: pointer;
|
|
121
|
+
z-index: 1;
|
|
122
|
+
}
|
|
123
|
+
#overlay-x {
|
|
124
|
+
position: absolute;
|
|
125
|
+
top: var(--spacer_h);
|
|
126
|
+
right: var(--spacer_h);
|
|
127
|
+
font-size: 1.75rem;
|
|
128
|
+
cursor: pointer;
|
|
129
|
+
color: var(--tc_light);
|
|
130
|
+
}
|
|
131
|
+
:host([overlay-close="false"]) #overlay-x {
|
|
132
|
+
display: none;
|
|
133
|
+
}
|
|
134
|
+
:host([overlay-close="false"]) #overlay {
|
|
135
|
+
cursor: default;
|
|
136
|
+
}
|
|
137
|
+
#menu {
|
|
138
|
+
position: absolute;
|
|
139
|
+
width: var(--width);
|
|
140
|
+
max-width: calc(100vw - 6rem);
|
|
141
|
+
height: 100vh;
|
|
142
|
+
overflow-y: auto;
|
|
143
|
+
left: calc(var(--width) * -1);
|
|
144
|
+
top: 0;
|
|
145
|
+
background: var(--bg);
|
|
146
|
+
transition: left var(--animation_ms, 256ms);
|
|
147
|
+
padding: var(--menu_padding, var(--spacer));
|
|
148
|
+
z-index: 2;
|
|
149
|
+
}
|
|
150
|
+
:host([opened]) #menu {
|
|
151
|
+
left: 0;
|
|
152
|
+
}
|
|
153
|
+
:host([side="right"]) #menu {
|
|
154
|
+
left: auto;
|
|
155
|
+
transition: right var(--animation_ms, 256ms);
|
|
156
|
+
right: calc(var(--width) * -1);
|
|
157
|
+
}
|
|
158
|
+
:host([opened][side="right"]) #menu {
|
|
159
|
+
right: 0;
|
|
160
|
+
}
|
|
161
|
+
:host([side="right"]) #overlay-x {
|
|
162
|
+
right: auto;
|
|
163
|
+
left: var(--spacer_h);
|
|
164
|
+
}
|
|
165
|
+
`;
|
|
166
|
+
}
|
|
167
|
+
window.customElements.define('k-side-menu', SideMenu);
|