qidian-vue-ui 2.0.57 → 2.0.58

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.
@@ -78,6 +78,9 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
78
78
  rowKey: {},
79
79
  size: {},
80
80
  selectType: {},
81
+ cellSelectable: {
82
+ type: Boolean
83
+ },
81
84
  reserveSelectedRowOnFilter: {
82
85
  type: Boolean
83
86
  },
@@ -25,6 +25,7 @@ export declare const qdCrudTableProps: {
25
25
  readonly readonly: undefined;
26
26
  readonly lazyForm: true;
27
27
  readonly editCellValidationBlock: "error";
28
+ readonly cellSelectable: undefined;
28
29
  readonly rowKey: "id";
29
30
  readonly expandIcon: true;
30
31
  readonly selectOnRowClick: undefined;
@@ -191,6 +191,7 @@ declare const _default: <D extends TableRowData = TableRowData, R = unknown, P =
191
191
  onAfter?: (() => void) | undefined;
192
192
  onSuccess?: ((data: import("qidian-shared").ServicePageDataType<D>) => void) | undefined;
193
193
  manual?: boolean | undefined;
194
+ cellSelectable?: boolean | undefined;
194
195
  selectType?: "single" | "multiple" | undefined;
195
196
  reserveSelectedRowOnFilter?: boolean | undefined;
196
197
  headerBg?: boolean | undefined;
@@ -44,6 +44,7 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
44
44
  rowKey: {},
45
45
  size: {},
46
46
  selectType: {},
47
+ cellSelectable: { type: Boolean },
47
48
  reserveSelectedRowOnFilter: { type: Boolean },
48
49
  headerBg: { type: Boolean },
49
50
  showFilterResult: { type: Boolean },
@@ -19,6 +19,7 @@ export declare const qdCrudTabsTableProps: {
19
19
  readonly readonly: undefined;
20
20
  readonly lazyForm: true;
21
21
  readonly editCellValidationBlock: "error";
22
+ readonly cellSelectable: undefined;
22
23
  readonly rowKey: "id";
23
24
  readonly expandIcon: true;
24
25
  readonly selectOnRowClick: undefined;
@@ -1,170 +1,177 @@
1
- .qd-service-table[data-v-75599918] {
1
+ .qd-service-table[data-v-203216f5] {
2
2
  height: 100%;
3
3
  display: flex;
4
4
  flex-direction: column;
5
5
  }
6
- .qd-service-table[data-v-75599918] > .t-table__content {
6
+ .qd-service-table[data-v-203216f5] > .t-table__content {
7
7
  flex: 1;
8
8
  }
9
- .qd-service-table--mini[data-v-75599918] {
9
+ .qd-service-table--mini[data-v-203216f5] {
10
10
  font: var(--td-font-body-small);
11
11
  }
12
- .qd-service-table--mini[data-v-75599918] th,
13
- .qd-service-table--mini[data-v-75599918] tr:not(.t-table__expanded-row) > td {
12
+ .qd-service-table--mini[data-v-203216f5] th,
13
+ .qd-service-table--mini[data-v-203216f5] tr:not(.t-table__expanded-row) > td {
14
14
  padding: var(--td-comp-paddingTB-xxs) var(--td-comp-paddingLR-xxs);
15
15
  line-height: var(--td-line-height-body-small);
16
16
  }
17
- .qd-service-table--mini[data-v-75599918] .t-table__row-full-element {
17
+ .qd-service-table--mini[data-v-203216f5] .t-table__row-full-element {
18
18
  padding: var(--td-comp-paddingTB-xs) var(--td-comp-paddingLR-s);
19
19
  }
20
- .qd-service-table--hide-empty-image[data-v-75599918] .t-table__empty {
20
+ .qd-service-table--hide-empty-image[data-v-203216f5] .t-table__empty {
21
21
  min-height: auto;
22
22
  }
23
- .qd-service-table--hide-empty-image[data-v-75599918] .t-table__empty .t-empty {
23
+ .qd-service-table--hide-empty-image[data-v-203216f5] .t-table__empty .t-empty {
24
24
  padding: 0 !important;
25
25
  }
26
- .qd-service-table--hide-empty-image[data-v-75599918] .t-table__empty .t-empty__image {
26
+ .qd-service-table--hide-empty-image[data-v-203216f5] .t-table__empty .t-empty__image {
27
27
  display: none;
28
28
  }
29
- .qd-service-table--hide-empty-image[data-v-75599918] .t-table__empty .t-empty__title {
29
+ .qd-service-table--hide-empty-image[data-v-203216f5] .t-table__empty .t-empty__title {
30
30
  margin-top: 0;
31
31
  }
32
- .qd-service-table[data-v-75599918] .t-table__tree-col:not(:has(.t-table__tree-op-icon)) {
32
+ .qd-service-table[data-v-203216f5] .t-table__tree-col:not(:has(.t-table__tree-op-icon)) {
33
33
  margin-left: calc(var(--td-font-size-body-large) + var(--td-comp-margin-s));
34
34
  }
35
- .qd-service-table[data-v-75599918] .t-table__tree-leaf-node .t-table__tree-op-icon:empty {
35
+ .qd-service-table[data-v-203216f5] .t-table__tree-leaf-node .t-table__tree-op-icon:empty {
36
36
  width: calc(var(--td-font-size-body-large) + var(--td-comp-margin-s));
37
37
  }
38
- .qd-service-table[data-v-75599918] .t-affix > .t-table__affixed-header-elm-wrap,
39
- .qd-service-table[data-v-75599918] .t-affix > .t-table__scrollbar--obvious {
40
- transform: var(--v298ee7ef);
38
+ .qd-service-table[data-v-203216f5] .t-affix > .t-table__affixed-header-elm-wrap,
39
+ .qd-service-table[data-v-203216f5] .t-affix > .t-table__scrollbar--obvious {
40
+ transform: var(--d1ae4892);
41
41
  }
42
- .qd-service-table--horizontal-bar-static[data-v-75599918] .t-table__scrollbar--obvious {
42
+ .qd-service-table--horizontal-bar-static[data-v-203216f5] .t-table__scrollbar--obvious {
43
43
  visibility: hidden;
44
44
  pointer-events: none;
45
45
  }
46
- .qd-service-table[data-v-75599918] .t-table__expanded-row .qd-service-table--horizontal-bar-static > div:has(> div > .t-table__scrollbar--obvious) {
46
+ .qd-service-table[data-v-203216f5] .t-table__expanded-row .qd-service-table--horizontal-bar-static > div:has(> div > .t-table__scrollbar--obvious) {
47
47
  display: none;
48
48
  }
49
- .qd-service-table[data-v-75599918] .t-table__expanded-row > td {
49
+ .qd-service-table[data-v-203216f5] .t-table__expanded-row > td {
50
50
  height: 0;
51
51
  }
52
- .qd-service-table[data-v-75599918] .t-table__affixed-header-elm-wrap {
52
+ .qd-service-table[data-v-203216f5] .t-table__affixed-header-elm-wrap {
53
53
  height: auto !important;
54
54
  }
55
- .qd-service-table[data-v-75599918] .t-table__affixed-header-elm {
55
+ .qd-service-table[data-v-203216f5] .t-table__affixed-header-elm {
56
56
  position: relative;
57
57
  scrollbar-width: none;
58
58
  }
59
- .qd-service-table[data-v-75599918] .t-table__affixed-header-elm::-webkit-scrollbar {
59
+ .qd-service-table[data-v-203216f5] .t-table__affixed-header-elm::-webkit-scrollbar {
60
60
  display: none;
61
61
  width: 0;
62
62
  height: 0;
63
63
  }
64
- .qd-service-table[data-v-75599918] .t-table__virtual-scroll-cursor + table {
64
+ .qd-service-table[data-v-203216f5] .t-table__virtual-scroll-cursor + table {
65
65
  border-collapse: separate;
66
66
  }
67
- .qd-service-table[data-v-75599918] .t-table__expanded-row-inner,
68
- .qd-service-table[data-v-75599918] .t-table__row-filter-inner {
67
+ .qd-service-table[data-v-203216f5] .t-table__expanded-row-inner,
68
+ .qd-service-table[data-v-203216f5] .t-table__row-filter-inner {
69
69
  display: block;
70
70
  position: sticky;
71
71
  left: 0;
72
- width: var(--v668d03b8) !important;
72
+ width: var(--v22a7e7ec) !important;
73
73
  }
74
- .qd-service-table[data-v-75599918] .t-table__cell-wrap > .t-form__controls > .t-form__controls-content > *:not(.t-switch):not(.t-tag):not(.t-icon):not(.qd-file-icon) {
74
+ .qd-service-table[data-v-203216f5] .t-table__cell-wrap > .t-form__controls > .t-form__controls-content > *:not(.t-switch):not(.t-tag):not(.t-icon):not(.qd-file-icon) {
75
75
  width: 100%;
76
76
  }
77
- .qd-service-table[data-v-75599918] .qd-service-table__non-editable-col {
77
+ .qd-service-table[data-v-203216f5] .qd-service-table__non-editable-col {
78
78
  background-color: color-mix(in srgb, var(--td-bg-color-component) 50%, transparent);
79
79
  }
80
- .qd-service-table[data-v-75599918] .qd-service-table__selected-cell {
80
+ .qd-service-table[data-v-203216f5] .qd-service-table__selected-cell {
81
81
  box-shadow: inset 0 0 0 1px var(--td-brand-color);
82
82
  }
83
- .qd-service-table[data-v-75599918] .qd-service-table__non-editable-col:is(
83
+ .qd-service-table[data-v-203216f5] tbody > tr.t-table__row--active {
84
+ background-color: var(--td-brand-color-light);
85
+ }
86
+ .qd-service-table[data-v-203216f5] tbody > tr.t-table__row--active.t-table__row--hover,
87
+ .qd-service-table[data-v-203216f5] tbody > tr.t-table__row--active:hover {
88
+ background-color: var(--td-brand-color-light-hover);
89
+ }
90
+ .qd-service-table[data-v-203216f5] .qd-service-table__non-editable-col:is(
84
91
  .t-table__cell--fixed-left,
85
92
  .t-table__cell--fixed-right
86
93
  ) {
87
94
  background-color: inherit;
88
95
  background-image: linear-gradient(color-mix(in srgb, var(--td-bg-color-secondarycontainer) 50%, transparent), color-mix(in srgb, var(--td-bg-color-secondarycontainer) 50%, transparent));
89
96
  }
90
- .qd-service-table--disable-horizontal-scroll[data-v-75599918] colgroup > col {
97
+ .qd-service-table--disable-horizontal-scroll[data-v-203216f5] colgroup > col {
91
98
  width: auto !important;
92
99
  }
93
- .qd-service-table[data-v-75599918] .t-table__filter-pop-content-inner {
100
+ .qd-service-table[data-v-203216f5] .t-table__filter-pop-content-inner {
94
101
  padding: var(--td-comp-paddingTB-s) var(--td-comp-paddingLR-s) 0;
95
102
  }
96
- .qd-service-table[data-v-75599918] .t-table__filter-pop-content-inner:has(.qd-service-table-filter-item) {
103
+ .qd-service-table[data-v-203216f5] .t-table__filter-pop-content-inner:has(.qd-service-table-filter-item) {
97
104
  padding: 0;
98
105
  }
99
- .qd-service-table[data-v-75599918] .t-table__filter-pop-content-inner:has(
106
+ .qd-service-table[data-v-203216f5] .t-table__filter-pop-content-inner:has(
100
107
  .qd-service-table-filter-input,
101
108
  .qd-service-table-filter-custom
102
109
  ) {
103
110
  padding-bottom: var(--td-comp-paddingTB-s);
104
111
  }
105
- .qd-service-table[data-v-75599918] .t-table__filter--bottom-buttons {
112
+ .qd-service-table[data-v-203216f5] .t-table__filter--bottom-buttons {
106
113
  padding: var(--td-comp-paddingTB-s) var(--td-comp-paddingLR-s);
107
114
  }
108
- .qd-service-table--mini[data-v-75599918] .t-table__filter-pop-content-inner {
115
+ .qd-service-table--mini[data-v-203216f5] .t-table__filter-pop-content-inner {
109
116
  padding: var(--td-comp-paddingTB-xs) var(--td-comp-paddingLR-xs) 0;
110
117
  }
111
- .qd-service-table--mini[data-v-75599918] .t-table__filter--bottom-buttons {
118
+ .qd-service-table--mini[data-v-203216f5] .t-table__filter--bottom-buttons {
112
119
  padding: var(--td-comp-paddingTB-xs) var(--td-comp-paddingLR-xs);
113
120
  }
114
- .qd-service-table--mini[data-v-75599918] .t-table__filter-pop-content-inner:has(.qd-service-table-filter-item) {
121
+ .qd-service-table--mini[data-v-203216f5] .t-table__filter-pop-content-inner:has(.qd-service-table-filter-item) {
115
122
  padding: 0;
116
123
  }
117
- .qd-service-table--mini[data-v-75599918] .t-table__filter-pop-content-inner:has(
124
+ .qd-service-table--mini[data-v-203216f5] .t-table__filter-pop-content-inner:has(
118
125
  .qd-service-table-filter-input,
119
126
  .qd-service-table-filter-custom
120
127
  ) {
121
128
  padding-bottom: var(--td-comp-paddingTB-xs);
122
129
  }
123
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item {
130
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item {
124
131
  width: 266px;
125
132
  }
126
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item__search,
127
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item__all,
128
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item__options {
133
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item__search,
134
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item__all,
135
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item__options {
129
136
  padding: var(--td-comp-paddingTB-s) var(--td-comp-paddingLR-s) 0;
130
137
  }
131
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item__all {
138
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item__all {
132
139
  display: flex;
133
140
  align-items: center;
134
141
  padding: 0 var(--td-comp-paddingLR-s);
135
142
  border-bottom: 1px solid var(--td-component-stroke);
136
143
  }
137
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item__options {
144
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item__options {
138
145
  display: flex;
139
146
  flex-direction: column;
140
147
  height: 206px;
141
148
  padding: 0 var(--td-comp-paddingLR-s);
142
149
  overflow-y: auto;
143
150
  }
144
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item__count {
151
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item__count {
145
152
  margin-left: var(--td-comp-margin-xs);
146
153
  color: var(--td-text-color-placeholder);
147
154
  }
148
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item__cell {
155
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item__cell {
149
156
  pointer-events: none;
150
157
  }
151
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item .t-checkbox,
152
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item .t-radio {
158
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item .t-checkbox,
159
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item .t-radio {
153
160
  display: flex;
154
161
  align-items: center;
155
162
  }
156
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item .t-checkbox__label,
157
- .qd-service-table[data-v-75599918] .qd-service-table-filter-item .t-radio__label {
163
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item .t-checkbox__label,
164
+ .qd-service-table[data-v-203216f5] .qd-service-table-filter-item .t-radio__label {
158
165
  display: inline-flex;
159
166
  flex: 1 1 0;
160
167
  align-items: center;
161
168
  min-width: 0;
162
169
  overflow: hidden;
163
170
  }
164
- .qd-service-table--mini[data-v-75599918] .qd-service-table-filter-item__search {
171
+ .qd-service-table--mini[data-v-203216f5] .qd-service-table-filter-item__search {
165
172
  padding: var(--td-comp-paddingTB-xs) var(--td-comp-paddingLR-xs) 0;
166
173
  }
167
- .qd-service-table--mini[data-v-75599918] .qd-service-table-filter-item__all,
168
- .qd-service-table--mini[data-v-75599918] .qd-service-table-filter-item__options {
174
+ .qd-service-table--mini[data-v-203216f5] .qd-service-table-filter-item__all,
175
+ .qd-service-table--mini[data-v-203216f5] .qd-service-table-filter-item__options {
169
176
  padding: 0 var(--td-comp-paddingLR-xs);
170
177
  }
@@ -2,7 +2,7 @@ import './index.css'
2
2
  import _sfc_main from "./index.vue2.mjs";
3
3
  /* empty css */
4
4
  import _export_sfc from "../../../_virtual/_plugin-vue_export-helper.mjs";
5
- const QdServiceTable = /* @__PURE__ */ _export_sfc(_sfc_main, [["__scopeId", "data-v-75599918"]]);
5
+ const QdServiceTable = /* @__PURE__ */ _export_sfc(_sfc_main, [["__scopeId", "data-v-203216f5"]]);
6
6
  export {
7
7
  QdServiceTable as default
8
8
  };
@@ -35,6 +35,9 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
35
35
  rowKey: {},
36
36
  size: {},
37
37
  selectType: {},
38
+ cellSelectable: {
39
+ type: Boolean
40
+ },
38
41
  reserveSelectedRowOnFilter: {
39
42
  type: Boolean
40
43
  },
@@ -339,8 +342,8 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
339
342
  emit: __emit
340
343
  }) {
341
344
  useCssVars((_ctx) => ({
342
- "v298ee7ef": affixedHeaderTransform.value,
343
- "v668d03b8": expandedRowWidth.value
345
+ "d1ae4892": affixedHeaderTransform.value,
346
+ "v22a7e7ec": expandedRowWidth.value
344
347
  }));
345
348
  const props = __props;
346
349
  const emit = __emit;
@@ -399,6 +402,10 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
399
402
  const activeEditingCell = shallowRef();
400
403
  const autofocusEditingCell = shallowRef();
401
404
  const selectedCell = shallowRef();
405
+ const selectedCells = shallowRef([]);
406
+ const selectedCellAnchor = shallowRef();
407
+ const handledSelectionEvents = /* @__PURE__ */ new WeakSet();
408
+ const selectionExcludedColKeys = /* @__PURE__ */ new Set(["expand", "drag"]);
402
409
  const editingCellValidationErrors = shallowRef(/* @__PURE__ */ new Map());
403
410
  const expandedRowProxyMap = /* @__PURE__ */ new WeakMap();
404
411
  let dataChangePending = false;
@@ -407,6 +414,7 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
407
414
  } = useActivated();
408
415
  const formItemColumns = computed(() => flattenFormItemColumns(props.columns || []));
409
416
  const editableColumns = computed(() => flattenEditableColumns(props.columns || []));
417
+ const reCellSelectable = computed(() => props.cellSelectable ?? (formItemColumns.value.length > 0 || editableColumns.value.length > 0));
410
418
  const parentAddBeforeSubmitQueue = inject(PROVIDE_FORM_ADD_BEFORE_SUBMIT_QUEUE, void 0);
411
419
  const beforeSubmitQueueMap = /* @__PURE__ */ new Map();
412
420
  const editingCellValidationVersions = /* @__PURE__ */ new Map();
@@ -794,7 +802,7 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
794
802
  };
795
803
  }
796
804
  }
797
- const reSelectOnRowClick = selectOnRowClick ?? (onRowClick ? void 0 : !expandOnRowClick && !reTree?.expandTreeNodeOnClick);
805
+ const reSelectOnRowClick = false;
798
806
  const reOnScroll = (params) => {
799
807
  onScroll?.(params);
800
808
  const target = params.e.target;
@@ -892,6 +900,9 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
892
900
  tableOptions: {
893
901
  ...reTableOptions,
894
902
  filterRow: showFilterResult ? reTableOptions.filterRow : null,
903
+ // 行高亮随单元格选中统一驱动(syncSelectedRowKeysFromCells 同步 activeRowKeys),
904
+ // 置空关闭 TDesign 行点击/键盘的原生高亮,避免双重写入打架
905
+ activeRowType: "",
895
906
  selectOnRowClick: reSelectOnRowClick,
896
907
  expandOnRowClick,
897
908
  tree: reTree,
@@ -1243,8 +1254,92 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1243
1254
  return !!findEditingCell(row, colKey);
1244
1255
  }
1245
1256
  function isSelectedCell(row, colKey) {
1246
- if (!selectedCell.value) return false;
1247
- return getRowValue(selectedCell.value.row) === getRowValue(row) && selectedCell.value.colKey === colKey;
1257
+ return selectedCells.value.some((item) => getRowValue(item.row) === getRowValue(row) && item.colKey === colKey);
1258
+ }
1259
+ function hasSelectionModifier(event) {
1260
+ return !!event && (event.metaKey || event.ctrlKey || event.shiftKey);
1261
+ }
1262
+ function expandSelectedCellRange(anchor, target) {
1263
+ if (!target.colKey || !anchor.colKey) return [target];
1264
+ const columns = adaptedColumns.value;
1265
+ const fromCol = columns.findIndex((col) => col.colKey === anchor.colKey);
1266
+ const toCol = columns.findIndex((col) => col.colKey === target.colKey);
1267
+ const rows = data.value;
1268
+ const fromRow = rows.findIndex((row) => getRowValue(row) === getRowValue(anchor.row));
1269
+ const toRow = rows.findIndex((row) => getRowValue(row) === getRowValue(target.row));
1270
+ if (fromCol < 0 || toCol < 0 || fromRow < 0 || toRow < 0) return [target];
1271
+ const [rowStart, rowEnd] = fromRow <= toRow ? [fromRow, toRow] : [toRow, fromRow];
1272
+ const [colStart, colEnd] = fromCol <= toCol ? [fromCol, toCol] : [toCol, fromCol];
1273
+ const colKeys = columns.slice(colStart, colEnd + 1).map((col) => col.colKey);
1274
+ return rows.slice(rowStart, rowEnd + 1).flatMap((row) => colKeys.map((colKey) => ({
1275
+ row,
1276
+ colKey
1277
+ })));
1278
+ }
1279
+ function isRowSelectDisabled(row, rowIndex) {
1280
+ const selectColumn = adaptedColumns.value.find((col) => col.type === "single" || col.type === "multiple");
1281
+ if (!selectColumn) return false;
1282
+ const context = {
1283
+ row,
1284
+ rowIndex
1285
+ };
1286
+ const disabled = typeof selectColumn.disabled === "function" ? selectColumn.disabled(context) : selectColumn.disabled;
1287
+ const checkProps = typeof selectColumn.checkProps === "function" ? selectColumn.checkProps(context) : selectColumn.checkProps;
1288
+ return !!disabled || !!checkProps?.disabled;
1289
+ }
1290
+ function syncSelectedRowKeysFromCells() {
1291
+ const rowKeys = [];
1292
+ const seen = /* @__PURE__ */ new Set();
1293
+ for (const item of selectedCells.value) {
1294
+ const rowValue = getRowValue(item.row);
1295
+ if (seen.has(rowValue)) continue;
1296
+ const rowIndex = data.value.findIndex((row) => getRowValue(row) === rowValue);
1297
+ if (isRowSelectDisabled(rowIndex >= 0 ? data.value[rowIndex] : item.row, rowIndex)) continue;
1298
+ seen.add(rowValue);
1299
+ rowKeys.push(rowValue);
1300
+ }
1301
+ selectedRowKeys.value = rowKeys;
1302
+ activeRowKeys.value = rowKeys;
1303
+ }
1304
+ function pruneDisabledSelectedRows(newData) {
1305
+ if (!selectedRowKeys.value.length) return;
1306
+ const next = selectedRowKeys.value.filter((key) => {
1307
+ const rowIndex = newData.findIndex((row) => getRowValue(row) === key);
1308
+ if (rowIndex < 0) return true;
1309
+ return !isRowSelectDisabled(newData[rowIndex], rowIndex);
1310
+ });
1311
+ if (next.length === selectedRowKeys.value.length) return;
1312
+ selectedRowKeys.value = next;
1313
+ }
1314
+ function isCellSelectableColumn(column) {
1315
+ if (selectionExcludedColKeys.has(String(column.colKey))) return false;
1316
+ if (column.type === "single" || column.type === "multiple") return false;
1317
+ return column.cellSelectable ?? String(column.colKey) !== "operation";
1318
+ }
1319
+ function applyCellSelection(cell, event) {
1320
+ if (!reCellSelectable.value) return;
1321
+ const column = adaptedColumns.value.find((col) => col.colKey === cell.colKey);
1322
+ if (!column || !isCellSelectableColumn(column)) return;
1323
+ if (event?.metaKey || event?.ctrlKey) {
1324
+ const exists = selectedCells.value.some((item) => isSameEditingCell(item, cell));
1325
+ const rest = selectedCells.value.filter((item) => !isSameEditingCell(item, cell));
1326
+ selectedCells.value = exists ? rest : [...rest, cell];
1327
+ selectedCell.value = selectedCells.value.at(-1);
1328
+ selectedCellAnchor.value = cell;
1329
+ syncSelectedRowKeysFromCells();
1330
+ return;
1331
+ }
1332
+ if (event?.shiftKey && selectedCellAnchor.value) {
1333
+ document.getSelection()?.removeAllRanges();
1334
+ selectedCells.value = expandSelectedCellRange(selectedCellAnchor.value, cell);
1335
+ selectedCell.value = cell;
1336
+ syncSelectedRowKeysFromCells();
1337
+ return;
1338
+ }
1339
+ selectedCells.value = [cell];
1340
+ selectedCell.value = cell;
1341
+ selectedCellAnchor.value = cell;
1342
+ syncSelectedRowKeysFromCells();
1248
1343
  }
1249
1344
  function resolveFormItemLazy(column) {
1250
1345
  const formItem = column.formItem;
@@ -1342,10 +1437,12 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1342
1437
  }
1343
1438
  function handleCellClick(context) {
1344
1439
  const column = context.col;
1345
- selectedCell.value = {
1440
+ const cell = {
1346
1441
  row: context.row,
1347
1442
  colKey: column.colKey
1348
1443
  };
1444
+ if (!handledSelectionEvents.has(context.e)) applyCellSelection(cell, context.e);
1445
+ if (hasSelectionModifier(context.e)) return;
1349
1446
  if (tableReadonly.value) return;
1350
1447
  if (column.formItem) {
1351
1448
  const editingCell = findEditingCell(context.row, column.colKey);
@@ -1386,17 +1483,20 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1386
1483
  function handleDocumentKeydown(event) {
1387
1484
  if (!activated.value) return;
1388
1485
  if (event.key !== "Escape" || event.defaultPrevented) return;
1389
- if (!activeEditingCell.value && !selectedCell.value) return;
1486
+ if (!activeEditingCell.value && !selectedCell.value && !selectedCells.value.length) return;
1390
1487
  const target = event.target;
1391
1488
  if (target?.closest(".t-select-input--popup-visible, .t-popup__content, .t-dialog, .t-drawer, .t-image-viewer, .qd-multi-file-viewer")) {
1392
1489
  return;
1393
1490
  }
1394
1491
  selectedCell.value = void 0;
1492
+ selectedCells.value = [];
1493
+ selectedRowKeys.value = [];
1494
+ activeRowKeys.value = [];
1395
1495
  exitActiveEditingCell();
1396
1496
  }
1397
1497
  function handleDocumentClick(event) {
1398
1498
  if (!activated.value) return;
1399
- if (!editingCells.value.length && !selectedCell.value) return;
1499
+ if (!editingCells.value.length && !selectedCell.value && !selectedCells.value.length) return;
1400
1500
  const hasVisibleDialog = Array.from(document.querySelectorAll(".t-dialog")).some((element) => element.getClientRects().length);
1401
1501
  const hasVisibleDrawer = Array.from(document.querySelectorAll(".t-drawer")).some((element) => element.classList.contains("t-drawer--open") || element.getAnimations({
1402
1502
  subtree: true
@@ -1405,6 +1505,7 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1405
1505
  const insideInteractiveArea = event.composedPath().some((target) => target instanceof Element && target.matches("td, .t-popup, .qd-dialog, .t-dialog, .t-drawer, .t-image-viewer, .qd-multi-file-viewer, [data-popper-placement]"));
1406
1506
  if (insideInteractiveArea) return;
1407
1507
  selectedCell.value = void 0;
1508
+ selectedCells.value = [];
1408
1509
  void exitAllEditingCells();
1409
1510
  }
1410
1511
  function getFirstValidationError(results) {
@@ -1991,12 +2092,13 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
1991
2092
  const previousAttrs = col.attrs;
1992
2093
  col.attrs = (context) => ({
1993
2094
  ...typeof previousAttrs === "function" ? previousAttrs(context) : previousAttrs,
1994
- onClickCapture: () => {
2095
+ onClickCapture: (event) => {
1995
2096
  if (context.type !== "td") return;
1996
- selectedCell.value = {
2097
+ handledSelectionEvents.add(event);
2098
+ applyCellSelection({
1997
2099
  row: context.row,
1998
2100
  colKey: column.colKey
1999
- };
2101
+ }, event);
2000
2102
  }
2001
2103
  });
2002
2104
  return col;
@@ -2344,7 +2446,10 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
2344
2446
  watch(expandedTreeNodes, adjustScrollWhenTreeExpanded, {
2345
2447
  flush: "post"
2346
2448
  });
2347
- watch(data, pruneCellValidationErrors);
2449
+ watch(data, (newData) => {
2450
+ pruneCellValidationErrors(newData);
2451
+ pruneDisabledSelectedRows(newData);
2452
+ });
2348
2453
  watch(tableContentVisible, (visible, _old, onCleanup) => {
2349
2454
  clearAffixFallbackTimer();
2350
2455
  if (!visible) return;
@@ -14,6 +14,7 @@ export declare const qdServiceTableProps: {
14
14
  readonly readonly: undefined;
15
15
  readonly lazyForm: true;
16
16
  readonly editCellValidationBlock: "error";
17
+ readonly cellSelectable: undefined;
17
18
  readonly rowKey: "id";
18
19
  readonly expandIcon: true;
19
20
  readonly selectOnRowClick: undefined;
@@ -13,6 +13,7 @@ const qdServiceTableProps = {
13
13
  readonly: void 0,
14
14
  lazyForm: true,
15
15
  editCellValidationBlock: "error",
16
+ cellSelectable: void 0,
16
17
  rowKey: "id",
17
18
  expandIcon: true,
18
19
  selectOnRowClick: void 0,
@@ -11,6 +11,7 @@ export type QdServiceTableScroll = NonNullable<TdEnhancedTableProps['scroll']> &
11
11
  export interface QdServiceTableCol<D extends TableRowData = TableRowData> extends Omit<TDesignServiceTableCol<D>, 'children' | 'foot'> {
12
12
  children?: QdServiceTableCol<D>[];
13
13
  foot?: string | TNode<BaseTableCellParams<D>>;
14
+ cellSelectable?: boolean;
14
15
  filterItem?: true | QdServiceTableFilterItem;
15
16
  formItem?: QdServiceTableFormItem;
16
17
  }
@@ -76,6 +77,7 @@ export interface QdServiceTableProps<D extends TableRowData = TableRowData, R =
76
77
  rowKey?: string;
77
78
  size?: TdEnhancedTableProps<D>['size'] | 'mini';
78
79
  selectType?: 'single' | 'multiple';
80
+ cellSelectable?: boolean;
79
81
  reserveSelectedRowOnFilter?: boolean;
80
82
  headerBg?: boolean;
81
83
  showFilterResult?: boolean;
@@ -66,6 +66,9 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
66
66
  },
67
67
  cacheColumnsKey: {},
68
68
  columns: {},
69
+ cellSelectable: {
70
+ type: Boolean
71
+ },
69
72
  reserveSelectedRowOnFilter: {
70
73
  type: Boolean
71
74
  },
@@ -42,6 +42,7 @@ export declare const qdServiceDialogTableSelectProps: {
42
42
  readonly emptyImage: true;
43
43
  readonly lazyForm: true;
44
44
  readonly editCellValidationBlock: "error";
45
+ readonly cellSelectable: undefined;
45
46
  readonly expandIcon: true;
46
47
  readonly selectOnRowClick: undefined;
47
48
  readonly bordered: undefined;
@@ -80,6 +80,9 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
80
80
  },
81
81
  cacheColumnsKey: {},
82
82
  columns: {},
83
+ cellSelectable: {
84
+ type: Boolean
85
+ },
83
86
  reserveSelectedRowOnFilter: {
84
87
  type: Boolean
85
88
  },
@@ -17,6 +17,7 @@ export declare const qdServiceDialogTabsTableSelectProps: {
17
17
  readonly emptyImage: true;
18
18
  readonly lazyForm: true;
19
19
  readonly editCellValidationBlock: "error";
20
+ readonly cellSelectable: undefined;
20
21
  readonly expandIcon: true;
21
22
  readonly selectOnRowClick: undefined;
22
23
  readonly bordered: undefined;
@@ -56,6 +56,9 @@ const _sfc_main = /* @__PURE__ */ defineComponent({
56
56
  },
57
57
  cacheColumnsKey: {},
58
58
  columns: {},
59
+ cellSelectable: {
60
+ type: Boolean
61
+ },
59
62
  reserveSelectedRowOnFilter: {
60
63
  type: Boolean
61
64
  },
@@ -16,6 +16,7 @@ export declare const qdServicePopupTableSelectProps: {
16
16
  readonly emptyImage: true;
17
17
  readonly lazyForm: true;
18
18
  readonly editCellValidationBlock: "error";
19
+ readonly cellSelectable: undefined;
19
20
  readonly expandIcon: true;
20
21
  readonly selectOnRowClick: undefined;
21
22
  readonly bordered: undefined;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "qidian-vue-ui",
3
- "version": "2.0.57",
3
+ "version": "2.0.58",
4
4
  "description": "基于 TDesign 的 QiDian Vue UI 组件库",
5
5
  "author": "qidian",
6
6
  "license": "MIT",