tianheng-ui 0.1.11 → 0.1.14

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 (51) hide show
  1. package/lib/theme-chalk/js/axios.js +3 -2
  2. package/lib/theme-chalk/js/util.js +23 -0
  3. package/lib/theme-chalk/styles/feature.scss +15 -0
  4. package/lib/tianheng-ui.js +13 -14
  5. package/package.json +1 -1
  6. package/packages/FormMaking/GenerateForm.vue +6 -1
  7. package/packages/FormMaking/GenerateFormItem.vue +9 -5
  8. package/packages/FormMaking/GenerateFormItemH5.vue +1 -1
  9. package/packages/FormMaking/WidgetConfig.vue +39 -51
  10. package/packages/FormMaking/WidgetForm.vue +9 -10
  11. package/packages/FormMaking/WidgetFormItem.vue +2 -2
  12. package/packages/FormMaking/WidgetSelect.vue +0 -1
  13. package/packages/FormMaking/WidgetTools.vue +539 -0
  14. package/packages/FormMaking/config/index.js +6 -0
  15. package/packages/FormMaking/custom/config.js +21 -24
  16. package/packages/FormMaking/custom/configs/button.vue +25 -25
  17. package/packages/FormMaking/custom/configs/cascader.vue +7 -7
  18. package/packages/FormMaking/custom/configs/checkbox.vue +23 -22
  19. package/packages/FormMaking/custom/configs/color.vue +3 -3
  20. package/packages/FormMaking/custom/configs/date.vue +3 -3
  21. package/packages/FormMaking/custom/configs/input.vue +3 -3
  22. package/packages/FormMaking/custom/configs/number.vue +3 -3
  23. package/packages/FormMaking/custom/configs/radio.vue +23 -19
  24. package/packages/FormMaking/custom/configs/rate.vue +3 -3
  25. package/packages/FormMaking/custom/configs/select.vue +25 -20
  26. package/packages/FormMaking/custom/configs/slider.vue +3 -3
  27. package/packages/FormMaking/custom/configs/switch.vue +3 -3
  28. package/packages/FormMaking/custom/configs/tabs.vue +12 -17
  29. package/packages/FormMaking/custom/configs/textarea.vue +3 -3
  30. package/packages/FormMaking/custom/configs/time.vue +3 -3
  31. package/packages/FormMaking/custom/configs/upload.vue +5 -5
  32. package/packages/FormMaking/custom/items/button.vue +35 -1
  33. package/packages/FormMaking/custom/items/checkbox.vue +1 -1
  34. package/packages/FormMaking/custom/items/date.vue +1 -0
  35. package/packages/FormMaking/custom/items/grid_dev.vue +3 -3
  36. package/packages/FormMaking/custom/items/tableH5_dev.vue +3 -3
  37. package/packages/FormMaking/custom/items/table_dev.vue +3 -3
  38. package/packages/FormMaking/custom/items/tabs_dev.vue +3 -3
  39. package/packages/FormMaking/custom/mixins/index.js +12 -12
  40. package/packages/FormMaking/index.vue +93 -469
  41. package/packages/FormMaking/styles/index.scss +1 -21
  42. package/packages/FormMaking/util/index.js +24 -0
  43. package/packages/FormMaking/util/request.js +9 -12
  44. package/packages/TableMaking/WidgetTools.vue +246 -0
  45. package/packages/TableMaking/custom/config.js +110 -0
  46. package/packages/TableMaking/generateTable.vue +2 -2
  47. package/packages/TableMaking/index.vue +62 -157
  48. package/packages/TableMaking/util/index.js +54 -1
  49. package/packages/TableMaking/widgetConfig.vue +261 -178
  50. package/packages/TableMaking/widgetTable.vue +16 -46
  51. package/packages/index.js +5 -4
@@ -41,3 +41,27 @@ export const inputTypeDict = val => {
41
41
  };
42
42
  return dict[val] || "text";
43
43
  };
