@ticatec/uniface-element 0.1.35 → 0.1.46

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 (48) hide show
  1. package/README.md +1 -1
  2. package/dist/app-layout/ClassicLayout.svelte +7 -4
  3. package/dist/attachment-files/AttachmentFilesField.svelte +1 -1
  4. package/dist/attachment-files/FileRender.svelte +2 -2
  5. package/dist/attachment-files/FileUploadPanel.svelte +1 -1
  6. package/dist/box/Box.svelte +1 -1
  7. package/dist/box/Box.svelte.d.ts +2 -2
  8. package/dist/cascade-options-select/CascadeOptionSelect.svelte +1 -1
  9. package/dist/criteria-field/CriteriaField.svelte +1 -2
  10. package/dist/criteria-field/CriteriaField.svelte.d.ts +0 -1
  11. package/dist/data-table/lib/IndicatorColumn.d.ts +1 -1
  12. package/dist/data-table/parts/FixedHeaderPanel.svelte +1 -1
  13. package/dist/data-table/parts/FixedRow.svelte +1 -1
  14. package/dist/date-picker/ScrollBar.svelte +2 -2
  15. package/dist/dialog/Dialog.svelte +1 -1
  16. package/dist/form-field/FormField.svelte +6 -6
  17. package/dist/form-field/FormField.svelte.d.ts +0 -1
  18. package/dist/form-panel/flex-form/CellField.svelte +1 -2
  19. package/dist/form-panel/flex-form/CellField.svelte.d.ts +0 -1
  20. package/dist/form-panel/flex-form/FlexForm.svelte +3 -1
  21. package/dist/form-panel/flex-form/FlexForm.svelte.d.ts +1 -0
  22. package/dist/form-panel/flex-row-form/FormContainer.svelte +2 -1
  23. package/dist/form-panel/flex-row-form/FormContainer.svelte.d.ts +1 -0
  24. package/dist/form-panel/grid-form/GridField.svelte +8 -6
  25. package/dist/form-panel/grid-form/GridField.svelte.d.ts +4 -3
  26. package/dist/form-panel/grid-form/GridForm.svelte +9 -2
  27. package/dist/form-panel/grid-form/GridForm.svelte.d.ts +2 -0
  28. package/dist/image-files/ImageFilesField.svelte +1 -1
  29. package/dist/image-files/ImagePreview.svelte +3 -3
  30. package/dist/image-files/ImageRender.svelte +2 -2
  31. package/dist/lib/TreeNodes.d.ts +58 -0
  32. package/dist/lib/TreeNodes.js +172 -0
  33. package/dist/list-box/ListBox.svelte +17 -15
  34. package/dist/lookup-editor/LookupEditor.svelte +1 -1
  35. package/dist/message-box/MessageBoxBoard.svelte +1 -1
  36. package/dist/navigator/Navigator.svelte +2 -0
  37. package/dist/navigator/Navigator.svelte.d.ts +1 -0
  38. package/dist/search-box/SearchBox.svelte +2 -2
  39. package/dist/tabs/Tabs.svelte +24 -34
  40. package/dist/tabs/Tabs.svelte.d.ts +1 -0
  41. package/dist/tag/Tag.svelte +4 -2
  42. package/dist/text-editor/PasswordEditor.svelte +3 -3
  43. package/dist/ticatec-uniface-web.css +80 -75
  44. package/dist/tree-view/TreeNodeView.svelte +1 -1
  45. package/dist/tree-view/TreeNodeView.svelte.d.ts +1 -1
  46. package/dist/tree-view/TreeView.svelte +1 -1
  47. package/dist/tree-view/TreeView.svelte.d.ts +1 -1
  48. package/package.json +1 -1
