@tmagic/table 1.2.0-beta.2 → 1.2.0-beta.21

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.
@@ -1,72 +1,61 @@
1
1
  <template>
2
- <el-table-column :label="config.label" :width="config.width" :fixed="config.fixed">
2
+ <TMagicTableColumn :label="config.label" :width="config.width" :fixed="config.fixed">
3
3
  <template v-slot="scope">
4
- <el-button
4
+ <TMagicButton
5
5
  v-for="(action, actionIndex) in config.actions"
6
6
  v-show="display(action.display, scope.row) && !editState[scope.$index]"
7
- v-html="action.text"
8
7
  class="action-btn"
9
8
  text
10
9
  type="primary"
11
10
  size="small"
11
+ :icon="action.icon"
12
12
  :key="actionIndex"
13
13
  @click="actionHandler(action, scope.row, scope.$index)"
14
- ></el-button>
15
- <el-button
14
+ ><span v-html="formatter(action.text, scope.row)"></span
15
+ ></TMagicButton>
16
+ <TMagicButton
16
17
  class="action-btn"
17
18
  v-show="editState[scope.$index]"
18
19
  text
19
20
  type="primary"
20
21
  size="small"
21
22
  @click="save(scope.$index, config)"
22
- >保存</el-button
23
+ >保存</TMagicButton
23
24
  >
24
- <el-button
25
+ <TMagicButton
25
26
  class="action-btn"
26
27
  v-show="editState[scope.$index]"
27
28
  text
28
29
  type="primary"
29
30
  size="small"
30
31
  @click="editState[scope.$index] = undefined"
31
- >取消</el-button
32
+ >取消</TMagicButton
32
33
  >
33
34
  </template>
34
- </el-table-column>
35
+ </TMagicTableColumn>
35
36
  </template>
36
37
 
37
- <script lang="ts">
38
- import { PropType } from 'vue';
39
- import { ElMessage, ElMessageBox } from 'element-plus';
38
+ <script lang="ts" setup name="MTableActionsColumn">
39
+ import { TMagicButton, tMagicMessage, TMagicTableColumn } from '@tmagic/design';
40
40
 
41
41
  import { ColumnActionConfig, ColumnConfig } from './schema';