44
+
45
+ export const deepClone = (obj, clone) => {
46
+ //判断拷贝的要进行深拷贝的是数组还是对象,是数组的话进行数组拷贝,对象的话进行对象拷贝
47
+ const toString = Object.prototype.toString;
48
+ toString.call(obj) === "[object Array]"
49
+ ? (clone = clone || [])
50
+ : (clone = clone || {});
51
+ for (const i in obj) {
52
+ if (typeof obj[i] === "object" && obj[i] !== null) {
53
+ // 要考虑深复制问题了
54
+ if (Array.isArray(obj[i])) {
55
+ // 这是数组
56
+ clone[i] = [];
57
+ } else {
58
+ // 这是对象
59
+ clone[i] = {};
60
+ }
61
+ deepClone(obj[i], clone[i]);
62
+ } else {
63
+ clone[i] = obj[i];
64
+ }
65
+ }
66
+ return clone;
67
+ };
@@ -1,28 +1,25 @@
1
- import axios from 'axios'
1
+ import axios from "axios";
2
2
 
3
3
  const request = axios.create({
4
4
  withCredentials: false
5
- })
5
+ });
6
6
 
7
7
  request.interceptors.request.use(
8
8
  config => {
9
- return config
9
+ return config;
10
10
  },
11
11
  error => {
12
- console.log('error', error)
13
- return Promise.reject(new Error(error).message)
12
+ return Promise.reject(new Error(error).message);
14
13
  }
15
- )
14
+ );
16
15
 
17
16
  request.interceptors.response.use(
18
17
  response => {
19
- console.log('.....', response)
20
- return response.data
18
+ return response.data;
21
19
  },
22
20
  error => {
23
- console.log('error', error)
24
- return Promise.reject(new Error(error).message)
21
+ return Promise.reject(new Error(error).message);
25
22
  }
26
- )
23
+ );
27
24
 
