@nokecy/qc-ui 1.1.73 → 1.1.74

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 (45) hide show
  1. package/dist/cjs/adapters/pagedApiAdapter.d.ts +2 -0
  2. package/dist/cjs/ag-grid-plus/ag-gridPlus.js +5 -3
  3. package/dist/cjs/ag-grid-plus/interface.d.ts +6 -0
  4. package/dist/cjs/ag-grid-plus/utils/aggregation.js +8 -14
  5. package/dist/cjs/ag-grid-plus/utils/columnProcessors.d.ts +2 -1
  6. package/dist/cjs/ag-grid-plus/utils/columnProcessors.js +5 -2
  7. package/dist/cjs/ag-grid-plus/utils/valueEnumColor.d.ts +17 -0
  8. package/dist/cjs/ag-grid-plus/utils/valueEnumColor.js +99 -0
  9. package/dist/cjs/dialogSelect/index.d.ts +29 -0
  10. package/dist/cjs/dialogSelect/index.js +152 -103
  11. package/dist/cjs/dialogSelect/index.less +39 -0
  12. package/dist/cjs/draggableModal/index.js +12 -8
  13. package/dist/cjs/index.d.ts +5 -0
  14. package/dist/cjs/index.js +123 -1
  15. package/dist/cjs/toolBar/index.d.ts +1 -0
  16. package/dist/cjs/toolBar/index.js +44 -10
  17. package/dist/cjs/toolBar/index.less +25 -7
  18. package/dist/cjs/utils/businessDecimal.d.ts +11 -0
  19. package/dist/cjs/utils/businessDecimal.js +53 -0
  20. package/dist/cjs/utils/contrast.d.ts +40 -0
  21. package/dist/cjs/utils/contrast.js +153 -0
  22. package/dist/esm/adapters/pagedApiAdapter.d.ts +2 -0
  23. package/dist/esm/ag-grid-plus/ag-gridPlus.js +5 -3
  24. package/dist/esm/ag-grid-plus/interface.d.ts +6 -0
  25. package/dist/esm/ag-grid-plus/utils/aggregation.js +1 -5
  26. package/dist/esm/ag-grid-plus/utils/columnProcessors.d.ts +2 -1
  27. package/dist/esm/ag-grid-plus/utils/columnProcessors.js +5 -2
  28. package/dist/esm/ag-grid-plus/utils/valueEnumColor.d.ts +17 -0
  29. package/dist/esm/ag-grid-plus/utils/valueEnumColor.js +95 -0
  30. package/dist/esm/dialogSelect/index.d.ts +29 -0
  31. package/dist/esm/dialogSelect/index.js +155 -105
  32. package/dist/esm/dialogSelect/index.less +39 -0
  33. package/dist/esm/draggableModal/index.js +12 -8
  34. package/dist/esm/index.d.ts +5 -0
  35. package/dist/esm/index.js +3 -0
  36. package/dist/esm/toolBar/index.d.ts +1 -0
  37. package/dist/esm/toolBar/index.js +43 -10
  38. package/dist/esm/toolBar/index.less +25 -7
  39. package/dist/esm/utils/businessDecimal.d.ts +11 -0
  40. package/dist/esm/utils/businessDecimal.js +47 -0
  41. package/dist/esm/utils/contrast.d.ts +40 -0
  42. package/dist/esm/utils/contrast.js +141 -0
  43. package/dist/umd/qc-ui.min.css +1 -1
  44. package/dist/umd/qc-ui.min.js +1 -1
  45. package/package.json +1 -1
@@ -2,7 +2,11 @@ import { SelectProps } from 'antd/lib/select';
2
2
  import React from 'react';
3
3
  import { ColDef, ColGroupDef } from 'ag-grid-community';
4
4
  import type { PagedApiAdapter } from '../adapters';
