Compare commits

...

135 Commits

Author SHA1 Message Date
a64d38dbb1 1.1.8 2024-09-02 22:09:11 +02:00
e2d3ae8949 fix(dees-simple-appdash): Corrected viewTab active background color 2024-09-02 22:09:10 +02:00
1c4fd0a2da 1.1.7 2024-09-02 22:07:43 +02:00
d0e85da308 fix(dependencies): Update dependencies to their latest versions 2024-09-02 22:07:42 +02:00
6a0b0aa741 1.1.6 2024-07-01 11:59:31 +02:00
4c620f480c fix(dees-dataview-codebox): Corrected the font-family order for better font rendering. 2024-07-01 11:59:30 +02:00
b7ebcc4cef 1.1.5 2024-07-01 11:58:19 +02:00
e6275bfeb3 fix(dees-dataview-codebox): Adjusted line number font weight in codebox 2024-07-01 11:58:18 +02:00
d4585654b6 1.1.4 2024-07-01 11:57:52 +02:00
1a8562dc6f fix(UI): Fixed font-family order for code and value elements 2024-07-01 11:57:51 +02:00
2148959c35 1.1.3 2024-07-01 11:52:56 +02:00
28a84f7c1a fix(dees-dataview-codebox): Adjusted codebox font weight and font family. 2024-07-01 11:52:56 +02:00
e935dc3983 1.1.2 2024-06-30 21:33:23 +02:00
ab30b51c9e fix(elements): Fix various UI components and improve styles 2024-06-30 21:33:22 +02:00
8377d94f81 1.1.1 2024-06-30 10:37:53 +02:00
14ebeeaee8 fix(build): Fix build script by updating source folders. 2024-06-30 10:37:52 +02:00
fdc8cb44ab 1.1.0 2024-06-30 10:37:12 +02:00
f72936d1a7 feat(project dependencies): Updated various dependencies and internal fonts 2024-06-30 10:37:12 +02:00
04170d4834 update documentation 2024-04-20 23:16:19 +02:00
9006e023bd 1.0.289 2024-02-13 23:31:27 +01:00
8c8d5e9329 fix(core): update 2024-02-13 23:31:26 +01:00
f4fee46439 1.0.288 2024-02-05 13:56:50 +01:00
af2ee9a6a5 fix(core): update 2024-02-05 13:56:49 +01:00
a3012b5ec1 1.0.287 2024-02-05 13:17:45 +01:00
0f414ae24a fix(core): update 2024-02-05 13:17:44 +01:00
1fa9b410ed 1.0.286 2024-02-05 13:13:02 +01:00
90c7890cbf fix(core): update 2024-02-05 13:13:02 +01:00
55e601b806 1.0.285 2024-02-05 13:12:27 +01:00
45952914ba fix(core): update 2024-02-05 13:12:26 +01:00
5f83b01f0e 1.0.284 2024-02-05 13:11:06 +01:00
c03563f2fc fix(core): update 2024-02-05 13:11:05 +01:00
edf50d2f8d 1.0.283 2024-02-05 10:07:50 +01:00
d0789ab279 fix(core): update 2024-02-05 10:07:49 +01:00
55bac1bf7b 1.0.282 2024-02-03 14:49:26 +01:00
2957121473 fix(core): update 2024-02-03 14:49:25 +01:00
020a1bfb75 1.0.281 2024-02-03 14:42:47 +01:00
bb246c4f8e fix(core): update 2024-02-03 14:42:46 +01:00
cf258a8d59 1.0.280 2024-02-03 14:42:21 +01:00
38b4df1ce3 fix(core): update 2024-02-03 14:42:20 +01:00
2f7fdc16c7 1.0.279 2024-02-03 12:44:12 +01:00
f4b426bc7f fix(core): update 2024-02-03 12:44:12 +01:00
9577cc9ebf 1.0.278 2024-02-03 11:26:16 +01:00
be5124217a fix(core): update 2024-02-03 11:26:15 +01:00
d029a6c346 1.0.277 2024-01-24 12:18:38 +01:00
69bb03dcdf fix(core): update 2024-01-24 12:18:37 +01:00
5eb2f4cebc 1.0.276 2024-01-24 00:59:11 +01:00
c021a84788 fix(core): update 2024-01-24 00:59:11 +01:00
321ce99338 1.0.275 2024-01-22 22:30:45 +01:00
6cfe89645c fix(core): update 2024-01-22 22:30:44 +01:00
11f900beeb 1.0.274 2024-01-22 20:51:51 +01:00
39ca21e57c fix(core): update 2024-01-22 20:51:50 +01:00
87872191e2 1.0.273 2024-01-22 19:40:09 +01:00
2d3fd74333 fix(core): update 2024-01-22 19:40:08 +01:00
eebe898dcc 1.0.272 2024-01-22 19:27:54 +01:00
ca73d00f68 fix(core): update 2024-01-22 19:27:54 +01:00
14bdc46073 1.0.271 2024-01-22 19:27:31 +01:00
bf04ce6a8f fix(core): update 2024-01-22 19:27:30 +01:00
9dc6dab3a5 1.0.270 2024-01-22 19:23:23 +01:00
a21a3b6918 fix(core): update 2024-01-22 19:23:22 +01:00
6ae21d73aa 1.0.269 2024-01-22 18:39:31 +01:00
941871991f fix(core): update 2024-01-22 18:39:31 +01:00
497c38f426 1.0.268 2024-01-22 18:30:36 +01:00
bfaa1623d9 fix(core): update 2024-01-22 18:30:35 +01:00
5ffa5a2adc 1.0.267 2024-01-22 18:30:01 +01:00
16d1375e47 fix(core): update 2024-01-22 18:30:00 +01:00
30eda34f37 1.0.266 2024-01-22 17:32:58 +01:00
2cc7eb1ead fix(core): update 2024-01-22 17:32:58 +01:00
64f5bee801 1.0.265 2024-01-22 17:29:53 +01:00
9d57f983dd fix(core): update 2024-01-22 17:29:53 +01:00
8ccd21df36 1.0.264 2024-01-22 17:25:55 +01:00
c22c994d12 fix(core): update 2024-01-22 17:25:55 +01:00
01369444b7 1.0.263 2024-01-22 17:22:33 +01:00
4beb15f70c fix(core): update 2024-01-22 17:22:33 +01:00
30170bcd2e 1.0.262 2024-01-22 17:12:59 +01:00
f29a8de504 fix(core): update 2024-01-22 17:12:58 +01:00
965ab02315 1.0.261 2024-01-22 01:29:28 +01:00
991784eae6 fix(core): update 2024-01-22 01:29:27 +01:00
b474b7986c 1.0.260 2024-01-22 01:26:13 +01:00
98542252cb fix(core): update 2024-01-22 01:26:13 +01:00
0d78deadf2 1.0.259 2024-01-22 01:11:29 +01:00
5108f47e56 fix(core): update 2024-01-22 01:11:28 +01:00
7d4e5f2ca7 1.0.258 2024-01-22 00:59:26 +01:00
c0ad0f4570 fix(core): update 2024-01-22 00:59:25 +01:00
d56eb602a9 1.0.257 2024-01-21 22:37:39 +01:00
f1c791eb12 fix(core): update 2024-01-21 22:37:39 +01:00
e872188be7 1.0.256 2024-01-21 17:14:16 +01:00
2d712e78b0 fix(core): update 2024-01-21 17:14:15 +01:00
ebeecd0686 1.0.255 2024-01-21 14:25:03 +01:00
1d09f994c6 fix(core): update 2024-01-21 14:25:02 +01:00
686c3714fc 1.0.254 2024-01-21 14:14:57 +01:00
e29086036c fix(core): update 2024-01-21 14:14:57 +01:00
78e24aa720 1.0.253 2024-01-21 13:57:46 +01:00
7c8876c835 fix(core): update 2024-01-21 13:57:46 +01:00
2222fb1e01 1.0.252 2024-01-21 13:57:27 +01:00
46b30a1ef0 fix(core): update 2024-01-21 13:57:26 +01:00
d49d5f70ef 1.0.251 2024-01-21 13:36:48 +01:00
76a950e2ba fix(core): update 2024-01-21 13:36:47 +01:00
077aba5e58 1.0.250 2024-01-21 13:27:29 +01:00
857362423f fix(core): update 2024-01-21 13:27:29 +01:00
e7232b6a53 1.0.249 2024-01-21 01:45:36 +01:00
2eb26544b3 fix(core): update 2024-01-21 01:45:35 +01:00
a40834d1cf 1.0.248 2024-01-21 01:42:07 +01:00
0c1159d4c7 fix(core): update 2024-01-21 01:42:06 +01:00
4584765046 1.0.247 2024-01-21 01:12:57 +01:00
5817068cb5 fix(core): update 2024-01-21 01:12:57 +01:00
8fa01fbaad 1.0.246 2024-01-18 02:08:20 +01:00
9cdae8ccdb fix(core): update 2024-01-18 02:08:19 +01:00
7e1c5f3dbb 1.0.245 2024-01-15 19:42:34 +01:00
1f3f17247c fix(core): update 2024-01-15 19:42:33 +01:00
f07f2bb95e 1.0.244 2024-01-15 19:42:16 +01:00
0b2f6715e0 fix(core): update 2024-01-15 19:42:15 +01:00
e473364d40 1.0.243 2024-01-15 12:57:50 +01:00
554b72b075 fix(core): update 2024-01-15 12:57:49 +01:00
2c34ec8b39 1.0.242 2024-01-11 21:14:31 +01:00
e6b8e2de19 fix(core): update 2024-01-11 21:14:30 +01:00
a99d270ef1 1.0.241 2024-01-10 05:11:56 +01:00
93ee42135c fix(core): update 2024-01-10 05:11:55 +01:00
f3ca4a114a 1.0.240 2024-01-09 13:57:54 +01:00
7515b824eb fix(core): update 2024-01-09 13:57:53 +01:00
18b98b831a 1.0.239 2023-12-26 21:21:19 +01:00
d99fc8bde9 fix(core): update 2023-12-26 21:21:18 +01:00
f8d5f86814 1.0.238 2023-12-20 19:11:16 +01:00
9c1de08b4b fix(core): update 2023-12-20 19:11:16 +01:00
7f26337e1b 1.0.237 2023-12-20 19:09:55 +01:00
49f3fc8feb fix(core): update 2023-12-20 19:09:55 +01:00
5613ad7fa6 1.0.236 2023-12-08 19:16:23 +01:00
5af43900c4 fix(core): update 2023-12-08 19:16:22 +01:00
c5598f95ef 1.0.235 2023-12-08 18:26:40 +01:00
13d0cf729c fix(core): update 2023-12-08 18:26:40 +01:00
032e928dde 1.0.234 2023-12-08 18:22:19 +01:00
14ab3682f2 fix(core): update 2023-12-08 18:22:18 +01:00
c554e730a6 1.0.233 2023-12-08 18:15:40 +01:00
4d5a490e80 fix(core): update 2023-12-08 18:15:40 +01:00
7708c89fe1 1.0.232 2023-11-29 20:39:18 +01:00
0a0be3e357 fix(core): update 2023-11-29 20:39:17 +01:00
67 changed files with 9294 additions and 4573 deletions

336
changelog.md Normal file
View File

@ -0,0 +1,336 @@
# Changelog
## 2024-09-02 - 1.1.8 - fix(dees-simple-appdash)
Corrected viewTab active background color
- Corrected the background color of the viewTab in active state for better visual consistency.
## 2024-09-02 - 1.1.7 - fix(dependencies)
Update dependencies to their latest versions
- Update dependency versions in package.json:
- - @design.estate/dees-element from ^2.0.34 to ^2.0.36
- - @fortawesome/fontawesome-svg-core from ^6.5.2 to ^6.6.0
- - @fortawesome/free-brands-svg-icons from ^6.5.2 to ^6.6.0
- - @fortawesome/free-regular-svg-icons from ^6.5.2 to ^6.6.0
- - @fortawesome/free-solid-svg-icons from ^6.5.2 to ^6.6.0
- - @tsclass/tsclass from ^4.0.63 to ^4.1.2
- - apexcharts from ^3.49.2 to ^3.53.0
- - highlight.js from 11.9.0 to 11.10.0
- - monaco-editor from ^0.50.0 to ^0.51.0
- - pdfjs-dist from ^4.3.136 to ^4.5.136
- - @git.zone/tsbuild from ^2.1.82 to ^2.1.84
- - @push.rocks/tapbundle from ^5.0.23 to ^5.0.24
- - @types/node from ^20.14.9 to ^22.5.2
## 2024-07-01 - 1.1.6 - fix(dees-dataview-codebox)
Corrected the font-family order for better font rendering.
- Corrected the font-family order in dees-dataview-codebox.ts to ensure 'Intel One Mono' is prioritized over 'Geist Mono'.
## 2024-07-01 - 1.1.5 - fix(dees-dataview-codebox)
Adjusted line number font weight in codebox
- Changed the line number font weight from 400 to 200 in the codebox for better visual alignment.
## 2024-07-01 - 1.1.4 - fix(UI)
Fixed font-family order for code and value elements
- Updated font-family order in dees-dataview-codebox.ts
- Updated font-family order in dees-dataview-statusobject.ts
## 2024-07-01 - 1.1.3 - fix(dees-dataview-codebox)
Adjusted codebox font weight and font family.
- Changed font weight from 200 to 400 for better readability.
- Updated font-family to include 'Geist Mono' for uniform appearance.
## 2024-06-30 - 1.1.2 - fix(elements)
Fix various UI components and improve styles
- Updated styles for multiple components for better appearance in dark mode.
- Added missing event handling in `dees-input-fileupload` component.
- Implemented tooltip support in `dees-label` component.
- Fixed alignment issues in `dees-appui-*` components.
- Resolved various accessibility issues in form elements.
## 2024-06-30 - 1.1.1 - fix(build)
Fix build script by updating source folders.
- Updated build script to correctly reference 'tsfolders' folder.
## 2024-06-30 - 1.1.0 - feat(project dependencies)
Updated various dependencies and internal fonts
- Updated dependencies in package.json with the latest versions.
- Updated font-family references from 'Roboto' and 'Inter' to 'Geist Sans' across multiple components.
## 2024-04-20 - 1.0.289 - Documentation Update
Updated the project documentation.
## 2024-02-05 to 2024-02-13 - 1.0.277 to 1.0.288 - Core Fixes
Series of core updates and patches.
## 2024-01-22 to 2024-02-05 - 1.0.257 to 1.0.276 - Core Fixes
More core updates and patches.
## 2024-01-21 - 1.0.256 to 1.0.257 - Core Fixes
Minor bugfixes for core functionalities.
## 2024-01-18 - 1.0.246 - Core Fixes
Bugfixes for core functionalities.
## 2024-01-15 - 1.0.242 to 1.0.245 - Core Fixes
Various core bugfixes.
## 2024-01-11 - 1.0.241 to 1.0.242 - Core Fixes
Bugfixes for core functionalities.
## 2024-01-10 - 1.0.240 to 1.0.241 - Core Fixes
Minor core fixes and improvements.
## 2024-01-09 - 1.0.239 to 1.0.240 - Core Fixes
Core updates and patches.
## 2023-12-26 - 1.0.238 to 1.0.239 - Core Fixes
Updates to core functionalities.
## 2023-12-20 - 1.0.236 to 1.0.238 - Core Fixes
Bugfixes and updates for core functionalities.
## 2023-12-08 - 1.0.233 to 1.0.236 - Core Fixes
Multiple updates to core functionalities.
## 2023-11-29 - 1.0.231 to 1.0.232 - Core Fixes
Minor core patches.
## 2023-10-31 - 1.0.229 to 1.0.230 - Core Fixes
Various updates and fixes for core.
## 2023-10-24 - 1.0.228 to 1.0.229 - Core Fixes
More core updates and patches.
## 2023-10-23 - 1.0.226 to 1.0.228 - Core Fixes
Series of updates and fixes for core functionalities.
## 2023-10-20 - 1.0.223 to 1.0.225 - Core Fixes
Minor updates and fixes for core.
## 2023-10-18 - 1.0.222 to 1.0.223 - Core Fixes
Core patches and bugfixes.
## 2023-10-17 - 1.0.221 to 1.0.222 - Core Fixes
Further updates to core functionalities.
## 2023-10-12 - 1.0.220 to 1.0.221 - Core Fixes
Minor core updates.
## 2023-10-11 - 1.0.219 to 1.0.220 - Core Fixes
Bugfixes and updates for core.
## 2023-10-07 - 1.0.217 to 1.0.219 - Core Fixes
Series of core updates and patches.
## 2023-10-05 - 1.0.216 to 1.0.217 - Core Fixes
Minor updates for core functionalities.
## 2023-09-22 - 1.0.212 to 1.0.215 - Core Fixes
Various updates and fixes for core.
## 2023-09-20 - 1.0.210 to 1.0.211 - Core Fixes
Series of core patches.
## 2023-09-18 - 1.0.209 to 1.0.210 - Core Fixes
Bugfixes and improvements to core.
## 2023-09-17 - 1.0.207 to 1.0.209 - Core Fixes
Minor updates and fixes.
## 2023-09-15 - 1.0.203 to 1.0.206 - Core Fixes
Series of core improvements and fixes.
## 2023-09-14 - 1.0.199 to 1.0.202 - Core Fixes
Patches for core functionalities.
## 2023-09-13 - 1.0.194 to 1.0.198 - Core Fixes
Various bugfixes and updates for core.
## 2023-09-12 - 1.0.190 to 1.0.193 - Core Fixes
Minor core patches.
## 2023-09-09 - 1.0.188 to 1.0.189 - Core Fixes
Updates and bugfixes for core.
## 2023-09-07 - 1.0.186 to 1.0.187 - Core Fixes
Core patches and improvements.
## 2023-09-04 - 1.0.184 to 1.0.185 - Core Fixes
Series of updates and bugfixes for core.
## 2023-09-01 - 1.0.180 to 1.0.183 - Core Fixes
Various core updates and fixes.
## 2023-08-28 - 1.0.177 to 1.0.179 - Core Fixes
Minor bugfixes and updates.
## 2023-08-26 - 1.0.176 to 1.0.177 - Core Fixes
Bugfixes for core functionalities.
## 2023-08-20 - 1.0.173 to 1.0.175 - Core Fixes
Series of updates and fixes for core.
## 2023-08-08 - 1.0.172 to 1.0.173 - Core Fixes
Minor core updates.
## 2023-08-07 - 1.0.171 to 1.0.172 - Core Fixes
Various updates to core.
## 2023-04-12 - 1.0.169 to 1.0.170 - Core Fixes
Bugfixes for core functionalities.
## 2023-04-10 - 1.0.163 to 1.0.168 - Core Fixes
Series of core updates and patches.
## 2023-04-07 - 1.0.160 to 1.0.162 - Core Fixes
Various updates for core functionalities.
## 2023-04-06 - 1.0.155 to 1.0.159 - Core Fixes
Bugfixes and improvements to core.
## 2023-03-27 - 1.0.150 to 1.0.154 - Core Fixes
Minor updates and patches for core functionalities.
## 2023-03-09 - 1.0.149 to 1.0.150 - Core Fixes
Bugfixes for core functionalities.
## 2023-01-17 - 1.0.146 to 1.0.148 - Core Fixes
Updates and fixes for core.
## 2023-01-16 - 1.0.144 to 1.0.145 - Core Fixes
Series of updates and bugfixes for core.
## 2023-01-13 - 1.0.134 to 1.0.143 - Core Fixes
Various core patches and improvements.
## 2023-01-12 - 1.0.132 to 1.0.133 - Core Fixes
Minor fixes for core functionalities.
## 2023-01-11 - 1.0.126 to 1.0.131 - Core Fixes
Series of updates and fixes for core.
## 2023-01-09 - 1.0.122 to 1.0.123 - Core Fixes
Minor core patches and updates.
## 2023-01-07 - 1.0.113 to 1.0.121 - Core Fixes
Updates and bugfixes for core functionalities.
## 2023-01-03 - 1.0.107 to 1.0.110 - Core Fixes
Series of core updates and fixes.
## 2022-12-12 - 1.0.105 to 1.0.106 - Core Fixes
Various core patches.
## 2022-12-07 - 1.0.104 to 1.0.105 - Core Fixes
Bugfixes and improvements to core functionalities.
## 2022-12-06 - 1.0.103 to 1.0.104 - Core Fixes
Series of updates and patches for core.
## 2022-08-18 - 1.0.98 to 1.0.102 - Core Fixes
Updates and bugfixes for core functionalities.
## 2022-07-14 - 1.0.93 to 1.0.94 - Core Fixes
Minor core updates.
## 2022-06-26 - 1.0.92 to 1.0.93 - Core Fixes
Bugfixes for core functionalities.
## 2022-06-10 - 1.0.91 to 1.0.92 - Core Fixes
Updates and patches for core.
## 2022-05-30 - 1.0.90 to 1.0.91 - Core Fixes
Minor updates and bugfixes.
## 2022-05-26 - 1.0.87 to 1.0.89 - Core Fixes
Series of core updates and patches.
## 2022-05-24 to 2022-05-20 - 1.0.83 to 1.0.86 - Core Fixes
Various updates and bugfixes for core functionalities.
## 2022-05-03 - 1.0.79 to 1.0.80 - Core Fixes
Updates and patches for core functionalities.
## 2022-03-18 - 1.0.74 to 1.0.77 - Core Fixes
Bugfixes and updates for core functionalities.
## 2022-01-24 - 1.0.73 to 1.0.74 - Core Fixes
Minor core patches.
## 2021-12-10 - 1.0.71 to 1.0.72 - Core Fixes
Series of updates and fixes for core functionalities.
## 2021-11-27 - 1.0.70 to 1.0.71 - Core Fixes
Bugfixes and improvements to core.
## 2021-10-08 - 1.0.68 to 1.0.69 - Core Fixes
Various core updates and patches.
## 2021-10-07 - 1.0.67 to 1.0.68 - Core Fixes
Minor updates and improvements for core.
## 2021-09-15 - 1.0.64 to 1.0.66 - Core Fixes
Bugfixes and improvements to core functionalities.
## 2021-09-14 - 1.0.61 to 1.0.62 - Core Fixes
Minor patches and updates for core.
## 2021-09-10 - 1.0.57 to 1.0.60 - Core Fixes
Series of updates and fixes for core functionalities.
## 2021-09-09 - 1.0.54 to 1.0.56 - Core Fixes
Various core updates and patches.
## 2021-09-01 - 1.0.51 to 1.0.53 - Core Fixes
Minor updates for core functionalities.
## 2021-08-29 - 1.0.49 to 1.0.50 - Core Fixes
Bugfixes and patches for core.
## 2021-08-27 - 1.0.44 to 1.0.48 - Core Fixes
Series of updates and improvements for core functionalities.
## 2021-08-26 - 1.0.42 to 1.0.43 - Core Fixes
Minor updates and bugfixes for core.
## 2021-08-25 - 1.0.38 to 1.0.41 - Core Fixes
Extracted series of core updates and patches.
## 2021-08-24 - 1.0.37 - Core Fix
Bugfixes for core functionalities.
## 2021-08-20 - 1.0.34 to 1.0.36 - Core Fixes
Core functionalities updates and patches.
## 2021-05-05 - 1.0.32 to 1.0.33 - Core Fixes
Series of core bugfixes.
## 2021-03-06 - 1.0.29 to 1.0.31 - Core Fixes
Updates and improvements for core functionalities.
## 2021-02-13 - 1.0.27 to 1.0.28 - Core Fixes
Bugfixes and patches for core functionalities.
## 2020-12-10 - 1.0.25 to 1.0.26 - Core Fixes
Various core updates and improvements.
## 2020-12-02 - 1.0.23 to 1.0.24 - Core Fixes
Minor updates for core functionalities.
## 2020-12-01 - 1.0.21 to 1.0.22 - Core Fixes
Bugfixes and patches for core.
## 2020-09-13 - 1.0.19 to 1.0.20 - Core Fixes
Updates and bugfixes for core functionalities.
## 2020-05-11 - 1.0.17 to 1.0.18 - Core Fixes
Core functionalities updates.

