@svar-ui/svelte-toolbar 2.6.0 → 2.6.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. package/dist/buttons/ButtonList.svelte +35 -0
  2. package/dist/buttons/ButtonList.svelte.d.ts +13 -0
  3. package/{src → dist}/buttons/Icon.svelte +7 -8
  4. package/dist/buttons/Icon.svelte.d.ts +16 -0
  5. package/{src → dist}/buttons/Item.svelte +5 -6
  6. package/dist/buttons/Item.svelte.d.ts +13 -0
  7. package/{src → dist}/buttons/Label.svelte +2 -2
  8. package/dist/buttons/Label.svelte.d.ts +9 -0
  9. package/{src → dist}/buttons/Separator.svelte +1 -2
  10. package/dist/buttons/Separator.svelte.d.ts +6 -0
  11. package/dist/buttons/Spacer.svelte.d.ts +26 -0
  12. package/dist/components/BarComponent.svelte +69 -0
  13. package/dist/components/BarComponent.svelte.d.ts +11 -0
  14. package/{src → dist}/components/Group.svelte +12 -18
  15. package/dist/components/Group.svelte.d.ts +12 -0
  16. package/{src → dist}/components/Menu.svelte +16 -21
  17. package/dist/components/Menu.svelte.d.ts +12 -0
  18. package/dist/components/Toolbar.svelte +160 -0
  19. package/dist/components/Toolbar.svelte.d.ts +14 -0
  20. package/dist/env.d.ts +7 -0
  21. package/dist/helpers.d.ts +6 -0
  22. package/dist/helpers.js +41 -0
  23. package/dist/index.d.ts +5 -0
  24. package/{src → dist}/index.js +5 -6
  25. package/dist/types.d.ts +39 -0
  26. package/dist/types.js +1 -0
  27. package/package.json +56 -53
  28. package/readme.md +5 -16
  29. package/whatsnew.md +46 -27
  30. package/src/buttons/Button.svelte +0 -39
  31. package/src/components/BarComponent.svelte +0 -86
  32. package/src/components/Toolbar.svelte +0 -190
  33. package/src/helpers.js +0 -32
  34. package/types/index.d.ts +0 -37
  35. /package/{src → dist}/buttons/Spacer.svelte +0 -0
