Showing
70 changed files
with
3411 additions
and
2 deletions
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { LateralNumericalControlConfig } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '/@/views/visual/packages/index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '/@/views/visual/packages/publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '../../../enum'; | ||
11 | + | ||
12 | +export const option: PublicPresetOptions = { | ||
13 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
14 | + [ComponentConfigFieldEnum.CONTROL_BAR_COLOR]: '#0072ff', | ||
15 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#000000', | ||
16 | +}; | ||
17 | + | ||
18 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
19 | + public key: string = LateralNumericalControlConfig.key; | ||
20 | + | ||
21 | + public attr = { ...componentInitConfig }; | ||
22 | + | ||
23 | + public componentConfig: ConfigType = cloneDeep(LateralNumericalControlConfig); | ||
24 | + | ||
25 | + public persetOption = cloneDeep(option); | ||
26 | + | ||
27 | + public option: PublicComponentOptions; | ||
28 | + | ||
29 | + constructor(option: PublicComponentOptions) { | ||
30 | + super(); | ||
31 | + this.option = { ...option }; | ||
32 | + } | ||
33 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
3 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + import { option } from './config'; | ||
6 | + | ||
7 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
8 | + schemas: [ | ||
9 | + { | ||
10 | + field: ComponentConfigFieldEnum.CONTROL_BAR_COLOR, | ||
11 | + label: '控制栏背景色', | ||
12 | + component: 'ColorPicker', | ||
13 | + changeEvent: 'update:value', | ||
14 | + defaultValue: option.controlBarColor, | ||
15 | + }, | ||
16 | + { | ||
17 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
18 | + label: '数值字体颜色', | ||
19 | + component: 'ColorPicker', | ||
20 | + changeEvent: 'update:value', | ||
21 | + defaultValue: option.fontColor, | ||
22 | + }, | ||
23 | + { | ||
24 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
25 | + label: '显示设备名称', | ||
26 | + component: 'Checkbox', | ||
27 | + defaultValue: option.showDeviceName, | ||
28 | + }, | ||
29 | + ], | ||
30 | + showActionButtonGroup: false, | ||
31 | + labelWidth: 120, | ||
32 | + baseColProps: { | ||
33 | + span: 12, | ||
34 | + }, | ||
35 | + }); | ||
36 | + | ||
37 | + const getFormValues = () => { | ||
38 | + return getFieldsValue(); | ||
39 | + }; | ||
40 | + | ||
41 | + const setFormValues = (data: Recordable) => { | ||
42 | + return setFieldsValue(data); | ||
43 | + }; | ||
44 | + | ||
45 | + defineExpose({ | ||
46 | + getFormValues, | ||
47 | + setFormValues, | ||
48 | + resetFormValues: resetFields, | ||
49 | + } as PublicFormInstaceType); | ||
50 | +</script> | ||
51 | + | ||
52 | +<template> | ||
53 | + <BasicForm @register="register" /> | ||
54 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { CreateComponentType } from '/@/views/visual/packages/index.type'; | ||
3 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
4 | + import { | ||
5 | + PublicComponentValueType, | ||
6 | + PublicFormInstaceType, | ||
7 | + } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
8 | + import { | ||
9 | + CommonDataSourceBindValueType, | ||
10 | + commonDataSourceSchemas, | ||
11 | + } from '../../../config/common.config'; | ||
12 | + import { DataSource } from '/@/views/visual/palette/types'; | ||
13 | + | ||
14 | + defineProps<{ | ||
15 | + values: PublicComponentValueType; | ||
16 | + componentConfig: CreateComponentType; | ||
17 | + }>(); | ||
18 | + | ||
19 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
20 | + labelWidth: 0, | ||
21 | + showActionButtonGroup: false, | ||
22 | + layout: 'horizontal', | ||
23 | + labelCol: { span: 0 }, | ||
24 | + schemas: commonDataSourceSchemas(), | ||
25 | + }); | ||
26 | + | ||
27 | + const getFormValues = () => { | ||
28 | + let value = getFieldsValue() as CommonDataSourceBindValueType; | ||
29 | + value = { | ||
30 | + ...value, | ||
31 | + customCommand: { | ||
32 | + transportType: value.transportType, | ||
33 | + service: value.service, | ||
34 | + command: value.command, | ||
35 | + commandType: value.commandType, | ||
36 | + }, | ||
37 | + }; | ||
38 | + return value; | ||
39 | + }; | ||
40 | + | ||
41 | + const setFormValues = (record: DataSource) => { | ||
42 | + const { customCommand } = record; | ||
43 | + return setFieldsValue({ | ||
44 | + ...record, | ||
45 | + transportType: customCommand?.transportType, | ||
46 | + service: customCommand?.service, | ||
47 | + command: customCommand?.command, | ||
48 | + commandType: customCommand?.commandType, | ||
49 | + } as unknown as Partial<CommonDataSourceBindValueType>); | ||
50 | + }; | ||
51 | + | ||
52 | + defineExpose({ | ||
53 | + getFormValues, | ||
54 | + setFormValues, | ||
55 | + validate, | ||
56 | + resetFormValues: resetFields, | ||
57 | + } as PublicFormInstaceType); | ||
58 | +</script> | ||
59 | + | ||
60 | +<template> | ||
61 | + <BasicForm @register="register" /> | ||
62 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('LateralNumericalControl'); | ||
5 | + | ||
6 | +export const LateralNumericalControlConfig: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + title: '控制组件1', | ||
9 | + package: PackagesCategoryEnum.CONTROL, | ||
10 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentPropsConfigType, DataFetchUpdateFn } from '/@/views/visual/packages/index.type'; | ||
3 | + import { option } from './config'; | ||
4 | + import { useDataFetch } from '/@/views/visual/packages/hook/useSocket'; | ||
5 | + import { Slider } from 'ant-design-vue'; | ||
6 | + import { computed, ref } from 'vue'; | ||
7 | + import { useComponentScale } from '../../../hook/useComponentScale'; | ||
8 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
9 | + | ||
10 | + const props = defineProps<{ | ||
11 | + config: ComponentPropsConfigType<typeof option>; | ||
12 | + }>(); | ||
13 | + | ||
14 | + const sliderValue = ref<number>(33); | ||
15 | + const sMin = ref<number>(0); | ||
16 | + const sMax = ref<number>(100); | ||
17 | + | ||
18 | + const getDesign = computed(() => { | ||
19 | + const { option, persetOption } = props.config; | ||
20 | + const { componentInfo, attribute, attributeRename } = option; | ||
21 | + const { controlBarColor: persetControlBarColor, fonColor: persetFontColor } = | ||
22 | + persetOption || {}; | ||
23 | + const { controlBarColor, fontColor } = componentInfo || {}; | ||
24 | + return { | ||
25 | + attribute: attributeRename || attribute, | ||
26 | + controlBarColor: controlBarColor ?? persetControlBarColor, | ||
27 | + fontColor: fontColor ?? persetFontColor, | ||
28 | + }; | ||
29 | + }); | ||
30 | + | ||
31 | + const handleChange = async () => {}; | ||
32 | + | ||
33 | + const updateFn: DataFetchUpdateFn = () => { | ||
34 | + // console.log(message, 'message', attribute, 'attribute'); | ||
35 | + }; | ||
36 | + | ||
37 | + useDataFetch(props, updateFn); | ||
38 | + const { getScale } = useComponentScale(props); | ||
39 | +</script> | ||
40 | + | ||
41 | +<template> | ||
42 | + <main class="w-full h-full flex flex-col justify-center"> | ||
43 | + <DeviceName :config="config" class="text-center" /> | ||
44 | + <main :style="getScale"> | ||
45 | + <div class="flex flex-col ml-11 mr-11"> | ||
46 | + <span | ||
47 | + :style="{ color: getDesign.fontColor }" | ||
48 | + class="font-bold text-xl mt-3 truncate text-center" | ||
49 | + >{{ sliderValue }}</span | ||
50 | + > | ||
51 | + <Slider | ||
52 | + :style="{ '--slider-color': getDesign.controlBarColor }" | ||
53 | + class="no-drag" | ||
54 | + v-model:value="sliderValue" | ||
55 | + :min="sMin" | ||
56 | + :max="sMax" | ||
57 | + @change="handleChange" | ||
58 | + /> | ||
59 | + | ||
60 | + <span | ||
61 | + :style="{ color: getDesign.fontColor }" | ||
62 | + class="mt-3 truncate font-bold text-xs text-center" | ||
63 | + > | ||
64 | + {{ getDesign.attribute || '设备1' }} | ||
65 | + </span> | ||
66 | + </div> | ||
67 | + </main> | ||
68 | + </main> | ||
69 | +</template> | ||
70 | +<style lang="less" scoped> | ||
71 | + :deep(.ant-slider-track) { | ||
72 | + background: var(--slider-color) !important; | ||
73 | + } | ||
74 | +</style> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { SwitchListConfig } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '/@/views/visual/packages/index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '/@/views/visual/packages/publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '../../../enum'; | ||
11 | + | ||
12 | +export const option: PublicPresetOptions = { | ||
13 | + multipleDataSourceComponent: true, | ||
14 | + [ComponentConfigFieldEnum.ICON]: 'shuiwen', | ||
15 | + [ComponentConfigFieldEnum.ICON_COLOR]: '#377DFF', | ||
16 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
17 | +}; | ||
18 | + | ||
19 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
20 | + public key: string = SwitchListConfig.key; | ||
21 | + | ||
22 | + public attr = { ...componentInitConfig }; | ||
23 | + | ||
24 | + public componentConfig: ConfigType = cloneDeep(SwitchListConfig); | ||
25 | + | ||
26 | + public persetOption = cloneDeep(option); | ||
27 | + | ||
28 | + public option: PublicComponentOptions; | ||
29 | + | ||
30 | + constructor(option: PublicComponentOptions) { | ||
31 | + super(); | ||
32 | + this.option = { ...option }; | ||
33 | + } | ||
34 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
3 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + import { option } from './config'; | ||
6 | + | ||
7 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
8 | + schemas: [ | ||
9 | + { | ||
10 | + field: ComponentConfigFieldEnum.ICON_COLOR, | ||
11 | + label: '图标颜色', | ||
12 | + component: 'ColorPicker', | ||
13 | + changeEvent: 'update:value', | ||
14 | + defaultValue: option.iconColor, | ||
15 | + }, | ||
16 | + { | ||
17 | + field: ComponentConfigFieldEnum.ICON, | ||
18 | + label: '图标', | ||
19 | + component: 'IconDrawer', | ||
20 | + changeEvent: 'update:value', | ||
21 | + defaultValue: option.icon, | ||
22 | + componentProps({ formModel }) { | ||
23 | + const color = formModel[ComponentConfigFieldEnum.ICON_COLOR]; | ||
24 | + return { | ||
25 | + color, | ||
26 | + }; | ||
27 | + }, | ||
28 | + }, | ||
29 | + { | ||
30 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
31 | + label: '显示设备名称', | ||
32 | + component: 'Checkbox', | ||
33 | + defaultValue: option.showDeviceName, | ||
34 | + }, | ||
35 | + ], | ||
36 | + showActionButtonGroup: false, | ||
37 | + labelWidth: 120, | ||
38 | + baseColProps: { | ||
39 | + span: 12, | ||
40 | + }, | ||
41 | + }); | ||
42 | + | ||
43 | + const getFormValues = () => { | ||
44 | + return getFieldsValue(); | ||
45 | + }; | ||
46 | + | ||
47 | + const setFormValues = (data: Recordable) => { | ||
48 | + return setFieldsValue(data); | ||
49 | + }; | ||
50 | + | ||
51 | + defineExpose({ | ||
52 | + getFormValues, | ||
53 | + setFormValues, | ||
54 | + resetFormValues: resetFields, | ||
55 | + } as PublicFormInstaceType); | ||
56 | +</script> | ||
57 | + | ||
58 | +<template> | ||
59 | + <BasicForm @register="register" /> | ||
60 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { CreateComponentType } from '/@/views/visual/packages/index.type'; | ||
3 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
4 | + import { | ||
5 | + PublicComponentValueType, | ||
6 | + PublicFormInstaceType, | ||
7 | + } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
8 | + import { | ||
9 | + CommonDataSourceBindValueType, | ||
10 | + commonDataSourceSchemas, | ||
11 | + } from '../../../config/common.config'; | ||
12 | + import { DataSource } from '/@/views/visual/palette/types'; | ||
13 | + | ||
14 | + defineProps<{ | ||
15 | + values: PublicComponentValueType; | ||
16 | + componentConfig: CreateComponentType; | ||
17 | + }>(); | ||
18 | + | ||
19 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
20 | + labelWidth: 0, | ||
21 | + showActionButtonGroup: false, | ||
22 | + layout: 'horizontal', | ||
23 | + labelCol: { span: 0 }, | ||
24 | + schemas: commonDataSourceSchemas(), | ||
25 | + }); | ||
26 | + | ||
27 | + const getFormValues = () => { | ||
28 | + let value = getFieldsValue() as CommonDataSourceBindValueType; | ||
29 | + value = { | ||
30 | + ...value, | ||
31 | + customCommand: { | ||
32 | + transportType: value.transportType, | ||
33 | + service: value.service, | ||
34 | + command: value.command, | ||
35 | + commandType: value.commandType, | ||
36 | + }, | ||
37 | + }; | ||
38 | + return value; | ||
39 | + }; | ||
40 | + | ||
41 | + const setFormValues = (record: DataSource) => { | ||
42 | + const { customCommand } = record; | ||
43 | + return setFieldsValue({ | ||
44 | + ...record, | ||
45 | + transportType: customCommand?.transportType, | ||
46 | + service: customCommand?.service, | ||
47 | + command: customCommand?.command, | ||
48 | + commandType: customCommand?.commandType, | ||
49 | + } as unknown as Partial<CommonDataSourceBindValueType>); | ||
50 | + }; | ||
51 | + | ||
52 | + defineExpose({ | ||
53 | + getFormValues, | ||
54 | + setFormValues, | ||
55 | + validate, | ||
56 | + resetFormValues: resetFields, | ||
57 | + } as PublicFormInstaceType); | ||
58 | +</script> | ||
59 | + | ||
60 | +<template> | ||
61 | + <BasicForm @register="register" /> | ||
62 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('SwitchList'); | ||
5 | + | ||
6 | +export const SwitchListConfig: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + title: '开关量控制列表', | ||
9 | + package: PackagesCategoryEnum.CONTROL, | ||
10 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { | ||
3 | + ComponentPropsConfigType, | ||
4 | + MultipleDataFetchUpdateFn, | ||
5 | + } from '/@/views/visual/packages/index.type'; | ||
6 | + import { option } from './config'; | ||
7 | + import { useMultipleDataFetch } from '/@/views/visual/packages/hook/useSocket'; | ||
8 | + import { SvgIcon } from '/@/components/Icon'; | ||
9 | + import { Switch } from 'ant-design-vue'; | ||
10 | + import { computed, ref } from 'vue'; | ||
11 | + import { useComponentScale } from '../../../hook/useComponentScale'; | ||
12 | + import { useSendCommand } from '../../../hook/useSendCommand'; | ||
13 | + import { unref } from 'vue'; | ||
14 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
15 | + | ||
16 | + const props = defineProps<{ | ||
17 | + config: ComponentPropsConfigType<typeof option>; | ||
18 | + }>(); | ||
19 | + | ||
20 | + const checked = ref(false); | ||
21 | + | ||
22 | + const svgList = ref<any>([ | ||
23 | + { | ||
24 | + value: 26.2, | ||
25 | + name: 'wendu', | ||
26 | + icon: 'zongfushe', | ||
27 | + unit: 'kw', | ||
28 | + iconColor: '#367BFF', | ||
29 | + fontColor: '#357CFB', | ||
30 | + checked: false, | ||
31 | + id: 0, | ||
32 | + }, | ||
33 | + { | ||
34 | + value: 53.7, | ||
35 | + name: 'shidu', | ||
36 | + icon: 'guangzhaoqiangdu', | ||
37 | + unit: '℃', | ||
38 | + iconColor: '#FFA000', | ||
39 | + fontColor: '#FFA000', | ||
40 | + checked: true, | ||
41 | + id: 1, | ||
42 | + }, | ||
43 | + ]); | ||
44 | + | ||
45 | + const getDesign = computed(() => { | ||
46 | + const { persetOption = {}, option } = props.config; | ||
47 | + const { dataSource = [] } = option || {}; | ||
48 | + const { | ||
49 | + unit: persetUnit, | ||
50 | + fontColor: persetFontColor, | ||
51 | + icon: persetIcon, | ||
52 | + iconColor: persetIconColor, | ||
53 | + } = persetOption || {}; | ||
54 | + return { | ||
55 | + dataSource: dataSource.map((item) => { | ||
56 | + const { fontColor, icon, iconColor, unit } = item.componentInfo; | ||
57 | + const { attribute, attributeRename } = item; | ||
58 | + return { | ||
59 | + unit: unit ?? persetUnit, | ||
60 | + fontColor: fontColor ?? persetFontColor, | ||
61 | + icon: icon ?? persetIcon, | ||
62 | + iconColor: iconColor ?? persetIconColor, | ||
63 | + attribute: attribute || attributeRename, | ||
64 | + attributeRename, | ||
65 | + }; | ||
66 | + }), | ||
67 | + }; | ||
68 | + }); | ||
69 | + | ||
70 | + const { sendCommand, loading } = useSendCommand(); | ||
71 | + const handleChange = async (index: number) => { | ||
72 | + const flag = await sendCommand(props.config.option, unref(checked)); | ||
73 | + if (!flag) svgList[index].checked = !svgList[index].checked; | ||
74 | + }; | ||
75 | + | ||
76 | + const updateFn: MultipleDataFetchUpdateFn = (message) => { | ||
77 | + const { data = {} } = message; | ||
78 | + const { dataSource } = unref(getDesign); | ||
79 | + svgList.value.length = 0; | ||
80 | + svgList.value = dataSource.map((item) => { | ||
81 | + const { icon, iconColor, unit, fontColor, attribute } = item || {}; | ||
82 | + const [latest] = data[attribute] || []; | ||
83 | + const [_timespan, value] = latest || []; | ||
84 | + return { | ||
85 | + value: Number(value), | ||
86 | + name: attribute, | ||
87 | + icon, | ||
88 | + unit, | ||
89 | + iconColor, | ||
90 | + fontColor, | ||
91 | + }; | ||
92 | + }); | ||
93 | + }; | ||
94 | + | ||
95 | + useMultipleDataFetch(props, updateFn); | ||
96 | + const { getRatio } = useComponentScale(props); | ||
97 | +</script> | ||
98 | + | ||
99 | +<template> | ||
100 | + <main class="w-full h-full flex flex-col justify-evenly items-center"> | ||
101 | + <DeviceName :config="config" /> | ||
102 | + <div | ||
103 | + style="width: 86%" | ||
104 | + v-for="(item, index) in svgList" | ||
105 | + :key="item.id" | ||
106 | + class="flex justify-between items-center" | ||
107 | + > | ||
108 | + <div class="flex items-center"> | ||
109 | + <SvgIcon | ||
110 | + :name="item.icon!" | ||
111 | + prefix="iconfont" | ||
112 | + :size="getRatio ? 30 * getRatio : 30" | ||
113 | + :style="{ color: item.iconColor }" | ||
114 | + /> | ||
115 | + | ||
116 | + <div class="text-gray-500 text-lg truncate ml-6">{{ item.attribute || '温度' }}</div> | ||
117 | + </div> | ||
118 | + | ||
119 | + <Switch v-model:checked="item.checked" :loading="loading" @change="handleChange(index)" /> | ||
120 | + </div> | ||
121 | + </main> | ||
122 | +</template> |
1 | import { ControlComponentSlidingSwitchConfig } from './ControlComponentSlidingSwitch'; | 1 | import { ControlComponentSlidingSwitchConfig } from './ControlComponentSlidingSwitch'; |
2 | import { ControlComponentSwitchWithIconConfig } from './ControlComponentSwitchWithIcon'; | 2 | import { ControlComponentSwitchWithIconConfig } from './ControlComponentSwitchWithIcon'; |
3 | import { ControlComponentToggleSwitchConfig } from './ControlComponentToggleSwitch'; | 3 | import { ControlComponentToggleSwitchConfig } from './ControlComponentToggleSwitch'; |
4 | +import { LateralNumericalControlConfig } from './LateralNumericalControl'; | ||
5 | +// import { SwitchListConfig } from './SwitchList'; | ||
4 | 6 | ||
5 | export const ControlList = [ | 7 | export const ControlList = [ |
6 | ControlComponentSwitchWithIconConfig, | 8 | ControlComponentSwitchWithIconConfig, |
7 | ControlComponentSlidingSwitchConfig, | 9 | ControlComponentSlidingSwitchConfig, |
8 | ControlComponentToggleSwitchConfig, | 10 | ControlComponentToggleSwitchConfig, |
11 | + LateralNumericalControlConfig, | ||
12 | + // SwitchListConfig, | ||
9 | ]; | 13 | ]; |
@@ -53,7 +53,6 @@ | @@ -53,7 +53,6 @@ | ||
53 | [ComponentConfigFieldEnum.FONT_COLOR]: fontColor, | 53 | [ComponentConfigFieldEnum.FONT_COLOR]: fontColor, |
54 | [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: showDeviceName, | 54 | [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: showDeviceName, |
55 | }; | 55 | }; |
56 | - console.log(value, 'valie'); | ||
57 | return setFieldsValue(value); | 56 | return setFieldsValue(value); |
58 | }; | 57 | }; |
59 | 58 |
@@ -32,7 +32,6 @@ | @@ -32,7 +32,6 @@ | ||
32 | } = persetOption || {}; | 32 | } = persetOption || {}; |
33 | const { unit, fontColor, pointerColor, gradientInfo, progressBarCircle, instrumentPanelColor } = | 33 | const { unit, fontColor, pointerColor, gradientInfo, progressBarCircle, instrumentPanelColor } = |
34 | componentInfo || {}; | 34 | componentInfo || {}; |
35 | - console.log(option, 'unit'); | ||
36 | return { | 35 | return { |
37 | unit: unit ?? presetUnit, | 36 | unit: unit ?? presetUnit, |
38 | fontColor: fontColor ?? presetFontColor, | 37 | fontColor: fontColor ?? presetFontColor, |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { StatisticsComponent1Config } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '../../../index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '../../../publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '../../../enum'; | ||
11 | + | ||
12 | +export enum Gradient { | ||
13 | + FIRST = 'first', | ||
14 | + SECOND = 'second', | ||
15 | +} | ||
16 | +export enum GradientColor { | ||
17 | + FIRST = '#07ffd6', | ||
18 | + SECOND = '#5eff10', | ||
19 | +} | ||
20 | +export const option: PublicPresetOptions = { | ||
21 | + multipleDataSourceComponent: true, | ||
22 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#FD7347', | ||
23 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
24 | + [ComponentConfigFieldEnum.UNIT]: '℃', | ||
25 | +}; | ||
26 | + | ||
27 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
28 | + public key: string = StatisticsComponent1Config.key; | ||
29 | + | ||
30 | + public attr = { ...componentInitConfig }; | ||
31 | + | ||
32 | + public componentConfig: ConfigType = cloneDeep(StatisticsComponent1Config); | ||
33 | + | ||
34 | + public persetOption = cloneDeep(option); | ||
35 | + | ||
36 | + public option: PublicComponentOptions; | ||
37 | + | ||
38 | + constructor(option: PublicComponentOptions) { | ||
39 | + super(); | ||
40 | + this.option = { ...option }; | ||
41 | + } | ||
42 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '../../../enum'; | ||
3 | + import { option } from './config'; | ||
4 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
5 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
6 | + import { ComponentInfo } from '/@/views/visual/palette/types'; | ||
7 | + | ||
8 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
9 | + schemas: [ | ||
10 | + { | ||
11 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
12 | + label: '数值字体颜色', | ||
13 | + component: 'ColorPicker', | ||
14 | + changeEvent: 'update:value', | ||
15 | + defaultValue: option.fontColor, | ||
16 | + }, | ||
17 | + { | ||
18 | + field: ComponentConfigFieldEnum.UNIT, | ||
19 | + label: '数值单位', | ||
20 | + component: 'Input', | ||
21 | + defaultValue: option.unit, | ||
22 | + }, | ||
23 | + { | ||
24 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
25 | + label: '显示设备名称', | ||
26 | + component: 'Checkbox', | ||
27 | + defaultValue: option.showDeviceName, | ||
28 | + }, | ||
29 | + ], | ||
30 | + showActionButtonGroup: false, | ||
31 | + labelWidth: 120, | ||
32 | + baseColProps: { | ||
33 | + span: 12, | ||
34 | + }, | ||
35 | + }); | ||
36 | + | ||
37 | + const getFormValues = () => { | ||
38 | + // return getFieldsValue(); | ||
39 | + const item = getFieldsValue(); | ||
40 | + return { | ||
41 | + fontColor: item[ComponentConfigFieldEnum.FONT_COLOR], | ||
42 | + unit: item[ComponentConfigFieldEnum.UNIT], | ||
43 | + showDeviceName: item[ComponentConfigFieldEnum.SHOW_DEVICE_NAME], | ||
44 | + } as ComponentInfo; | ||
45 | + }; | ||
46 | + | ||
47 | + const setFormValues = (data: Recordable) => { | ||
48 | + // return setFieldsValue(data); | ||
49 | + const { unit, fontColor, showDeviceName } = data; | ||
50 | + | ||
51 | + const value = { | ||
52 | + [ComponentConfigFieldEnum.UNIT]: unit, | ||
53 | + [ComponentConfigFieldEnum.FONT_COLOR]: fontColor, | ||
54 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: showDeviceName, | ||
55 | + }; | ||
56 | + return setFieldsValue(value); | ||
57 | + }; | ||
58 | + | ||
59 | + defineExpose({ | ||
60 | + getFormValues, | ||
61 | + setFormValues, | ||
62 | + resetFormValues: resetFields, | ||
63 | + } as PublicFormInstaceType); | ||
64 | +</script> | ||
65 | + | ||
66 | +<template> | ||
67 | + <BasicForm @register="register" /> | ||
68 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { CreateComponentType } from '../../../index.type'; | ||
4 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
5 | + import { | ||
6 | + PublicComponentValueType, | ||
7 | + PublicFormInstaceType, | ||
8 | + } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
9 | + | ||
10 | + defineProps<{ | ||
11 | + values: PublicComponentValueType; | ||
12 | + componentConfig: CreateComponentType; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
16 | + labelWidth: 0, | ||
17 | + showActionButtonGroup: false, | ||
18 | + layout: 'horizontal', | ||
19 | + labelCol: { span: 0 }, | ||
20 | + schemas: commonDataSourceSchemas(), | ||
21 | + }); | ||
22 | + | ||
23 | + const getFormValues = () => { | ||
24 | + return getFieldsValue(); | ||
25 | + }; | ||
26 | + | ||
27 | + const setFormValues = (record: Recordable) => { | ||
28 | + return setFieldsValue(record); | ||
29 | + }; | ||
30 | + | ||
31 | + defineExpose({ | ||
32 | + getFormValues, | ||
33 | + setFormValues, | ||
34 | + validate, | ||
35 | + resetFormValues: resetFields, | ||
36 | + } as PublicFormInstaceType); | ||
37 | +</script> | ||
38 | + | ||
39 | +<template> | ||
40 | + <BasicForm @register="register" /> | ||
41 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('StatisticsComponent1'); | ||
5 | + | ||
6 | +export const StatisticsComponent1Config: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + title: '饼图', | ||
9 | + package: PackagesCategoryEnum.STATISTICS, | ||
10 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { EChartsOption, SeriesOption, ECharts, init } from 'echarts'; | ||
3 | + import { unref, ref, onMounted, computed, nextTick } from 'vue'; | ||
4 | + import { useMultipleDataFetch } from '../../../hook/useSocket'; | ||
5 | + import { ComponentPropsConfigType, MultipleDataFetchUpdateFn } from '../../../index.type'; | ||
6 | + import { option } from './config'; | ||
7 | + import { UpdateTime } from '/@/views/visual/commonComponents/UpdateTime'; | ||
8 | + import { useComponentScale } from '../../../hook/useComponentScale'; | ||
9 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
10 | + | ||
11 | + const props = defineProps<{ | ||
12 | + config: ComponentPropsConfigType<typeof option>; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const chartRefEl = ref<Nullable<HTMLDivElement>>(null); | ||
16 | + | ||
17 | + const chartInstance = ref<Nullable<ECharts>>(null); | ||
18 | + | ||
19 | + const time = ref<Nullable<number>>(null); | ||
20 | + | ||
21 | + const getDesign = computed(() => { | ||
22 | + const { persetOption, option } = props.config; | ||
23 | + const { dataSource = [] } = option || {}; | ||
24 | + const { unit: presetUnit, fontColor: presetFontColor } = persetOption || {}; | ||
25 | + return { | ||
26 | + dataSource: dataSource?.map((item) => { | ||
27 | + const { unit, fontColor } = item.componentInfo || {}; | ||
28 | + const { attribute, attributeRename } = item; | ||
29 | + return { | ||
30 | + unit: unit ?? presetUnit, | ||
31 | + fontColor: fontColor ?? presetFontColor, | ||
32 | + attribute, | ||
33 | + attributeRename, | ||
34 | + }; | ||
35 | + }), | ||
36 | + }; | ||
37 | + }); | ||
38 | + | ||
39 | + const options = (): EChartsOption => { | ||
40 | + // getStageColor(gradientInfo); | ||
41 | + return { | ||
42 | + tooltip: { | ||
43 | + trigger: 'item', | ||
44 | + }, | ||
45 | + legend: { | ||
46 | + top: '5%', | ||
47 | + left: 'center', | ||
48 | + textStyle: { | ||
49 | + fontSize: unref(getRatio) ? 14 * unref(getRatio) : 14, | ||
50 | + }, | ||
51 | + }, | ||
52 | + series: [ | ||
53 | + { | ||
54 | + name: '', | ||
55 | + type: 'pie', | ||
56 | + radius: ['%', '70%'], | ||
57 | + center: ['50%', '65%'], | ||
58 | + avoidLabelOverlap: false, | ||
59 | + itemStyle: { | ||
60 | + borderRadius: 4, | ||
61 | + borderColor: '#fff', | ||
62 | + borderWidth: 2, | ||
63 | + }, | ||
64 | + label: { | ||
65 | + show: false, | ||
66 | + position: 'center', | ||
67 | + }, | ||
68 | + labelLine: { | ||
69 | + show: false, | ||
70 | + }, | ||
71 | + data: [ | ||
72 | + { value: 1048, name: '数据1' }, | ||
73 | + { value: 735, name: '数据2' }, | ||
74 | + { value: 580, name: '数据3' }, | ||
75 | + ], | ||
76 | + }, | ||
77 | + ], | ||
78 | + }; | ||
79 | + }; | ||
80 | + | ||
81 | + const initial = () => { | ||
82 | + chartInstance.value = init(unref(chartRefEl)! as HTMLElement); | ||
83 | + chartInstance.value.setOption(options()); | ||
84 | + }; | ||
85 | + | ||
86 | + // const randomFn = () => { | ||
87 | + // useIntervalFn(() => { | ||
88 | + // const value = (Math.random() * 100).toFixed(0); | ||
89 | + // unref(chartInstance)?.setOption({ | ||
90 | + // series: [{ data: [{ value }] }, { data: [{ value }] }], | ||
91 | + // } as EChartsOption); | ||
92 | + // }, 3000); | ||
93 | + // }; | ||
94 | + | ||
95 | + const updateChart = (data: SeriesOption['data']) => { | ||
96 | + unref(chartInstance)?.setOption({ | ||
97 | + series: [{ data }], | ||
98 | + // color: unref(list).map((item) => item.title.color), | ||
99 | + } as EChartsOption); | ||
100 | + }; | ||
101 | + | ||
102 | + const updateFn: MultipleDataFetchUpdateFn = (message) => { | ||
103 | + const { data = {} } = message; | ||
104 | + const { dataSource } = unref(getDesign); | ||
105 | + const series = dataSource.map((item) => { | ||
106 | + const { attribute, attributeRename, fontColor, unit } = item; | ||
107 | + const [latest] = data[attribute] || []; | ||
108 | + const [_timespan, value] = latest || []; | ||
109 | + | ||
110 | + return { | ||
111 | + value, | ||
112 | + name: attributeRename ?? attribute, | ||
113 | + itemStyle: { color: fontColor }, | ||
114 | + tooltip: { | ||
115 | + valueFormatter(value) { | ||
116 | + return `${value} ${unit ?? ''}`; | ||
117 | + }, | ||
118 | + }, | ||
119 | + } as SeriesOption['data']; | ||
120 | + }); | ||
121 | + updateChart(series); | ||
122 | + }; | ||
123 | + | ||
124 | + useMultipleDataFetch(props, updateFn); | ||
125 | + | ||
126 | + onMounted(() => { | ||
127 | + initial(); | ||
128 | + // !props.config.option.uuid && randomFn(); | ||
129 | + !props.config.option.uuid; | ||
130 | + }); | ||
131 | + | ||
132 | + const resize = async () => { | ||
133 | + await nextTick(); | ||
134 | + | ||
135 | + // 修改echarts大小 | ||
136 | + unref(chartInstance)?.setOption({ | ||
137 | + legend: { | ||
138 | + textStyle: { | ||
139 | + fontSize: 14 * unref(getRatio), | ||
140 | + }, | ||
141 | + }, | ||
142 | + } as EChartsOption); | ||
143 | + unref(chartInstance)?.resize(); | ||
144 | + }; | ||
145 | + | ||
146 | + const { getRatio } = useComponentScale(props, resize); | ||
147 | +</script> | ||
148 | + | ||
149 | +<template> | ||
150 | + <main class="w-full h-full flex flex-col justify-center items-center"> | ||
151 | + <DeviceName :config="config" /> | ||
152 | + <div ref="chartRefEl" class="flex-1 w-full h-full"> </div> | ||
153 | + <UpdateTime :time="time" /> | ||
154 | + </main> | ||
155 | +</template> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { StatisticsComponent2Config } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '../../../index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '../../../publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '../../../enum'; | ||
11 | + | ||
12 | +export enum Gradient { | ||
13 | + FIRST = 'first', | ||
14 | + SECOND = 'second', | ||
15 | +} | ||
16 | +export enum GradientColor { | ||
17 | + FIRST = '#07ffd6', | ||
18 | + SECOND = '#5eff10', | ||
19 | +} | ||
20 | +export const option: PublicPresetOptions = { | ||
21 | + multipleDataSourceComponent: true, | ||
22 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#FD7347', | ||
23 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
24 | + [ComponentConfigFieldEnum.UNIT]: '℃', | ||
25 | +}; | ||
26 | + | ||
27 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
28 | + public key: string = StatisticsComponent2Config.key; | ||
29 | + | ||
30 | + public attr = { ...componentInitConfig }; | ||
31 | + | ||
32 | + public componentConfig: ConfigType = cloneDeep(StatisticsComponent2Config); | ||
33 | + | ||
34 | + public persetOption = cloneDeep(option); | ||
35 | + | ||
36 | + public option: PublicComponentOptions; | ||
37 | + | ||
38 | + constructor(option: PublicComponentOptions) { | ||
39 | + super(); | ||
40 | + this.option = { ...option }; | ||
41 | + } | ||
42 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '../../../enum'; | ||
3 | + import { option } from './config'; | ||
4 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
5 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
6 | + import { ComponentInfo } from '/@/views/visual/palette/types'; | ||
7 | + | ||
8 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
9 | + schemas: [ | ||
10 | + { | ||
11 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
12 | + label: '数值字体颜色', | ||
13 | + component: 'ColorPicker', | ||
14 | + changeEvent: 'update:value', | ||
15 | + defaultValue: option.fontColor, | ||
16 | + }, | ||
17 | + { | ||
18 | + field: ComponentConfigFieldEnum.UNIT, | ||
19 | + label: '数值单位', | ||
20 | + component: 'Input', | ||
21 | + defaultValue: option.unit, | ||
22 | + }, | ||
23 | + { | ||
24 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
25 | + label: '显示设备名称', | ||
26 | + component: 'Checkbox', | ||
27 | + defaultValue: option.showDeviceName, | ||
28 | + }, | ||
29 | + ], | ||
30 | + showActionButtonGroup: false, | ||
31 | + labelWidth: 120, | ||
32 | + baseColProps: { | ||
33 | + span: 12, | ||
34 | + }, | ||
35 | + }); | ||
36 | + | ||
37 | + const getFormValues = () => { | ||
38 | + // return getFieldsValue(); | ||
39 | + const item = getFieldsValue(); | ||
40 | + return { | ||
41 | + fontColor: item[ComponentConfigFieldEnum.FONT_COLOR], | ||
42 | + unit: item[ComponentConfigFieldEnum.UNIT], | ||
43 | + showDeviceName: item[ComponentConfigFieldEnum.SHOW_DEVICE_NAME], | ||
44 | + } as ComponentInfo; | ||
45 | + }; | ||
46 | + | ||
47 | + const setFormValues = (data: Recordable) => { | ||
48 | + // return setFieldsValue(data); | ||
49 | + const { unit, fontColor, showDeviceName } = data; | ||
50 | + | ||
51 | + const value = { | ||
52 | + [ComponentConfigFieldEnum.UNIT]: unit, | ||
53 | + [ComponentConfigFieldEnum.FONT_COLOR]: fontColor, | ||
54 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: showDeviceName, | ||
55 | + }; | ||
56 | + return setFieldsValue(value); | ||
57 | + }; | ||
58 | + | ||
59 | + defineExpose({ | ||
60 | + getFormValues, | ||
61 | + setFormValues, | ||
62 | + resetFormValues: resetFields, | ||
63 | + } as PublicFormInstaceType); | ||
64 | +</script> | ||
65 | + | ||
66 | +<template> | ||
67 | + <BasicForm @register="register" /> | ||
68 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { CreateComponentType } from '../../../index.type'; | ||
4 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
5 | + import { | ||
6 | + PublicComponentValueType, | ||
7 | + PublicFormInstaceType, | ||
8 | + } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
9 | + | ||
10 | + defineProps<{ | ||
11 | + values: PublicComponentValueType; | ||
12 | + componentConfig: CreateComponentType; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
16 | + labelWidth: 0, | ||
17 | + showActionButtonGroup: false, | ||
18 | + layout: 'horizontal', | ||
19 | + labelCol: { span: 0 }, | ||
20 | + schemas: commonDataSourceSchemas(), | ||
21 | + }); | ||
22 | + | ||
23 | + const getFormValues = () => { | ||
24 | + return getFieldsValue(); | ||
25 | + }; | ||
26 | + | ||
27 | + const setFormValues = (record: Recordable) => { | ||
28 | + return setFieldsValue(record); | ||
29 | + }; | ||
30 | + | ||
31 | + defineExpose({ | ||
32 | + getFormValues, | ||
33 | + setFormValues, | ||
34 | + validate, | ||
35 | + resetFormValues: resetFields, | ||
36 | + } as PublicFormInstaceType); | ||
37 | +</script> | ||
38 | + | ||
39 | +<template> | ||
40 | + <BasicForm @register="register" /> | ||
41 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('StatisticsComponent2'); | ||
5 | + | ||
6 | +export const StatisticsComponent2Config: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + title: '半环形图', | ||
9 | + package: PackagesCategoryEnum.STATISTICS, | ||
10 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { EChartsOption, SeriesOption, ECharts, init } from 'echarts'; | ||
3 | + import { unref, ref, onMounted, computed, nextTick } from 'vue'; | ||
4 | + import { useMultipleDataFetch } from '../../../hook/useSocket'; | ||
5 | + import { ComponentPropsConfigType, MultipleDataFetchUpdateFn } from '../../../index.type'; | ||
6 | + import { option } from './config'; | ||
7 | + import { UpdateTime } from '/@/views/visual/commonComponents/UpdateTime'; | ||
8 | + import { useComponentScale } from '../../../hook/useComponentScale'; | ||
9 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
10 | + | ||
11 | + const props = defineProps<{ | ||
12 | + config: ComponentPropsConfigType<typeof option>; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const chartRefEl = ref<Nullable<HTMLDivElement>>(null); | ||
16 | + | ||
17 | + const chartInstance = ref<Nullable<ECharts>>(null); | ||
18 | + | ||
19 | + const time = ref<Nullable<number>>(null); | ||
20 | + | ||
21 | + const getDesign = computed(() => { | ||
22 | + const { persetOption, option } = props.config; | ||
23 | + const { dataSource = [] } = option || {}; | ||
24 | + const { unit: presetUnit, fontColor: presetFontColor } = persetOption || {}; | ||
25 | + return { | ||
26 | + dataSource: dataSource?.map((item) => { | ||
27 | + const { unit, fontColor } = item.componentInfo || {}; | ||
28 | + const { attribute, attributeRename } = item; | ||
29 | + return { | ||
30 | + unit: unit ?? presetUnit, | ||
31 | + fontColor: fontColor ?? presetFontColor, | ||
32 | + attribute, | ||
33 | + attributeRename, | ||
34 | + }; | ||
35 | + }), | ||
36 | + }; | ||
37 | + }); | ||
38 | + | ||
39 | + const options = (): EChartsOption => { | ||
40 | + // getStageColor(gradientInfo); | ||
41 | + return { | ||
42 | + tooltip: { | ||
43 | + trigger: 'item', | ||
44 | + }, | ||
45 | + legend: { | ||
46 | + top: '5%', | ||
47 | + left: 'center', | ||
48 | + selectedMode: false, | ||
49 | + textStyle: { | ||
50 | + fontSize: unref(getRatio) ? 14 * unref(getRatio) : 14, | ||
51 | + }, | ||
52 | + }, | ||
53 | + series: [ | ||
54 | + { | ||
55 | + type: 'pie', | ||
56 | + radius: ['40%', '70%'], | ||
57 | + center: ['50%', '70%'], | ||
58 | + // adjust the start angle | ||
59 | + startAngle: 180, | ||
60 | + label: { | ||
61 | + show: false, | ||
62 | + }, | ||
63 | + itemStyle: { | ||
64 | + borderRadius: 4, | ||
65 | + borderColor: '#fff', | ||
66 | + borderWidth: 2, | ||
67 | + }, | ||
68 | + data: [ | ||
69 | + { value: 1048, name: '数据1' }, | ||
70 | + { value: 735, name: '数据2' }, | ||
71 | + { | ||
72 | + value: 1048 + 735, | ||
73 | + itemStyle: { | ||
74 | + color: 'none', | ||
75 | + decal: { | ||
76 | + symbol: 'none', | ||
77 | + }, | ||
78 | + }, | ||
79 | + label: { | ||
80 | + show: false, | ||
81 | + }, | ||
82 | + }, | ||
83 | + ], | ||
84 | + }, | ||
85 | + ], | ||
86 | + }; | ||
87 | + }; | ||
88 | + | ||
89 | + const initial = () => { | ||
90 | + chartInstance.value = init(unref(chartRefEl)! as HTMLElement); | ||
91 | + chartInstance.value.setOption(options()); | ||
92 | + }; | ||
93 | + | ||
94 | + // const randomFn = () => { | ||
95 | + // useIntervalFn(() => { | ||
96 | + // const value = (Math.random() * 100).toFixed(0); | ||
97 | + // unref(chartInstance)?.setOption({ | ||
98 | + // series: [{ data: [{ value }] }, { data: [{ value }] }], | ||
99 | + // } as EChartsOption); | ||
100 | + // }, 3000); | ||
101 | + // }; | ||
102 | + | ||
103 | + const updateChart = (data: SeriesOption['data']) => { | ||
104 | + unref(chartInstance)?.setOption({ | ||
105 | + series: [{ data }], | ||
106 | + // color: unref(list).map((item) => item.title.color), | ||
107 | + } as EChartsOption); | ||
108 | + }; | ||
109 | + | ||
110 | + const updateFn: MultipleDataFetchUpdateFn = (message) => { | ||
111 | + const { data = {} } = message; | ||
112 | + const { dataSource } = unref(getDesign); | ||
113 | + const series = dataSource.map((item) => { | ||
114 | + const { attribute, attributeRename, fontColor, unit } = item; | ||
115 | + const [latest] = data[attribute] || []; | ||
116 | + const [_timespan, value] = latest || []; | ||
117 | + | ||
118 | + return { | ||
119 | + value, | ||
120 | + name: attributeRename ?? attribute, | ||
121 | + itemStyle: { color: fontColor }, | ||
122 | + tooltip: { | ||
123 | + valueFormatter(value) { | ||
124 | + return `${value} ${unit ?? ''}`; | ||
125 | + }, | ||
126 | + }, | ||
127 | + } as SeriesOption['data']; | ||
128 | + }); | ||
129 | + // if (series.length > 1) { | ||
130 | + series.push({ | ||
131 | + value: series.reduce((total: number, current: any) => total + Number(current.value), 0), | ||
132 | + itemStyle: { | ||
133 | + color: 'none', | ||
134 | + decal: { | ||
135 | + symbol: 'none', | ||
136 | + }, | ||
137 | + }, | ||
138 | + label: { | ||
139 | + show: false, | ||
140 | + }, | ||
141 | + }); | ||
142 | + // } | ||
143 | + // console.log(message, 'message', series, 'series', sum); | ||
144 | + updateChart(series); | ||
145 | + }; | ||
146 | + | ||
147 | + useMultipleDataFetch(props, updateFn); | ||
148 | + | ||
149 | + onMounted(() => { | ||
150 | + initial(); | ||
151 | + // !props.config.option.uuid && randomFn(); | ||
152 | + !props.config.option.uuid; | ||
153 | + }); | ||
154 | + | ||
155 | + const resize = async () => { | ||
156 | + await nextTick(); | ||
157 | + | ||
158 | + // 修改echarts大小 | ||
159 | + unref(chartInstance)?.setOption({ | ||
160 | + legend: { | ||
161 | + textStyle: { | ||
162 | + fontSize: 14 * unref(getRatio), | ||
163 | + }, | ||
164 | + }, | ||
165 | + } as EChartsOption); | ||
166 | + unref(chartInstance)?.resize(); | ||
167 | + }; | ||
168 | + | ||
169 | + const { getRatio } = useComponentScale(props, resize); | ||
170 | +</script> | ||
171 | + | ||
172 | +<template> | ||
173 | + <main class="w-full h-full flex flex-col justify-center items-center"> | ||
174 | + <DeviceName :config="config" /> | ||
175 | + <div ref="chartRefEl" class="flex-1 w-full h-full"> </div> | ||
176 | + <UpdateTime :time="time" /> | ||
177 | + </main> | ||
178 | +</template> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { StatisticsComponent3Config } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '../../../index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '../../../publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '../../../enum'; | ||
11 | + | ||
12 | +export enum Gradient { | ||
13 | + FIRST = 'first', | ||
14 | + SECOND = 'second', | ||
15 | +} | ||
16 | +export enum GradientColor { | ||
17 | + FIRST = '#07ffd6', | ||
18 | + SECOND = '#5eff10', | ||
19 | +} | ||
20 | +export const option: PublicPresetOptions = { | ||
21 | + multipleDataSourceComponent: true, | ||
22 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#FD7347', | ||
23 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
24 | + [ComponentConfigFieldEnum.UNIT]: '℃', | ||
25 | +}; | ||
26 | + | ||
27 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
28 | + public key: string = StatisticsComponent3Config.key; | ||
29 | + | ||
30 | + public attr = { ...componentInitConfig }; | ||
31 | + | ||
32 | + public componentConfig: ConfigType = cloneDeep(StatisticsComponent3Config); | ||
33 | + | ||
34 | + public persetOption = cloneDeep(option); | ||
35 | + | ||
36 | + public option: PublicComponentOptions; | ||
37 | + | ||
38 | + constructor(option: PublicComponentOptions) { | ||
39 | + super(); | ||
40 | + this.option = { ...option }; | ||
41 | + } | ||
42 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '../../../enum'; | ||
3 | + import { option } from './config'; | ||
4 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
5 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
6 | + import { ComponentInfo } from '/@/views/visual/palette/types'; | ||
7 | + | ||
8 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
9 | + schemas: [ | ||
10 | + { | ||
11 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
12 | + label: '数值字体颜色', | ||
13 | + component: 'ColorPicker', | ||
14 | + changeEvent: 'update:value', | ||
15 | + defaultValue: option.fontColor, | ||
16 | + }, | ||
17 | + { | ||
18 | + field: ComponentConfigFieldEnum.UNIT, | ||
19 | + label: '数值单位', | ||
20 | + component: 'Input', | ||
21 | + defaultValue: option.unit, | ||
22 | + }, | ||
23 | + { | ||
24 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
25 | + label: '显示设备名称', | ||
26 | + component: 'Checkbox', | ||
27 | + defaultValue: option.showDeviceName, | ||
28 | + }, | ||
29 | + ], | ||
30 | + showActionButtonGroup: false, | ||
31 | + labelWidth: 120, | ||
32 | + baseColProps: { | ||
33 | + span: 12, | ||
34 | + }, | ||
35 | + }); | ||
36 | + | ||
37 | + const getFormValues = () => { | ||
38 | + // return getFieldsValue(); | ||
39 | + const item = getFieldsValue(); | ||
40 | + return { | ||
41 | + fontColor: item[ComponentConfigFieldEnum.FONT_COLOR], | ||
42 | + unit: item[ComponentConfigFieldEnum.UNIT], | ||
43 | + showDeviceName: item[ComponentConfigFieldEnum.SHOW_DEVICE_NAME], | ||
44 | + } as ComponentInfo; | ||
45 | + }; | ||
46 | + | ||
47 | + const setFormValues = (data: Recordable) => { | ||
48 | + // return setFieldsValue(data); | ||
49 | + const { unit, fontColor, showDeviceName } = data; | ||
50 | + | ||
51 | + const value = { | ||
52 | + [ComponentConfigFieldEnum.UNIT]: unit, | ||
53 | + [ComponentConfigFieldEnum.FONT_COLOR]: fontColor, | ||
54 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: showDeviceName, | ||
55 | + }; | ||
56 | + return setFieldsValue(value); | ||
57 | + }; | ||
58 | + | ||
59 | + defineExpose({ | ||
60 | + getFormValues, | ||
61 | + setFormValues, | ||
62 | + resetFormValues: resetFields, | ||
63 | + } as PublicFormInstaceType); | ||
64 | +</script> | ||
65 | + | ||
66 | +<template> | ||
67 | + <BasicForm @register="register" /> | ||
68 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { CreateComponentType } from '../../../index.type'; | ||
4 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
5 | + import { | ||
6 | + PublicComponentValueType, | ||
7 | + PublicFormInstaceType, | ||
8 | + } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
9 | + | ||
10 | + defineProps<{ | ||
11 | + values: PublicComponentValueType; | ||
12 | + componentConfig: CreateComponentType; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
16 | + labelWidth: 0, | ||
17 | + showActionButtonGroup: false, | ||
18 | + layout: 'horizontal', | ||
19 | + labelCol: { span: 0 }, | ||
20 | + schemas: commonDataSourceSchemas(), | ||
21 | + }); | ||
22 | + | ||
23 | + const getFormValues = () => { | ||
24 | + return getFieldsValue(); | ||
25 | + }; | ||
26 | + | ||
27 | + const setFormValues = (record: Recordable) => { | ||
28 | + return setFieldsValue(record); | ||
29 | + }; | ||
30 | + | ||
31 | + defineExpose({ | ||
32 | + getFormValues, | ||
33 | + setFormValues, | ||
34 | + validate, | ||
35 | + resetFormValues: resetFields, | ||
36 | + } as PublicFormInstaceType); | ||
37 | +</script> | ||
38 | + | ||
39 | +<template> | ||
40 | + <BasicForm @register="register" /> | ||
41 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('StatisticsComponent3'); | ||
5 | + | ||
6 | +export const StatisticsComponent3Config: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + title: '横柱状图', | ||
9 | + package: PackagesCategoryEnum.STATISTICS, | ||
10 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { EChartsOption, SeriesOption, ECharts, init } from 'echarts'; | ||
3 | + import { unref, ref, onMounted, computed, nextTick } from 'vue'; | ||
4 | + import { useMultipleDataFetch } from '../../../hook/useSocket'; | ||
5 | + import { ComponentPropsConfigType, MultipleDataFetchUpdateFn } from '../../../index.type'; | ||
6 | + import { option } from './config'; | ||
7 | + import { UpdateTime } from '/@/views/visual/commonComponents/UpdateTime'; | ||
8 | + import { useComponentScale } from '../../../hook/useComponentScale'; | ||
9 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
10 | + | ||
11 | + const props = defineProps<{ | ||
12 | + config: ComponentPropsConfigType<typeof option>; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const chartRefEl = ref<Nullable<HTMLDivElement>>(null); | ||
16 | + | ||
17 | + const chartInstance = ref<Nullable<ECharts>>(null); | ||
18 | + | ||
19 | + const time = ref<Nullable<number>>(null); | ||
20 | + | ||
21 | + const getDesign = computed(() => { | ||
22 | + const { persetOption, option } = props.config; | ||
23 | + const { dataSource = [] } = option || {}; | ||
24 | + const { unit: presetUnit, fontColor: presetFontColor } = persetOption || {}; | ||
25 | + return { | ||
26 | + dataSource: dataSource?.map((item) => { | ||
27 | + const { unit, fontColor } = item.componentInfo || {}; | ||
28 | + const { attribute, attributeRename } = item; | ||
29 | + return { | ||
30 | + unit: unit ?? presetUnit, | ||
31 | + fontColor: fontColor ?? presetFontColor, | ||
32 | + attribute, | ||
33 | + attributeRename, | ||
34 | + }; | ||
35 | + }), | ||
36 | + }; | ||
37 | + }); | ||
38 | + const seriesList = [ | ||
39 | + { value: 120, name: '123', itemStyle: { color: '#02E5F0' } }, | ||
40 | + { value: 150, name: '456', itemStyle: { color: '#028CF0' } }, | ||
41 | + { value: 40, name: '789', itemStyle: { color: '#F09202' } }, | ||
42 | + ]; | ||
43 | + const data = ['温度', '湿度', '温度1']; | ||
44 | + const options = (): EChartsOption => { | ||
45 | + // getStageColor(gradientInfo); | ||
46 | + return { | ||
47 | + color: ['#3398DB'], | ||
48 | + tooltip: { | ||
49 | + // 提示框 | ||
50 | + trigger: 'axis', | ||
51 | + axisPointer: { | ||
52 | + type: 'shadow', | ||
53 | + }, | ||
54 | + }, | ||
55 | + xAxis: { | ||
56 | + type: 'category', | ||
57 | + data: data, | ||
58 | + axisTick: { | ||
59 | + alignWithLabel: true, | ||
60 | + }, | ||
61 | + axisPointer: { | ||
62 | + type: 'line', | ||
63 | + }, | ||
64 | + }, | ||
65 | + grid: { | ||
66 | + top: '15%', | ||
67 | + left: '20%', | ||
68 | + bottom: '15%', | ||
69 | + }, | ||
70 | + yAxis: { | ||
71 | + type: 'value', | ||
72 | + }, | ||
73 | + series: [ | ||
74 | + { | ||
75 | + name: '', | ||
76 | + type: 'bar', | ||
77 | + barWidth: '60%', | ||
78 | + data: seriesList, | ||
79 | + }, | ||
80 | + ], | ||
81 | + }; | ||
82 | + }; | ||
83 | + | ||
84 | + const initial = () => { | ||
85 | + chartInstance.value = init(unref(chartRefEl)! as HTMLElement); | ||
86 | + chartInstance.value.setOption(options()); | ||
87 | + }; | ||
88 | + | ||
89 | + // const randomFn = () => { | ||
90 | + // useIntervalFn(() => { | ||
91 | + // const value = (Math.random() * 100).toFixed(0); | ||
92 | + // unref(chartInstance)?.setOption({ | ||
93 | + // series: [{ data: [{ value }] }, { data: [{ value }] }], | ||
94 | + // } as EChartsOption); | ||
95 | + // }, 3000); | ||
96 | + // }; | ||
97 | + | ||
98 | + const updateChart = (data: SeriesOption['data'], xAxisData) => { | ||
99 | + unref(chartInstance)?.setOption({ | ||
100 | + series: [{ data }], | ||
101 | + xAxis: { data: xAxisData }, | ||
102 | + // color: unref(list).map((item) => item.title.color), | ||
103 | + } as EChartsOption); | ||
104 | + }; | ||
105 | + | ||
106 | + const updateFn: MultipleDataFetchUpdateFn = (message) => { | ||
107 | + const { data = {} } = message; | ||
108 | + const { dataSource } = unref(getDesign); | ||
109 | + const series = dataSource.map((item) => { | ||
110 | + const { attribute, attributeRename, fontColor, unit } = item; | ||
111 | + const [latest] = data[attribute] || []; | ||
112 | + const [_timespan, value] = latest || []; | ||
113 | + | ||
114 | + return { | ||
115 | + value, | ||
116 | + name: attributeRename ?? attribute, | ||
117 | + itemStyle: { color: fontColor }, | ||
118 | + tooltip: { | ||
119 | + valueFormatter(value) { | ||
120 | + return `${value} ${unit ?? ''}`; | ||
121 | + }, | ||
122 | + }, | ||
123 | + } as SeriesOption['data']; | ||
124 | + }); | ||
125 | + const xAxisData = series.map((item) => { | ||
126 | + const { name } = item as any; | ||
127 | + return name; | ||
128 | + }); | ||
129 | + // } | ||
130 | + // console.log(message, 'message', series, 'series', sum); | ||
131 | + updateChart(series, xAxisData); | ||
132 | + }; | ||
133 | + | ||
134 | + useMultipleDataFetch(props, updateFn); | ||
135 | + | ||
136 | + onMounted(() => { | ||
137 | + initial(); | ||
138 | + // !props.config.option.uuid && randomFn(); | ||
139 | + !props.config.option.uuid; | ||
140 | + }); | ||
141 | + | ||
142 | + const resize = async () => { | ||
143 | + await nextTick(); | ||
144 | + | ||
145 | + // 修改echarts大小 | ||
146 | + unref(chartInstance)?.setOption({ | ||
147 | + legend: { | ||
148 | + textStyle: { | ||
149 | + fontSize: 14 * unref(getRatio), | ||
150 | + }, | ||
151 | + }, | ||
152 | + } as EChartsOption); | ||
153 | + unref(chartInstance)?.resize(); | ||
154 | + }; | ||
155 | + | ||
156 | + const { getRatio } = useComponentScale(props, resize); | ||
157 | +</script> | ||
158 | + | ||
159 | +<template> | ||
160 | + <main class="w-full h-full flex flex-col justify-center items-center"> | ||
161 | + <DeviceName :config="config" /> | ||
162 | + <div ref="chartRefEl" class="flex-1 w-full h-full"> </div> | ||
163 | + <UpdateTime :time="time" /> | ||
164 | + </main> | ||
165 | +</template> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { StatisticsComponent4Config } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '../../../index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '../../../publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '../../../enum'; | ||
11 | + | ||
12 | +export enum Gradient { | ||
13 | + FIRST = 'first', | ||
14 | + SECOND = 'second', | ||
15 | +} | ||
16 | +export enum GradientColor { | ||
17 | + FIRST = '#07ffd6', | ||
18 | + SECOND = '#5eff10', | ||
19 | +} | ||
20 | +export const option: PublicPresetOptions = { | ||
21 | + multipleDataSourceComponent: true, | ||
22 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#FD7347', | ||
23 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
24 | + [ComponentConfigFieldEnum.UNIT]: '℃', | ||
25 | +}; | ||
26 | + | ||
27 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
28 | + public key: string = StatisticsComponent4Config.key; | ||
29 | + | ||
30 | + public attr = { ...componentInitConfig }; | ||
31 | + | ||
32 | + public componentConfig: ConfigType = cloneDeep(StatisticsComponent4Config); | ||
33 | + | ||
34 | + public persetOption = cloneDeep(option); | ||
35 | + | ||
36 | + public option: PublicComponentOptions; | ||
37 | + | ||
38 | + constructor(option: PublicComponentOptions) { | ||
39 | + super(); | ||
40 | + this.option = { ...option }; | ||
41 | + } | ||
42 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '../../../enum'; | ||
3 | + import { option } from './config'; | ||
4 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
5 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
6 | + import { ComponentInfo } from '/@/views/visual/palette/types'; | ||
7 | + | ||
8 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
9 | + schemas: [ | ||
10 | + { | ||
11 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
12 | + label: '数值字体颜色', | ||
13 | + component: 'ColorPicker', | ||
14 | + changeEvent: 'update:value', | ||
15 | + defaultValue: option.fontColor, | ||
16 | + }, | ||
17 | + { | ||
18 | + field: ComponentConfigFieldEnum.UNIT, | ||
19 | + label: '数值单位', | ||
20 | + component: 'Input', | ||
21 | + defaultValue: option.unit, | ||
22 | + }, | ||
23 | + { | ||
24 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
25 | + label: '显示设备名称', | ||
26 | + component: 'Checkbox', | ||
27 | + defaultValue: option.showDeviceName, | ||
28 | + }, | ||
29 | + ], | ||
30 | + showActionButtonGroup: false, | ||
31 | + labelWidth: 120, | ||
32 | + baseColProps: { | ||
33 | + span: 12, | ||
34 | + }, | ||
35 | + }); | ||
36 | + | ||
37 | + const getFormValues = () => { | ||
38 | + // return getFieldsValue(); | ||
39 | + const item = getFieldsValue(); | ||
40 | + return { | ||
41 | + fontColor: item[ComponentConfigFieldEnum.FONT_COLOR], | ||
42 | + unit: item[ComponentConfigFieldEnum.UNIT], | ||
43 | + showDeviceName: item[ComponentConfigFieldEnum.SHOW_DEVICE_NAME], | ||
44 | + } as ComponentInfo; | ||
45 | + }; | ||
46 | + | ||
47 | + const setFormValues = (data: Recordable) => { | ||
48 | + // return setFieldsValue(data); | ||
49 | + const { unit, fontColor, showDeviceName } = data; | ||
50 | + | ||
51 | + const value = { | ||
52 | + [ComponentConfigFieldEnum.UNIT]: unit, | ||
53 | + [ComponentConfigFieldEnum.FONT_COLOR]: fontColor, | ||
54 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: showDeviceName, | ||
55 | + }; | ||
56 | + return setFieldsValue(value); | ||
57 | + }; | ||
58 | + | ||
59 | + defineExpose({ | ||
60 | + getFormValues, | ||
61 | + setFormValues, | ||
62 | + resetFormValues: resetFields, | ||
63 | + } as PublicFormInstaceType); | ||
64 | +</script> | ||
65 | + | ||
66 | +<template> | ||
67 | + <BasicForm @register="register" /> | ||
68 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { CreateComponentType } from '../../../index.type'; | ||
4 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
5 | + import { | ||
6 | + PublicComponentValueType, | ||
7 | + PublicFormInstaceType, | ||
8 | + } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
9 | + | ||
10 | + defineProps<{ | ||
11 | + values: PublicComponentValueType; | ||
12 | + componentConfig: CreateComponentType; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
16 | + labelWidth: 0, | ||
17 | + showActionButtonGroup: false, | ||
18 | + layout: 'horizontal', | ||
19 | + labelCol: { span: 0 }, | ||
20 | + schemas: commonDataSourceSchemas(), | ||
21 | + }); | ||
22 | + | ||
23 | + const getFormValues = () => { | ||
24 | + return getFieldsValue(); | ||
25 | + }; | ||
26 | + | ||
27 | + const setFormValues = (record: Recordable) => { | ||
28 | + return setFieldsValue(record); | ||
29 | + }; | ||
30 | + | ||
31 | + defineExpose({ | ||
32 | + getFormValues, | ||
33 | + setFormValues, | ||
34 | + validate, | ||
35 | + resetFormValues: resetFields, | ||
36 | + } as PublicFormInstaceType); | ||
37 | +</script> | ||
38 | + | ||
39 | +<template> | ||
40 | + <BasicForm @register="register" /> | ||
41 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('StatisticsComponent4'); | ||
5 | + | ||
6 | +export const StatisticsComponent4Config: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + title: '竖柱状图', | ||
9 | + package: PackagesCategoryEnum.STATISTICS, | ||
10 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { EChartsOption, SeriesOption, ECharts, init } from 'echarts'; | ||
3 | + import { unref, ref, onMounted, computed, nextTick } from 'vue'; | ||
4 | + import { useMultipleDataFetch } from '../../../hook/useSocket'; | ||
5 | + import { ComponentPropsConfigType, MultipleDataFetchUpdateFn } from '../../../index.type'; | ||
6 | + import { option } from './config'; | ||
7 | + import { UpdateTime } from '/@/views/visual/commonComponents/UpdateTime'; | ||
8 | + import { useComponentScale } from '../../../hook/useComponentScale'; | ||
9 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
10 | + | ||
11 | + const props = defineProps<{ | ||
12 | + config: ComponentPropsConfigType<typeof option>; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const chartRefEl = ref<Nullable<HTMLDivElement>>(null); | ||
16 | + | ||
17 | + const chartInstance = ref<Nullable<ECharts>>(null); | ||
18 | + | ||
19 | + const time = ref<Nullable<number>>(null); | ||
20 | + | ||
21 | + const getDesign = computed(() => { | ||
22 | + const { persetOption, option } = props.config; | ||
23 | + const { dataSource = [] } = option || {}; | ||
24 | + const { unit: presetUnit, fontColor: presetFontColor } = persetOption || {}; | ||
25 | + return { | ||
26 | + dataSource: dataSource?.map((item) => { | ||
27 | + const { unit, fontColor } = item.componentInfo || {}; | ||
28 | + const { attribute, attributeRename } = item; | ||
29 | + return { | ||
30 | + unit: unit ?? presetUnit, | ||
31 | + fontColor: fontColor ?? presetFontColor, | ||
32 | + attribute, | ||
33 | + attributeRename, | ||
34 | + }; | ||
35 | + }), | ||
36 | + }; | ||
37 | + }); | ||
38 | + const seriesList = [ | ||
39 | + { value: 120, name: '123', itemStyle: { color: '#02E5F0' } }, | ||
40 | + { value: 150, name: '456', itemStyle: { color: '#028CF0' } }, | ||
41 | + { value: 40, name: '789', itemStyle: { color: '#F09202' } }, | ||
42 | + ]; | ||
43 | + const data = ['温度', '湿度', '温度1']; | ||
44 | + const options = (): EChartsOption => { | ||
45 | + // getStageColor(gradientInfo); | ||
46 | + return { | ||
47 | + color: ['#3398DB'], | ||
48 | + tooltip: { | ||
49 | + // 提示框 | ||
50 | + trigger: 'axis', | ||
51 | + axisPointer: { | ||
52 | + type: 'shadow', | ||
53 | + }, | ||
54 | + }, | ||
55 | + xAxis: { | ||
56 | + type: 'value', | ||
57 | + }, | ||
58 | + yAxis: { | ||
59 | + type: 'category', | ||
60 | + data: data, | ||
61 | + axisTick: { | ||
62 | + alignWithLabel: true, | ||
63 | + }, | ||
64 | + axisPointer: { | ||
65 | + type: 'line', | ||
66 | + }, | ||
67 | + }, | ||
68 | + grid: { | ||
69 | + top: '15%', | ||
70 | + left: '28%', | ||
71 | + bottom: '15%', | ||
72 | + }, | ||
73 | + series: [ | ||
74 | + { | ||
75 | + name: '', | ||
76 | + type: 'bar', | ||
77 | + barWidth: '60%', | ||
78 | + data: seriesList, | ||
79 | + }, | ||
80 | + ], | ||
81 | + }; | ||
82 | + }; | ||
83 | + | ||
84 | + const initial = () => { | ||
85 | + chartInstance.value = init(unref(chartRefEl)! as HTMLElement); | ||
86 | + chartInstance.value.setOption(options()); | ||
87 | + }; | ||
88 | + | ||
89 | + // const randomFn = () => { | ||
90 | + // useIntervalFn(() => { | ||
91 | + // const value = (Math.random() * 100).toFixed(0); | ||
92 | + // unref(chartInstance)?.setOption({ | ||
93 | + // series: [{ data: [{ value }] }, { data: [{ value }] }], | ||
94 | + // } as EChartsOption); | ||
95 | + // }, 3000); | ||
96 | + // }; | ||
97 | + | ||
98 | + const updateChart = (data: SeriesOption['data'], yAxisData) => { | ||
99 | + unref(chartInstance)?.setOption({ | ||
100 | + series: [{ data }], | ||
101 | + yAxis: { data: yAxisData }, | ||
102 | + // color: unref(list).map((item) => item.title.color), | ||
103 | + } as EChartsOption); | ||
104 | + }; | ||
105 | + | ||
106 | + const updateFn: MultipleDataFetchUpdateFn = (message) => { | ||
107 | + const { data = {} } = message; | ||
108 | + const { dataSource } = unref(getDesign); | ||
109 | + const series = dataSource.map((item) => { | ||
110 | + const { attribute, attributeRename, fontColor, unit } = item; | ||
111 | + const [latest] = data[attribute] || []; | ||
112 | + const [_timespan, value] = latest || []; | ||
113 | + | ||
114 | + return { | ||
115 | + value, | ||
116 | + name: attributeRename ?? attribute, | ||
117 | + itemStyle: { color: fontColor }, | ||
118 | + tooltip: { | ||
119 | + valueFormatter(value) { | ||
120 | + return `${value} ${unit ?? ''}`; | ||
121 | + }, | ||
122 | + }, | ||
123 | + } as SeriesOption['data']; | ||
124 | + }); | ||
125 | + const yAxisData = series.map((item) => { | ||
126 | + const { name } = item as any; | ||
127 | + return name; | ||
128 | + }); | ||
129 | + // } | ||
130 | + // console.log(message, 'message', series, 'series', sum); | ||
131 | + updateChart(series, yAxisData); | ||
132 | + }; | ||
133 | + | ||
134 | + useMultipleDataFetch(props, updateFn); | ||
135 | + | ||
136 | + onMounted(() => { | ||
137 | + initial(); | ||
138 | + // !props.config.option.uuid && randomFn(); | ||
139 | + !props.config.option.uuid; | ||
140 | + }); | ||
141 | + | ||
142 | + const resize = async () => { | ||
143 | + await nextTick(); | ||
144 | + | ||
145 | + // 修改echarts大小 | ||
146 | + unref(chartInstance)?.setOption({ | ||
147 | + legend: { | ||
148 | + textStyle: { | ||
149 | + fontSize: 14 * unref(getRatio), | ||
150 | + }, | ||
151 | + }, | ||
152 | + } as EChartsOption); | ||
153 | + unref(chartInstance)?.resize(); | ||
154 | + }; | ||
155 | + | ||
156 | + const { getRatio } = useComponentScale(props, resize); | ||
157 | +</script> | ||
158 | + | ||
159 | +<template> | ||
160 | + <main class="w-full h-full flex flex-col justify-center items-center"> | ||
161 | + <DeviceName :config="config" /> | ||
162 | + <div ref="chartRefEl" class="flex-1 w-full h-full"> </div> | ||
163 | + <UpdateTime :time="time" /> | ||
164 | + </main> | ||
165 | +</template> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { StatisticsComponent5Config } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '../../../index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '../../../publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '../../../enum'; | ||
11 | + | ||
12 | +export enum Gradient { | ||
13 | + FIRST = 'first', | ||
14 | + SECOND = 'second', | ||
15 | +} | ||
16 | +export enum GradientColor { | ||
17 | + FIRST = '#07ffd6', | ||
18 | + SECOND = '#5eff10', | ||
19 | +} | ||
20 | +export const option: PublicPresetOptions = { | ||
21 | + multipleDataSourceComponent: true, | ||
22 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#FD7347', | ||
23 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
24 | + [ComponentConfigFieldEnum.UNIT]: '℃', | ||
25 | +}; | ||
26 | + | ||
27 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
28 | + public key: string = StatisticsComponent5Config.key; | ||
29 | + | ||
30 | + public attr = { ...componentInitConfig }; | ||
31 | + | ||
32 | + public componentConfig: ConfigType = cloneDeep(StatisticsComponent5Config); | ||
33 | + | ||
34 | + public persetOption = cloneDeep(option); | ||
35 | + | ||
36 | + public option: PublicComponentOptions; | ||
37 | + | ||
38 | + constructor(option: PublicComponentOptions) { | ||
39 | + super(); | ||
40 | + this.option = { ...option }; | ||
41 | + } | ||
42 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '../../../enum'; | ||
3 | + import { option } from './config'; | ||
4 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
5 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
6 | + import { ComponentInfo } from '/@/views/visual/palette/types'; | ||
7 | + | ||
8 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
9 | + schemas: [ | ||
10 | + { | ||
11 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
12 | + label: '数值字体颜色', | ||
13 | + component: 'ColorPicker', | ||
14 | + changeEvent: 'update:value', | ||
15 | + defaultValue: option.fontColor, | ||
16 | + }, | ||
17 | + { | ||
18 | + field: ComponentConfigFieldEnum.UNIT, | ||
19 | + label: '数值单位', | ||
20 | + component: 'Input', | ||
21 | + defaultValue: option.unit, | ||
22 | + }, | ||
23 | + { | ||
24 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
25 | + label: '显示设备名称', | ||
26 | + component: 'Checkbox', | ||
27 | + defaultValue: option.showDeviceName, | ||
28 | + }, | ||
29 | + ], | ||
30 | + showActionButtonGroup: false, | ||
31 | + labelWidth: 120, | ||
32 | + baseColProps: { | ||
33 | + span: 12, | ||
34 | + }, | ||
35 | + }); | ||
36 | + | ||
37 | + const getFormValues = () => { | ||
38 | + // return getFieldsValue(); | ||
39 | + const item = getFieldsValue(); | ||
40 | + return { | ||
41 | + fontColor: item[ComponentConfigFieldEnum.FONT_COLOR], | ||
42 | + unit: item[ComponentConfigFieldEnum.UNIT], | ||
43 | + showDeviceName: item[ComponentConfigFieldEnum.SHOW_DEVICE_NAME], | ||
44 | + } as ComponentInfo; | ||
45 | + }; | ||
46 | + | ||
47 | + const setFormValues = (data: Recordable) => { | ||
48 | + // return setFieldsValue(data); | ||
49 | + const { unit, fontColor, showDeviceName } = data; | ||
50 | + | ||
51 | + const value = { | ||
52 | + [ComponentConfigFieldEnum.UNIT]: unit, | ||
53 | + [ComponentConfigFieldEnum.FONT_COLOR]: fontColor, | ||
54 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: showDeviceName, | ||
55 | + }; | ||
56 | + return setFieldsValue(value); | ||
57 | + }; | ||
58 | + | ||
59 | + defineExpose({ | ||
60 | + getFormValues, | ||
61 | + setFormValues, | ||
62 | + resetFormValues: resetFields, | ||
63 | + } as PublicFormInstaceType); | ||
64 | +</script> | ||
65 | + | ||
66 | +<template> | ||
67 | + <BasicForm @register="register" /> | ||
68 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { CreateComponentType } from '../../../index.type'; | ||
4 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
5 | + import { | ||
6 | + PublicComponentValueType, | ||
7 | + PublicFormInstaceType, | ||
8 | + } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
9 | + | ||
10 | + defineProps<{ | ||
11 | + values: PublicComponentValueType; | ||
12 | + componentConfig: CreateComponentType; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
16 | + labelWidth: 0, | ||
17 | + showActionButtonGroup: false, | ||
18 | + layout: 'horizontal', | ||
19 | + labelCol: { span: 0 }, | ||
20 | + schemas: commonDataSourceSchemas(), | ||
21 | + }); | ||
22 | + | ||
23 | + const getFormValues = () => { | ||
24 | + return getFieldsValue(); | ||
25 | + }; | ||
26 | + | ||
27 | + const setFormValues = (record: Recordable) => { | ||
28 | + return setFieldsValue(record); | ||
29 | + }; | ||
30 | + | ||
31 | + defineExpose({ | ||
32 | + getFormValues, | ||
33 | + setFormValues, | ||
34 | + validate, | ||
35 | + resetFormValues: resetFields, | ||
36 | + } as PublicFormInstaceType); | ||
37 | +</script> | ||
38 | + | ||
39 | +<template> | ||
40 | + <BasicForm @register="register" /> | ||
41 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('StatisticsComponent5'); | ||
5 | + | ||
6 | +export const StatisticsComponent5Config: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + title: '实时数据表格', | ||
9 | + package: PackagesCategoryEnum.STATISTICS, | ||
10 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { reactive, ref } from 'vue'; | ||
3 | + import { useMultipleDataFetch } from '../../../hook/useSocket'; | ||
4 | + import { ComponentPropsConfigType, MultipleDataFetchUpdateFn } from '../../../index.type'; | ||
5 | + import { option } from './config'; | ||
6 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
7 | + import { BasicTable, useTable, BasicColumn } from '/@/components/Table'; | ||
8 | + | ||
9 | + const props = defineProps<{ | ||
10 | + config: ComponentPropsConfigType<typeof option>; | ||
11 | + }>(); | ||
12 | + | ||
13 | + const realTimeList = ref<any>([ | ||
14 | + { attribute: '测试', price: 2, time: '2023-06-29' }, | ||
15 | + { attribute: '测试1', price: 21, time: '2023-06-29' }, | ||
16 | + { attribute: '测试2', price: 213, time: '2023-06-29' }, | ||
17 | + ]); | ||
18 | + const realTimeColumn = reactive<BasicColumn[]>([ | ||
19 | + { title: '属性', dataIndex: 'attribute', width: 80, ellipsis: true }, | ||
20 | + { title: '值', dataIndex: 'price', width: 80, ellipsis: true }, | ||
21 | + { title: '时间', dataIndex: 'time', width: 80, ellipsis: true }, | ||
22 | + ]); | ||
23 | + | ||
24 | + const [registerTable] = useTable({ | ||
25 | + showIndexColumn: false, | ||
26 | + showTableSetting: false, | ||
27 | + dataSource: realTimeList, | ||
28 | + canResize: true, | ||
29 | + maxHeight: 144, | ||
30 | + size: 'small', | ||
31 | + // columns: [{ title: '属性', dataIndex: 'attribute', width: 80 }], | ||
32 | + columns: realTimeColumn as any, | ||
33 | + }); | ||
34 | + | ||
35 | + // const getDesign = computed(() => { | ||
36 | + // const { persetOption, option } = props.config; | ||
37 | + // clearInterval; | ||
38 | + // return {}; | ||
39 | + // }); | ||
40 | + | ||
41 | + // const randomFn = () => { | ||
42 | + // useIntervalFn(() => { | ||
43 | + // const value = (Math.random() * 100).toFixed(0); | ||
44 | + // unref(chartInstance)?.setOption({ | ||
45 | + // series: [{ data: [{ value }] }, { data: [{ value }] }], | ||
46 | + // } as EChartsOption); | ||
47 | + // }, 3000); | ||
48 | + // }; | ||
49 | + | ||
50 | + const updateFn: MultipleDataFetchUpdateFn = () => {}; | ||
51 | + | ||
52 | + useMultipleDataFetch(props, updateFn); | ||
53 | + | ||
54 | + // const { getRatio } = useComponentScale(props); | ||
55 | +</script> | ||
56 | + | ||
57 | +<template> | ||
58 | + <main class="flex flex-col justify-center items-center"> | ||
59 | + <DeviceName :config="config" /> | ||
60 | + <div> | ||
61 | + <!-- <PageWrapper> --> | ||
62 | + <BasicTable @register="registerTable" /> | ||
63 | + <!-- </PageWrapper> --> | ||
64 | + </div> | ||
65 | + </main> | ||
66 | +</template> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { StatisticsComponent6Config } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '../../../index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '../../../publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '../../../enum'; | ||
11 | + | ||
12 | +export enum Gradient { | ||
13 | + FIRST = 'first', | ||
14 | + SECOND = 'second', | ||
15 | +} | ||
16 | +export enum GradientColor { | ||
17 | + FIRST = '#07ffd6', | ||
18 | + SECOND = '#5eff10', | ||
19 | +} | ||
20 | +export const option: PublicPresetOptions = { | ||
21 | + multipleDataSourceComponent: true, | ||
22 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#FD7347', | ||
23 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
24 | + [ComponentConfigFieldEnum.UNIT]: '℃', | ||
25 | +}; | ||
26 | + | ||
27 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
28 | + public key: string = StatisticsComponent6Config.key; | ||
29 | + | ||
30 | + public attr = { ...componentInitConfig }; | ||
31 | + | ||
32 | + public componentConfig: ConfigType = cloneDeep(StatisticsComponent6Config); | ||
33 | + | ||
34 | + public persetOption = cloneDeep(option); | ||
35 | + | ||
36 | + public option: PublicComponentOptions; | ||
37 | + | ||
38 | + constructor(option: PublicComponentOptions) { | ||
39 | + super(); | ||
40 | + this.option = { ...option }; | ||
41 | + } | ||
42 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '../../../enum'; | ||
3 | + import { option } from './config'; | ||
4 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
5 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
6 | + import { ComponentInfo } from '/@/views/visual/palette/types'; | ||
7 | + | ||
8 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
9 | + schemas: [ | ||
10 | + { | ||
11 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
12 | + label: '数值字体颜色', | ||
13 | + component: 'ColorPicker', | ||
14 | + changeEvent: 'update:value', | ||
15 | + defaultValue: option.fontColor, | ||
16 | + }, | ||
17 | + { | ||
18 | + field: ComponentConfigFieldEnum.UNIT, | ||
19 | + label: '数值单位', | ||
20 | + component: 'Input', | ||
21 | + defaultValue: option.unit, | ||
22 | + }, | ||
23 | + { | ||
24 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
25 | + label: '显示设备名称', | ||
26 | + component: 'Checkbox', | ||
27 | + defaultValue: option.showDeviceName, | ||
28 | + }, | ||
29 | + ], | ||
30 | + showActionButtonGroup: false, | ||
31 | + labelWidth: 120, | ||
32 | + baseColProps: { | ||
33 | + span: 12, | ||
34 | + }, | ||
35 | + }); | ||
36 | + | ||
37 | + const getFormValues = () => { | ||
38 | + // return getFieldsValue(); | ||
39 | + const item = getFieldsValue(); | ||
40 | + return { | ||
41 | + fontColor: item[ComponentConfigFieldEnum.FONT_COLOR], | ||
42 | + unit: item[ComponentConfigFieldEnum.UNIT], | ||
43 | + showDeviceName: item[ComponentConfigFieldEnum.SHOW_DEVICE_NAME], | ||
44 | + } as ComponentInfo; | ||
45 | + }; | ||
46 | + | ||
47 | + const setFormValues = (data: Recordable) => { | ||
48 | + // return setFieldsValue(data); | ||
49 | + const { unit, fontColor, showDeviceName } = data; | ||
50 | + | ||
51 | + const value = { | ||
52 | + [ComponentConfigFieldEnum.UNIT]: unit, | ||
53 | + [ComponentConfigFieldEnum.FONT_COLOR]: fontColor, | ||
54 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: showDeviceName, | ||
55 | + }; | ||
56 | + return setFieldsValue(value); | ||
57 | + }; | ||
58 | + | ||
59 | + defineExpose({ | ||
60 | + getFormValues, | ||
61 | + setFormValues, | ||
62 | + resetFormValues: resetFields, | ||
63 | + } as PublicFormInstaceType); | ||
64 | +</script> | ||
65 | + | ||
66 | +<template> | ||
67 | + <BasicForm @register="register" /> | ||
68 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { CreateComponentType } from '../../../index.type'; | ||
4 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
5 | + import { | ||
6 | + PublicComponentValueType, | ||
7 | + PublicFormInstaceType, | ||
8 | + } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
9 | + | ||
10 | + defineProps<{ | ||
11 | + values: PublicComponentValueType; | ||
12 | + componentConfig: CreateComponentType; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
16 | + labelWidth: 0, | ||
17 | + showActionButtonGroup: false, | ||
18 | + layout: 'horizontal', | ||
19 | + labelCol: { span: 0 }, | ||
20 | + schemas: commonDataSourceSchemas(), | ||
21 | + }); | ||
22 | + | ||
23 | + const getFormValues = () => { | ||
24 | + return getFieldsValue(); | ||
25 | + }; | ||
26 | + | ||
27 | + const setFormValues = (record: Recordable) => { | ||
28 | + return setFieldsValue(record); | ||
29 | + }; | ||
30 | + | ||
31 | + defineExpose({ | ||
32 | + getFormValues, | ||
33 | + setFormValues, | ||
34 | + validate, | ||
35 | + resetFormValues: resetFields, | ||
36 | + } as PublicFormInstaceType); | ||
37 | +</script> | ||
38 | + | ||
39 | +<template> | ||
40 | + <BasicForm @register="register" /> | ||
41 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('StatisticsComponent6'); | ||
5 | + | ||
6 | +export const StatisticsComponent6Config: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + title: '实时数据折线图', | ||
9 | + package: PackagesCategoryEnum.STATISTICS, | ||
10 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { EChartsOption, ECharts, init } from 'echarts'; | ||
3 | + import { unref, ref, onMounted, nextTick } from 'vue'; | ||
4 | + import { useMultipleDataFetch } from '../../../hook/useSocket'; | ||
5 | + import { ComponentPropsConfigType, MultipleDataFetchUpdateFn } from '../../../index.type'; | ||
6 | + import { option } from './config'; | ||
7 | + import { UpdateTime } from '/@/views/visual/commonComponents/UpdateTime'; | ||
8 | + import { useComponentScale } from '../../../hook/useComponentScale'; | ||
9 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
10 | + import { dateFormat } from '/@/utils/common/compUtils'; | ||
11 | + | ||
12 | + const props = defineProps<{ | ||
13 | + config: ComponentPropsConfigType<typeof option>; | ||
14 | + }>(); | ||
15 | + | ||
16 | + const chartRefEl = ref<Nullable<HTMLDivElement>>(null); | ||
17 | + | ||
18 | + const chartInstance = ref<Nullable<ECharts>>(null); | ||
19 | + | ||
20 | + const time = ref<Nullable<number>>(null); | ||
21 | + | ||
22 | + function randomData() { | ||
23 | + now.value = now.value + oneDay; | ||
24 | + const newTime = dateFormat(unref(now), 'MM-dd hh:mm:ss'); | ||
25 | + value = value + Math.random() * 21 - 10; | ||
26 | + return { | ||
27 | + name: newTime, | ||
28 | + value: [newTime, Math.round(value)], | ||
29 | + }; | ||
30 | + } | ||
31 | + const data = ref<any>([]); | ||
32 | + const now = ref<number>(1688026367000); | ||
33 | + let oneDay = 5000; //间隔秒数 | ||
34 | + let value = Math.random() * 1000; | ||
35 | + for (let i = 0; i < 10; i++) { | ||
36 | + data.value.push(randomData()); | ||
37 | + } | ||
38 | + setInterval(function () { | ||
39 | + for (let i = 0; i < 1; i++) { | ||
40 | + data.value.shift(); | ||
41 | + data.value.push(randomData()); | ||
42 | + } | ||
43 | + unref(chartInstance)?.setOption(options()); | ||
44 | + }, 1000); | ||
45 | + | ||
46 | + // const getDesign = computed(() => { | ||
47 | + // const { persetOption, option } = props.config; | ||
48 | + // const { dataSource = [] } = option || {}; | ||
49 | + // const { unit: presetUnit, fontColor: presetFontColor } = persetOption || {}; | ||
50 | + // return { | ||
51 | + // dataSource: dataSource?.map((item) => { | ||
52 | + // const { unit, fontColor } = item.componentInfo || {}; | ||
53 | + // const { attribute, attributeRename } = item; | ||
54 | + // return { | ||
55 | + // unit: unit ?? presetUnit, | ||
56 | + // fontColor: fontColor ?? presetFontColor, | ||
57 | + // attribute, | ||
58 | + // attributeRename, | ||
59 | + // }; | ||
60 | + // }), | ||
61 | + // }; | ||
62 | + // }); | ||
63 | + | ||
64 | + const options = (): EChartsOption => { | ||
65 | + // getStageColor(gradientInfo); | ||
66 | + return { | ||
67 | + trigger: 'axis', | ||
68 | + axisPointer: { | ||
69 | + lineStyle: { | ||
70 | + width: 1, | ||
71 | + color: '#019680', | ||
72 | + }, | ||
73 | + }, | ||
74 | + legend: { | ||
75 | + top: '10%', | ||
76 | + left: 'center', | ||
77 | + data: ['温度', '湿度'], | ||
78 | + }, | ||
79 | + grid: { | ||
80 | + top: '45%', | ||
81 | + left: '20%', | ||
82 | + bottom: '14%', | ||
83 | + containLabel: true, | ||
84 | + }, | ||
85 | + xAxis: { | ||
86 | + type: 'category', | ||
87 | + splitLine: { | ||
88 | + show: true, | ||
89 | + lineStyle: { | ||
90 | + width: 1, | ||
91 | + type: 'solid', | ||
92 | + color: 'rgba(226,226,226,0.5)', | ||
93 | + }, | ||
94 | + }, | ||
95 | + data: unref(data).map((item) => item.name), | ||
96 | + }, | ||
97 | + yAxis: { | ||
98 | + type: 'value', | ||
99 | + boundaryGap: [0, '50%'], | ||
100 | + splitLine: { | ||
101 | + show: false, | ||
102 | + }, | ||
103 | + }, | ||
104 | + series: [ | ||
105 | + { | ||
106 | + type: 'line', | ||
107 | + name: '温度', | ||
108 | + stack: 'Total', | ||
109 | + data: unref(data).map((item) => item.value), | ||
110 | + }, | ||
111 | + { | ||
112 | + type: 'line', | ||
113 | + name: '湿度', | ||
114 | + stack: 'Total', | ||
115 | + data: unref(data).map((item) => { | ||
116 | + return Number(item.value[1]) * 0.99; | ||
117 | + }), | ||
118 | + }, | ||
119 | + ], | ||
120 | + }; | ||
121 | + }; | ||
122 | + | ||
123 | + const initial = () => { | ||
124 | + chartInstance.value = init(unref(chartRefEl)! as HTMLElement); | ||
125 | + chartInstance.value.setOption(options()); | ||
126 | + }; | ||
127 | + | ||
128 | + // const updateChart = (data: SeriesOption['data'], yAxisData) => { | ||
129 | + // unref(chartInstance)?.setOption({ | ||
130 | + // series: [{ data }], | ||
131 | + // yAxis: { data: yAxisData }, | ||
132 | + // } as EChartsOption); | ||
133 | + // }; | ||
134 | + | ||
135 | + const updateFn: MultipleDataFetchUpdateFn = () => { | ||
136 | + // console.log(message, 'message'); | ||
137 | + return {}; | ||
138 | + }; | ||
139 | + | ||
140 | + useMultipleDataFetch(props, updateFn); | ||
141 | + | ||
142 | + onMounted(() => { | ||
143 | + initial(); | ||
144 | + // !props.config.option.uuid && randomFn(); | ||
145 | + !props.config.option.uuid; | ||
146 | + }); | ||
147 | + | ||
148 | + const resize = async () => { | ||
149 | + await nextTick(); | ||
150 | + | ||
151 | + // 修改echarts大小 | ||
152 | + unref(chartInstance)?.setOption({ | ||
153 | + legend: { | ||
154 | + textStyle: { | ||
155 | + fontSize: 14 * unref(getRatio), | ||
156 | + }, | ||
157 | + }, | ||
158 | + } as EChartsOption); | ||
159 | + unref(chartInstance)?.resize(); | ||
160 | + }; | ||
161 | + | ||
162 | + const { getRatio } = useComponentScale(props, resize); | ||
163 | +</script> | ||
164 | + | ||
165 | +<template> | ||
166 | + <main class="w-full h-full flex flex-col justify-center items-center"> | ||
167 | + <DeviceName :config="config" /> | ||
168 | + <div ref="chartRefEl" class="flex-1 w-full h-full"> </div> | ||
169 | + <UpdateTime :time="time" /> | ||
170 | + </main> | ||
171 | +</template> |
1 | +import { StatisticsComponent1Config } from './StatisticsComponent1'; | ||
2 | +import { StatisticsComponent2Config } from './StatisticsComponent2'; | ||
3 | +// import { StatisticsComponent3Config } from './StatisticsComponent3'; | ||
4 | +// import { StatisticsComponent4Config } from './StatisticsComponent4'; | ||
5 | +// import { StatisticsComponent5Config } from './StatisticsComponent5'; | ||
6 | +// import { StatisticsComponent6Config } from './StatisticsComponent6'; | ||
7 | + | ||
8 | +export const STATISTICSList = [ | ||
9 | + StatisticsComponent1Config, | ||
10 | + StatisticsComponent2Config, | ||
11 | + // StatisticsComponent3Config, | ||
12 | + // StatisticsComponent4Config, | ||
13 | + // StatisticsComponent5Config, | ||
14 | + // StatisticsComponent6Config, | ||
15 | +]; |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { SwitchSignalLightConfig } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '/@/views/visual/packages/index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '/@/views/visual/packages/publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
11 | + | ||
12 | +export const option: PublicPresetOptions = { | ||
13 | + [ComponentConfigFieldEnum.OPEN_COLOR]: '#30f230', | ||
14 | + [ComponentConfigFieldEnum.CLOSE_COLOR]: '#eeeeee', | ||
15 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: true, | ||
16 | +}; | ||
17 | + | ||
18 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
19 | + public key: string = SwitchSignalLightConfig.key; | ||
20 | + | ||
21 | + public attr = { ...componentInitConfig }; | ||
22 | + | ||
23 | + public componentConfig: ConfigType = cloneDeep(SwitchSignalLightConfig); | ||
24 | + | ||
25 | + public persetOption = cloneDeep(option); | ||
26 | + | ||
27 | + public option: PublicComponentOptions; | ||
28 | + | ||
29 | + constructor(option: PublicComponentOptions) { | ||
30 | + super(); | ||
31 | + this.option = { ...option }; | ||
32 | + } | ||
33 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
3 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + import { option } from './config'; | ||
6 | + | ||
7 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
8 | + schemas: [ | ||
9 | + { | ||
10 | + field: ComponentConfigFieldEnum.OPEN_COLOR, | ||
11 | + label: 'ON颜色', | ||
12 | + component: 'ColorPicker', | ||
13 | + changeEvent: 'update:value', | ||
14 | + componentProps: { | ||
15 | + defaultValue: option.openColor, | ||
16 | + }, | ||
17 | + }, | ||
18 | + { | ||
19 | + field: ComponentConfigFieldEnum.CLOSE_COLOR, | ||
20 | + label: 'OFF颜色', | ||
21 | + component: 'ColorPicker', | ||
22 | + changeEvent: 'update:value', | ||
23 | + componentProps: { | ||
24 | + defaultValue: option.closeColor, | ||
25 | + }, | ||
26 | + }, | ||
27 | + { | ||
28 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
29 | + label: '显示设备名称', | ||
30 | + component: 'Checkbox', | ||
31 | + defaultValue: option.showDeviceName, | ||
32 | + }, | ||
33 | + ], | ||
34 | + showActionButtonGroup: false, | ||
35 | + labelWidth: 120, | ||
36 | + baseColProps: { | ||
37 | + span: 12, | ||
38 | + }, | ||
39 | + }); | ||
40 | + | ||
41 | + const getFormValues = () => { | ||
42 | + return getFieldsValue(); | ||
43 | + }; | ||
44 | + | ||
45 | + const setFormValues = (data: Recordable) => { | ||
46 | + return setFieldsValue(data); | ||
47 | + }; | ||
48 | + | ||
49 | + defineExpose({ | ||
50 | + getFormValues, | ||
51 | + setFormValues, | ||
52 | + resetFormValues: resetFields, | ||
53 | + } as PublicFormInstaceType); | ||
54 | +</script> | ||
55 | + | ||
56 | +<template> | ||
57 | + <BasicForm @register="register" /> | ||
58 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + | ||
6 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
7 | + labelWidth: 0, | ||
8 | + showActionButtonGroup: false, | ||
9 | + layout: 'horizontal', | ||
10 | + labelCol: { span: 0 }, | ||
11 | + schemas: commonDataSourceSchemas(), | ||
12 | + }); | ||
13 | + | ||
14 | + const getFormValues = () => { | ||
15 | + return getFieldsValue(); | ||
16 | + }; | ||
17 | + | ||
18 | + const setFormValues = (record: Recordable) => { | ||
19 | + return setFieldsValue(record); | ||
20 | + }; | ||
21 | + | ||
22 | + defineExpose({ | ||
23 | + getFormValues, | ||
24 | + setFormValues, | ||
25 | + validate, | ||
26 | + resetFormValues: resetFields, | ||
27 | + } as PublicFormInstaceType); | ||
28 | +</script> | ||
29 | + | ||
30 | +<template> | ||
31 | + <BasicForm @register="register" /> | ||
32 | +</template> |
1 | +// import { ComponentEnum, ComponentNameEnum } from '../index.type'; | ||
2 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
3 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
4 | + | ||
5 | +const componentKeys = useComponentKeys('SwitchSignalLight'); | ||
6 | +export const SwitchSignalLightConfig: ConfigType = { | ||
7 | + ...componentKeys, | ||
8 | + // title: ComponentNameEnum.TEXT_COMPONENT_1, | ||
9 | + title: '开关量信号灯', | ||
10 | + package: PackagesCategoryEnum.TEXT, | ||
11 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentPropsConfigType, DataFetchUpdateFn } from '/@/views/visual/packages/index.type'; | ||
3 | + import { option } from './config'; | ||
4 | + import { useComponentScale } from '/@/views/visual/packages/hook/useComponentScale'; | ||
5 | + import { useDataFetch } from '/@/views/visual/packages/hook/useSocket'; | ||
6 | + import { computed } from 'vue'; | ||
7 | + import { ref, onMounted, unref } from 'vue'; | ||
8 | + import { useIntervalFn } from '@vueuse/core'; | ||
9 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
10 | + | ||
11 | + const props = defineProps<{ | ||
12 | + config: ComponentPropsConfigType<typeof option>; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const isOpenClose = ref<boolean>(true); | ||
16 | + | ||
17 | + const getDesign = computed(() => { | ||
18 | + const { persetOption = {}, option } = props.config; | ||
19 | + const { | ||
20 | + openColor: persetOpenColor, | ||
21 | + closeColor: persetCloseColor, | ||
22 | + showDeviceName: persetShowDeviceName, | ||
23 | + } = persetOption || {}; | ||
24 | + const { componentInfo } = option; | ||
25 | + | ||
26 | + const { openColor, closeColor, showDeviceName } = componentInfo || {}; | ||
27 | + return { | ||
28 | + openColor: openColor ?? persetOpenColor, | ||
29 | + closeColor: closeColor ?? persetCloseColor, | ||
30 | + showDeviceName: showDeviceName ?? persetShowDeviceName, | ||
31 | + }; | ||
32 | + }); | ||
33 | + | ||
34 | + const randomFn = () => { | ||
35 | + useIntervalFn(() => { | ||
36 | + isOpenClose.value = !unref(isOpenClose); | ||
37 | + }, 2000); | ||
38 | + }; | ||
39 | + | ||
40 | + const updateFn: DataFetchUpdateFn = () => {}; | ||
41 | + | ||
42 | + onMounted(() => { | ||
43 | + !props.config.option.uuid && randomFn(); | ||
44 | + }); | ||
45 | + | ||
46 | + useDataFetch(props, updateFn); | ||
47 | + | ||
48 | + const { getScale } = useComponentScale(props); | ||
49 | +</script> | ||
50 | + | ||
51 | +<template> | ||
52 | + <main :style="getScale" class="w-full h-full flex flex-col justify-center items-center"> | ||
53 | + <DeviceName :config="config" class="text-center" /> | ||
54 | + <div | ||
55 | + :style="{ | ||
56 | + '--open-color': getDesign.openColor, | ||
57 | + '--close-color': getDesign.closeColor, | ||
58 | + }" | ||
59 | + :class="isOpenClose ? 'switch_open' : 'switch_close'" | ||
60 | + ></div> | ||
61 | + </main> | ||
62 | +</template> | ||
63 | +<style lang="less" scoped> | ||
64 | + .switch_open { | ||
65 | + background: var(--open-color); | ||
66 | + box-shadow: var(--open-color) 0 0 10px 3px; | ||
67 | + width: 60px; | ||
68 | + height: 60px; | ||
69 | + border-radius: 50%; | ||
70 | + margin: 10px 0; | ||
71 | + } | ||
72 | + | ||
73 | + .switch_close { | ||
74 | + background-color: var(--close-color); | ||
75 | + box-shadow: none; | ||
76 | + width: 42.023px; | ||
77 | + height: 42.023px; | ||
78 | + border-radius: 50%; | ||
79 | + margin: 10px 0; | ||
80 | + } | ||
81 | +</style> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { SwitchStatusConfig } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '/@/views/visual/packages/index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '/@/views/visual/packages/publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
11 | + | ||
12 | +export const option: PublicPresetOptions = { | ||
13 | + [ComponentConfigFieldEnum.ICON]: 'shuiwen', | ||
14 | + [ComponentConfigFieldEnum.ICON_COLOR]: '#367bff', | ||
15 | + [ComponentConfigFieldEnum.ICON_CLOSE]: 'shuiwen', | ||
16 | + [ComponentConfigFieldEnum.ICON_COLOR_CLOSE]: '#CCCCCC', | ||
17 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
18 | +}; | ||
19 | + | ||
20 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
21 | + public key: string = SwitchStatusConfig.key; | ||
22 | + | ||
23 | + public attr = { ...componentInitConfig }; | ||
24 | + | ||
25 | + public componentConfig: ConfigType = cloneDeep(SwitchStatusConfig); | ||
26 | + | ||
27 | + public persetOption = cloneDeep(option); | ||
28 | + | ||
29 | + public option: PublicComponentOptions; | ||
30 | + | ||
31 | + constructor(option: PublicComponentOptions) { | ||
32 | + super(); | ||
33 | + this.option = { ...option }; | ||
34 | + } | ||
35 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
3 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + import { option } from './config'; | ||
6 | + | ||
7 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
8 | + schemas: [ | ||
9 | + { | ||
10 | + field: ComponentConfigFieldEnum.ICON, | ||
11 | + label: '开启状态图标', | ||
12 | + component: 'IconDrawer', | ||
13 | + changeEvent: 'update:value', | ||
14 | + defaultValue: option.icon, | ||
15 | + componentProps({ formModel }) { | ||
16 | + const color = formModel[ComponentConfigFieldEnum.ICON_COLOR]; | ||
17 | + return { | ||
18 | + color, | ||
19 | + }; | ||
20 | + }, | ||
21 | + }, | ||
22 | + { | ||
23 | + field: ComponentConfigFieldEnum.ICON_COLOR, | ||
24 | + label: '开启图标颜色', | ||
25 | + component: 'ColorPicker', | ||
26 | + changeEvent: 'update:value', | ||
27 | + defaultValue: option.iconColor, | ||
28 | + }, | ||
29 | + { | ||
30 | + field: ComponentConfigFieldEnum.ICON_CLOSE, | ||
31 | + label: '关闭状态图标', | ||
32 | + component: 'IconDrawer', | ||
33 | + changeEvent: 'update:value', | ||
34 | + defaultValue: option.iconClose, | ||
35 | + componentProps({ formModel }) { | ||
36 | + const color = formModel[ComponentConfigFieldEnum.ICON_COLOR_CLOSE]; | ||
37 | + return { | ||
38 | + color, | ||
39 | + }; | ||
40 | + }, | ||
41 | + }, | ||
42 | + { | ||
43 | + field: ComponentConfigFieldEnum.ICON_COLOR_CLOSE, | ||
44 | + label: '关闭图标颜色', | ||
45 | + component: 'ColorPicker', | ||
46 | + changeEvent: 'update:value', | ||
47 | + defaultValue: option.iconColorClose, | ||
48 | + }, | ||
49 | + { | ||
50 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
51 | + label: '显示设备名称', | ||
52 | + component: 'Checkbox', | ||
53 | + defaultValue: option.showDeviceName, | ||
54 | + }, | ||
55 | + ], | ||
56 | + showActionButtonGroup: false, | ||
57 | + labelWidth: 120, | ||
58 | + baseColProps: { | ||
59 | + span: 12, | ||
60 | + }, | ||
61 | + }); | ||
62 | + | ||
63 | + const getFormValues = () => { | ||
64 | + return getFieldsValue(); | ||
65 | + }; | ||
66 | + | ||
67 | + const setFormValues = (data: Recordable) => { | ||
68 | + return setFieldsValue(data); | ||
69 | + }; | ||
70 | + | ||
71 | + defineExpose({ | ||
72 | + getFormValues, | ||
73 | + setFormValues, | ||
74 | + resetFormValues: resetFields, | ||
75 | + } as PublicFormInstaceType); | ||
76 | +</script> | ||
77 | + | ||
78 | +<template> | ||
79 | + <BasicForm @register="register" /> | ||
80 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + | ||
6 | + // const props = defineProps<{ | ||
7 | + // values: PublicComponentDataSourceProps; | ||
8 | + // }>(); | ||
9 | + | ||
10 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
11 | + labelWidth: 0, | ||
12 | + showActionButtonGroup: false, | ||
13 | + layout: 'horizontal', | ||
14 | + labelCol: { span: 0 }, | ||
15 | + schemas: commonDataSourceSchemas(), | ||
16 | + }); | ||
17 | + | ||
18 | + const getFormValues = () => { | ||
19 | + return getFieldsValue(); | ||
20 | + }; | ||
21 | + | ||
22 | + const setFormValues = (record: Recordable) => { | ||
23 | + return setFieldsValue(record); | ||
24 | + }; | ||
25 | + | ||
26 | + defineExpose({ | ||
27 | + getFormValues, | ||
28 | + setFormValues, | ||
29 | + validate, | ||
30 | + resetFormValues: resetFields, | ||
31 | + } as PublicFormInstaceType); | ||
32 | +</script> | ||
33 | + | ||
34 | +<template> | ||
35 | + <BasicForm @register="register" /> | ||
36 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('SwitchStatus'); | ||
5 | +export const SwitchStatusConfig: ConfigType = { | ||
6 | + ...componentKeys, | ||
7 | + title: '开关量状态', | ||
8 | + package: PackagesCategoryEnum.TEXT, | ||
9 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { useDataFetch } from '/@/views/visual/packages/hook/useSocket'; | ||
3 | + import { ComponentPropsConfigType, DataFetchUpdateFn } from '/@/views/visual/packages/index.type'; | ||
4 | + | ||
5 | + import { option } from './config'; | ||
6 | + import { SvgIcon } from '/@/components/Icon'; | ||
7 | + import { computed } from 'vue'; | ||
8 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
9 | + | ||
10 | + const props = defineProps<{ | ||
11 | + config: ComponentPropsConfigType<typeof option>; | ||
12 | + }>(); | ||
13 | + | ||
14 | + const getDesign = computed(() => { | ||
15 | + const { persetOption = {}, option } = props.config; | ||
16 | + | ||
17 | + const { | ||
18 | + iconColor: persetIconColor, | ||
19 | + unit: perseUnit, | ||
20 | + icon: persetIcon, | ||
21 | + fontColor: persetFontColor, | ||
22 | + } = persetOption; | ||
23 | + | ||
24 | + const { componentInfo, attribute, attributeRename } = option; | ||
25 | + | ||
26 | + const { icon, iconColor, fontColor, unit } = componentInfo || {}; | ||
27 | + return { | ||
28 | + iconColor: iconColor || persetIconColor, | ||
29 | + unit: unit ?? perseUnit, | ||
30 | + icon: icon || persetIcon, | ||
31 | + fontColor: fontColor || persetFontColor, | ||
32 | + attribute: attributeRename || attribute, | ||
33 | + }; | ||
34 | + }); | ||
35 | + | ||
36 | + // const svgList = ref<any>([ | ||
37 | + // { | ||
38 | + // value: 26.2, | ||
39 | + // name: 'wendu', | ||
40 | + // icon: 'zongfushe', | ||
41 | + // unit: 'kw', | ||
42 | + // iconColor: '#367BFF', | ||
43 | + // fontColor: '#357CFB', | ||
44 | + // }, | ||
45 | + // { | ||
46 | + // value: 53.7, | ||
47 | + // name: 'shidu', | ||
48 | + // icon: 'guangzhaoqiangdu', | ||
49 | + // unit: '℃', | ||
50 | + // iconColor: '#FFA000', | ||
51 | + // fontColor: '#FFA000', | ||
52 | + // }, | ||
53 | + // ]); | ||
54 | + | ||
55 | + const updateFn: DataFetchUpdateFn = () => {}; | ||
56 | + | ||
57 | + useDataFetch(props, updateFn); | ||
58 | +</script> | ||
59 | + | ||
60 | +<template> | ||
61 | + <main class="w-full h-full flex flex-col justify-evenly items-center"> | ||
62 | + <DeviceName :config="config" /> | ||
63 | + <div class="flex justify-center items-center"> | ||
64 | + <SvgIcon | ||
65 | + :name="getDesign.icon!" | ||
66 | + prefix="iconfont" | ||
67 | + :size="60" | ||
68 | + :style="{ color: getDesign.iconColor }" | ||
69 | + /> | ||
70 | + </div> | ||
71 | + </main> | ||
72 | +</template> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { ValueList1Config } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '/@/views/visual/packages/index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '/@/views/visual/packages/publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
11 | + | ||
12 | +export const option: PublicPresetOptions = { | ||
13 | + multipleDataSourceComponent: true, | ||
14 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#000', | ||
15 | + [ComponentConfigFieldEnum.UNIT]: '℃', | ||
16 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
17 | + [ComponentConfigFieldEnum.BACKGROUND_COLOR]: '#377dff', | ||
18 | + fontSize: '18px', | ||
19 | +}; | ||
20 | + | ||
21 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
22 | + public key: string = ValueList1Config.key; | ||
23 | + | ||
24 | + public attr = { ...componentInitConfig }; | ||
25 | + | ||
26 | + public componentConfig: ConfigType = cloneDeep(ValueList1Config); | ||
27 | + | ||
28 | + public persetOption = cloneDeep(option); | ||
29 | + | ||
30 | + public option: PublicComponentOptions; | ||
31 | + | ||
32 | + constructor(option: PublicComponentOptions) { | ||
33 | + super(); | ||
34 | + this.option = { ...option }; | ||
35 | + } | ||
36 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
3 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + import { option } from './config'; | ||
6 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
7 | + schemas: [ | ||
8 | + { | ||
9 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
10 | + label: '数值字体颜色', | ||
11 | + component: 'ColorPicker', | ||
12 | + changeEvent: 'update:value', | ||
13 | + componentProps: { | ||
14 | + defaultValue: option.fontColor, | ||
15 | + }, | ||
16 | + }, | ||
17 | + { | ||
18 | + field: ComponentConfigFieldEnum.BACKGROUND_COLOR, | ||
19 | + label: '进度条背景色', | ||
20 | + component: 'ColorPicker', | ||
21 | + changeEvent: 'update:value', | ||
22 | + componentProps: { | ||
23 | + defaultValue: option.backgroundColor, | ||
24 | + }, | ||
25 | + }, | ||
26 | + | ||
27 | + { | ||
28 | + field: ComponentConfigFieldEnum.UNIT, | ||
29 | + label: '数值单位', | ||
30 | + component: 'Input', | ||
31 | + defaultValue: option.unit, | ||
32 | + }, | ||
33 | + // { | ||
34 | + // field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
35 | + // label: '显示设备名称', | ||
36 | + // component: 'Checkbox', | ||
37 | + // }, | ||
38 | + ], | ||
39 | + showActionButtonGroup: false, | ||
40 | + labelWidth: 120, | ||
41 | + baseColProps: { | ||
42 | + span: 12, | ||
43 | + }, | ||
44 | + }); | ||
45 | + | ||
46 | + const getFormValues = () => { | ||
47 | + return getFieldsValue(); | ||
48 | + }; | ||
49 | + | ||
50 | + const setFormValues = (data: Recordable) => { | ||
51 | + return setFieldsValue(data); | ||
52 | + }; | ||
53 | + | ||
54 | + defineExpose({ | ||
55 | + getFormValues, | ||
56 | + setFormValues, | ||
57 | + resetFormValues: resetFields, | ||
58 | + } as PublicFormInstaceType); | ||
59 | +</script> | ||
60 | + | ||
61 | +<template> | ||
62 | + <BasicForm @register="register" /> | ||
63 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + | ||
6 | + // const props = defineProps<{ | ||
7 | + // values: PublicComponentDataSourceProps; | ||
8 | + // }>(); | ||
9 | + | ||
10 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
11 | + labelWidth: 0, | ||
12 | + showActionButtonGroup: false, | ||
13 | + layout: 'horizontal', | ||
14 | + labelCol: { span: 0 }, | ||
15 | + schemas: commonDataSourceSchemas(), | ||
16 | + }); | ||
17 | + | ||
18 | + const getFormValues = () => { | ||
19 | + return getFieldsValue(); | ||
20 | + }; | ||
21 | + | ||
22 | + const setFormValues = (record: Recordable) => { | ||
23 | + return setFieldsValue(record); | ||
24 | + }; | ||
25 | + | ||
26 | + defineExpose({ | ||
27 | + getFormValues, | ||
28 | + setFormValues, | ||
29 | + validate, | ||
30 | + resetFormValues: resetFields, | ||
31 | + } as PublicFormInstaceType); | ||
32 | +</script> | ||
33 | + | ||
34 | +<template> | ||
35 | + <BasicForm @register="register" /> | ||
36 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('ValueList1'); | ||
5 | +export const ValueList1Config: ConfigType = { | ||
6 | + ...componentKeys, | ||
7 | + title: '数值列表1', | ||
8 | + package: PackagesCategoryEnum.TEXT, | ||
9 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { option } from './config'; | ||
3 | + // import { useComponentScale } from '/@/views/visual/packages/hook/useComponentScale'; | ||
4 | + import { ComponentPropsConfigType, MultipleDataFetchUpdateFn } from '../../../index.type'; | ||
5 | + import { useMultipleDataFetch } from '/@/views/visual/packages/hook/useSocket'; | ||
6 | + import { computed } from 'vue'; | ||
7 | + import { ref } from 'vue'; | ||
8 | + import { Progress } from 'ant-design-vue'; | ||
9 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
10 | + import { unref } from 'vue'; | ||
11 | + import { onMounted } from 'vue'; | ||
12 | + | ||
13 | + const props = defineProps<{ | ||
14 | + config: ComponentPropsConfigType<typeof option>; | ||
15 | + }>(); | ||
16 | + | ||
17 | + const percentList = ref<any[]>([ | ||
18 | + { | ||
19 | + value: 20, | ||
20 | + fontColor: '#19eff', | ||
21 | + backgroundColor: '#19eff', | ||
22 | + color: '#000', | ||
23 | + fontSize: '16px', | ||
24 | + unit: '℃', | ||
25 | + id: 1, | ||
26 | + }, | ||
27 | + { | ||
28 | + value: 66, | ||
29 | + fontColor: '#1E8667', | ||
30 | + backgroundColor: '#1E8667', | ||
31 | + color: '#000', | ||
32 | + fontSize: '16px', | ||
33 | + unit: '℃', | ||
34 | + id: 2, | ||
35 | + }, | ||
36 | + { | ||
37 | + value: 49, | ||
38 | + fontColor: '#2196F3', | ||
39 | + backgroundColor: '#2196F3', | ||
40 | + color: '#000', | ||
41 | + fontSize: '16px', | ||
42 | + unit: '℃', | ||
43 | + id: 3, | ||
44 | + }, | ||
45 | + ]); | ||
46 | + | ||
47 | + const getDesign = computed(() => { | ||
48 | + const { persetOption = {}, option } = props.config; | ||
49 | + const { dataSource = [] } = option || {}; | ||
50 | + const { | ||
51 | + unit: presetUnit, | ||
52 | + fontColor: presetFontColor, | ||
53 | + backgroundColor: persetBackgroundColor, | ||
54 | + } = persetOption || {}; | ||
55 | + return { | ||
56 | + dataSource: dataSource?.map((item) => { | ||
57 | + const { unit, fontColor, fontSize, backgroundColor } = item.componentInfo || {}; | ||
58 | + const { attribute, attributeRename } = item; | ||
59 | + return { | ||
60 | + unit: unit ?? presetUnit, | ||
61 | + fontColor: fontColor ?? presetFontColor, | ||
62 | + fontSize, | ||
63 | + backgroundColor: backgroundColor ?? persetBackgroundColor, | ||
64 | + attribute, | ||
65 | + attributeRename, | ||
66 | + }; | ||
67 | + }), | ||
68 | + }; | ||
69 | + }); | ||
70 | + | ||
71 | + const newPercentList = ref<any[]>([]); | ||
72 | + | ||
73 | + const updateFn: MultipleDataFetchUpdateFn = (message) => { | ||
74 | + const { data = {} } = message; | ||
75 | + const { dataSource } = unref(getDesign); | ||
76 | + newPercentList.value = dataSource.map((item) => { | ||
77 | + const { attribute, fontSize, attributeRename, fontColor, unit, backgroundColor } = item; | ||
78 | + | ||
79 | + const [latest] = data[attribute] || []; | ||
80 | + const [_timespan, value] = latest || []; | ||
81 | + return { | ||
82 | + value: Number(value), | ||
83 | + name: attributeRename ?? attribute, | ||
84 | + fontSize, | ||
85 | + unit, | ||
86 | + backgroundColor: backgroundColor, | ||
87 | + fontColor: fontColor, | ||
88 | + }; | ||
89 | + }); | ||
90 | + // console.log(numberList, 'numberList'); | ||
91 | + }; | ||
92 | + | ||
93 | + onMounted(() => { | ||
94 | + newPercentList.value = percentList.value; | ||
95 | + !props.config.option.uuid; | ||
96 | + }); | ||
97 | + | ||
98 | + useMultipleDataFetch(props, updateFn); | ||
99 | + | ||
100 | + // const { getScale } = useComponentScale(props); | ||
101 | +</script> | ||
102 | + | ||
103 | +<template> | ||
104 | + <main class="w-full h-full flex flex-col justify-center"> | ||
105 | + <DeviceName :config="config" /> | ||
106 | + | ||
107 | + <div | ||
108 | + v-for="item in newPercentList" | ||
109 | + :key="item.id" | ||
110 | + class="flex flex-col ml-3 mr-3 items-stretch" | ||
111 | + > | ||
112 | + <div class="flex justify-between"> | ||
113 | + <div class="text-gray-500 text-lg truncate">{{ item.name || '温度' }}</div> | ||
114 | + <span class="text-lg" :style="{ color: item.fontColor }" | ||
115 | + >{{ item.value }} {{ item.unit }}</span | ||
116 | + > | ||
117 | + </div> | ||
118 | + <div> | ||
119 | + <Progress :strokeColor="item.backgroundColor" :percent="item.value" :showInfo="false" /> | ||
120 | + </div> | ||
121 | + </div> | ||
122 | + </main> | ||
123 | +</template> | ||
124 | +<style lang="less" scoped> | ||
125 | + // :deep(.ant-progress-success-bg, .ant-progress-bg) { | ||
126 | + // background: '#2196F3' !important; | ||
127 | + // } | ||
128 | +</style> |
1 | +import cloneDeep from 'lodash-es/cloneDeep'; | ||
2 | +import { ValueList2Config } from '.'; | ||
3 | +import { | ||
4 | + ConfigType, | ||
5 | + CreateComponentType, | ||
6 | + PublicComponentOptions, | ||
7 | + PublicPresetOptions, | ||
8 | +} from '/@/views/visual/packages/index.type'; | ||
9 | +import { PublicConfigClass, componentInitConfig } from '/@/views/visual/packages/publicConfig'; | ||
10 | +import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
11 | + | ||
12 | +export const option: PublicPresetOptions = { | ||
13 | + multipleDataSourceComponent: true, | ||
14 | + [ComponentConfigFieldEnum.UNIT]: '℃', | ||
15 | + [ComponentConfigFieldEnum.ICON]: 'shuiwen', | ||
16 | + [ComponentConfigFieldEnum.ICON_COLOR]: '#367bff', | ||
17 | + [ComponentConfigFieldEnum.FONT_COLOR]: '#000', | ||
18 | + [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]: false, | ||
19 | +}; | ||
20 | + | ||
21 | +export default class Config extends PublicConfigClass implements CreateComponentType { | ||
22 | + public key: string = ValueList2Config.key; | ||
23 | + | ||
24 | + public attr = { ...componentInitConfig }; | ||
25 | + | ||
26 | + public componentConfig: ConfigType = cloneDeep(ValueList2Config); | ||
27 | + | ||
28 | + public persetOption = cloneDeep(option); | ||
29 | + | ||
30 | + public option: PublicComponentOptions; | ||
31 | + | ||
32 | + constructor(option: PublicComponentOptions) { | ||
33 | + super(); | ||
34 | + this.option = { ...option }; | ||
35 | + } | ||
36 | +} |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentConfigFieldEnum } from '/@/views/visual/packages/enum'; | ||
3 | + import { useForm, BasicForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + import { option } from './config'; | ||
6 | + | ||
7 | + const [register, { getFieldsValue, setFieldsValue, resetFields }] = useForm({ | ||
8 | + schemas: [ | ||
9 | + { | ||
10 | + field: ComponentConfigFieldEnum.FONT_COLOR, | ||
11 | + label: '数值字体颜色', | ||
12 | + component: 'ColorPicker', | ||
13 | + changeEvent: 'update:value', | ||
14 | + valueField: 'value', | ||
15 | + defaultValue: option.fontColor, | ||
16 | + }, | ||
17 | + { | ||
18 | + field: ComponentConfigFieldEnum.UNIT, | ||
19 | + label: '数值单位', | ||
20 | + component: 'Input', | ||
21 | + defaultValue: option.unit, | ||
22 | + componentProps: { | ||
23 | + placeholder: '请输入数值单位', | ||
24 | + }, | ||
25 | + }, | ||
26 | + { | ||
27 | + field: ComponentConfigFieldEnum.ICON_COLOR, | ||
28 | + label: '图标颜色', | ||
29 | + component: 'ColorPicker', | ||
30 | + changeEvent: 'update:value', | ||
31 | + defaultValue: option.iconColor, | ||
32 | + }, | ||
33 | + { | ||
34 | + field: ComponentConfigFieldEnum.ICON, | ||
35 | + label: '图标', | ||
36 | + component: 'IconDrawer', | ||
37 | + changeEvent: 'update:value', | ||
38 | + valueField: 'value', | ||
39 | + defaultValue: option.icon, | ||
40 | + componentProps({ formModel }) { | ||
41 | + const color = formModel[ComponentConfigFieldEnum.ICON_COLOR]; | ||
42 | + return { | ||
43 | + color, | ||
44 | + }; | ||
45 | + }, | ||
46 | + }, | ||
47 | + { | ||
48 | + field: ComponentConfigFieldEnum.SHOW_DEVICE_NAME, | ||
49 | + label: '显示设备名称', | ||
50 | + component: 'Checkbox', | ||
51 | + defaultValue: option.showDeviceName, | ||
52 | + }, | ||
53 | + ], | ||
54 | + showActionButtonGroup: false, | ||
55 | + labelWidth: 120, | ||
56 | + baseColProps: { | ||
57 | + span: 12, | ||
58 | + }, | ||
59 | + }); | ||
60 | + | ||
61 | + const getFormValues = () => { | ||
62 | + return getFieldsValue(); | ||
63 | + }; | ||
64 | + | ||
65 | + const setFormValues = (data: Recordable) => { | ||
66 | + return setFieldsValue(data); | ||
67 | + }; | ||
68 | + | ||
69 | + defineExpose({ | ||
70 | + getFormValues, | ||
71 | + setFormValues, | ||
72 | + resetFormValues: resetFields, | ||
73 | + } as PublicFormInstaceType); | ||
74 | +</script> | ||
75 | + | ||
76 | +<template> | ||
77 | + <BasicForm @register="register" /> | ||
78 | +</template> |
1 | +<script lang="ts" setup> | ||
2 | + import { commonDataSourceSchemas } from '../../../config/common.config'; | ||
3 | + import { BasicForm, useForm } from '/@/components/Form'; | ||
4 | + import { PublicFormInstaceType } from '/@/views/visual/dataSourceBindPanel/index.type'; | ||
5 | + | ||
6 | + // const props = defineProps<{ | ||
7 | + // values: PublicComponentDataSourceProps; | ||
8 | + // }>(); | ||
9 | + | ||
10 | + const [register, { getFieldsValue, setFieldsValue, validate, resetFields }] = useForm({ | ||
11 | + labelWidth: 0, | ||
12 | + showActionButtonGroup: false, | ||
13 | + layout: 'horizontal', | ||
14 | + labelCol: { span: 0 }, | ||
15 | + schemas: commonDataSourceSchemas(), | ||
16 | + }); | ||
17 | + | ||
18 | + const getFormValues = () => { | ||
19 | + return getFieldsValue(); | ||
20 | + }; | ||
21 | + | ||
22 | + const setFormValues = (record: Recordable) => { | ||
23 | + return setFieldsValue(record); | ||
24 | + }; | ||
25 | + | ||
26 | + defineExpose({ | ||
27 | + getFormValues, | ||
28 | + setFormValues, | ||
29 | + validate, | ||
30 | + resetFormValues: resetFields, | ||
31 | + } as PublicFormInstaceType); | ||
32 | +</script> | ||
33 | + | ||
34 | +<template> | ||
35 | + <BasicForm @register="register" /> | ||
36 | +</template> |
1 | +import { useComponentKeys } from '/@/views/visual/packages/hook/useComponentKeys'; | ||
2 | +import { ConfigType, PackagesCategoryEnum } from '/@/views/visual/packages/index.type'; | ||
3 | + | ||
4 | +const componentKeys = useComponentKeys('ValueList2'); | ||
5 | +export const ValueList2Config: ConfigType = { | ||
6 | + ...componentKeys, | ||
7 | + title: '数值列表2', | ||
8 | + package: PackagesCategoryEnum.TEXT, | ||
9 | +}; |
1 | +<script lang="ts" setup> | ||
2 | + import { ComponentPropsConfigType, MultipleDataFetchUpdateFn } from '../../../index.type'; | ||
3 | + | ||
4 | + import { option } from './config'; | ||
5 | + import { useMultipleDataFetch } from '/@/views/visual/packages/hook/useSocket'; | ||
6 | + import { ref, unref } from 'vue'; | ||
7 | + import { SvgIcon } from '/@/components/Icon'; | ||
8 | + import { computed } from 'vue'; | ||
9 | + import { DeviceName } from '/@/views/visual/commonComponents/DeviceName'; | ||
10 | + | ||
11 | + const props = defineProps<{ | ||
12 | + config: ComponentPropsConfigType<typeof option>; | ||
13 | + }>(); | ||
14 | + | ||
15 | + const getDesign = computed(() => { | ||
16 | + const { persetOption = {}, option } = props.config; | ||
17 | + const { dataSource = [] } = option || {}; | ||
18 | + const { | ||
19 | + unit: persetUnit, | ||
20 | + fontColor: persetFontColor, | ||
21 | + icon: persetIcon, | ||
22 | + iconColor: persetIconColor, | ||
23 | + } = persetOption || {}; | ||
24 | + return { | ||
25 | + dataSource: dataSource.map((item) => { | ||
26 | + const { fontColor, icon, iconColor, unit } = item.componentInfo; | ||
27 | + const { attribute, attributeRename } = item; | ||
28 | + return { | ||
29 | + unit: unit ?? persetUnit, | ||
30 | + fontColor: fontColor ?? persetFontColor, | ||
31 | + icon: icon ?? persetIcon, | ||
32 | + iconColor: iconColor ?? persetIconColor, | ||
33 | + attribute: attribute || attributeRename, | ||
34 | + attributeRename, | ||
35 | + }; | ||
36 | + }), | ||
37 | + }; | ||
38 | + }); | ||
39 | + const svgList = ref<any>([ | ||
40 | + { | ||
41 | + value: 26.2, | ||
42 | + name: 'wendu', | ||
43 | + icon: 'zongfushe', | ||
44 | + unit: 'kw', | ||
45 | + iconColor: '#367BFF', | ||
46 | + fontColor: '#357CFB', | ||
47 | + }, | ||
48 | + { | ||
49 | + value: 53.7, | ||
50 | + name: 'shidu', | ||
51 | + icon: 'guangzhaoqiangdu', | ||
52 | + unit: '℃', | ||
53 | + iconColor: '#FFA000', | ||
54 | + fontColor: '#FFA000', | ||
55 | + }, | ||
56 | + ]); | ||
57 | + | ||
58 | + const updateFn: MultipleDataFetchUpdateFn = (message) => { | ||
59 | + const { data = {} } = message; | ||
60 | + const { dataSource } = unref(getDesign); | ||
61 | + svgList.value.length = 0; | ||
62 | + svgList.value = dataSource.map((item) => { | ||
63 | + const { icon, iconColor, unit, fontColor, attribute } = item || {}; | ||
64 | + const [latest] = data[attribute] || []; | ||
65 | + const [_timespan, value] = latest || []; | ||
66 | + return { | ||
67 | + value: Number(value), | ||
68 | + name: attribute, | ||
69 | + icon, | ||
70 | + unit, | ||
71 | + iconColor, | ||
72 | + fontColor, | ||
73 | + }; | ||
74 | + }); | ||
75 | + }; | ||
76 | + | ||
77 | + useMultipleDataFetch(props, updateFn); | ||
78 | +</script> | ||
79 | + | ||
80 | +<template> | ||
81 | + <main class="w-full h-full flex flex-col justify-evenly items-center"> | ||
82 | + <DeviceName :config="config" /> | ||
83 | + <div | ||
84 | + style="width: 86%" | ||
85 | + v-for="item in svgList" | ||
86 | + :key="item.id" | ||
87 | + class="flex justify-between items-center" | ||
88 | + > | ||
89 | + <div class="flex items-center"> | ||
90 | + <SvgIcon | ||
91 | + :name="item.icon!" | ||
92 | + prefix="iconfont" | ||
93 | + :size="45" | ||
94 | + :style="{ color: item.iconColor }" | ||
95 | + /> | ||
96 | + | ||
97 | + <div class="text-gray-500 text-lg truncate ml-6">{{ item.attribute || '温度' }}</div> | ||
98 | + </div> | ||
99 | + | ||
100 | + <h1 class="font-bold text-xl m-2 truncate" :style="{ color: item.fontColor }"> | ||
101 | + <span> {{ item.value || 0 }}</span> | ||
102 | + <span>{{ item.unit }} </span> | ||
103 | + </h1> | ||
104 | + </div> | ||
105 | + </main> | ||
106 | +</template> |
@@ -2,10 +2,18 @@ import { TextComponent1Config } from './TextComponent1'; | @@ -2,10 +2,18 @@ import { TextComponent1Config } from './TextComponent1'; | ||
2 | import { TextComponent2Config } from './TextComponent2'; | 2 | import { TextComponent2Config } from './TextComponent2'; |
3 | import { TextComponent3Config } from './TextComponent3'; | 3 | import { TextComponent3Config } from './TextComponent3'; |
4 | import { TextComponent4Config } from './TextComponent4'; | 4 | import { TextComponent4Config } from './TextComponent4'; |
5 | +import { SwitchSignalLightConfig } from './SwitchSignalLight'; | ||
6 | +// import { SwitchStatusConfig } from './SwitchStatus'; | ||
7 | +import { ValueList1Config } from './ValueList1'; | ||
8 | +// import { ValueList2Config } from './ValueList2'; | ||
5 | 9 | ||
6 | export const TextList = [ | 10 | export const TextList = [ |
7 | TextComponent1Config, | 11 | TextComponent1Config, |
8 | TextComponent2Config, | 12 | TextComponent2Config, |
9 | TextComponent3Config, | 13 | TextComponent3Config, |
10 | TextComponent4Config, | 14 | TextComponent4Config, |
15 | + ValueList1Config, | ||
16 | + // ValueList2Config, | ||
17 | + SwitchSignalLightConfig, | ||
18 | + // SwitchStatusConfig, | ||
11 | ]; | 19 | ]; |
@@ -3,12 +3,15 @@ export enum ComponentConfigFieldEnum { | @@ -3,12 +3,15 @@ export enum ComponentConfigFieldEnum { | ||
3 | UNIT = 'unit', | 3 | UNIT = 'unit', |
4 | POINTER_COLOR = 'pointerColor', | 4 | POINTER_COLOR = 'pointerColor', |
5 | INSTRUMENT_PANEL_COLOR = 'instrumentPanelColor', | 5 | INSTRUMENT_PANEL_COLOR = 'instrumentPanelColor', |
6 | + CONTROL_BAR_COLOR = 'controlBarColor', | ||
6 | // INSTRUMENT_PANEL_WIDTH = 'instrumentPanelWidth', | 7 | // INSTRUMENT_PANEL_WIDTH = 'instrumentPanelWidth', |
7 | 8 | ||
8 | PROGRESS_BAR_CIRCLE = 'progressBarCircle', | 9 | PROGRESS_BAR_CIRCLE = 'progressBarCircle', |
9 | 10 | ||
10 | ICON_COLOR = 'iconColor', | 11 | ICON_COLOR = 'iconColor', |
12 | + ICON_COLOR_CLOSE = 'iconColorClose', | ||
11 | ICON = 'icon', | 13 | ICON = 'icon', |
14 | + ICON_CLOSE = 'iconClose', | ||
12 | FIRST_PHASE_COLOR = 'firstPhaseColor', | 15 | FIRST_PHASE_COLOR = 'firstPhaseColor', |
13 | SECOND_PHASE_COLOR = 'secondPhaseColor', | 16 | SECOND_PHASE_COLOR = 'secondPhaseColor', |
14 | THIRD_PHASE_COLOR = 'thirdPhaseColor', | 17 | THIRD_PHASE_COLOR = 'thirdPhaseColor', |
@@ -23,4 +26,6 @@ export enum ComponentConfigFieldEnum { | @@ -23,4 +26,6 @@ export enum ComponentConfigFieldEnum { | ||
23 | WAVE_SECOND = 'waveSecond', | 26 | WAVE_SECOND = 'waveSecond', |
24 | WAVE_THIRD = 'waveThird', | 27 | WAVE_THIRD = 'waveThird', |
25 | BACKGROUND_COLOR = 'backgroundColor', | 28 | BACKGROUND_COLOR = 'backgroundColor', |
29 | + OPEN_COLOR = 'openColor', | ||
30 | + CLOSE_COLOR = 'closeColor', | ||
26 | } | 31 | } |
@@ -8,6 +8,7 @@ export const useGetComponentConfig = ( | @@ -8,6 +8,7 @@ export const useGetComponentConfig = ( | ||
8 | ): CreateComponentType => { | 8 | ): CreateComponentType => { |
9 | try { | 9 | try { |
10 | const config = createComponent({ key: transformComponentKey(key) } as ConfigType, options); | 10 | const config = createComponent({ key: transformComponentKey(key) } as ConfigType, options); |
11 | + if (!config) console.error(`can not get component config by component key (${key})`); | ||
11 | return config; | 12 | return config; |
12 | } catch (error) { | 13 | } catch (error) { |
13 | console.error(`can not get component config by component key (${key})`); | 14 | console.error(`can not get component config by component key (${key})`); |
@@ -20,6 +20,7 @@ export enum PackagesCategoryNameEnum { | @@ -20,6 +20,7 @@ export enum PackagesCategoryNameEnum { | ||
20 | CONTROL = '控制组件', | 20 | CONTROL = '控制组件', |
21 | MAP = '地图组件', | 21 | MAP = '地图组件', |
22 | FLOWMETER = '流量计', | 22 | FLOWMETER = '流量计', |
23 | + STATISTICS = '统计', | ||
23 | OTHER = '其他', | 24 | OTHER = '其他', |
24 | } | 25 | } |
25 | 26 | ||
@@ -33,6 +34,7 @@ export enum PackagesCategoryEnum { | @@ -33,6 +34,7 @@ export enum PackagesCategoryEnum { | ||
33 | CONTROL = 'CONTROL', | 34 | CONTROL = 'CONTROL', |
34 | MAP = 'MAP', | 35 | MAP = 'MAP', |
35 | FLOWMETER = 'FLOWMETER', | 36 | FLOWMETER = 'FLOWMETER', |
37 | + STATISTICS = 'STATISTICS', | ||
36 | OTHER = 'OTHER', | 38 | OTHER = 'OTHER', |
37 | } | 39 | } |
38 | 40 | ||
@@ -92,6 +94,7 @@ export interface PublicPresetOptions { | @@ -92,6 +94,7 @@ export interface PublicPresetOptions { | ||
92 | [ComponentConfigFieldEnum.UNIT]?: string; | 94 | [ComponentConfigFieldEnum.UNIT]?: string; |
93 | [ComponentConfigFieldEnum.ICON_COLOR]?: string; | 95 | [ComponentConfigFieldEnum.ICON_COLOR]?: string; |
94 | [ComponentConfigFieldEnum.ICON]?: string; | 96 | [ComponentConfigFieldEnum.ICON]?: string; |
97 | + [ComponentConfigFieldEnum.CONTROL_BAR_COLOR]?: string; | ||
95 | [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]?: boolean; | 98 | [ComponentConfigFieldEnum.SHOW_DEVICE_NAME]?: boolean; |
96 | [ComponentConfigFieldEnum.PROGRESS_BAR_CIRCLE]?: boolean; | 99 | [ComponentConfigFieldEnum.PROGRESS_BAR_CIRCLE]?: boolean; |
97 | [ComponentConfigFieldEnum.GRADIENT_INFO]?: ComponentInfoGradientInfoType[]; | 100 | [ComponentConfigFieldEnum.GRADIENT_INFO]?: ComponentInfoGradientInfoType[]; |
@@ -134,6 +137,7 @@ export interface PackagesType { | @@ -134,6 +137,7 @@ export interface PackagesType { | ||
134 | [PackagesCategoryEnum.CONTROL]: ConfigType[]; | 137 | [PackagesCategoryEnum.CONTROL]: ConfigType[]; |
135 | [PackagesCategoryEnum.MAP]: ConfigType[]; | 138 | [PackagesCategoryEnum.MAP]: ConfigType[]; |
136 | [PackagesCategoryEnum.FLOWMETER]: ConfigType[]; | 139 | [PackagesCategoryEnum.FLOWMETER]: ConfigType[]; |
140 | + [PackagesCategoryEnum.STATISTICS]: ConfigType[]; | ||
137 | [PackagesCategoryEnum.OTHER]: ConfigType[]; | 141 | [PackagesCategoryEnum.OTHER]: ConfigType[]; |
138 | } | 142 | } |
139 | 143 |
@@ -5,6 +5,7 @@ import { MapList } from './components/Map'; | @@ -5,6 +5,7 @@ import { MapList } from './components/Map'; | ||
5 | import { OtherList } from './components/Other'; | 5 | import { OtherList } from './components/Other'; |
6 | import { PictureList } from './components/Picture'; | 6 | import { PictureList } from './components/Picture'; |
7 | import { TextList } from './components/Text'; | 7 | import { TextList } from './components/Text'; |
8 | +import { STATISTICSList } from './components/Statistics'; | ||
8 | import { PackagesCategoryEnum, PackagesType } from './index.type'; | 9 | import { PackagesCategoryEnum, PackagesType } from './index.type'; |
9 | 10 | ||
10 | export const packageList: PackagesType = { | 11 | export const packageList: PackagesType = { |
@@ -14,5 +15,6 @@ export const packageList: PackagesType = { | @@ -14,5 +15,6 @@ export const packageList: PackagesType = { | ||
14 | [PackagesCategoryEnum.CONTROL]: ControlList, | 15 | [PackagesCategoryEnum.CONTROL]: ControlList, |
15 | [PackagesCategoryEnum.MAP]: MapList, | 16 | [PackagesCategoryEnum.MAP]: MapList, |
16 | [PackagesCategoryEnum.FLOWMETER]: FlowmeterList, | 17 | [PackagesCategoryEnum.FLOWMETER]: FlowmeterList, |
18 | + [PackagesCategoryEnum.STATISTICS]: STATISTICSList, | ||
17 | [PackagesCategoryEnum.OTHER]: OtherList, | 19 | [PackagesCategoryEnum.OTHER]: OtherList, |
18 | }; | 20 | }; |
@@ -58,6 +58,7 @@ export interface ComponentInfo { | @@ -58,6 +58,7 @@ export interface ComponentInfo { | ||
58 | instrumentPanelColor?: string; | 58 | instrumentPanelColor?: string; |
59 | // instrumentPanelWidth?: string | number; | 59 | // instrumentPanelWidth?: string | number; |
60 | progressBarCircle?: Boolean; | 60 | progressBarCircle?: Boolean; |
61 | + [key: string]: any; | ||
61 | } | 62 | } |
62 | 63 | ||
63 | export interface CustomCommand { | 64 | export interface CustomCommand { |