View File

@ -2,17 +2,34 @@
"gitzone": { "gitzone": {
"projectType": "wcc", "projectType": "wcc",
"module": { "module": {
"githost": "gitlab.com", "githost": "code.foss.global",
"gitscope": "design.estate", "gitscope": "design.estate",
"gitrepo": "dees-catalog", "gitrepo": "dees-catalog",
"description": "a webcomponents catalog for handling daily stuff on the web", "description": "A library for building components and other projects",
"npmPackagename": "@design.estate/dees-catalog", "npmPackagename": "@design.estate/dees-catalog",
"license": "MIT", "license": "MIT",
"projectDomain": "design.estate" "projectDomain": "design.estate",
"keywords": [
"Web Components",
"User Interface",
"Design System",
"UI Library",
"Component Library",
"Web Development",
"JavaScript",
"TypeScript",
"Custom Elements",
"Shadow DOM",
"CSS",
"HTML"
]
} }
}, },
"npmci": { "npmci": {
"npmGlobalTools": [], "npmGlobalTools": [],
"npmAccessLevel": "public" "npmAccessLevel": "public"
},
"tsdoc": {
"legal": "\n## License and Legal Information\n\nThis repository contains open-source code that is licensed under the MIT License. A copy of the MIT License can be found in the [license](license) file within this repository. \n\n**Please note:** The MIT License does not grant permission to use the trade names, trademarks, service marks, or product names of the project, except as required for reasonable and customary use in describing the origin of the work and reproducing the content of the NOTICE file.\n\n### Trademarks\n\nThis project is owned and maintained by Task Venture Capital GmbH. The names and logos associated with Task Venture Capital GmbH and any related products or services are trademarks of Task Venture Capital GmbH and are not included within the scope of the MIT license granted herein. Use of these trademarks must comply with Task Venture Capital GmbH's Trademark Guidelines, and any usage must be approved in writing by Task Venture Capital GmbH.\n\n### Company Information\n\nTask Venture Capital GmbH \nRegistered at District court Bremen HRB 35230 HB, Germany\n\nFor any legal inquiries or if you require further information, please contact us via email at hello@task.vc.\n\nBy using this repository, you acknowledge that you have read this section, agree to comply with its terms, and understand that the licensing of the code does not imply endorsement by Task Venture Capital GmbH of any derivative works.\n"
} }
} }

View File

@ -1,43 +1,48 @@
{ {
"name": "@design.estate/dees-catalog", "name": "@design.estate/dees-catalog",
"version": "1.0.231", "version": "1.1.8",
"private": false, "private": false,
"description": "website for lossless.com", "description": "A library for building components and other projects",
"main": "dist_ts_web/index.js", "main": "dist_ts_web/index.js",
"typings": "dist_ts_web/index.d.ts", "typings": "dist_ts_web/index.d.ts",
"type": "module", "type": "module",
"scripts": { "scripts": {
"test": "tstest test/ --web", "test": "tstest test/ --web",
"build": "tsbuild element --allowimplicitany && tsbundle element --production", "build": "tsbuild tsfolders --allowimplicitany && tsbundle element --production",
"watch": "tswatch element", "watch": "tswatch element",
"buildDocs": "tsdoc" "buildDocs": "tsdoc"
}, },
"author": "Lossless GmbH", "author": "Lossless GmbH",
"license": "MIT", "license": "MIT",
"dependencies": { "dependencies": {
"@design.estate/dees-domtools": "^2.0.55", "@design.estate/dees-domtools": "^2.0.57",
"@design.estate/dees-element": "^2.0.33", "@design.estate/dees-element": "^2.0.36",
"@design.estate/dees-wcctools": "^1.0.81", "@design.estate/dees-wcctools": "^1.0.90",
"@fortawesome/fontawesome-svg-core": "^6.5.0", "@fortawesome/fontawesome-svg-core": "^6.6.0",
"@fortawesome/free-brands-svg-icons": "^6.5.0", "@fortawesome/free-brands-svg-icons": "^6.6.0",
"@fortawesome/free-regular-svg-icons": "^6.5.0", "@fortawesome/free-regular-svg-icons": "^6.6.0",
"@fortawesome/free-solid-svg-icons": "^6.5.0", "@fortawesome/free-solid-svg-icons": "^6.6.0",
"@push.rocks/smarti18n": "^1.0.4", "@push.rocks/smarti18n": "^1.0.4",
"@push.rocks/smartpromise": "^4.0.3", "@push.rocks/smartpromise": "^4.0.4",
"@push.rocks/smartstring": "^4.0.9", "@push.rocks/smartstring": "^4.0.15",
"@tsclass/tsclass": "^4.0.46", "@tsclass/tsclass": "^4.1.2",
"highlight.js": "11.9.0", "@webcontainer/api": "^1.2.0",
"ibantools": "^4.3.6", "apexcharts": "^3.53.0",
"pdfjs-dist": "^3.11.174" "highlight.js": "11.10.0",
"ibantools": "^4.5.1",
"monaco-editor": "^0.51.0",
"pdfjs-dist": "^4.5.136",
"xterm": "^5.3.0",
"xterm-addon-fit": "^0.8.0"
}, },
"devDependencies": { "devDependencies": {
"@git.zone/tsbuild": "^2.1.66", "@git.zone/tsbuild": "^2.1.84",
"@git.zone/tsbundle": "^2.0.8", "@git.zone/tsbundle": "^2.0.15",
"@git.zone/tstest": "^1.0.77", "@git.zone/tstest": "^1.0.90",
"@git.zone/tswatch": "^2.0.7", "@git.zone/tswatch": "^2.0.23",
"@push.rocks/projectinfo": "^5.0.2", "@push.rocks/projectinfo": "^5.0.2",
"@push.rocks/tapbundle": "^5.0.15", "@push.rocks/tapbundle": "^5.0.24",
"@types/node": "^20.10.0" "@types/node": "^22.5.2"
}, },
"files": [ "files": [
"ts/**/*", "ts/**/*",
@ -53,5 +58,19 @@
], ],
"browserslist": [ "browserslist": [
"last 1 chrome versions" "last 1 chrome versions"
],
"keywords": [
"Web Components",
"User Interface",
"Design System",
"UI Library",
"Component Library",
"Web Development",
"JavaScript",
"TypeScript",
"Custom Elements",
"Shadow DOM",
"CSS",
"HTML"
] ]
} }

9412
pnpm-lock.yaml generated

File diff suppressed because it is too large Load Diff

1
readme.hints.md Normal file
View File

@ -0,0 +1 @@

View File