@@ -0,0 +1,39 @@
1
+ import type { Component } from "svelte";
2
+ export type TID = string | number;
3
+ export interface IToolbarItem {
4
+ id?: TID;
5
+ comp?: string | Component<any>;
6
+ icon?: string;
7
+ css?: string;
8
+ type?: string;
9
+ title?: string;
10
+ text?: string;
11
+ tooltip?: string;
12
+ menuText?: string;
13
+ key?: string;
14
+ disabled?: boolean;
15
+ spacer?: boolean;
16
+ collapsed?: boolean;
17
+ handler?: (item: IToolbarItem, value?: any) => void;
18
+ layout?: "column";
19
+ items?: IToolbarItem[];
20
+ pinned?: boolean;
21
+ [key: string]: any;
22
+ }
23
+ export type TToolbarValues = {
24
+ [key: string]: any;
25
+ };
26
+ export interface IToolbarClickEvent {
27
+ item: IToolbarItem;
28
+ }
29
+ export interface IToolbarChangeEvent {
30
+ value: any;
31
+ item: IToolbarItem;
32
+ }
33
+ export interface IButtonListOption {
34
+ id: TID;
35
+ label: string;
36
+ }
37
+ export interface IItemConfig {
38
+ menu?: boolean;
39
+ }
package/dist/types.js ADDED
@@ -0,0 +1 @@
1
+ export {};
package/package.json CHANGED
@@ -1,54 +1,57 @@
1
1
  {
2
- "name": "@svar-ui/svelte-toolbar",
3
- "version": "2.6.0",
4
- "description": "Svelte toolbar component. Lightweight, customizable, easy-to-use.",
5
- "productTag": "toolbar",
6
- "productTrial": false,
7
- "type": "module",
8
- "scripts": {
9
- "build": "vite build",
10
- "build:dist": "vite build --mode dist",
11
- "build:tests": "vite build --mode test",
12
- "lint": "yarn eslint ./demos ./src",
13
- "start": "vite --open",
14
- "start:tests": "vite --open=/tests/ --host 0.0.0.0 --port 5100 --mode test",
15
- "test": "true",
16
- "test:cypress": "cypress run -P ./ --config \"baseUrl=http://localhost:5100/tests\""
17
- },
18
- "svelte": "src/index.js",
19
- "exports": {
20
- ".": {
21
- "svelte": "./src/index.js",
22
- "types": "./types/index.d.ts"
23
- },
24
- "./package.json": "./package.json"
25
- },
26
- "license": "MIT",
27
- "repository": {
28
- "type": "git",
29
- "url": "https://github.com/svar-widgets/toolbar.git"
30
- },
31
- "bugs": {
32
- "url": "https://forum.svar.dev"
33
- },
34
- "homepage": "https://svar.dev/svelte/core/",
35
- "dependencies": {
36
- "@svar-ui/svelte-core": "2.6.0",
37
- "@svar-ui/lib-dom": "0.13.1"
38
- },
39
- "files": [
40
- "src",
41
- "types",
42
- "readme.md",
43
- "whatsnew.md",
44
- "license.txt"
45
- ],
46
- "keywords": [
47
- "svelte",
48
- "svelte toolbar",
49
- "toolbar",
50
- "toolbar component",
51
- "buttons panel",
52
- "svar widgets"
53
- ]
54
- }
2
+ "name": "@svar-ui/svelte-toolbar",
3
+ "version": "2.6.2",
4
+ "description": "Svelte toolbar component. Lightweight, customizable, easy-to-use.",
5
+ "keywords": [
6
+ "buttons panel",
7
+ "svar widgets",
8
+ "svelte",
9
+ "svelte toolbar",
10
+ "toolbar",
11
+ "toolbar component"
12
+ ],
13
+ "homepage": "https://svar.dev/svelte/core/",
14
+ "bugs": {
15
+ "url": "https://forum.svar.dev"
16
+ },
17
+ "license": "MIT",
18
+ "repository": {
19
+ "type": "git",
20
+ "url": "https://github.com/svar-widgets/toolbar.git"
21
+ },
22
+ "files": [
23
+ "dist",
24
+ "readme.md",
25
+ "whatsnew.md",
26
+ "license.txt"
27
+ ],
28
+ "type": "module",
29
+ "types": "./dist/index.d.ts",
30
+ "svelte": "./dist/index.js",
31
+ "exports": {
32
+ ".": {
33
+ "svelte": "./dist/index.js",
34
+ "types": "./dist/index.d.ts"
35
+ },
36
+ "./package.json": "./package.json"
37
+ },
38
+ "dependencies": {
39
+ "@svar-ui/lib-dom": "0.14.2",
40
+ "@svar-ui/svelte-core": "2.6.2"
41
+ },
42
+ "devDependencies": {
43
+ "@sveltejs/package": "^2.5.7",
44
+ "@sveltejs/vite-plugin-svelte": "^7.1.2",
45
+ "svelte": "5.56.9",
46
+ "svelte-check": "^4.4.6"
47
+ },
48
+ "peerDependencies": {
49
+ "svelte": "^5.0.0"
50
+ },
51
+ "productTag": "toolbar",
52
+ "scripts": {
53
+ "check": "svelte-check --tsconfig ./tsconfig.json",
54
+ "build": "svelte-package -i ./src",
55
+ "dev": "svelte-package -i ./src --watch"
56
+ }
57
+ }
package/readme.md CHANGED
@@ -1,5 +1,5 @@
1
1
  <div align="center">
2
-
2
+
3
3
  # SVAR Svelte Toolbar
4
4
 