42
- </script>
43
-
44
- <script lang="ts" setup>
45
- const props = defineProps({
46
- columns: {
47
- type: Array as PropType<any[]>,
48
- require: true,
49
- default: () => [],
50
- },
51
-
52
- config: {
53
- type: Object as PropType<ColumnConfig>,
54
- require: true,
55
- default: () => {},
56
- },
57
-
58
- rowkeyName: {
59
- type: String,
60
- default: 'c_id',
61
- },
62
42
 
63
- editState: {
64
- type: Object,
65
- default: () => {},
43
+ const props = withDefaults(
44
+ defineProps<{
45
+ columns: any[];
46
+ config: ColumnConfig;
47
+ rowkeyName?: string;
48
+ editState?: any;
49
+ }>(),
50
+ {
51
+ columns: () => [],
52
+ config: () => ({}),
53
+ rowkeyName: 'c_id',
54
+ editState: () => [],
66
55
  },
67
- });
56
+ );
68
57
 
69
- const emit = defineEmits(['afterAction']);
58
+ const emit = defineEmits(['after-action']);
70
59
 
71
60
  const display = (fuc: boolean | Function | undefined, row: any) => {
72
61
  if (typeof fuc === 'function') {
@@ -75,56 +64,16 @@ const display = (fuc: boolean | Function | undefined, row: any) => {
75
64
  return true;
76
65
  };
77
66
 
78
- const success = (msg: string, action: ColumnActionConfig, row: any) => {
79
- ElMessage.success(msg);
80
- action.after?.(row);
81
- };
82
-
83
- const error = (msg: string) => ElMessage.error(msg);
84
-
85
- const deleteAction = async (action: ColumnActionConfig, row: any) => {
86
- await ElMessageBox.confirm(`确认删除${row[action.name || 'c_name']}(${row[props.rowkeyName]})?`, '提示', {
87
- confirmButtonText: '确定',
88
- cancelButtonText: '取消',
89
- type: 'warning',
90
- });
91
-
92
- const res = await action.handler?.(row);
93
-
94
- if (res.ret === 0) {
95
- success('删除成功!', action, row);
96
- } else {
97
- error(res.msg || '删除失败');
98
- }
99
- };
100
-
101
- const copyHandler = async (action: ColumnActionConfig, row: any) => {
102
- await ElMessageBox.confirm(`确定复制${row[action.name || 'c_name']}(${row.c_id})?`, '提示', {
103
- confirmButtonText: '确定',
104
- cancelButtonText: '取消',
105
- type: 'warning',
106
- });
107
-
108
- try {
109
- const res = await action.handler?.(row);
110
-
111
- if (res.ret === 0) {
112
- success('复制成功!', action, row);
113
- } else {
114
- error(`复制失败!${res.msg}`);
115
- }
116
- } catch (e) {
117
- error('复制失败!');
67
+ const formatter = (fuc: string | Function | undefined, row: any) => {
68
+ if (typeof fuc === 'function') {
69
+ return fuc(row);
118
70
  }
71
+ return fuc;
119
72
  };
120
73
 
121
74
  const actionHandler = async (action: ColumnActionConfig, row: any, index: number) => {
122
75
  await action.before?.(row);
123
- if (action.type === 'delete') {
124
- await deleteAction(action, row);
125
- } else if (action.type === 'copy') {
126
- await copyHandler(action, row);
127
- } else if (action.type === 'edit') {
76
+ if (action.type === 'edit') {
128
77
  props.editState[index] = row;
129
78
  } else {
130
79
  await action.handler?.(row);
@@ -150,20 +99,15 @@ const save = async (index: number, config: ColumnConfig) => {
150
99
 
151
100
  if (res) {
152
101
  if (res.ret === 0) {
153
- ElMessage.success('保存成功');
102
+ tMagicMessage.success('保存成功');
154
103
  props.editState[index] = undefined;
155
- emit('afterAction');
104
+ emit('after-action');
156
105
  } else {
157
- ElMessage.error({
158
- duration: 10000,
159
- showClose: true,
160
- dangerouslyUseHTMLString: true,
161
- message: res.msg || '保存失败',
162
- });
106
+ tMagicMessage.error(res.msg || '保存失败');
163
107
  }
164
108
  } else {
165
109
  props.editState[index] = undefined;
166
- emit('afterAction');
110
+ emit('after-action');
167
111
  }
168
112
  };
169
113
  </script>
@@ -1,37 +1,43 @@
1
1
  <template>
2
- <el-table-column type="expand">
2
+ <TMagicTableColumn type="expand">
3
3
  <template #default="scope">
4
- <m-table
4
+ <MTable
5
5
  v-if="config.table"
6
6
  :show-header="false"
7
7
  :columns="config.table"
8
- :data="scope.row[config.prop]"
9
- ></m-table>
10
- <m-form
8
+ :data="(config.prop && scope.row[config.prop]) || []"
9
+ ></MTable>
10
+ <MForm
11
11
  v-if="config.form"
12
12
  :config="config.form"
13
- :init-values="config.values || scope.row[config.prop] || {}"
14
- ></m-form>
13
+ :init-values="config.values || (config.prop && scope.row[config.prop]) || {}"
14
+ ></MForm>
15
+ <div v-if="config.expandContent" v-html="config.expandContent(scope.row, config.prop)"></div>
16
+ <component v-if="config.component" :is="config.component" v-bind="componentProps(scope.row)"></component>
15
17
  </template>
16
- </el-table-column>
18
+ </TMagicTableColumn>
17
19
  </template>
18
20
 
19
- <script lang="ts">
20
- import { defineComponent, PropType } from 'vue';
21
-
21
+ <script lang="ts" setup name="MTableExpandColumn">
22
+ import { TMagicTableColumn } from '@tmagic/design';
22
23
  import { MForm } from '@tmagic/form';
23
24
 
24
25
  import { ColumnConfig } from './schema';
26
+ import MTable from './Table.vue';
25
27
 
26
- export default defineComponent({
27
- components: { MForm },
28
-
29
- props: {
30
- config: {
31
- type: Object as PropType<ColumnConfig>,
32
- default: () => ({}),
33
- required: true,
34
- },
28
+ const props = withDefaults(
29
+ defineProps<{
30
+ config: ColumnConfig;
31
+ }>(),
32
+ {
33
+ config: () => ({}),
35
34
  },
36
- });
35
+ );
36
+
37
+ const componentProps = (row: any) => {
38
+ if (typeof props.config.props === 'function') {
39
+ return props.config.props(row) || {};
40
+ }
41
+ return props.config.props || {};
42
+ };
37
43
  </script>
@@ -1,40 +1,39 @@
1
1
  <template>
2
- <el-table-column :label="config.label" :width="config.width" :fixed="config.fixed">
2
+ <TMagicTableColumn :label="config.label" :width="config.width" :fixed="config.fixed">
3
3
  <template v-slot="scope">
4
- <el-popover :placement="config.popover.placement" :width="config.popover.width" :trigger="config.popover.trigger">
5
- <m-table
4
+ <TMagicPopover
5
+ v-if="config.popover"
6
+ :placement="config.popover.placement"
7
+ :width="config.popover.width"
8
+ :trigger="config.popover.trigger"
9
+ >
10
+ <MTable
6
11
  v-if="config.popover.tableEmbed"
7
12
  :show-header="config.showHeader"
8
13
  :columns="config.table"
9
- :data="scope.row[config.prop]"
10
- ></m-table>
14
+ :data="(config.prop && scope.row[config.prop]) || []"
15
+ ></MTable>
11
16
  <template #reference>
12
- <el-button text type="primary"> {{ config.text || formatter(config, scope.row) }}</el-button>
17
+ <TMagicButton text type="primary"> {{ config.text || formatter(config, scope.row) }}</TMagicButton>
13
18
  </template>
14
- </el-popover>
19
+ </TMagicPopover>
15
20
  </template>
16
- </el-table-column>
21
+ </TMagicTableColumn>
17
22
  </template>
18
23
 
19
- <script lang="ts">
20
- import { defineComponent, PropType } from 'vue';
24
+ <script lang="ts" setup name="MTablePopoverColumn">
25
+ import { TMagicButton, TMagicPopover, TMagicTableColumn } from '@tmagic/design';
21
26
 
22
27
  import { ColumnConfig } from './schema';
28
+ import MTable from './Table.vue';
23
29
  import { formatter } from './utils';
24
30
 
25
- export default defineComponent({
26
- props: {
27
- config: {
28
- type: Object as PropType<ColumnConfig>,
29
- default: () => ({}),
30
- required: true,
31
- },
31
+ withDefaults(
32
+ defineProps<{
33
+ config: ColumnConfig;
34
+ }>(),
35
+ {
36
+ config: () => ({}),
32
37
  },
33
-
34
- setup() {
35
- return {
36
- formatter,
37
- };
38
- },
39
- });
38
+ );
40
39
  </script>
package/src/Table.vue CHANGED
@@ -1,15 +1,15 @@
1
1
  <template>
2
- <el-table
2
+ <TMagicTable
3
3
  tooltip-effect="dark"
4
4
  class="m-table"
5
- ref="table"
5
+ ref="tMagicTable"
6
6
  v-loading="loading"
7
7
  :data="tableData"
8
8
  :show-header="showHeader"
9
9
  :max-height="bodyHeight"
10
10
  :default-expand-all="defaultExpandAll"
11
11
  :border="hasBorder"
12
- :row-key="rowkeyName || 'c_id'"
12
+ :row-key="rowkeyName || 'id'"
13
13
  :tree-props="{ children: 'children' }"
14
14
  :empty-text="emptyText || '暂无数据'"
15
15
  :span-method="objectSpanMethod"
@@ -17,190 +17,174 @@
17
17
  @select="selectHandler"
18
18
  @select-all="selectAllHandler"
19
19
  @selection-change="selectionChangeHandler"
20
+ @cell-click="cellClickHandler"
21
+ @expand-change="expandChange"
20
22
  >
21
23
  <template v-for="(item, columnIndex) in columns">
22
24
  <template v-if="item.type === 'expand'">
23
- <expand-column :config="item" :key="columnIndex"></expand-column>
25
+ <ExpandColumn :config="item" :key="columnIndex"></ExpandColumn>
24
26
  </template>
25
27
 
26
28
  <template v-else-if="item.selection">
27
- <el-table-column type="selection" :key="columnIndex" width="40" :selectable="item.selectable"></el-table-column>
29
+ <component
30
+ width="40"
31
+ type="selection"
32
+ :is="tableColumnComponent.component"
33
+ :key="columnIndex"
34
+ :selectable="item.selectable"
35
+ ></component>
28
36
  </template>
29
37
 
30
38
  <template v-else-if="item.actions">
31
- <actions-column
39
+ <ActionsColumn
32
40
  :columns="columns"
33
41
  :config="item"
34
42
  :rowkey-name="rowkeyName"
35
43
  :edit-state="editState"
36
44
  :key="columnIndex"
37
- @afterAction="$emit('afterAction')"
38
- ></actions-column>
45
+ @after-action="$emit('after-action')"
46
+ ></ActionsColumn>
39
47
  </template>
40
48
 
41
49
  <template v-else-if="item.type === 'popover'">
42
- <popover-column :key="columnIndex" :config="item"></popover-column>
50
+ <PopoverColumn :key="columnIndex" :config="item"></PopoverColumn>
43
51
  </template>
44
52
 
45
53
  <template v-else>
46
- <text-column :key="columnIndex" :config="item" :edit-state="editState"></text-column>
54
+ <TextColumn :key="columnIndex" :config="item" :edit-state="editState"></TextColumn>
47
55
  </template>
48
56
  </template>
49
- </el-table>
57
+ </TMagicTable>
50
58
  </template>
51
59
 
52
- <script lang="ts">
53
- import { defineComponent, PropType } from 'vue';
54
- import { ElTable } from 'element-plus';
60
+ <script lang="ts" setup name="MTable">
61
+ import { computed, ref } from 'vue';
55
62
  import { cloneDeep } from 'lodash-es';
56
63
 
64
+ import { getConfig, TMagicTable } from '@tmagic/design';
65
+
57
66
  import ActionsColumn from './ActionsColumn.vue';
58
67
  import ExpandColumn from './ExpandColumn.vue';
59
68
  import PopoverColumn from './PopoverColumn.vue';
60
69
  import TextColumn from './TextColumn.vue';
61
70
 
62
- export default defineComponent({
63
- name: 'm-table',
64
-
65
- components: { ExpandColumn, ActionsColumn, PopoverColumn, TextColumn },
66
-
67
- props: {
68
- data: {
69
- type: Array,
70
- require: true,
71
- },
72
-
73
- columns: {
74
- type: Array as PropType<any[]>,
75
- require: true,
76
- default: () => [],
77
- },
78
-
71
+ const props = withDefaults(
72
+ defineProps<{
73
+ data: any[];
74
+ columns?: any[];
79
75
  /** 合并行或列的计算方法 */
80
- spanMethod: {
81
- type: Function as PropType<
82
- (data: { row: any; column: any; rowIndex: number; columnIndex: number }) => [number, number]
83
- >,
84
- },
76
+ spanMethod?: (data: { row: any; column: any; rowIndex: number; columnIndex: number }) => [number, number];
77
+ loading?: boolean;
78
+ /** Table 的最大高度。合法的值为数字或者单位为 px 的高度 */
79
+ bodyHeight?: string | number;
80
+ /** 是否显示表头 */
81
+ showHeader?: boolean;
82
+ /** 空数据时显示的文本内容 */
83
+ emptyText?: string;
84
+ /** 是否默认展开所有行,当 Table 包含展开行存在或者为树形表格时有效 */
85
+ defaultExpandAll?: boolean;
86
+ rowkeyName?: string;
87
+ /** 是否带有纵向边框 */
88
+ border?: boolean;
89
+ }>(),
90
+ {
91
+ columns: () => [],
92
+ loading: false,
93
+ showHeader: true,
94
+ defaultExpandAll: false,
95
+ border: false,
96
+ },
97
+ );
98
+
99
+ const emit = defineEmits([
100
+ 'sort-change',
101
+ 'after-action',
102
+ 'select',
103
+ 'select-all',
104
+ 'selection-change',
105
+ 'expand-change',
106
+ 'cell-click',
107
+ ]);
108
+
109
+ const tMagicTable = ref<InstanceType<typeof TMagicTable>>();
110
+
111
+ const editState = ref([]);
112
+
113
+ const tableColumnComponent = getConfig('components').tableColumn;
114
+ const selectionColumn = computed(() => {
115
+ const column = props.columns.filter((item) => item.selection);
116
+ return column.length ? column[0] : null;
117
+ });
85
118
 
86
- loading: {
87
- type: Boolean,
88
- default: false,
89
- },
119
+ const tableData = computed(() => {
120
+ if (selectionColumn.value) {
121
+ return props.data || [];
122
+ }
90
123
 
91
- /** Table 的最大高度。合法的值为数字或者单位为 px 的高度 */
92
- bodyHeight: {
93
- type: [String, Number],
94
- },
124
+ return cloneDeep(props.data) || [];
125
+ });
95
126
 
96
- /** 是否显示表头 */
97
- showHeader: {
98
- type: Boolean,
99
- default: true,
100
- },
127
+ const hasBorder = computed(() => (typeof props.border !== 'undefined' ? props.border : true));
101
128
 
102
- /** 空数据时显示的文本内容 */
103
- emptyText: {
104
- type: String,
105
- },
129
+ const sortChange = (data: any) => {
130
+ emit('sort-change', data);
131
+ };
106
132
 
107
- /** 是否默认展开所有行,当 Table 包含展开行存在或者为树形表格时有效 */
108
- defaultExpandAll: {
109
- type: Boolean,
110
- default: false,
111
- },
133
+ const selectHandler = (selection: any, row: any) => {
134
+ const column = selectionColumn.value;
135
+ if (!column) {
136
+ return;
137
+ }
112
138
 
113
- rowkeyName: {
114
- type: String,
115
- },
139
+ if (column.selection === 'single') {
140
+ // this.clearSelection()
141
+ // this.toggleRowSelection(row, true)
142
+ }
143
+ emit('select', selection, row);
144
+ };
116
145
 
117
- /** 是否带有纵向边框 */
118
- border: {
119
- type: Boolean,
120
- default: false,
121
- },
122
- },
146
+ const selectAllHandler = (selection: any) => {
147
+ emit('select-all', selection);
148
+ };
123
149
 
124
- emits: ['sort-change', 'afterAction', 'select', 'select-all', 'selection-change'],
150
+ const selectionChangeHandler = (selection: any) => {
151
+ emit('selection-change', selection);
152
+ };
125
153
 
126
- data(): {
127
- editState: any[];
128
- } {
129
- return {
130
- editState: [],
131
- };
132
- },
154
+ const cellClickHandler = (...args: any[]) => {
155
+ emit('cell-click', ...args);
156
+ };
133
157
 
134
- computed: {
135
- tableData() {
136
- if (this.selectionColumn) {
137
- return this.data || [];
138
- }
158
+ const expandChange = (...args: any[]) => {
159
+ emit('expand-change', ...args);
160
+ };
139
161
 
140
- return cloneDeep(this.data) || [];
141
- },
162
+ const toggleRowSelection = (row: any, selected: boolean) => {
163
+ tMagicTable.value?.toggleRowSelection(row, selected);
164
+ };
142
165
 
143
- selectionColumn() {
144
- const column = this.columns.filter((item) => item.selection);
145
- return column.length ? column[0] : null;
146
- },
166
+ const toggleRowExpansion = (row: any, expanded: boolean) => {
167
+ tMagicTable.value?.toggleRowExpansion(row, expanded);
168
+ };
147
169
 
148
- hasBorder() {
149
- return typeof this.border !== 'undefined' ? this.border : true;
150
- },
151
- },
170
+ const clearSelection = () => {
171
+ tMagicTable.value?.clearSelection();
172
+ };
152
173
 
153
- methods: {
154
- sortChange(data: any) {
155
- this.$emit('sort-change', data);
156
- },
157
-
158
- selectHandler(selection: any, row: any) {
159
- const column = this.selectionColumn;
160
- if (!column) {
161
- return;
162
- }
163
-
164
- if (column.selection === 'single') {
165
- // this.clearSelection()
166
- // this.toggleRowSelection(row, true)
167
- }
168
- this.$emit('select', selection, row);
169
- },
170
-
171
- selectAllHandler(selection: any) {
172
- this.$emit('select-all', selection);
173
- },
174
-
175
- selectionChangeHandler(selection: any) {
176
- this.$emit('selection-change', selection);
177
- },
178
-
179
- toggleRowSelection(row: any, selected: boolean) {
180
- const table = this.$refs.table as InstanceType<typeof ElTable>;
181
- table.toggleRowSelection.bind(table)(row, selected);
182
- },
183
-
184
- toggleRowExpansion(row: any, expanded: boolean) {
185
- const table = this.$refs.table as InstanceType<typeof ElTable>;
186
- table.toggleRowExpansion.bind(table)(row, expanded);
187
- },
188
-
189
- clearSelection() {
190
- const table = this.$refs.table as InstanceType<typeof ElTable>;
191
- table.clearSelection.bind(table)();
192
- },
193
-
194
- objectSpanMethod(data: any) {
195
- if (typeof this.spanMethod === 'function') {
196
- return this.spanMethod(data);
197
- }
198
- return () => ({
199
- rowspan: 0,
200
- colspan: 0,
201
- });
202
- },
203
- },
174
+ const objectSpanMethod = (data: any) => {
175
+ if (typeof props.spanMethod === 'function') {
176
+ return props.spanMethod(data);
177
+ }
178
+ return () => ({
179
+ rowspan: 0,
180
+ colspan: 0,
181
+ });
182
+ };
183
+
184
+ defineExpose({
185
+ toggleRowSelection,
186
+ toggleRowExpansion,
187
+ clearSelection,
204
188
  });
205
189
  </script>
206
190