28
- export default request
25
+ export default request;
@@ -0,0 +1,246 @@
1
+ <template>
2
+ <div class="widgetTools">
3
+ <div class="left">
4
+ <el-button
5
+ :class="{ active: client === 'monitor' }"
6
+ type="text"
7
+ size="medium"
8
+ icon="el-icon-monitor"
9
+ @click="handleClick('monitor')"
10
+ >
11
+ </el-button>
12
+ <!-- <el-button
13
+ :class="{ active: client === 'mobile' }"
14
+ type="text"
15
+ size="medium"
16
+ icon="el-icon-mobile"
17
+ @click="client = 'mobile'"
18
+ >
19
+ </el-button> -->
20
+ </div>
21
+ <div class="right">
22
+ <slot> </slot>
23
+ <el-button
24
+ v-if="permissions.includes('clearable')"
25
+ style="margin-left:10px;"
26
+ type="text"
27
+ size="medium"
28
+ icon="el-icon-delete"
29
+ disabled
30
+ @click="handleClick('clear')"
31
+ >重置
32
+ </el-button>
33
+ <el-button
34
+ v-if="permissions.includes('preview')"
35
+ type="text"
36
+ size="medium"
37
+ icon="el-icon-view"
38
+ disabled
39
+ @click="handleDialogOpen('preview')"
40
+ >预览
41
+ </el-button>
42
+ <el-popover style="margin-left:10px;" placement="bottom" trigger="hover">
43
+ <el-button
44
+ v-if="permissions.includes('upload')"
45
+ type="text"
46
+ size="medium"
47
+ icon="el-icon-upload2"
48
+ slot="reference"
49
+ >导入</el-button
50
+ >
51
+ <div>
52
+ <div>
53
+ <el-button
54
+ type="text"
55
+ size="medium"
56
+ @click="handleDialogOpen('importJson')"
57
+ >导入JSON
58
+ </el-button>
59
+ </div>
60
+ <div>
61
+ <el-upload
62
+ action
63
+ accept=".xlsx, .xls"
64
+ :auto-upload="false"
65
+ :show-file-list="false"
66
+ disabled
67
+ :on-change="handleExcelFileChange"
68
+ >
69
+ <el-button type="text" size="medium" disabled
70
+ >导入EXCEL</el-button
71
+ >
72
+ </el-upload>
73
+ </div>
74
+ <div>
75
+ <el-button
76
+ type="text"
77
+ size="medium"
78
+ disabled
79
+ @click="handleDialogOpen('importTemplate')"
80
+ >导入模板
81
+ </el-button>
82
+ </div>
83
+ </div>
84
+ </el-popover>
85
+ <el-popover style="margin-left:10px;" placement="bottom" trigger="hover">
86
+ <el-button
87
+ v-if="
88
+ permissions.includes('generateJson') ||
89
+ permissions.includes('generateCode')
90
+ "
91
+ type="text"
92
+ size="medium"
93
+ icon="el-icon-document"
94
+ slot="reference"
95
+ >生成</el-button
96
+ >
97
+ <div>
98
+ <div>
99
+ <el-button
100
+ v-if="permissions.includes('generateJson')"
101
+ type="text"
102
+ size="medium"
103
+ @click="handleDialogOpen('generateJson')"
104
+ >
105
+ 生成JSON
106
+ </el-button>
107
+ </div>
108
+ <div>
109
+ <el-button
110
+ v-if="permissions.includes('generateCode')"
111
+ type="text"
112
+ size="medium"
113
+ disabled
114
+ @click="handleDialogOpen('generateCode')"
115
+ >
116
+ 生成代码
117
+ </el-button>
118
+ </div>
119
+ </div>
120
+ </el-popover>
121
+ </div>
122
+
123
+ <th-dialog
124
+ v-model="dialog.show"
125
+ :title="dialogTitles[dialog.action]"
126
+ :modal-append-to-body="false"
127
+ :showFooter="['importJson', 'importTemplate'].includes(dialog.action)"
128
+ @on-fullscreen="handleDialogFullscreen"
129
+ @on-close="handleDialogClose"
130
+ @on-affirm="handleDialogAffirm"
131
+ >
132
+ <template v-if="dialog.action === 'preview'"></template>
133
+ <template v-else-if="dialog.action === 'importJson'">
134
+ <el-alert
135
+ type="info"
136
+ title="JSON格式如下,直接复制生成的json覆盖此处代码点击确定即可"
137
+ ></el-alert>
138
+ <th-code-editor
139
+ v-model="dialog.data.config"
140
+ ref="codeEditor"
141
+ ></th-code-editor>
142
+ </template>
143
+ <template v-else-if="dialog.action === 'importTemplate'"></template>
144
+ <template v-else-if="dialog.action === 'generateJson'">
145
+ <th-code-editor
146
+ v-model="dialog.data.config"
147
+ ref="codeEditor"
148
+ ></th-code-editor>
149
+ </template>
150
+ <template v-else-if="dialog.action === 'generateCode'"></template>
151
+ </th-dialog>
152
+ </div>
153
+ </template>
154
+
155
+ <script>
156
+ export default {
157
+ props: {
158
+ config: Object,
159
+ client: String,
160
+ permissions: Array
161
+ },
162
+ data() {
163
+ return {
164
+ dialog: {
165
+ show: false,
166
+ action: "",
167
+ data: {}
168
+ },
169
+ dialogTitles: {
170
+ preview: "预览",
171
+ importJson: "导入JSON",
172
+ importTemplate: "导入模板",
173
+ generateJson: "生成JSON",
174
+ generateCode: "生成代码"
175
+ }
176
+ };
177
+ },
178
+ created() {},
179
+ mounted() {},
180
+ methods: {
181
+ handleClick(val, data) {
182
+ this.$emit("click", val, data);
183
+ },
184
+ handleDialogOpen(action, data = {}) {
185
+ switch (action) {
186
+ case "generateJson":
187
+ const configText = JSON.stringify(this.config, null, 2);
188
+ data.config = configText;
189
+ break;
190
+
191
+ default:
192
+ break;
193
+ }
194
+ this.dialog = { show: true, action, data };
195
+ },
196
+ handleDialogFullscreen() {
197
+ this.$refs.codeEditor.resize();
198
+ },
199
+ handleDialogAffirm() {
200
+ const action = this.dialog.action;
201
+ switch (action) {
202
+ case "importJson":
203
+ this.handleClick("import-json", JSON.parse(this.dialog.data.config));
204
+ break;
205
+
206
+ default:
207
+ break;
208
+ }
209
+ this.handleDialogClose();
210
+ },
211
+ handleDialogClose() {
212
+ this.dialog.show = false;
213
+ },
214
+ handleExcelFileChange() {},
215
+ handleGenerateJson() {},
216
+ handleGenerateCode() {}
217
+ }
218
+ };
219
+ </script>
220
+
221
+ <style lang="scss" scoped>
222
+ .widgetTools {
223
+ display: flex;
224
+ align-items: center;
225
+ width: 100%;
226
+ height: 45px;
227
+ padding: 0 15px;
228
+ border-bottom: solid 2px #e4e7ed;
229
+
230
+ .left {
231
+ min-width: 60px;
232
+ .el-button {
233
+ color: #333;
234
+ }
235
+ .active {
236
+ color: #409eff;
237
+ }
238
+ }
239
+ .right {
240
+ flex: 1;
241
+ display: flex;
242
+ align-items: center;
243
+ justify-content: right;
244
+ }
245
+ }
246
+ </style>
@@ -0,0 +1,110 @@
1
+ // 查询配置
2
+ export const search = {
3
+ show: true,
4
+ options: []
5
+ };
6
+
7
+ // 列表配置
8
+ export const table = {
9
+ options: [],
10
+ pageInfo: {
11
+ show: true,
12
+ options: {
13
+ pageCount: 0,
14
+ pageSize: 20,
15
+ currentPage: 1,
16
+ total: 0,
17
+ sizes: [10, 20, 30, 50, 100]
18
+ }
19
+ },
20
+ sort: {
21
+ type: "1",
22
+ key: ""
23
+ },
24
+ loading: {
25
+ show: false,
26
+ text: "加载中",
27
+ image: ""
28
+ },
29
+ empty: {
30
+ show: true,
31
+ text: "暂无数据",
32
+ image: ""
33
+ },
34
+ sequence: true
35
+ };
36
+
37
+ // 按钮配置
38
+ export const tools = {
39
+ add: {
40
+ show: true,
41
+ name: "新增",
42
+ text: "新增",
43
+ position: "header",
44
+ form: "",
45
+ api: ""
46
+ },
47
+ edit: {
48
+ show: true,
49
+ name: "编辑",
50
+ text: "编辑",
51
+ position: "row",
52
+ form: "",
53
+ api: ""
54
+ },
55
+ detail: {
56
+ show: false,
57
+ name: "查看",
58
+ text: "查看",
59
+ position: "row",
60
+ form: "",
61
+ api: ""
62
+ },
63
+ delete: {
64
+ show: true,
65
+ name: "删除",
66
+ text: "删除",
67
+ position: "row",
68
+ form: "",
69
+ api: ""
70
+ },
71
+ batchDelete: {
72
+ show: false,
73
+ name: "批量删除",
74
+ text: "批量删除",
75
+ position: "header",
76
+ form: "",
77
+ api: ""
78
+ },
79
+ export: {
80
+ show: false,
81
+ name: "导出",
82
+ text: "导出",
83
+ position: "header",
84
+ form: "",
85
+ api: ""
86
+ },
87
+ import: {
88
+ show: false,
89
+ name: "导入",
90
+ text: "导入",
91
+ position: "header",
92
+ form: "",
93
+ api: ""
94
+ }
95
+ };
96
+
97
+ // 接口配置
98
+ export const network = {
99
+ mounted: {
100
+ method: "get",
101
+ api: "/list"
102
+ }
103
+ };
104
+
105
+ export const tableConfig = {
106
+ search,
107
+ table,
108
+ tools,
109
+ network
110
+ };
@@ -248,10 +248,10 @@ export default {
248
248
  }
