@thefreshop/tb 1.1.3 → 1.1.4
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 +273 -0
- package/dist/cjs/index.js +38 -8
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/tbframe/layout/main.d.ts +3 -1
- package/dist/cjs/tbpage/component/modules/antBaseTable/btn_widget.d.ts +3 -1
- package/dist/cjs/types/antBaseTable.types.d.ts +1 -0
- package/dist/cjs/types/tbframe.types.d.ts +1 -0
- package/dist/esm/index.js +38 -8
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/tbframe/layout/main.d.ts +3 -1
- package/dist/esm/tbpage/component/modules/antBaseTable/btn_widget.d.ts +3 -1
- package/dist/esm/types/antBaseTable.types.d.ts +1 -0
- package/dist/esm/types/tbframe.types.d.ts +1 -0
- package/dist/index.d.ts +2 -0
- package/package.json +1 -1
package/README.md
ADDED
|
@@ -0,0 +1,273 @@
|
|
|
1
|
+
# @thefreshop/tb — tb framework
|
|
2
|
+
|
|
3
|
+
## 1) 패키지 이름 + 한 줄 소개
|
|
4
|
+
Ant Design 기반의 React UI 프레임워크로, 탭형 어드민 프레임과 CRUD 테이블/검색/페이지 스캐폴드를 제공합니다.
|
|
5
|
+
|
|
6
|
+
## 2) Why / What it solves
|
|
7
|
+
- 탭 기반 어드민 프레임(Top/Nav/Bottom)과 라우팅을 빠르게 구성.
|
|
8
|
+
- 검색/테이블/모달 CRUD 흐름을 재사용 가능한 컴포넌트로 표준화.
|
|
9
|
+
- Ant Design을 기반으로 일관된 관리자 UI 구축.
|
|
10
|
+
|
|
11
|
+
## 3) Features
|
|
12
|
+
- [x] 탭 기반 프레임 레이아웃 + 동적 라우팅
|
|
13
|
+
- [x] 세션 기반 탭 상태 저장(`sessionStorage`)
|
|
14
|
+
- [x] 검색 박스 + 테이블 + 로딩 레이아웃 스캐폴드
|
|
15
|
+
- [x] Ant Design Table 기반 CRUD 래퍼 + 모달 생성/수정
|
|
16
|
+
- [x] 한국어 로케일 기본 제공(dayjs/moment/antd)
|
|
17
|
+
|
|
18
|
+
## 4) Installation
|
|
19
|
+
```bash
|
|
20
|
+
npm i @thefreshop/tb
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
```bash
|
|
24
|
+
yarn add @thefreshop/tb
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
```bash
|
|
28
|
+
pnpm add @thefreshop/tb
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
### Peer Dependencies
|
|
32
|
+
이 패키지는 아래 피어 의존성을 필요로 합니다:
|
|
33
|
+
```bash
|
|
34
|
+
npm i react react-dom react-router antd @ant-design/icons dayjs moment react-error-boundary @monaco-editor/react
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
## 5) Quick Start
|
|
38
|
+
```tsx
|
|
39
|
+
import React from "react";
|
|
40
|
+
import { TbProvider, TbpProvider, TbFrame } from "@thefreshop/tb";
|
|
41
|
+
import type { navType, topType, tbframeType } from "@thefreshop/tb";
|
|
42
|
+
|
|
43
|
+
const setting: tbframeType = { islogin: false, startTabKey: "dashboard" };
|
|
44
|
+
const top: topType = { title: "TB Admin", topMenuSetting: [{ key: "main", title: "Main" }] };
|
|
45
|
+
const nav: navType = {
|
|
46
|
+
menuSet: [
|
|
47
|
+
{
|
|
48
|
+
parentkey: "main",
|
|
49
|
+
menuSetting: [
|
|
50
|
+
{ tab: { key: "dashboard", title: "Dashboard", page: <div>Home</div> }, hasPage: true },
|
|
51
|
+
],
|
|
52
|
+
},
|
|
53
|
+
],
|
|
54
|
+
};
|
|
55
|
+
|
|
56
|
+
export default function App() {
|
|
57
|
+
return (
|
|
58
|
+
<TbProvider basename="/">
|
|
59
|
+
<TbpProvider>
|
|
60
|
+
<TbFrame setting={setting} top={top} nav={nav} />
|
|
61
|
+
</TbpProvider>
|
|
62
|
+
</TbProvider>
|
|
63
|
+
);
|
|
64
|
+
}
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
## 6) Usage
|
|
68
|
+
### 기본 사용
|
|
69
|
+
```tsx
|
|
70
|
+
import { Tbpage } from "@thefreshop/tb";
|
|
71
|
+
|
|
72
|
+
const columns = [
|
|
73
|
+
{
|
|
74
|
+
tableProps: { dataIndex: "name", title: "Name" },
|
|
75
|
+
search: true,
|
|
76
|
+
create: true,
|
|
77
|
+
modify: true,
|
|
78
|
+
},
|
|
79
|
+
];
|
|
80
|
+
|
|
81
|
+
export default function Users() {
|
|
82
|
+
return (
|
|
83
|
+
<Tbpage
|
|
84
|
+
title="Users"
|
|
85
|
+
decs="User list"
|
|
86
|
+
searchOption={[{ key: "base", items: [{ type: "input", key: "name", title: "Name" }] }]}
|
|
87
|
+
tableProps={{ rowKey: "id", columns, dataSource: [] }}
|
|
88
|
+
/>
|
|
89
|
+
);
|
|
90
|
+
}
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
### 옵션/설정(핵심 props 요약)
|
|
94
|
+
#### TbFrame
|
|
95
|
+
| 이름 | 타입 | 기본값 | 설명 |
|
|
96
|
+
| --- | --- | --- | --- |
|
|
97
|
+
| `setting` | `tbframeType` | - | 로그인/시작 탭 등 기본 프레임 설정 |
|
|
98
|
+
| `top` | `topType` | - | 상단 영역 설정 |
|
|
99
|
+
| `nav` | `navType` | - | 네비게이션/탭 정의 |
|
|
100
|
+
| `bottom` | `bottomType` | `undefined` | 하단 영역 |
|
|
101
|
+
| `top_banner` | `React.ReactNode` | `undefined` | 상단 배너 영역 |
|
|
102
|
+
| `hashmode` | `boolean` | `false` | 해시 라우팅 사용 여부 |
|
|
103
|
+
| `frameStyle` | `FrameStyleType` | `undefined` | 스타일 오버라이드 |
|
|
104
|
+
|
|
105
|
+
#### Tbpage
|
|
106
|
+
| 이름 | 타입 | 기본값 | 설명 |
|
|
107
|
+
| --- | --- | --- | --- |
|
|
108
|
+
| `tableProps` | `any` | - | AntBaseTable에 전달되는 props |
|
|
109
|
+
| `searchOption` | `any` | `undefined` | SearchBox 옵션 |
|
|
110
|
+
| `searchDisabled` | `boolean` | `false` | 검색 비활성화 |
|
|
111
|
+
| `onSubmit` | `(searchdata?, rowdata?, isReset?) => void` | `undefined` | 검색 제출/리셋 콜백 |
|
|
112
|
+
| `isLoading` | `boolean` | `undefined` | 로딩 오버레이 |
|
|
113
|
+
| `title`/`decs` | `string` | `undefined` | 타이틀/설명 |
|
|
114
|
+
| `PageStyle` | `PageStyleType` | `undefined` | 스타일 오버라이드 |
|
|
115
|
+
|
|
116
|
+
> 더 많은 props 및 타입은 `docs/API.md`를 참고하세요.
|
|
117
|
+
|
|
118
|
+
### 반환값/에러
|
|
119
|
+
| 항목 | 반환 | 에러/주의사항 |
|
|
120
|
+
| --- | --- | --- |
|
|
121
|
+
| `useTbState()` | `ProviderType` | `TbProvider` 밖에서 호출 시 Error throw |
|
|
122
|
+
|
|
123
|
+
## 7) API Reference
|
|
124
|
+
API가 많은 관계로 `docs/API.md`로 분리했습니다.
|
|
125
|
+
- 핵심 export: `TbProvider`, `useTbState`, `tbContext`, `TbFrame`, `TbpProvider`, `ContentLayout`, `Tbpage`, `TbpageSm`, `Tblist`, `TbpageMulti`, `AntBaseTable`, `AntBaseModalCreate`, `AuthTable` 및 타입들
|
|
126
|
+
|
|
127
|
+
## 8) TypeScript
|
|
128
|
+
- 타입 엔트리: `package.json`의 `types: ./dist/cjs/index.d.ts`
|
|
129
|
+
- 공개 타입: `export type * from "./types"`로 노출
|
|
130
|
+
|
|
131
|
+
```ts
|
|
132
|
+
import type { tbframeType, navType, antBasePropsType } from "@thefreshop/tb";
|
|
133
|
+
```
|
|
134
|
+
|
|
135
|
+
## 9) Compatibility
|
|
136
|
+
- **Runtime**: 브라우저 기반 React 앱 (DOM lib 사용)
|
|
137
|
+
- **React**: `react@^19.1.1` (peer)
|
|
138
|
+
- **Router**: `react-router@^7.10.0` (peer)
|
|
139
|
+
- **UI**: `antd@^6.0.0` (peer)
|
|
140
|
+
- **CJS/ESM**: `main`(CJS), `module`(ESM) 빌드 제공
|
|
141
|
+
- **Node 엔진**: Not found in repository
|
|
142
|
+
|
|
143
|
+
## 10) Bundling / Tree-shaking
|
|
144
|
+
- `exports`/`sideEffects` 필드가 없어 트리 셰이킹 동작은 번들러 설정에 의존합니다.
|
|
145
|
+
- Rollup 빌드에서 CSS Modules를 런타임 inject 하므로 일부 부수효과(side effects)가 있을 수 있습니다.
|
|
146
|
+
|
|
147
|
+
## 11) Examples
|
|
148
|
+
### Basic (프레임 구성)
|
|
149
|
+
```tsx
|
|
150
|
+
import { TbProvider, TbpProvider, TbFrame } from "@thefreshop/tb";
|
|
151
|
+
import type { navType, topType, tbframeType } from "@thefreshop/tb";
|
|
152
|
+
|
|
153
|
+
const setting: tbframeType = { islogin: false };
|
|
154
|
+
const top: topType = { title: "Admin", topMenuSetting: [{ key: "main", title: "Main" }] };
|
|
155
|
+
const nav: navType = {
|
|
156
|
+
menuSet: [
|
|
157
|
+
{
|
|
158
|
+
parentkey: "main",
|
|
159
|
+
menuSetting: [{ tab: { key: "home", title: "Home", page: <div>Home</div> }, hasPage: true }],
|
|
160
|
+
},
|
|
161
|
+
],
|
|
162
|
+
};
|
|
163
|
+
|
|
164
|
+
export default function App() {
|
|
165
|
+
return (
|
|
166
|
+
<TbProvider>
|
|
167
|
+
<TbpProvider>
|
|
168
|
+
<TbFrame setting={setting} top={top} nav={nav} />
|
|
169
|
+
</TbpProvider>
|
|
170
|
+
</TbProvider>
|
|
171
|
+
);
|
|
172
|
+
}
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
### Advanced (검색 + 테이블)
|
|
176
|
+
```tsx
|
|
177
|
+
import { Tbpage } from "@thefreshop/tb";
|
|
178
|
+
|
|
179
|
+
const columns = [
|
|
180
|
+
{ tableProps: { dataIndex: "name", title: "Name" }, search: true, create: true, modify: true },
|
|
181
|
+
];
|
|
182
|
+
|
|
183
|
+
export default function Users() {
|
|
184
|
+
return (
|
|
185
|
+
<Tbpage
|
|
186
|
+
title="Users"
|
|
187
|
+
searchOption={[{ key: "base", items: [{ type: "input", key: "name", title: "Name" }] }]}
|
|
188
|
+
tableProps={{ rowKey: "id", columns, dataSource: [] }}
|
|
189
|
+
onSubmit={(query, data) => {
|
|
190
|
+
console.log(query, data);
|
|
191
|
+
}}
|
|
192
|
+
/>
|
|
193
|
+
);
|
|
194
|
+
}
|
|
195
|
+
```
|
|
196
|
+
|
|
197
|
+
### Real-world (멀티 패널)
|
|
198
|
+
```tsx
|
|
199
|
+
import { TbpageMulti } from "@thefreshop/tb";
|
|
200
|
+
|
|
201
|
+
export default function Dashboard() {
|
|
202
|
+
return (
|
|
203
|
+
<TbpageMulti
|
|
204
|
+
title="Dashboard"
|
|
205
|
+
arrtableProps={[
|
|
206
|
+
{ type: "table", title: "Left", tableprops: { rowKey: "id", columns: [], dataSource: [] } },
|
|
207
|
+
{ type: "module", title: "Right", module: <div>Custom Module</div> },
|
|
208
|
+
]}
|
|
209
|
+
arrflex={[2, 1]}
|
|
210
|
+
direction="row"
|
|
211
|
+
/>
|
|
212
|
+
);
|
|
213
|
+
}
|
|
214
|
+
```
|
|
215
|
+
|
|
216
|
+
## 12) Troubleshooting
|
|
217
|
+
1. **peerDependencies 충돌**: React/antd/react-router 버전이 맞지 않으면 런타임 오류가 발생합니다.
|
|
218
|
+
2. **CSS Modules 미적용**: 소비 앱 번들러에서 CSS Modules가 비활성화되면 레이아웃이 깨집니다.
|
|
219
|
+
3. **SSR 환경 오류**: `sessionStorage` 사용으로 SSR 시 `window` 관련 에러가 날 수 있습니다.
|
|
220
|
+
4. **CJS/ESM 혼용 오류**: 번들러가 `module`/`main` 선택을 잘못하면 중복 React 경고가 발생할 수 있습니다.
|
|
221
|
+
5. **타입 인식 실패**: `types` 경로(`dist/cjs/index.d.ts`)가 올바르게 배포되었는지 확인하세요.
|
|
222
|
+
6. **Ant Design 스타일 누락**: 소비 앱에서 antd 스타일을 로드하지 않으면 컴포넌트가 깨집니다.
|
|
223
|
+
7. **모달 폼 초기값 미반영**: `AntBaseModalCreate`에서 `initialValues` 사용 시 `open` 타이밍을 확인하세요.
|
|
224
|
+
|
|
225
|
+
## 13) FAQ
|
|
226
|
+
1. **React 18에서도 동작하나요?** Not found in repository (peerDependencies는 React 19 기준입니다).
|
|
227
|
+
2. **React Router v6 사용 가능?** Not found in repository (peerDependencies는 v7 기준입니다).
|
|
228
|
+
3. **라우팅 구조는 어떻게 만들나요?** `nav.menuSet`과 `nav.globalTabs` 기반으로 라우트가 자동 생성됩니다.
|
|
229
|
+
4. **해시 라우팅을 지원하나요?** `TbFrame`의 `hashmode`로 지원합니다.
|
|
230
|
+
5. **탭 상태는 어디에 저장되나요?** `sessionStorage`의 `tbFrameState` 키에 저장됩니다.
|
|
231
|
+
6. **로케일 설정은 어디서 하나요?** `TbpProvider`가 `antd` `ConfigProvider`와 `ko_KR` 로케일을 설정합니다.
|
|
232
|
+
7. **테스트 예제나 Storybook이 있나요?** Not found in repository.
|
|
233
|
+
8. **변경 이력(Changelog)이 있나요?** No changelog found.
|
|
234
|
+
|
|
235
|
+
## 14) Contributing
|
|
236
|
+
### 로컬 개발
|
|
237
|
+
```bash
|
|
238
|
+
yarn install
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
```bash
|
|
242
|
+
yarn dev
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
```bash
|
|
246
|
+
yarn build
|
|
247
|
+
```
|
|
248
|
+
|
|
249
|
+
- 테스트/린트 스크립트: Not found in repository
|
|
250
|
+
- 배포 스크립트: Not found in repository
|
|
251
|
+
|
|
252
|
+
## 15) Security
|
|
253
|
+
- 공급망 보안: peerDependencies 버전을 고정/검증하세요.
|
|
254
|
+
- 토큰/시크릿 관리: 레포에 환경변수 파일이 없으므로 소비 앱에서 안전하게 관리하세요.
|
|
255
|
+
- 취약점 신고: `package.json`의 `bugs.url` 참고.
|
|
256
|
+
|
|
257
|
+
## 16) License
|
|
258
|
+
- `package.json`: MIT
|
|
259
|
+
- LICENSE 파일: No license file found
|
|
260
|
+
|
|
261
|
+
## 17) Quick Commands
|
|
262
|
+
| 목적 | 명령 | 비고 |
|
|
263
|
+
| --- | --- | --- |
|
|
264
|
+
| 개발(와치) | ```bash
|
|
265
|
+
yarn dev
|
|
266
|
+
``` | Rollup watch 빌드 |
|
|
267
|
+
| 빌드 | ```bash
|
|
268
|
+
yarn build
|
|
269
|
+
``` | `dist/` 출력 |
|
|
270
|
+
| 테스트 | Not found in repository | - |
|
|
271
|
+
| 린트 | Not found in repository | - |
|
|
272
|
+
| 타입체크 | Not found in repository | - |
|
|
273
|
+
| 퍼블리시 | Not found in repository | - |
|
package/dist/cjs/index.js
CHANGED
|
@@ -403,11 +403,11 @@ var css_248z$7 = ".main-module_mainFrame__Etjvl{height:100%;width:100%}.main-mod
|
|
|
403
403
|
var styles$5 = {"mainFrame":"main-module_mainFrame__Etjvl","mainFrameFullscreen":"main-module_mainFrameFullscreen__oEwV8"};
|
|
404
404
|
styleInject(css_248z$7);
|
|
405
405
|
|
|
406
|
-
const Main = () => {
|
|
406
|
+
const Main = ({ style }) => {
|
|
407
407
|
const [sp] = reactRouter.useSearchParams();
|
|
408
408
|
const isFs = sp.get("fs") === "1" || sp.get("fullscreen") === "1";
|
|
409
409
|
// console.log("Main render, isFs:", isFs);
|
|
410
|
-
return (React.createElement("div", { className: isFs ? styles$5.mainFrameFullscreen : styles$5.mainFrame },
|
|
410
|
+
return (React.createElement("div", { className: isFs ? styles$5.mainFrameFullscreen : styles$5.mainFrame, style: style },
|
|
411
411
|
React.createElement(reactRouter.Outlet, null)));
|
|
412
412
|
};
|
|
413
413
|
|
|
@@ -636,7 +636,7 @@ const MainLayout = ({ errMsg, setting, top_banner, nav, user, top, bottom, frame
|
|
|
636
636
|
React.createElement(Nav, { nav: nav, islogin: setting.islogin ?? false, frameStyle: frameStyle }),
|
|
637
637
|
React.createElement("div", { className: styles$9.contentsFrame, style: frameStyle?.contentsFrame },
|
|
638
638
|
React.createElement(Tabs, { nav: nav, frameStyle: frameStyle }),
|
|
639
|
-
React.createElement(Main,
|
|
639
|
+
React.createElement(Main, { style: frameStyle?.contentsMainFrame }))),
|
|
640
640
|
React.createElement("div", { className: styles$9.bottomFrame, style: frameStyle?.bottomFrame }, bottom && React.createElement(Bottom, { bottom: bottom, frameStyle: frameStyle }))))));
|
|
641
641
|
};
|
|
642
642
|
|
|
@@ -705,7 +705,7 @@ const FORM_CREATE = "등록";
|
|
|
705
705
|
|
|
706
706
|
* @todo
|
|
707
707
|
*/
|
|
708
|
-
const TableTopButtonGroup = ({ isSelect, onRefresh, isCounter, autoRefreshTime, addProps, modifyProps, deleteProps, removeProps, resetProps, customProps, }) => {
|
|
708
|
+
const TableTopButtonGroup = ({ isSelect, onRefresh, isCounter, autoRefreshTime, addProps, modifyProps, deleteProps, removeProps, resetProps, customProps, isInSearch = false, onInSearch, }) => {
|
|
709
709
|
if (!addProps && !modifyProps && !deleteProps && !removeProps && !resetProps && !customProps && !onRefresh) {
|
|
710
710
|
return null;
|
|
711
711
|
}
|
|
@@ -752,7 +752,8 @@ const TableTopButtonGroup = ({ isSelect, onRefresh, isCounter, autoRefreshTime,
|
|
|
752
752
|
deleteProps ? (React.createElement(antd.Button, { danger: true, disabled: !isSelect || deleteProps.disable, onClick: deleteProps.onFun }, deleteProps.title ? deleteProps.title : TABLE_DELETE)) : null,
|
|
753
753
|
resetProps ? (React.createElement(antd.Button, { disabled: !isSelect || resetProps.disable, onClick: resetProps.onFun }, resetProps.title ? resetProps.title : TABLE_RESET)) : null,
|
|
754
754
|
removeProps ? (React.createElement(antd.Button, { danger: true, type: "primary", disabled: !isSelect || removeProps.disable, onClick: removeProps.onFun }, removeProps.title ? removeProps.title : TABLE_REMOVE)) : null,
|
|
755
|
-
customProps?.rightRender && customProps?.rightRender()
|
|
755
|
+
customProps?.rightRender && customProps?.rightRender(),
|
|
756
|
+
isInSearch && onInSearch ? React.createElement(InSearchForm, { onInSearch: onInSearch }) : null))));
|
|
756
757
|
};
|
|
757
758
|
const TableBottomButtonGroup = ({ isSelect, topProps, bottomProps, upProps, downProps, }) => {
|
|
758
759
|
return (React.createElement(antd.Row, { justify: "space-between" },
|
|
@@ -766,6 +767,22 @@ const TableBottomButtonGroup = ({ isSelect, topProps, bottomProps, upProps, down
|
|
|
766
767
|
downProps ? (React.createElement(antd.Button, { disabled: !isSelect || downProps.disable, onClick: downProps.onFun }, TABLE_DOWN)) : null,
|
|
767
768
|
bottomProps ? (React.createElement(antd.Button, { disabled: !isSelect || bottomProps.disable, onClick: bottomProps.onFun }, TABLE_BOTTOM)) : null))));
|
|
768
769
|
};
|
|
770
|
+
const InSearchForm = ({ onInSearch }) => {
|
|
771
|
+
const [inputSearch, setInputSearch] = React.useState("");
|
|
772
|
+
const SearchClick = () => {
|
|
773
|
+
onInSearch(inputSearch);
|
|
774
|
+
};
|
|
775
|
+
const activeEnter = (e) => {
|
|
776
|
+
if (e.key === "Enter") {
|
|
777
|
+
SearchClick();
|
|
778
|
+
}
|
|
779
|
+
};
|
|
780
|
+
return (React.createElement(antd.Space.Compact, null,
|
|
781
|
+
React.createElement(antd.Input, { style: { width: "150px" }, onChange: (e) => {
|
|
782
|
+
setInputSearch(e.target.value);
|
|
783
|
+
}, value: inputSearch, onKeyDown: (e) => activeEnter(e) }),
|
|
784
|
+
React.createElement(antd.Button, { onClick: SearchClick }, "\uAC80\uC0C9")));
|
|
785
|
+
};
|
|
769
786
|
|
|
770
787
|
var commonjsGlobal = typeof globalThis !== 'undefined' ? globalThis : typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};
|
|
771
788
|
|
|
@@ -23343,11 +23360,24 @@ const AntBaseModalCreate = ({ modalProps, formProps, props }) => {
|
|
|
23343
23360
|
|
|
23344
23361
|
const { Title: Title$1 } = antd.Typography;
|
|
23345
23362
|
const { confirm: confirm$1 } = antd.Modal;
|
|
23346
|
-
const AntBaseTable = ({ bordered, className, rowKey, rowName, dataSource, initData, customColumn, customValue, columns, expandable, size, onDoubleClick, onClick, selectProps, addProps, modifyProps, deleteProps, removeProps, resetProps, customProps, topProps, bottomProps, upProps, downProps, pageProps, scroll, onRefresh, isCounter, autoRefreshTime, createModalWidth = 1000, onCreateClose, }, ref) => {
|
|
23363
|
+
const AntBaseTable = ({ bordered, className, rowKey, rowName, dataSource, initData, customColumn, customValue, columns, expandable, size, onDoubleClick, onClick, selectProps, addProps, modifyProps, deleteProps, removeProps, resetProps, customProps, topProps, bottomProps, upProps, downProps, pageProps, scroll, onRefresh, isCounter, autoRefreshTime, createModalWidth = 1000, onCreateClose, isInSearch = false, }, ref) => {
|
|
23347
23364
|
const [selectedRowKeys, setSelectedRowKeys] = React.useState([]);
|
|
23348
23365
|
const [selectedRow, setSelectedRow] = React.useState();
|
|
23349
23366
|
const [popupCreate, setPopupCreate] = React.useState(false);
|
|
23350
23367
|
const [popupModify, setPopupModify] = React.useState(false);
|
|
23368
|
+
const [viewData, setViewData] = React.useState(dataSource);
|
|
23369
|
+
const onInSearch = (value) => {
|
|
23370
|
+
const search = value.trim().toLowerCase();
|
|
23371
|
+
if (!search) {
|
|
23372
|
+
setViewData(dataSource);
|
|
23373
|
+
return;
|
|
23374
|
+
}
|
|
23375
|
+
setViewData(dataSource.filter((item) => Object.values(item).some((itemValue) => {
|
|
23376
|
+
if (itemValue == null)
|
|
23377
|
+
return false;
|
|
23378
|
+
return String(itemValue).toLowerCase().includes(search);
|
|
23379
|
+
})));
|
|
23380
|
+
};
|
|
23351
23381
|
React.useEffect(() => {
|
|
23352
23382
|
setSelectedRow(dataSource?.find((m) => {
|
|
23353
23383
|
if (m) {
|
|
@@ -23440,7 +23470,7 @@ const AntBaseTable = ({ bordered, className, rowKey, rowName, dataSource, initDa
|
|
|
23440
23470
|
height: "100%",
|
|
23441
23471
|
padding: "20px",
|
|
23442
23472
|
} },
|
|
23443
|
-
React.createElement(TableTopButtonGroup, { isSelect: isSelect, isCounter: isCounter, onRefresh: onRefresh, autoRefreshTime: autoRefreshTime, addProps: addProps && {
|
|
23473
|
+
React.createElement(TableTopButtonGroup, { isInSearch: isInSearch, onInSearch: onInSearch, isSelect: isSelect, isCounter: isCounter, onRefresh: onRefresh, autoRefreshTime: autoRefreshTime, addProps: addProps && {
|
|
23444
23474
|
...addProps,
|
|
23445
23475
|
onFun: () => {
|
|
23446
23476
|
if (addProps.customModal) {
|
|
@@ -23621,7 +23651,7 @@ const AntBaseTable = ({ bordered, className, rowKey, rowName, dataSource, initDa
|
|
|
23621
23651
|
return {
|
|
23622
23652
|
onClick: () => { }, // click header row
|
|
23623
23653
|
};
|
|
23624
|
-
}, dataSource:
|
|
23654
|
+
}, dataSource: viewData?.map((i) => i),
|
|
23625
23655
|
// columns={tableColumns(
|
|
23626
23656
|
// columns.concat(
|
|
23627
23657
|
// deleteCol({
|