tianheng-ui 0.1.80 → 0.1.82

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,157 +1,427 @@
1
- function findRemoteFunc(list, funcList, tokenFuncList, blankList) {
2
- for (let i = 0; i < list.length; i++) {
3
- if (list[i].type == "grid") {
4
- list[i].options.columns.forEach(item => {
5
- findRemoteFunc(item.list, funcList, tokenFuncList, blankList);
6
- });
7
- } else if (list[i].type == "tabs") {
8
- list[i].options.columns.forEach(item => {
9
- findRemoteFunc(item.list, funcList, tokenFuncList, blankList);
10
- });
11
- } else if (list[i].type == "table") {
12
- // list[i].options.columns.forEach(item => {
13
- findRemoteFunc(list[i].list, funcList, tokenFuncList, blankList);
14
- // })
15
- } else {
16
- if (list[i].type == "blank") {
17
- if (list[i].model) {
18
- blankList.push({
19
- name: list[i].model,
20
- label: list[i].name
21
- });
22
- }
23
- } else if (list[i].type == "upload") {
24
- if (list[i].options.tokenFunc) {
25
- tokenFuncList.push({
26
- func: list[i].options.tokenFunc,
27
- label: list[i].name,
28
- model: list[i].model
29
- });
30
- }
31
- } else {
32
- if (list[i].options.remote.open && list[i].options.remote.api) {
33
- funcList.push({
34
- func: list[i].options.remote.api,
35
- label: list[i].name,
36
- model: list[i].model
37
- });
38
- }
39
- }
40
- }
41
- }
42
- }
43
-
44
- export default function(config, type = "making") {
45
- const funcList = [];
46
-
47
- const tokenFuncList = [];
48
-
49
- const blankList = [];
50
-
51
- findRemoteFunc(
52
- JSON.parse(config.formConfig).list,
53
- funcList,
54
- tokenFuncList,
55
- blankList
56
- );
57
-
58
- let funcTemplate = "";
59
-
60
- let blankTemplate = "";
61
-
62
- for (let i = 0; i < funcList.length; i++) {
63
- funcTemplate += `
64
- ${funcList[i].func} (resolve) {
65
- // ${funcList[i].label} ${funcList[i].model}
66
- // Call callback function once get the data from remote server
67
- // resolve(data)
68
- },
69
- `;
70
- }
71
-
72
- for (let i = 0; i < tokenFuncList.length; i++) {
73
- funcTemplate += `
74
- ${tokenFuncList[i].func} (resolve) {
75
- // ${tokenFuncList[i].label} ${tokenFuncList[i].model}
76
- // Call callback function once get the token
77
- // resolve(token)
78
- },
79
- `;
80
- }
81
-
82
- for (let i = 0; i < blankList.length; i++) {
83
- blankTemplate += `
84
- <template slot="${blankList[i].name}" slot-scope="scope">
85
- <!-- ${blankList[i].label} -->
86
- <!-- use v-model="scope.model.${blankList[i].name}" to bind data -->
87
- </template>
88
- `;
89
- }
90
-
91
- if (type == "making") {
92
- return `
93
- <template>
94
- <th-form-making :config="formConfig" :oauthConfig="oauthConfig" :apiOptions="apiOptions" ref="makingForm">
95
- <div slot="action">
96
- <el-button type="danger" icon="el-icon-close" size="mini" @click="$router.go(-1)">关闭</el-button>
97
- <el-button type="primary" icon="el-icon-finished" size="mini" @click="handleSubmit">保存</el-button>
98
- <el-button type="warning" icon="el-icon-document-copy" size="mini" @click="handleSubmit">另存为</el-button>
99
- </div>
100
- ${blankTemplate}
101
- </th-form-making>
102
- </template>
103
-
104
- <script>
105
- export default {
106
- data () {
107
- return {
108
- formConfig: ${config.formConfig},
109
- apiOptions: ${config.apiOptions},
110
- oauthConfig: ${config.oauthConfig},
111
- }
112
- },
113
- methods: {
114
- handleSubmit () {
115
- this.$refs.makingForm.getData().then(res => {
116
- console.log(res);
117
- });
118
- }
119
- }
120
- }
121
- </script>`;
122
- } else {
123
- return `
124
- <template>
125
- <th-form-generate :config="formConfig" :value="formValue" :oauthConfig="oauthConfig" :slotKeys="slotKeys" @change="handleChange" @button-submit="handleSubmit" ref="generateForm">
126
- ${blankTemplate}
127
- </th-form-generate>
128
- </template>
129
-
130
- <script>
131
- export default {
132
- data () {
133
- return {
134
- formConfig: ${config.formConfig},
135
- formValue: {},
136
- oauthConfig: ${config.oauthConfig},
137
- slotKeys: ${JSON.stringify(
138
- blankList.map(item => {
139
- return item.name;
140
- })
141
- )}
142
- }
143
- },
144
- methods: {
145
- handleChange (val) {
146
- console.log(val);
147
- },
148
- handleSubmit () {
149
- this.$refs.generateForm.getData().then(res => {
150
- console.log(res);
151
- });
152
- }
153
- }
154
- }
155
- </script>`;
156
- }
157
- }
1
+ function findRemoteFunc(list, funcList, tokenFuncList, blankList) {
2
+ for (let i = 0; i < list.length; i++) {
3
+ if (list[i].type == "grid") {
4
+ list[i].options.columns.forEach(item => {
5
+ findRemoteFunc(item.list, funcList, tokenFuncList, blankList);
6
+ });
7
+ } else if (list[i].type == "tabs") {
8
+ list[i].options.columns.forEach(item => {
9
+ findRemoteFunc(item.list, funcList, tokenFuncList, blankList);
10
+ });
11
+ } else if (list[i].type == "table") {
12
+ // list[i].options.columns.forEach(item => {
13
+ findRemoteFunc(list[i].options, funcList, tokenFuncList, blankList);
14
+ // })
15
+ } else {
16
+ if (list[i].type == "blank") {
17
+ if (list[i].model) {
18
+ blankList.push({
19
+ name: list[i].model,
20
+ label: list[i].name
21
+ });
22
+ }
23
+ } else if (list[i].type == "upload") {
24
+ if (list[i].options.tokenFunc) {
25
+ tokenFuncList.push({
26
+ func: list[i].options.tokenFunc,
27
+ label: list[i].name,
28
+ model: list[i].model
29
+ });
30
+ }
31
+ } else {
32
+ if (list[i].options.remote?.open && list[i].options.remote?.api) {
33
+ funcList.push({
34
+ func: list[i].options.remote.api,
35
+ label: list[i].name,
36
+ model: list[i].model
37
+ });
38
+ }
39
+ }
40
+ }
41
+ }
42
+ }
43
+
44
+ export default function(config, type = "making") {
45
+ const formConfigStr = JSON.stringify(config.formConfig, null, 2);
46
+ const apiOptionsStr = JSON.stringify(config.apiOptions, null, 2);
47
+ const oauthConfigStr = JSON.stringify(config.oauthConfig, null, 2);
48
+
49
+ const funcList = []; //方法函数列表
50
+ const tokenFuncList = [];
51
+ const blankList = []; //自定义插槽
52
+
53
+ findRemoteFunc(config.formConfig.list, funcList, tokenFuncList, blankList);
54
+
55
+ let funcTemplate = "";
56
+
57
+ let blankTemplate = "";
58
+
59
+ for (let i = 0; i < funcList.length; i++) {
60
+ funcTemplate += `
61
+ ${funcList[i].func} (resolve) {
62
+ // ${funcList[i].label} ${funcList[i].model}
63
+ // Call callback function once get the data from remote server
64
+ // resolve(data)
65
+ },
66
+ `;
67
+ }
68
+
69
+ for (let i = 0; i < tokenFuncList.length; i++) {
70
+ funcTemplate += `
71
+ ${tokenFuncList[i].func} (resolve) {
72
+ // ${tokenFuncList[i].label} ${tokenFuncList[i].model}
73
+ // Call callback function once get the token
74
+ // resolve(token)
75
+ },
76
+ `;
77
+ }
78
+
79
+ for (let i = 0; i < blankList.length; i++) {
80
+ blankTemplate += `
81
+ <template slot="${blankList[i].name}" slot-scope="scope">
82
+ <!-- ${blankList[i].label} -->
83
+ <!-- use v-model="scope.model.${blankList[i].name}" to bind data -->
84
+ </template>
85
+ `;
86
+ }
87
+
88
+ if (type === "making") {
89
+ return `
90
+ <template>
91
+ <th-form-making :config="formConfig" :oauthConfig="oauthConfig" :apiOptions="apiOptions" ref="makingForm">
92
+ <div slot="action">
93
+ <el-button type="danger" icon="el-icon-close" size="mini" @click="$router.go(-1)">关闭</el-button>
94
+ <el-button type="primary" icon="el-icon-finished" size="mini" @click="handleSubmit">保存</el-button>
95
+ <el-button type="warning" icon="el-icon-document-copy" size="mini" @click="handleSubmit">另存为</el-button>
96
+ </div>
97
+ ${blankTemplate}
98
+ </th-form-making>
99
+ </template>
100
+
101
+ <script>
102
+ export default {
103
+ data () {
104
+ return {
105
+ formConfig: ${formConfigStr},
106
+ apiOptions: ${apiOptionsStr},
107
+ oauthConfig: ${oauthConfigStr},
108
+ }
109
+ },
110
+ methods: {
111
+ handleSubmit () {
112
+ this.$refs.makingForm.getData().then(res => {
113
+ console.log(res);
114
+ });
115
+ }
116
+ }
117
+ }
118
+ </script>`;
119
+ }
120
+ if (type === "generate") {
121
+ return `
122
+ <template>
123
+ <th-form-generate :config="formConfig" :value="formValue" :oauthConfig="oauthConfig" :slotKeys="slotKeys" @change="handleChange" @button-submit="handleSubmit" ref="generateForm">
124
+ ${blankTemplate}
125
+ </th-form-generate>
126
+ </template>
127
+
128
+ <script>
129
+ export default {
130
+ data () {
131
+ return {
132
+ formConfig: ${formConfigStr},
133
+ formValue: {},
134
+ oauthConfig: ${oauthConfigStr},
135
+ slotKeys: ${JSON.stringify(
136
+ blankList.map(item => {
137
+ return item.name;
138
+ })
139
+ )}
140
+ }
141
+ },
142
+ methods: {
143
+ handleChange (val) {
144
+ console.log(val);
145
+ },
146
+ handleSubmit () {
147
+ this.$refs.generateForm.getData().then(res => {
148
+ console.log(res);
149
+ });
150
+ }
151
+ }
152
+ }
153
+ </script>`;
154
+ }
155
+ if (type === "codeSnippet") {
156
+ return codeSnippet(config);
157
+ }
158
+ }
159
+
160
+ const codeSnippet = config => {
161
+ let templateNode = "";
162
+ for (let i = 0; i < config.formConfig.list.length; i++) {
163
+ const element = config.formConfig.list[i];
164
+ templateNode += nodeList(element);
165
+ }
166
+
167
+ return templateNode;
168
+ };
169
+
170
+ const nodeList = element => {
171
+ if (element.type === "page-table") {
172
+ const treeConfig = element.options.columns.tree;
173
+ const searchConfig = element.options.columns.search;
174
+ const toolsConfig = element.options.columns.tools;
175
+ const tableConfig = element.options.columns.table;
176
+ // 搜索
177
+ let searchParams = {};
178
+ let searchDom = "";
179
+ if (searchConfig.show) {
180
+ let searchItemNodes = "";
181
+ searchConfig.list.map(item => {
182
+ searchParams[item.model] = item.options.defaultValue;
183
+ searchItemNodes += `<a-col :span="${searchConfig.props.grid.span}">
184
+ <a-form-item label="${item.name}" name="${item.model}">
185
+ ${nodeList(item)}
186
+ </a-form-item>
187
+ </a-col>
188
+ `;
189
+ });
190
+ searchDom = `<a-card :bordered="false" :body-style="{ 'margin-bottom': '10px' }">
191
+ <a-form ref="searchFormRef" :model="state.searchParams" :colon="false">
192
+ <a-row :gutter="${searchConfig.props.grid.gutter}">
193
+ ${searchItemNodes}
194
+ <a-col :span="${searchConfig.props.grid.span}">
195
+ <a-space>
196
+ <a-button type="primary" @click="getData">查询</a-button>
197
+ <a-button @click="handleReset">重置</a-button>
198
+ </a-space>
199
+ </a-col>
200
+ </a-row>
201
+ </a-form>
202
+ </a-card>
203
+ `;
204
+ }
205
+
206
+ let treeDom = "";
207
+ if (treeConfig.show) {
208
+ treeDom = `<a-card :bordered="false">
209
+ <a-tree
210
+ v-if="state.tree.data.length"
211
+ :treeData="state.tree.data"
212
+ v-model:selectedKeys="state.tree.selectedKeys"
213
+ ${
214
+ treeConfig.props.checkable
215
+ ? 'v-model:checkedKeys="state.tree.checkedKeys"'
216
+ : ""
217
+ }
218
+ :checkable="state.tree.checkable"
219
+ :defaultExpandAll="state.tree.defaultExpandAll"
220
+ :field-names="state.tree.fieldNames"
221
+ @select="handleTableLoad">
222
+ </a-tree>
223
+ </a-card>`;
224
+ }
225
+
226
+ let toolsDom = "";
227
+ if (toolsConfig.show) {
228
+ toolsDom = "<a-space>";
229
+ toolsConfig.list.map(item => {
230
+ toolsDom += `
231
+ <a-button type="${
232
+ item.options.buttonType
233
+ }" @click="handleToolsClick('${item.options.defaultValue}')">
234
+ ${
235
+ item.options.buttonIcon
236
+ ? `<template #icon><${item.options.buttonIcon} /></template>`
237
+ : ""
238
+ }
239
+ ${item.options.defaultValue}
240
+ </a-button>`;
241
+ });
242
+ toolsDom += `
243
+ </a-space>`;
244
+ }
245
+
246
+ let tableDom = "";
247
+ if (tableConfig.show) {
248
+ tableDom = `<a-card :bordered="false">
249
+ ${toolsDom}
250
+ <a-table
251
+ :columns="state.tableColumns"
252
+ :data-source="state.tableData"
253
+ :pagination="state.pagination"
254
+ @change="handleTableChange"
255
+ >
256
+ <template #bodyCell="{ column, record }">
257
+ <template v-if="column.dataIndex === 'action'">
258
+ <span>
259
+ <a @click="handleActionClick(record)">编辑</a>
260
+ <a-divider type="vertical" />
261
+ <a @click="handleActionClick(record)">删除</a>
262
+ </span>
263
+ </template>
264
+ <template v-else>{{ record[column.dataIndex] }}</template>
265
+ </template>
266
+ </a-table>
267
+ </a-card>`;
268
+ }
269
+
270
+ const nodeStr = `
271
+ <!-- ${element.name} -->
272
+ <template>
273
+ <a-row :gutter="${element.options.gutter}">
274
+ <a-col :span="4">
275
+ ${treeDom}
276
+ </a-col>
277
+
278
+ <a-col :span="20">
279
+ ${searchDom}
280
+ ${tableDom}
281
+ </a-col>
282
+ </a-row>
283
+
284
+ <!-- 弹窗 -->
285
+ <a-modal :width="1200" v-model:visible="state.modal.show" title="标题" destroyOnClose @ok="handleModalOk">
286
+ <!-- 此处放弹窗业务代码,示例: -->
287
+ <a-form v-if="state.modal.action === '新增'" ref="addFormRef" :model="state.modal.data" autocomplete="off">
288
+ <a-form-item
289
+ label="Username"
290
+ name="username"
291
+ :rules="[{ required: true, message: 'Please input your username!' }]"
292
+ >
293
+ <a-input v-model:value="state.modal.data.username" />
294
+ </a-form-item>
295
+
296
+ <a-form-item
297
+ label="Password"
298
+ name="password"
299
+ :rules="[{ required: true, message: 'Please input your password!' }]"
300
+ >
301
+ <a-input-password v-model:value="state.modal.data.password" />
302
+ </a-form-item>
303
+ </a-form>
304
+ </a-modal>
305
+ </template>
306
+
307
+ <script setup>
308
+ import { ref, reactive, onMounted } from 'vue'
309
+ // 引入api文件
310
+ // import api from '@/api/xxx.js'
311
+
312
+ // 定义变量
313
+ const state = reactive({
314
+ tree: ${JSON.stringify(treeConfig.props, null, 2)},
315
+ searchParams: ${JSON.stringify(searchParams)},
316
+ tableColumns: ${JSON.stringify(tableConfig.columns)},
317
+ tableData: ${JSON.stringify(tableConfig.data)},
318
+ pagination: ${
319
+ tableConfig.pagination.show
320
+ ? JSON.stringify(tableConfig.pagination.options)
321
+ : false
322
+ },
323
+ modal: { show: false, action: '', data: {} }
324
+ })
325
+ // 搜索区域实例
326
+ const searchFormRef = ref(null)
327
+ // 新增表单实例
328
+ const addFormRef = ref(null)
329
+
330
+ // 页面挂载完成
331
+ onMounted(() => {
332
+ getData()
333
+ })
334
+
335
+ // 数据请求
336
+ const getData = () =>{
337
+ ${
338
+ tableConfig.pagination.show
339
+ ? `
340
+ const {current, pageSize} = state.pagination
341
+ let params = {
342
+ current,
343
+ size: pageSize,
344
+ treeValue: state.tree.selectedKeys[0],
345
+ ...state.searchParams
346
+ }
347
+ api.getTableData(params).then((res) => {
348
+ state.pagination.total = res.total
349
+ const records = res.records
350
+ if (current === 1) state.tableData = records
351
+ else state.tableData = state.tableData.concat(records)
352
+ })
353
+ `
354
+ : `
355
+ let params = {
356
+ treeValue: state.tree.selectedKeys[0],
357
+ ...state.searchParams
358
+ }
359
+ api.getTableData(params).then((res) => {
360
+ const data = res.data
361
+ state.tableData = data
362
+ })
363
+ `
364
+ }
365
+ }
366
+
367
+ const handleTableLoad = (val) => {
368
+ ${tableConfig.pagination.show ? "state.pagination.current = 1" : ""}
369
+ getData()
370
+ }
371
+
372
+ const handleReset = () => {
373
+ // 表单重置到初始状态
374
+ searchFormRef.value.resetFields()
375
+ handleTableLoad()
376
+ }
377
+
378
+ const handleActionClick = () => {
379
+
380
+ }
381
+
382
+ const handleToolsClick = (val) => {
383
+ state.modal = { show: true, action: val, data: {} }
384
+ }
385
+
386
+ const handleModalOk = () => {
387
+ addFormRef.value.validate().then((res) => {
388
+ console.log(state.modal.data)
389
+ // 此处编写提交方法
390
+ // ...
391
+ // 提交成功后,关闭弹窗 handleModalCancel
392
+ handleModalCancel()
393
+ })
394
+ }
395
+
396
+ const handleModalCancel = () => {
397
+ state.modal = { show: false, action: '', data: {} }
398
+ }
399
+
400
+ </script>
401
+ \n\n`;
402
+
403
+ return nodeStr;
404
+ }
405
+
406
+ if (element.type === "input") {
407
+ let nodeStr = `<a-input v-model:value="state.searchParams.${element.model}"`;
408
+ if (element.options.maxlength !== -1)
409
+ nodeStr += ` maxLength="${element.options.maxlength}"`;
410
+ if (element.options.placeholder)
411
+ nodeStr += ` placeholder="${element.options.placeholder}"`;
412
+ if (element.options.disabled) nodeStr += " disabled";
413
+ if (element.options.clearable) nodeStr += " allow-clear";
414
+ nodeStr += " />\n";
415
+ return nodeStr;
416
+ }
417
+
418
+ if (element.type === "textarea") {
419
+ const nodeStr = `<a-textarea v-model:value="state.searchParams.${element.model}" maxLength="200" placeholder="请输入" auto-size allow-clear />\n`;
420
+ return nodeStr;
421
+ }
422
+
423
+ if (element.type === "select") {
424
+ const nodeStr = `<a-select v-model:value="state.searchParams.${element.model}" placeholder="请输入" allow-clear @change="handleSelectChange" />\n`;
425
+ return nodeStr;
426
+ }
427
+ };
@@ -98,6 +98,7 @@ export const tools = {
98
98
  name: "新增",
99
99
  text: "新增",
100
100
  position: "header",
101
+ page: "",
101
102
  form: "",
102
103
  api: "",
103
104
  style: { ...buttonStyle, type: "primary" }
@@ -108,6 +109,7 @@ export const tools = {
108
109
  name: "编辑",
109
110
  text: "编辑",
110
111
  position: "row",
112
+ page: "",
111
113
  form: "",
112
114
  api: "",
113
115
  style: { ...buttonStyle, type: "primary", plain: true }
@@ -118,6 +120,7 @@ export const tools = {
118
120
  name: "查看",
119
121
  text: "查看",
120
122
  position: "row",
123
+ page: "",
121
124
  form: "",
122
125
  api: "",
123
126
  style: { ...buttonStyle, type: "primary", plain: true }
@@ -128,6 +131,7 @@ export const tools = {
128
131
  name: "删除",
129
132
  text: "删除",
130
133
  position: "row",
134
+ page: "",
131
135
  form: "",
132
136
  api: "",
133
137
  style: { ...buttonStyle, type: "danger", plain: true }
@@ -138,6 +142,7 @@ export const tools = {
138
142
  name: "批量删除",
139
143
  text: "批量删除",
140
144
  position: "header",
145
+ page: "",
141
146
  form: "",
142
147
  api: "",
143
148
  style: { ...buttonStyle, type: "danger", plain: true }
@@ -148,6 +153,7 @@ export const tools = {
148
153
  name: "导出",
149
154
  text: "导出",
150
155
  position: "header",
156
+ page: "",
151
157
  form: "",
152
158
  api: "",
153
159
  style: { ...buttonStyle }
@@ -158,6 +164,7 @@ export const tools = {
158
164
  name: "导入",
159
165
  text: "导入",
160
166
  position: "header",
167
+ page: "",
161
168
  form: "",
162
169
  api: "",
163
170
  style: { ...buttonStyle }
@@ -627,6 +627,17 @@
627
627
  <el-form-item label="按钮图标">
628
628
  <th-icons v-model="dialog.data.style.icon"></th-icons>
629
629
  </el-form-item>
630
+ <el-form-item>
631
+ <el-tooltip
632
+ slot="label"
633
+ effect="light"
634
+ content="按钮点击事件绑定的原生页面路径,参数可使用key={value}占位,例:/page/path?id={id}&name=123"
635
+ placement="top"
636
+ >
637
+ <span style="color: #409EFF;">关联页面</span>
638
+ </el-tooltip>
639
+ <el-input v-model="dialog.data.page" placeholder="请填写页面路径"></el-input>
640
+ </el-form-item>
630
641
  <el-form-item>
631
642
  <el-tooltip
632
643
  slot="label"
@@ -27,7 +27,7 @@
27
27
  <el-radio-button label="api">接口导入</el-radio-button>
28
28
  </el-radio-group>
29
29
  </el-form-item>
30
- <el-form-item v-if="config.table.fields.type==='api'">
30
+ <el-form-item v-if="config.table.fields.type === 'api'">
31
31
  <el-tooltip
32
32
  slot="label"
33
33
  effect="light"
@@ -166,8 +166,7 @@ export default {
166
166
  return [];
167
167
  }
168
168
  },
169
- created() {},
170
- mounted() {
169
+ created() {
171
170
  bus.$on("fieldsData", data => {
172
171
  const initParams = (list, params) => {
173
172
  list.map(item => {
@@ -215,6 +214,9 @@ export default {
215
214
  handleOutParamsChange() {
216
215
  bus.$emit("fieldsOutParamsActive", this.outParamsActive);
217
216
  }
217
+ },
218
+ beforeDestroy() {
219
+ bus.$off("fieldsData");
218
220
  }
219
221
  };
220
222
  </script>