249
249
  const dic = toolsItemConfig(key, element);
250
250
  dic.form = element.form;
251
- if (element.position === 1) {
251
+ if (element.position === 1 || element.position === 'header') {
252
252
  this.toolsConfig.show = true;
253
253
  this.toolsConfig.options.push(dic);
254
- } else if (element.position === 2) {
254
+ } else if (element.position === 2 || element.position === 'row') {
255
255
  action.hide = false;
256
256
  action.actions.push(dic);
257
257
  }
@@ -1,189 +1,94 @@
1
1
  <template>
2
- <div class="th-table-making">
3
- <el-container>
4
- <el-container>
5
- <el-header>
6
- <div class="client">
7
- <el-button
8
- :class="{ active: client === 'monitor' }"
9
- type="text"
10
- size="medium"
11
- icon="el-icon-monitor"
12
- @click="client = 'monitor'"
13
- >
14
- 桌面端
15
- </el-button>
16
- <!-- <el-button
17
- :class="{ active: client === 'mobile' }"
18
- type="text"
19
- size="medium"
20
- icon="el-icon-mobile"
21
- @click="client = 'mobile'"
22
- >
23
- 移动端
24
- </el-button> -->
25
- </div>
26
- <slot name="action"></slot>
27
- </el-header>
28
- <el-main>
29
- <widget-table
30
- :searchFields="searchFields"
31
- :tableFields="tableFields"
32
- @move="handleMoveChange"
33
- ></widget-table>
34
- </el-main>
35
- </el-container>
36
- <el-aside width="300px">
37
- <widget-config
38
- :fields="fields"
39
- ref="configRef"
40
- @fields-change="handleFieldsChange"
41
- ></widget-config>
42
- </el-aside>
43
- </el-container>
2
+ <div class="th-table-making th-flex_box">
3
+ <div class="th-fiex_content">
4
+ <widget-tools
5
+ :config="config"
6
+ :client="client"
7
+ :permissions="permissions"
8
+ @click="handleToolsClick"
9
+ >
10
+ <slot name="action"></slot>
11
+ </widget-tools>
12
+ <widget-table
13
+ style="height:calc(100% - 45px)"
14
+ :config="config"
15
+ ></widget-table>
16
+ </div>
17
+ <div class="th-flex_aside th-is_border_left" style="width:300px">
18
+ <widget-config
19
+ :config="config"
20
+ :fields.sync="fields"
21
+ :formOptions="formOptions"
22
+ :apiOptions="apiOptions"
23
+ ref="configRef"
24
+ ></widget-config>
25
+ </div>
44
26
  </div>
45
27
  </template>
46
28
 
47
29
  <script>
30
+ import WidgetTools from "./WidgetTools.vue";
48
31
  import WidgetTable from "./widgetTable.vue";
49
32
  import WidgetConfig from "./widgetConfig.vue";
33
+ import { deepClone, deepMerge } from "./util/index";
34
+ import { tableConfig } from "./custom/config";
50
35
  export default {
51
36
  name: "ThTableMaking",
52
- components: { WidgetTable, WidgetConfig },
37
+ components: { WidgetTools, WidgetTable, WidgetConfig },
53
38
  props: {
54
- fields: {
55
- type: Array,
56
- default: () => {
57
- return [];
58
- }
59
- },
60
- config: {
39
+ data: {
61
40
  type: Object,
62
41
  default: () => {
63
- return {};
42
+ return deepClone(tableConfig);
64
43
  }
44
+ },
45
+ fields: Array,
46
+ formOptions: Array,
47
+ apiOptions: Array,
48
+ permissions: {
49
+ type: Array,
50
+ default: () => [
51
+ "monitor",
52
+ "mobile",
53
+ "upload",
54
+ "clearable",
55
+ "preview",
56
+ "generateCode",
57
+ "generateJson"
58
+ ]
65
59
  }
66
60
  },
67
61
  data() {
68
62
  return {
69
- searchFields: [],
70
- tableFields: [],
63
+ config: this.data,
71
64
  client: "monitor"
72
65
  };
73
66
  },
74
67
  watch: {
75
- fields: {
76
- handler(val, oldVal) {
77
- if (oldVal.length === 0) {
78
- this.initConfig();
79
- }
80
- },
81
- deep: true
68
+ config: {
69
+ deep: true,
70
+ handler: function(val) {
71
+ this.$emit("update:data", val);
72
+ }
82
73
  },
83
- config(val) {
84
- this.initConfig();
74
+ data(val) {
75
+ this.config = val;
85
76
  }
86
77
  },
87
- mounted() {
88
- this.initConfig();
89
- },
78
+ mounted() {},
90
79
  methods: {
91
- initConfig() {
92
- if (!this.config || Object.keys(this.config).length === 0) return;
80
+ handleToolsClick(action, data) {
81
+ switch (action) {
82
+ case "import-json":
83
+ this.config = data;
84
+ break;
93
85
 
94
- this.$refs.configRef.tableConfig = this.config;
95
-
96
- const searchFields = [];
97
- const searchFieldsIndexs = [];
98
- if (this.config.search) {
99
- const searchOptions = this.config.search.options;
100
- for (const item of searchOptions) {
101
- for (let i = 0; i < this.fields.length; i++) {
102
- const element = this.fields[i];
103
- if (element.prop === item.prop) {
104
- searchFields.push(item);
105
- searchFieldsIndexs.push(i);
106
- }
107
- }
108
- }
109
- this.searchFields = searchFields;
110
- this.$refs.configRef.search = {
111
- fields: searchFieldsIndexs,
112
- isCheckAll: searchFieldsIndexs.length === this.fields.length,
113
- isIndeterminate:
114
- searchFieldsIndexs.length > 0 &&
115
- searchFieldsIndexs.length < this.fields.length
116
- };
117
- }
118
-
119
- const tableFields = [];
120
- const tableFieldsIndexs = [];
121
- if (this.config.table) {
122
- const tableOptions = this.config.table.options;
123
- for (const item of tableOptions) {
124
- for (let i = 0; i < this.fields.length; i++) {
125
- const element = this.fields[i];
126
- if (element.prop === item.prop) {
127
- tableFields.push(item);
128
- tableFieldsIndexs.push(i);
129
- }
130
- }
131
- }
132
- this.tableFields = tableFields;
133
- this.$refs.configRef.table = {
134
- fields: tableFieldsIndexs,
135
- isCheckAll: tableFieldsIndexs.length === this.fields.length,
136
- isIndeterminate:
137
- tableFieldsIndexs.length > 0 &&
138
- tableFieldsIndexs.length < this.fields.length
139
- };
140
- }
141
- },
142
- handleFieldsChange(val) {
143
- const type = val.type;
144
- const data = val.data;
145
- const list = [];
146
- data.forEach(i => {
147
- list.push(this.fields[i]);
148
- });
149
- if (type === 0) {
150
- this.searchFields = list;
151
- } else {
152
- this.tableFields = list;
153
- }
154
- },
155
- handleMoveChange(val) {
156
- const newIndex = val.data.newIndex;
157
- const oldIndex = val.data.oldIndex;
158
- if (val.type === "search") {
159
- let list = this.$refs.configRef.search.fields;
160
- list = this.handleMobile(list, oldIndex, newIndex);
161
- this.$refs.configRef.search.fields = list;
162
- this.searchFields = this.handleMobile(this.searchFields, oldIndex, newIndex);
163
- } else {
164
- let list = this.$refs.configRef.table.fields;
165
- list = this.handleMobile(list, oldIndex, newIndex);
166
- this.$refs.configRef.table.fields = list;
167
- this.tableFields = this.handleMobile(this.tableFields, oldIndex, newIndex);
168
- }
169
- },
170
- handleMobile(list, oldIndex, newIndex) {
171
- const item = JSON.parse(JSON.stringify(list[oldIndex]));
172
- if (oldIndex < newIndex) {
173
- list.splice(newIndex + 1, 0, item);
174
- list.splice(oldIndex, 1);
175
- }
176
- if (oldIndex > newIndex) {
177
- list.splice(newIndex, 0, item);
178
- list.splice(oldIndex + 1, 1);
86
+ default:
87
+ break;
179
88
  }
180
- return list;
181
89
  },
182
90
  getJson() {
183
- const tableConfig = this.$refs.configRef.getJson();
184
- tableConfig.search.options = this.searchFields;
185
- tableConfig.table.options = this.tableFields;
186
- return tableConfig;
91
+ return this.config;
187
92
  }
188
93
  }
189
94
  };