5
+ import './index.less';
6
+ /** 选择窗口的行选择模式。 */
7
+ type DialogSelectionMode = 'single' | 'multiple';
5
8
  interface IDialogSelectProps extends SelectProps<any> {
9
+ /** 隐藏选择窗口入口(输入框内的后缀图标),只保留输入与下拉。 */
6
10
  hideBtn?: boolean;
7
11
  request?: any;
8
12
  columnDefs?: (ColDef | ColGroupDef)[] | null;
@@ -13,6 +17,31 @@ interface IDialogSelectProps extends SelectProps<any> {
13
17
  useAutoComplete?: boolean;
14
18
  /** 分页 API 适配器(默认 ABP)。@author nokecy */
15
19
  pagedApiAdapter?: PagedApiAdapter;
20
+ /** 选择窗口宽度,默认 960。 */
21
+ modalWidth?: number | string;
22
+ /** 选择窗口层级,默认 9999(高于抽屉、其他弹窗)。 */
23
+ dialogZIndex?: number;
24
+ /** 选择窗口中的行选择模式;缺省按 `mode` 推断,外层 Select 仍可保持单值。 */
25
+ dialogMode?: DialogSelectionMode;
26
+ /** 选择窗口表格的初始分页大小;不影响外层 Select。 */
27
+ dialogPageSize?: number;
28
+ /** 选择窗口表格可选分页大小。 */
29
+ dialogPageSizeOptions?: number[];
30
+ /** 选择窗口表格的列方案标识。 */
31
+ dialogGridKey?: string;
32
+ /** 已由业务限定范围的本地候选;传入后不再请求接口,表格直接筛选完整候选集且不分页。 */
33
+ dialogDataSource?: any[];
34
+ /** 业务限制下不可带入的行;单击、确认和双击共用该条件。 */
35
+ dialogIsRowSelectable?: (row: any) => boolean;
36
+ /** 自定义选择窗口内容;确认时回传所选行。传入后不再渲染内置的表格窗口。 */
37
+ dialogRenderer?: (context: {
38
+ open: boolean;
39
+ mode: DialogSelectionMode;
40
+ onCancel: () => void;
41
+ onConfirm: (rows: any[]) => void;
42
+ }) => React.ReactNode;
43
+ /** 选择窗口里使用的表格组件,默认 `AgGridPlus`;宿主可注入自己封装过的表格基座。 */
44
+ gridComponent?: React.ComponentType<any>;
16
45
  }
17
46
  declare const DialogSelect: (props: IDialogSelectProps) => React.JSX.Element;
18
47
  export { IDialogSelectProps };
@@ -1,4 +1,4 @@
1
- var _excluded = ["request", "columnDefs", "value", "labelField", "valueField", "onChangeItem"];
1
+ var _excluded = ["request", "columnDefs", "value", "labelField", "valueField", "onChangeItem", "hideBtn", "useAutoComplete", "queryFun", "pagedApiAdapter", "modalWidth", "dialogZIndex", "dialogMode", "dialogPageSize", "dialogPageSizeOptions", "dialogGridKey", "dialogDataSource", "dialogIsRowSelectable", "dialogRenderer", "gridComponent"];
2
2
  function _regeneratorRuntime() { "use strict"; /*! regenerator-runtime -- Copyright (c) 2014-present, Facebook, Inc. -- license (MIT): https://github.com/facebook/regenerator/blob/main/LICENSE */ _regeneratorRuntime = function _regeneratorRuntime() { return e; }; var t, e = {}, r = Object.prototype, n = r.hasOwnProperty, o = Object.defineProperty || function (t, e, r) { t[e] = r.value; }, i = "function" == typeof Symbol ? Symbol : {}, a = i.iterator || "@@iterator", c = i.asyncIterator || "@@asyncIterator", u = i.toStringTag || "@@toStringTag"; function define(t, e, r) { return Object.defineProperty(t, e, { value: r, enumerable: !0, configurable: !0, writable: !0 }), t[e]; } try { define({}, ""); } catch (t) { define = function define(t, e, r) { return t[e] = r; }; } function wrap(t, e, r, n) { var i = e && e.prototype instanceof Generator ? e : Generator, a = Object.create(i.prototype), c = new Context(n || []); return o(a, "_invoke", { value: makeInvokeMethod(t, r, c) }), a; } function tryCatch(t, e, r) { try { return { type: "normal", arg: t.call(e, r) }; } catch (t) { return { type: "throw", arg: t }; } } e.wrap = wrap; var h = "suspendedStart", l = "suspendedYield", f = "executing", s = "completed", y = {}; function Generator() {} function GeneratorFunction() {} function GeneratorFunctionPrototype() {} var p = {}; define(p, a, function () { return this; }); var d = Object.getPrototypeOf, v = d && d(d(values([]))); v && v !== r && n.call(v, a) && (p = v); var g = GeneratorFunctionPrototype.prototype = Generator.prototype = Object.create(p); function defineIteratorMethods(t) { ["next", "throw", "return"].forEach(function (e) { define(t, e, function (t) { return this._invoke(e, t); }); }); } function AsyncIterator(t, e) { function invoke(r, o, i, a) { var c = tryCatch(t[r], t, o); if ("throw" !== c.type) { var u = c.arg, h = u.value; return h && "object" == _typeof(h) && n.call(h, "__await") ? e.resolve(h.__await).then(function (t) { invoke("next", t, i, a); }, function (t) { invoke("throw", t, i, a); }) : e.resolve(h).then(function (t) { u.value = t, i(u); }, function (t) { return invoke("throw", t, i, a); }); } a(c.arg); } var r; o(this, "_invoke", { value: function value(t, n) { function callInvokeWithMethodAndArg() { return new e(function (e, r) { invoke(t, n, e, r); }); } return r = r ? r.then(callInvokeWithMethodAndArg, callInvokeWithMethodAndArg) : callInvokeWithMethodAndArg(); } }); } function makeInvokeMethod(e, r, n) { var o = h; return function (i, a) { if (o === f) throw new Error("Generator is already running"); if (o === s) { if ("throw" === i) throw a; return { value: t, done: !0 }; } for (n.method = i, n.arg = a;;) { var c = n.delegate; if (c) { var u = maybeInvokeDelegate(c, n); if (u) { if (u === y) continue; return u; } } if ("next" === n.method) n.sent = n._sent = n.arg;else if ("throw" === n.method) { if (o === h) throw o = s, n.arg; n.dispatchException(n.arg); } else "return" === n.method && n.abrupt("return", n.arg); o = f; var p = tryCatch(e, r, n); if ("normal" === p.type) { if (o = n.done ? s : l, p.arg === y) continue; return { value: p.arg, done: n.done }; } "throw" === p.type && (o = s, n.method = "throw", n.arg = p.arg); } }; } function maybeInvokeDelegate(e, r) { var n = r.method, o = e.iterator[n]; if (o === t) return r.delegate = null, "throw" === n && e.iterator.return && (r.method = "return", r.arg = t, maybeInvokeDelegate(e, r), "throw" === r.method) || "return" !== n && (r.method = "throw", r.arg = new TypeError("The iterator does not provide a '" + n + "' method")), y; var i = tryCatch(o, e.iterator, r.arg); if ("throw" === i.type) return r.method = "throw", r.arg = i.arg, r.delegate = null, y; var a = i.arg; return a ? a.done ? (r[e.resultName] = a.value, r.next = e.nextLoc, "return" !== r.method && (r.method = "next", r.arg = t), r.delegate = null, y) : a : (r.method = "throw", r.arg = new TypeError("iterator result is not an object"), r.delegate = null, y); } function pushTryEntry(t) { var e = { tryLoc: t[0] }; 1 in t && (e.catchLoc = t[1]), 2 in t && (e.finallyLoc = t[2], e.afterLoc = t[3]), this.tryEntries.push(e); } function resetTryEntry(t) { var e = t.completion || {}; e.type = "normal", delete e.arg, t.completion = e; } function Context(t) { this.tryEntries = [{ tryLoc: "root" }], t.forEach(pushTryEntry, this), this.reset(!0); } function values(e) { if (e || "" === e) { var r = e[a]; if (r) return r.call(e); if ("function" == typeof e.next) return e; if (!isNaN(e.length)) { var o = -1, i = function next() { for (; ++o < e.length;) if (n.call(e, o)) return next.value = e[o], next.done = !1, next; return next.value = t, next.done = !0, next; }; return i.next = i; } } throw new TypeError(_typeof(e) + " is not iterable"); } return GeneratorFunction.prototype = GeneratorFunctionPrototype, o(g, "constructor", { value: GeneratorFunctionPrototype, configurable: !0 }), o(GeneratorFunctionPrototype, "constructor", { value: GeneratorFunction, configurable: !0 }), GeneratorFunction.displayName = define(GeneratorFunctionPrototype, u, "GeneratorFunction"), e.isGeneratorFunction = function (t) { var e = "function" == typeof t && t.constructor; return !!e && (e === GeneratorFunction || "GeneratorFunction" === (e.displayName || e.name)); }, e.mark = function (t) { return Object.setPrototypeOf ? Object.setPrototypeOf(t, GeneratorFunctionPrototype) : (t.__proto__ = GeneratorFunctionPrototype, define(t, u, "GeneratorFunction")), t.prototype = Object.create(g), t; }, e.awrap = function (t) { return { __await: t }; }, defineIteratorMethods(AsyncIterator.prototype), define(AsyncIterator.prototype, c, function () { return this; }), e.AsyncIterator = AsyncIterator, e.async = function (t, r, n, o, i) { void 0 === i && (i = Promise); var a = new AsyncIterator(wrap(t, r, n, o), i); return e.isGeneratorFunction(r) ? a : a.next().then(function (t) { return t.done ? t.value : a.next(); }); }, defineIteratorMethods(g), define(g, u, "Generator"), define(g, a, function () { return this; }), define(g, "toString", function () { return "[object Generator]"; }), e.keys = function (t) { var e = Object(t), r = []; for (var n in e) r.push(n); return r.reverse(), function next() { for (; r.length;) { var t = r.pop(); if (t in e) return next.value = t, next.done = !1, next; } return next.done = !0, next; }; }, e.values = values, Context.prototype = { constructor: Context, reset: function reset(e) { if (this.prev = 0, this.next = 0, this.sent = this._sent = t, this.done = !1, this.delegate = null, this.method = "next", this.arg = t, this.tryEntries.forEach(resetTryEntry), !e) for (var r in this) "t" === r.charAt(0) && n.call(this, r) && !isNaN(+r.slice(1)) && (this[r] = t); }, stop: function stop() { this.done = !0; var t = this.tryEntries[0].completion; if ("throw" === t.type) throw t.arg; return this.rval; }, dispatchException: function dispatchException(e) { if (this.done) throw e; var r = this; function handle(n, o) { return a.type = "throw", a.arg = e, r.next = n, o && (r.method = "next", r.arg = t), !!o; } for (var o = this.tryEntries.length - 1; o >= 0; --o) { var i = this.tryEntries[o], a = i.completion; if ("root" === i.tryLoc) return handle("end"); if (i.tryLoc <= this.prev) { var c = n.call(i, "catchLoc"), u = n.call(i, "finallyLoc"); if (c && u) { if (this.prev < i.catchLoc) return handle(i.catchLoc, !0); if (this.prev < i.finallyLoc) return handle(i.finallyLoc); } else if (c) { if (this.prev < i.catchLoc) return handle(i.catchLoc, !0); } else { if (!u) throw new Error("try statement without catch or finally"); if (this.prev < i.finallyLoc) return handle(i.finallyLoc); } } } }, abrupt: function abrupt(t, e) { for (var r = this.tryEntries.length - 1; r >= 0; --r) { var o = this.tryEntries[r]; if (o.tryLoc <= this.prev && n.call(o, "finallyLoc") && this.prev < o.finallyLoc) { var i = o; break; } } i && ("break" === t || "continue" === t) && i.tryLoc <= e && e <= i.finallyLoc && (i = null); var a = i ? i.completion : {}; return a.type = t, a.arg = e, i ? (this.method = "next", this.next = i.finallyLoc, y) : this.complete(a); }, complete: function complete(t, e) { if ("throw" === t.type) throw t.arg; return "break" === t.type || "continue" === t.type ? this.next = t.arg : "return" === t.type ? (this.rval = this.arg = t.arg, this.method = "return", this.next = "end") : "normal" === t.type && e && (this.next = e), y; }, finish: function finish(t) { for (var e = this.tryEntries.length - 1; e >= 0; --e) { var r = this.tryEntries[e]; if (r.finallyLoc === t) return this.complete(r.completion, r.afterLoc), resetTryEntry(r), y; } }, catch: function _catch(t) { for (var e = this.tryEntries.length - 1; e >= 0; --e) { var r = this.tryEntries[e]; if (r.tryLoc === t) { var n = r.completion; if ("throw" === n.type) { var o = n.arg; resetTryEntry(r); } return o; } } throw new Error("illegal catch attempt"); }, delegateYield: function delegateYield(e, r, n) { return this.delegate = { iterator: values(e), resultName: r, nextLoc: n }, "next" === this.method && (this.arg = t), y; } }, e; }
3
3
  function asyncGeneratorStep(gen, resolve, reject, _next, _throw, key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { Promise.resolve(value).then(_next, _throw); } }
4
4
  function _asyncToGenerator(fn) { return function () { var self = this, args = arguments; return new Promise(function (resolve, reject) { var gen = fn.apply(self, args); function _next(value) { asyncGeneratorStep(gen, resolve, reject, _next, _throw, "next", value); } function _throw(err) { asyncGeneratorStep(gen, resolve, reject, _next, _throw, "throw", err); } _next(undefined); }); }; }
@@ -17,185 +17,235 @@ function _iterableToArrayLimit(r, l) { var t = null == r ? null : "undefined" !=
17
17
  function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
18
18
  function _objectWithoutProperties(source, excluded) { if (source == null) return {}; var target = _objectWithoutPropertiesLoose(source, excluded); var key, i; if (Object.getOwnPropertySymbols) { var sourceSymbolKeys = Object.getOwnPropertySymbols(source); for (i = 0; i < sourceSymbolKeys.length; i++) { key = sourceSymbolKeys[i]; if (excluded.indexOf(key) >= 0) continue; if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue; target[key] = source[key]; } } return target; }
19
19
  function _objectWithoutPropertiesLoose(source, excluded) { if (source == null) return {}; var target = {}; var sourceKeys = Object.keys(source); var key, i; for (i = 0; i < sourceKeys.length; i++) { key = sourceKeys[i]; if (excluded.indexOf(key) >= 0) continue; target[key] = source[key]; } return target; }
20
- import { Button, AutoComplete } from 'antd';
20
+ import { AutoComplete, theme } from 'antd';
21
21
  import { Select } from '@formily/antd-v5';
22
- import { DashOutlined } from '@ant-design/icons';
22
+ import { SearchOutlined } from '@ant-design/icons';
23
23
  import React, { useState } from 'react';
24
24
  import { AgGridPlus } from "../ag-grid-plus";
25
25
  import { useBoolean, useControllableValue } from 'ahooks';
26
26
  import DraggableModal from "../draggableModal";
27
27
  import { abpPagedApiAdapter } from "../adapters";
28
+ import "./index.less";
29
+
30
+ /** 选择窗口的行选择模式。 */
31
+
28
32
  var DialogSelect = function DialogSelect(props) {
33
+ var _selectRows$length;
34
+ // 这些是本组件自己的属性,不能透传给 Select(否则会落到 DOM 上触发未知属性告警)。
29
35
  var request = props.request,
30
36
  columnDefs = props.columnDefs,
31
37
  value = props.value,
32
38
  labelField = props.labelField,
33
39
  valueField = props.valueField,
34
40
  onChangeItem = props.onChangeItem,
41
+ hideBtn = props.hideBtn,
42
+ useAutoComplete = props.useAutoComplete,
43
+ queryFun = props.queryFun,
44
+ pagedApiAdapter = props.pagedApiAdapter,
45
+ _props$modalWidth = props.modalWidth,
46
+ modalWidth = _props$modalWidth === void 0 ? 960 : _props$modalWidth,
47
+ _props$dialogZIndex = props.dialogZIndex,
48
+ dialogZIndex = _props$dialogZIndex === void 0 ? 9999 : _props$dialogZIndex,
49
+ dialogMode = props.dialogMode,
50
+ dialogPageSize = props.dialogPageSize,
51
+ dialogPageSizeOptions = props.dialogPageSizeOptions,
52
+ dialogGridKey = props.dialogGridKey,
53
+ dialogDataSource = props.dialogDataSource,
54
+ dialogIsRowSelectable = props.dialogIsRowSelectable,
55
+ dialogRenderer = props.dialogRenderer,
56
+ gridComponent = props.gridComponent,
35
57
  rest = _objectWithoutProperties(props, _excluded);
58
+ var Grid = gridComponent !== null && gridComponent !== void 0 ? gridComponent : AgGridPlus;
36
59
  var _useControllableValue = useControllableValue(props),
37
60
  _useControllableValue2 = _slicedToArray(_useControllableValue, 2),
38
61
  state = _useControllableValue2[0],
39
62
  setState = _useControllableValue2[1];
40
- var _useState = useState(),
41
- _useState2 = _slicedToArray(_useState, 2),
42
- gridApi = _useState2[0],
43
- setGridApi = _useState2[1];
44
63
  var _useBoolean = useBoolean(false),
45
64
  _useBoolean2 = _slicedToArray(_useBoolean, 2),
46
65
  visible = _useBoolean2[0],
47
66
  _useBoolean2$ = _useBoolean2[1],
48
67
  setTrue = _useBoolean2$.setTrue,
49
68
  setFalse = _useBoolean2$.setFalse;
50
- var _useState3 = useState(undefined),
51
- _useState4 = _slicedToArray(_useState3, 2),
52
- selectRows = _useState4[0],
53
- setSelectRows = _useState4[1];
54
- var _useState5 = useState([]),
55
- _useState6 = _slicedToArray(_useState5, 2),
56
- items = _useState6[0],
57
- setItems = _useState6[1];
58
- var getValue = function getValue(selectRows) {
59
- var mode = props.mode,
60
- labelInValue = props.labelInValue,
61
- valueField = props.valueField,
62
- labelField = props.labelField;
63
- var selectRow = selectRows[0];
64
- var value = selectRow[valueField !== null && valueField !== void 0 ? valueField : 'id'];
65
- var label = selectRow[labelField !== null && labelField !== void 0 ? labelField : 'name'];
66
- if (props.mode === 'multiple' || props.mode === 'tags') {
67
- return labelInValue ? selectRows.map(function (it) {
69
+ var _useState = useState(undefined),
70
+ _useState2 = _slicedToArray(_useState, 2),
71
+ selectRows = _useState2[0],
72
+ setSelectRows = _useState2[1];
73
+ var _theme$useToken = theme.useToken(),
74
+ token = _theme$useToken.token;
75
+ var isMultipleValue = props.mode === 'multiple' || props.mode === 'tags';
76
+ var selectionMode = dialogMode !== null && dialogMode !== void 0 ? dialogMode : isMultipleValue ? 'multiple' : 'single';
77
+ var key = valueField !== null && valueField !== void 0 ? valueField : 'id';
78
+ var localData = Array.isArray(dialogDataSource);
79
+ var getValue = function getValue(rows) {
80
+ var row = rows[0];
81
+ var labelKey = labelField !== null && labelField !== void 0 ? labelField : 'name';
82
+ if (isMultipleValue) {
83
+ return props.labelInValue ? rows.map(function (it) {
68
84
  return {
69
- value: it[valueField !== null && valueField !== void 0 ? valueField : 'id'],
70
- label: it[labelField !== null && labelField !== void 0 ? labelField : 'name'],
85
+ value: it[key],
86
+ label: it[labelKey],
71
87
  key: it === null || it === void 0 ? void 0 : it.id
72
88
  };
73
- }) : selectRows.map(function (it) {
74
- return it[valueField !== null && valueField !== void 0 ? valueField : 'id'];
89
+ }) : rows.map(function (it) {
90
+ return it[key];
75
91
  });
76
- } else {
77
- return labelInValue ? {
78
- value: value,
79
- label: label
80
- } : value;
81
92
  }
93
+ return props.labelInValue ? {
94
+ value: row[key],
95
+ label: row[labelKey]
96
+ } : row[key];
82
97
  };
83
- var handleOk = function handleOk() {
84
- var selectRow = selectRows[0];
85
- setState(getValue(selectRows));
98
+ var close = function close() {
86
99
  setFalse();
87
- if (onChangeItem) onChangeItem(props.mode ? selectRows : selectRow);
100
+ setSelectRows(undefined);
101
+ };
102
+ var confirmRows = function confirmRows(rows) {
103
+ if (!(rows !== null && rows !== void 0 && rows.length)) return;
104
+ if (dialogIsRowSelectable && rows.some(function (row) {
105
+ return !dialogIsRowSelectable(row);
106
+ })) return;
107
+ setState(getValue(rows));
108
+ close();
109
+ // 回传完整数据行,供调用方回填关联字段。
110
+ onChangeItem === null || onChangeItem === void 0 || onChangeItem(selectionMode === 'multiple' ? rows : rows[0]);
88
111
  };
89
112
  var onSelectionChanged = function onSelectionChanged(e) {
90
- var selectedRows = e.api.getSelectedRows();
91
- setSelectRows(selectedRows);
113
+ setSelectRows(e.api.getSelectedRows());
92
114
  };
93
- return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement("div", {
94
- style: {
95
- display: 'flex',
96
- flexDirection: 'row'
115
+
116
+ // 入口做成输入框内的后缀图标:不占右侧宽度,禁用/只读时不出现。@author nokecy
117
+ var canOpen = !props.disabled && !hideBtn;
118
+ var trigger = canOpen ? /*#__PURE__*/React.createElement("span", {
119
+ className: "qc-dialog-select-trigger",
120
+ role: "button",
121
+ "aria-label": "\u6253\u5F00\u9009\u62E9\u7A97\u53E3",
122
+ title: "\u9009\u62E9"
123
+ // 阻止冒泡:点图标只开选择窗口,不展开下拉也不抢走输入框焦点。
124
+ ,
125
+ onMouseDown: function onMouseDown(e) {
126
+ e.preventDefault();
127
+ e.stopPropagation();
128
+ },
129
+ onClick: function onClick(e) {
130
+ e.stopPropagation();
131
+ setSelectRows(undefined);
132
+ setTrue();
97
133
  }
98
- }, props.useAutoComplete && !props.labelInValue ? /*#__PURE__*/React.createElement(AutoComplete, _extends({}, rest, {
134
+ }, /*#__PURE__*/React.createElement(SearchOutlined, null)) : undefined;
135
+ var mergedClassName = ['qc-dialog-select', rest.className].filter(Boolean).join(' ');
136
+ var triggerStyle = {
137
+ '--qc-dialog-select-trigger-color': token.colorTextTertiary,
138
+ '--qc-dialog-select-trigger-hover': token.colorPrimary
139
+ };
140
+ var commonProps = _objectSpread(_objectSpread({}, rest), {}, {
141
+ className: mergedClassName,
99
142
  value: state,
100
- style: _objectSpread(_objectSpread({}, rest === null || rest === void 0 ? void 0 : rest.style), {}, {
101
- width: "calc(100% - 0px)",
102
- marginRight: !props.hideBtn ? 5 : 0
103
- })
104
- })) : /*#__PURE__*/React.createElement(Select, _extends({
143
+ style: _objectSpread(_objectSpread({}, triggerStyle), rest.style || {})
144
+ }, trigger ? {
145
+ suffixIcon: trigger
146
+ } : {});
147
+ return /*#__PURE__*/React.createElement(React.Fragment, null, useAutoComplete && !props.labelInValue ? /*#__PURE__*/React.createElement(AutoComplete, commonProps) : /*#__PURE__*/React.createElement(Select, _extends({
105
148
  maxTagCount: 'responsive',
106
149
  filterOption: false
107
- }, rest, {
108
- value: state,
109
- style: _objectSpread({
110
- width: "calc(100% - 0px)",
111
- marginRight: !props.hideBtn ? 5 : 0
112
- }, rest.style || {})
113
- })), !props.disabled && !props.hideBtn ? /*#__PURE__*/React.createElement(Button, {
114
- icon: /*#__PURE__*/React.createElement(DashOutlined, null),
115
- onClick: function onClick() {
116
- setTrue();
117
- },
118
- disabled: rest.disabled
119
- }) : null), /*#__PURE__*/React.createElement(DraggableModal, {
120
- width: 960,
150
+ }, commonProps)), dialogRenderer ? dialogRenderer({
151
+ open: visible,
152
+ mode: selectionMode,
153
+ onCancel: close,
154
+ onConfirm: confirmRows
155
+ }) : /*#__PURE__*/React.createElement(DraggableModal, {
156
+ width: modalWidth,
121
157
  title: "\u9009\u62E9",
122
- style: {
123
- zIndex: 9999
124
- },
158
+ zIndex: dialogZIndex,
125
159
  destroyOnClose: true,
126
160
  open: visible,
127
- onOk: handleOk,
128
- onCancel: setFalse
129
- }, /*#__PURE__*/React.createElement(AgGridPlus, {
161
+ onOk: function onOk() {
162
+ return confirmRows(selectRows || []);
163
+ },
164
+ onCancel: close,
165
+ okButtonProps: {
166
+ disabled: !(selectRows !== null && selectRows !== void 0 && selectRows.length)
167
+ }
168
+ }, selectionMode === 'multiple' && /*#__PURE__*/React.createElement("div", {
169
+ style: {
170
+ marginBottom: 8,
171
+ textAlign: 'right'
172
+ }
173
+ }, "\u5DF2\u9009 ", (_selectRows$length = selectRows === null || selectRows === void 0 ? void 0 : selectRows.length) !== null && _selectRows$length !== void 0 ? _selectRows$length : 0, " \u9879"), /*#__PURE__*/React.createElement(Grid, _extends({
174
+ gridKey: dialogGridKey,
175
+ dataSource: dialogDataSource,
176
+ hidePagination: localData
177
+ }, localData ? {
178
+ getRowId: function getRowId(_ref) {
179
+ var data = _ref.data;
180
+ return String(data[key]);
181
+ }
182
+ } : {}, {
130
183
  style: {
131
184
  height: 450
132
185
  },
133
- onGridReady: function onGridReady(gridReadEvent) {
134
- setGridApi(gridReadEvent.api);
135
- },
136
- onFirstDataRendered: function onFirstDataRendered(_ref) {
137
- var api = _ref.api;
138
- // 多选时重开弹窗要把已经选中的行勾回来,否则用户会以为之前的选择丢了。
186
+ pageSize: dialogPageSize,
187
+ pageSizeOptions: dialogPageSizeOptions,
188
+ onFirstDataRendered: function onFirstDataRendered(_ref2) {
189
+ var api = _ref2.api;
190
+ // 重开弹窗要把已经选中的行勾回来,否则用户会以为之前的选择丢了。
139
191
  // 放在首屏数据渲染完成时做:弹窗是 destroyOnClose,打开的那一刻表格还没有数据。@author nokecy
140
- if (!Array.isArray(state) || state.length === 0) return;
141
- var key = valueField !== null && valueField !== void 0 ? valueField : 'id';
142
- var selected = state.map(function (it) {
192
+ var current = Array.isArray(state) ? state : state == null ? [] : [state];
193
+ var selected = current.map(function (it) {
143
194
  return it && _typeof(it) === 'object' ? it.value : it;
144
195
  });
196
+ if (!selected.length) return;
145
197
  api.forEachNode(function (node) {
146
- if (node.data && selected.includes(node.data[key])) {
147
- node.setSelected(true);
148
- }
198
+ if (node.data && selected.includes(node.data[key])) node.setSelected(true);
149
199
  });
150
200
  },
151
- search: (columnDefs === null || columnDefs === void 0 ? void 0 : columnDefs.filter(function (i) {
201
+ search: !localData && (columnDefs === null || columnDefs === void 0 ? void 0 : columnDefs.filter(function (i) {
152
202
  return !i.hideInSearch;
153
203
  }).length) !== 0,
154
204
  onSelectionChanged: onSelectionChanged,
155
- rowSelection: props.mode === 'multiple' ? props.mode : 'single',
156
- onRowDoubleClicked: function onRowDoubleClicked(_ref2) {
157
- var data = _ref2.data;
158
- setFalse();
159
- setState(getValue([data]));
160
- // 回传完整数据行:原来这里硬编码成 { label: data.name, value: data.code },
161
- // 与「确定」按钮走的 handleOk 口径不一致,且对没有 name/code 字段的实体直接取到 undefined。@author nokecy
162
- if (onChangeItem) onChangeItem(props.mode === 'multiple' ? [data] : data);
205
+ rowSelection: dialogIsRowSelectable ? {
206
+ mode: selectionMode === 'multiple' ? 'multiRow' : 'singleRow',
207
+ isRowSelectable: function isRowSelectable(node) {
208
+ return !!node.data && dialogIsRowSelectable(node.data);
209
+ }
210
+ } : selectionMode === 'multiple' ? 'multiple' : 'single',
211
+ onRowDoubleClicked: function onRowDoubleClicked(_ref3) {
212
+ var data = _ref3.data;
213
+ if (dialogIsRowSelectable && !dialogIsRowSelectable(data)) return;
214
+ confirmRows([data]);
163
215
  },
164
- request: ( /*#__PURE__*/function () {
165
- var _ref3 = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee(params, _, record) {
166
- var _props$pagedApiAdapte;
167
- var adapter, data, requestData;
216
+ request: localData ? undefined : ( /*#__PURE__*/function () {
217
+ var _ref4 = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime().mark(function _callee(params, _, record) {
218
+ var adapter, data;
168
219
  return _regeneratorRuntime().wrap(function _callee$(_context) {
169
220
  while (1) switch (_context.prev = _context.next) {
170
221
  case 0:
171
- adapter = (_props$pagedApiAdapte = props.pagedApiAdapter) !== null && _props$pagedApiAdapte !== void 0 ? _props$pagedApiAdapte : abpPagedApiAdapter;
222
+ adapter = pagedApiAdapter !== null && pagedApiAdapter !== void 0 ? pagedApiAdapter : abpPagedApiAdapter;
172
223
  _context.next = 3;
173
224
  return request(adapter.toRequest({
174
- filter: props !== null && props !== void 0 && props.queryFun ? props === null || props === void 0 ? void 0 : props.queryFun(params === null || params === void 0 ? void 0 : params.filter) : params === null || params === void 0 ? void 0 : params.filter,
225
+ filter: queryFun ? queryFun(params === null || params === void 0 ? void 0 : params.filter) : params === null || params === void 0 ? void 0 : params.filter,
175
226
  sorter: params === null || params === void 0 ? void 0 : params.sorter,
176
227
  skipCount: params === null || params === void 0 ? void 0 : params.skipCount,
177
- maxResultCount: params === null || params === void 0 ? void 0 : params.maxResultCount
228
+ maxResultCount: params === null || params === void 0 ? void 0 : params.maxResultCount,
229
+ record: record
178
230
  }), record);
179
231
  case 3:
180
232
  data = _context.sent;
181
- requestData = {
233
+ return _context.abrupt("return", {
182
234
  success: true,
183
235
  data: adapter.getItems(data),
184
236
  total: adapter.getTotal(data)
185
- };
186
- setItems(adapter.getItems(data));
187
- return _context.abrupt("return", requestData);
188
- case 7:
237
+ });
238
+ case 5:
189
239
  case "end":
190
240
  return _context.stop();
191
241
  }
192
242
  }, _callee);
193
243
  }));
194
244
  return function (_x, _x2, _x3) {
195
- return _ref3.apply(this, arguments);
245
+ return _ref4.apply(this, arguments);
196
246
  };
197
247
  }()),
198
248
  columnDefs: columnDefs
199
- })));
249
+ }))));
200
250
  };
201
251
  export default DialogSelect;
@@ -0,0 +1,39 @@
1
+ // 选择窗口入口放在输入框内部(后缀图标),不再在右侧另占一个按钮的宽度。@author nokecy
2
+ .qc-dialog-select {
3
+ width: 100%;
4
+
5
+ // 后缀图标可点;antd 默认给后缀 pointer-events: none。
6
+ .qc-dialog-select-trigger {
7
+ display: inline-flex;
8
+ align-items: center;
9
+ justify-content: center;
10
+ width: 100%;
11
+ height: 100%;
12
+ cursor: pointer;
13
+ pointer-events: auto;
14
+ color: var(--qc-dialog-select-trigger-color, rgba(0, 0, 0, 0.45));
15
+ transition: color 0.2s;
16
+
17
+ &:hover {
18
+ color: var(--qc-dialog-select-trigger-hover, #1677ff);
19
+ }
20
+ }
21
+
22
+ // 悬停时 antd 会把后缀淡出、换成清除图标;这里让入口始终可见,清除图标左移一格并排。
23
+ &.ant-select.ant-select:hover .ant-select-arrow:not(:last-child) {
24
+ opacity: 1;
25
+ }
26
+
27
+ &.ant-select-allow-clear .ant-select-clear {
28
+ inset-inline-end: 31px;
29
+ }
30
+
31
+ &.ant-select-allow-clear .ant-select-selection-item,
32
+ &.ant-select-allow-clear .ant-select-selection-placeholder {
33
+ padding-inline-end: 36px;
34
+ }
35
+
36
+ &.ant-select-multiple .ant-select-selector {
37
+ padding-inline-end: 38px;
38
+ }
39
+ }
@@ -67,14 +67,18 @@ var DraggableModal = function DraggableModal(props) {
67
67
  // 修复 AgGrid 等组件在 Modal 中高度不展开的问题
68
68
  // 当 Modal 打开时触发 window resize 事件
69
69
  useEffect(function () {
70
- if (open) {
71
- // 使用 requestAnimationFrame 和 setTimeout 确保 DOM 完全渲染
72
- requestAnimationFrame(function () {
73
- setTimeout(function () {
74
- window.dispatchEvent(new Event('resize'));
75
- }, 100);
76
- });
77
- }
70
+ if (!open) return;
71
+ // 使用 requestAnimationFrame 和 setTimeout 确保 DOM 完全渲染;卸载或关闭时取消,避免对已销毁的环境派发事件
72
+ var timer;
73
+ var frame = requestAnimationFrame(function () {
74
+ timer = setTimeout(function () {
75
+ window.dispatchEvent(new Event('resize'));
76
+ }, 100);
77
+ });
78
+ return function () {
79
+ cancelAnimationFrame(frame);
80
+ if (timer !== undefined) clearTimeout(timer);
81
+ };
78
82
  }, [open]);
79
83
  var _onStart = function onStart(_event, uiData) {
80
84
  var _draggleRef$current;
@@ -31,4 +31,9 @@ export type * from "./RuleBuilder";
31
31
  export type { ColumnConfig } from "./array-table/columnHelper";
32
32
  export type { CentralizedColumnScheme, QueryScheme, SchemeStorageAdapter, SchemeSyncDataDto, CurrentSchemeDto, SchemeStorageConfig, LocalStorageAdapterConfig, BackendApiAdapterConfig, UseSchemeManagerConfig, GridPlusContextValue, GlobalConfigPermissions, } from "./ag-grid-plus";
33
33
  export * from './adapters';
34
+ export { semanticTextColors, toGridTextColor, gridValueEnum } from "./ag-grid-plus/utils/valueEnumColor";
35
+ export type { SemanticPreset } from "./ag-grid-plus/utils/valueEnumColor";
36
+ export { contrastRatio, relativeLuminance, darkenUntilContrast, lightenUntilContrast, toRgb, toHsl, fromHsl } from "./utils/contrast";
37
+ export { BusinessDecimal, decimal, decimalText, nonNegativeDecimal, roundDecimal, sumDecimals, formatDecimal } from "./utils/businessDecimal";
38
+ export type { DecimalValue } from "./utils/businessDecimal";
34
39
  export type { ParseResult as RegexParseResult, ValidationResult as RegexValidationResult, RegexError, ComplexityMetrics, ASTNode, AstRegExp, RegexTemplate, TestResult as RegexTestResult, CodeMirrorWrapperProps, RegexEditorProps, RegexFlags, MatchResult, RegexTesterProps, FlagsSelectorProps, MatchItemProps, RegexRailroadDiagramProps, } from "./components/RegexEditor";
package/dist/esm/index.js CHANGED
@@ -42,5 +42,8 @@ useSchemeManager, useGridSchemes, LocalStorageSchemeAdapter, BackendApiSchemeAda
42
42
 
43
43
  // 分页适配器:值 + 类型一并导出,支持非 ABP 后端注入
44
44
  export * from "./adapters";
45
+ export { semanticTextColors, toGridTextColor, gridValueEnum } from "./ag-grid-plus/utils/valueEnumColor";
46
+ export { contrastRatio, relativeLuminance, darkenUntilContrast, lightenUntilContrast, toRgb, toHsl, fromHsl } from "./utils/contrast";
47
+ export { BusinessDecimal, decimal, decimalText, nonNegativeDecimal, roundDecimal, sumDecimals, formatDecimal } from "./utils/businessDecimal";
45
48
 
46
49
  // RegexEditor 类型定义 - 使用命名导出避免冲突
@@ -1,4 +1,5 @@
1
1
  import React from 'react';
2
2
  import './index.less';
3
+ /** 详情、表单共用工具栏:按实际操作元素统一留出间距,宽度不足时换行。@author nokecy */
3
4
  declare const ToolBar: (props: any) => React.JSX.Element;
4
5
  export default ToolBar;
@@ -1,28 +1,61 @@
1
- var _excluded = ["children", "className", "extra", "style", "renderContent", "getTargetContainer"];
1
+ var _excluded = ["children", "className", "extra", "identity", "banner", "style", "renderContent", "getTargetContainer"];
2
2
  function _objectWithoutProperties(source, excluded) { if (source == null) return {}; var target = _objectWithoutPropertiesLoose(source, excluded); var key, i; if (Object.getOwnPropertySymbols) { var sourceSymbolKeys = Object.getOwnPropertySymbols(source); for (i = 0; i < sourceSymbolKeys.length; i++) { key = sourceSymbolKeys[i]; if (excluded.indexOf(key) >= 0) continue; if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue; target[key] = source[key]; } } return target; }
3
3
  function _objectWithoutPropertiesLoose(source, excluded) { if (source == null) return {}; var target = {}; var sourceKeys = Object.keys(source); var key, i; for (i = 0; i < sourceKeys.length; i++) { key = sourceKeys[i]; if (excluded.indexOf(key) >= 0) continue; target[key] = source[key]; } return target; }
4
- import React from 'react';
5
- import { Affix, Space } from 'antd';
4
+ import React, { useCallback, useRef } from 'react';
5
+ import { Affix, theme } from 'antd';
6
6
  import "./index.less";
7
+
8
+ /** 详情、表单共用工具栏:按实际操作元素统一留出间距,宽度不足时换行。@author nokecy */
7
9
  var ToolBar = function ToolBar(props) {
8
10
  var children = props.children,
9
11
  className = props.className,
10
12
  extra = props.extra,
13
+ identity = props.identity,
14
+ banner = props.banner,
11
15
  style = props.style,
12
16
  renderContent = props.renderContent,
13
17
  getTargetContainer = props.getTargetContainer,
14
18
  restProps = _objectWithoutProperties(props, _excluded);
19
+ var _theme$useToken = theme.useToken(),
20
+ token = _theme$useToken.token; // 单据操作栏跟随宿主主题。@author nokecy
21
+ var barRef = useRef(null);
22
+ // @author nokecy:KeepAlive 内容区独立滚动,吸顶应相对其视口,避免定位到应用顶栏下面。
23
+ var defaultTarget = useCallback(function () {
24
+ var _barRef$current$paren, _barRef$current;
25
+ var parent = (_barRef$current$paren = (_barRef$current = barRef.current) === null || _barRef$current === void 0 ? void 0 : _barRef$current.parentElement) !== null && _barRef$current$paren !== void 0 ? _barRef$current$paren : null;
26
+ while (parent) {
27
+ if (/auto|scroll/.test(getComputedStyle(parent).overflowY)) return parent;
28
+ parent = parent.parentElement;
29
+ }
30
+ return window;
31
+ }, []);
15
32
  return /*#__PURE__*/React.createElement(Affix, {
16
33
  offsetTop: 2,
17
34
  style: style,
18
35
  offsetBottom: 2,
19
- target: getTargetContainer
36
+ target: getTargetContainer || defaultTarget
20
37
  }, /*#__PURE__*/React.createElement("div", {
21
- className: "antd-tool-bar"
22
- }, /*#__PURE__*/React.createElement("div", {
23
- className: "antd-tool-bar-left".trim()
24
- }, /*#__PURE__*/React.createElement(Space, null, extra)), /*#__PURE__*/React.createElement("div", {
25
- className: "antd-tool-bar-right".trim()
26
- }, /*#__PURE__*/React.createElement(Space, null, children))));
38
+ ref: barRef,
39
+ className: "antd-tool-bar",
40
+ style: {
41
+ backgroundColor: token.colorBgContainer,
42
+ color: token.colorText,
43
+ borderBlockStartColor: token.colorBorderSecondary,
44
+ gap: token.marginXS,
45
+ paddingBlock: token.paddingXXS
46
+ }
47
+ }, banner && /*#__PURE__*/React.createElement("div", {
48
+ className: "antd-tool-bar-banner"
49
+ }, banner), /*#__PURE__*/React.createElement("div", {
50
+ className: "antd-tool-bar-left",
51
+ style: {
52
+ gap: token.marginXS
53
+ }
54
+ }, extra, identity), /*#__PURE__*/React.createElement("div", {
55
+ className: "antd-tool-bar-right",
56
+ style: {
57
+ gap: token.marginXS
58
+ }
59
+ }, children)));
27
60
  };
28
61
  export default ToolBar;
@@ -1,25 +1,43 @@
1
1
  .antd-tool-bar {
2
2
  display: flex;
3
+ flex-wrap: wrap;
3
4
  align-items: center;
4
5
  box-sizing: border-box;
5
6
  width: 100%;
6
- color: rgba(0, 0, 0, 0.88);
7
7
  line-height: 40px;
8
- background-color: rgba(255, 255, 255);
9
- -webkit-backdrop-filter: blur(8px);
8
+ backdrop-filter: blur(8px);
10
9
  backdrop-filter: blur(8px);
11
10
  transition: all 0.2s ease 0s;
12
11
  inset-inline-end: 0;
13
12
  padding-inline: 16px;
14
13
  padding-block: 0;
15
- border-block-start: 1px solid rgba(5, 5, 5, 0.06);
14
+ // 颜色由组件读取主题 token;子区域继承正文色。
15
+ border-block-start: 1px solid;
16
+ }
17
+
18
+ .antd-tool-bar-banner {
19
+ flex: 1 0 100%;
20
+ min-width: 0;
21
+ line-height: normal;
16
22
  }
17
23
 
18
24
  .antd-tool-bar-left {
19
- flex: 1;
20
- color: rgba(0, 0, 0, 0.88);
25
+ flex: 1 0 auto;
26
+ color: inherit;
27
+ }
28
+
29
+ .antd-tool-bar-right {
30
+ margin-inline-start: auto;
31
+ justify-content: flex-end;
32
+ color: inherit;
21
33
  }
22
34
 
35
+ /* 直接排列组件输出的按钮,React Fragment 内的按钮也获得相同间距。@author nokecy */
36
+ .antd-tool-bar-left,
23
37
  .antd-tool-bar-right {
24
- color: rgba(0, 0, 0, 0.88);
38
+ display: flex;
39
+ flex-wrap: wrap;
40
+ align-items: center;
41
+ min-width: 0;
42
+ max-width: 100%;
25
43
  }
@@ -0,0 +1,11 @@
1
+ import Decimal from 'decimal.js';
2
+ /** 业务值保留十进制文本,运算使用十进制库;整型标识和时间不经过此入口。@author nokecy */
3
+ export declare const BusinessDecimal: typeof Decimal;
4
+ export type DecimalValue = string | number | Decimal | null | undefined;
5
+ export declare const decimal: (value: DecimalValue) => Decimal;
6
+ export declare const decimalText: (value: DecimalValue) => string;
7
+ export declare const nonNegativeDecimal: (value: DecimalValue) => string;
8
+ export declare const roundDecimal: (value: DecimalValue, places: number) => string;
9
+ export declare const sumDecimals: (values: DecimalValue[]) => string;
10
+ /** 指定取位规则显示,千分位直接处理文本,不转换为 JavaScript number。@author nokecy */
11
+ export declare const formatDecimal: (value: DecimalValue, places?: number, minimumPlaces?: number) => string;