@epxing/business 5.3.0-beta.2 → 5.3.0-beta.3
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/API.md +8 -4
- package/README.md +44 -44
- package/dist/src/base/AiSkillEditor.js +1 -1
- package/dist/src/base/AiSkillEditor.vue.js +2 -0
- package/dist/src/base/AppConfigFormItem.js +1 -3
- package/dist/src/base/AppConfigFormItem.vue.js +210 -85
- package/dist/src/base/CommonFieldList.js +1 -1
- package/dist/src/base/CommonFieldList.vue.js +2 -1
- package/dist/src/base/ConfigModuleIndex.js +38 -1
- package/dist/src/base/ManageAppNav.js +1 -1
- package/dist/src/base/ManageMenu.js +1 -1
- package/dist/src/base/RoleBindTrace.js +253 -0
- package/dist/src/base/RoleGroupManage.js +1037 -0
- package/dist/src/base/ServiceMenu.js +7 -6
- package/dist/src/components/AiList.js +1278 -3
- package/dist/src/components/EntityCheckboxFind.vue.js +14 -10
- package/dist/src/components/EntityRightFormItem.js +1 -5
- package/dist/src/components/EntityRightFormItem.vue.js +3 -1
- package/dist/src/components/EntitySystemEr.js +492 -0
- package/dist/src/components/HallNav.vue.js +7 -36
- package/dist/src/components/IconFontLibrary.js +22 -1
- package/dist/src/components/IconFontList.js +21 -1
- package/dist/src/components/PrintFormList.js +2 -1
- package/dist/src/components/PrintFormList.vue.js +3 -1
- package/dist/src/components/WikiWorkbench.js +153 -129
- package/dist/src/components/authorization/AuthorizationInterface.js +3 -1
- package/dist/src/components/custom-bpmn/PropertiesView.js +1991 -1942
- package/dist/src/components/icon-gallery/IconGallery.js +193 -0
- package/dist/src/components/icon-gallery/mixin.js +150 -0
- package/dist/src/components/wiki-workbench/WikiIntake.js +86 -93
- package/dist/src/components/wiki-workbench/WikiIntake.vue.js +153 -73
- package/dist/src/index.js +26 -20
- package/dist/src/public-components.js +16 -14
- package/dist/src/route-components.js +5 -5
- package/dist/src/system.component.index.js +1 -1
- package/dist/src/system.component.js +8 -3
- package/dist/src/system.component.lazy.js +1 -1
- package/dist/src/views/Add.js +1 -1
- package/dist/src/views/Add.vue.js +8 -3
- package/dist/src/views/AiToolManager.js +792 -317
- package/dist/src/views/App.js +3 -45
- package/dist/src/views/AppRoleSelect.js +3 -230
- package/dist/src/views/Error.js +3 -207
- package/dist/src/views/ExcelDesign.js +326 -316
- package/dist/src/views/JvmMemoryMonitor.js +463 -0
- package/dist/src/views/Module.js +3 -170
- package/dist/src/views/WikiBinding.js +88 -25
- package/dist/style.css +2867 -1487
- package/package.json +12 -6
- package/src/base/AiSkillEditor.vue +2 -0
- package/src/base/AppConfigFormItem.vue +211 -145
- package/src/base/CommonFieldList.vue +9 -6
- package/src/base/ConfigModuleIndex.vue +37 -1
- package/src/base/ManageAppNav.vue +1188 -1188
- package/src/base/ManageMenu.vue +933 -933
- package/src/base/RoleBindTrace.vue +364 -0
- package/src/base/RoleGroupManage.vue +1160 -0
- package/src/base/ServiceMenu.vue +6 -5
- package/src/components/AiList.vue +439 -113
- package/src/components/EntityCheckboxFind.vue +12 -8
- package/src/components/EntityRightFormItem.vue +9 -10
- package/src/components/EntitySystemEr.vue +517 -0
- package/src/components/HallNav.vue +6 -33
- package/src/components/IconFontLibrary.vue +27 -60
- package/src/components/IconFontList.vue +13 -64
- package/src/components/PrintFormList.vue +33 -27
- package/src/components/WikiWorkbench.vue +90 -60
- package/src/components/authorization/AuthorizationInterface.vue +2 -0
- package/src/components/custom-bpmn/CustomPalette.js +1 -1
- package/src/components/custom-bpmn/CustomRenderer.js +1 -1
- package/src/components/custom-bpmn/PropertiesView.vue +35 -4
- package/src/components/custom-bpmn/index.js +1 -1
- package/src/components/icon-gallery/IconGallery.vue +130 -0
- package/src/components/icon-gallery/mixin.jsx +109 -0
- package/src/components/wiki-workbench/WikiIntake.vue +178 -104
- package/src/index.js +24 -20
- package/src/public-components.js +1 -0
- package/src/route-components.js +4 -4
- package/src/system.component.index.js +1 -1
- package/src/views/Add.vue +8 -5
- package/src/views/AiToolManager.vue +326 -4
- package/src/views/App.vue +4 -53
- package/src/views/AppRoleSelect.vue +4 -334
- package/src/views/Error.vue +4 -63
- package/src/views/ExcelDesign.vue +24 -7
- package/src/views/JvmMemoryMonitor.vue +284 -0
- package/src/views/Module.vue +4 -210
- package/src/views/WikiBinding.vue +42 -0
- package/types/app.d.ts +1 -0
- package/types/dept-find.d.ts +1 -1
- package/types/index.d.ts +15 -14
- package/types/popup.d.ts +2 -2
- package/types/route-components.d.ts +1 -1
- package/types/user-find.d.ts +1 -1
- package/dist/assets/role_select-DTqRlFNz.webp +0 -0
- package/dist/src/components/AiList.vue.js +0 -93
- package/dist/src/components/IconFontLibrary.vue.js +0 -67
- package/dist/src/components/IconFontList.vue.js +0 -79
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@epxing/business",
|
|
3
|
-
"version": "5.3.0-beta.
|
|
3
|
+
"version": "5.3.0-beta.3",
|
|
4
4
|
"description": "平台业务组件与页面(Login/base/custom-bpmn 等;不含 designer 懒注册)",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"exports": {
|
|
@@ -10,6 +10,11 @@
|
|
|
10
10
|
"default": "./dist/src/index.js"
|
|
11
11
|
},
|
|
12
12
|
"./src": "./dist/src/index.js",
|
|
13
|
+
"./app": {
|
|
14
|
+
"types": "./types/app.d.ts",
|
|
15
|
+
"import": "./dist/src/views/App.js",
|
|
16
|
+
"default": "./dist/src/views/App.js"
|
|
17
|
+
},
|
|
13
18
|
"./user-find": {
|
|
14
19
|
"types": "./types/user-find.d.ts",
|
|
15
20
|
"import": "./dist/src/components/UserFind.js",
|
|
@@ -100,11 +105,12 @@
|
|
|
100
105
|
"tiny-svg": "^4.1.4",
|
|
101
106
|
"@hufe921/canvas-editor": "^0.9.100",
|
|
102
107
|
"@hufe921/canvas-editor-plugin-docx": "^0.0.5",
|
|
103
|
-
"@epxing/
|
|
104
|
-
"@epxing/
|
|
105
|
-
"@epxing/
|
|
106
|
-
"@epxing/
|
|
107
|
-
"@epxing/
|
|
108
|
+
"@epxing/components": "^5.3.0-beta.3",
|
|
109
|
+
"@epxing/dashboard": "^5.3.0-beta.3",
|
|
110
|
+
"@epxing/core": "^5.3.0-beta.3",
|
|
111
|
+
"@epxing/icons": "^5.3.0-beta.3",
|
|
112
|
+
"@epxing/utils": "^5.3.0-beta.3",
|
|
113
|
+
"@epxing/theme": "^5.3.0-beta.3"
|
|
108
114
|
},
|
|
109
115
|
"peerDependencies": {
|
|
110
116
|
"vue": "3.5.39",
|
|
@@ -2,18 +2,41 @@
|
|
|
2
2
|
// @jsx-vue3(T30 JSX 批:Vue3 JSX 语法,@vue/babel-plugin-jsx 编译)
|
|
3
3
|
|
|
4
4
|
import AddFormItem from '@epxing/components/src/add-form-item'
|
|
5
|
+
import TableForm from '@epxing/components/src/form'
|
|
6
|
+
import AppSettings from '@epxing/components/src/app-settings/AppSettings.vue'
|
|
7
|
+
import AppAppearancePreview from '@epxing/components/src/app-settings/AppAppearancePreview.vue'
|
|
8
|
+
import { createAppUiDraft } from '@epxing/core/src/app-ui-settings'
|
|
9
|
+
import { captureRef } from '@epxing/core/src/capture-ref'
|
|
5
10
|
export default {
|
|
6
11
|
name: 'epx-base-app-config-form-item',
|
|
7
12
|
extends: AddFormItem,
|
|
13
|
+
components: { AppSettings, AppAppearancePreview, TableForm },
|
|
8
14
|
data () {
|
|
9
15
|
return {
|
|
10
16
|
config: {},
|
|
11
|
-
fieldsConfigs: []
|
|
17
|
+
fieldsConfigs: [],
|
|
18
|
+
layoutFieldsConfigs: [],
|
|
19
|
+
activeGroup: 'theme',
|
|
20
|
+
uiDraft: {},
|
|
21
|
+
initialConfig: '{}',
|
|
22
|
+
syncingDraft: true,
|
|
23
|
+
settingsGroups: [
|
|
24
|
+
{ key: 'theme', label: '主题与配色' },
|
|
25
|
+
{ key: 'layout', label: '导航与布局' },
|
|
26
|
+
{ key: 'style', label: '界面风格' },
|
|
27
|
+
{ key: 'tabs', label: '页签设置' },
|
|
28
|
+
{ key: 'page', label: '页面与效果' }
|
|
29
|
+
]
|
|
12
30
|
}
|
|
13
31
|
},
|
|
14
32
|
computed: {
|
|
33
|
+
readOnly () { return ['DETAIL', 'READONLY'].includes(this.componentType) },
|
|
15
34
|
showFieldsConfigs () {
|
|
16
|
-
return this.
|
|
35
|
+
return this.layoutFieldsConfigs.filter(item => {
|
|
36
|
+
const themeKeys = ['navBackgroundColorType', 'navBackgroundColor']
|
|
37
|
+
const pageKeys = ['pageBackgroundType', 'pageBackgroundColor', 'pageBackgroundGradient', 'pageBackgroundImage', 'pageBackgroundSize']
|
|
38
|
+
const group = themeKeys.includes(item.key) ? 'theme' : pageKeys.includes(item.key) ? 'page' : 'layout'
|
|
39
|
+
if (group !== this.activeGroup) return false
|
|
17
40
|
let flag = true
|
|
18
41
|
if (item.showFlag) {
|
|
19
42
|
for (const key in item.showFlag) {
|
|
@@ -30,10 +53,20 @@ export default {
|
|
|
30
53
|
watch: {
|
|
31
54
|
config: {
|
|
32
55
|
handler (v) {
|
|
56
|
+
if (this.syncingDraft || this.readOnly) return
|
|
33
57
|
const APP_CONFIG = JSON.stringify(v)
|
|
34
58
|
this.$emit('change', { ...this.data, APP_CONFIG })
|
|
35
59
|
},
|
|
36
60
|
deep: true
|
|
61
|
+
},
|
|
62
|
+
uiDraft: {
|
|
63
|
+
deep: true,
|
|
64
|
+
handler (value) {
|
|
65
|
+
if (!this.syncingDraft && !this.readOnly) this.config.uiDefaults = JSON.parse(JSON.stringify(value))
|
|
66
|
+
}
|
|
67
|
+
},
|
|
68
|
+
'formData.APP_CONFIG' (value) {
|
|
69
|
+
if (value !== JSON.stringify(this.config)) this.loadConfig(value)
|
|
37
70
|
}
|
|
38
71
|
},
|
|
39
72
|
methods: {
|
|
@@ -76,6 +109,7 @@ export default {
|
|
|
76
109
|
key: 'navBackgroundColor',
|
|
77
110
|
label: '自定义导航背景色',
|
|
78
111
|
type: 'color',
|
|
112
|
+
showFlag: { navBackgroundColorType: 'custom' },
|
|
79
113
|
predefineColors: []
|
|
80
114
|
},
|
|
81
115
|
{
|
|
@@ -188,69 +222,34 @@ export default {
|
|
|
188
222
|
defaultValue: 992
|
|
189
223
|
}
|
|
190
224
|
]
|
|
191
|
-
if (this.appConfig['SYSTEM|TYPE'] === 'hall') {
|
|
192
|
-
fieldsConfigs.splice(9, 0, {
|
|
193
|
-
key: 'componentMargin',
|
|
194
|
-
label: '页面组件间距',
|
|
195
|
-
type: 'radio',
|
|
196
|
-
options: [
|
|
197
|
-
{
|
|
198
|
-
label: '小',
|
|
199
|
-
value: 'small'
|
|
200
|
-
},
|
|
201
|
-
{
|
|
202
|
-
label: '中',
|
|
203
|
-
value: 'medium'
|
|
204
|
-
},
|
|
205
|
-
{
|
|
206
|
-
label: '默认',
|
|
207
|
-
value: 'base'
|
|
208
|
-
}
|
|
209
|
-
],
|
|
210
|
-
defaultValue: 'base'
|
|
211
|
-
},
|
|
212
|
-
{
|
|
213
|
-
key: 'borderRadius',
|
|
214
|
-
label: '圆角',
|
|
215
|
-
type: 'radio',
|
|
216
|
-
options: [
|
|
217
|
-
{
|
|
218
|
-
label: '无',
|
|
219
|
-
value: 'zero'
|
|
220
|
-
},
|
|
221
|
-
{
|
|
222
|
-
label: '默认',
|
|
223
|
-
value: 'base'
|
|
224
|
-
},
|
|
225
|
-
{
|
|
226
|
-
label: '中',
|
|
227
|
-
value: 'medium'
|
|
228
|
-
},
|
|
229
|
-
{
|
|
230
|
-
label: '大',
|
|
231
|
-
value: 'large'
|
|
232
|
-
}
|
|
233
|
-
],
|
|
234
|
-
defaultValue: 'base'
|
|
235
|
-
})
|
|
236
|
-
}
|
|
237
225
|
for (const item of fieldsConfigs) {
|
|
238
226
|
item.state = pageType
|
|
239
227
|
if (item.options) item.options = item.options.map(item => ({ id: item.value, code: item.value, name: item.label, preview: item.preview }))
|
|
240
228
|
}
|
|
241
|
-
this.
|
|
229
|
+
this.layoutFieldsConfigs = fieldsConfigs
|
|
230
|
+
// 父表单只提交 APP_CONFIG;导航等草稿字段均封装在该 JSON 内。
|
|
231
|
+
this.fieldsConfigs = [{ attriName: 'APP_CONFIG', state: 'HIDDEN' }]
|
|
242
232
|
},
|
|
243
233
|
changeConfigItem (key, value) {
|
|
234
|
+
if (this.readOnly) return
|
|
244
235
|
this.config[key] = value
|
|
245
236
|
},
|
|
246
237
|
save () {
|
|
238
|
+
if (this.readOnly) return
|
|
239
|
+
// 优先交给父表单整表提交,保留应用的名称、权限等其他字段。
|
|
240
|
+
if (this.form?.submitForm && !this.isEdit) {
|
|
241
|
+
this.$nextTick(() => this.form.submitForm())
|
|
242
|
+
return
|
|
243
|
+
}
|
|
247
244
|
const params = {}
|
|
248
245
|
const submitFlag = true
|
|
249
246
|
const { submitParams: querySumitParams = {} } = this.$query
|
|
250
247
|
if (this.formData[this.$metaKey]) {
|
|
251
248
|
params[`bean.${this.$metaKey}`] = this.formData[this.$metaKey]
|
|
252
249
|
}
|
|
253
|
-
|
|
250
|
+
Object.entries({ ...this.formData, APP_CONFIG: JSON.stringify(this.config) }).forEach(([key, value]) => {
|
|
251
|
+
params[`bean.${key}`] = value
|
|
252
|
+
})
|
|
254
253
|
|
|
255
254
|
// 表单校验
|
|
256
255
|
const { componentEvents = {} } = this.$configs
|
|
@@ -276,53 +275,112 @@ export default {
|
|
|
276
275
|
})
|
|
277
276
|
},
|
|
278
277
|
switchNav (value, item) {
|
|
279
|
-
if (item.state
|
|
278
|
+
if (!['DETAIL', 'READONLY'].includes(item.state)) {
|
|
280
279
|
this.config[item.key] = value
|
|
281
280
|
}
|
|
282
281
|
},
|
|
282
|
+
loadConfig (value = '{}') {
|
|
283
|
+
this.syncingDraft = true
|
|
284
|
+
const config = JSON.parse(value || '{}')
|
|
285
|
+
this.initialConfig = JSON.stringify(config)
|
|
286
|
+
for (const item of this.layoutFieldsConfigs) {
|
|
287
|
+
if (config[item.key] === undefined && item.defaultValue !== undefined) config[item.key] = item.defaultValue
|
|
288
|
+
}
|
|
289
|
+
this.config = config
|
|
290
|
+
this.uiDraft = createAppUiDraft(config)
|
|
291
|
+
this.$nextTick(() => { this.syncingDraft = false })
|
|
292
|
+
},
|
|
293
|
+
restorePlatform () {
|
|
294
|
+
if (this.readOnly) return
|
|
295
|
+
this.uiDraft = createAppUiDraft()
|
|
296
|
+
const businessKeys = ['appPageType', 'pageId', 'navComponent', 'navOperates', 'mobileSize']
|
|
297
|
+
for (const field of this.layoutFieldsConfigs) {
|
|
298
|
+
if (businessKeys.includes(field.key)) continue
|
|
299
|
+
if (field.defaultValue !== undefined) this.config[field.key] = field.defaultValue
|
|
300
|
+
else delete this.config[field.key]
|
|
301
|
+
}
|
|
302
|
+
},
|
|
303
|
+
discardDraft () {
|
|
304
|
+
const initial = this.initialConfig
|
|
305
|
+
this.loadConfig(initial)
|
|
306
|
+
this.$emit('change', { ...this.data, APP_CONFIG: initial })
|
|
307
|
+
},
|
|
283
308
|
renderForm () {
|
|
284
309
|
return (
|
|
285
|
-
<
|
|
310
|
+
<section class="epx-app-interface-settings">
|
|
311
|
+
<div hidden>
|
|
312
|
+
<TableForm ref={captureRef(this, 'form')} fieldsConfigs={this.fieldsConfigs} modelValue={{ ...this.data, APP_CONFIG: JSON.stringify(this.config) }} type="auto" showRelyFlag={false} valueRelyFlag={false} requiredRelyFlag={false} />
|
|
313
|
+
</div>
|
|
314
|
+
<div class="epx-app-interface-settings__heading">
|
|
315
|
+
<p>设置当前应用的默认外观;用户的个人选择优先。右侧预览不会改变当前界面。</p>
|
|
316
|
+
</div>
|
|
317
|
+
<div class="epx-app-interface-settings__workspace">
|
|
318
|
+
<nav class="epx-app-interface-settings__nav" aria-label="界面设置分组">
|
|
319
|
+
{this.settingsGroups.map(group => (
|
|
320
|
+
<button type="button" key={group.key} class={{ 'is-active': this.activeGroup === group.key }} aria-current={this.activeGroup === group.key ? 'page' : undefined} onClick={() => { this.activeGroup = group.key }}>{group.label}</button>
|
|
321
|
+
))}
|
|
322
|
+
</nav>
|
|
323
|
+
<div class="epx-app-interface-settings__editor">
|
|
324
|
+
<h4>{this.settingsGroups.find(group => group.key === this.activeGroup)?.label}</h4>
|
|
325
|
+
<AppSettings embedded settings={this.uiDraft} sections={[this.activeGroup]} disabled={this.readOnly} />
|
|
326
|
+
{this.renderLayoutFields()}
|
|
327
|
+
</div>
|
|
328
|
+
<AppAppearancePreview config={this.config} settings={this.uiDraft} title={this.data.NAME || '应用名称'} />
|
|
329
|
+
</div>
|
|
330
|
+
{!this.readOnly && <div class="epx-app-interface-settings__actions">
|
|
331
|
+
<el-button onClick={this.restorePlatform}>恢复平台默认</el-button>
|
|
332
|
+
<el-button onClick={this.discardDraft}>撤销本次修改</el-button>
|
|
333
|
+
<el-button type="primary" onClick={this.save}>保存</el-button>
|
|
334
|
+
</div>}
|
|
335
|
+
</section>
|
|
336
|
+
)
|
|
337
|
+
},
|
|
338
|
+
renderLayoutFields () {
|
|
339
|
+
return (
|
|
340
|
+
<el-form disabled={this.readOnly} class="epx-base-app-config-form-item__form">
|
|
286
341
|
{
|
|
287
342
|
this.showFieldsConfigs.map(item => (
|
|
288
|
-
<
|
|
289
|
-
{
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
343
|
+
<div key={item.key} class={['epx-app-interface-settings__field', { 'epx-app-interface-settings__field--block': item.block || item.type === 'radio' }]}>
|
|
344
|
+
<span class="epx-app-interface-settings__label">{item.label}</span>
|
|
345
|
+
<div class="epx-app-interface-settings__control">
|
|
346
|
+
{
|
|
347
|
+
item.key === 'navType' ? (
|
|
348
|
+
<div class="nav-type" role="group" aria-label={item.label}>
|
|
349
|
+
{
|
|
350
|
+
item.options.map(option => (
|
|
351
|
+
<button type="button" class={['nav-type__item', { 'is-active': this.config[item.key] === option.id }]} key={option.id} disabled={this.readOnly} aria-pressed={this.config[item.key] === option.id} onClick={this.switchNav.bind(this, option.id, item)}>
|
|
352
|
+
<img src={option.preview} alt="" />
|
|
353
|
+
<span>{option.name}</span>
|
|
354
|
+
</button>
|
|
355
|
+
))
|
|
356
|
+
}
|
|
357
|
+
</div>
|
|
358
|
+
) : item.type === 'radio' ? (
|
|
359
|
+
<el-radio-group v-model={this.config[item.key]} size="small" aria-label={item.label}>
|
|
360
|
+
{item.options.map(option => <el-radio-button key={option.id} value={option.id}>{option.name}</el-radio-button>)}
|
|
361
|
+
</el-radio-group>
|
|
362
|
+
) : item.type === 'object' ? (
|
|
363
|
+
<epx-visual-config-object value={this.config[item.key]} onChangeConfigs={this.changeConfigItem.bind(this, item.key)} label={item.label} object={item.object} flag={item.flag} dataKey={item.dataKey} state={item.state}></epx-visual-config-object>
|
|
364
|
+
) : item.type === 'color' ? (
|
|
365
|
+
<el-color-picker v-model={this.config[item.key]} predefine={item.predefineColors} disabled={this.readOnly}></el-color-picker>
|
|
366
|
+
) : item.type === 'gradient' ? (
|
|
367
|
+
<epx-color-picker v-model={this.config[item.key]} disabled={this.readOnly}></epx-color-picker>
|
|
368
|
+
) : item.type === 'photo' ? (
|
|
369
|
+
<epx-photo v-model={this.config[item.key]} fieldConfigs={{ state: item.state, attriName: item.key, attriLabel: item.label }}></epx-photo>
|
|
370
|
+
) : ['num', 'number'].includes(item.type) ? (
|
|
371
|
+
<epx-number v-model={this.config[item.key]} fieldConfigs={{ state: item.state, attriName: item.key, attriLabel: item.label, value: item.defaultValue }}></epx-number>
|
|
372
|
+
) : item.type === 'operates' ? (
|
|
373
|
+
<epx-visual-config-operate
|
|
374
|
+
value={this.config[item.key]}
|
|
375
|
+
state={item.state}
|
|
376
|
+
onChangeConfigs={this.changeConfigItem.bind(this, item.key)}
|
|
377
|
+
/>
|
|
378
|
+
) : (
|
|
379
|
+
<epx-input class="input" v-model={this.config[item.key]} fieldConfigs={{ state: item.state, attriName: item.key, attriLabel: item.label }}></epx-input>
|
|
380
|
+
)
|
|
381
|
+
}
|
|
382
|
+
</div>
|
|
383
|
+
</div>
|
|
326
384
|
))
|
|
327
385
|
}
|
|
328
386
|
|
|
@@ -331,74 +389,82 @@ export default {
|
|
|
331
389
|
}
|
|
332
390
|
},
|
|
333
391
|
created () {
|
|
334
|
-
|
|
335
|
-
const appConfig = JSON.parse(APP_CONFIG)
|
|
336
|
-
for (const item of this.fieldsConfigs) {
|
|
337
|
-
if (!appConfig[item.key] && item.defaultValue) {
|
|
338
|
-
appConfig[item.key] = item.defaultValue
|
|
339
|
-
}
|
|
340
|
-
}
|
|
341
|
-
this.config = appConfig
|
|
392
|
+
this.loadConfig(this.data.APP_CONFIG)
|
|
342
393
|
}
|
|
343
394
|
}
|
|
344
395
|
</script>
|
|
345
396
|
|
|
346
|
-
<style lang="scss"
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
}
|
|
354
|
-
:deep(.el-form-item__label::after) {
|
|
355
|
-
content: ': '
|
|
356
|
-
}
|
|
357
|
-
|
|
358
|
-
}
|
|
359
|
-
|
|
360
|
-
.nav-type {
|
|
361
|
-
display: flex;
|
|
362
|
-
flex-wrap: wrap;
|
|
363
|
-
&.is-disabled {
|
|
364
|
-
.nav-type__item {
|
|
365
|
-
>div {
|
|
366
|
-
cursor: not-allowed;
|
|
367
|
-
}
|
|
368
|
-
}
|
|
397
|
+
<style lang="scss">
|
|
398
|
+
// 通过表单根类隔离样式,避免继承渲染时丢失 scoped 标记导致预览恢复原图尺寸。
|
|
399
|
+
.epx-base-app-config-form-item__form {
|
|
400
|
+
.nav-type {
|
|
401
|
+
display: grid;
|
|
402
|
+
grid-template-columns: repeat(4, minmax(0, 1fr));
|
|
403
|
+
gap: var(--epx-space-2);
|
|
369
404
|
}
|
|
370
|
-
}
|
|
371
405
|
|
|
372
|
-
.nav-type__item {
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
406
|
+
.nav-type__item {
|
|
407
|
+
min-width: 0;
|
|
408
|
+
padding: var(--epx-space-1);
|
|
409
|
+
text-align: center;
|
|
410
|
+
font: inherit;
|
|
411
|
+
font-size: var(--epx-font-size-s);
|
|
412
|
+
color: var(--epx-text-secondary);
|
|
413
|
+
background: transparent;
|
|
414
|
+
border: 1px solid var(--epx-border);
|
|
378
415
|
border-radius: var(--epx-radius-base);
|
|
379
|
-
border: 1px solid transparent;
|
|
380
|
-
overflow: hidden;
|
|
381
416
|
cursor: pointer;
|
|
382
|
-
transition: all .5s;
|
|
383
|
-
}
|
|
384
|
-
img {
|
|
385
|
-
width: 100%;
|
|
386
|
-
opacity: 0.5;
|
|
387
|
-
transition: all .5s;
|
|
388
|
-
}
|
|
389
|
-
&:hover {
|
|
390
417
|
img {
|
|
391
|
-
|
|
418
|
+
display: block;
|
|
419
|
+
width: 100%;
|
|
420
|
+
aspect-ratio: 10 / 7;
|
|
421
|
+
object-fit: contain;
|
|
422
|
+
margin-bottom: var(--epx-space-1);
|
|
392
423
|
}
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
424
|
+
&:focus-visible {
|
|
425
|
+
outline: 2px solid var(--el-color-primary);
|
|
426
|
+
outline-offset: 2px;
|
|
427
|
+
}
|
|
428
|
+
&:hover:not(:disabled), &.is-active {
|
|
429
|
+
@include font_color_primary;
|
|
397
430
|
@include border_color_primary;
|
|
398
431
|
}
|
|
399
|
-
|
|
400
|
-
|
|
432
|
+
&:disabled {
|
|
433
|
+
cursor: not-allowed;
|
|
434
|
+
opacity: .6;
|
|
401
435
|
}
|
|
402
436
|
}
|
|
403
437
|
}
|
|
438
|
+
|
|
439
|
+
.epx-app-interface-settings {
|
|
440
|
+
&__heading { margin-bottom: 20px; }
|
|
441
|
+
&__heading p { margin: 0; color: var(--el-text-color-secondary); font-size: 13px; }
|
|
442
|
+
&__workspace { display: grid; grid-template-columns: 140px minmax(300px, 1fr) minmax(300px, 420px); gap: 20px; align-items: start; }
|
|
443
|
+
&__nav { display: flex; flex-direction: column; gap: 6px; }
|
|
444
|
+
&__nav button { border: 0; border-radius: 6px; background: transparent; color: inherit; text-align: left; padding: 12px; cursor: pointer; }
|
|
445
|
+
&__nav button.is-active { background: var(--el-color-primary-light-9); color: var(--el-color-primary); }
|
|
446
|
+
&__editor { min-width: 0; }
|
|
447
|
+
&__editor h4 { margin: 0 0 12px; }
|
|
448
|
+
&__field { display: flex; align-items: center; justify-content: space-between; gap: var(--epx-space-2); min-height: 40px; padding: var(--epx-space-1) var(--epx-space-4); }
|
|
449
|
+
&__label { flex-shrink: 0; font-size: var(--epx-font-size-base); color: var(--epx-text); }
|
|
450
|
+
&__control { min-width: 0; max-width: 100%; }
|
|
451
|
+
&__field--block { flex-direction: column; align-items: stretch; padding-bottom: var(--epx-space-2); }
|
|
452
|
+
&__field--block .el-radio-group { display: flex; width: 100%; }
|
|
453
|
+
&__field--block .el-radio-button { flex: 1; }
|
|
454
|
+
&__field--block .el-radio-button__inner { width: 100%; padding-left: 0; padding-right: 0; }
|
|
455
|
+
&__control .el-input-number { width: 150px; }
|
|
456
|
+
&__editor .epx-app-settings__body { padding: 0; }
|
|
457
|
+
&__editor .el-collapse { border: 0; }
|
|
458
|
+
&__editor .el-collapse-item__header { display: none; }
|
|
459
|
+
&__actions { display: flex; justify-content: flex-end; gap: 8px; border-top: 1px solid var(--el-border-color-light); padding-top: 16px; margin-top: 20px; }
|
|
460
|
+
@media (max-width: 1200px) {
|
|
461
|
+
&__workspace { grid-template-columns: 130px minmax(0, 1fr); }
|
|
462
|
+
.epx-app-appearance-preview { grid-column: 2; }
|
|
463
|
+
}
|
|
464
|
+
@media (max-width: 650px) {
|
|
465
|
+
&__workspace { display: flex; flex-direction: column; }
|
|
466
|
+
&__nav { flex-direction: row; flex-wrap: wrap; }
|
|
467
|
+
&__editor, .epx-app-appearance-preview { width: 100%; }
|
|
468
|
+
}
|
|
469
|
+
}
|
|
404
470
|
</style>
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
<script>
|
|
1
|
+
<script lang="jsx">
|
|
2
2
|
// @jsx-vue3(T30 JSX 批③:scopedSlots 集群 Vue3 化)
|
|
3
3
|
import EntitySubList from '@epxing/components/src/entity-sub-list'
|
|
4
4
|
import draggable from '@epxing/core/src/components/draggable'
|
|
@@ -324,7 +324,7 @@ export default {
|
|
|
324
324
|
modelValue={this.showFieldDialog}
|
|
325
325
|
{...{ 'onUpdate:modelValue': v => { this.showFieldDialog = v } }}
|
|
326
326
|
append-to-body={true}
|
|
327
|
-
class="show-field-dialog"
|
|
327
|
+
class="show-field-dialog epx-common-field-dialog"
|
|
328
328
|
destroy-on-close
|
|
329
329
|
width="800px"
|
|
330
330
|
top="10vh"
|
|
@@ -402,7 +402,7 @@ export default {
|
|
|
402
402
|
},
|
|
403
403
|
renderNameDialog () {
|
|
404
404
|
return (
|
|
405
|
-
<el-dialog modelValue={this.addCommonFieldDialod} {...{ 'onUpdate:modelValue': v => { this.addCommonFieldDialod = v } }} width="400px" title="新增常用导出字段" v-slots={{
|
|
405
|
+
<el-dialog class="epx-common-field-dialog" modelValue={this.addCommonFieldDialod} {...{ 'onUpdate:modelValue': v => { this.addCommonFieldDialod = v } }} width="400px" title="新增常用导出字段" v-slots={{
|
|
406
406
|
footer: () => (<span class="dialog-footer">
|
|
407
407
|
<el-button onClick={() => { this.addCommonFieldDialod = false }}>取 消</el-button>
|
|
408
408
|
<el-button type="primary" onClick={this.saveCommonField.bind(this)}>确 定</el-button>
|
|
@@ -1248,7 +1248,9 @@ $paddingSize: 16px;
|
|
|
1248
1248
|
}
|
|
1249
1249
|
</style>
|
|
1250
1250
|
|
|
1251
|
-
<style
|
|
1251
|
+
<style lang="scss">
|
|
1252
|
+
// 父类调用渲染函数时不会附加本组件的 scoped 标记,弹窗使用独立容器限定样式。
|
|
1253
|
+
.epx-common-field-dialog {
|
|
1252
1254
|
.field-setting {
|
|
1253
1255
|
display: flex;
|
|
1254
1256
|
width: 100%;
|
|
@@ -1301,7 +1303,7 @@ $paddingSize: 16px;
|
|
|
1301
1303
|
flex: 1;
|
|
1302
1304
|
overflow: auto;
|
|
1303
1305
|
|
|
1304
|
-
|
|
1306
|
+
.el-tree-node__content {
|
|
1305
1307
|
height: 48px;
|
|
1306
1308
|
}
|
|
1307
1309
|
|
|
@@ -1342,7 +1344,7 @@ $paddingSize: 16px;
|
|
|
1342
1344
|
.setting-field__row {
|
|
1343
1345
|
margin-bottom: 10px;
|
|
1344
1346
|
|
|
1345
|
-
|
|
1347
|
+
>.el-form-item {
|
|
1346
1348
|
vertical-align: auto;
|
|
1347
1349
|
width: 100%;
|
|
1348
1350
|
display: flex;
|
|
@@ -1394,4 +1396,5 @@ $paddingSize: 16px;
|
|
|
1394
1396
|
width: 90px;
|
|
1395
1397
|
}
|
|
1396
1398
|
}
|
|
1399
|
+
}
|
|
1397
1400
|
</style>
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
<div class="container">
|
|
3
3
|
<div class="content" v-if="data.ID">
|
|
4
4
|
<keep-alive>
|
|
5
|
-
<epx-menu id="menu" v-if="showMenu && uiShowSideNav" :showNav="false" class="aside hidden-sm-and-down" :modules="menu" :moduleName="`${data.NAME || $t('application')}${$t('configuration')}`" :subTitle="data['CLIENT#']" :toPages="toPages" :clickItem="toPage"></epx-menu>
|
|
5
|
+
<epx-menu id="menu" v-if="showMenu && uiShowSideNav" :showNav="false" class="aside hidden-sm-and-down" :modules="menu" :activeMenuId="configMenuKey" :moduleName="`${data.NAME || $t('application')}${$t('configuration')}`" :subTitle="data['CLIENT#']" :toPages="toPages" :clickItem="toPage"></epx-menu>
|
|
6
6
|
</keep-alive>
|
|
7
7
|
<div class="main">
|
|
8
8
|
<epx-router-view ref="router" v-if="menu.length>0" :init-route="initRoute"></epx-router-view>
|
|
@@ -20,6 +20,7 @@
|
|
|
20
20
|
<script>
|
|
21
21
|
import ModuleIndexVue from '@epxing/components/src/menu-index'
|
|
22
22
|
import { openExternalMenu } from '@epxing/utils/src/menu-open'
|
|
23
|
+
import { findMenuByKey, getRouteMenuKey } from '@epxing/core/src/menu-route'
|
|
23
24
|
const _comp = {
|
|
24
25
|
name: 'epx-base-config-module-index',
|
|
25
26
|
extends: ModuleIndexVue,
|
|
@@ -28,7 +29,42 @@ const _comp = {
|
|
|
28
29
|
data: {}
|
|
29
30
|
}
|
|
30
31
|
},
|
|
32
|
+
computed: {
|
|
33
|
+
configMenuKey () {
|
|
34
|
+
return this.$route.name === 'system' ? getRouteMenuKey(this.$route) : ''
|
|
35
|
+
},
|
|
36
|
+
initRoute () {
|
|
37
|
+
const menu = findMenuByKey(this.menu, this.configMenuKey)
|
|
38
|
+
if (menu && menu.OPEN_TYPE !== '1') {
|
|
39
|
+
return { moduleId: menu.ID, component: 'module-list-page', pageId: menu.MAIN_PAGE, menuTitle: menu.text }
|
|
40
|
+
}
|
|
41
|
+
return ModuleIndexVue.computed.initRoute.call(this)
|
|
42
|
+
}
|
|
43
|
+
},
|
|
44
|
+
watch: {
|
|
45
|
+
configMenuKey: 'restoreMenuFromRoute',
|
|
46
|
+
menu: 'restoreMenuFromRoute',
|
|
47
|
+
'data.ID': 'restoreMenuFromRoute'
|
|
48
|
+
},
|
|
31
49
|
methods: {
|
|
50
|
+
restoreMenuFromRoute () {
|
|
51
|
+
if (this.$route.name !== 'system') return
|
|
52
|
+
// 等专用菜单和系统上下文就绪后,沿用原有点击入口,保留页面参数与打开方式。
|
|
53
|
+
this.$nextTick(() => {
|
|
54
|
+
const view = this.$refs.router
|
|
55
|
+
if (!view || !this.data.ID) return
|
|
56
|
+
const menu = findMenuByKey(this.menu, this.configMenuKey)
|
|
57
|
+
if (menu) {
|
|
58
|
+
if (view.route?.moduleId === menu.ID) return
|
|
59
|
+
const activeTab = this.$tabs.find(tab => tab.active)
|
|
60
|
+
if (menu.OPEN_TYPE === '1' && activeTab?.moduleId === menu.ID) return
|
|
61
|
+
this.toPage(menu)
|
|
62
|
+
} else if (!this.configMenuKey) {
|
|
63
|
+
view.clearPage()
|
|
64
|
+
view.createPage(this.initRoute)
|
|
65
|
+
}
|
|
66
|
+
})
|
|
67
|
+
},
|
|
32
68
|
getInfo () {
|
|
33
69
|
const { name, params = {}, query = {} } = this.$route
|
|
34
70
|
const { system: querySystem = '' } = query
|