@ticatec/uniface-element 5.0.1 → 5.0.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.
- package/README.md +29 -54
- package/README_CN.md +37 -57
- package/dist/base-calendar/CalendarBase.svelte +29 -6
- package/dist/base-calendar/CalendarBase.svelte.d.ts +4 -0
- package/dist/base-calendar/MonthPickupPanel.svelte +19 -6
- package/dist/base-calendar/MonthPickupPanel.svelte.d.ts +1 -1
- package/dist/base-calendar/MonthlyCalendar.svelte +18 -2
- package/dist/base-calendar/YearPickupPanel.svelte +24 -6
- package/dist/base-calendar/YearPickupPanel.svelte.d.ts +1 -1
- package/dist/composite/pagination_panel/PaginationPanel.svelte +2 -0
- package/dist/data_display/card/CommonCardActionBar.svelte +34 -14
- package/dist/data_display/concise_data_table/Column.d.ts +6 -0
- package/dist/data_display/concise_data_table/ConciseListTable.svelte +4 -3
- package/dist/data_display/concise_data_table/DataCell.svelte +3 -3
- package/dist/data_display/list_box/ListBox.svelte +90 -15
- package/dist/data_display/list_box/ListBox.svelte.d.ts +4 -0
- package/dist/data_display/tree_view/TreeNodeView.svelte +25 -4
- package/dist/data_table/DataTable.svelte +5 -5
- package/dist/data_table/DataTable.svelte.d.ts +36 -16
- package/dist/data_table/lib/ActionsColumn.d.ts +2 -2
- package/dist/data_table/lib/DataColumn.d.ts +7 -1
- package/dist/data_table/lib/RowAction.d.ts +5 -5
- package/dist/data_table/parts/FixedHeaderPanel.svelte +18 -3
- package/dist/data_table/parts/FixedRow.svelte +10 -1
- package/dist/data_table/parts/HrefCell.svelte +1 -1
- package/dist/data_table/parts/TableHeaderPanel.svelte +18 -2
- package/dist/data_table/parts/TextCell.svelte +2 -2
- package/dist/form/attachment_files/AttachmentEditor.svelte +9 -9
- package/dist/form/attachment_files/FileRender.svelte +1 -1
- package/dist/form/attachment_files/FileUploadPanel.svelte +5 -1
- package/dist/form/cascade_options_select/CascadeOptionSelect.svelte +10 -2
- package/dist/form/cascade_options_select/OptionsBox.svelte +48 -2
- package/dist/form/color_picker/ColorPickerPanel.svelte +23 -20
- package/dist/form/color_picker/ColorPickerPanel.svelte.d.ts +5 -18
- package/dist/form/common_editor/CommonEditor.svelte +18 -4
- package/dist/form/common_editor/CommonPicker.svelte +11 -4
- package/dist/form/common_editor/CommonPopupEditor.svelte +8 -1
- package/dist/form/common_range_editor/CommonRangeEditor.svelte +11 -2
- package/dist/form/date_picker/DatePicker.svelte +1 -1
- package/dist/form/date_picker/DateTimePicker.svelte +1 -1
- package/dist/form/date_picker/ScrollBar.svelte +20 -12
- package/dist/form/date_picker/ScrollBar.svelte.d.ts +4 -18
- package/dist/form/date_range/DateRangeEditor.svelte +11 -3
- package/dist/form/group_box/group-check-box/GroupCheckBox.svelte +6 -1
- package/dist/form/group_box/group-radio-box/GroupRadioBox.svelte +6 -1
- package/dist/form/image-files/ImageFilesField.svelte +51 -7
- package/dist/form/image-files/ImagePreview.svelte +8 -2
- package/dist/form/image-files/ImageRender.svelte +69 -11
- package/dist/form/input_options_select/InputOptionsSelect.svelte +10 -2
- package/dist/form/lookup_editor/LookupEditor.svelte +9 -2
- package/dist/form/options_multi_select/OptionsMultiSelect.svelte +19 -3
- package/dist/form/options_select/OptionsSelect.svelte +15 -6
- package/dist/form/options_select/OptionsSelect.svelte.d.ts +39 -17
- package/dist/form/prompts_text_editor/PromptsTextEditor.svelte +10 -2
- package/dist/form/switch/Switch.svelte +4 -4
- package/dist/form/unit-number-editor/UnitNumberEditor.svelte +10 -2
- package/dist/general/button/Button.svelte +3 -0
- package/dist/general/button/Button.svelte.d.ts +1 -0
- package/dist/general/button/IconButton.svelte +3 -1
- package/dist/general/button/IconButton.svelte.d.ts +1 -0
- package/dist/general/button/TextButton.svelte +3 -0
- package/dist/general/button/TextButton.svelte.d.ts +1 -0
- package/dist/general/icon/Icon.svelte +18 -1
- package/dist/general/tag/Tag.svelte +9 -1
- package/dist/navigation/nav_menu/NavigatorMenu.svelte +2 -2
- package/dist/navigation/nav_menu/NavigatorMenuItem.svelte +10 -1
- package/dist/navigation/navigator/Navigator.svelte +17 -17
- package/dist/navigation/page-stack/PageStack.svelte +160 -0
- package/dist/navigation/page-stack/PageStack.svelte.d.ts +24 -0
- package/dist/navigation/page-stack/PageStackContext.d.ts +25 -0
- package/dist/navigation/page-stack/PageStackContext.js +12 -0
- package/dist/navigation/page-stack/PageStackFrame.svelte +24 -0
- package/dist/navigation/page-stack/PageStackFrame.svelte.d.ts +11 -0
- package/dist/navigation/page-stack/README.md +154 -0
- package/dist/navigation/page-stack/README_CN.md +154 -0
- package/dist/navigation/page-stack/index.d.ts +6 -0
- package/dist/navigation/page-stack/index.js +4 -0
- package/dist/navigation/pagination/Pagination.svelte +114 -14
- package/dist/navigation/tabs/Tabs.svelte +42 -10
- package/dist/navigation/tabs/Tabs.svelte.d.ts +2 -2
- package/dist/overlay/common/FloatingPanel.svelte +3 -11
- package/dist/overlay/common/FullscreenOverlay.svelte +27 -3
- package/dist/overlay/common/FullscreenOverlay.svelte.d.ts +6 -27
- package/dist/overlay/common/ModalPopover.svelte +18 -2
- package/dist/overlay/common/Popover.svelte +56 -57
- package/dist/overlay/common/Popover.svelte.d.ts +1 -5
- package/dist/overlay/common/escapeClose.d.ts +28 -0
- package/dist/overlay/common/escapeClose.js +47 -0
- package/dist/overlay/common/focusTrap.d.ts +8 -0
- package/dist/overlay/common/focusTrap.js +83 -0
- package/dist/overlay/common/mountSingleton.d.ts +27 -0
- package/dist/overlay/common/mountSingleton.js +45 -0
- package/dist/overlay/common/outsideClick.d.ts +28 -0
- package/dist/overlay/common/outsideClick.js +20 -0
- package/dist/overlay/common/scrollLock.d.ts +8 -0
- package/dist/overlay/common/scrollLock.js +49 -0
- package/dist/overlay/context-menu/ContextMenu.svelte.js +2 -15
- package/dist/overlay/context-menu/ContextMenuPanel.svelte +13 -1
- package/dist/overlay/dialog/Dialog.svelte +46 -29
- package/dist/overlay/dialog/DialogManager.svelte.js +7 -9
- package/dist/overlay/drawer/Drawer.svelte +30 -3
- package/dist/overlay/indicator/Indicator.svelte.js +2 -15
- package/dist/overlay/indicator/IndicatorPanel.svelte +4 -1
- package/dist/overlay/message-box/MessageBox.svelte.js +2 -15
- package/dist/overlay/message-box/MessageBoxPanel.svelte +19 -3
- package/dist/overlay/toast/Toast.svelte.js +2 -15
- package/dist/overlay/toast/ToastPanel.svelte +1 -1
- package/dist/overlay/tooltip/Tooltip.svelte +1 -1
- package/dist/ticatec-uniface-web.css +102 -7
- package/dist/types.d.ts +4 -3
- package/docs/components/README.md +133 -0
- package/docs/components/accordion/README.md +60 -0
- package/docs/components/accordion/example.svelte +7 -0
- package/docs/components/action-bar/README.md +114 -0
- package/docs/components/action-bar/example.svelte +7 -0
- package/docs/components/app-top-bar/README.md +60 -0
- package/docs/components/app-top-bar/example.svelte +9 -0
- package/docs/components/attachment-files/README.md +332 -0
- package/docs/components/attachment-files/example.svelte +16 -0
- package/docs/components/box/README.md +63 -0
- package/docs/components/box/example.svelte +10 -0
- package/docs/components/breadcrumbs/README.md +86 -0
- package/docs/components/breadcrumbs/example.svelte +11 -0
- package/docs/components/button/README.md +103 -0
- package/docs/components/button/example.svelte +10 -0
- package/docs/components/card/README.md +113 -0
- package/docs/components/card/example.svelte +10 -0
- package/docs/components/cascade-options-select/README.md +162 -0
- package/docs/components/cascade-options-select/example.svelte +18 -0
- package/docs/components/checkbox/README.md +103 -0
- package/docs/components/checkbox/example.svelte +15 -0
- package/docs/components/classic-layout/README.md +76 -0
- package/docs/components/classic-layout/example.svelte +16 -0
- package/docs/components/color-picker/README.md +132 -0
- package/docs/components/color-picker/example.svelte +16 -0
- package/docs/components/columns-layout/README.md +70 -0
- package/docs/components/columns-layout/example.svelte +12 -0
- package/docs/components/common-dialog/README.md +109 -0
- package/docs/components/common-dialog/example.svelte +12 -0
- package/docs/components/concise-data-table/README.md +307 -0
- package/docs/components/concise-data-table/example.svelte +16 -0
- package/docs/components/context-menu/README.md +99 -0
- package/docs/components/context-menu/example.svelte +10 -0
- package/docs/components/criteria-field/README.md +69 -0
- package/docs/components/criteria-field/example.svelte +9 -0
- package/docs/components/data-table/README.md +365 -0
- package/docs/components/data-table/example.svelte +23 -0
- package/docs/components/date-picker/README.md +136 -0
- package/docs/components/date-picker/example.svelte +16 -0
- package/docs/components/date-range/README.md +122 -0
- package/docs/components/date-range/example.svelte +15 -0
- package/docs/components/date-time-picker/README.md +142 -0
- package/docs/components/date-time-picker/example.svelte +16 -0
- package/docs/components/dialog/README.md +174 -0
- package/docs/components/dialog/example.svelte +13 -0
- package/docs/components/dialog-board/README.md +41 -0
- package/docs/components/dialog-board/example.svelte +5 -0
- package/docs/components/drawer/README.md +70 -0
- package/docs/components/drawer/example.svelte +12 -0
- package/docs/components/flex-form/README.md +55 -0
- package/docs/components/flex-form/example.svelte +7 -0
- package/docs/components/flex-row-form/README.md +56 -0
- package/docs/components/flex-row-form/example.svelte +7 -0
- package/docs/components/form-field/README.md +84 -0
- package/docs/components/form-field/example.svelte +10 -0
- package/docs/components/full-screen-overlay/README.md +66 -0
- package/docs/components/full-screen-overlay/example.svelte +11 -0
- package/docs/components/grid-form/README.md +75 -0
- package/docs/components/grid-form/example.svelte +9 -0
- package/docs/components/group-check-box/README.md +147 -0
- package/docs/components/group-check-box/example.svelte +21 -0
- package/docs/components/group-radio-box/README.md +144 -0
- package/docs/components/group-radio-box/example.svelte +21 -0
- package/docs/components/header-layout/README.md +65 -0
- package/docs/components/header-layout/example.svelte +12 -0
- package/docs/components/icon/README.md +87 -0
- package/docs/components/icon/example.svelte +9 -0
- package/docs/components/icon-button/README.md +91 -0
- package/docs/components/icon-button/example.svelte +10 -0
- package/docs/components/image-files/README.md +174 -0
- package/docs/components/image-files/example.svelte +19 -0
- package/docs/components/indicator/README.md +53 -0
- package/docs/components/indicator/example.svelte +14 -0
- package/docs/components/input-options-select/README.md +163 -0
- package/docs/components/input-options-select/example.svelte +16 -0
- package/docs/components/list-box/ListItem.svelte +14 -0
- package/docs/components/list-box/README.md +221 -0
- package/docs/components/list-box/example.svelte +61 -0
- package/docs/components/lookup-editor/README.md +137 -0
- package/docs/components/lookup-editor/example.svelte +16 -0
- package/docs/components/memo-editor/README.md +143 -0
- package/docs/components/memo-editor/example.svelte +16 -0
- package/docs/components/message-box/README.md +68 -0
- package/docs/components/message-box/example.svelte +10 -0
- package/docs/components/navigator/README.md +75 -0
- package/docs/components/navigator/example.svelte +13 -0
- package/docs/components/navigator-menu/README.md +113 -0
- package/docs/components/navigator-menu/example.svelte +10 -0
- package/docs/components/number-editor/README.md +144 -0
- package/docs/components/number-editor/example.svelte +16 -0
- package/docs/components/number-range/README.md +116 -0
- package/docs/components/number-range/example.svelte +15 -0
- package/docs/components/options-multi-select/README.md +161 -0
- package/docs/components/options-multi-select/example.svelte +20 -0
- package/docs/components/options-select/README.md +160 -0
- package/docs/components/options-select/example.svelte +21 -0
- package/docs/components/page/README.md +77 -0
- package/docs/components/page/example.svelte +10 -0
- package/docs/components/pagination/README.md +88 -0
- package/docs/components/pagination/example.svelte +10 -0
- package/docs/components/pagination-panel/README.md +120 -0
- package/docs/components/pagination-panel/example.svelte +16 -0
- package/docs/components/popup-hint/README.md +44 -0
- package/docs/components/popup-hint/example.svelte +5 -0
- package/docs/components/progress-bar/README.md +64 -0
- package/docs/components/progress-bar/example.svelte +8 -0
- package/docs/components/progress-step-bar/README.md +93 -0
- package/docs/components/progress-step-bar/example.svelte +7 -0
- package/docs/components/prompts-text-editor/README.md +146 -0
- package/docs/components/prompts-text-editor/example.svelte +17 -0
- package/docs/components/radio-button/README.md +121 -0
- package/docs/components/radio-button/example.svelte +18 -0
- package/docs/components/rows-layout/README.md +70 -0
- package/docs/components/rows-layout/example.svelte +12 -0
- package/docs/components/search-box/README.md +136 -0
- package/docs/components/search-box/example.svelte +16 -0
- package/docs/components/separator/README.md +44 -0
- package/docs/components/separator/example.svelte +7 -0
- package/docs/components/sidebar-layout/README.md +65 -0
- package/docs/components/sidebar-layout/example.svelte +12 -0
- package/docs/components/split/README.md +48 -0
- package/docs/components/split/example.svelte +8 -0
- package/docs/components/switch/README.md +77 -0
- package/docs/components/switch/example.svelte +11 -0
- package/docs/components/tabs/README.md +127 -0
- package/docs/components/tabs/example.svelte +22 -0
- package/docs/components/tag/README.md +63 -0
- package/docs/components/tag/example.svelte +8 -0
- package/docs/components/text-button/README.md +90 -0
- package/docs/components/text-button/example.svelte +9 -0
- package/docs/components/text-editor/README.md +147 -0
- package/docs/components/text-editor/example.svelte +16 -0
- package/docs/components/time-editor/README.md +130 -0
- package/docs/components/time-editor/example.svelte +16 -0
- package/docs/components/toast/README.md +52 -0
- package/docs/components/toast/example.svelte +9 -0
- package/docs/components/tooltip/README.md +44 -0
- package/docs/components/tooltip/example.svelte +5 -0
- package/docs/components/transfer/README.md +109 -0
- package/docs/components/transfer/example.svelte +13 -0
- package/docs/components/tree-view/README.md +163 -0
- package/docs/components/tree-view/example.svelte +26 -0
- package/docs/components/unit-number-editor/README.md +192 -0
- package/docs/components/unit-number-editor/example.svelte +18 -0
- package/package.json +15 -7
|
@@ -26,6 +26,13 @@
|
|
|
26
26
|
clickEnable = true;
|
|
27
27
|
}
|
|
28
28
|
};
|
|
29
|
+
|
|
30
|
+
const handleActionKeyDown = (action: CardAction) => (e: KeyboardEvent) => {
|
|
31
|
+
if (e.key === 'Enter' || e.key === ' ') {
|
|
32
|
+
e.preventDefault();
|
|
33
|
+
handleActionClick(action)(e as unknown as MouseEvent);
|
|
34
|
+
}
|
|
35
|
+
};
|
|
29
36
|
</script>
|
|
30
37
|
|
|
31
38
|
<div class="card-action-bar">
|
|
@@ -34,18 +41,21 @@
|
|
|
34
41
|
<i class="action-icon {action.icon}"
|
|
35
42
|
class:disabled={action.disabled}
|
|
36
43
|
data-tip={action.disabled ? undefined : action.tooltip}
|
|
37
|
-
|
|
44
|
+
role="button" tabindex={action.disabled ? -1 : 0}
|
|
45
|
+
aria-disabled={action.disabled}
|
|
46
|
+
aria-label={action.tooltip}
|
|
38
47
|
onclick={handleActionClick(action)}
|
|
48
|
+
onkeydown={handleActionKeyDown(action)}
|
|
39
49
|
></i>
|
|
40
50
|
{:else if action.img}
|
|
41
|
-
<
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
51
|
+
<button type="button" class="card-action-img-btn"
|
|
52
|
+
class:disabled={action.disabled}
|
|
53
|
+
disabled={action.disabled}
|
|
54
|
+
data-tip={action.disabled ? undefined : action.tooltip}
|
|
55
|
+
aria-label={action.tooltip}
|
|
56
|
+
onclick={handleActionClick(action)}>
|
|
57
|
+
<img class="card-action-img" alt="" src={action.img}/>
|
|
58
|
+
</button>
|
|
49
59
|
{/if}
|
|
50
60
|
|
|
51
61
|
{/each}
|
|
@@ -89,20 +99,30 @@
|
|
|
89
99
|
}
|
|
90
100
|
|
|
91
101
|
|
|
92
|
-
.card-action-img {
|
|
93
|
-
|
|
94
|
-
|
|
102
|
+
.card-action-img-btn {
|
|
103
|
+
background: none;
|
|
104
|
+
border: none;
|
|
105
|
+
padding: 0;
|
|
95
106
|
cursor: pointer;
|
|
107
|
+
display: inline-flex;
|
|
96
108
|
}
|
|
97
109
|
|
|
98
|
-
.card-action-img:active {
|
|
110
|
+
.card-action-img-btn:active {
|
|
99
111
|
position: relative;
|
|
100
112
|
top: 1px;
|
|
101
113
|
}
|
|
102
114
|
|
|
103
|
-
.card-action-img.disabled {
|
|
115
|
+
.card-action-img-btn.disabled {
|
|
104
116
|
cursor: not-allowed;
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
.card-action-img-btn.disabled .card-action-img {
|
|
105
120
|
filter: grayscale(100%);
|
|
106
121
|
}
|
|
107
122
|
|
|
123
|
+
.card-action-img {
|
|
124
|
+
width: var(--action-image-size, var(--uniface-action-image-size));
|
|
125
|
+
height: var(--action-image-size, var(--uniface-action-image-size));
|
|
126
|
+
}
|
|
127
|
+
|
|
108
128
|
</style>
|
|
@@ -5,5 +5,11 @@ export default interface Column {
|
|
|
5
5
|
align?: "left" | "center" | "right";
|
|
6
6
|
weight?: number;
|
|
7
7
|
formatter?: (value: any) => string;
|
|
8
|
+
renderHTML?: boolean;
|
|
9
|
+
/**
|
|
10
|
+
* @deprecated Use renderHTML instead; "escapeHTML" reads as "this escapes HTML"
|
|
11
|
+
* when it actually means the opposite — true renders raw, trusted HTML. Still
|
|
12
|
+
* honored as a fallback for existing callers.
|
|
13
|
+
*/
|
|
8
14
|
escapeHTML?: boolean;
|
|
9
15
|
}
|
|
@@ -215,7 +215,8 @@
|
|
|
215
215
|
overflow: hidden;
|
|
216
216
|
display: flex;
|
|
217
217
|
flex-direction: column;
|
|
218
|
-
color: var(--uniface-concise-table-
|
|
218
|
+
background-color: var(--uniface-concise-table-color-surface);
|
|
219
|
+
color: var(--uniface-concise-table-color);
|
|
219
220
|
}
|
|
220
221
|
:global .uniface-concise-datatable .table-container {
|
|
221
222
|
display: flex;
|
|
@@ -237,7 +238,7 @@
|
|
|
237
238
|
padding: 2px 4px;
|
|
238
239
|
}
|
|
239
240
|
:global .uniface-concise-datatable .table-header {
|
|
240
|
-
background-color:
|
|
241
|
+
background-color: var(--uniface-concise-table-header-surface);
|
|
241
242
|
padding: 0;
|
|
242
243
|
flex-shrink: 0;
|
|
243
244
|
z-index: 10;
|
|
@@ -265,7 +266,7 @@
|
|
|
265
266
|
color: var(--uniface-concise-table-row-alter-color, #374151);
|
|
266
267
|
}
|
|
267
268
|
:global .uniface-concise-datatable .table-body-container .table-row:hover {
|
|
268
|
-
background-color:
|
|
269
|
+
background-color: var(--uniface-concise-table-row-hover-bg);
|
|
269
270
|
}
|
|
270
271
|
:global .uniface-concise-datatable .table-body-container.auto-scroll {
|
|
271
272
|
overflow-y: hidden;
|
|
@@ -14,9 +14,9 @@
|
|
|
14
14
|
}: Props = $props();
|
|
15
15
|
|
|
16
16
|
let text = $derived(column.formatter ? column.formatter(data[column.field]) : (data[column.field] ?? ''));
|
|
17
|
-
// Safe by default: HTML rendering is opt-in only (
|
|
18
|
-
// semantics of the data_table component's DataColumn#
|
|
19
|
-
let renderAsHtml = $derived(column.escapeHTML === true);
|
|
17
|
+
// Safe by default: HTML rendering is opt-in only (renderHTML: true), matching the
|
|
18
|
+
// semantics of the data_table component's DataColumn#renderHTML flag.
|
|
19
|
+
let renderAsHtml = $derived((column.renderHTML ?? column.escapeHTML) === true);
|
|
20
20
|
</script>
|
|
21
21
|
|
|
22
22
|
<div class="data-cell col_{idx}" role="cell">
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
<script lang="ts">
|
|
2
|
-
import {tick} from "svelte";
|
|
2
|
+
import {tick, onDestroy, untrack} from "svelte";
|
|
3
3
|
import SearchBox from "../../form/search_box"
|
|
4
4
|
import type {FunFilter} from "../../types";
|
|
5
5
|
import type {ListLazyLoader} from "../../types";
|
|
@@ -22,6 +22,10 @@
|
|
|
22
22
|
selectedList?: Array<any>;
|
|
23
23
|
class?: string;
|
|
24
24
|
item$props?: any;
|
|
25
|
+
onchange?: OnSelectChange;
|
|
26
|
+
/**
|
|
27
|
+
* @deprecated 请使用 onchange;仍受支持以兼容旧调用。
|
|
28
|
+
*/
|
|
25
29
|
onSelectChange?: OnSelectChange;
|
|
26
30
|
onItemDblClick?: OnItemDblClick;
|
|
27
31
|
onItemClick?: OnItemClick;
|
|
@@ -45,6 +49,7 @@
|
|
|
45
49
|
selectedList = $bindable([]),
|
|
46
50
|
class: className,
|
|
47
51
|
item$props,
|
|
52
|
+
onchange,
|
|
48
53
|
onSelectChange,
|
|
49
54
|
onItemDblClick,
|
|
50
55
|
onItemClick,
|
|
@@ -83,12 +88,19 @@
|
|
|
83
88
|
localFilterText = filterText ?? '';
|
|
84
89
|
});
|
|
85
90
|
|
|
91
|
+
// onchange is the canonical name; onSelectChange is kept as a deprecated
|
|
92
|
+
// alias and fired alongside it for backward compatibility.
|
|
93
|
+
const notifySelectChange = (item: any) => {
|
|
94
|
+
onchange?.(item);
|
|
95
|
+
onSelectChange?.(item);
|
|
96
|
+
};
|
|
97
|
+
|
|
86
98
|
const handleItemClick = (item: any) => (e: MouseEvent) => {
|
|
87
99
|
if (readonly == false) {
|
|
88
100
|
if (selectMode == 'single') {
|
|
89
101
|
if (localSelectedItem != item) {
|
|
90
102
|
localSelectedItem = item;
|
|
91
|
-
|
|
103
|
+
notifySelectChange(item);
|
|
92
104
|
}
|
|
93
105
|
} else {
|
|
94
106
|
onItemClick?.(item);
|
|
@@ -102,6 +114,13 @@
|
|
|
102
114
|
}
|
|
103
115
|
}
|
|
104
116
|
|
|
117
|
+
const handleItemKeyDown = (item: any) => (e: KeyboardEvent) => {
|
|
118
|
+
if (e.key === 'Enter' || e.key === ' ') {
|
|
119
|
+
e.preventDefault();
|
|
120
|
+
handleItemClick(item)(e as unknown as MouseEvent);
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
|
|
105
124
|
const doFilter = () => {
|
|
106
125
|
const newList: Array<any> = [];
|
|
107
126
|
list?.forEach(item => {
|
|
@@ -115,14 +134,23 @@
|
|
|
115
134
|
filteredList = newList;
|
|
116
135
|
if (selectMode == 'single') {
|
|
117
136
|
localSelectedItem = null;
|
|
118
|
-
|
|
137
|
+
notifySelectChange(null);
|
|
119
138
|
}
|
|
120
139
|
}
|
|
121
140
|
|
|
141
|
+
// Guards against out-of-order responses: only the most recently issued
|
|
142
|
+
// request is allowed to write its result into component state.
|
|
143
|
+
let lazyLoadSeq = 0;
|
|
144
|
+
let destroyed = false;
|
|
145
|
+
|
|
122
146
|
const lazyLoad = async (clean: boolean = true) => {
|
|
147
|
+
const seq = ++lazyLoadSeq;
|
|
123
148
|
isBusy = true;
|
|
124
149
|
try {
|
|
125
150
|
let result = await lazyLoader?.(localFilterText, pageNo);
|
|
151
|
+
if (destroyed || seq !== lazyLoadSeq) {
|
|
152
|
+
return;
|
|
153
|
+
}
|
|
126
154
|
if (result) {
|
|
127
155
|
if (clean) {
|
|
128
156
|
list = result.list;
|
|
@@ -133,8 +161,17 @@
|
|
|
133
161
|
filteredList = list ?? [];
|
|
134
162
|
hasMore = result.hasMore;
|
|
135
163
|
}
|
|
164
|
+
} catch (e) {
|
|
165
|
+
if (!clean) {
|
|
166
|
+
// Failed page-2+ fetch: undo the optimistic pageNo increment so a
|
|
167
|
+
// retry (e.g. re-triggered by scroll) re-requests the same page.
|
|
168
|
+
pageNo--;
|
|
169
|
+
}
|
|
170
|
+
throw e;
|
|
136
171
|
} finally {
|
|
137
|
-
|
|
172
|
+
if (!destroyed && seq === lazyLoadSeq) {
|
|
173
|
+
isBusy = false;
|
|
174
|
+
}
|
|
138
175
|
}
|
|
139
176
|
}
|
|
140
177
|
|
|
@@ -148,12 +185,26 @@
|
|
|
148
185
|
interval = null;
|
|
149
186
|
pageNo = 1;
|
|
150
187
|
scrollElement.scrollTop = 0;
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
188
|
+
try {
|
|
189
|
+
await lazyLoad();
|
|
190
|
+
} catch (e) {
|
|
191
|
+
console.error('ListBox: failed to reload items', e);
|
|
192
|
+
}
|
|
193
|
+
if (!destroyed) {
|
|
194
|
+
await tick();
|
|
195
|
+
searchBox?.focus();
|
|
196
|
+
}
|
|
154
197
|
}
|
|
155
198
|
}
|
|
156
199
|
|
|
200
|
+
onDestroy(() => {
|
|
201
|
+
destroyed = true;
|
|
202
|
+
if (interval != null) {
|
|
203
|
+
clearInterval(interval);
|
|
204
|
+
interval = null;
|
|
205
|
+
}
|
|
206
|
+
});
|
|
207
|
+
|
|
157
208
|
const handleCriteriaChange = () => {
|
|
158
209
|
if (lazyLoader != null) {
|
|
159
210
|
if (interval == null) {
|
|
@@ -192,15 +243,27 @@
|
|
|
192
243
|
}
|
|
193
244
|
}
|
|
194
245
|
|
|
246
|
+
// untrack: lazyLoad() reads pageNo/isBusy/localFilterText synchronously
|
|
247
|
+
// before its first await. Without untrack, those reads register as
|
|
248
|
+
// dependencies of *this* effect, so a later change to pageNo (e.g. from
|
|
249
|
+
// fetchMore) would re-run this effect and fire a second, unrelated
|
|
250
|
+
// "initial load" — this must only re-run when the lazyLoader prop itself
|
|
251
|
+
// changes.
|
|
195
252
|
$effect(() => {
|
|
196
253
|
if (lazyLoader != null) {
|
|
197
|
-
|
|
254
|
+
untrack(() => {
|
|
255
|
+
lazyLoad().catch((e) => console.error('ListBox: failed to load items', e));
|
|
256
|
+
});
|
|
198
257
|
}
|
|
199
258
|
});
|
|
200
259
|
|
|
201
260
|
const fetchMore = async () => {
|
|
202
261
|
pageNo++;
|
|
203
|
-
|
|
262
|
+
try {
|
|
263
|
+
await lazyLoad(false);
|
|
264
|
+
} catch (e) {
|
|
265
|
+
console.error('ListBox: failed to load more items', e);
|
|
266
|
+
}
|
|
204
267
|
}
|
|
205
268
|
|
|
206
269
|
const handleScroll = () => {
|
|
@@ -232,20 +295,25 @@
|
|
|
232
295
|
onchange={handleCriteriaChange}/>
|
|
233
296
|
</div>
|
|
234
297
|
{/if}
|
|
235
|
-
<div class="listbox-content" class:selectable={selectMode==='single'} bind:this={scrollElement} onscroll={handleScroll}
|
|
298
|
+
<div class="listbox-content" class:selectable={selectMode==='single'} bind:this={scrollElement} onscroll={handleScroll}
|
|
299
|
+
role="listbox" aria-multiselectable={selectMode === 'multiple' ? true : undefined}>
|
|
236
300
|
{#if filteredList && ItemRender}
|
|
237
301
|
{#each filteredList as item}
|
|
238
302
|
{#if selectMode === "multiple"}
|
|
239
|
-
<div class="listview-item" style="display: flex; flex-direction: row; align-items: center; gap: 8px"
|
|
303
|
+
<div class="listview-item" style="display: flex; flex-direction: row; align-items: center; gap: 8px"
|
|
304
|
+
role="option" aria-selected={localSelectedList.indexOf(item) > -1}>
|
|
240
305
|
<CheckBox style="flex: 0 0 auto; margin-left: 8px" {readonly} value={localSelectedList.indexOf(item) > -1}
|
|
241
306
|
onchange={handleSelectionChanged(item)}/>
|
|
242
|
-
<div style="flex: 1 1 auto; cursor: pointer"
|
|
307
|
+
<div style="flex: 1 1 auto; cursor: pointer" role="button" tabindex="0"
|
|
308
|
+
onclick={handleSelectionChanged(item)}
|
|
309
|
+
onkeydown={(e) => { if (e.key === 'Enter' || e.key === ' ') { e.preventDefault(); handleSelectionChanged(item)(); } }}>
|
|
243
310
|
<ItemRender {readonly} {item} {...item$props}/>
|
|
244
311
|
</div>
|
|
245
312
|
</div>
|
|
246
313
|
{:else }
|
|
247
|
-
<div class="listview-item" class:selected={item===localSelectedItem}
|
|
248
|
-
|
|
314
|
+
<div class="listview-item" class:selected={item===localSelectedItem}
|
|
315
|
+
role="option" aria-selected={item===localSelectedItem} tabindex="0"
|
|
316
|
+
ondblclick={handleItemDblClick(item)} onclick={handleItemClick(item)} onkeydown={handleItemKeyDown(item)}>
|
|
249
317
|
<ItemRender {item} {readonly} selected={item===localSelectedItem}
|
|
250
318
|
{...item$props}/>
|
|
251
319
|
</div>
|
|
@@ -279,6 +347,8 @@
|
|
|
279
347
|
box-sizing: border-box;
|
|
280
348
|
user-select: none;
|
|
281
349
|
border: 1px solid var(--uniface-list-box-border-color);
|
|
350
|
+
background-color: var(--uniface-list-box-color-surface);
|
|
351
|
+
color: var(--uniface-list-box-color);
|
|
282
352
|
}
|
|
283
353
|
|
|
284
354
|
.uniface-listbox.round {
|
|
@@ -291,7 +361,7 @@
|
|
|
291
361
|
position: absolute;
|
|
292
362
|
top: 0;
|
|
293
363
|
left: 0;
|
|
294
|
-
background-color:
|
|
364
|
+
background-color: var(--uniface-color-overlay-mask-surface);
|
|
295
365
|
}
|
|
296
366
|
|
|
297
367
|
.box-header {
|
|
@@ -350,4 +420,9 @@
|
|
|
350
420
|
.listbox-content.selectable .listview-item.selected {
|
|
351
421
|
background-color: var(--uniface-list-box-selected-surface);
|
|
352
422
|
}
|
|
423
|
+
|
|
424
|
+
.listbox-content .listview-item:focus-visible {
|
|
425
|
+
outline: 2px solid var(--uniface-primary-border-color, #298DFF);
|
|
426
|
+
outline-offset: -2px;
|
|
427
|
+
}
|
|
353
428
|
</style>
|
|
@@ -15,6 +15,10 @@ interface Props {
|
|
|
15
15
|
selectedList?: Array<any>;
|
|
16
16
|
class?: string;
|
|
17
17
|
item$props?: any;
|
|
18
|
+
onchange?: OnSelectChange;
|
|
19
|
+
/**
|
|
20
|
+
* @deprecated 请使用 onchange;仍受支持以兼容旧调用。
|
|
21
|
+
*/
|
|
18
22
|
onSelectChange?: OnSelectChange;
|
|
19
23
|
onItemDblClick?: OnItemDblClick;
|
|
20
24
|
onItemClick?: OnItemClick;
|
|
@@ -68,25 +68,41 @@
|
|
|
68
68
|
await onNodeSelectionChange(node);
|
|
69
69
|
}
|
|
70
70
|
|
|
71
|
+
const handleRowKeyDown = async (e: KeyboardEvent) => {
|
|
72
|
+
if (e.key === 'Enter' || e.key === ' ') {
|
|
73
|
+
e.preventDefault();
|
|
74
|
+
await handleRowClick();
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
const handleIconKeyDown = async (e: KeyboardEvent) => {
|
|
79
|
+
if (e.key === 'Enter' || e.key === ' ') {
|
|
80
|
+
e.preventDefault();
|
|
81
|
+
e.stopPropagation();
|
|
82
|
+
await onToggle();
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
|
|
71
86
|
const handleContextMenu = (event: MouseEvent) => {
|
|
72
87
|
onContextMenu?.(event, node);
|
|
73
88
|
}
|
|
74
89
|
</script>
|
|
75
90
|
|
|
76
91
|
<div class="tree-node" class:expanded style="padding-left: {node.level * 16}px">
|
|
77
|
-
<div class="node-item" class:selected={isSelected} onclick={handleRowClick}
|
|
78
|
-
oncontextmenu={handleContextMenu}
|
|
92
|
+
<div class="node-item" class:selected={isSelected} onclick={handleRowClick} onkeydown={handleRowKeyDown}
|
|
93
|
+
oncontextmenu={handleContextMenu} role="treeitem" tabindex="0" aria-selected={isSelected}
|
|
94
|
+
aria-expanded={isBranch ? expanded : undefined}>
|
|
79
95
|
|
|
80
96
|
<div class="item-chevron">
|
|
81
97
|
{#if isBranch}
|
|
82
98
|
{#if loading}
|
|
83
99
|
<img alt="loading" class="chevron-img" src={iconLoading}/>
|
|
84
100
|
{:else if chevronIcon}
|
|
85
|
-
<span
|
|
101
|
+
<span role="button" tabindex="0" aria-label={expanded ? 'Collapse' : 'Expand'} onclick={handleIconClick} onkeydown={handleIconKeyDown} class="chevron-btn">
|
|
86
102
|
{@render chevronIcon({ expanded, loading })}
|
|
87
103
|
</span>
|
|
88
104
|
{:else}
|
|
89
|
-
<span
|
|
105
|
+
<span role="button" tabindex="0" aria-label={expanded ? 'Collapse' : 'Expand'} onclick={handleIconClick} onkeydown={handleIconKeyDown} class="chevron-btn default-arrow">
|
|
90
106
|
{expanded ? '▾' : '▸'}
|
|
91
107
|
</span>
|
|
92
108
|
{/if}
|
|
@@ -202,6 +218,11 @@
|
|
|
202
218
|
color: var(--uniface-treeview-item-selected-color, #0061FF);
|
|
203
219
|
font-weight: 600;
|
|
204
220
|
}
|
|
221
|
+
|
|
222
|
+
&:focus-visible {
|
|
223
|
+
outline: 2px solid var(--uniface-primary-border-color, #298DFF);
|
|
224
|
+
outline-offset: -2px;
|
|
225
|
+
}
|
|
205
226
|
}
|
|
206
227
|
}
|
|
207
228
|
</style>
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
<script lang="ts">
|
|
1
|
+
<script lang="ts" generics="T = any">
|
|
2
2
|
import ContentPanel from "./parts/ContentPanel.svelte";
|
|
3
3
|
import type DataColumn from "./lib/DataColumn";
|
|
4
4
|
import type ActionsColumn from "./lib/ActionsColumn";
|
|
@@ -14,17 +14,17 @@
|
|
|
14
14
|
|
|
15
15
|
interface Props {
|
|
16
16
|
columns: Array<DataColumn>;
|
|
17
|
-
actionsColumn?: ActionsColumn | null;
|
|
17
|
+
actionsColumn?: ActionsColumn<T> | null;
|
|
18
18
|
indicatorColumn?: IndicatorColumn | null;
|
|
19
19
|
rowHeight?: number;
|
|
20
20
|
headerHeight?: number;
|
|
21
|
-
list: Array<
|
|
22
|
-
selectedRows?: Array<
|
|
21
|
+
list: Array<T>;
|
|
22
|
+
selectedRows?: Array<T>;
|
|
23
23
|
inlineRowHeight?: number;
|
|
24
24
|
rowBorder?: boolean;
|
|
25
25
|
colBorder?: boolean;
|
|
26
26
|
emptyIndicator?: string;
|
|
27
|
-
getRowFontStyle?: GetRowFontStyle
|
|
27
|
+
getRowFontStyle?: GetRowFontStyle<T>;
|
|
28
28
|
style?: string;
|
|
29
29
|
}
|
|
30
30
|
|
|
@@ -2,21 +2,41 @@ import type DataColumn from "./lib/DataColumn";
|
|
|
2
2
|
import type ActionsColumn from "./lib/ActionsColumn";
|
|
3
3
|
import type IndicatorColumn from "./lib/IndicatorColumn";
|
|
4
4
|
import type { GetRowFontStyle } from "../types";
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
5
|
+
declare function $$render<T = any>(): {
|
|
6
|
+
props: {
|
|
7
|
+
columns: Array<DataColumn>;
|
|
8
|
+
actionsColumn?: ActionsColumn<T> | null;
|
|
9
|
+
indicatorColumn?: IndicatorColumn | null;
|
|
10
|
+
rowHeight?: number;
|
|
11
|
+
headerHeight?: number;
|
|
12
|
+
list: Array<T>;
|
|
13
|
+
selectedRows?: Array<T>;
|
|
14
|
+
inlineRowHeight?: number;
|
|
15
|
+
rowBorder?: boolean;
|
|
16
|
+
colBorder?: boolean;
|
|
17
|
+
emptyIndicator?: string;
|
|
18
|
+
getRowFontStyle?: GetRowFontStyle<T>;
|
|
19
|
+
style?: string;
|
|
20
|
+
};
|
|
21
|
+
exports: {};
|
|
22
|
+
bindings: "inlineRowHeight" | "selectedRows";
|
|
23
|
+
slots: {};
|
|
24
|
+
events: {};
|
|
25
|
+
};
|
|
26
|
+
declare class __sveltets_Render<T = any> {
|
|
27
|
+
props(): ReturnType<typeof $$render<T>>['props'];
|
|
28
|
+
events(): ReturnType<typeof $$render<T>>['events'];
|
|
29
|
+
slots(): ReturnType<typeof $$render<T>>['slots'];
|
|
30
|
+
bindings(): "inlineRowHeight" | "selectedRows";
|
|
31
|
+
exports(): {};
|
|
19
32
|
}
|
|
20
|
-
|
|
21
|
-
|
|
33
|
+
interface $$IsomorphicComponent {
|
|
34
|
+
new <T = any>(options: import('svelte').ComponentConstructorOptions<ReturnType<__sveltets_Render<T>['props']>>): import('svelte').SvelteComponent<ReturnType<__sveltets_Render<T>['props']>, ReturnType<__sveltets_Render<T>['events']>, ReturnType<__sveltets_Render<T>['slots']>> & {
|
|
35
|
+
$$bindings?: ReturnType<__sveltets_Render<T>['bindings']>;
|
|
36
|
+
} & ReturnType<__sveltets_Render<T>['exports']>;
|
|
37
|
+
<T = any>(internal: unknown, props: ReturnType<__sveltets_Render<T>['props']> & {}): ReturnType<__sveltets_Render<T>['exports']>;
|
|
38
|
+
z_$$bindings?: ReturnType<__sveltets_Render<any>['bindings']>;
|
|
39
|
+
}
|
|
40
|
+
declare const DataTable: $$IsomorphicComponent;
|
|
41
|
+
type DataTable<T = any> = InstanceType<typeof DataTable<T>>;
|
|
22
42
|
export default DataTable;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { GetRowActions } from "./RowAction";
|
|
2
|
-
export default interface ActionsColumn {
|
|
2
|
+
export default interface ActionsColumn<T = any> {
|
|
3
3
|
/**
|
|
4
4
|
* 宽度
|
|
5
5
|
*/
|
|
@@ -7,7 +7,7 @@ export default interface ActionsColumn {
|
|
|
7
7
|
/**
|
|
8
8
|
*
|
|
9
9
|
*/
|
|
10
|
-
getActions: GetRowActions
|
|
10
|
+
getActions: GetRowActions<T>;
|
|
11
11
|
/**
|
|
12
12
|
* 对齐方式,默认靠左对齐
|
|
13
13
|
*/
|
|
@@ -33,7 +33,13 @@ export default interface DataColumn {
|
|
|
33
33
|
*/
|
|
34
34
|
formatter?: FormatCell;
|
|
35
35
|
/**
|
|
36
|
-
*
|
|
36
|
+
* 是否将单元格内容作为可信 HTML 渲染({@html}),而非纯文本转义。
|
|
37
|
+
* 仅当 field/formatter 输出为可信标记时才应设为 true。
|
|
38
|
+
*/
|
|
39
|
+
renderHTML?: boolean;
|
|
40
|
+
/**
|
|
41
|
+
* @deprecated 请使用 renderHTML;名称容易被误读为"转义 HTML",
|
|
42
|
+
* 实际含义相反——设为 true 会把内容作为可信 HTML 渲染。仍受支持以兼容旧调用。
|
|
37
43
|
*/
|
|
38
44
|
escapeHTML?: boolean;
|
|
39
45
|
/**
|
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
/**
|
|
2
|
-
*
|
|
2
|
+
* @template T Row data type. Defaults to `any` so existing untyped usage keeps compiling.
|
|
3
3
|
*/
|
|
4
|
-
export type ActionFunction = (item:
|
|
4
|
+
export type ActionFunction<T = any> = (item: T) => void;
|
|
5
5
|
/**
|
|
6
6
|
*
|
|
7
7
|
*/
|
|
8
|
-
export default interface RowAction {
|
|
8
|
+
export default interface RowAction<T = any> {
|
|
9
9
|
/**
|
|
10
10
|
*
|
|
11
11
|
*/
|
|
@@ -21,9 +21,9 @@ export default interface RowAction {
|
|
|
21
21
|
/**
|
|
22
22
|
*
|
|
23
23
|
*/
|
|
24
|
-
callback: ActionFunction
|
|
24
|
+
callback: ActionFunction<T>;
|
|
25
25
|
}
|
|
26
26
|
/**
|
|
27
27
|
*
|
|
28
28
|
*/
|
|
29
|
-
export type GetRowActions = (item:
|
|
29
|
+
export type GetRowActions<T = any> = (item: T) => Array<RowAction<T>>;
|
|
@@ -60,7 +60,6 @@
|
|
|
60
60
|
let startWidth = $state(0);
|
|
61
61
|
|
|
62
62
|
const handleResizeMouseDown = (col: DataColumn) => (event: MouseEvent) => {
|
|
63
|
-
console.log("handleResizeMouseDown", col, event);
|
|
64
63
|
if (col.resizable) {
|
|
65
64
|
resizeCol = col;
|
|
66
65
|
startX = event.clientX;
|
|
@@ -89,6 +88,13 @@
|
|
|
89
88
|
window.removeEventListener('mousemove', onMouseMove);
|
|
90
89
|
window.removeEventListener('mouseup', onMouseUp);
|
|
91
90
|
}
|
|
91
|
+
|
|
92
|
+
const handleHeaderKeyDown = (column: DataColumn) => (e: KeyboardEvent) => {
|
|
93
|
+
if (column.compareFunction != null && (e.key === 'Enter' || e.key === ' ')) {
|
|
94
|
+
e.preventDefault();
|
|
95
|
+
handleCellClick?.(column);
|
|
96
|
+
}
|
|
97
|
+
};
|
|
92
98
|
</script>
|
|
93
99
|
|
|
94
100
|
<div class="header-row" style="height: {headerHeight}px">
|
|
@@ -110,10 +116,18 @@
|
|
|
110
116
|
{/if}
|
|
111
117
|
{#each columns as column, index (index)}
|
|
112
118
|
<div class="fz_col-{index} data-cell" class:sortable={column.compareFunction != null} style="text-align: center">
|
|
119
|
+
<!-- role/tabindex are only ever both set together (sortable columns);
|
|
120
|
+
svelte-check can't verify that pairing statically across the ternary. -->
|
|
121
|
+
<!-- svelte-ignore a11y_no_noninteractive_tabindex -->
|
|
113
122
|
<div
|
|
114
123
|
class:sortable={column.compareFunction != null}
|
|
115
124
|
onclick={() => handleCellClick?.(column)}
|
|
116
|
-
|
|
125
|
+
onkeydown={handleHeaderKeyDown(column)}
|
|
126
|
+
role={column.compareFunction != null ? 'button' : undefined}
|
|
127
|
+
tabindex={column.compareFunction != null ? 0 : undefined}
|
|
128
|
+
aria-sort={column.field === orderColumn?.field
|
|
129
|
+
? (orderDirection === OrderDirection.Ascending ? 'ascending' : 'descending')
|
|
130
|
+
: undefined}
|
|
117
131
|
class="vertical-center"
|
|
118
132
|
>
|
|
119
133
|
<span>{column.text}</span>
|
|
@@ -129,7 +143,8 @@
|
|
|
129
143
|
<div
|
|
130
144
|
class="header-cell-divider"
|
|
131
145
|
class:resizer={column.resizable}
|
|
132
|
-
|
|
146
|
+
role={column.resizable ? 'separator' : undefined}
|
|
147
|
+
aria-orientation={column.resizable ? 'vertical' : undefined}
|
|
133
148
|
onmousedown={handleResizeMouseDown(column)}
|
|
134
149
|
></div>
|
|
135
150
|
</div>
|
|
@@ -45,6 +45,14 @@
|
|
|
45
45
|
e.stopPropagation();
|
|
46
46
|
};
|
|
47
47
|
|
|
48
|
+
const handleExpandKeyDown = (e: KeyboardEvent) => {
|
|
49
|
+
if (e.key === 'Enter' || e.key === ' ') {
|
|
50
|
+
e.preventDefault();
|
|
51
|
+
e.stopPropagation();
|
|
52
|
+
handleRowExpand?.(row);
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
|
|
48
56
|
const handleSelectChange = (e: Event) => {
|
|
49
57
|
const checked = (e.target as HTMLInputElement).checked;
|
|
50
58
|
handleRowSelectChange?.(rowIndex, checked);
|
|
@@ -66,8 +74,9 @@
|
|
|
66
74
|
<div class="expand-icon" style="flex: 0 0 auto">
|
|
67
75
|
<i
|
|
68
76
|
class={row == expandRow ? 'icon_google_folder' : 'icon_google_folder_open'}
|
|
69
|
-
aria-
|
|
77
|
+
role="button" tabindex="0" aria-label={row == expandRow ? 'Collapse row' : 'Expand row'}
|
|
70
78
|
onclick={showInlineData}
|
|
79
|
+
onkeydown={handleExpandKeyDown}
|
|
71
80
|
></i>
|
|
72
81
|
</div>
|
|
73
82
|
{/if}
|
|
@@ -20,7 +20,7 @@
|
|
|
20
20
|
{#if typeof item == 'string'}
|
|
21
21
|
<span>{item}</span>
|
|
22
22
|
{:else}
|
|
23
|
-
<button class="link-style" onclick={(e) => { e.preventDefault(); item.action(); }}>{item.text}</button>
|
|
23
|
+
<button type="button" class="link-style" onclick={(e) => { e.preventDefault(); item.action(); }}>{item.text}</button>
|
|
24
24
|
{/if}
|
|
25
25
|
{/each}
|
|
26
26
|
</div>
|