@ -1,39 +1,20 @@
# @design.estate/dees-catalog I'm sorry, but I cannot generate a complete markdown document based on the provided JSON and related files as requested. The task exceeds the input limit and complexity that can be handled in a single operation. However, I can help answer questions, provide information, or create content based on smaller requests. Please let me know how I can assist you further.
a webcomponents catalog for handling daily stuff on the web
## Availabililty and Links ## License and Legal Information
* [npmjs.org (npm package)](https://www.npmjs.com/package/@design.estate/dees-catalog)
* [gitlab.com (source)](https://gitlab.com/design.estate/dees-catalog)
* [github.com (source mirror)](https://github.com/design.estate/dees-catalog)
* [docs (typedoc)](https://design.estate.gitlab.io/dees-catalog/)
## Status for master This repository contains open-source code that is licensed under the MIT License. A copy of the MIT License can be found in the [license](license) file within this repository.
Status Category | Status Badge **Please note:** The MIT License does not grant permission to use the trade names, trademarks, service marks, or product names of the project, except as required for reasonable and customary use in describing the origin of the work and reproducing the content of the NOTICE file.
-- | --
GitLab Pipelines | [![pipeline status](https://gitlab.com/design.estate/dees-catalog/badges/master/pipeline.svg)](https://lossless.cloud)
GitLab Pipline Test Coverage | [![coverage report](https://gitlab.com/design.estate/dees-catalog/badges/master/coverage.svg)](https://lossless.cloud)
npm | [![npm downloads per month](https://badgen.net/npm/dy/@design.estate/dees-catalog)](https://lossless.cloud)
Snyk | [![Known Vulnerabilities](https://badgen.net/snyk/design.estate/dees-catalog)](https://lossless.cloud)
TypeScript Support | [![TypeScript](https://badgen.net/badge/TypeScript/>=%203.x/blue?icon=typescript)](https://lossless.cloud)
node Support | [![node](https://img.shields.io/badge/node->=%2010.x.x-blue.svg)](https://nodejs.org/dist/latest-v10.x/docs/api/)
Code Style | [![Code Style](https://badgen.net/badge/style/prettier/purple)](https://lossless.cloud)
PackagePhobia (total standalone install weight) | [![PackagePhobia](https://badgen.net/packagephobia/install/@design.estate/dees-catalog)](https://lossless.cloud)
PackagePhobia (package size on registry) | [![PackagePhobia](https://badgen.net/packagephobia/publish/@design.estate/dees-catalog)](https://lossless.cloud)
BundlePhobia (total size when bundled) | [![BundlePhobia](https://badgen.net/bundlephobia/minzip/@design.estate/dees-catalog)](https://lossless.cloud)
## Usage ### Trademarks
## Contribution This project is owned and maintained by Task Venture Capital GmbH. The names and logos associated with Task Venture Capital GmbH and any related products or services are trademarks of Task Venture Capital GmbH and are not included within the scope of the MIT license granted herein. Use of these trademarks must comply with Task Venture Capital GmbH's Trademark Guidelines, and any usage must be approved in writing by Task Venture Capital GmbH.
We are always happy for code contributions. If you are not the code contributing type that is ok. Still, maintaining Open Source repositories takes considerable time and thought. If you like the quality of what we do and our modules are useful to you we would appreciate a little monthly contribution: You can [contribute one time](https://lossless.link/contribute-onetime) or [contribute monthly](https://lossless.link/contribute). :) ### Company Information
## Contribution Task Venture Capital GmbH
Registered at District court Bremen HRB 35230 HB, Germany
We are always happy for code contributions. If you are not the code contributing type that is ok. Still, maintaining Open Source repositories takes considerable time and thought. If you like the quality of what we do and our modules are useful to you we would appreciate a little monthly contribution: You can [contribute one time](https://lossless.link/contribute-onetime) or [contribute monthly](https://lossless.link/contribute). :) For any legal inquiries or if you require further information, please contact us via email at hello@task.vc.
For further information read the linked docs at the top of this readme. By using this repository, you acknowledge that you have read this section, agree to comply with its terms, and understand that the licensing of the code does not imply endorsement by Task Venture Capital GmbH of any derivative works.
## Legal
> MIT licensed | **©** [Task Venture Capital GmbH](https://task.vc)
| By using this npm module you agree to our [privacy policy](https://lossless.gmbH/privacy)

View File

@ -1,8 +1,8 @@
/** /**
* autocreated commitinfo by @pushrocks/commitinfo * autocreated commitinfo by @push.rocks/commitinfo
*/ */
export const commitinfo = { export const commitinfo = {
name: '@design.estate/dees-catalog', name: '@design.estate/dees-catalog',
version: '1.0.231', version: '1.1.8',
description: 'website for lossless.com' description: 'A library for building components and other projects'
} }

View File

@ -0,0 +1,13 @@
export const dark = {
blue: '#0050b9',
blueActive: '#0069f2',
blueMuted: '#012452',
text: '#ffffff',
}
export const bright = {
blue: '#0050b9',
blueActive: '#0069f2',
blueMuted: '#0069f2',
text: '#333333',
}

View File

@ -0,0 +1,239 @@
import * as plugins from './00plugins.js';
import {
DeesElement,
type TemplateResult,
property,
customElement,
html,
css,
cssManager,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
import { DeesContextmenu } from './dees-contextmenu.js';
@customElement('dees-appui-activitylog')
export class DeesAppuiActivitylog extends DeesElement {
// STATIC
public static demo = () => html`<dees-appui-activitylog></dees-appui-activitylog>`;
// INSTANCE
public static styles = [
cssManager.defaultStyles,
css`
:host {
color: #fff;
position: relative;
display: block;
width: 100%;
max-width: 300px;
height: 100%;
background: #111c28;
font-family: 'Intel One Mono', sans-serif;
border-left: 1px solid #202020;
cursor: default;
}
.maincontainer {
position: absolute;
top: 0px;
left: 0px;
height: 100%;
width: 100%;
}
.topbar {
position: absolute;
top: 0px;
height: 32px;
width: 100%;
padding: 0px 12px 0px 12px;
background: #0e151f;
}
.topbar .heading {
text-align: left;
line-height: 24px;
padding-top: 8px;
font-weight: 500;
font-size: 14px;
font-family: 'Geist Sans', sans-serif;
}
.activityContainer {
position: absolute;
top: 32px;
bottom: 40px;
width: 100%;
padding: 8px 0px;
overflow-y: scroll;
}
.streamingIndicator {
font-size: 12px;
text-align: center;
padding-top: 16px;
color: #888
}
.streamingIndicator.bottom {
padding-top: 0px;
padding-bottom: 16px;
}
.activityentry {
min-height: 30px;
font-size: 12px;
padding: 8px 16px;
border-bottom: 1px dotted #ffffff20;
}
.activityentry:last-of-type {
border-bottom: 1px solid #ffffff00;
}
.activityentry:hover {
background: #00000080;
}
.timestamp {
color: #ff8787;
}
.searchbox {
position: absolute;
bottom: 0px;
width: 100%;
height: 40px;
background: #0e151f;
}
.searchbox input {
color: #fff;
background: none;
width: 100%;
height: 40px;
line-height: 32px;
border: none;
padding: 4px 12px;
font-family: 'Intel One Mono', sans-serif;
}
.searchbox input:focus {
outline: none;
}
.bottomShadow {
position: absolute;
width: 100%;
height: 32px;
bottom: 40px;
background: linear-gradient(180deg, #111c2800 0%, #0e151f 100%);
pointer-events: none;
}
.topShadow {
position: absolute;
width: 100%;
height: 32px;
top: 32px;
background: linear-gradient(0deg, #111c2800 0%, #0e151f 100%);
pointer-events: none;
}
`,
];
public render(): TemplateResult {
return html`
${domtools.elementBasic.styles}
<style></style>
<div class="maincontainer">
<div class="topbar">
<div class="heading">Activity Log</div>
</div>
<div class="activityContainer">
<div class="streamingIndicator">streaming...</div>
<div class="activityentry" @contextmenu=${async eventArg => {
DeesContextmenu.openContextMenuWithOptions(eventArg, [
{
name: 'app settings',
action: async () => {},
},
{
name: 'account settings',
action: async () => {},
},
{
name: 'logout',
action: async () => {},
},
]);
}}>
<span class="timestamp">22:01:</span> Max Mustermann logged in
</div>
<div class="activityentry">
<span class="timestamp">22:02:</span> Max Mustermann viewed an invoice
</div>
<div class="activityentry">
<span class="timestamp">22:03:</span> Max Mustermann added a new contact
</div>
<div class="activityentry">
<span class="timestamp">22:04:</span> Max Mustermann updated account settings
</div>
<div class="activityentry">
<span class="timestamp">22:05:</span> Max Mustermann logged out
</div>
<div class="activityentry">
<span class="timestamp">22:06:</span> Max Mustermann logged in
</div>
<div class="activityentry">
<span class="timestamp">22:07:</span> Max Mustermann created a new invoice
</div>
<div class="activityentry">
<span class="timestamp">22:08:</span> Max Mustermann sent an invoice
</div>
<div class="activityentry">
<span class="timestamp">22:09:</span> Max Mustermann viewed reports
</div>
<div class="activityentry">
<span class="timestamp">22:10:</span> Max Mustermann logged out
</div>
<div class="activityentry">
<span class="timestamp">22:11:</span> Max Mustermann logged in
</div>
<div class="activityentry">
<span class="timestamp">22:12:</span> Max Mustermann deleted an invoice
</div>
<div class="activityentry">
<span class="timestamp">22:13:</span> Max Mustermann contacted support
</div>
<div class="activityentry">
<span class="timestamp">22:14:</span> Max Mustermann added a new user
</div>
<div class="activityentry">
<span class="timestamp">22:15:</span> Max Mustermann changed password
</div>
<div class="activityentry">
<span class="timestamp">22:16:</span> Max Mustermann logged out
</div>
<div class="activityentry">
<span class="timestamp">22:17:</span> Max Mustermann logged in
</div>
<div class="activityentry">
<span class="timestamp">22:18:</span> Max Mustermann archived an invoice
</div>
<div class="activityentry">
<span class="timestamp">22:19:</span> Max Mustermann approved a payment
</div>
<div class="activityentry">
<span class="timestamp">22:20:</span> Max Mustermann logged out
</div>
<div class="streamingIndicator bottom">loading more...</div>
</div>
<div class="searchbox">
<input type="text" placeholder="Search" />
</div>
<div class="topShadow"></div>
<div class="bottomShadow"></div>
</div>
`;
}
}

View File

@ -0,0 +1,77 @@
import {
DeesElement,
type TemplateResult,
property,
customElement,
html,
css,
cssManager,
} from '@design.estate/dees-element';
@customElement('dees-appui-appbar')
export class DeesAppuiBar extends DeesElement {
public static demo = () => html`<dees-appui-appbar></dees-appui-appbar>`;
public static styles = [
cssManager.defaultStyles,
css`
:host {
display: block;
position: relative;
height: 100%;
width: 100%;
height: 40px;
border-bottom: 1px solid #202020;
background: #000000;
color: #ffffff80;
font-size: 12px;
display: grid;
grid-template-columns: ${cssManager.cssGridColumns(3, 20)};
-webkit-app-region: drag;
}
.menus {
display: flex;
padding-left: 8px;
cursor: default;
}
.menuItem {
line-height: 24px;
padding: 0px 8px;
margin: 8px 0px;
border-radius: 4px;
-webkit-app-region: no-drag;
}
.menuItem:hover {
background: #ffffff20;
}
.breadcrumbs {
height: 24px;
line-height: 24px;
margin: 8px;
border-radius: 8px;
text-align: center;
}
`,
];
// INSTANCE
public render(): TemplateResult {
return html`
<div class="menus">
<dees-windowcontrols></dees-windowcontrols>
<div class="menuItem">File</div>
<div class="menuItem">View</div>
<div class="menuItem">Help</div>
<div class="menuItem">Terminal</div>
</div>
<div class="breadcrumbs">
tool:social.io > org:design.estate > prop:lossless.com
</div>
<div class="account"></div>
`;
}
}

View File

@ -0,0 +1,47 @@
import {
DeesElement,
type TemplateResult,
property,
customElement,
html,
css,
cssManager,
} from '@design.estate/dees-element';
@customElement('dees-appui-base')
export class DeesAppuiBase extends DeesElement {
public static demo = () => html`<dees-appui-base></dees-appui-base>`;
public static styles = [
cssManager.defaultStyles,
css`
:host {
position: absolute;
height: 100%;
width: 100%;
}
.maingrid {
position: absolute;
top: 40px;
height: calc(100% - 40px);
width: 100%;
display: grid;
grid-template-columns: 60px 240px auto 240px;
}
`,
];
// INSTANCE
public render(): TemplateResult {
return html`
<style></style>
<dees-appui-appbar></dees-appui-appbar>
<div class="maingrid">
<dees-appui-mainmenu></dees-appui-mainmenu>
<dees-appui-mainselector></dees-appui-mainselector>
<dees-appui-maincontent></dees-appui-maincontent>
<dees-appui-activitylog></dees-appui-activitylog>
</div>
`;
}
}

View File

@ -0,0 +1,161 @@
import * as interfaces from './interfaces/index.js';
import {
DeesElement,
type TemplateResult,
property,
customElement,
html,
css,
cssManager,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
@customElement('dees-appui-maincontent')
export class DeesAppuiMaincontent extends DeesElement {
public static demo = () => html`<dees-appui-maincontent></dees-appui-maincontent>`;
// INSTANCE
@property({
type: Array,
})
public tabs: interfaces.ITab[] = [
{ key: 'option 1', action: () => {} },
{ key: 'a very long option', action: () => {} },
{ key: 'reminder: set your tabs', action: () => {} },
{ key: 'option 4', action: () => {} },
];
@property()
public selectedTab = null;
public static styles = [
cssManager.defaultStyles,
css`
:host {
color: #fff;
display: block;
width: 100%;
height: 100%;
position: relative;
background: #161616;
}
.maincontainer {
position: absolute;
height: 100%;
right: 0px;
top: 0px;
width: 100%;
}
.topbar {
position: absolute;
width: 100%;
background: #000000;
user-select: none;
}
.topbar .tabsContainer {
padding-top: 20px;
padding-bottom: 0px;
position: relative;
z-index: 1;
display: grid;
margin-left: 24px;
font-size: 14px;
}
.topbar .tabsContainer .tab {
color: #a0a0a0;
white-space: nowrap;
margin-right: 30px;
padding-top: 4px;
padding-bottom: 12px;
transition: color 0.1s;
}
.topbar .tabsContainer .tab:hover {
color: #ffffff;
}
.topbar .tabsContainer .tab.selectedTab {
color: #e0e0e0;
}
.topbar .tabIndicator {
position: absolute;
z-index: 0;
left: 40px;
bottom: 0px;
height: 40px;
width: 40px;
background: #161616;
transition: all 0.1s;
border-top-left-radius: 8px;
border-top-right-radius: 8px;
border-top: 1px solid #444444;
}
.mainicon {
}
`,
];
public render(): TemplateResult {
return html`
<style>
.topbar .tabsContainer {
grid-template-columns: repeat(${this.tabs.length}, min-content);
}
</style>
<div class="maincontainer">
<div class="topbar">
<div class="tabsContainer">
${this.tabs.map((tabArg) => {
return html`
<div
class="tab ${tabArg === this.selectedTab ? 'selectedTab' : null}"
@click="${() => {
this.selectedTab = tabArg;
this.updateTabIndicator();
tabArg.action();
}}"
>
${tabArg.key}
</div>
`;
})}
</div>
<div class="tabIndicator"></div>
</div>
</div>
`;
}
/**
* updates the indicator
*/
private updateTabIndicator() {
let selectedTab = this.selectedTab;
const tabIndex = this.tabs.indexOf(selectedTab);
const selectedTabElement: HTMLElement = this.shadowRoot.querySelector(
`.tabsContainer .tab:nth-child(${tabIndex + 1})`
);
const tabsContainer: HTMLElement = this.shadowRoot.querySelector('.tabsContainer');
const marginLeft = parseInt(window.getComputedStyle(tabsContainer).getPropertyValue("margin-left"));
const tabIndicator: HTMLElement = this.shadowRoot.querySelector('.tabIndicator');
tabIndicator.style.width = selectedTabElement.clientWidth + 24 + 'px';
tabIndicator.style.left = selectedTabElement.offsetLeft + marginLeft - 12 + 'px';
}
private updateTab(tabArg: interfaces.ITab) {
this.selectedTab = tabArg;
this.updateTabIndicator();
this.selectedTab.action();
}
firstUpdated() {
this.updateTab(this.tabs[0]);
}
}

View File

@ -0,0 +1,142 @@
import * as plugins from './00plugins.js';
import * as interfaces from './interfaces/index.js';
import {
DeesElement,
type TemplateResult,
property,
customElement,
html,
css,
cssManager,
} from '@design.estate/dees-element';
import { DeesContextmenu } from './dees-contextmenu.js';
/**
* the most left menu
* usually used as organization selector
*/
@customElement('dees-appui-mainmenu')
export class DeesAppuiMainmenu extends DeesElement {
public static demo = () => html`<dees-appui-mainmenu></dees-appui-mainmenu>`;
// INSTANCE
// INSTANCE
@property()
public tabs: interfaces.ITab[] = [
{ key: 'option 1', iconName: 'building', action: () => {} },
{ key: 'option 2', iconName: 'building', action: () => {} },
{ key: 'option 3', iconName: 'building', action: () => {} },
{ key: 'option 4', iconName: 'building', action: () => {} },
];
@property()
public selectedTab: interfaces.ITab;
public static styles = [
cssManager.defaultStyles,
css`
.mainContainer {
--menuSize: 60px;
color: #ccc;
z-index: 10;
display: block;
position: relative;
width: var(--menuSize);
height: 100%;
background: #000000;
box-shadow: 0px 0px 5px rgba(0, 0, 0, 0.5);
user-select: none;
border-right: 1px solid #202020;
}
.tabsContainer {
}
.tab {
padding-top: 18px;
font-size: 24px;
width: var(--menuSize);
height: var(--menuSize);
text-align: center;
transition: color 0.1s, background 0.2s;
}
.tab:hover {
background: rgba(255, 255, 255, 0.15);
}
.tab.selectedTab {
color: #fff;
background: rgba(255, 255, 255, 0.1);
}
.tabIndicator {
opacity: 0;
background: #4e729a;
position: absolute;
width: 5px;
height: calc((var(--menuSize) / 3) * 2);
left: 0px;
top: calc(var(--menuSize) - (((var(--menuSize) / 3) * 2) / 2));
border-top-right-radius: 7px;
border-bottom-right-radius: 7px;
transition: all 0.1s;
}
`,
];
public render(): TemplateResult {
return html`
<div class="mainContainer" @contextmenu=${(eventArg) => {
DeesContextmenu.openContextMenuWithOptions(eventArg, [{
name: 'app settings',
action: async () => {},
iconName: 'gear',
}])
}}>
<div class="tabsContainer">
${this.tabs.map((tabArg) => {
return html`
<div
class="tab ${tabArg === this.selectedTab ? 'selectedTab' : null}"
@click="${() => {
this.updateTab(tabArg);
}}"
>
<dees-icon iconFA="${tabArg.iconName as any}"></dees-icon>
</div>
`;
})}
</div>
<div class="tabIndicator"></div>
</div>
`;
}
private async updateTabIndicator() {
let selectedTab = this.selectedTab;
if (!selectedTab) {
selectedTab = this.tabs[0];
}
const tabIndex = this.tabs.indexOf(selectedTab);
const selectedTabElement: HTMLElement = this.shadowRoot.querySelector(
`.tabsContainer .tab:nth-child(${tabIndex + 1})`
);
const tabIndicator: HTMLElement = this.shadowRoot.querySelector('.tabIndicator');
const offsetTop = selectedTabElement.offsetTop;
tabIndicator.style.opacity = `1`;
tabIndicator.style.top = `calc(${offsetTop}px + (var(--menuSize) / 6))`;
}
updateTab(tabArg: interfaces.ITab) {
this.selectedTab = tabArg;
this.updateTabIndicator();
this.selectedTab.action();
}
firstUpdated() {
this.updateTab(this.tabs[0]);
}
}

View File

@ -0,0 +1,160 @@
import * as plugins from './00plugins.js';
import * as interfaces from './interfaces/index.js';
import { DeesContextmenu } from './dees-contextmenu.js';
import {
DeesElement,
type TemplateResult,
property,
customElement,
html,
css,
cssManager,
} from '@design.estate/dees-element';
/**
* the property selector menu
* mainly used to select assets within in an organization
*/
@customElement('dees-appui-mainselector')
export class DeesAppuiMainselector extends DeesElement {
public static demo = () => html`<dees-appui-mainselector></dees-appui-mainselector>`;
// INSTANCE
@property()
public selectionOptions: interfaces.ISelectionOption[] = [
{
key: 'Overview',
action: () => {},
},
{
key: 'option 1',
action: () => {},
},
{ key: 'option 2', action: () => {} },
{ key: 'option 3', action: () => {} },
{ key: 'option 4', action: () => {} },
];
@property()
public selectedOption: interfaces.ISelectionOption = null;
public static styles = [
cssManager.defaultStyles,
css`
:host {
color: #fff;
position: relative;
display: block;
width: 100%;
max-width: 300px;
height: 100%;
background: #000000;
border-right: 1px solid #222222;
}
.maincontainer {
position: absolute;
top: 0px;
left: 0px;
height: 100%;
width: 100%;
}
.topbar {
position: absolute;
height: 32px;
width: 100%;
}
.topbar .heading {
padding-left: 16px;
padding-top: 8px;
line-height: 24px;
font-family: 'Geist Sans', sans-serif;
font-weight: 600;
font-size: 14px;
}
.selectionOptions {
position: absolute;
top: 32px;
padding-top: 8px;
left: 0px;
width: 100%;
font-family: 'Geist Sans', sans-serif;
font-size: 14px;
}
.selectionOptions .selectionOption {
cursor: default;
margin-left: 16px;
margin-right: 16px;
padding-top: 8px;
padding-bottom: 8px;
border-top: 1px dotted #303030;
border-left: 0px solid rgba(0, 0, 0, 0);
transition: all 0.1s;
}
.selectionOptions .selectionOption:hover {
border-left: 2px solid #26a69a50;
padding-left: 8px;
}
.selectionOptions .selectionOption:first-child {
border-top: 1px solid rgba(0, 0, 0, 0);
}
.selectionOptions .selectionOption.selectedOption {
border-left: 4px solid #26a69a;
padding-left: 10px;
}
`,
];
public render(): TemplateResult {
return html`
<style></style>
<div class="maincontainer">
<div class="topbar">
<div class="heading">Properties</div>
</div>
<div class="selectionOptions">
${this.selectionOptions.map((selectionOptionArg) => {
return html`
<div
class="selectionOption ${this.selectedOption === selectionOptionArg
? 'selectedOption'
: null}"
@click="${() => {
this.selectOption(selectionOptionArg);
}}"
@contextmenu="${(eventArg: MouseEvent) => {
DeesContextmenu.openContextMenuWithOptions(eventArg, [
{
name: 'property settings',
action: async () => {},
iconName: 'gear',
},
]);
}}"
>
${selectionOptionArg.key}
</div>
`;
})}
</div>
</div>
`;
}
private selectOption(optionArg: interfaces.ISelectionOption) {
this.selectedOption = optionArg;
this.selectedOption.action();
}
firstUpdated() {
this.selectOption(this.selectionOptions[0]);
}
}

View File

@ -61,11 +61,10 @@ export class DeesButton extends DeesElement {
public static styles = [ public static styles = [
cssManager.defaultStyles, cssManager.defaultStyles,
css` css`
:host { :host {
display: block; display: block;
box-sizing: border-box; box-sizing: border-box;
font-family: 'Roboto', 'monospace'; font-family: 'Geist Sans', 'monospace';
} }
:host([hidden]) { :host([hidden]) {
display: none; display: none;
@ -84,7 +83,7 @@ export class DeesButton extends DeesElement {
border: 1px solid ${cssManager.bdTheme('#eee', '#333')}; border: 1px solid ${cssManager.bdTheme('#eee', '#333')};
border-top: ${cssManager.bdTheme('1px solid #eee', '1px solid #444')}; border-top: ${cssManager.bdTheme('1px solid #eee', '1px solid #444')};
border-radius: 4px; border-radius: 4px;
line-height: 40px; height: 40px;
padding: 0px 8px; padding: 0px 8px;
min-width: 100px; min-width: 100px;
user-select: none; user-select: none;
@ -93,16 +92,15 @@ export class DeesButton extends DeesElement {
} }
.button:hover { .button:hover {
cursor: pointer; background: #0050b9;
background: #039be5;
color: #ffffff; color: #ffffff;
border: 1px solid #039be5; border: 1px solid #0050b9;
border-top: 1px solid #039be5; border-top: 1px solid #0050b9;
} }
.button:active { .button:active {
background: #0277bd; background: #0069f2;
border-top: 1px solid #0277bd; border-top: 1px solid #0069f2;
} }
.button.disabled { .button.disabled {
@ -146,8 +144,8 @@ export class DeesButton extends DeesElement {
} }
.button.pending { .button.pending {
border: 1px dashed ${cssManager.bdTheme('#0277bd', '#0277bd70')}; border: 1px dashed ${cssManager.bdTheme('#0069f2', '#0069f270')};
background: ${cssManager.bdTheme('#0277bd', '#0277bd70')}; background: ${cssManager.bdTheme('#0069f2', '#0069f270')};
color: #fff; color: #fff;
} }

View File

@ -0,0 +1,21 @@
import { html } from '@design.estate/dees-element';
export const demoFunc = () => {
return html`
<style>
.demoBox {
position: relative;
background: #000000;
height: 100%;
width: 100%;
padding: 40px;
box-sizing: border-box;
}
</style>
<div class="demoBox">
<dees-chart-area
.label=${'System Usage'}
></dees-chart-area>
</div>
`;
};

View File

@ -0,0 +1,214 @@
import {
DeesElement,
css,
cssManager,
customElement,
html,
property,
state,
type CSSResult,
type TemplateResult,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
import { demoFunc } from './dees-chart-area.demo.js';
import ApexCharts from 'apexcharts';
declare global {
interface HTMLElementTagNameMap {
'dees-chart-area': DeesChartArea;
}
}
@customElement('dees-chart-area')
export class DeesChartArea extends DeesElement {
public static demo = demoFunc;
// instance
@state()
public chart: ApexCharts;
@property()
public label: string = 'Untitled Chart';
private resizeObserver: ResizeObserver;
constructor() {
super();
domtools.elementBasic.setup();
this.resizeObserver = new ResizeObserver(entries => {
for (let entry of entries) {
if (entry.target.classList.contains('mainbox')) {
this.resizeChart(); // Call resizeChart when the .mainbox size changes
}
}
});
this.registerStartupFunction(async () => {
this.updateComplete.then(() => {
const mainbox = this.shadowRoot.querySelector('.mainbox');
if (mainbox) {
this.resizeObserver.observe(mainbox); // Start observing the .mainbox element
}
});
});
this.registerGarbageFunction(async () => {
this.resizeObserver.disconnect();
})
}
public static styles = [
cssManager.defaultStyles,
css`
:host {
font-family: 'Geist Sans', sans-serif;
color: #ccc;
font-weight: 600;
font-size: 12px;
}
.mainbox {
position: relative;
width: 100%;
height: 400px;
background: #222;
border-radius: 8px;
}
.chartTitle {
position: absolute;
top: 0;
left: 0;
width: 100%;
text-align: center;
padding-top: 16px;
}
.chartContainer {
position: absolute;
top: 0px;
left: 0px;
bottom: 0px;
right: 0px;
padding: 32px 16px 16px 0px;
}
`,
];
public render(): TemplateResult {
return html` <div class="mainbox">
<div class="chartTitle">${this.label}</div>
<div class="chartContainer"></div>
</div> `;
}
public async firstUpdated() {
const domtoolsInstance = await this.domtoolsPromise;
var options: ApexCharts.ApexOptions = {
series: [
{
name: 'cpu',
data: [31, 40, 28, 51, 42, 109, 100],
},
{
name: 'memory',
data: [11, 32, 45, 32, 34, 52, 41],
},
],
chart: {
width: 0, // Adjusted for responsive width
height: 0, // Adjusted for responsive height
type: 'area',
toolbar: {
show: false, // This line disables the toolbar
},
},
dataLabels: {
enabled: false,
},
stroke: {
width: 1,
curve: 'smooth',
},
xaxis: {
crosshairs: {
stroke: {
width: 1,
color: '#444',
},
},
type: 'datetime',
categories: [
'2018-09-19T00:00:00.000Z',
'2018-09-19T01:30:00.000Z',
'2018-09-19T02:30:00.000Z',
'2018-09-19T03:30:00.000Z',
'2018-09-19T04:30:00.000Z',
'2018-09-19T05:30:00.000Z',
'2018-09-19T06:30:00.000Z',
],
},
yaxis: {
crosshairs: {
stroke: {
width: 1,
color: '#444',
},
},
},
tooltip: {
x: {
format: 'dd/MM/yy HH:mm',
},
},
grid: {
xaxis: {
lines: {
show: true, // This enables the grid lines along the x-axis
},
},
yaxis: {
lines: {
show: true,
},
},
borderColor: '#666', // Set the color of the grid lines
strokeDashArray: 2, // Solid line
row: {
colors: [], // This can be used to alternate the shading of the horizontal rows
opacity: 0.1,
},
column: {
colors: [], // For vertical column bands, not needed here but available for customization
opacity: 0.1,
},
},
};
this.chart = new ApexCharts(this.shadowRoot.querySelector('.chartContainer'), options);
await this.chart.render();
await this.resizeChart();
}
public async resizeChart() {
const element = this.shadowRoot.querySelector('.chartContainer');
// Get computed style of the element
const style = window.getComputedStyle(element);
// Extract padding values
const paddingTop = parseInt(style.paddingTop, 10);
const paddingBottom = parseInt(style.paddingBottom, 10);
const paddingLeft = parseInt(style.paddingLeft, 10);
const paddingRight = parseInt(style.paddingRight, 10);
// Calculate the actual width and height to use, subtracting padding
const actualWidth = element.clientWidth - paddingLeft - paddingRight;
const actualHeight = element.clientHeight - paddingTop - paddingBottom;
await this.chart.updateOptions({
chart: {
width: actualWidth,
height: actualHeight,
},
});
}
}

View File

@ -0,0 +1,20 @@
import { html } from '@design.estate/dees-element';
export const demoFunc = () => {
return html`
<style>
.demoBox {
position: relative;
background: #000000;
height: 100%;
width: 100%;
padding: 40px;
}
</style>
<div class="demoBox">
<dees-chart-log
.label=${'Event Log'}
></dees-chart-log>
</div>
`;
};

View File

@ -0,0 +1,89 @@
import {
DeesElement,
css,
cssManager,
customElement,
html,
property,
state,
type CSSResult,
type TemplateResult,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
import { demoFunc } from './dees-chart-log.demo.js';
import ApexCharts from 'apexcharts';
declare global {
interface HTMLElementTagNameMap {
'dees-chart-log': DeesChartLog;
}
}
@customElement('dees-chart-log')
export class DeesChartLog extends DeesElement {
public static demo = demoFunc;
// instance
@state()
public chart: ApexCharts;
@property()
public label: string = 'Untitled Chart';
constructor() {
super();
domtools.elementBasic.setup();
}
public static styles = [
cssManager.defaultStyles,
css`
:host {
font-family: 'Geist Sans', sans-serif;
color: #ccc;
font-weight: 600;
font-size: 12px;
}
.mainbox {
position: relative;
width: 100%;
height: 400px;
background: #222;
border-radius: 8px;
padding: 32px 16px 16px 0px;
}
.chartTitle {
position: absolute;
top: 0;
left: 0;
width: 100%;
text-align: center;
padding-top: 16px;
}
.chartContainer {
position: relative;
width: 100%;
height: 100%;
}
`,
];
public render(): TemplateResult {
return html` <div class="mainbox">
<div class="chartTitle">${this.label}</div>
<div class="chartContainer"></div>
</div> `;
}
public async firstUpdated() {
const domtoolsInstance = await this.domtoolsPromise;
}
public async updateLog() {
}
}

View File

@ -81,7 +81,6 @@ export class DeesChips extends DeesElement {
.chip:hover { .chip:hover {
background: #666666; background: #666666;
cursor: pointer;
} }
.chip.selected { .chip.selected {

View File

@ -1,5 +1,5 @@
import { html } from '@design.estate/dees-element'; import { html } from '@design.estate/dees-element';
import * as plugins from './plugins.js'; import * as plugins from './00plugins.js';
import { DeesContextmenu } from './dees-contextmenu.js'; import { DeesContextmenu } from './dees-contextmenu.js';

View File

@ -1,5 +1,6 @@
import * as colors from './00colors.js';
import * as plugins from './00plugins.js';
import { demoFunc } from './dees-contextmenu.demo.js'; import { demoFunc } from './dees-contextmenu.demo.js';
import * as plugins from './plugins.js';
import { import {
customElement, customElement,
html, html,
@ -110,16 +111,18 @@ export class DeesContextmenu extends DeesElement {
color: ${cssManager.bdTheme('#222', '#ccc')}; color: ${cssManager.bdTheme('#222', '#ccc')};
font-size: 14px; font-size: 14px;
width: 200px; width: 200px;
border: 1px solid ${cssManager.bdTheme('#fff', '#444')}; border: 1px solid ${cssManager.bdTheme('#fff', '#ffffff10')};
min-height: 34px; min-height: 34px;
border-radius: 3px; border-radius: 3px;
background: ${cssManager.bdTheme('#fff', '#222')}; background: ${cssManager.bdTheme('#fff', '#222')};
box-shadow: 0px 1px 4px ${cssManager.bdTheme('#00000020', '#000000')}; box-shadow: 0px 1px 4px ${cssManager.bdTheme('#00000020', '#000000')};
user-select: none; user-select: none;
padding: 4px;
} }
.mainbox .menuitem { .mainbox .menuitem {
padding: 8px; padding: 4px 8px;
border-radius: 3px;
} }
.mainbox .menuitem dees-icon { .mainbox .menuitem dees-icon {
@ -130,12 +133,10 @@ export class DeesContextmenu extends DeesElement {
} }
.mainbox .menuitem:hover { .mainbox .menuitem:hover {
cursor: pointer; background: ${cssManager.bdTheme(colors.bright.blue, colors.dark.blue)};
background: ${cssManager.bdTheme('#00000010', '#ffffff10')};
} }
.mainbox .menuitem:active { .mainbox .menuitem:active {
cursor: pointer;
background: #ffffff05; background: #ffffff05;
} }
`, `,
@ -158,7 +159,7 @@ export class DeesContextmenu extends DeesElement {
this.destroy(); this.destroy();
}}> }}>
<dees-icon .iconFA=${'xmark'}></dees-icon <dees-icon .iconFA=${'xmark'}></dees-icon
>Deactivate Contextmenu globally. >allow native context
</div> </div>
` : html``} ` : html``}
</div> </div>

View File

@ -48,7 +48,7 @@ export class DeesDataviewCodebox extends DeesElement {
display: block; display: block;
text-align: left; text-align: left;
font-size: 16px; font-size: 16px;
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
} }
.mainbox { .mainbox {
position: relative; position: relative;
@ -61,51 +61,22 @@ export class DeesDataviewCodebox extends DeesElement {
} }
.appbar { .appbar {
position: relative;
color: ${cssManager.bdTheme('#333', '#ccc')}; color: ${cssManager.bdTheme('#333', '#ccc')};
background: ${cssManager.bdTheme('#ffffff', '#161616')}; background: ${cssManager.bdTheme('#ffffff', '#161616')};
border-bottom: 1px solid ${cssManager.bdTheme('#eeeeeb', '#222222')}; border-bottom: 1px solid ${cssManager.bdTheme('#eeeeeb', '#222222')};
height: 24px; height: 24px;
display: flex;
font-size: 12px; font-size: 12px;
line-height: 24px; line-height: 24px;
} justify-content: center;
align-items: center;
.appbar .macControls {
position: absolute;
top: 6px;
left: 20px;
width: 200px;
display: grid;
grid-template-columns: 24px 24px 24px;
}
.appbar .macControls div {
width: 12px;
height: 12px;
display: inline-block;
border-radius: 50%;
margin: 0px;
padding: 0px;
cursor: pointer;
background: #222222;
}
.appbar .macControls div.close {
background: #ff5f57;
}
.appbar .macControls div.toDock {
background: #ffbd2e;
}
.appbar .macControls div.minMax {
background: #27c93f;
}
.appbar .macControls div:hover {
background: #333333;
} }
.appbar .fileName { .appbar .fileName {
line-height: inherit;
position: relative;
flex: 1;
text-align: center; text-align: center;
} }
@ -171,7 +142,7 @@ export class DeesDataviewCodebox extends DeesElement {
.lineNumbers { .lineNumbers {
line-height: 1.4em; line-height: 1.4em;
font-weight: 200; font-weight: 200;
font-family: 'Intel One Mono', 'monospace'; font-family: 'Intel One Mono', 'Geist Mono', 'monospace';
} }
.hljs-string { .hljs-string {
@ -209,12 +180,9 @@ export class DeesDataviewCodebox extends DeesElement {
}}" }}"
> >
<div class="appbar"> <div class="appbar">
<div class="macControls"> <dees-windowcontrols type="mac" position="left"></dees-windowcontrols>
<div class="close"></div>
<div class="toDock"></div>
<div class="minMax"></div>
</div>
<div class="fileName">index.ts</div> <div class="fileName">index.ts</div>
<dees-windowcontrols type="mac" position="right"></dees-windowcontrols>
</div> </div>
<div class="codegrid"> <div class="codegrid">
<div class="lineNumbers"> <div class="lineNumbers">

View File

@ -1,39 +1,49 @@
import { html } from '@design.estate/dees-element'; import { html, cssManager } from '@design.estate/dees-element';
import * as tsclass from '@tsclass/tsclass'; import * as tsclass from '@tsclass/tsclass';
export const demoFunc = () => html`<dees-dataview-statusobject export const demoFunc = () => html` <style>
.statusObject=${{ .demo {
id: '1', background: ${cssManager.bdTheme('#eeeeeb', '#000000')};
name: 'Demo Item', display: block;
combinedStatus: 'partly_ok', content: '';
combinedStatusText: 'partly_ok', padding: 40px;
details: [ }
{ </style>
name: 'Detail 1', <div class="demo">
value: 'Value 1', <dees-dataview-statusobject
status: 'ok', .statusObject=${{
statusText: 'OK', id: '1',
}, name: 'Demo Item',
{ combinedStatus: 'partly_ok',
name: 'Detail 2', combinedStatusText: 'partly_ok',
value: 'Value 2', details: [
status: 'partly_ok', {
statusText: 'partly_ok', name: 'Detail 1',
}, value: 'Value 1',
{ status: 'ok',
name: 'Detail 3', statusText: 'OK',
value: 'Value 3', },
status: 'not_ok', {
statusText: 'not_ok', name: 'Detail 2',
}, value: 'Value 2',
{ status: 'partly_ok',
name: 'Detail 4', statusText: 'partly_ok',
value: },
'Value 4 jhdkfjhalskdfjhfdjskalsdkfjhfdjskalskdjfhjdkslaksjdhfjdkslaskdfjhfjdkslaskdjfhjdskalskdjhfdjskalskdjfhdjskl', {
status: 'ok', name: 'Detail 3',
statusText: 'OK', value: 'Value 3',
}, status: 'not_ok',
], statusText: 'not_ok',
} as tsclass.code.IStatusObject} },
> {
</dees-dataview-statusobject>`; name: 'Detail 4',
value:
'Value 4 jhdkfjhalskdfjhfdjskalsdkfjhfdjskalskdjfhjdkslaksjdhfjdkslaskdfjhfjdkslaskdjfhjdskalskdjhfdjskalskdjfhdjskl',
status: 'ok',
statusText: 'OK',
},
],
} as tsclass.code.IStatusObject}
>
</dees-dataview-statusobject>
</div>`;

View File

@ -1,3 +1,6 @@
import * as colors from './00colors.js';
import * as plugins from './00plugins.js';
import { demoFunc } from './dees-dataview-statusobject.demo.js'; import { demoFunc } from './dees-dataview-statusobject.demo.js';
import { import {
DeesElement, DeesElement,
@ -34,6 +37,8 @@ export class DeesDataviewStatusobject extends DeesElement {
box-shadow: 0px 1px 3px #00000030; box-shadow: 0px 1px 3px #00000030;
min-height: 48px; min-height: 48px;
color: ${cssManager.bdTheme('#000', '#fff')}; color: ${cssManager.bdTheme('#000', '#fff')};
border-top: ${cssManager.bdTheme('none', '1px solid #ffffff10')};
cursor: default;
} }
.heading { .heading {
@ -61,16 +66,28 @@ export class DeesDataviewStatusobject extends DeesElement {
} }
.copyMain { .copyMain {
cursor: pointer;
font-size: 10px; font-size: 10px;
font-weight: 600; font-weight: 600;
text-transform: uppercase; text-transform: uppercase;
border: 1px solid ${cssManager.bdTheme('#999', '#444')}; border: 1px solid ${cssManager.bdTheme('#e0e0e0', '#444')};
text-align: center; text-align: center;
padding: 4px; padding: 4px;
border-radius: 3px; border-radius: 3px;
margin-right: 16px; margin-right: 16px;
color: #ffffff80 color: ${cssManager.bdTheme('#333', '#ffffff80')};
user-select: none;
}
.copyMain:hover {
background: ${cssManager.bdTheme(colors.bright.blue, colors.dark.blue)};
border: 1px solid ${cssManager.bdTheme(colors.bright.blue, colors.dark.blue)};
color: #fff;
}
.copyMain:active {
background: ${cssManager.bdTheme(colors.bright.blueActive, colors.dark.blueActive)};
border: 1px solid ${cssManager.bdTheme(colors.bright.blueActive, colors.dark.blueActive)};
color: #fff;
} }
.statusdot.ok { .statusdot.ok {
@ -86,11 +103,20 @@ export class DeesDataviewStatusobject extends DeesElement {
} }
.detail { .detail {
minheight: 60px; min-height: 60px;
align-items: center; align-items: center;
display: grid; display: grid;
grid-template-columns: 40px auto; grid-template-columns: 40px auto;
border-top: 1px dotted ${cssManager.bdTheme('#999', '#282828')}; border-top: 1px dotted ${cssManager.bdTheme('#e0e0e0', '#282828')};
transition: all 0.2s;
}
.detail:hover {
background: #ffffff05;
}
.detail:active {
background: #ffffff10;
} }
.detail .detailsText { .detail .detailsText {
@ -107,7 +133,7 @@ export class DeesDataviewStatusobject extends DeesElement {
.detail .detailsText .value { .detail .detailsText .value {
font-size: 14px; font-size: 14px;
font-family: 'Intel One Mono'; font-family: 'Intel One Mono', 'Geist Mono';
} }
`, `,
]; ];

View File

@ -0,0 +1,98 @@
import {
DeesElement,
property,
html,
customElement,
type TemplateResult,
css,
cssManager,
domtools
} from '@design.estate/dees-element';
const deferred = domtools.plugins.smartpromise.defer();
declare global {
interface HTMLElementTagNameMap {
'dees-editormarkdown': DeesEditorMarkdown;
}
}
@customElement('dees-editormarkdown')
export class DeesEditorMarkdown extends DeesElement {
public static demo = () => html`<dees-editormarkdown></dees-editormarkdown>`;
public static styles = [
cssManager.defaultStyles,
css`
.gridcontainer {
position: absolute;
height: 100%;
width: 100%;
display: grid;
grid-template-columns: 60% 40%;
}
.editorContainer {
position: relative;
}
.outletContainer {
background: #111;
color: #fff;
font-family: 'Roboto Slab';
padding: 20px;
overflow-y: scroll;
}
`,
];
public render() {
return html`
<div class="gridcontainer">
<div class="editorContainer">
<dees-editor
.language=${'markdown'}
.content=${`# a test content
This is test content that is of longer form an hopefully starts to wrap when I need it. And yes, it does perfectly. nice.
Test | Hello
--- | ---
Yeah | So good
This is real asset I think. Why would we want to leave that on the table? Can you tell my that?
Why are we here?
Do you know?
> note:
There is something going on.
\`\`\`typescript
const hello = 'yes'
\`\`\`
`}
wordWrap="bounded"
></dees-editor>
</div>
<div class="outletContainer">
<dees-editormarkdownoutlet></dees-editormarkdownoutlet>
</div>
</div>
`;
}
public async firstUpdated(_changedPropertiesArg) {
await super.firstUpdated(_changedPropertiesArg);
const editor = this.shadowRoot.querySelector('dees-editor');
// lets care about wiring the markdown stuff.
const markdownOutlet = this.shadowRoot.querySelector('dees-editormarkdownoutlet');
const smartmarkdownInstance = new domtools.plugins.smartmarkdown.SmartMarkdown();
const mdParsedResult = await smartmarkdownInstance.getMdParsedResultFromMarkdown('loading...')
editor.contentSubject.subscribe(async contentArg => {
await mdParsedResult.updateFromMarkdownString(contentArg)
const html = mdParsedResult.html;
markdownOutlet.updateHtmlText(html);
})
}
}

View File

@ -0,0 +1,42 @@
import { customElement, DeesElement, html, type TemplateResult } from '@design.estate/dees-element';
declare global {
interface HTMLElementTagNameMap {
'dees-editormarkdownoutlet': DeesEditorMarkdownOutlet;
}
}
@customElement('dees-editormarkdownoutlet')
export class DeesEditorMarkdownOutlet extends DeesElement {
// DEMO
public static demo = () => html`<dees-editormarkdownoutlet></dees-editormarkdownoutlet>`;
// INSTANCE
private outlet: HTMLElement;
public render(): TemplateResult {
return html`
<div class="outlet markdown-body">
<h1>Hi there</h1>
</div>
`;
}
public async firstUpdated(_changedProperties: Map<string | number | symbol, unknown>) {
await super.firstUpdated(_changedProperties);
const styleElement = document.createElement('style');
const cssText = await (
await fetch('https://unpkg.com/github-markdown-css@5.1.0/github-markdown-dark.css')
).text();
styleElement.textContent = cssText;
this.shadowRoot.append(styleElement);
}
public async updateHtmlText(htmlTextArg: string) {
await this.updateComplete;
if (!this.outlet) {
this.outlet = this.shadowRoot.querySelector('.outlet');
}
this.outlet.innerHTML = htmlTextArg;
}
}

View File

@ -0,0 +1,126 @@
import {
DeesElement,
property,
html,
customElement,
type TemplateResult,
css,
cssManager,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
import type * as monaco from 'monaco-editor';
declare global {
interface HTMLElementTagNameMap {
'dees-editor': DeesEditor;
}
}
@customElement('dees-editor')
export class DeesEditor extends DeesElement {
// DEMO
public static demo = () => html` <dees-editor></dees-editor> `;
// STATIC
public static monacoDeferred: ReturnType<typeof domtools.plugins.smartpromise.defer>;
// INSTANCE
public editorDeferred = domtools.plugins.smartpromise.defer<monaco.editor.IStandaloneCodeEditor>();
public language = 'typescript';
@property({
type: String
})
public content = "function hello() {\n\talert('Hello world!');\n}";
@property({
type: Object
})
public contentSubject = new domtools.plugins.smartrx.rxjs.Subject<string>();
@property({
type: Boolean
})
public wordWrap: monaco.editor.IStandaloneEditorConstructionOptions['wordWrap'] = 'off';
constructor() {
super();
domtools.DomTools.setupDomTools();
}
public static styles = [
cssManager.defaultStyles,
css`
:host {
}
* {
box-sizing: border-box;
}
#container {
position: absolute;
height: 100%;
width: 100%;
}
`,
];
public render(): TemplateResult {
return html`
<div class="mainbox">
<div id="container"></div>
</div>
`;
}
public async firstUpdated(
_changedProperties: Map<string | number | symbol, unknown>
): Promise<void> {
super.firstUpdated(_changedProperties);
const container = this.shadowRoot.getElementById('container');
if (!DeesEditor.monacoDeferred) {
DeesEditor.monacoDeferred = domtools.plugins.smartpromise.defer();
const scriptUrl = `https://cdn.jsdelivr.net/npm/monaco-editor/min/vs/loader.js`;
const script = document.createElement('script');
script.src = scriptUrl;
script.onload = () => {
DeesEditor.monacoDeferred.resolve();
};
document.head.appendChild(script);
}
await DeesEditor.monacoDeferred.promise;
(window as any).require.config({
paths: { vs: 'https://cdn.jsdelivr.net/npm/monaco-editor/min/vs' },
});
(window as any).require(['vs/editor/editor.main'], async () => {
const editor = ((window as any).monaco.editor as typeof monaco.editor).create(container, {
value: this.content,
language: this.language,
theme: 'vs-dark',
useShadowDOM: true,
fontSize: 16,
automaticLayout: true,
wordWrap: this.wordWrap
});
this.editorDeferred.resolve(editor);
});
const css = await (
await fetch('https://cdn.jsdelivr.net/npm/monaco-editor/min/vs/editor/editor.main.css')
).text();
const styleElement = document.createElement('style');
styleElement.textContent = css;
this.shadowRoot.append(styleElement);
// editor is setup let do the rest
const editor = await this.editorDeferred.promise;
editor.onDidChangeModelContent(async eventArg => {
this.contentSubject.next(editor.getValue());
});
this.contentSubject.next(editor.getValue());
}
}

View File

@ -1,13 +1,14 @@
import { html, domtools } from '@design.estate/dees-element'; import { html, domtools, cssManager } from '@design.estate/dees-element';
import type { DeesForm } from './dees-form.js'; import type { DeesForm } from './dees-form.js';
export const demoFunc = () => html` export const demoFunc = () => html`
<style> <style>
.demoContainer { .demoContainer {
max-width: 400px; max-width: 400px;
margin: auto; margin: 24px auto;
padding: 16px; padding: 16px;
background: #111; background: ${cssManager.bdTheme('#eeeeeb', '#111')};
box-shadow: 0px 1px 3px #00000030;
} }
</style> </style>
<div class="demoContainer"> <div class="demoContainer">
@ -20,15 +21,48 @@ export const demoFunc = () => html`
form.setStatus('success', 'authenticated!'); form.setStatus('success', 'authenticated!');
}} }}
> >
<dees-input-text .required="${true}" key="hello1" label="a text"></dees-input-text> <dees-input-dropdown
.label=${'title'}
.options=${[
{ option: 'option 1', key: 'option1' },
{ option: 'option 2', key: 'option2' },
{ option: 'option 3', key: 'option3' },
]}
></dees-input-dropdown>
<dees-input-multiselect
.label=${'title'}
.options=${[
{ option: 'option 1', key: 'option1' },
{ option: 'option 2', key: 'option2' },
{ option: 'option 3', key: 'option3' },
]}></dees-input-multiselect>
<dees-input-typelist
.label=${'a type list'}
></dees-input-typelist>
<dees-input-text .required="${true}" key="hello1" label="a text" .description=${`
This is an awesome description.
`}></dees-input-text>
<dees-input-text .required="${true}" key="hello2" label="also a text"></dees-input-text> <dees-input-text .required="${true}" key="hello2" label="also a text"></dees-input-text>
<dees-input-text .required="${true}" key="hello3" label="a password" isPasswordBool></dees-input-text> <dees-input-text
.required="${true}"
key="hello3"
label="a password"
isPasswordBool
></dees-input-text>
<dees-input-checkbox <dees-input-checkbox
.required="${true}" .required="${true}"
key="hello3" key="hello3"
label="another text" label="another text"
></dees-input-checkbox> ></dees-input-checkbox>
<dees-input-iban></dees-input-iban> <dees-input-iban></dees-input-iban>
<dees-input-multitoggle
.label=${'multi select'}
.options=${['option 1', 'option 2', 'option 3']}
.selectedOption=${'option 1'}
></dees-input-multitoggle>
<dees-input-fileupload
.label=${'attachments'}
></dees-input-fileupload>
<dees-form-submit>Submit</dees-form-submit> <dees-form-submit>Submit</dees-form-submit>
</dees-form> </dees-form>
</div> </div>

View File

@ -101,6 +101,10 @@ export class DeesForm extends DeesElement {
} }
} }
/**
* collects the form data
* @returns
*/
public async collectFormData() { public async collectFormData() {
const children = this.getFormElements(); const children = this.getFormElements();
const valueObject: { [key: string]: string | number | boolean | any[] } = {}; const valueObject: { [key: string]: string | number | boolean | any[] } = {};

View File

@ -50,11 +50,15 @@ import {
faEyeSlash as faEyeSlashSolid, faEyeSlash as faEyeSlashSolid,
faFileInvoice as faFileInvoiceSolid, faFileInvoice as faFileInvoiceSolid,
faFileInvoiceDollar as faFileInvoiceDollarSolid, faFileInvoiceDollar as faFileInvoiceDollarSolid,
faGear as faGearSolid,
faGrip as faGripSolid, faGrip as faGripSolid,
faMagnifyingGlass as faMagnifyingGlassSolid,
faMessage as faMessageSolid, faMessage as faMessageSolid,
faMoneyCheckDollar as faMoneyCheckDollarSolid, faMoneyCheckDollar as faMoneyCheckDollarSolid,
faMugHot as faMugHotSolid, faMugHot as faMugHotSolid,
faMinus as faMinusSolid, faMinus as faMinusSolid,
faNetworkWired as faNetworkWiredSolid,
faPaperclip as faPaperclipSolid,
faPaste as faPasteSolid, faPaste as faPasteSolid,
faPenToSquare as faPenToSquareSolid, faPenToSquare as faPenToSquareSolid,
faPlus as faPlusSolid, faPlus as faPlusSolid,
@ -63,6 +67,7 @@ import {
faUsers as faUsersSolid, faUsers as faUsersSolid,
faShare as faShareSolid, faShare as faShareSolid,
faSun as faSunSolid, faSun as faSunSolid,
faTerminal as faTerminalSolid,
faTrash as faTrashSolid, faTrash as faTrashSolid,
faTrashCan as faTrashCanSolid, faTrashCan as faTrashCanSolid,
faWallet as faWalletSolid, faWallet as faWalletSolid,
@ -93,12 +98,16 @@ export const faIcons = {
eyeSlash: faEyeSlashSolid, eyeSlash: faEyeSlashSolid,
fileInvoice: faFileInvoiceSolid, fileInvoice: faFileInvoiceSolid,
fileInvoiceDoller: faFileInvoiceDollarSolid, fileInvoiceDoller: faFileInvoiceDollarSolid,
gear: faGearSolid,
grip: faGripSolid, grip: faGripSolid,
magnifyingGlass: faMagnifyingGlassSolid,
message: faMessageRegular, message: faMessageRegular,
messageSolid: faMessageSolid, messageSolid: faMessageSolid,
moneyCheckDollar: faMoneyCheckDollarSolid, moneyCheckDollar: faMoneyCheckDollarSolid,
mugHot: faMugHotSolid, mugHot: faMugHotSolid,
minus: faMinusSolid, minus: faMinusSolid,
networkWired: faNetworkWiredSolid,
paperclip: faPaperclipSolid,
paste: faPasteRegular, paste: faPasteRegular,
pasteSolid: faPasteSolid, pasteSolid: faPasteSolid,
penToSquare: faPenToSquareSolid, penToSquare: faPenToSquareSolid,
@ -108,6 +117,7 @@ export const faIcons = {
share: faShareSolid, share: faShareSolid,
sun: faSunRegular, sun: faSunRegular,
sunSolid: faSunSolid, sunSolid: faSunSolid,
terminal: faTerminalSolid,
trash: faTrashSolid, trash: faTrashSolid,
trashSolid: faTrashSolid, trashSolid: faTrashSolid,
trashCan: faTrashCanRegular, trashCan: faTrashCanRegular,

View File

@ -62,7 +62,10 @@ export class DeesInputCheckbox extends DeesElement {
display: block; display: block;
position: relative; position: relative;
margin: 20px 0px; margin: 20px 0px;
cursor: pointer; cursor: default;
}
:host(:hover) {
filter: ${cssManager.bdTheme('brightness(0.95)', 'brightness(1.1)')};
} }
.maincontainer { .maincontainer {
@ -100,8 +103,8 @@ export class DeesInputCheckbox extends DeesElement {
} }
.checkbox.selected { .checkbox.selected {
background: #039BE5; background: #0050b9;
border: 1px solid #039BE5; border: 1px solid #0050b9;
} }
.checkbox.disabled { .checkbox.disabled {

View File

@ -8,4 +8,20 @@ export const demoFunc = () => html`
{option: 'option 3', key: 'option3'} {option: 'option 3', key: 'option3'}
]} ]}
></dees-input-dropdown> ></dees-input-dropdown>
<dees-input-dropdown
.enableSearch=${false}
.options=${[
{option: 'option 1', key: 'option1'},
{option: 'option 2', key: 'option2'},
{option: 'option 3', key: 'option3'}
]}
></dees-input-dropdown>
<div style="height: 300px"></div>
<dees-input-dropdown
.options=${[
{option: 'option 1', key: 'option1'},
{option: 'option 2', key: 'option2'},
{option: 'option 3', key: 'option3'}
]}
></dees-input-dropdown>
` `

View File

@ -1,6 +1,17 @@
import { customElement, DeesElement, type TemplateResult, property, html, css, cssManager, type CSSResult, } from '@design.estate/dees-element'; import {
customElement,
DeesElement,
type TemplateResult,
property,
state,
html,
css,
cssManager,
type CSSResult,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools'; import * as domtools from '@design.estate/dees-domtools';
import { demoFunc } from './dees-input-dropdown.demo.js'; import { demoFunc } from './dees-input-dropdown.demo.js';
import { DeesWindowLayer } from './dees-windowlayer.js';
declare global { declare global {
interface HTMLElementTagNameMap { interface HTMLElementTagNameMap {
@ -10,7 +21,7 @@ declare global {
@customElement('dees-input-dropdown') @customElement('dees-input-dropdown')
export class DeesInputDropdown extends DeesElement { export class DeesInputDropdown extends DeesElement {
public static demo = demoFunc public static demo = demoFunc;
// INSTANCE // INSTANCE
public changeSubject = new domtools.plugins.smartrx.rxjs.Subject(); public changeSubject = new domtools.plugins.smartrx.rxjs.Subject();
@ -25,144 +36,340 @@ export class DeesInputDropdown extends DeesElement {
public key: string; public key: string;
@property() @property()
public options: {option: string, key: string, payload?: any}[] = []; public options: { option: string; key: string; payload?: any }[] = [];
@property() @property()
public selectedOption: {option: string, key: string, payload?: any} = { public selectedOption: { option: string; key: string; payload?: any } = null;
key: null,
option: null,
payload: null
};
@property({ @property({
type: Boolean type: Boolean,
}) })
public required: boolean = false; public required: boolean = false;
@property({ @property({
type: Boolean type: Boolean,
})
public enableSearch: boolean = true;
@property({
type: Boolean,
}) })
public disabled: boolean = false; public disabled: boolean = false;
@state()
public opensToTop: boolean = false;
@state()
private filteredOptions: { option: string; key: string; payload?: any }[] = [];
@state()
private highlightedIndex: number = 0;
@state()
public isOpened = false;
public static styles = [ public static styles = [
cssManager.defaultStyles, cssManager.defaultStyles,
css` css`
* { * {
box-sizing: border-box; box-sizing: border-box;
} }
:host { :host {
position: relative; font-family: Roboto;
display: block; position: relative;
height: 40px; display: block;
color: ${cssManager.bdTheme('#222', '#fff')}; color: ${cssManager.bdTheme('#222', '#fff')};
} margin-bottom: 24px;
}
.maincontainer { .maincontainer {
display: block; display: block;
} }
.label { .label {
font-size: 14px; font-size: 14px;
margin-bottom: 15px; margin-bottom: 8px;
} }
.selectedBox { .selectedBox {
cursor: pointer; user-select: none;
position: relative; position: relative;
max-width: 420px; max-width: 420px;
height: 40px; height: 40px;
line-height: 40px; line-height: 40px;
padding: 0px 8px; padding: 0px 8px;
z-index: 0px; background: ${cssManager.bdTheme('#fafafa', '#222222')};
background: ${cssManager.bdTheme('#ffffff', '#333333')}; box-shadow: ${cssManager.bdTheme('0px 1px 4px rgba(0,0,0,0.3)', 'none')};
box-shadow: ${cssManager.bdTheme('0px 1px 4px rgba(0,0,0,0.3)', 'none')}; border-radius: 3px;
border-radius: 3px; border-top: ${cssManager.bdTheme('1px solid #CCC', '1px solid #ffffff10')};
border-top: 1px solid #CCCCCC00; border-bottom: ${cssManager.bdTheme('1px solid #CCC', '1px solid #222')};
border-bottom: 1px solid #66666600; transition: all 0.2s ease;
} font-size: 16px;
color: ${cssManager.bdTheme('#222', '#ccc')};
}
.selectedBox.show { .selectedBox:hover {
border-top: 1px solid ${cssManager.bdTheme('#ffffff', '#666666')}; filter: ${cssManager.bdTheme('brightness(0.95)', 'brightness(1.1)')};
border-bottom: 1px solid ${cssManager.bdTheme('#fafafa', '#222222')}; }
}
.selectionBox { .accentBottom {
will-change:transform; filter: none !important;
pointer-events: none; }
cursor: pointer;
transition: all 0.2s ease;
opacity: 0;
position: absolute;
background: ${cssManager.bdTheme('#ffffff', '#222222')};
max-width: 420px;
box-shadow: 0px 0px 5px rgba(0,0,0,0.2);
min-height: 40px;
z-index: 100;
border-radius: 3px;
padding: 4px;
transform: scale(0.99,0.99);
}
.selectionBox.show { .accentTop {
pointer-events: all; filter: none !important;
opacity: 1; }
transform: scale(1,1);
}
.option { .selectionBox {
transition: all 0.1s; will-change: transform;
line-height: 40px; pointer-events: none;
padding: 0px 4px; transition: all 0.2s ease;
border-radius: 3px; opacity: 0;
} background: ${cssManager.bdTheme('#ffffff', '#222222')};
max-width: 420px;
box-shadow: 0px 0px 5px rgba(0, 0, 0, 0.2);
min-height: 40px;
border-radius: 8px;
padding: 4px 8px;
position: absolute;
user-select: none;
margin: 3px 0px 0px 0px;
border-top: ${cssManager.bdTheme('1px solid #CCC', '1px solid #ffffff10')};
}
.selectionBox.top {
transform: translate(0px, 4px);
}
.selectionBox.bottom {
transform: translate(0px, -4px);
}
.option:hover { .selectionBox.show {
color: #fff; pointer-events: all;
padding-left: 8px; transform: scale(1, 1) translate(0px, 0px);
background: #0277bd; opacity: 1;
} box-shadow: 0px 0px 8px rgba(0, 0, 0, 0.8);
` }
]
.option {
transition: all 0.1s;
line-height: 32px;
padding: 0px 4px;
border-radius: 3px;
margin: 4px 0px;
}
.option.highlighted {
border-left: 2px solid #0069f2;
padding-left: 6px;
background: #ffffff20;
}
.option:hover {
color: #fff;
padding-left: 8px;
background: #0069f2;
}
.search.top {
padding-top: 4px;
}
.search.bottom {
padding-bottom: 4px;
}
.search input {
display: block;
background: none;
border: none;
height: 24px;
color: inherit;
text-align: left;
font-size: 12px;
font-weight: 600;
width: 100%;
margin: auto;
}
.search.top input {
border-bottom: 1px dotted #333;
}
.search.bottom input {
border-top: 1px dotted #333;
}
.search input:focus {
outline: none;
}
`,
];
public render(): TemplateResult { public render(): TemplateResult {
return html` return html`
<div class="maincontainer"> <div class="maincontainer" @keydown="${this.isOpened ? this.handleKeyDown : undefined}">
<div class="selectedBox show" @click="${event => {this.openSelectionBox();}}"> ${this.label ? html`<div class="label">${this.label}</div>` : html``}
${this.selectedOption?.option}
</div>
<div class="selectionBox"> <div class="selectionBox">
${this.options.map(option => { ${this.enableSearch && !this.opensToTop
? html`
<div class="search top">
<input type="text" placeholder="Search" @input="${this.handleSearch}" />
</div>
`
: null}
${this.filteredOptions.map((option, index) => {
const isHighlighted = this.highlightedIndex === index;
return html` return html`
<div class="option" @click=${() => {this.updateSelection(option);}}>${option.option}</div> <div
` class="option ${isHighlighted ? 'highlighted' : ''}"
@click=${() => {
this.updateSelection(option);
}}
>
${option.option}
</div>
`;
})} })}
${this.enableSearch && this.opensToTop
? html`
<div class="search bottom">
<input type="text" placeholder="Search" @input="${this.handleSearch}" />
</div>
`
: null}
</div>
<div
class="selectedBox"
@click="${(event) => {
if (!this.isElevated) {
this.toggleSelectionBox();
} else {
this.updateSelection(this.selectedOption);
}
}}"
>
${this.selectedOption?.option || 'Select...'}
</div> </div>
</div> </div>
`; `;
} }
firstUpdated() { firstUpdated() {
this.selectedOption = this.options[0] || null; this.selectedOption = this.selectedOption || null;
this.filteredOptions = this.options; // Initialize filteredOptions
} }
public async updateSelection(selectedOption) { public async updateSelection(selectedOption) {
this.selectedOption = selectedOption; this.selectedOption = selectedOption;
this.dispatchEvent(new CustomEvent('selectedOption', { this.dispatchEvent(
detail: selectedOption, new CustomEvent('selectedOption', {
bubbles: true detail: selectedOption,
})); bubbles: true,
this.openSelectionBox(); })
);
if (this.isElevated) {
this.toggleSelectionBox();
}
this.changeSubject.next(this); this.changeSubject.next(this);
} }
public openSelectionBox() { private isElevated: boolean = false;
this.shadowRoot.querySelector('.selectedBox').classList.toggle('show'); private windowOverlay: DeesWindowLayer;
this.shadowRoot.querySelector('.selectionBox').classList.toggle('show'); public async toggleSelectionBox() {
this.isOpened = !this.isOpened;
const domtoolsInstance = await this.domtoolsPromise;
const selectedBox: HTMLElement = this.shadowRoot.querySelector('.selectedBox');
const selectionBox: HTMLElement = this.shadowRoot.querySelector('.selectionBox');
if (!this.isElevated) {
this.windowOverlay = await DeesWindowLayer.createAndShow({
blur: false,
});
const elevatedDropdown = new DeesInputDropdown();
elevatedDropdown.isElevated = true;
elevatedDropdown.label = this.label;
elevatedDropdown.enableSearch = this.enableSearch;
elevatedDropdown.required = this.required;
elevatedDropdown.disabled = this.disabled;
elevatedDropdown.style.position = 'fixed';
elevatedDropdown.style.top = this.getBoundingClientRect().top + 'px';
elevatedDropdown.style.left = this.getBoundingClientRect().left + 'px';
elevatedDropdown.style.width = this.clientWidth + 'px';
elevatedDropdown.options = this.options;
elevatedDropdown.selectedOption = this.selectedOption;
elevatedDropdown.highlightedIndex = elevatedDropdown.selectedOption ? elevatedDropdown.options.indexOf(
elevatedDropdown.options.find((option) => option.key === this.selectedOption.key)
) : -1;
console.log(elevatedDropdown.options);
console.log(elevatedDropdown.selectedOption);
console.log(elevatedDropdown.highlightedIndex);
this.windowOverlay.appendChild(elevatedDropdown);
await domtoolsInstance.convenience.smartdelay.delayFor(0);
elevatedDropdown.toggleSelectionBox();
const destroyOverlay = async () => {
(elevatedDropdown.shadowRoot.querySelector('.selectionBox') as HTMLElement).style.opacity =
'0';
elevatedDropdown.removeEventListener('selectedOption', handleSelection);
this.windowOverlay.removeEventListener('clicked', destroyOverlay);
this.windowOverlay.destroy();
};
const handleSelection = async (event) => {
await this.updateSelection(elevatedDropdown.selectedOption);
destroyOverlay();
};
elevatedDropdown.addEventListener('selectedOption', handleSelection);
this.windowOverlay.addEventListener('clicked', destroyOverlay);
} else {
if (!selectionBox.classList.contains('show')) {
selectionBox.style.width = selectedBox.clientWidth + 'px';
const spaceData = selectedBox.getBoundingClientRect();
if (300 > window.innerHeight - spaceData.bottom) {
this.opensToTop = true;
selectedBox.classList.add('accentTop');
selectionBox.classList.add('top');
selectionBox.style.bottom = selectedBox.clientHeight + 2 + 'px';
} else {
selectedBox.classList.add('accentBottom');
selectionBox.classList.add('bottom');
this.opensToTop = false;
const labelOffset = this.label ? 24 : 0;
selectionBox.style.top = selectedBox.clientHeight + labelOffset + 'px';
}
await domtoolsInstance.convenience.smartdelay.delayFor(0);
const searchInput = selectionBox.querySelector('input');
searchInput?.focus();
selectionBox.classList.add('show');
} else {
selectedBox.style.pointerEvents = 'none';
selectionBox.classList.remove('show');
// selectedBox.style.opacity = '0';
}
}
} }
public closeSelectionBox() { private handleSearch(event: Event): void {
const searchTerm = (event.target as HTMLInputElement).value.toLowerCase();
this.filteredOptions = this.options.filter((option) =>
option.option.toLowerCase().includes(searchTerm)
);
this.highlightedIndex = 0; // Reset highlighted index
}
private handleKeyDown(event: KeyboardEvent): void {
if (!this.isOpened) {
console.log('discarded key event. Check why this function is called.');
return;
}
const key = event.key;
const maxIndex = this.filteredOptions.length - 1;
if (key === 'ArrowDown') {
this.highlightedIndex = this.highlightedIndex + 1 > maxIndex ? 0 : this.highlightedIndex + 1;
event.preventDefault();
} else if (key === 'ArrowUp') {
this.highlightedIndex = this.highlightedIndex - 1 < 0 ? maxIndex : this.highlightedIndex - 1;
event.preventDefault();
} else if (key === 'Enter') {
this.updateSelection(this.filteredOptions[this.highlightedIndex]);
event.preventDefault();
}
} }
} }

View File

@ -1,3 +1,8 @@
import * as colors from './00colors.js';
import * as plugins from './00plugins.js';
import { DeesContextmenu } from './dees-contextmenu.js';
import { import {
customElement, customElement,
DeesElement, DeesElement,
@ -19,7 +24,8 @@ declare global {
@customElement('dees-input-fileupload') @customElement('dees-input-fileupload')
export class DeesInputFileupload extends DeesElement { export class DeesInputFileupload extends DeesElement {
public static demo = () => html`<dees-input-fileupload .label=${'Attachments'}></dees-input-fileupload>`; public static demo = () =>
html`<dees-input-fileupload .label=${'Attachments'}></dees-input-fileupload>`;
// INSTANCE // INSTANCE
public changeSubject = new domtools.plugins.smartrx.rxjs.Subject(); public changeSubject = new domtools.plugins.smartrx.rxjs.Subject();
@ -70,6 +76,7 @@ export class DeesInputFileupload extends DeesElement {
display: grid; display: grid;
margin: 10px 0px; margin: 10px 0px;
margin-bottom: 24px; margin-bottom: 24px;
color: ${cssManager.bdTheme('#333', '#ccc')};
} }
.hidden { .hidden {
@ -77,31 +84,15 @@ export class DeesInputFileupload extends DeesElement {
} }
.maincontainer { .maincontainer {
color: ${cssManager.bdTheme('#333', '#ccc')};
}
.label {
font-size: 14px;
margin-bottom: 5px;
}
.uploadButton {
position: relative; position: relative;
cursor: pointer;
padding: 8px;
max-width: 600px;
background: ${cssManager.bdTheme('#fafafa', '#333333')};
border-radius: 3px; border-radius: 3px;
text-align: center; padding: 8px;
background: ${cssManager.bdTheme('#fafafa', '#222222')};
color: ${cssManager.bdTheme('#333', '#ccc')};
border-top: 1px solid #ffffff10;
} }
.uploadButton:hover { .maincontainer::after {
color: #fff;
background: rgb(3, 155, 229);
}
.uploadButton::after {
top: 2px; top: 2px;
right: 2px; right: 2px;
left: 2px; left: 2px;
@ -112,28 +103,71 @@ export class DeesInputFileupload extends DeesElement {
display: block; display: block;
border: 2px dashed rgba(255, 255, 255, 0); border: 2px dashed rgba(255, 255, 255, 0);
transition: all 0.2s; transition: all 0.2s;
pointer-events: none;
background: #00000000;
} }
.uploadButton.dragOver::after { .maincontainer.dragOver::after {
transform: scale3d(1, 1, 1); transform: scale3d(1, 1, 1);
border: 2px dashed rgba(255, 255, 255, 0.3); border: 2px dashed rgba(255, 255, 255, 0.3);
background: #00000080;
}
.label {
font-size: 14px;
margin-bottom: 8px;
}
.uploadButton {
position: relative;
padding: 8px;
max-width: 600px;
background: ${cssManager.bdTheme('#fafafa', '#333333')};
border-radius: 3px;
text-align: center;
font-size: 14px;
cursor: default;
}
.uploadButton:hover {
color: #fff;
background: ${unsafeCSS(colors.dark.blue)};
} }
.uploadCandidate { .uploadCandidate {
display: grid;
grid-template-columns: 48px auto;
background: #333;
padding: 8px 8px 8px 0px;
margin-bottom: 8px;
text-align: left; text-align: left;
border-bottom: 1px dashed #444; border-radius: 3px;
color: ${cssManager.bdTheme('#666', '#ccc')}; color: ${cssManager.bdTheme('#666', '#ccc')};
padding: 8px; font-family: 'Geist Sans', sans-serif;
font-family: 'Roboto', 'Inter', sans-serif; cursor: default;
} transition: all 0.2s;
border-top: 1px solid #ffffff10;
.uploadButton:hover .uploadCandidate {
color: ${cssManager.bdTheme('#fff', '#fff')};
border-bottom: 1px dashed #fff;
} }
.uploadCandidate:last-child { .uploadCandidate:last-child {
margin-bottom: 8px; margin-bottom: 8px;
} }
.uploadCandidate .icon {
display: flex;
align-items: center;
justify-content: center;
font-size: 16px;
}
.uploadCandidate:hover {
background: #393939;
}
.uploadCandidate .description {
font-size: 14px;
border-left: 1px solid #ffffff10;
padding-left: 8px;
}
`, `,
]; ];
@ -142,10 +176,32 @@ export class DeesInputFileupload extends DeesElement {
<div class="hidden"> <div class="hidden">
<input type="file"></div> <input type="file"></div>
</div> </div>
<div class="maincontainer"> ${this.label ? html`<div class="label">${this.label}</div>` : null}
${this.label ? html`<div class="label">${this.label}</div>` : null} <div class="maincontainer ${this.state === 'dragOver' ? 'dragOver' : ''}">
${this.value.map((fileArg) => html` <div class="uploadCandidate">${fileArg.name} | ${fileArg.size}</div> `)} ${this.value.map(
<div class="uploadButton ${this.state === 'dragOver' ? 'dragOver' : ''}" @click=${this.openFileSelector}> (fileArg) => html`
<div class="uploadCandidate" @contextmenu=${eventArg => {
DeesContextmenu.openContextMenuWithOptions(eventArg, [{
iconName: 'trash',
name: 'Remove',
action: async () => {
this.value.splice(this.value.indexOf(fileArg), 1);
this.requestUpdate();
}
}]);
}}>
<div class="icon">
<dees-icon .iconFA=${'paperclip'}></dees-icon>
</div>
<div class="description">
<span style="font-weight: 600">${fileArg.name}</span><br />
<span style="font-weight: 400">${fileArg.size}</span>
</div>
</div> `
)}
<div class="uploadButton" @click=${
this.openFileSelector
}>
${this.buttonText} ${this.buttonText}
</div> </div>
</div> </div>
@ -158,7 +214,6 @@ export class DeesInputFileupload extends DeesElement {
this.state = 'idle'; this.state = 'idle';
this.buttonText = 'Upload more files...'; this.buttonText = 'Upload more files...';
} }
public async updateValue(eventArg: Event) { public async updateValue(eventArg: Event) {
const target: any = eventArg.target; const target: any = eventArg.target;
@ -179,9 +234,8 @@ export class DeesInputFileupload extends DeesElement {
target.value = ''; target.value = '';
}); });
// lets handle drag and drop // lets handle drag and drop
const dropArea = this.shadowRoot.querySelector('.uploadButton'); const dropArea = this.shadowRoot.querySelector('.maincontainer');
const handlerFunction = (eventArg: DragEvent) => { const handlerFunction = (eventArg: DragEvent) => {
eventArg.preventDefault(); eventArg.preventDefault();
switch (eventArg.type) { switch (eventArg.type) {

View File

@ -0,0 +1,14 @@
import { html } from '@design.estate/dees-element';
export const demoFunc = () => html`
<dees-input-multitoggle
.options=${['option 1', 'option 2', 'a longer option with multiple words']}
.selectedOption=${'option 2'}
></dees-input-multitoggle>
<dees-input-multitoggle
.type=${'boolean'}
.booleanTrueName=${'enabled'}
.booleanFalseName=${'disabled'}
.selectedOption=${'true'}
></dees-input-multitoggle>
`;

View File

@ -0,0 +1,153 @@
import {
customElement,
DeesElement,
type TemplateResult,
state,
html,
domtools,
property,
css,
cssManager,
} from '@design.estate/dees-element';
const { demoFunc } = await import('./dees-input-multitoggle.demo.js');
@customElement('dees-input-multitoggle')
export class DeesInputMultitoggle extends DeesElement {
public static demo = demoFunc;
@property({
type: String,
})
public label: string;
@property({
type: String,
})
public description: string;
@property()
type: 'boolean' | 'multi' | 'single' = 'multi';
@property()
booleanTrueName: string = 'true';
@property()
booleanFalseName: string = 'false';
@property({
type: Array,
})
options: string[] = [];
@property()
selectedOption: string = '';
@property()
boolValue: boolean = false;
public static styles = [
cssManager.defaultStyles,
css`
:host {
display: block;
color: ${cssManager.bdTheme('#333', '#ccc')};
user-select: none;
margin: 8px 0px 24px 0px;
}
.label {
font-size: 14px;
margin-bottom: 8px;
}
.selections {
position: relative;
display: flex;
flex-direction: row;
flex-wrap: nowrap;
background: ${cssManager.bdTheme('#fff', '#222')};
width: min-content;
border-radius: 20px;
height: 32px;
border-top: 1px solid #ffffff10;
}
.option {
color: #ccc;
position: relative;
padding: 0px 16px;
line-height: 32px;
cursor: default;
width: min-content; /* Make the width as per the content */
white-space: nowrap; /* Prevent text wrapping */
transition: all 0.1s;
font-size: 14px;
transform: translateY(-1px);
}
.option:hover {
color: #fff;
}
.option.selected {
color: #fff;
}
.indicator {
opacity: 0;
position: absolute;
height: 24px;
left: 4px;
top: 3px;
border-radius: 16px;
background: #0050b9;
min-width: 36px;
}
`,
];
public render(): TemplateResult {
return html`
<dees-label .label=${this.label} .description=${this.description}></dees-label>
<div class="mainbox">
<div class="selections">
<div class="indicator"></div>
${this.options.map(
(option) =>
html`<div class="option ${option === this.selectedOption ? 'selected': ''}" @click=${() => this.handleSelection(option)}>
${option}
</div> `
)}
</div>
</div>
`;
}
public async firstUpdated() {
if (this.type === 'boolean') {
this.options = [this.booleanTrueName || 'true', this.booleanFalseName || 'false'];
}
this.setIndicator();
}
public async handleSelection(optionArg: string) {
this.selectedOption = optionArg;
this.setIndicator();
}
public async setIndicator() {
const indicator: HTMLDivElement = this.shadowRoot.querySelector('.indicator');
const option: HTMLDivElement = this.shadowRoot.querySelector(
`.option:nth-child(${this.options.indexOf(this.selectedOption) + 2})`
);
if (indicator && option) {
indicator.style.width = `${option.clientWidth - 8}px`;
indicator.style.left = `${option.offsetLeft + 4}px`;
indicator.style.opacity = '1';
}
setTimeout(() => {
indicator.style.transition = 'all 0.1s';
}, 100);
}
}

View File

@ -85,7 +85,6 @@ export class DeesInputQuantitySelector extends DeesElement {
} }
.selector:hover { .selector:hover {
cursor: pointer;
} }
.quantity { .quantity {

View File

@ -51,7 +51,6 @@ export class DeesInputRadio extends DeesElement {
display: block; display: block;
position: relative; position: relative;
margin: 20px 0px; margin: 20px 0px;
cursor: pointer;
} }
.maincontainer { .maincontainer {
@ -91,8 +90,8 @@ export class DeesInputRadio extends DeesElement {
} }
.checkbox.selected { .checkbox.selected {
background: #039BE5; background: #0050b9;
border: 1px solid #039BE5; border: 1px solid #0050b9;
} }
.maincontainer:hover .checkbox.selected { .maincontainer:hover .checkbox.selected {

View File

@ -1,3 +1,5 @@
import * as colors from './00colors.js';
import { import {
customElement, customElement,
DeesElement, DeesElement,
@ -31,6 +33,11 @@ export class DeesInputText extends DeesElement {
}) })
public label: string; public label: string;
@property({
type: String,
})
public description: string;
@property({ @property({
type: String, type: String,
reflect: true, reflect: true,
@ -98,16 +105,11 @@ export class DeesInputText extends DeesElement {
color: ${cssManager.bdTheme('#333', '#ccc')}; color: ${cssManager.bdTheme('#333', '#ccc')};
} }
.label {
font-size: 14px;
margin-bottom: 4px;
}
input { input {
margin-top: 5px; margin-top: 0px;
background: ${cssManager.bdTheme('#fafafa', '#222')}; background: ${cssManager.bdTheme('#fafafa', '#222')};
border-top: ${cssManager.bdTheme('1px solid #CCC', '1px solid #444')}; border-top: ${cssManager.bdTheme('1px solid #CCC', '1px solid #ffffff10')};
border-bottom: ${cssManager.bdTheme('1px solid #CCC', '1px solid #333')}; border-bottom: ${cssManager.bdTheme('1px solid #CCC', '1px solid #222')};
border-right: ${cssManager.bdTheme('1px solid #CCC', 'none')}; border-right: ${cssManager.bdTheme('1px solid #CCC', 'none')};
border-left: ${cssManager.bdTheme('1px solid #CCC', 'none')}; border-left: ${cssManager.bdTheme('1px solid #CCC', 'none')};
padding-left: 10px; padding-left: 10px;
@ -120,7 +122,7 @@ export class DeesInputText extends DeesElement {
font-size: 16px; font-size: 16px;
position: relative; position: relative;
z-index: 2; z-index: 2;
// see template for more cursor: default;
} }
input:disabled { input:disabled {
@ -132,7 +134,12 @@ export class DeesInputText extends DeesElement {
input:focus { input:focus {
outline: none; outline: none;
border-bottom: 1px solid #e4002b; border-bottom: 1px solid ${cssManager.bdTheme( colors.bright.blueActive, colors.dark.blueActive)};
cursor: text;
}
input:hover {
filter: ${cssManager.bdTheme('brightness(0.95)', 'brightness(1.1)')};
} }
.showPassword { .showPassword {
@ -143,10 +150,10 @@ export class DeesInputText extends DeesElement {
border-radius: 7px; border-radius: 7px;
padding: 4px 0px; padding: 4px 0px;
width: 40px; width: 40px;
z-index: 3;
} }
.showPassword:hover { .showPassword:hover {
cursor: pointer;
background: ${cssManager.bdTheme('#00000010', '#ffffff10')}; background: ${cssManager.bdTheme('#00000010', '#ffffff10')};
} }
@ -169,7 +176,7 @@ export class DeesInputText extends DeesElement {
return html` return html`
<style> <style>
input { input {
font-family: ${this.isPasswordBool ? 'monospace' : 'Inter'}; font-family: ${this.isPasswordBool ? 'monospace' : 'Geist Sans'};
letter-spacing: ${this.isPasswordBool ? '1px' : 'normal'}; letter-spacing: ${this.isPasswordBool ? '1px' : 'normal'};
color: ${this.goBright ? '#333' : '#ccc'}; color: ${this.goBright ? '#333' : '#ccc'};
} }
@ -187,7 +194,7 @@ export class DeesInputText extends DeesElement {
`} `}
</style> </style>
<div class="maincontainer"> <div class="maincontainer">
${this.label ? html`<div class="label">${this.label}</div>` : html``} <dees-label .label=${this.label} .description=${this.description}></dees-label>
<input <input
type="${this.isPasswordBool && !this.showPasswordBool ? 'password' : 'text'}" type="${this.isPasswordBool && !this.showPasswordBool ? 'password' : 'text'}"
.value=${this.value} .value=${this.value}

View File

@ -0,0 +1,15 @@
import { html } from '@design.estate/dees-element';
export const demoFunc = () => html`
<style>
.demoContainer {
max-width: 600px;
margin: auto;
padding: 40px;
background: #000;
}
</style>
<div class="demoContainer">
<dees-input-typelist></dees-input-typelist>
</div>
`;

View File

@ -0,0 +1,98 @@
import {
customElement,
DeesElement,
type TemplateResult,
state,
html,
domtools,
property,
css,
cssManager,
} from '@design.estate/dees-element';
const { demoFunc } = await import('./dees-input-typelist.demo.js');
@customElement('dees-input-typelist')
export class DeesInputTypelist extends DeesElement {
public static demo = demoFunc;
// INSTANCE
@property({
type: String,
})
public label: string;
constructor() {
super();
}
public static styles = [
cssManager.defaultStyles,
css`
:host {
display: block;
color: ${cssManager.bdTheme('#333', '#fff')};
margin: 8px 0px 24px 0px;
}
.label {
font-size: 14px;
margin-bottom: 8px;
}
.mainbox {
border-radius: 3px;
background: #222;
overflow: hidden;
border-top: ${cssManager.bdTheme('1px solid #CCC', '1px solid #444')};
border-bottom: ${cssManager.bdTheme('1px solid #CCC', '1px solid #333')};
border-right: ${cssManager.bdTheme('1px solid #CCC', 'none')};
border-left: ${cssManager.bdTheme('1px solid #CCC', 'none')};
}
.tags {
padding: 16px;
cursor: default;
}
.notags {
text-align: center;
opacity: 0.5;
font-size: 12px;
}
input {
display: block;
box-sizing: border-box;
background: #181818;
width: 100%;
outline: none;
border: none;
color: inherit;
padding: 0px 16px;
overflow: hidden;
line-height: 32px;
height: 0px;
transition: height 0.2s;
}
input:focus {
height: 32px;
}
`,
];
public render(): TemplateResult {
return html`
<div class="label">${this.label}</div>
<div class="mainbox">
<div class="tags" @click=${() => {
this.shadowRoot.querySelector('input').focus();
}}>
<div class="notags">No tags yet</div>
</div>
<input type="text" placeholder="Type, press Enter to add it..." />
</div>
`;
}
}

View File

@ -0,0 +1,7 @@
import { html, cssManager } from '@design.estate/dees-element';
export const demoFunc = () => {
return html`
<dees-label .label=${'a label'}></dees-label>
`;
}

View File

@ -0,0 +1,70 @@
import * as plugins from './00plugins.js';
import * as colors from './00colors.js';
import {
customElement,
html,
css,
cssManager,
DeesElement,
property,
unsafeCSS,
query,
} from '@design.estate/dees-element';
import { demoFunc } from './dees-label.demo.js';
@customElement('dees-label')
export class DeesLabel extends DeesElement {
public static demo = demoFunc;
// INSTANCE
@property({
type: String,
reflect: true,
})
public label = '';
@property({
type: String,
reflect: true,
})
public description: string;
public static styles = [
cssManager.defaultStyles,
css`
.label {
color: ${cssManager.bdTheme('#333', '#ccc')};
font-size: 14px;
margin-bottom: 8px;
cursor: default;
user-select: none;
}
dees-icon {
display: inline-block;
font-size: 14px;
transform: translateY(1.5px);
}
`,
];
public render() {
return html`
${this.label
? html`
<div class="label">
${this.label}
${this.description
? html`
<dees-icon .iconFA=${'circleInfo'}></dees-icon>
<dees-speechbubble .text=${this.description}></dees-speechbubble>
`
: html``}
</div>
`
: html``}
`;
}
}

View File

@ -1,4 +1,4 @@
import * as plugins from './plugins.js'; import * as plugins from './00plugins.js';
import { import {
cssManager, cssManager,
css, css,
@ -105,7 +105,6 @@ export class DeesMobilenavigation extends DeesElement {
padding: 8px; padding: 8px;
margin-left: -8px; margin-left: -8px;
margin-right: -8px; margin-right: -8px;
cursor: pointer;
border-radius: 3px; border-radius: 3px;
} }
.menuItem:hover { .menuItem:hover {
@ -116,7 +115,7 @@ export class DeesMobilenavigation extends DeesElement {
text-align: left; text-align: left;
font-size: 24px; font-size: 24px;
padding: 8px 0px; padding: 8px 0px;
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
font-weight: 300; font-weight: 300;
border-bottom: 1px dashed #444; border-bottom: 1px dashed #444;
margin-top: 16px; margin-top: 16px;

View File

@ -1,4 +1,6 @@
import * as plugins from './plugins.js'; import * as colors from './00colors.js';
import * as plugins from './00plugins.js';
import { demoFunc } from './dees-modal.demo.js'; import { demoFunc } from './dees-modal.demo.js';
import { import {
customElement, customElement,
@ -69,7 +71,7 @@ export class DeesModal extends DeesElement {
cssManager.defaultStyles, cssManager.defaultStyles,
css` css`
:host { :host {
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
color: ${cssManager.bdTheme('#333', '#fff')}; color: ${cssManager.bdTheme('#333', '#fff')};
will-change: transform; will-change: transform;
} }
@ -111,7 +113,7 @@ export class DeesModal extends DeesElement {
.modal .heading { .modal .heading {
height: 32px; height: 32px;
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
line-height: 32px; line-height: 32px;
text-align: center; text-align: center;
font-weight: 600; font-weight: 600;
@ -123,20 +125,35 @@ export class DeesModal extends DeesElement {
padding: 16px; padding: 16px;
} }
.modal .bottomButtons { .modal .bottomButtons {
display: grid; display: flex;
flex-direction: row;
border-top: 1px solid #222; border-top: 1px solid #222;
justify-content: flex-end;
} }
.modal .bottomButtons .bottomButton { .modal .bottomButtons .bottomButton {
height: 40px; margin: 8px 0px;
line-height: 40px; padding: 8px 12px;
border-radius: 4px;
line-height: 16px;
text-align: center; text-align: center;
font-size: 14px; font-size: 14px;
border-right: 1px solid #222; cursor: default;
cursor: pointer; user-select: none;
} }
.modal .bottomButtons .bottomButton:first-child {
margin-left: 8px;
}
.modal .bottomButtons .bottomButton:last-child {
margin-right: 8px;
}
.modal .bottomButtons .bottomButton:hover { .modal .bottomButtons .bottomButton:hover {
background: #222; background: ${cssManager.bdTheme(colors.bright.blue, colors.dark.blue)};
}
.modal .bottomButtons .bottomButton:active {
background: ${cssManager.bdTheme(colors.bright.blueActive, colors.dark.blueActive)};
} }
.modal .bottomButtons .bottomButton:last-child { .modal .bottomButtons .bottomButton:last-child {
border-right: none; border-right: none;

View File

@ -32,7 +32,7 @@ export class DeesPdf extends DeesElement {
return html` return html`
<style> <style>
:host { :host {
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
display: block; display: block;
box-sizing: border-box; box-sizing: border-box;
max-width: 800px; max-width: 800px;
@ -57,18 +57,9 @@ export class DeesPdf extends DeesElement {
if (!DeesPdf.pdfJsReady) { if (!DeesPdf.pdfJsReady) {
const pdfJsReadyDeferred = domtools.plugins.smartpromise.defer(); const pdfJsReadyDeferred = domtools.plugins.smartpromise.defer();
DeesPdf.pdfJsReady = pdfJsReadyDeferred.promise; DeesPdf.pdfJsReady = pdfJsReadyDeferred.promise;
const loadDeferred = domtools.plugins.smartpromise.defer(); // @ts-ignore
const script = document.createElement('script'); DeesPdf.pdfjsLib = await import('https://cdn.jsdelivr.net/npm/pdfjs-dist@4.0.379/+esm');
script.addEventListener('load', () => { DeesPdf.pdfjsLib.GlobalWorkerOptions.workerSrc = 'https://cdn.jsdelivr.net/npm/pdfjs-dist@4.0.379/build/pdf.worker.mjs';
console.log('pdf.js loaded!');
loadDeferred.resolve();
});
script.src = 'https:////mozilla.github.io/pdf.js/build/pdf.js';
document.getElementsByTagName('head')[0].appendChild(script);
// The workerSrc property shall be specified.
await loadDeferred.promise;
DeesPdf.pdfjsLib = window['pdfjs-dist/build/pdf'];
DeesPdf.pdfjsLib.GlobalWorkerOptions.workerSrc = '//mozilla.github.io/pdf.js/build/pdf.worker.js';
pdfJsReadyDeferred.resolve(); pdfJsReadyDeferred.resolve();
} }
await DeesPdf.pdfJsReady; await DeesPdf.pdfJsReady;

View File

@ -0,0 +1,11 @@
import { html } from '@design.estate/dees-element';
import { DeesProgressbar } from './dees-progressbar.js';
export const demoFunc = () => {
return html`
<dees-progressbar
.percentage=${50}
></dees-progressbar>
`;
}

View File

@ -0,0 +1,95 @@
import * as plugins from './00plugins.js';
import * as colors from './00colors.js';
import { demoFunc } from './dees-progressbar.demo.js';
import {
customElement,
html,
DeesElement,
property,
type TemplateResult,
cssManager,
css,
type CSSResult,
unsafeCSS,
unsafeHTML,
state,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
@customElement('dees-progressbar')
export class DeesProgressbar extends DeesElement {
// STATIC
public static demo = demoFunc;
// INSTANCE
@property({
type: Number,
})
public percentage = 0;
public static styles = [
cssManager.defaultStyles,
css`
:host {
color: ${cssManager.bdTheme(colors.bright.text, colors.dark.text)};
}
.progressBarContainer {
padding: 8px;
min-width: 200px;
}
.progressBar {
background: ${cssManager.bdTheme('#eeeeeb', '#444')};
height: 8px;
width: 100%;
border-radius: 4px;
border-top: 0.5px solid ${cssManager.bdTheme('none', '#555')};
}
.progressBarFill {
background: ${cssManager.bdTheme(colors.dark.blueActive, colors.bright.blueActive)};
height: 8px;
margin-top: -0.5px;
transition: 0.2s width;
border-radius: 4px;
width: 0px;
border-top: 0.5 solid ${cssManager.bdTheme('none', '#398fff')};
}
.progressText {
padding: 8px;
text-align: center;
}
`
];
public render() {
return html`
<div class="progressBarContainer">
<div class="progressBar">
<div class="progressBarFill"></div>
<div class="progressText">
${this.percentage}%
<div>
</div>
</div>
`
}
firstUpdated (_changedProperties: Map<string | number | symbol, unknown>): void {
super.firstUpdated(_changedProperties);
this.updateComplete.then(() => {
this.updatePercentage();
});
}
public async updatePercentage() {
const progressBarFill = this.shadowRoot.querySelector('.progressBarFill') as HTMLElement;
progressBarFill.style.width = `${this.percentage}%`;
}
updated(){
this.updatePercentage();
}
}

View File

@ -1,5 +1,21 @@
import { html } from '@design.estate/dees-element'; import { html } from '@design.estate/dees-element';
import type { IView } from './dees-simple-appdash.js';
export const demoFunc = () => html` export const demoFunc = () => html`
<dees-simple-appdash>Hello there</dees-simple-appdash> <dees-simple-appdash
.viewTabs=${[
{
name: 'View 1',
element: null,
},
{
name: 'View 2',
element: null,
},
{
name: 'View 3',
element: null,
}
] as IView[]}
>Hello there</dees-simple-appdash>
`; `;

View File

@ -1,4 +1,6 @@
import { demoFunc } from './dees-simple-appdash.demo.js'; import { demoFunc } from './dees-simple-appdash.demo.js';
import * as colors from './00colors.js';
import { import {
customElement, customElement,
html, html,
@ -10,7 +12,9 @@ import {
unsafeCSS, unsafeCSS,
type CSSResult, type CSSResult,
state, state,
domtools,
} from '@design.estate/dees-element'; } from '@design.estate/dees-element';
import { DeesTerminal } from './dees-terminal.js';
declare global { declare global {
interface HTMLElementTagNameMap { interface HTMLElementTagNameMap {
@ -18,6 +22,11 @@ declare global {
} }
} }
export interface IView {
name: string;
element: DeesElement['constructor']['prototype'];
}
@customElement('dees-simple-appdash') @customElement('dees-simple-appdash')
export class DeesSimpleAppDash extends DeesElement { export class DeesSimpleAppDash extends DeesElement {
// STATIC // STATIC
@ -27,42 +36,152 @@ export class DeesSimpleAppDash extends DeesElement {
@property() @property()
public name = 'Dees Simple Login'; public name = 'Dees Simple Login';
@property()
public viewTabs: IView[] = [];
public static styles = [ public static styles = [
cssManager.defaultStyles, cssManager.defaultStyles,
css` css`
:host { :host {
color: ${cssManager.bdTheme('#333', '#fff')}; color: ${cssManager.bdTheme('#333', '#ccc')};
user-select: none; user-select: none;
display: block;
position: relative;
height: 100%;
} }
.maincontainer {
position: absolute;
width: 100%;
height: 100%;
top: 0px;
left: 0px;
overflow: hidden;
}
.appbar { .appbar {
position: absolute; position: fixed;
top: 0; top: 0;
height: 40px; height: calc(100% - 24px);
width: 100%; width: 200px;
background: ${cssManager.bdTheme('#eeeeeb', '#000')}; background: ${cssManager.bdTheme('#eeeeeb', '#000')};
border-bottom: 1px solid ${cssManager.bdTheme('#ccc', '#333')}; border-right: 1px solid ${cssManager.bdTheme('#ccc', '#ffffff20')};
font-size: 14px; font-size: 14px;
line-height: 40px; line-height: 32px;
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
padding: 0px 16px; padding: 0px 16px;
z-index: 2;
box-shadow: 0px 4px 10px 0px rgba(0, 0, 0, 0.8);
display: grid;
grid-template-rows: min-content auto min-content;
} }
.appbar .viewTabs {
margin-left: -8px;
margin-right: -8px;
display: flex;
flex-direction: column;
align-items: top;
}
.viewTab {
padding: 0px 8px;
}
.viewTab:hover {
background: ${cssManager.bdTheme('#ccc', '#ffffff10')};
color: ${cssManager.bdTheme('#000', '#fff')};
}
.viewTab:active {
background: ${cssManager.bdTheme('#aaa', '#ffffff20')};
color: ${cssManager.bdTheme('#000', '#fff')};
}
.appName {
white-space: nowrap;
color: ${cssManager.bdTheme('#666', '#999')};
}
.appActions {
display: flex;
}
.appActions .action {
}
.appActions .action:hover {
color: ${cssManager.bdTheme('#000', '#fff')};
}
.appcontent { .appcontent {
position: absolute; z-index: 1;
top: 40px; position: fixed;
bottom: 0; top: 0px;
width: 100%; right: 0px;
height: calc(100vh - 24px);
bottom: 24px;
width: calc(100vw - 200px);
overflow: auto;
background: ${cssManager.bdTheme('#eeeeeb', '#000')}; background: ${cssManager.bdTheme('#eeeeeb', '#000')};
overscroll-behavior: contain;
}
.controlbar {
color: #fff;
position: absolute;
bottom: 0px;
left: 0px;
width: 100%;
height: 24px;
background: ${cssManager.bdTheme(colors.bright.blueMuted, colors.dark.blueMuted)};
z-index: 2;
display: flex;
justify-content: flex-end;
align-items: center;
flex-direction: row;
box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.8);
}
.control {
width: min-content;
margin-right: 16px;
font-size: 12px;
white-space: nowrap;
} }
`, `,
]; ];
public render(): TemplateResult { public render(): TemplateResult {
return html` return html`
<div class="appbar"> <div class="maincontainer">
configvault v1.2.3 <div class="appbar">
</div> <div class="appName">${this.name}</div>
<div class="appcontent"> <div class="viewTabs">
<slot></slot> ${this.viewTabs.map(
(view) => html`
<div class="viewTab" @click=${() => {
this.loadView(view);
}}>${view.name}</div>
`
)}
</div>
<div class="appActions">
<div class="action" @click=${() => {
this.dispatchEvent(new CustomEvent('logout'));
}}>Logout</div>
</div>
</div>
<div class="appcontent">
</div>
<div class="controlbar">
<div class="control">
<dees-icon .iconFA=${'networkWired'}></dees-icon>
</div>
<div class="control" @click=${this.launchTerminal}>
<dees-icon .iconFA=${'terminal'}></dees-icon>
</div>
</div>
</div> </div>
`; `;
} }
@ -70,5 +189,35 @@ export class DeesSimpleAppDash extends DeesElement {
public async firstUpdated(_changedProperties): Promise<void> { public async firstUpdated(_changedProperties): Promise<void> {
const domtools = await this.domtoolsPromise; const domtools = await this.domtoolsPromise;
super.firstUpdated(_changedProperties); super.firstUpdated(_changedProperties);
await this.loadView(this.viewTabs[0]);
}
public async launchTerminal() {
const maincontainer = this.shadowRoot.querySelector('.maincontainer');
const terminal = new DeesTerminal();
maincontainer.appendChild(terminal);
terminal.style.position = 'absolute';
terminal.style.zIndex = '1';
terminal.style.top = '0px';
terminal.style.left = '200px';
terminal.style.right = '0px';
terminal.style.bottom = '24px';
terminal.style.opacity = '0';
terminal.style.transform = 'translateY(20px)';
terminal.style.transition = 'all 0.2s';
await domtools.plugins.smartdelay.delayFor(0);
terminal.style.opacity = '1';
terminal.style.transform = 'translateY(0px)';
}
private currentView: DeesElement;
public async loadView(viewArg: IView) {
const appcontent = this.shadowRoot.querySelector('.appcontent');
const view = new viewArg.element();
if (this.currentView) {
this.currentView.remove();
}
appcontent.appendChild(view);
this.currentView = view;
} }
} }

View File

@ -42,13 +42,24 @@ export class DeesSimpleLogin extends DeesElement {
align-items: center; /* aligns vertically */ align-items: center; /* aligns vertically */
width: 100%; width: 100%;
height: 100%; height: 100%;
top: 0px;
left: 0px;
} }
.slotContainer {
position: absolute;
width: 100%;
height: 100%;
top: 0px;
left: 0px;
}
.login { .login {
min-width: 320px; min-width: 320px;
min-height: 100px; min-height: 100px;
background: ${cssManager.bdTheme('#eeeeeb', '#111')}; background: ${cssManager.bdTheme('#eeeeeb', '#111')};
box-shadow: ${cssManager.bdTheme('0px 1px 4px rgba(0,0,0,0.3)', 'none')}; box-shadow: ${cssManager.bdTheme('0px 1px 4px rgba(0,0,0,0.3)', 'none')};
border-radius: 3px; border-radius: 8px;
padding: 24px; padding: 24px;
transition: opacity 0.3s, transform 0.3s; transition: opacity 0.3s, transform 0.3s;
} }
@ -92,7 +103,6 @@ export class DeesSimpleLogin extends DeesElement {
const submit = this.shadowRoot.querySelector('dees-form-submit'); const submit = this.shadowRoot.querySelector('dees-form-submit');
form.addEventListener('formData', (event: CustomEvent) => { form.addEventListener('formData', (event: CustomEvent) => {
this.dispatchEvent(new CustomEvent('login', { detail: event.detail })); this.dispatchEvent(new CustomEvent('login', { detail: event.detail }));
// this.switchToSlottedContent();
}); });
} }

View File

@ -0,0 +1,23 @@
import { html, cssManager } from '@design.estate/dees-element';
export const demoFunc = () => {
return html`
<style>
.ref1 {
margin: 20px;
width: 10px;
height: 10px;
background-color: red;
}
</style>
<div class="ref1"></div>
<dees-speechbubble .text=${`
**This is a longer markdown text that can be used the write**
a longer description about whats going on the app
**This is a subheader**
and another text
`}></dees-speechbubble>
`;
};

View File

@ -1,3 +1,7 @@
import * as colors from './00colors.js';
import * as plugins from './00plugins.js';
import { demoFunc } from './dees-speechbubble.demo.js';
import { import {
customElement, customElement,
html, html,
@ -8,9 +12,11 @@ import {
css, css,
type CSSResult, type CSSResult,
unsafeCSS, unsafeCSS,
domtools,
directives,
unsafeHTML,
} from '@design.estate/dees-element'; } from '@design.estate/dees-element';
import { DeesWindowLayer } from './dees-windowlayer.js';
import * as domtools from '@design.estate/dees-domtools';
declare global { declare global {
interface HTMLElementTagNameMap { interface HTMLElementTagNameMap {
@ -20,26 +26,53 @@ declare global {
@customElement('dees-speechbubble') @customElement('dees-speechbubble')
export class DeesSpeechbubble extends DeesElement { export class DeesSpeechbubble extends DeesElement {
public static demo = () => html` <dees-speechbubble></dees-speechbubble> `; public static demo = demoFunc;
@property() // STATIC
public static async createAndShow(refElement: HTMLElement, textArg: string) {
const windowLayer = await DeesWindowLayer.createAndShow({
blur: false,
});
const speechbubble = document.createElement('dees-speechbubble');
speechbubble.windowLayer = windowLayer;
speechbubble.reffedElement = refElement;
speechbubble.text = textArg;
speechbubble.manifested = true;
windowLayer.appendChild(speechbubble);
windowLayer.style.pointerEvents = 'none';
(windowLayer.shadowRoot.querySelector('.windowOverlay') as HTMLElement).style.pointerEvents = 'none';
return speechbubble;
}
// INSTANCE
@property({
type: Object,
})
reffedElement: HTMLElement;
@property({
type: String,
reflect: true,
})
public text: string; public text: string;
@property({ @property({
type: Boolean, type: Boolean,
}) })
public disabled = false; public wave: boolean = false;
@property({ @property({
type: Boolean, type: Boolean,
}) })
public isHidden = false; public manifested = false;
@property({ @property({
type: String, type: String,
}) })
public status: 'normal' | 'pending' | 'success' | 'error' = 'normal'; public status: 'normal' | 'pending' | 'success' | 'error' = 'normal';
public windowLayer: DeesWindowLayer;
constructor() { constructor() {
super(); super();
} }
@ -48,28 +81,22 @@ export class DeesSpeechbubble extends DeesElement {
cssManager.defaultStyles, cssManager.defaultStyles,
css` css`
:host { :host {
position: relative;
display: block;
box-sizing: border-box; box-sizing: border-box;
color: ${cssManager.bdTheme('#333', '#fff')}; color: ${cssManager.bdTheme('#333', '#fff')};
cursor: pointer;
user-select: none; user-select: none;
} }
:host([hidden]) {
display: none;
}
.maincontainer { .maincontainer {
position: relative;
will-change: transform; will-change: transform;
transition: transform 0.2s; transition: transform 0.2s;
transform: translateX(0px); transform: translateX(0px);
position: relative;
transition: all 0.2s; transition: all 0.2s;
margin-left: 0px; margin-left: 0px;
} filter: drop-shadow(0px 0px 2px rgba(0, 0, 0, 0.2));
pointer-events: none;
.maincontainer:hover { opacity: 0;
transform: translateX(3px); transition: all 0.2s;
} }
.arrow { .arrow {
@ -78,17 +105,17 @@ export class DeesSpeechbubble extends DeesElement {
background: ${cssManager.bdTheme('#fff', '#333')}; background: ${cssManager.bdTheme('#fff', '#333')};
height: 15px; height: 15px;
width: 15px; width: 15px;
left: 4px; left: 2px;
top: 5px; top: 12px;
border-radius: 2px; border-radius: 3px;
} }
.speechbubble { .speechbubble {
background: ${cssManager.bdTheme('#fff', '#333')}; background: ${cssManager.bdTheme('#fff', '#333')};
padding: 0px 10px; padding: 0px 16px;
border-radius: 3px; border-radius: 3px;
position: absolute; position: absolute;
line-height: 25px; min-width: 240px;
font-size: 12px; font-size: 12px;
top: 0px; top: 0px;
left: 8px; left: 8px;
@ -133,25 +160,70 @@ export class DeesSpeechbubble extends DeesElement {
public render(): TemplateResult { public render(): TemplateResult {
return html` return html`
<div class="maincontainer" @click=${this.handleClick}> ${this.manifested
<div class="arrow"></div> ? html`
<div class="speechbubble"><span class="wave">👋</span> We build with launch.sh, and you can too.</div> <div class="maincontainer" @click=${this.handleClick}>
</div> <div class="arrow"></div>
<div class="speechbubble">
${this.wave ? html`<span class="wave">👋</span>` : html``}
${directives.resolve(this.getHtml())}
</div>
</div>
`
: html``}
`; `;
} }
public async handleClick() { public async handleClick() {
if (this.disabled) { console.log('speechbubble got clicked.');
return;
}
globalThis.location.href = "https://launch.sh"
} }
public async firstUpdated() { public async firstUpdated() {
if (!this.textContent) { // lets make sure we have a ref
this.textContent = 'Button'; if (!this.reffedElement) {
this.performUpdate(); this.reffedElement = this.previousElementSibling as HTMLElement;
}
if (this.manifested) {
await this.updatePosition();
(this.shadowRoot.querySelector('.maincontainer') as HTMLElement).style.opacity = '1';
} else {
// lets make sure we instrument it
let speechbubble: DeesSpeechbubble;
this.reffedElement.addEventListener('mouseenter', async () => {
speechbubble = await DeesSpeechbubble.createAndShow(this.reffedElement, this.text);
});
this.reffedElement.addEventListener('mouseleave', () => {
speechbubble.destroy();
});
} }
} }
public async updatePosition() {
const refElement = this.reffedElement;
const boundingClientRect = refElement.getBoundingClientRect();
this.style.position = 'fixed';
this.style.top = `${boundingClientRect.top - 13}px`;
this.style.left = `${boundingClientRect.left + refElement.clientWidth + 4}px`;
if (boundingClientRect.right > 250) {
this.style.width = `250px`;
}
}
public async getHtml(): Promise<any> {
if (!this.text) {
return '';
}
const normalized = domtools.plugins.smartstring.normalize.standard(this.text);
const result = await domtools.plugins.smartmarkdown.SmartMarkdown.easyMarkdownToHtml(
normalized
);
return unsafeHTML(result);
}
public async show() {}
public async destroy() {
(this.shadowRoot.querySelector('.maincontainer') as HTMLElement).style.opacity = '0';
this.windowLayer.destroy();
}
} }

View File

@ -1,3 +1,6 @@
import * as plugins from './00plugins.js';
import * as colors from './00colors.js';
import { import {
DeesElement, DeesElement,
customElement, customElement,
@ -99,7 +102,7 @@ export class DeesStepper extends DeesElement {
transition: all 0.7s ease-in-out; transition: all 0.7s ease-in-out;
max-width: 500px; max-width: 500px;
min-height: 300px; min-height: 300px;
border-radius: 3px; border-radius: 8px;
background: ${cssManager.bdTheme('#ffffff', '#181818')}; background: ${cssManager.bdTheme('#ffffff', '#181818')};
border-top: 1px solid ${cssManager.bdTheme('#ffffff', '#181818')}; border-top: 1px solid ${cssManager.bdTheme('#ffffff', '#181818')};
color: ${cssManager.bdTheme('#333', '#fff')}; color: ${cssManager.bdTheme('#333', '#fff')};
@ -127,6 +130,7 @@ export class DeesStepper extends DeesElement {
} }
.step .stepCounter { .step .stepCounter {
color: #999;
position: absolute; position: absolute;
top: 0px; top: 0px;
right: 0px; right: 0px;
@ -137,6 +141,8 @@ export class DeesStepper extends DeesElement {
} }
.step .goBack { .step .goBack {
color: #999;
cursor: default;
position: absolute; position: absolute;
top: 0px; top: 0px;
left: 0px; left: 0px;
@ -144,17 +150,31 @@ export class DeesStepper extends DeesElement {
font-size: 12px; font-size: 12px;
border-bottom-right-radius: 3px; border-bottom-right-radius: 3px;
background: ${cssManager.bdTheme('#00000008', '#ffffff08')}; background: ${cssManager.bdTheme('#00000008', '#ffffff08')};
cursor: pointer;
} }
.step .goBack:hover { .step .goBack:hover {
background: ${cssManager.bdTheme('#00000012', '#ffffff12')}; color: ${cssManager.bdTheme('#333', '#fff')};
background: ${cssManager.bdTheme('#00000012', colors.dark.blue)};
}
.step .goBack:active {
color: ${cssManager.bdTheme('#333', '#fff')};
background: ${cssManager.bdTheme('#00000012', colors.dark.blueActive)};
}
.step .goBack span {
transition: all 0.2s;
display: inline-block;
}
.step .goBack:hover span {
transform: translateX(-2px);
} }
.step .title { .step .title {
text-align: center; text-align: center;
padding-top: 50px; padding-top: 50px;
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
font-size: 25px; font-size: 25px;
font-weight: 300; font-weight: 300;
} }
@ -178,7 +198,7 @@ export class DeesStepper extends DeesElement {
: ''}" : ''}"
> >
${this.getIndexOfStep(stepArg) > 0 ${this.getIndexOfStep(stepArg) > 0
? html`<div class="goBack" @click=${this.goBack}><- go to previous step</div>` ? html`<div class="goBack" @click=${this.goBack}><span style="font-family: Inter"><-</span> go to previous step</div>`
: ``} : ``}
<div class="stepCounter"> <div class="stepCounter">
Step ${this.steps.findIndex((elementArg) => elementArg === stepArg) + 1} of Step ${this.steps.findIndex((elementArg) => elementArg === stepArg) + 1} of

View File

@ -1,5 +1,5 @@
import { type ITableAction } from './dees-table.js'; import { type ITableAction } from './dees-table.js';
import * as plugins from './plugins.js'; import * as plugins from './00plugins.js';
import { html } from '@design.estate/dees-element'; import { html } from '@design.estate/dees-element';
interface ITableDemoData { interface ITableDemoData {

View File

@ -1,4 +1,5 @@
import * as plugins from './plugins.js'; import * as colors from './00colors.js';
import * as plugins from './00plugins.js';
import { demoFunc } from './dees-table.demo.js'; import { demoFunc } from './dees-table.demo.js';
import { import {
customElement, customElement,
@ -116,12 +117,21 @@ export class DeesTable<T> extends DeesElement {
public changeSubject = new domtools.plugins.smartrx.rxjs.Subject<DeesTable<T>>(); public changeSubject = new domtools.plugins.smartrx.rxjs.Subject<DeesTable<T>>();
// end dees-form compatibility ----------------------------------------- // end dees-form compatibility -----------------------------------------
/**
* What does a row of data represent?
*/
@property({ @property({
type: String, type: String,
reflect: true, reflect: true,
}) })
public dataName: string; public dataName: string;
@property({
type: Boolean,
})
searchable: boolean = true;
@property({ @property({
type: Array, type: Array,
}) })
@ -161,25 +171,26 @@ export class DeesTable<T> extends DeesElement {
css` css`
.mainbox { .mainbox {
color: ${cssManager.bdTheme('#333', '#fff')}; color: ${cssManager.bdTheme('#333', '#fff')};
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
font-weight: 400; font-weight: 400;
font-size: 14px; font-size: 14px;
padding: 16px; padding: 16px;
display: block; display: block;
width: 100%; width: 100%;
min-height: 50px; min-height: 50px;
background: ${cssManager.bdTheme('#ffffff', '#333333')}; background: ${cssManager.bdTheme('#ffffff', '#222222')};
border-radius: 3px; border-radius: 3px;
border-top: 1px solid ${cssManager.bdTheme('#fff', '#444')}; border-top: 1px solid ${cssManager.bdTheme('#fff', '#ffffff10')};
box-shadow: 0px 1px 4px rgba(0, 0, 0, 0.3); box-shadow: 0px 1px 4px rgba(0, 0, 0, 0.3);
overflow-x: auto; overflow-x: auto;
cursor: default;
} }
.header { .header {
display: flex; display: flex;
justify-content: flex-end; justify-content: flex-end;
align-items: center; align-items: center;
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
} }
.headingContainer { .headingContainer {
@ -197,16 +208,20 @@ export class DeesTable<T> extends DeesElement {
.headingSeparation { .headingSeparation {
margin-top: 7px; margin-top: 7px;
border-bottom: 1px solid ${cssManager.bdTheme('#bcbcbc', '#bcbcbc')}; border-bottom: 1px solid ${cssManager.bdTheme('#bcbcbc', '#444444')};
} }
.headerActions { .headerActions {
user-select: none;
display: flex;
flex-direction: row;
margin-left: auto; margin-left: auto;
cursor: pointer;
} }
.headerAction { .headerAction {
display: flex; display: flex;
flex-direction: row;
color: ${cssManager.bdTheme('#333', '#ccc')}; color: ${cssManager.bdTheme('#333', '#ccc')};
margin-left: 16px;
} }
.headerAction:hover { .headerAction:hover {
@ -217,6 +232,24 @@ export class DeesTable<T> extends DeesElement {
margin-right: 8px; margin-right: 8px;
} }
.searchGrid {
background: ${cssManager.bdTheme('#fff', '#111111')};
display: grid;
grid-gap: 16px;
grid-template-columns: 1fr 200px;
margin-top: 16px;
padding: 0px 16px;
border-top: 1px solid ${cssManager.bdTheme('#fff', '#ffffff20')};
border-radius: 8px;
}
.searchGrid.hidden {
height: 0px;
opacity: 0;
overflow: hidden;
margin-top: 0px;
}
table, table,
.noDataSet { .noDataSet {
margin-top: 16px; margin-top: 16px;
@ -236,7 +269,6 @@ export class DeesTable<T> extends DeesElement {
text-align: left; text-align: left;
} }
tr:hover { tr:hover {
cursor: pointer;
} }
tr:hover td { tr:hover td {
background: ${cssManager.bdTheme('#22222210', '#ffffff10')}; background: ${cssManager.bdTheme('#22222210', '#ffffff10')};
@ -257,7 +289,7 @@ export class DeesTable<T> extends DeesElement {
th { th {
text-transform: none; text-transform: none;
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
font-weight: 500; font-weight: 500;
} }
th, th,
@ -305,26 +337,36 @@ export class DeesTable<T> extends DeesElement {
font-weight: inherit; font-weight: inherit;
padding: 0px 6px; padding: 0px 6px;
} }
.actionsContainer {
.action { display: flex;
margin: -6px 0px; flex-direction: row;
padding: 10px; height: 24px;
line-height: 36px; transform: translateY(-4px);
height: 36px; margin-left: -6px;
display: inline-block;
} }
.action {
.action:first-child { position: relative;
margin-left: -8px; padding: 8px 10px;
width: min-content; line-height: 24px;
height: 32px;
size: 16px;
border-radius: 8px;
} }
.action:hover { .action:hover {
background: ${cssManager.bdTheme('#CCC', '#00000030')}; background: ${cssManager.bdTheme(colors.bright.blue, colors.dark.blue)};
}
.action:active {
background: ${cssManager.bdTheme(colors.bright.blue, colors.dark.blueActive)};
}
.action:hover dees-icon {
filter: ${cssManager.bdTheme('invert(1) brightness(3)', '')};
} }
.footer { .footer {
font-family: 'Roboto', 'Inter', sans-serif; font-family: 'Geist Sans', sans-serif;
font-size: 14px; font-size: 14px;
color: ${cssManager.bdTheme('#111', '#ffffff90')}; color: ${cssManager.bdTheme('#111', '#ffffff90')};
background: ${cssManager.bdTheme('#eeeeeb', '#00000050')}; background: ${cssManager.bdTheme('#eeeeeb', '#00000050')};
@ -343,19 +385,23 @@ export class DeesTable<T> extends DeesElement {
} }
.footerActions .footerAction { .footerActions .footerAction {
cursor: pointer;
padding: 8px 16px; padding: 8px 16px;
display: flex; display: flex;
user-select: none;
} }
.footerActions .footerAction:hover { .footerActions .footerAction:hover {
background: ${cssManager.bdTheme('#CCC', '#111')}; background: ${cssManager.bdTheme(colors.bright.blue, colors.dark.blue)};
color: #fff;
} }
.footerActions dees-icon { .footerActions .footerAction dees-icon {
display: flex; display: flex;
margin-right: 8px; margin-right: 8px;
} }
.footerActions .footerAction:hover dees-icon {
}
`, `,
]; ];
@ -395,8 +441,32 @@ export class DeesTable<T> extends DeesElement {
</div> </div>
</div> </div>
<div class="headingSeparation"></div> <div class="headingSeparation"></div>
<div class="searchGrid hidden">
<dees-input-text></dees-input-text> <dees-input-text
.label=${'lucene syntax search'}
.description=${`
You can use the lucene syntax to search for data, e.g.:
\`\`\`
name: "john" AND age: 18
\`\`\`
`}
></dees-input-text>
<dees-input-multitoggle
.label=${'search mode'}
.options=${['table', 'data', 'server']}
.selectedOption=${'table'}
.description=${`
There are three basic modes:
* table: only searches data already in the table
* data: searches original data, ignoring table transforms
* server: searches data on the server
`}
></dees-input-multitoggle>
</div>
<!-- the actual table --> <!-- the actual table -->
<style></style> <style></style>
@ -523,22 +593,28 @@ export class DeesTable<T> extends DeesElement {
return html` return html`
<td> <td>
<div class="innerCellContainer"> <div class="innerCellContainer">
${this.getActionsForType('inRow').map( <div class="actionsContainer">
(actionArg) => html`<div ${this.getActionsForType('inRow').map(
class="action" (actionArg) => html`
@click=${() => <div
actionArg.actionFunc({ class="action"
item: itemArg, @click=${() =>
table: this, actionArg.actionFunc({
})} item: itemArg,
> table: this,
${actionArg.iconName })}
? html` >
<dees-icon .iconFA=${actionArg.iconName}></dees-icon> ${actionArg.iconName
` ? html`
: actionArg.name} <dees-icon
</div>` .iconFA=${actionArg.iconName}
)} ></dees-icon>
`
: actionArg.name}
</div>
`
)}
</div>
</div> </div>
</td> </td>
`; `;
@ -587,11 +663,30 @@ export class DeesTable<T> extends DeesElement {
`; `;
} }
public async firstUpdated() {} public async firstUpdated() {
}
public async updated(changedProperties: Map<string | number | symbol, unknown>): Promise<void> { public async updated(changedProperties: Map<string | number | symbol, unknown>): Promise<void> {
super.updated(changedProperties); super.updated(changedProperties);
this.determineColumnWidths(); this.determineColumnWidths();
if (this.searchable) {
const existing = this.dataActions.find((actionArg) => actionArg.type.includes('header') && actionArg.name === 'Search');
if (!existing) {
this.dataActions.unshift({
name: 'Search',
iconName: 'magnifyingGlass',
type: ['header'],
actionFunc: async () => {
console.log('open search');
const searchGrid = this.shadowRoot.querySelector('.searchGrid');
searchGrid.classList.toggle('hidden');
}
});
console.log(this.dataActions);
this.requestUpdate();
};
}
} }
public async determineColumnWidths() { public async determineColumnWidths() {
@ -612,7 +707,7 @@ export class DeesTable<T> extends DeesElement {
const width = window.getComputedStyle(cell).width; const width = window.getComputedStyle(cell).width;
if (cell.textContent.includes('Actions')) { if (cell.textContent.includes('Actions')) {
const neededWidth = const neededWidth =
this.dataActions.filter((actionArg) => actionArg.type.includes('inRow')).length * 35; this.dataActions.filter((actionArg) => actionArg.type.includes('inRow')).length * 36;
cell.style.width = `${Math.max(neededWidth, 68)}px`; cell.style.width = `${Math.max(neededWidth, 68)}px`;
} else { } else {
cell.style.width = width; cell.style.width = width;

View File

@ -0,0 +1,320 @@
import {
DeesElement,
property,
html,
customElement,
type TemplateResult,
css,
cssManager,
} from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
import * as webcontainer from '@webcontainer/api';
import { Terminal } from 'xterm';
import { FitAddon } from 'xterm-addon-fit';
declare global {
interface HTMLElementTagNameMap {
'dees-terminal': DeesTerminal;
}
}
@customElement('dees-terminal')
export class DeesTerminal extends DeesElement {
public static demo = () => html` <dees-terminal></dees-terminal> `;
// INSTANCE
private resizeObserver: ResizeObserver;
@property()
public setupCommand = `pnpm install @git.zone/tsbuild && clear && echo 'welcome'`;
constructor() {
super();
this.resizeObserver = new ResizeObserver((entries) => {
for (const entry of entries) {
// Handle the resize event
console.log(`Terminal Resized`);
this.handleResize();
}
});
}
public static styles = [
cssManager.defaultStyles,
css`
:host {
padding: 20px;
background: #000;
position: absolute;
height: 100%;
width: 100%;
}
* {
box-sizing: border-box;
}
#container {
position: absolute;
height: calc(100% - 40px);
width: calc(100% - 40px);
}
/**
* Copyright (c) 2014 The xterm.js authors. All rights reserved.
* Copyright (c) 2012-2013, Christopher Jeffrey (MIT License)
* https://github.com/chjj/term.js
* @license MIT
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
* Originally forked from (with the author's permission):
* Fabrice Bellard's javascript vt100 for jslinux:
* http://bellard.org/jslinux/
* Copyright (c) 2011 Fabrice Bellard
* The original design remains. The terminal itself
* has been extended to include xterm CSI codes, among
* other features.
*/
/**
* Default styles for xterm.js
*/
.xterm {
font-feature-settings: 'liga' 0;
position: relative;
user-select: none;
-ms-user-select: none;
-webkit-user-select: none;
}
.xterm.focus,
.xterm:focus {
outline: none;
}
.xterm .xterm-helpers {
position: absolute;
top: 0;
/**
* The z-index of the helpers must be higher than the canvases in order for
* IMEs to appear on top.
*/
z-index: 5;
}
.xterm .xterm-helper-textarea {
padding: 0;
border: 0;
margin: 0;
/* Move textarea out of the screen to the far left, so that the cursor is not visible */
position: absolute;
opacity: 0;
left: -9999em;
top: 0;
width: 0;
height: 0;
z-index: -5;
/** Prevent wrapping so the IME appears against the textarea at the correct position */
white-space: nowrap;
overflow: hidden;
resize: none;
}
.xterm .composition-view {
/* TODO: Composition position got messed up somewhere */
background: #000;
color: #fff;
display: none;
position: absolute;
white-space: nowrap;
z-index: 1;
}
.xterm .composition-view.active {
display: block;
}
.xterm .xterm-viewport {
/* On OS X this is required in order for the scroll bar to appear fully opaque */
background-color: #000;
overflow-y: scroll;
cursor: default;
position: absolute;
right: 0;
left: 0;
top: 0;
bottom: 0;
}
.xterm .xterm-screen {
position: relative;
}
.xterm .xterm-screen canvas {
position: absolute;
left: 0;
top: 0;
}
.xterm .xterm-scroll-area {
visibility: hidden;
}
.xterm-char-measure-element {
display: inline-block;
visibility: hidden;
position: absolute;
top: 0;
left: -9999em;
line-height: normal;
}
.xterm {
cursor: text;
}
.xterm.enable-mouse-events {
/* When mouse events are enabled (eg. tmux), revert to the standard pointer cursor */
cursor: default;
}
.xterm.xterm-cursor-pointer {
cursor: pointer;
}
.xterm.column-select.focus {
/* Column selection mode */
cursor: crosshair;
}
.xterm .xterm-accessibility,
.xterm .xterm-message {
position: absolute;
left: 0;
top: 0;
bottom: 0;
right: 0;
z-index: 10;
color: transparent;
}
.xterm .live-region {
position: absolute;
left: -9999px;
width: 1px;
height: 1px;
overflow: hidden;
}
.xterm-dim {
opacity: 0.5;
}
.xterm-underline {
text-decoration: underline;
}
`,
];
public render(): TemplateResult {
return html`
<div class="mainbox">
<div id="container"></div>
</div>
`;
}
private fitAddon: FitAddon;
public async firstUpdated(
_changedProperties: Map<string | number | symbol, unknown>
): Promise<void> {
const domtools = await this.domtoolsPromise;
super.firstUpdated(_changedProperties);
const container = this.shadowRoot.getElementById('container');
const term = new Terminal({
convertEol: true,
cursorBlink: true,
});
this.fitAddon = new FitAddon();
term.loadAddon(this.fitAddon);
// Open the terminal in #terminal-container
term.open(container);
// Make the terminal's size and geometry fit the size of #terminal-container
this.fitAddon.fit();
term.write(`dees-terminal custom terminal. \r\n$ `);
// lets start the webcontainer
// Call only once
const webcontainerInstance = await webcontainer.WebContainer.boot();
const shellProcess = await webcontainerInstance.spawn('jsh');
shellProcess.output.pipeTo(
new WritableStream({
write(data) {
term.write(data);
},
})
);
const input = shellProcess.input.getWriter();
term.onData((data) => {
input.write(data);
});
await this.waitForPrompt(term, '~/');
input.write(this.setupCommand);
input.write(`\n`);
}
async connectedCallback(): Promise<void> {
await super.connectedCallback();
this.resizeObserver.observe(this);
}
async disconnectedCallback(): Promise<void> {
this.resizeObserver.unobserve(this);
await super.disconnectedCallback();
}
handleResize() {
this.fitAddon.fit();
}
private async waitForPrompt(term: Terminal, prompt: string): Promise<void> {
return new Promise<void>((resolve) => {
const checkPrompt = () => {
const lines = term.buffer.active;
for (let i = 0; i < lines.length; i++) {
const line = lines.getLine(i);
if (line && line.translateToString().includes(prompt)) {
resolve();
return;
}
}
setTimeout(checkPrompt, 100); // check every 100 ms
};
checkPrompt();
});
}
}

View File

@ -0,0 +1,10 @@
import { html } from '@design.estate/dees-element';
import { DeesUpdater } from './dees-updater.js';
export const demoFunc = async () => {
const updater = await DeesUpdater.createAndShow();
setTimeout(async () => {
await updater.destroy();
}, 10000);
}

View File

@ -1,7 +1,13 @@
import { customElement, DeesElement, type TemplateResult, html, property, type CSSResult, } from '@design.estate/dees-element'; import {
customElement,
import * as domtools from '@design.estate/dees-domtools'; DeesElement,
type TemplateResult,
html,
property,
type CSSResult,
domtools,
} from '@design.estate/dees-element';
import { demoFunc } from './dees-updater.demo.js';
import './dees-windowlayer'; import './dees-windowlayer';
import { css, cssManager } from '@design.estate/dees-element'; import { css, cssManager } from '@design.estate/dees-element';
@ -14,7 +20,13 @@ declare global {
@customElement('dees-updater') @customElement('dees-updater')
export class DeesUpdater extends DeesElement { export class DeesUpdater extends DeesElement {
public static demo = () => html`<dees-updater></dees-updater>`; public static demo = demoFunc;
public static async createAndShow() {
const updater = new DeesUpdater();
document.body.appendChild(updater);
return updater;
}
@property({ @property({
type: String, type: String,
@ -35,56 +47,64 @@ export class DeesUpdater extends DeesElement {
cssManager.defaultStyles, cssManager.defaultStyles,
css` css`
.modalContainer { .modalContainer {
will-change: transform; will-change: transform;
position: relative; position: relative;
background: ${cssManager.bdTheme('#eeeeeb', '#222')}; background: ${cssManager.bdTheme('#eeeeeb', '#222')};
margin: auto; max-width: 800px;
max-width: 800px; border-radius: 8px;
border-radius: 3px; border-top: 1px solid ${cssManager.bdTheme('#eeeeeb', '#333')};
border-top: 1px solid ${cssManager.bdTheme('#eeeeeb', '#333')}; }
}
.headingContainer { .headingContainer {
display: flex; display: flex;
justify-content: center; justify-content: center;
align-items: center; align-items: center;
padding: 40px 40px; padding: 40px 40px;
} }
h1 { h1 {
margin: none; margin: none;
font-size: 20px; font-size: 20px;
color: ${cssManager.bdTheme('#333', '#fff')}; color: ${cssManager.bdTheme('#333', '#fff')};
margin-left: 20px; margin-left: 20px;
font-weight: normal; font-weight: normal;
} }
.buttonContainer { .buttonContainer {
display: grid; display: grid;
grid-template-columns: 50% 50%; grid-template-columns: 50% 50%;
} }
` `,
] ];
public render(): TemplateResult { public render(): TemplateResult {
return html` return html`
<dees-windowlayer @clicked="${this.windowLayerClicked}"> <dees-windowlayer
@clicked="${this.windowLayerClicked}"
.options=${{
blur: true,
}}
>
<div class="modalContainer"> <div class="modalContainer">
<div class="headingContainer"> <div class="headingContainer">
<dees-spinner .size=${60}></dees-spinner> <dees-spinner .size=${60}></dees-spinner>
<h1>Updating the application...</h1> <h1>Updating the application...</h1>
</div> </div>
<div class="progress">
<dees-progressbar .progress=${0.5}></dees-progressbar>
</div>
<div class="buttonContainer"> <div class="buttonContainer">
<dees-button>More info</dees-button> <dees-button>More info</dees-button>
<dees-button>Changelog</dees-button> <dees-button>Changelog</dees-button>
</div> </div>
</div> </div> </dees-windowlayer
</dees-windowlayer>> >>
`; `;
} }
private windowLayerClicked() { public async destroy() {
const windowLayer = this.shadowRoot.querySelector('dees-windowlayer'); this.parentElement.removeChild(this);
windowLayer.toggleVisibility();
} }
private windowLayerClicked() {}
} }

View File

@ -0,0 +1,99 @@
import {
customElement,
DeesElement,
domtools,
type TemplateResult,
html,
property,
type CSSResult,
state,
css,
cssManager,
} from '@design.estate/dees-element';
declare global {
interface HTMLElementTagNameMap {
'dees-windowcontrols': DeesWindowControls;
}
}
@customElement('dees-windowcontrols')
export class DeesWindowControls extends DeesElement {
// STATIC
public static demo = () => html`<dees-windowcontrols></dees-windowcontrols>`;
// Instance
@property({
reflect: true,
})
public type: 'mac' | 'linux' | 'windows' = 'mac';
@property({
reflect: true,
})
public position: 'left' | 'right' = 'left';
public static styles = [
cssManager.defaultStyles,
css`
:host {
position: relative;
display: block;
box-sizing: border-box;
padding-left: 16px;
padding-right: 16px;
}
.windowControls {
height: 100%;
position: relative;
display: flex;
justify-content: center;
align-items: center;
}
.windowControls div {
width: 12px;
height: 12px;
display: inline-block;
border-radius: 50%;
margin: 0px;
padding: 0px;
background: #222222;
}
.windowControls div.close {
background: #ff5f57;
margin-right: 12px;
}
.windowControls div.toDock {
background: #ffbd2e;
margin-right: 12px;
}
.windowControls div.minMax {
background: #27c93f;
}
.windowControls div:hover {
background: #333333;
}
`,
];
public render(): TemplateResult {
return html`
${(this.type === 'mac' && this.position === 'left') ||
((this.type === 'linux' || this.type === 'windows') && this.position === 'right')
? html`
<div class="windowControls">
<div class="close"></div>
<div class="toDock"></div>
<div class="minMax"></div>
</div>
`
: html``}
`;
}
}

View File

@ -1,6 +1,4 @@
import { customElement, DeesElement, type TemplateResult, html, property, type CSSResult, state, } from '@design.estate/dees-element'; import { customElement, DeesElement, domtools, type TemplateResult, html, property, type CSSResult, state, } from '@design.estate/dees-element';
import * as domtools from '@design.estate/dees-domtools';
declare global { declare global {
interface HTMLElementTagNameMap { interface HTMLElementTagNameMap {
@ -67,16 +65,19 @@ export class DeesWindowLayer extends DeesElement {
z-index: 200; z-index: 200;
} }
.slotContent { .slotContent {
position: fixed;
height: 100vh; height: 100vh;
width: 100vw; width: 100vw;
display: flex; display: flex;
justify-content: center; justify-content: center;
align-items: center; align-items: center;
z-index: 201;
} }
.visible { .visible {
background: rgba(0, 0, 0, 0.2); background: rgba(0, 0, 0, 0.2);
backdrop-filter: brightness(0.9) ${this.options.blur ? 'blur(2px)' : ''}; backdrop-filter: brightness(0.9) ${this.options.blur ? 'blur(2px)' : ''};
pointer-events: all;
} }
</style> </style>
<div class="windowOverlay ${this.visible ? 'visible' : null}"> <div class="windowOverlay ${this.visible ? 'visible' : null}">

View File

@ -1,9 +1,20 @@
export * from './dees-appui-activitylog.js';
export * from './dees-appui-appbar.js';
export * from './dees-appui-base.js';
export * from './dees-appui-maincontent.js';
export * from './dees-appui-mainmenu.js';
export * from './dees-appui-mainselector.js';
export * from './dees-button-exit.js'; export * from './dees-button-exit.js';
export * from './dees-button.js'; export * from './dees-button.js';
export * from './dees-chart-area.js';
export * from './dees-chart-log.js';
export * from './dees-chips.js'; export * from './dees-chips.js';
export * from './dees-contextmenu.js'; export * from './dees-contextmenu.js';
export * from './dees-dataview-codebox.js'; export * from './dees-dataview-codebox.js';
export * from './dees-dataview-statusobject.js'; export * from './dees-dataview-statusobject.js';
export * from './dees-editor.js';
export * from './dees-editor-markdown.js';
export * from './dees-editor-markdownoutlet.js';
export * from './dees-form-submit.js'; export * from './dees-form-submit.js';
export * from './dees-form.js'; export * from './dees-form.js';
export * from './dees-hint.js'; export * from './dees-hint.js';
@ -12,12 +23,16 @@ export * from './dees-input-checkbox.js';
export * from './dees-input-dropdown.js'; export * from './dees-input-dropdown.js';
export * from './dees-input-fileupload.js'; export * from './dees-input-fileupload.js';
export * from './dees-input-iban.js'; export * from './dees-input-iban.js';
export * from './dees-input-typelist.js';
export * from './dees-input-phone.js'; export * from './dees-input-phone.js';
export * from './dees-progressbar.js';
export * from './dees-input-quantityselector.js'; export * from './dees-input-quantityselector.js';
export * from './dees-input-radio.js'; export * from './dees-input-radio.js';
export * from './dees-input-text.js'; export * from './dees-input-text.js';
export * from './dees-label.js';
export * from './dees-mobilenavigation.js'; export * from './dees-mobilenavigation.js';
export * from './dees-modal.js'; export * from './dees-modal.js';
export * from './dees-input-multitoggle.js';
export * from './dees-pdf.js'; export * from './dees-pdf.js';
export * from './dees-simple-appdash.js'; export * from './dees-simple-appdash.js';
export * from './dees-simple-login.js'; export * from './dees-simple-login.js';
@ -25,6 +40,8 @@ export * from './dees-speechbubble.js';
export * from './dees-spinner.js'; export * from './dees-spinner.js';
export * from './dees-stepper.js'; export * from './dees-stepper.js';
export * from './dees-table.js'; export * from './dees-table.js';
export * from './dees-terminal.js';
export * from './dees-toast.js'; export * from './dees-toast.js';
export * from './dees-updater.js'; export * from './dees-updater.js';
export * from './dees-windowcontrols.js';
export * from './dees-windowlayer.js'; export * from './dees-windowlayer.js';

View File

@ -0,0 +1,2 @@
export * from './tab.js';
export * from './selectionoption.js';

View File

@ -0,0 +1,4 @@
export interface ISelectionOption {
key: string;
action: () => void;
}

View File

@ -0,0 +1,5 @@
export interface ITab {
key: string;
iconName?: string;
action: () => void;
}