@@ -0,0 +1,172 @@
1
+ export function compareNumber(a, b) {
2
+ return a === b ? 0 : a > b ? 1 : -1;
3
+ }
4
+ export default class TreeNodes {
5
+ checkIsRoot;
6
+ keyField;
7
+ parentKeyField;
8
+ textField;
9
+ nodeMap;
10
+ compareFun;
11
+ expendDeep;
12
+ #nodes = [];
13
+ constructor(options) {
14
+ this.checkIsRoot = options.checkIsRoot;
15
+ this.compareFun = options.compareFun;
16
+ this.keyField = options.keyField ?? 'id';
17
+ this.textField = options.textField ?? 'text';
18
+ this.parentKeyField = options.parentKeyField ?? 'parentId';
19
+ this.nodeMap = new Map();
20
+ this.expendDeep = options.expendDeep ?? 999;
21
+ }
22
+ setData(list) {
23
+ this.nodeMap = new Map();
24
+ this.#nodes = [];
25
+ // 初始化每个节点
26
+ for (const item of list) {
27
+ const node = {
28
+ item,
29
+ expand: true
30
+ };
31
+ const key = item[this.keyField];
32
+ this.nodeMap.set(key, node);
33
+ }
34
+ for (const item of list) {
35
+ const node = this.nodeMap.get(item[this.keyField]);
36
+ if (node) {
37
+ this.appendNode(node);
38
+ }
39
+ }
40
+ }
41
+ appendNode(node, doSort = false) {
42
+ let item = node.item;
43
+ const parentKey = item[this.parentKeyField];
44
+ if (this.checkIsRoot(item) || !this.nodeMap.has(parentKey)) {
45
+ this.#nodes.push(node);
46
+ }
47
+ else {
48
+ const parentNode = this.nodeMap.get(parentKey);
49
+ if (parentNode) {
50
+ parentNode.expand = true;
51
+ parentNode.children = [...(parentNode.children ?? []), node];
52
+ if (doSort && this.compareFun) {
53
+ parentNode.children = parentNode.children.sort(this.compareFun);
54
+ }
55
+ }
56
+ }
57
+ }
58
+ collectExpandedNodes(tree) {
59
+ const result = [];
60
+ function traverse(nodes) {
61
+ for (const node of nodes) {
62
+ result.push(node);
63
+ if (node.expand && node.children) {
64
+ traverse(node.children);
65
+ }
66
+ }
67
+ }
68
+ traverse(tree);
69
+ return result;
70
+ }
71
+ /**
72
+ * 获取展开的展示列表
73
+ */
74
+ getHierarchyList() {
75
+ return this.collectExpandedNodes(this.#nodes);
76
+ }
77
+ /**
78
+ * 获取节点
79
+ */
80
+ get nodes() {
81
+ return this.#nodes;
82
+ }
83
+ /**
84
+ * 增加一个新节点
85
+ * @param item
86
+ */
87
+ append(item) {
88
+ const node = {
89
+ item,
90
+ expand: true
91
+ };
92
+ this.appendNode(node, true);
93
+ this.nodeMap.set(item[this.keyField], node);
94
+ }
95
+ /**
96
+ * 替换一个节点的数据
97
+ * @param item
98
+ */
99
+ replace(item) {
100
+ let node = this.nodeMap.get(item[this.keyField]);
101
+ if (node) {
102
+ node.item = item;
103
+ let parent = this.nodeMap.get(item[this.parentKeyField]);
104
+ if (parent && parent.children && parent.children.length > 0) {
105
+ parent.children = parent.children.sort(this.compareFun);
106
+ }
107
+ }
108
+ }
109
+ remove(item) {
110
+ let idKey = item[this.keyField];
111
+ let node = this.nodeMap.get(idKey);
112
+ if (node) {
113
+ let parent = this.nodeMap.get(node.item[this.parentKeyField]);
114
+ this.nodeMap.delete(idKey);
115
+ if (parent && parent.children) {
116
+ let pos = parent.children.findIndex(el => el.item[this.keyField] == idKey);
117
+ if (pos > -1) {
118
+ parent.children.splice(pos, 1);
119
+ }
120
+ }
121
+ }
122
+ }
123
+ /**
124
+ * 将一个节点移动到另外一个节点下
125
+ * @param item
126
+ * @param parentId
127
+ */
128
+ moveTo(item, parentId) {
129
+ let newParent = this.nodeMap.get(parentId);
130
+ let node = this.nodeMap.get(item[this.keyField]);
131
+ let currentParent = this.nodeMap.get(item[this.parentKeyField]);
132
+ if (newParent && node && currentParent && currentParent.children) {
133
+ let pos = currentParent.children.findIndex(el => el.item[this.keyField] == item[this.keyField]);
134
+ if (pos > -1) {
135
+ currentParent.children.splice(pos, 1);
136
+ }
137
+ newParent.children = [...(newParent.children ?? []), node];
138
+ if (this.compareFun) {
139
+ newParent.children = newParent.children.sort(this.compareFun);
140
+ }
141
+ }
142
+ }
143
+ extractChildrenDirectories(node, exclusiveValue) {
144
+ if (node.children && node.item[this.keyField] != exclusiveValue) {
145
+ let newNode = {
146
+ item: node.item,
147
+ expand: true,
148
+ children: []
149
+ };
150
+ for (let childNode of node.children) {
151
+ let ncNode = this.extractChildrenDirectories(childNode, exclusiveValue);
152
+ if (ncNode) {
153
+ newNode.children?.push(ncNode);
154
+ }
155
+ }
156
+ return newNode;
157
+ }
158
+ else {
159
+ return;
160
+ }
161
+ }
162
+ extractDirectories(exclusiveValue) {
163
+ let dirNodes = [];
164
+ for (let node of this.nodes) {
165
+ let newNode = this.extractChildrenDirectories(node, exclusiveValue);
166
+ if (newNode) {
167
+ dirNodes.push(newNode);
168
+ }
169
+ }
170
+ return dirNodes;
171
+ }
172
+ }
@@ -68,7 +68,6 @@
68
68
  }