5
5
  [![npm](https://img.shields.io/npm/v/@svar-ui/svelte-toolbar.svg)](https://www.npmjs.com/package/@svar-ui/svelte-toolbar)
@@ -46,21 +46,10 @@ To use the widget, simply import the package and include the component in your S
46
46
 
47
47
  Typically, you don't need to modify the code. However, if you wish to do so, follow these steps:
48
48
 
49
- 1. Run `yarn` to install dependencies. Note that this project is a monorepo using `yarn` workspaces, so npm will not work
50
- 2. Start the project in development mode with `yarn start`
51
-
52
- ### Run Tests
53
-
54
- To run the test:
55
-
56
- 1. Start the test examples with:
57
- ```sh
58
- yarn start:tests
59
- ```
60
- 2. In a separate console, run the end-to-end tests with:
61
- ```sh
62
- yarn test:cypress
63
- ```
49
+ 1. Install [vite-plus](https://vite.plus) (`curl -fsSL https://vite.plus | bash` on Mac/Linux, `irm https://vite.plus/ps1 | iex` on Windows). The project uses `pnpm` workspaces under the hood, so plain `npm` will not work.
50
+ 2. Run `vp i` from the project root to install dependencies.
51
+ 3. Run `vp run build` to build all packages.
52
+ 4. Start the demo app in development mode with `vp run start`.
64
53
 
65
54
  ### Need help?
66
55
 
package/whatsnew.md CHANGED
@@ -1,110 +1,129 @@
1
+ ## 2.6.2
2
+
3
+ ### Updates
4
+
5
+ - Native TypeScript support with types generated from the component sources
6
+
7
+ ### Fixes
8
+
9
+ - An item with key throws an error when the Toolbar has no values
10
+ - Changing an item without key writes `values["undefined"]`
11
+ - ButtonList without css gets an undefined CSS class
12
+
13
+ ## 2.6.1
14
+
15
+ ### Updates
16
+
17
+ - Impossible to render an item differently in the `menu` mode
18
+ - Option based items are not usable in the `menu` mode
19
+
1
20
  ## 2.6.0
2
21
 
3
22
  ### New features
4
23
 
5
- - Tooltip for toolbar items
24
+ - Tooltip for toolbar items
6
25
 
7
26
  ### Fixes
8
27
 
9
- - Duplicate separators are auto removed
28
+ - Duplicate separators are auto removed
10
29
 
11
30
  ## 2.5.3
12
31
 
13
32
  ### Fixes
14
33
 
15
- - Impossible to arrange first level items as a column
16
- - Impossible to fix certain items as always visible
34
+ - Impossible to arrange first level items as a column
35
+ - Impossible to fix certain items as always visible
17
36
 
18
37
  ## 2.5.1
19
38
 
20
- - Using Svelte Core v2.5.1
39
+ - Using Svelte Core v2.5.1
21
40
 
22
41
  ## 2.5.0
23
42
 
24
- - Using Svelte Core v2.5.0
43
+ - Using Svelte Core v2.5.0
25
44
 
26
45
  ## 2.4.1
27
46
 
28
- - Using Svelte Core v2.4.1
47
+ - Using Svelte Core v2.4.1
29
48
 
30
49
  ## 2.4.0
31
50
 
32
- - Using Svelte Core v2.4.0
51
+ - Using Svelte Core v2.4.0
33
52
 
34
53
  ## 2.3.0
35
54
 
36
55
  ### New features
37
56
 
38
- - TypeScript definitions
57
+ - TypeScript definitions
39
58
 
40
59
  ### Fixes
41
60
 
42
- - item `menuText` property is not applied
61
+ - item `menuText` property is not applied
43
62
 
44
63
  ## 2.2.1
45
64
 
46
65
  ### Fixes
47
66
 
48
- - Using in Salesforce environment
67
+ - Using in Salesforce environment
49
68
 
50
69
  ## 2.2.0
51
70
 
52
- - Using core@2.2.0
71
+ - Using core@2.2.0
53
72
 
54
73
  ## 2.1.0
55
74
 
56
- - Using core@2.1.0
75
+ - Using core@2.1.0
57
76
 
58
77
  ## 2.0.1
59
78
 
60
79
  ### New features
61
80
 
62
- - Svelte 5 support
81
+ - Svelte 5 support
63
82
 
64
83
  ## 1.3.0
65
84
 
66
- - Using core@1.3.0
85
+ - Using core@1.3.0
67
86
 
68
87
  ## 1.2.3
69
88
 
70
89
  ### Fixes
71
90
 
72
- - Regression in overflow menu closing
73
- - Regression in dropdown rendering
91
+ - Regression in overflow menu closing
92
+ - Regression in dropdown rendering
74
93
 
75
94
  ## 1.2.1
76
95
 
77
- - Using core@1.2.0
96
+ - Using core@1.2.0
78
97
 
79
98
  ## 1.2.1
80
99
 
81
100
  ### New features
82
101
 
83
- - Labels can be bound to data
102
+ - Labels can be bound to data
84
103
 
85
104
  ## 1.2.0
86
105
 
87
106
  ### New features
88
107
 
89
- - Extra demo for the HeaderMenu scenario
90
- - Ability to use `spacer` on toolbar items
91
- - Ability to use `item` subtype for the drop-down menus
108
+ - Extra demo for the HeaderMenu scenario
109
+ - Ability to use `spacer` on toolbar items
110
+ - Ability to use `item` subtype for the drop-down menus
92
111
 
93
112
  ### Fixes
94
113
 
95
- - Separator rendering in drop-down menus
96
- - Names of css classes corrected
114
+ - Separator rendering in drop-down menus
115
+ - Names of css classes corrected
97
116
 
98
117
  ## 1.1.2
99
118
 
100
119
  ### Updates
101
120
 
102
- - Inner css classes renamed, "wx" prefix added
121
+ - Inner css classes renamed, "wx" prefix added
103
122
 
104
123
  ## 1.1.1
105
124
 
106
- - Migrated to vite based toolchain
125
+ - Migrated to vite based toolchain
107
126
 
108
127
  ### 1.1.0
109
128
 
110
- - Initial version
129
+ - Initial version
@@ -1,39 +0,0 @@
1
- <script>
2
- import { Button } from "@svar-ui/svelte-core";
3
-
4
- let {
5
- icon,
6
- title,
7
- text = "",
8
- tooltip,
9
- css,
10
- type,
11
- disabled,
12
- menu,
13
- onclick,
14
- } = $props();
15
- </script>
16
-
17
- {#if menu}
18
- <!-- svelte-ignore a11y_click_events_have_key_events -->
19
- <!-- svelte-ignore a11y_no_static_element_interactions -->
20
- <div class="wx-item" {onclick}>
21
- <i class="{icon || 'wxi-empty'} {css || ''}"></i>
22
- {text}
23
- </div>
24
- {:else}
25
- <Button {icon} {type} {css} {title} {text} {tooltip} {disabled} {onclick} />
26
- {/if}
27
-
28
- <style>
29
- i {
30
- margin-right: 8px;
31
- font-size: var(--wx-button-icon-size);
32
- color: var(--wx-icon-color);
33
- }
34
- .wx-item {
35
- cursor: pointer;
36
- white-space: nowrap;
37
- line-height: 26px;
38
- }
39
- </style>
@@ -1,86 +0,0 @@
1
- <script>
2
- import { setID } from "@svar-ui/lib-dom";
3
- import { getItemHandler } from "../helpers";
4
- import Separator from "../buttons/Separator.svelte";
5
- import Spacer from "../buttons/Spacer.svelte";
6
-
7
- let { item = {}, menu = false, values, onclick, onchange } = $props();
8
-
9
- let itemComponent = $derived(getItemHandler(item.comp || "label"));
10
-
11
- function onClick() {
12
- if (item.handler) item.handler(item);
13
- onclick && onclick({ item });
14
- }
15
-
16
- let value = $derived(item.key ? values[item.key] : undefined);
17
- function detectChange({ value }) {
18
- if (item.handler) item.handler(item, value);
19
- onchange && onchange({ value, item });
20
- }
21
-
22
- const text = $derived(menu ? item.menuText || item.text : item.text);
23
- </script>
24
-
25
- {#if item.comp == "spacer"}
26
- <Spacer />
27
- {:else if item.comp == "separator"}
28
- <Separator {menu} />
29
- {:else}
30
- {@const SvelteComponent = itemComponent}
31
- <div
32
- class="wx-tb-element {item.css || ''}"
33
- class:wx-spacer={item.spacer}
34
- class:wx-menu={menu}
35
- data-id={setID(item.id)}
36
- >
37
- <SvelteComponent
38
- {value}
39
- onchange={detectChange}
40
- onclick={onClick}
41
- {menu}
42
- {...item}
43
- {text}
44
- />
45
- </div>
46
- {/if}
47
-
48
- <style>
49
- .wx-spacer {
50
- flex: 1;
51
- }
52
- .wx-tb-element {
53
- padding: 4px;
54
- flex-shrink: 0;
55
- align-self: center;
56
- display: flex;
57
- }
58
- .wx-menu.wx-tb-element {
59
- height: 36px;
60
- line-height: 36px;
61
- padding: 2px 8px;
62
- background-color: var(--wx-background);
63
- }
64
-
65
- .wx-menu :global(button) {
66
- width: 100%;
67
- background: transparent;
68
- text-align: left;
69
- padding-left: 0;
70
- font-weight: var(--wx-font-weight);
71
- font-size: var(--wx-font-size);
72
- }
73
- .wx-menu :global(.wx-tb-element) {
74
- align-self: stretch;
75
- }
76
- .wx-menu.wx-tb-element :global(button:hover) {
77
- background: var(--wx-background-alt);
78
- }
79
- .wx-menu :global(button i) {
80
- margin-right: 4px;
81
- font-size: var(--wx-icon-size);
82
- }
83
- .wx-menu.wx-tb-element:hover {
84
- background: var(--wx-background-alt);
85
- }
86
- </style>
@@ -1,190 +0,0 @@
1
- <script>
2
- import Menu from "./Menu.svelte";
3
- import Group from "./Group.svelte";
4
- import BarComponent from "./BarComponent.svelte";
5
-
6
- import { onMount, tick } from "svelte";
7
- import { normalizeToolbarItems } from "../helpers";
8
-
9
- let {
10
- items = $bindable([]),
11
- menuCss = "",
12
- css = "",
13
- values = $bindable(null),
14
- overflow = "menu",
15
- layout = "row",
16
- onclick,
17
- onchange,
18
- } = $props();
19
-
20
- function handleChange(ev) {
21
- if (values) {
22
- values[ev.item.key] = ev.value;
23
- values = values;
24
- }
25
- onchange && onchange(ev);
26
- }
27
-
28
- let div = null;
29
- let menuItems = $state([]);
30
-
31
- const barItems = $derived(normalizeToolbarItems(items));
32
-
33
- function getTotalWidth() {
34
- const nodes = div.children;
35
- let sum = 0;
36
- for (let i = 0; i < barItems.length; i++) {
37
- if (barItems[i].comp != "spacer") {
38
- sum += nodes[i]?.clientWidth || 0;
39
- if (barItems[i].comp == "separator") sum += 8;
40
- }
41
- }
42
- return sum;
43
- }
44
-
45
- function collapseGroups() {
46
- for (let i = barItems.length - 1; i >= 0; i--) {
47
- // close rightmost open group
48
- if (barItems[i].items && !barItems[i].collapsed) {
49
- barItems[i].collapsed = true;
50
- barItems[i].$width = div.children[i].offsetWidth;
51
- // check after dom update, maybe we need to close more
52
- tick().then(processOverflow);
53
-
54
- // items are not deep reactive, so we need to trigger the update
55
- items = [...items];
56
- return;
57
- }
58
- }
59
- }
60
-
61
- function expandGroups(freeSpace) {
62
- for (let i = 0; i < barItems.length; i++) {
63
- // open leftmost closed group that was collapsed by overflow
64
- if (barItems[i].collapsed && barItems[i].$width) {
65
- // check if group can fit in free space
66
- if (
67
- barItems[i].$width - div.children[i].offsetWidth <
68
- freeSpace + 10
69
- ) {
70
- barItems[i].collapsed = false;
71
- // items are not deep reactive, so we need to trigger the update
72
- items = [...items];
73
- // check after dom update, maybe we can open one more
74
- tick().then(processOverflow);
75
- }
76
- return;
77
- }
78
- }
79
- }
80
-
81
- function processOverflow() {
82
- if (overflow === "wrap") return;
83
-
84
- const nodes = div.children;
85
- // restore all items so widths can be measured
86
- for (let i = 0; i < barItems.length; i++) {
87
- if (nodes[i]) nodes[i].style.display = "";
88
- }
89
-
90
- const visibleWidth = div.clientWidth;
91
- const fullWidth = div.scrollWidth;
92
- const needMenu = fullWidth > visibleWidth;
93
-
94
- if (needMenu) {
95
- if (overflow === "collapse") return collapseGroups();
96
-
97
- // pinned items always stay visible
98
- let pinnedWidth = 0;
99
- for (let i = 0; i < barItems.length; i++) {
100
- if (barItems[i].pinned) pinnedWidth += nodes[i].clientWidth;
101
- }
102
-
103
- let sum = 0;
104
- for (let i = 0; i < barItems.length; i++) {
105
- if (barItems[i].pinned) continue;
106
- sum += nodes[i].clientWidth;
107
- if (barItems[i].comp == "separator") sum += 8;
108
- if (sum > visibleWidth - 40 - pinnedWidth) {
109
- // we need to hide nodes[i] and all next non-pinned nodes
110
- menuItems = [];
111
- for (let j = i; j < barItems.length; j++) {
112
- if (barItems[j].pinned) continue;
113
- menuItems.push(barItems[j]);
114
- nodes[j].style.display = "none";
115
- }
116
- // hide the ending separator
117
- if (
118
- i > 0 &&
119
- barItems[i - 1].comp == "separator" &&
120
- !barItems[i - 1].pinned
121
- ) {
122
- nodes[i - 1].style.display = "none";
123
- }
124
- break;
125
- }
126
- }
127
- } else {
128
- const freeWidth = visibleWidth - getTotalWidth();
129
- if (freeWidth <= 0) return;
130
- if (overflow === "collapse") return expandGroups(freeWidth);
131
-
132
- if (menuItems.length) menuItems = [];
133
- }
134
- }
135
-
136
- onMount(() => {
137
- const resizeObserver = new ResizeObserver(() => processOverflow());
138
- resizeObserver.observe(div);
139
-
140
- return () => {
141
- resizeObserver.unobserve(div);
142
- };
143
- });
144
- </script>
145
-
146
- <div
147
- class="wx-toolbar {css}"
148
- class:wx-wrap={overflow === "wrap"}
149
- class:wx-column={layout == "column"}
150
- class:wx-has-menu={menuItems.length}
151
- bind:this={div}
152
- >
153
- {#each barItems as item}
154
- {#if item.items}
155
- <Group {item} {values} {onclick} onchange={handleChange} />
156
- {:else}
157
- <BarComponent {item} {values} {onclick} onchange={handleChange} />
158
- {/if}
159
- {/each}
160
- {#if menuItems.length}
161
- <Menu
162
- items={menuItems}
163
- css={menuCss}
164
- {values}
165
- {onclick}
166
- onchange={handleChange}
167
- />
168
- {/if}
169
- </div>
170
-
171
- <style>
172
- .wx-toolbar {
173
- width: 100%;
174
- flex-wrap: nowrap;
175
- display: flex;
176
- align-items: stretch;
177
- padding: 4px;
178
- position: relative;
179
- min-height: 48px;
180
- }
181
- .wx-toolbar.wx-has-menu {
182
- padding-right: 48px;
183
- }
184
- .wx-toolbar.wx-wrap {
185
- flex-wrap: wrap;
186
- }
187
- .wx-column {
188
- flex-flow: column;
189
- }
190
- </style>
package/src/helpers.js DELETED
@@ -1,32 +0,0 @@
1
- import { uid } from "@svar-ui/lib-dom";
2
-
3
- const handlers = {};
4
- export function getItemHandler(type) {
5
- return handlers[type] || type;
6
- }
7
- export function registerToolbarItem(type, handler) {
8
- handlers[type] = handler;
9
- }
10
-
11
- // Assign stable ids and collapse consecutive separators
12
- export function normalizeToolbarItems(items) {
13
- if (!items?.length) return [];
14
- for (const item of items) {
15
- if (!item.id) item.id = uid();
16
- }
17
- return collapseSeparators(items);
18
- }
19
-
20
- // Keep the first of consecutive separator
21
- export function collapseSeparators(items) {
22
- if (!items?.length) return items || [];
23
- const out = [];
24
- let prevWasSeparator = false;
25
- for (const item of items) {
26
- const isSeparator = item.comp === "separator";
27
- if (isSeparator && prevWasSeparator) continue;
28
- out.push(item);
29
- prevWasSeparator = isSeparator;
30
- }
31
- return out;
32
- }