69
69
 
70
70
  const lazyLoad = async (clean: boolean = true) => {
71
- console.log('加载数据...')
72
71
  isBusy = true;
73
72
  try {
74
73
  let result = await lazyLoader?.(filterText, pageNo);
@@ -81,7 +80,6 @@
81
80
  selectedItem = null;
82
81
  filteredList = list;
83
82
  hasMore = result.hasMore;
84
- console.log('加载数据完成')
85
83
  }
86
84
  } finally {
87
85
  isBusy = false;
@@ -157,7 +155,7 @@
157
155
  let searchBox: any;
158
156
 
159
157
  const handleScroll = () => {
160
- const bottom = scrollElement.scrollHeight - scrollElement.scrollTop === scrollElement.clientHeight;
158
+ const bottom = scrollElement.scrollHeight - scrollElement.scrollTop - scrollElement.clientHeight < 2;
161
159
  if (bottom && lazyLoader && !isBusy && hasMore) {
162
160
  fetchMore();
163
161
  }
@@ -167,18 +165,22 @@
167
165
 
168
166
  </script>
169
167
 
170
- <div {style} class="uniface-box {className}" class:round>
171
- {#if title || $$slots['header']}
172
- <slot name="header">
173
- <div class="title" style={boxHeaderStyle}>
174
- <span>{title}</span>
175
- </div>
176
- </slot>
177
- {/if}
178
- {#if readonly === false && (filter || lazyLoader)}
179
- <div class="header-search">
180
- <SearchBox bind:this={searchBox} compact variant="plain" disabled={isBusy} style="width: 100%" bind:value={filterText}
181
- onChange={handleCriteriaChange}/>
168
+ <div {style} class="uniface-listbox {className}" class:round>
169
+ {#if title || $$slots['header'] || (readonly === false && (filter || lazyLoader))}
170
+ <div class="box-header">
171
+ {#if title || $$slots['header']}
172
+ <slot name="header">
173
+ <div class="title" style={boxHeaderStyle}>
174
+ <span>{title}</span>
175
+ </div>
176
+ </slot>
177
+ {/if}
178
+ {#if readonly === false && (filter || lazyLoader)}
179
+ <div class="header-search">
180
+ <SearchBox bind:this={searchBox} compact variant="plain" disabled={isBusy} style="width: 100%" bind:value={filterText}
181
+ onChange={handleCriteriaChange}/>
182
+ </div>
183
+ {/if}
182
184
  </div>
183
185
  {/if}
184
186
  <div class="listbox-content" class:selectable={selectMode==='single'} bind:this={scrollElement} on:scroll={handleScroll}>
@@ -38,7 +38,7 @@
38
38
 
39
39
  </script>
40
40
 
41
- <CommonPicker {displayMode} {variant} {style} {compact} className="multiple" dropDownIcon="uniface-icon-more-horizontal"
41
+ <CommonPicker {displayMode} {variant} {style} {compact} className="multiple" dropDownIcon="icon_google_keyboard_control"
42
42
  canClean={!mandatory && value!=null} autoFit {clean} textValue={text} {readonly} {disabled} iconClickHandler={handleActionIconClick}>
43
43
  <input style="width: 100%" {placeholder} class="text-editor" readonly value={text??''} {disabled}
44
44
  on:keydown on:focus on:click={handleActionIconClick}/>
@@ -114,7 +114,7 @@
114
114
  <div style="top: {top}px; left: {left}px">
115
115
  <div class="title-bar" aria-hidden="true" on:mousedown={handleMouseDown} on:mouseup={handleMouseUp}>
116
116
  <div>
117
- <i class="uniface-icon-x dialog-action-button" aria-hidden="true" on:click={handleCloseClick}></i>
117
+ <i class="icon_google_clear dialog-action-button" aria-hidden="true" on:click={handleCloseClick}></i>
118
118
  </div>
119
119
  </div>
120
120
  <div class="box-content" style="min-height: 40px">
@@ -8,6 +8,7 @@
8
8
  export let items: Array<any>;
9
9
  export let activeItem: any = null;
10
10
  export let style: string = "";
11
+ export let highlights: Array<any> = [];
11
12
  export let itemClickHandler: ItemClickHandler;
12
13
  export let retrieveStatus: RetrieveItemStatus;
13
14
 
@@ -22,6 +23,7 @@
22
23
  <div class="navigator-content">
23
24
  {#each items as item}
24
25
  <div class="uniface-navigator-item {retrieveStatus?.(item)??NavItemStatus.Completed}" class:active={activeItem===item}
26
+ class:highlight={highlights.indexOf(item)>-1}
25
27
  aria-hidden="true" on:click={handleItemClick(item)}>
26
28
  <span>{item.text}</span>
27
29
  </div>
@@ -16,6 +16,7 @@ declare const Navigator: $$__sveltets_2_IsomorphicComponent<{
16
16
  items: Array<any>;
17
17
  activeItem?: any;
18
18
  style?: string;
19
+ highlights?: Array<any>;
19
20
  itemClickHandler: (item: any) => void;
20
21
  retrieveStatus: (item: any) => NavItemStatus;
21
22
  }, {
@@ -48,8 +48,8 @@
48
48
  </script>
49
49
 
50
50
  <CommonEditor {variant} {compact} {style} showActionIcon={value != null && value.length > 0} {clean}>
51
- <div slot='leading-icon'>
52
- <i class="uniface-icon-search"></i>
51
+ <div slot='leading-icon' style="line-height: 16px; font-size: 18px">
52
+ <i class="icon_google_search"></i>
53
53
  </div>
54
54
  <input bind:this={editor} style="width: 100%" bind:value={inputText} {disabled} on:input={handleInput} on:compositionstart={handleCompositionStart}
55
55
  on:compositionend={handleCompositionEnd} {placeholder}/>
@@ -1,17 +1,17 @@
1
1
  <script lang="ts">
2
2
 
3
- import {onMount, onDestroy} from "svelte";
3
+ import {onMount, onDestroy, tick} from "svelte";
4
4
  import {Tween} from 'svelte/motion';
5
5
  import {cubicOut} from 'svelte/easing';
6
6
  import type {TabActionHandler, TabCloseHandler, TabRender} from "./types";
7
7
 
8
8
 
9
-
10
9
  export {className as class};
11
10
  export let simple: boolean = false;
12
11
  export let textField: string = 'text';
13
12
  export let style: string = '';
14
13
  export let tabs: Array<any> = [];
14
+ export let scrollStep = 100;
15
15
  export let closable: boolean | TabActionHandler = false;
16
16
  export let activeTab: any = null;
17
17
  export let tabRender: TabRender = null as unknown as TabRender;
@@ -30,25 +30,26 @@
30
30
  if (activeTab == null && tabs.length > 0) {
31
31
  activeTab = tabs[0];
32
32
  }
33
-
34
33
  checkOverflow();
35
- container.addEventListener('scroll', checkOverflow);
36
34
  window.addEventListener('resize', checkOverflow);
37
- checkOverflow();
35
+ container.addEventListener('scroll', checkOverflow);
38
36
  });
39
37
 
40
38
  onDestroy(() => {
41
39
  window.removeEventListener('resize', checkOverflow);
40
+ container.removeEventListener('scroll', checkOverflow);
42
41
  });
43
42
 
43
+
44
44
  const checkOverflow = () => {
45
45
  if (container) {
46
- if (currentLeft + container.clientWidth > container.scrollWidth) {
46
+ console.log(currentLeft, container.clientWidth, container.scrollWidth);
47
+ if (currentLeft + container.clientWidth >= container.scrollWidth) {
47
48
  currentLeft = container.scrollWidth - container.clientWidth;
48
49
  scrollX.set(currentLeft);
49
50
  }
50
- if (currentLeft > 0 && container.clientWidth <= container.scrollWidth) {
51
- currentLeft = container.scrollWidth - container.clientWidth;
51
+ if (currentLeft > 0 && container.clientWidth >= container.scrollWidth) {
52
+ currentLeft = 0;
52
53
  scrollX.set(currentLeft);
53
54
  }
54
55
  showRight = currentLeft + container.clientWidth < container.scrollWidth;
@@ -56,18 +57,13 @@
56
57
  }
57
58
  };
58
59
 
59
- const scroll = (direction: any) => {
60
- if (container) {
61
- const scrollAmount = 100;
62
- currentLeft = currentLeft + direction * scrollAmount;
63
- if (currentLeft < 0) {
64
- currentLeft = 0;
65
- } else if (currentLeft + container.clientWidth > container.scrollWidth) {
66
- currentLeft = container.scrollWidth - container.clientWidth + 1;
67
- }
68
- scrollX.set(currentLeft);
69
- checkOverflow();
70
- }
60
+ const scroll = (dir: 1 | -1) => {
61
+ const maxScroll = container.scrollWidth - container.clientWidth;
62
+ currentLeft += dir * scrollStep;
63
+ if (currentLeft < 0) currentLeft = 0;
64
+ if (currentLeft > maxScroll) currentLeft = maxScroll;
65
+ scrollX.set(currentLeft);
66
+ checkOverflow();
71
67
  };
72
68
 
73
69
 
@@ -85,18 +81,12 @@
85
81
  tabs.splice(pos, 1);
86
82
  tabs = [...tabs];
87
83
  if (tab == activeTab) {
88
- if (tabs.length > 0) {
89
- if (pos > tabs.length) {
90
- pos = tabs.length - 1;
91
- }
92
- if (pos == -1) {
93
- pos = 0;
94
- }
95
- activeTab = tabs[pos];
96
- } else {
97
- activeTab = null;
84
+ if (pos >= tabs.length) {
85
+ pos = tabs.length - 1;
98
86
  }
87
+ activeTab = tabs[pos];
99
88
  }
89
+ await tick();
100
90
  checkOverflow();
101
91
  }
102
92
  }
@@ -107,7 +97,7 @@
107
97
  const reloadTab = (tab: any) => (e: MouseEvent) => {
108
98
  reloadHandler?.(tab);
109
99
  }
110
-
100
+ //
111
101
 
112
102
  </script>
113
103
  <div class="uniface-tab-panel {className}" {style}>
@@ -123,14 +113,14 @@
123
113
  {#if tabRender != null}
124
114
  <svelte:component this={tabRender} {tab} closeTab={closeHandler != null ? closeTab(tab) : null}
125
115
  reloadTab={reloadHandler != null ? reloadTab(tab) : null}
126
- closable={closable === true || (typeof (closable) == "function" && closable(tab))} />
116
+ closable={closable === true || (typeof (closable) == "function" && closable(tab))}/>
127
117
  {:else}
128
118
  <span>{tab[textField]}</span>
129
119
  {#if reloadHandler != null}
130
120
  <i class="icon_google_refresh tab-refresh" on:click={reloadTab(tab)} aria-hidden="true"></i>
131
121
  {/if}
132
- {#if closable === true || (typeof (closable) == "function" && closable(tab))}
133
- <i class="icon_google_clear tab-action" on:click={closeTab(tab)} aria-hidden="true"></i>
122
+ {#if tabs.length > 1 && (closable === true || (typeof (closable) == "function" && closable(tab)))}
123
+ <i class="icon_google_clear tab-action" on:click|stopPropagation={closeTab(tab)} aria-hidden="true"></i>
134
124
  {/if}
135
125
  {/if}
136
126
  </div>
@@ -23,6 +23,7 @@ declare const Tabs: $$__sveltets_2_IsomorphicComponent<$$__sveltets_2_PropsWithC
23
23
  textField?: string;
24
24
  style?: string;
25
25
  tabs?: Array<any>;
26
+ scrollStep?: number;
26
27
  closable?: boolean | TabActionHandler;
27
28
  activeTab?: any;
28
29
  tabRender?: TabRender;
@@ -20,8 +20,10 @@
20
20
 
21
21
  </script>
22
22
  <div class="uniface-tag" {style}>
23
- <div class="{size} {variant} {className} {colorClass}" class:removable={removable} >
23
+ <div class="{size} {variant} {className} {colorClass}" class:removable={removable}>
24
24
  <span>{text}</span>
25
- <Icon name="icon_google_clear" clickable class="uniface-remove-icon" onClick={removeHandler}/>
25
+ {#if removable}
26
+ <Icon name="icon_google_clear" class="uniface-remove-icon" onClick={removeHandler}/>
27
+ {/if}
26
28
  </div>
27
29
  </div>
@@ -28,7 +28,7 @@
28
28
 
29
29
 
30
30
  </script>
31
- <CommonEditor {style} {value} type="password" {readonly} {variant} {compact} class={className}>
31
+ <CommonEditor {style} {value} {readonly} {variant} {compact} class={className}>
32
32
  {#if type=="password"}
33
33
  <input type="password" style="flex: 1 1 auto" bind:value={value} {disabled} {...input$}
34
34
  on:blur on:focus />
@@ -36,9 +36,9 @@
36
36
  <input type="text" style="flex: 1 1 auto" bind:value={value} {disabled} {...input$}
37
37
  on:blur on:focus />
38
38
  {/if}
39
- <div slot="trailing-icon" class="editor-embed-icon password-icon">
39
+ <div slot="trailing-icon" class="editor-embed-icon">
40
40
  {#if (!readonly && !disabled)}
41
- <i class={type == "password" ? "uniface-icon-eye" : "uniface-icon-eye-off"} on:click={toggleType}></i>
41
+ <i class={type == "password" ? "icon_google_remove_red_eye" : "icon_google_visibility_off"} on:click={toggleType}></i>
42
42
  {/if}
43
43
  </div>
44
44
  </CommonEditor>