Commit 3fd01bf32adbe61ce4a0921e78fb55a67bd3224e

Authored by fengistao
1 parent 83fb89db

feat(frontend):场景联动新增页面编写

1 # Whether to open mock 1 # Whether to open mock
2 -VITE_USE_MOCK = false 2 +VITE_USE_MOCK = true
3 3
4 # public path 4 # public path
5 VITE_PUBLIC_PATH = / 5 VITE_PUBLIC_PATH = /
6 6
7 # Cross-domain proxy, you can configure multiple 7 # Cross-domain proxy, you can configure multiple
8 # Please note that no line breaks 8 # Please note that no line breaks
9 -VITE_PROXY = [["/api","http://localhost:8082/api"],["/upload","http://localhost:3300/upload"]] 9 +# If Use Online Mock,Address Is ["https://www.fastmock.site/mock/87187f474cb8128e88a517a04d77d80c/api"]
  10 +VITE_PROXY = [["/api","http://192.168.10.116:8082/api"],["/upload","http://localhost:3300/upload"]]
  11 +# VITE_PROXY = [["/api","https://www.fastmock.site/mock/87187f474cb8128e88a517a04d77d80c/api]",["/upload","http://localhost:3300/upload"]]
10 # VITE_PROXY=[["/api","https://vvbin.cn/test"]] 12 # VITE_PROXY=[["/api","https://vvbin.cn/test"]]
11 13
12 # Delete console 14 # Delete console
  1 +import {defHttp} from "/@/utils/http/axios";
  2 +import {
  3 + DeviceModel,
  4 + DeviceProfileModel,
  5 + DeviceProfileQueryParam,
  6 + DeviceQueryParam
  7 +} from "/@/api/device/model/deviceModel";
  8 +
  9 +enum DeviceManagerApi {
  10 + /**
  11 + * 设备URL
  12 + */
  13 + DEVICE_URL = "/device",
  14 + /**
  15 + * 设备配置URL
  16 + */
  17 + DEVICE_PROFILE_URL = "/deviceProfile"
  18 +}
  19 +
  20 +export const devicePage = (params: DeviceQueryParam) =>{
  21 + return defHttp.get<DeviceModel>({
  22 + url: DeviceManagerApi.DEVICE_URL,
  23 + params
  24 + });
  25 +}
  26 +
  27 +/**
  28 + * 分页查询设备配置页面
  29 + * @param params pageSize page name
  30 + */
  31 +export const deviceProfilePage = (params: DeviceProfileQueryParam) => {
  32 + return defHttp.get<DeviceProfileModel>({
  33 + url: DeviceManagerApi.DEVICE_PROFILE_URL,
  34 + params
  35 + });
  36 +}
  37 +/**
  38 + * 删除设备配置
  39 + * @param ids 删除的ids
  40 + */
  41 +export const deleteDeviceProfile = (ids: string[]) => {
  42 + return defHttp.delete({
  43 + url: DeviceManagerApi.DEVICE_PROFILE_URL,
  44 + data:{
  45 + ids:ids
  46 + }
  47 + })
  48 +}
  49 +
  50 +/**
  51 + * 删除设备
  52 + * @param ids 删除的ids
  53 + */
  54 +export const deleteDevice = (ids: string[]) => {
  55 + return defHttp.delete({
  56 + url: DeviceManagerApi.DEVICE_URL,
  57 + data:{
  58 + ids:ids
  59 + }
  60 + })
  61 +}
  1 +import {BasicPageParams} from "/@/api/model/baseModel";
  2 +export enum DeviceState {
  3 + INACTIVE='INACTIVE',
  4 + ONLINE='ONLINE',
  5 + OFFLINE='OFFLINE'
  6 +}
  7 +export enum DeviceTypeEnum{
  8 + GATEWAY='GATEWAY',
  9 + DIRECT_CONNECTION='DIRECT_CONNECTION',
  10 + SENSOR='SENSOR'
  11 +}
  12 +export type DeviceProfileQueryParam = BasicPageParams & DeviceProfileParam
  13 +export type DeviceQueryParam = BasicPageParams & DeviceParam
  14 +export type DeviceParam = {
  15 + name?:string,
  16 + deviceProfileId?:string
  17 +}
  18 +export type DeviceProfileParam = {
  19 + name?: string
  20 +}
  21 +
  22 +export interface DeviceModel{
  23 + id:string,
  24 + name:string,
  25 + deviceInfo:any,
  26 + activeTime:string,
  27 + deviceState:DeviceState,
  28 + profileId:string,
  29 + label:string,
  30 + lastConnectTime:string,
  31 + deviceType:DeviceTypeEnum
  32 +}
  33 +
  34 +export interface DeviceProfileModel{
  35 + id:string,
  36 + name:string,
  37 + transportType:string,
  38 + createTime:string,
  39 + description:string
  40 +}
@@ -4,40 +4,61 @@ @@ -4,40 +4,61 @@
4 <template #toolbar> 4 <template #toolbar>
5 <a-button type="primary" @click="handleCreate"> 新增设备 </a-button> 5 <a-button type="primary" @click="handleCreate"> 新增设备 </a-button>
6 </template> 6 </template>
7 - <template #config="{record}"> 7 + <template #config="{ record }">
8 <a-button type="link" class="ml-2" @click="showData(record)"> 查看配置 </a-button> 8 <a-button type="link" class="ml-2" @click="showData(record)"> 查看配置 </a-button>
9 </template> 9 </template>
10 - <template #deviceProfile="{record}">  
11 - <a-button type="link" class="ml-2" @click="goDeviceProfile"> {{record.deviceProfile.name}} </a-button> 10 + <template #deviceProfile="{ record }">
  11 + <a-button type="link" class="ml-2" @click="goDeviceProfile">
  12 + {{ record.deviceProfile.name }}
  13 + </a-button>
12 </template> 14 </template>
13 - <template #deviceType = "{record}"> 15 + <template #deviceType="{ record }">
14 <Tag color="success" class="ml-2"> 16 <Tag color="success" class="ml-2">
15 - {{record.deviceType==DeviceTypeEnum.GATEWAY ?'网关设备':  
16 - record.deviceType==DeviceTypeEnum.DIRECT_CONNECTION ?'直连设备':'网关子设备'}} 17 + {{
  18 + record.deviceType == DeviceTypeEnum.GATEWAY
  19 + ? '网关设备'
  20 + : record.deviceType == DeviceTypeEnum.DIRECT_CONNECTION
  21 + ? '直连设备'
  22 + : '网关子设备'
  23 + }}
17 </Tag> 24 </Tag>
18 </template> 25 </template>
19 - <template #deviceState = "{record}">  
20 - <Tag :color="record.deviceState==DeviceState.INACTIVE?'warning':record.deviceState==DeviceState.ONLINE?'success':'error'" class="ml-2">  
21 - {{record.deviceState==DeviceState.INACTIVE ?'待激活':  
22 - record.deviceState==DeviceState.ONLINE ?'在线':'离线'}} 26 + <template #deviceState="{ record }">
  27 + <Tag
  28 + :color="
  29 + record.deviceState == DeviceState.INACTIVE
  30 + ? 'warning'
  31 + : record.deviceState == DeviceState.ONLINE
  32 + ? 'success'
  33 + : 'error'
  34 + "
  35 + class="ml-2"
  36 + >
  37 + {{
  38 + record.deviceState == DeviceState.INACTIVE
  39 + ? '待激活'
  40 + : record.deviceState == DeviceState.ONLINE
  41 + ? '在线'
  42 + : '离线'
  43 + }}
23 </Tag> 44 </Tag>
24 </template> 45 </template>
25 <template #action="{ record }"> 46 <template #action="{ record }">
26 <TableAction 47 <TableAction
27 :actions="[ 48 :actions="[
28 { 49 {
29 - label:'编辑', 50 + label: '编辑',
30 icon: 'clarity:note-edit-line', 51 icon: 'clarity:note-edit-line',
31 onClick: handleEdit.bind(null, record), 52 onClick: handleEdit.bind(null, record),
32 }, 53 },
33 { 54 {
34 - label:'删除', 55 + label: '删除',
35 icon: 'ant-design:delete-outlined', 56 icon: 'ant-design:delete-outlined',
36 color: 'error', 57 color: 'error',
37 popConfirm: { 58 popConfirm: {
38 title: '是否确认删除', 59 title: '是否确认删除',
39 confirm: handleDelete.bind(null, record), 60 confirm: handleDelete.bind(null, record),
40 - } 61 + },
41 }, 62 },
42 ]" 63 ]"
43 /> 64 />
@@ -47,93 +68,93 @@ @@ -47,93 +68,93 @@
47 </div> 68 </div>
48 </template> 69 </template>
49 <script lang="ts"> 70 <script lang="ts">
50 -import { defineComponent,h} from 'vue';  
51 -import {DeviceState, DeviceTypeEnum} from "/@/api/device/model/deviceModel";  
52 -import { BasicTable, useTable, TableAction } from '/@/components/Table';  
53 -import { useDrawer } from '/@/components/Drawer';  
54 -import ConfigDrawer from './DeviceDrawer.vue';  
55 -import { columns, searchFormSchema } from './config.data';  
56 -import {Modal, Tag} from 'ant-design-vue';  
57 -import { CodeEditor,JsonPreview } from '/@/components/CodeEditor';  
58 -import {useMessage} from "/@/hooks/web/useMessage";  
59 -import {deleteDevice, devicePage} from "/@/api/device/deviceManager";  
60 -import {PageEnum} from "/@/enums/pageEnum";  
61 -import {useGo} from "/@/hooks/web/usePage"; 71 + import { defineComponent, h } from 'vue';
  72 + import { DeviceState, DeviceTypeEnum } from '/@/api/device/model/deviceModel';
  73 + import { BasicTable, useTable, TableAction } from '/@/components/Table';
  74 + import { useDrawer } from '/@/components/Drawer';
  75 + import ConfigDrawer from './DeviceDrawer.vue';
  76 + import { columns, searchFormSchema } from './config.data';
  77 + import { Modal, Tag } from 'ant-design-vue';
  78 + import { CodeEditor, JsonPreview } from '/@/components/CodeEditor';
  79 + import { useMessage } from '/@/hooks/web/useMessage';
  80 + import { deleteDevice, devicePage } from '/@/api/device/deviceManager';
  81 + import { PageEnum } from '/@/enums/pageEnum';
  82 + import { useGo } from '/@/hooks/web/usePage';
62 83
63 -export default defineComponent({  
64 - name: 'DeviceManagement',  
65 - components: { BasicTable, ConfigDrawer, TableAction ,CodeEditor,Tag},  
66 - setup() {  
67 - const [registerDrawer, { openDrawer }] = useDrawer();  
68 - const {createMessage} = useMessage();  
69 - const go = useGo();  
70 - const [registerTable, { reload }] = useTable({  
71 - title: '设备列表',  
72 - api: devicePage,  
73 - columns,  
74 - formConfig: {  
75 - labelWidth: 120,  
76 - schemas: searchFormSchema,  
77 - },  
78 - useSearchForm: true,  
79 - showTableSetting: true,  
80 - bordered: true,  
81 - showIndexColumn: false,  
82 - actionColumn: {  
83 - width: 180,  
84 - title: '操作',  
85 - dataIndex: 'action',  
86 - slots: { customRender: 'action' },  
87 - fixed: undefined,  
88 - },  
89 - });  
90 -  
91 - function handleCreate() {  
92 - openDrawer(true, {  
93 - isUpdate: false, 84 + export default defineComponent({
  85 + name: 'DeviceManagement',
  86 + components: { BasicTable, ConfigDrawer, TableAction, CodeEditor, Tag },
  87 + setup() {
  88 + const [registerDrawer, { openDrawer }] = useDrawer();
  89 + const { createMessage } = useMessage();
  90 + const go = useGo();
  91 + const [registerTable, { reload }] = useTable({
  92 + title: '设备列表',
  93 + api: devicePage,
  94 + columns,
  95 + formConfig: {
  96 + labelWidth: 120,
  97 + schemas: searchFormSchema,
  98 + },
  99 + useSearchForm: true,
  100 + showTableSetting: true,
  101 + bordered: true,
  102 + showIndexColumn: false,
  103 + actionColumn: {
  104 + width: 180,
  105 + title: '操作',
  106 + dataIndex: 'action',
  107 + slots: { customRender: 'action' },
  108 + fixed: undefined,
  109 + },
94 }); 110 });
95 - }  
96 111
97 - function handleEdit(record: Recordable) {  
98 - openDrawer(true, {  
99 - record,  
100 - isUpdate: true,  
101 - });  
102 - } 112 + function handleCreate() {
  113 + openDrawer(true, {
  114 + isUpdate: false,
  115 + });
  116 + }
103 117
104 - function handleDelete(record: Recordable) {  
105 - let ids = [record.id];  
106 - deleteDevice(ids).then(()=>{  
107 - createMessage.success("删除设备成功")  
108 - handleSuccess()  
109 - });  
110 - } 118 + function handleEdit(record: Recordable) {
  119 + openDrawer(true, {
  120 + record,
  121 + isUpdate: true,
  122 + });
  123 + }
111 124
112 - function handleSuccess() {  
113 - reload();  
114 - }  
115 - function showData(record: Recordable){  
116 - Modal.info({  
117 - title: '当前配置',  
118 - width:480,  
119 - content: h(JsonPreview, { data: JSON.parse(JSON.stringify(record.deviceInfo)) }),  
120 - });  
121 - }  
122 - function goDeviceProfile(){  
123 - go(PageEnum.DEVICE_PROFILE)  
124 - }  
125 - return {  
126 - registerTable,  
127 - registerDrawer,  
128 - showData,  
129 - handleCreate,  
130 - handleEdit,  
131 - handleDelete,  
132 - handleSuccess,  
133 - goDeviceProfile,  
134 - DeviceTypeEnum,  
135 - DeviceState  
136 - };  
137 - },  
138 -}); 125 + function handleDelete(record: Recordable) {
  126 + let ids = [record.id];
  127 + deleteDevice(ids).then(() => {
  128 + createMessage.success('删除设备成功');
  129 + handleSuccess();
  130 + });
  131 + }
  132 +
  133 + function handleSuccess() {
  134 + reload();
  135 + }
  136 + function showData(record: Recordable) {
  137 + Modal.info({
  138 + title: '当前配置',
  139 + width: 480,
  140 + content: h(JsonPreview, { data: JSON.parse(JSON.stringify(record.deviceInfo)) }),
  141 + });
  142 + }
  143 + function goDeviceProfile() {
  144 + go(PageEnum.DEVICE_PROFILE);
  145 + }
  146 + return {
  147 + registerTable,
  148 + registerDrawer,
  149 + showData,
  150 + handleCreate,
  151 + handleEdit,
  152 + handleDelete,
  153 + handleSuccess,
  154 + goDeviceProfile,
  155 + DeviceTypeEnum,
  156 + DeviceState,
  157 + };
  158 + },
  159 + });
139 </script> 160 </script>
  1 +<template>
  2 + <BasicDrawer
  3 + v-bind="$attrs"
  4 + @register="registerDrawer"
  5 + showFooter
  6 + :title="getTitle"
  7 + width="500px"
  8 + @ok="handleSubmit"
  9 + >
  10 + <BasicForm @register="registerForm"/>
  11 + </BasicDrawer>
  12 +</template>
  13 +<script lang="ts">
  14 + import { defineComponent, ref, computed, unref } from 'vue';
  15 + import { BasicForm, useForm } from '/@/components/Form';
  16 + import { formSchema } from './config.data';
  17 + import { BasicDrawer, useDrawerInner } from '/@/components/Drawer';
  18 + import {saveOrEditMessageConfig} from "/@/api/message/config";
  19 + import {useMessage} from "/@/hooks/web/useMessage";
  20 +
  21 + export default defineComponent({
  22 + name: 'ConfigDrawer',
  23 + components: { BasicDrawer, BasicForm },
  24 + emits: ['success', 'register'],
  25 + setup(_, { emit }) {
  26 + const isUpdate = ref(true);
  27 +
  28 + const [registerForm, { validate,setFieldsValue,resetFields }] = useForm({
  29 + labelWidth: 120,
  30 + schemas: formSchema,
  31 + showActionButtonGroup: false,
  32 + });
  33 +
  34 + const [registerDrawer, { setDrawerProps, closeDrawer }] = useDrawerInner(async (data) => {
  35 + await resetFields();
  36 + setDrawerProps({ confirmLoading: false });
  37 + isUpdate.value = !!data?.isUpdate;
  38 + if (unref(isUpdate)) {
  39 + const config = data.record.config;
  40 + for (const key in config){
  41 + Reflect.set(data.record, key+'', config[key]);
  42 + }
  43 + await setFieldsValue({
  44 + ...data.record,
  45 + });
  46 + }
  47 + });
  48 +
  49 + const getTitle = computed(() => (!unref(isUpdate) ? '新增消息配置' : '编辑消息配置'));
  50 +
  51 + async function handleSubmit() {
  52 + try {
  53 + const values = await validate();
  54 + const { createMessage } = useMessage();
  55 + setDrawerProps({ confirmLoading: true });
  56 + let config={};
  57 + if(values.messageType === 'PHONE_MESSAGE'){
  58 + config ={
  59 + "accessKeyId":values.accessKeyId,
  60 + "accessKeySecret":values.accessKeySecret,
  61 + }
  62 + }else if(values.messageType === 'EMAIL_MESSAGE'){
  63 + config ={
  64 + "host":values.host,
  65 + "port":values.port,
  66 + "username":values.username,
  67 + "password":values.password,
  68 + }
  69 + }
  70 + Reflect.set(values, 'config', config);
  71 + let saveMessage = "添加成功";
  72 + let updateMessage = "修改成功";
  73 + await saveOrEditMessageConfig(values, unref(isUpdate));
  74 + closeDrawer();
  75 + emit('success');
  76 + createMessage.success(unref(isUpdate)?updateMessage:saveMessage);
  77 + } finally {
  78 + setDrawerProps({ confirmLoading: false });
  79 + }
  80 + }
  81 +
  82 + return {
  83 + registerDrawer,
  84 + registerForm,
  85 + getTitle,
  86 + handleSubmit,
  87 + };
  88 + },
  89 + });
  90 +</script>
  1 +import { BasicColumn } from '/@/components/Table';
  2 +import { FormSchema } from '/@/components/Table';
  3 +import { findDictItemByCode } from '/@/api/system/dict';
  4 +
  5 +export const columns: BasicColumn[] = [
  6 + {
  7 + title: '场景联动名称',
  8 + },
  9 + {
  10 + title: '触发方式',
  11 + // dataIndex: 'name',
  12 + width: 200,
  13 + },
  14 + {
  15 + title: '状态',
  16 + // dataIndex: 'deviceType',
  17 + width: 200,
  18 + // slots: { customRender: 'deviceType' },
  19 + },
  20 + {
  21 + title: '描述',
  22 + // dataIndex: 'deviceProfile.name',
  23 + width: 180,
  24 + // slots: { customRender: 'deviceProfile' },
  25 + },
  26 +];
  27 +
  28 +export const formSchema: FormSchema[] = [
  29 + {
  30 + field: 'configName',
  31 + label: '场景联动名称',
  32 + required: true,
  33 + component: 'Input',
  34 + },
  35 + {
  36 + field: 'messageType',
  37 + label: '所属组织',
  38 + required: true,
  39 + component: 'ApiSelect',
  40 + componentProps: {
  41 + api: findDictItemByCode,
  42 + params: {
  43 + dictCode: 'message_type',
  44 + },
  45 + labelField: 'itemText',
  46 + valueField: 'itemValue',
  47 + },
  48 + },
  49 + {
  50 + field: 'no1',
  51 + label: '触发器',
  52 + required: true,
  53 + component: 'Input',
  54 + },
  55 + {
  56 + field: 'no2',
  57 + label: '执行条件',
  58 + required: true,
  59 + component: 'Input',
  60 + },
  61 + {
  62 + field: 'no3',
  63 + label: '执行动作',
  64 + required: true,
  65 + component: 'Input',
  66 + },
  67 +];
  1 +<template>
  2 + <div>
  3 + <BasicTable @register="registerTable">
  4 + <template #toolbar>
  5 + <a-button type="primary" @click="handleCreate"> 新增设备 </a-button>
  6 + </template>
  7 + <template #config="{ record }">
  8 + <a-button type="link" class="ml-2" @click="showData(record)"> 查看配置 </a-button>
  9 + </template>
  10 + <template #deviceProfile="{ record }">
  11 + <a-button type="link" class="ml-2" @click="goDeviceProfile">
  12 + {{ record.deviceProfile.name }}
  13 + </a-button>
  14 + </template>
  15 + <template #deviceType="{ record }">
  16 + <Tag color="success" class="ml-2">
  17 + {{
  18 + record.deviceType == DeviceTypeEnum.GATEWAY
  19 + ? '网关设备'
  20 + : record.deviceType == DeviceTypeEnum.DIRECT_CONNECTION
  21 + ? '直连设备'
  22 + : '网关子设备'
  23 + }}
  24 + </Tag>
  25 + </template>
  26 + <template #deviceState="{ record }">
  27 + <Tag
  28 + :color="
  29 + record.deviceState == DeviceState.INACTIVE
  30 + ? 'warning'
  31 + : record.deviceState == DeviceState.ONLINE
  32 + ? 'success'
  33 + : 'error'
  34 + "
  35 + class="ml-2"
  36 + >
  37 + {{
  38 + record.deviceState == DeviceState.INACTIVE
  39 + ? '待激活'
  40 + : record.deviceState == DeviceState.ONLINE
  41 + ? '在线'
  42 + : '离线'
  43 + }}
  44 + </Tag>
  45 + </template>
  46 + <template #action="{ record }">
  47 + <TableAction
  48 + :actions="[
  49 + {
  50 + label: '编辑',
  51 + icon: 'clarity:note-edit-line',
  52 + onClick: handleEdit.bind(null, record),
  53 + },
  54 + {
  55 + label: '删除',
  56 + icon: 'ant-design:delete-outlined',
  57 + color: 'error',
  58 + popConfirm: {
  59 + title: '是否确认删除',
  60 + confirm: handleDelete.bind(null, record),
  61 + },
  62 + },
  63 + ]"
  64 + />
  65 + </template>
  66 + </BasicTable>
  67 + <RuleEngineDrawer @register="registerDrawer" @success="handleSuccess" />
  68 + </div>
  69 +</template>
  70 +<script lang="ts">
  71 + import { defineComponent, h } from 'vue';
  72 + import { DeviceState, DeviceTypeEnum } from '/@/api/device/model/deviceModel';
  73 + import { BasicTable, useTable, TableAction } from '/@/components/Table';
  74 + import { useDrawer } from '/@/components/Drawer';
  75 + import RuleEngineDrawer from './RuleEngineDrawer.vue';
  76 + import { columns } from './config.data';
  77 + import { Modal, Tag } from 'ant-design-vue';
  78 + import { useMessage } from '/@/hooks/web/useMessage';
  79 + import { deleteDevice, devicePage } from '/@/api/device/deviceManager';
  80 + import { PageEnum } from '/@/enums/pageEnum';
  81 + import { useGo } from '/@/hooks/web/usePage';
  82 +
  83 + export default defineComponent({
  84 + name: 'DeviceManagement',
  85 + components: { BasicTable, RuleEngineDrawer, TableAction, Tag },
  86 + setup() {
  87 + const [registerDrawer, { openDrawer }] = useDrawer();
  88 + const { createMessage } = useMessage();
  89 + const go = useGo();
  90 + const [registerTable, { reload }] = useTable({
  91 + title: '设备列表',
  92 + api: devicePage,
  93 + columns,
  94 + formConfig: {
  95 + labelWidth: 120,
  96 + schemas: searchFormSchema,
  97 + },
  98 + useSearchForm: true,
  99 + showTableSetting: true,
  100 + bordered: true,
  101 + showIndexColumn: false,
  102 + actionColumn: {
  103 + width: 180,
  104 + title: '操作',
  105 + dataIndex: 'action',
  106 + slots: { customRender: 'action' },
  107 + fixed: undefined,
  108 + },
  109 + });
  110 +
  111 + function handleCreate() {
  112 + openDrawer(true, {
  113 + isUpdate: false,
  114 + });
  115 + }
  116 +
  117 + function handleEdit(record: Recordable) {
  118 + openDrawer(true, {
  119 + record,
  120 + isUpdate: true,
  121 + });
  122 + }
  123 +
  124 + function handleDelete(record: Recordable) {
  125 + let ids = [record.id];
  126 + deleteDevice(ids).then(() => {
  127 + createMessage.success('删除设备成功');
  128 + handleSuccess();
  129 + });
  130 + }
  131 +
  132 + function handleSuccess() {
  133 + reload();
  134 + }
  135 + function showData(record: Recordable) {
  136 + Modal.info({
  137 + title: '当前配置',
  138 + width: 480,
  139 + content: h(JsonPreview, { data: JSON.parse(JSON.stringify(record.deviceInfo)) }),
  140 + });
  141 + }
  142 + function goDeviceProfile() {
  143 + go(PageEnum.DEVICE_PROFILE);
  144 + }
  145 + return {
  146 + registerTable,
  147 + registerDrawer,
  148 + showData,
  149 + handleCreate,
  150 + handleEdit,
  151 + handleDelete,
  152 + handleSuccess,
  153 + goDeviceProfile,
  154 + DeviceTypeEnum,
  155 + DeviceState,
  156 + };
  157 + },
  158 + });
  159 +</script>
  1 +<template>
  2 + <CollapseContainer title="执行条件" style="background-color: #eeeeee">
  3 + <BasicForm
  4 + style="display: inline-block"
  5 + layout="inline"
  6 + :actionColOptions="{ span: 24 }"
  7 + :labelWidth="100"
  8 + :showResetButton="false"
  9 + :showSubmitButton="false"
  10 + autoFocusFirstItem
  11 + labelAlign="left"
  12 + @register="register"
  13 + >
  14 + <template #add="{ field }">
  15 + <br />
  16 + <Button
  17 + style="margin-left: -575px; margin-top: 15px"
  18 + v-if="Number(field) === 0"
  19 + @click="add"
  20 + type="primary"
  21 + >+新增执行条件</Button
  22 + >
  23 + <br />
  24 + <Button
  25 + style="margin-left: -415px; margin-top: -15px"
  26 + v-if="field > 0"
  27 + @click="add"
  28 + type="primary"
  29 + >+新增执行条件</Button
  30 + >
  31 + <Button style="margin-left: 10px" v-if="field > 0" @click="del(field)" type="primary"
  32 + >删除</Button
  33 + >
  34 + <br />
  35 + </template>
  36 + </BasicForm>
  37 + </CollapseContainer>
  38 +</template>
  39 +<script lang="ts">
  40 + import { defineComponent, ref } from 'vue';
  41 + import { CollapseContainer } from '/@/components/Container/index';
  42 + import { BasicForm, useForm } from '/@/components/Form/index';
  43 + import { Input } from 'ant-design-vue';
  44 + import { Button } from '/@/components/Button';
  45 + import { useConditionDrawerSchema } from '../config.d';
  46 +
  47 + export default defineComponent({
  48 + components: { CollapseContainer, BasicForm, [Input.name]: Input, Button },
  49 + setup() {
  50 + const formData = ref([]);
  51 + const [register, { appendSchemaByField, removeSchemaByFiled, validate }] = useForm({
  52 + labelWidth: 100,
  53 + schemas: useConditionDrawerSchema,
  54 + actionColOptions: { span: 24 },
  55 + });
  56 +
  57 + async function handleSubmit() {
  58 + try {
  59 + const data = await validate();
  60 + formData.value = data;
  61 + console.log(formData.value);
  62 + } catch (e) {
  63 + console.log(e);
  64 + }
  65 + }
  66 + const n = ref(1);
  67 + function add() {
  68 + appendSchemaByField(
  69 + {
  70 + field: `field${n.value}a`,
  71 + component: 'ApiSelect',
  72 + label: '',
  73 + componentProps: {
  74 + placeholder: '请选择',
  75 + },
  76 + colProps: {
  77 + span: 8,
  78 + offset: 1,
  79 + },
  80 + required: true,
  81 + },
  82 + ''
  83 + );
  84 + appendSchemaByField(
  85 + {
  86 + field: `field${n.value}b`,
  87 + component: 'Input',
  88 + label: '',
  89 + componentProps: {
  90 + placeholder: '请输入',
  91 + },
  92 + colProps: {
  93 + span: 8,
  94 + offset: 1,
  95 + },
  96 + required: true,
  97 + },
  98 + ''
  99 + );
  100 + appendSchemaByField(
  101 + {
  102 + field: `field${n.value}c`,
  103 + component: 'ApiSelect',
  104 + label: '',
  105 + componentProps: {
  106 + placeholder: '请选择',
  107 + },
  108 + colProps: {
  109 + span: 8,
  110 + },
  111 + required: true,
  112 + },
  113 + ''
  114 + );
  115 + appendSchemaByField(
  116 + {
  117 + field: `field${n.value}d`,
  118 + component: 'ApiSelect',
  119 + label: '',
  120 + componentProps: {
  121 + placeholder: '请选择',
  122 + },
  123 + colProps: {
  124 + span: 8,
  125 + },
  126 + required: true,
  127 + },
  128 + ''
  129 + );
  130 + appendSchemaByField(
  131 + {
  132 + field: `field${n.value}e`,
  133 + component: 'ApiSelect',
  134 + label: '',
  135 + componentProps: {
  136 + placeholder: '请选择',
  137 + },
  138 + colProps: {
  139 + span: 8,
  140 + },
  141 + required: true,
  142 + },
  143 + ''
  144 + );
  145 + appendSchemaByField(
  146 + {
  147 + field: `field${n.value}f`,
  148 + component: 'Input',
  149 + label: '',
  150 + componentProps: {
  151 + placeholder: '请输入',
  152 + },
  153 + colProps: {
  154 + span: 8,
  155 + },
  156 + required: true,
  157 + },
  158 + ''
  159 + );
  160 + appendSchemaByField(
  161 + {
  162 + field: `${n.value}`,
  163 + component: 'ApiSelect',
  164 + label: ' ',
  165 + colProps: {
  166 + span: 8,
  167 + offset: 1,
  168 + },
  169 + slot: 'add',
  170 + },
  171 + ''
  172 + );
  173 + n.value++;
  174 + }
  175 +
  176 + function del(field) {
  177 + removeSchemaByFiled([
  178 + `field${field}a`,
  179 + `field${field}b`,
  180 + `field${field}c`,
  181 + `field${field}d`,
  182 + `field${field}e`,
  183 + `field${field}f`,
  184 + `field${field}g`,
  185 + `field${field}h`,
  186 + `${field}`,
  187 + ]);
  188 + n.value--;
  189 + }
  190 +
  191 + return { register, handleSubmit, add, del, formData };
  192 + },
  193 + });
  194 +</script>
  1 +<template>
  2 + <CollapseContainer title="执行动作" style="background-color: #eeeeee">
  3 + <BasicForm
  4 + style="display: inline-block"
  5 + layout="inline"
  6 + :actionColOptions="{ span: 24 }"
  7 + :labelWidth="100"
  8 + :showResetButton="false"
  9 + :showSubmitButton="false"
  10 + autoFocusFirstItem
  11 + labelAlign="left"
  12 + @register="register"
  13 + >
  14 + <template #add="{ field }">
  15 + <br />
  16 + <Button
  17 + style="margin-left: -575px; margin-top: 15px"
  18 + v-if="Number(field) === 0"
  19 + @click="add"
  20 + type="primary"
  21 + >+新增执行动作</Button
  22 + >
  23 + <br />
  24 + <Button
  25 + style="margin-left: -415px; margin-top: -15px"
  26 + v-if="field > 0"
  27 + @click="add"
  28 + type="primary"
  29 + >+新增执行动作</Button
  30 + >
  31 + <Button style="margin-left: 10px" v-if="field > 0" @click="del(field)" type="primary"
  32 + >删除</Button
  33 + >
  34 + <br />
  35 + </template>
  36 + </BasicForm>
  37 + </CollapseContainer>
  38 +</template>
  39 +<script lang="ts">
  40 + import { defineComponent, ref } from 'vue';
  41 + import { CollapseContainer } from '/@/components/Container/index';
  42 + import { BasicForm, useForm } from '/@/components/Form/index';
  43 + import { Input } from 'ant-design-vue';
  44 + import { Button } from '/@/components/Button';
  45 + import { useActionDrawerSchema } from '../config.d';
  46 +
  47 + export default defineComponent({
  48 + components: { CollapseContainer, BasicForm, [Input.name]: Input, Button },
  49 + setup() {
  50 + const formData = ref([]);
  51 + const [register, { appendSchemaByField, removeSchemaByFiled, validate }] = useForm({
  52 + labelWidth: 100,
  53 + schemas: useActionDrawerSchema,
  54 + actionColOptions: { span: 24 },
  55 + });
  56 +
  57 + async function handleSubmit() {
  58 + try {
  59 + const data = await validate();
  60 + formData.value = data;
  61 + console.log(formData.value);
  62 + } catch (e) {
  63 + console.log(e);
  64 + }
  65 + }
  66 + const n = ref(1);
  67 + function add() {
  68 + appendSchemaByField(
  69 + {
  70 + field: `field${n.value}a`,
  71 + component: 'ApiSelect',
  72 + label: '',
  73 + componentProps: {
  74 + placeholder: '请选择',
  75 + },
  76 + colProps: {
  77 + span: 8,
  78 + offset: 1,
  79 + },
  80 + required: true,
  81 + },
  82 + ''
  83 + );
  84 + appendSchemaByField(
  85 + {
  86 + field: `field${n.value}b`,
  87 + component: 'Input',
  88 + label: '',
  89 + componentProps: {
  90 + placeholder: '请输入',
  91 + },
  92 + colProps: {
  93 + span: 8,
  94 + offset: 1,
  95 + },
  96 + required: true,
  97 + },
  98 + ''
  99 + );
  100 + appendSchemaByField(
  101 + {
  102 + field: `field${n.value}c`,
  103 + component: 'ApiSelect',
  104 + label: '',
  105 + componentProps: {
  106 + placeholder: '请选择',
  107 + },
  108 + colProps: {
  109 + span: 8,
  110 + },
  111 + required: true,
  112 + },
  113 + ''
  114 + );
  115 + appendSchemaByField(
  116 + {
  117 + field: `field${n.value}d`,
  118 + component: 'ApiSelect',
  119 + label: '',
  120 + componentProps: {
  121 + placeholder: '请选择',
  122 + },
  123 + colProps: {
  124 + span: 8,
  125 + },
  126 + required: true,
  127 + },
  128 + ''
  129 + );
  130 + appendSchemaByField(
  131 + {
  132 + field: `field${n.value}e`,
  133 + component: 'ApiSelect',
  134 + label: '',
  135 + componentProps: {
  136 + placeholder: '请选择',
  137 + },
  138 + colProps: {
  139 + span: 8,
  140 + },
  141 + required: true,
  142 + },
  143 + ''
  144 + );
  145 + appendSchemaByField(
  146 + {
  147 + field: `field${n.value}f`,
  148 + component: 'Input',
  149 + label: '',
  150 + componentProps: {
  151 + placeholder: '请输入',
  152 + },
  153 + colProps: {
  154 + span: 8,
  155 + },
  156 + required: true,
  157 + },
  158 + ''
  159 + );
  160 + appendSchemaByField(
  161 + {
  162 + field: `${n.value}`,
  163 + component: 'ApiSelect',
  164 + label: ' ',
  165 + colProps: {
  166 + span: 8,
  167 + offset: 1,
  168 + },
  169 + slot: 'add',
  170 + },
  171 + ''
  172 + );
  173 + n.value++;
  174 + }
  175 +
  176 + function del(field) {
  177 + removeSchemaByFiled([
  178 + `field${field}a`,
  179 + `field${field}b`,
  180 + `field${field}c`,
  181 + `field${field}d`,
  182 + `field${field}e`,
  183 + `field${field}f`,
  184 + `field${field}g`,
  185 + `field${field}h`,
  186 + `${field}`,
  187 + ]);
  188 + n.value--;
  189 + }
  190 +
  191 + return { register, handleSubmit, add, del, formData };
  192 + },
  193 + });
  194 +</script>
  1 +<template>
  2 + <CollapseContainer title="触发器" style="background-color: #eeeeee">
  3 + <BasicForm
  4 + style="display: inline-block"
  5 + layout="inline"
  6 + :actionColOptions="{ span: 24 }"
  7 + :labelWidth="100"
  8 + :showResetButton="false"
  9 + :showSubmitButton="false"
  10 + autoFocusFirstItem
  11 + labelAlign="left"
  12 + @register="register"
  13 + >
  14 + <template #add="{ field }">
  15 + <Button
  16 + style="margin-left: -575px; margin-top: 40px"
  17 + v-if="Number(field) === 0"
  18 + @click="add"
  19 + type="primary"
  20 + >+新增触发器</Button
  21 + >
  22 + <Button
  23 + style="margin-left: 10px"
  24 + v-if="Number(field) === 0"
  25 + @click="handleSubmit"
  26 + type="primary"
  27 + >保存</Button
  28 + >
  29 + <br />
  30 + <Button
  31 + style="margin-left: -456px; margin-top: 20px"
  32 + v-if="field > 0"
  33 + @click="add"
  34 + type="primary"
  35 + >+新增触发器</Button
  36 + >
  37 + <Button style="margin-left: 10px" v-if="field > 0" @click="handleSubmit" type="primary"
  38 + >保存</Button
  39 + >
  40 + <Button style="margin-left: 10px" v-if="field > 0" @click="del(field)" type="primary"
  41 + >删除</Button
  42 + >
  43 + <br />
  44 + </template>
  45 + </BasicForm>
  46 + </CollapseContainer>
  47 +</template>
  48 +<script lang="ts">
  49 + import { defineComponent, ref } from 'vue';
  50 + import { CollapseContainer } from '/@/components/Container/index';
  51 + import { BasicForm, useForm } from '/@/components/Form/index';
  52 + import { Input } from 'ant-design-vue';
  53 + import { Button } from '/@/components/Button';
  54 + import { useTriggerDrawerSchema } from '../config.d';
  55 +
  56 + export default defineComponent({
  57 + components: { CollapseContainer, BasicForm, [Input.name]: Input, Button },
  58 + setup(_, { emit }) {
  59 + const [register, { appendSchemaByField, removeSchemaByFiled, getFieldsValue }] = useForm({
  60 + labelWidth: 100,
  61 + schemas: useTriggerDrawerSchema,
  62 + actionColOptions: { span: 24 },
  63 + });
  64 + const formData = ref([]);
  65 + async function handleSubmit() {
  66 + try {
  67 + const data = await getFieldsValue();
  68 + formData.value = data;
  69 + emit('get-formdata', formData.value);
  70 + } catch (e) {
  71 + console.log(e);
  72 + }
  73 + }
  74 + const n = ref(1);
  75 + function add() {
  76 + appendSchemaByField(
  77 + {
  78 + field: `field${n.value}a`,
  79 + component: 'ApiSelect',
  80 + label: '',
  81 + componentProps: {
  82 + placeholder: '请选择',
  83 + },
  84 + colProps: {
  85 + span: 8,
  86 + offset: 1,
  87 + },
  88 + required: true,
  89 + },
  90 + ''
  91 + );
  92 + appendSchemaByField(
  93 + {
  94 + field: `field${n.value}b`,
  95 + component: 'Input',
  96 + label: '',
  97 + componentProps: {
  98 + placeholder: '请输入',
  99 + },
  100 + colProps: {
  101 + span: 8,
  102 + offset: 1,
  103 + },
  104 + required: true,
  105 + },
  106 + ''
  107 + );
  108 + appendSchemaByField(
  109 + {
  110 + field: `field${n.value}c`,
  111 + component: 'ApiSelect',
  112 + label: '',
  113 + componentProps: {
  114 + placeholder: '请选择',
  115 + },
  116 + colProps: {
  117 + span: 8,
  118 + },
  119 + required: true,
  120 + },
  121 + ''
  122 + );
  123 + appendSchemaByField(
  124 + {
  125 + field: `field${n.value}d`,
  126 + component: 'ApiSelect',
  127 + label: '',
  128 + componentProps: {
  129 + placeholder: '请选择',
  130 + },
  131 + colProps: {
  132 + span: 8,
  133 + },
  134 + required: true,
  135 + },
  136 + ''
  137 + );
  138 + appendSchemaByField(
  139 + {
  140 + field: `field${n.value}e`,
  141 + component: 'ApiSelect',
  142 + label: '',
  143 + componentProps: {
  144 + placeholder: '请选择',
  145 + },
  146 + colProps: {
  147 + span: 8,
  148 + },
  149 + required: true,
  150 + },
  151 + ''
  152 + );
  153 + appendSchemaByField(
  154 + {
  155 + field: `field${n.value}f`,
  156 + component: 'Input',
  157 + label: '',
  158 + componentProps: {
  159 + placeholder: '请输入',
  160 + },
  161 + colProps: {
  162 + span: 8,
  163 + },
  164 + required: true,
  165 + },
  166 + ''
  167 + );
  168 + appendSchemaByField(
  169 + {
  170 + field: `${n.value}`,
  171 + component: 'ApiSelect',
  172 + label: ' ',
  173 + colProps: {
  174 + span: 8,
  175 + offset: 1,
  176 + },
  177 + slot: 'add',
  178 + },
  179 + ''
  180 + );
  181 + n.value++;
  182 + }
  183 +
  184 + function del(field) {
  185 + removeSchemaByFiled([
  186 + `field${field}a`,
  187 + `field${field}b`,
  188 + `field${field}c`,
  189 + `field${field}d`,
  190 + `field${field}e`,
  191 + `field${field}f`,
  192 + `field${field}g`,
  193 + `field${field}h`,
  194 + `${field}`,
  195 + ]);
  196 + n.value--;
  197 + }
  198 +
  199 + return { register, handleSubmit, add, del, formData };
  200 + },
  201 + });
  202 +</script>
  1 +import { BasicColumn } from '/@/components/Table';
  2 +import { FormSchema } from '/@/components/Table';
  3 +import { findDictItemByCode } from '/@/api/system/dict';
  4 +
  5 +export const columns: BasicColumn[] = [
  6 + {
  7 + title: '场景联动名称',
  8 + dataIndex: 'name',
  9 + width: 200,
  10 + slots: { customRender: 'name' },
  11 + },
  12 + {
  13 + title: '触发方式',
  14 + dataIndex: 'act',
  15 + width: 200,
  16 + },
  17 + {
  18 + title: '状态',
  19 + dataIndex: 'stu',
  20 + width: 200,
  21 + slots: { customRender: 'stu' },
  22 + },
  23 + {
  24 + title: '描述',
  25 + dataIndex: 'desc',
  26 + width: 200,
  27 + },
  28 + {
  29 + title: '创建时间',
  30 + dataIndex: 'createTime',
  31 + width: 180,
  32 + },
  33 +];
  34 +
  35 +export const formSchema: FormSchema[] = [
  36 + {
  37 + field: 'name',
  38 + label: '场景联动名称',
  39 + colProps: { span: 20 },
  40 + required: true,
  41 + component: 'Input',
  42 + componentProps: {
  43 + placeholder: '请输入场景联动名称',
  44 + },
  45 + },
  46 + {
  47 + field: 'org',
  48 + label: '所属组织',
  49 + required: true,
  50 + colProps: { span: 20 },
  51 + component: 'ApiSelect',
  52 + componentProps: {
  53 + api: findDictItemByCode,
  54 + params: {
  55 + dictCode: 'message_type',
  56 + },
  57 + labelField: 'itemText',
  58 + valueField: 'itemValue',
  59 + },
  60 + },
  61 + {
  62 + field: 'nn',
  63 + label: '描述',
  64 + // colProps: { span: 20 },
  65 + component: 'InputTextArea',
  66 + componentProps: {
  67 + placeholder: '请输入描述',
  68 + },
  69 + },
  70 +];
  71 +
  72 +export const searchFormSchema: FormSchema[] = [
  73 + {
  74 + field: 'org',
  75 + label: '所属组织',
  76 + component: 'ApiTreeSelect',
  77 + componentProps: {
  78 + placeholder: '请输入所属组织',
  79 + },
  80 + colProps: { span: 7 },
  81 + },
  82 + {
  83 + field: 'name1',
  84 + label: '名称',
  85 + component: 'Input',
  86 + colProps: { span: 8 },
  87 + componentProps: {
  88 + placeholder: '请输入场景联动状态',
  89 + },
  90 + },
  91 + {
  92 + field: 's1',
  93 + label: '状态',
  94 + component: 'ApiSelect',
  95 + componentProps: {
  96 + placeholder: '请选择状态',
  97 + },
  98 + colProps: { span: 4 },
  99 + },
  100 +];
  101 +
  102 +export const useTriggerDrawerSchema: FormSchema[] = [
  103 + {
  104 + field: 'field0a',
  105 + label: '',
  106 + component: 'ApiSelect',
  107 + componentProps: {
  108 + api: findDictItemByCode,
  109 + params: {
  110 + dictCode: 'message_type',
  111 + },
  112 + labelField: 'itemText',
  113 + valueField: 'itemValue',
  114 + },
  115 + colProps: {
  116 + span: 6,
  117 + },
  118 + required: true,
  119 + },
  120 + {
  121 + field: 'field0b',
  122 + label: '',
  123 + component: 'Input',
  124 + componentProps: {
  125 + placeholder: '请输入',
  126 + },
  127 + onChange: (e: any) => {
  128 + console.log(e);
  129 + },
  130 + colProps: {
  131 + span: 6,
  132 + },
  133 + required: true,
  134 + },
  135 + {
  136 + field: 'field0c',
  137 + label: '',
  138 + component: 'ApiSelect',
  139 + componentProps: {
  140 + api: findDictItemByCode,
  141 + params: {
  142 + dictCode: 'message_type',
  143 + },
  144 + labelField: 'itemText',
  145 + valueField: 'itemValue',
  146 + },
  147 + colProps: {
  148 + span: 6,
  149 + },
  150 + required: true,
  151 + },
  152 + {
  153 + field: 'field0d',
  154 + component: 'ApiSelect',
  155 + label: '',
  156 + componentProps: {
  157 + placeholder: '请选择',
  158 + },
  159 + colProps: {
  160 + span: 6,
  161 + },
  162 + required: true,
  163 + },
  164 + {
  165 + field: 'field0e',
  166 + component: 'ApiSelect',
  167 + label: '',
  168 + componentProps: {
  169 + placeholder: '请选择',
  170 + },
  171 + colProps: {
  172 + span: 6,
  173 + },
  174 + required: true,
  175 + },
  176 + {
  177 + field: 'field0f',
  178 + component: 'Input',
  179 + label: '',
  180 + componentProps: {
  181 + placeholder: '请输入',
  182 + },
  183 + colProps: {
  184 + span: 6,
  185 + },
  186 + required: true,
  187 + },
  188 + {
  189 + field: '0',
  190 + component: 'ApiSelect',
  191 + label: ' ',
  192 + colProps: {
  193 + span: 6,
  194 + },
  195 + slot: 'add',
  196 + },
  197 +];
  198 +
  199 +export const useConditionDrawerSchema: FormSchema[] = [
  200 + {
  201 + field: 'field0a',
  202 + component: 'ApiSelect',
  203 + label: '',
  204 + componentProps: {
  205 + placeholder: '请选择',
  206 + },
  207 + colProps: {
  208 + span: 6,
  209 + },
  210 + required: true,
  211 + },
  212 + {
  213 + field: 'field0b',
  214 + component: 'Input',
  215 + label: '',
  216 + componentProps: {
  217 + placeholder: '请输入',
  218 + },
  219 + onChange: (e: any) => {
  220 + console.log(e);
  221 + },
  222 + colProps: {
  223 + span: 6,
  224 + },
  225 + required: true,
  226 + },
  227 + {
  228 + field: 'field0c',
  229 + component: 'ApiSelect',
  230 + label: '',
  231 + componentProps: {
  232 + placeholder: '请选择',
  233 + },
  234 + colProps: {
  235 + span: 6,
  236 + },
  237 + required: true,
  238 + },
  239 + {
  240 + field: 'field0d',
  241 + component: 'ApiSelect',
  242 + label: '',
  243 + componentProps: {
  244 + placeholder: '请选择',
  245 + },
  246 + colProps: {
  247 + span: 6,
  248 + },
  249 + required: true,
  250 + },
  251 + {
  252 + field: 'field0e',
  253 + component: 'ApiSelect',
  254 + label: '',
  255 + componentProps: {
  256 + placeholder: '请选择',
  257 + },
  258 + colProps: {
  259 + span: 6,
  260 + },
  261 + required: true,
  262 + },
  263 + {
  264 + field: 'field0f',
  265 + component: 'Input',
  266 + label: '',
  267 + componentProps: {
  268 + placeholder: '请输入',
  269 + },
  270 + colProps: {
  271 + span: 6,
  272 + },
  273 + required: true,
  274 + },
  275 + {
  276 + field: '0',
  277 + component: 'ApiSelect',
  278 + label: ' ',
  279 + colProps: {
  280 + span: 6,
  281 + },
  282 + slot: 'add',
  283 + },
  284 +];
  285 +
  286 +export const useActionDrawerSchema: FormSchema[] = [
  287 + {
  288 + field: 'field0a',
  289 + component: 'ApiSelect',
  290 + label: '',
  291 + componentProps: {
  292 + placeholder: '请选择',
  293 + },
  294 + colProps: {
  295 + span: 6,
  296 + },
  297 + required: true,
  298 + },
  299 + {
  300 + field: 'field0b',
  301 + component: 'Input',
  302 + label: '',
  303 + componentProps: {
  304 + placeholder: '请输入',
  305 + },
  306 + onChange: (e: any) => {
  307 + console.log(e);
  308 + },
  309 + colProps: {
  310 + span: 6,
  311 + },
  312 + required: true,
  313 + },
  314 + {
  315 + field: 'field0c',
  316 + component: 'ApiSelect',
  317 + label: '',
  318 + componentProps: {
  319 + placeholder: '请选择',
  320 + },
  321 + colProps: {
  322 + span: 6,
  323 + },
  324 + required: true,
  325 + },
  326 + {
  327 + field: 'field0d',
  328 + component: 'ApiSelect',
  329 + label: '',
  330 + componentProps: {
  331 + placeholder: '请选择',
  332 + },
  333 + colProps: {
  334 + span: 6,
  335 + },
  336 + required: true,
  337 + },
  338 + {
  339 + field: 'field0e',
  340 + component: 'ApiSelect',
  341 + label: '',
  342 + componentProps: {
  343 + placeholder: '请选择',
  344 + },
  345 + colProps: {
  346 + span: 6,
  347 + },
  348 + required: true,
  349 + },
  350 + {
  351 + field: 'field0f',
  352 + component: 'Input',
  353 + label: '',
  354 + componentProps: {
  355 + placeholder: '请输入',
  356 + },
  357 + colProps: {
  358 + span: 6,
  359 + },
  360 + required: true,
  361 + },
  362 + {
  363 + field: '0',
  364 + component: 'ApiSelect',
  365 + label: ' ',
  366 + colProps: {
  367 + span: 6,
  368 + },
  369 + slot: 'add',
  370 + },
  371 +];
  1 +<template>
  2 + <div>
  3 + <BasicTable :clickToRowSelect="true" @register="registerTable">
  4 + <template #toolbar>
  5 + <a-button type="primary" @click="handleAdd"> 新增场景联动 </a-button>
  6 + <a-button type="error" @click="handleToolbarDel"> 删除 </a-button>
  7 + </template>
  8 + <template #action="{ record }">
  9 + <TableAction
  10 + :actions="[
  11 + {
  12 + label: '编辑',
  13 + icon: 'clarity:note-edit-line',
  14 + onClick: handleEdit.bind(null, record),
  15 + },
  16 + {
  17 + label: '删除',
  18 + icon: 'ant-design:delete-outlined',
  19 + color: 'error',
  20 + popConfirm: {
  21 + title: '是否确认删除',
  22 + confirm: handleDelete.bind(null, record),
  23 + },
  24 + },
  25 + ]"
  26 + />
  27 + </template>
  28 + </BasicTable>
  29 + <SceneLinkAgeDrawer @register="registerDrawer" @success="handleSuccess" />
  30 + </div>
  31 +</template>
  32 +<script lang="ts">
  33 + import { defineComponent } from 'vue';
  34 + import { DeviceState, DeviceTypeEnum } from '/@/api/device/model/deviceModel';
  35 + import { BasicTable, useTable, TableAction } from '/@/components/Table';
  36 + import { useDrawer } from '/@/components/Drawer';
  37 + import SceneLinkAgeDrawer from './useDrawer.vue';
  38 + import { columns, searchFormSchema } from './config.d';
  39 + // import { Modal } from 'ant-design-vue';
  40 + // import { useMessage } from '/@/hooks/web/useMessage';
  41 + // import { deleteDevice, devicePage } from '/@/api/device/deviceManager';
  42 + import { PageEnum } from '/@/enums/pageEnum';
  43 + import { useGo } from '/@/hooks/web/usePage';
  44 +
  45 + export default defineComponent({
  46 + name: 'DeviceManagement',
  47 + components: { BasicTable, SceneLinkAgeDrawer, TableAction },
  48 + setup() {
  49 + const [registerDrawer, { openDrawer }] = useDrawer();
  50 + // const { createMessage } = useMessage();
  51 + const go = useGo();
  52 + const [registerTable, { reload }] = useTable({
  53 + title: '',
  54 + // api: devicePage,
  55 + columns,
  56 + formConfig: {
  57 + labelWidth: 120,
  58 + schemas: searchFormSchema,
  59 + },
  60 + useSearchForm: true,
  61 + showTableSetting: true,
  62 + bordered: true,
  63 + showIndexColumn: false,
  64 + rowSelection: {
  65 + type: 'checkbox',
  66 + },
  67 + actionColumn: {
  68 + width: 180,
  69 + title: '操作',
  70 + dataIndex: 'action',
  71 + slots: { customRender: 'action' },
  72 + fixed: undefined,
  73 + },
  74 + });
  75 +
  76 + function handleAdd() {
  77 + openDrawer(true, {
  78 + isUpdate: false,
  79 + });
  80 + }
  81 + function handleToolbarDel() {
  82 + return;
  83 + }
  84 +
  85 + function handleEdit(record: Recordable) {
  86 + openDrawer(true, {
  87 + record,
  88 + isUpdate: true,
  89 + });
  90 + }
  91 +
  92 + function handleDelete(record: Recordable) {
  93 + return record;
  94 + // let ids = [record.id];
  95 + // deleteDevice(ids).then(() => {
  96 + // createMessage.success('删除设备成功');
  97 + // handleSuccess();
  98 + // });
  99 + }
  100 +
  101 + function handleSuccess() {
  102 + reload();
  103 + }
  104 + function showData(record: Recordable) {
  105 + return record;
  106 + // Modal.info({
  107 + // title: '当前配置',
  108 + // width: 480,
  109 + // content: h(JsonPreview, { data: JSON.parse(JSON.stringify(record.deviceInfo)) }),
  110 + // });
  111 + }
  112 + function goDeviceProfile() {
  113 + go(PageEnum.DEVICE_PROFILE);
  114 + }
  115 + return {
  116 + registerTable,
  117 + registerDrawer,
  118 + showData,
  119 + handleAdd,
  120 + handleToolbarDel,
  121 + handleEdit,
  122 + handleDelete,
  123 + handleSuccess,
  124 + goDeviceProfile,
  125 + DeviceTypeEnum,
  126 + DeviceState,
  127 + };
  128 + },
  129 + });
  130 +</script>
  1 +<template>
  2 + <BasicDrawer
  3 + v-bind="$attrs"
  4 + @register="registerDrawer"
  5 + showFooter
  6 + :title="getTitle"
  7 + width="1000px"
  8 + @ok="handleSubmit"
  9 + >
  10 + <BasicForm @register="registerForm" />
  11 + <AddTriggerForm @get-formdata="getFormData" ref="triggerRef" />
  12 + <AddConditiForm ref="conditionRef" />
  13 + <AddActionForm ref="actionRef" />
  14 + </BasicDrawer>
  15 +</template>
  16 +<script lang="ts">
  17 + import { defineComponent, ref, computed, unref } from 'vue';
  18 + import { BasicForm, useForm } from '/@/components/Form';
  19 + import { formSchema } from './config.d';
  20 + import { BasicDrawer, useDrawerInner } from '/@/components/Drawer';
  21 + // import { saveOrEditMessageConfig } from '/@/api/message/config';
  22 + // import { useMessage } from '/@/hooks/web/useMessage';
  23 + import AddTriggerForm from './addForm/trigger.vue';
  24 + import AddActionForm from './addForm/doaction.vue';
  25 + import AddConditiForm from './addForm/condition.vue';
  26 +
  27 + export default defineComponent({
  28 + name: 'ConfigDrawer',
  29 + components: { BasicDrawer, BasicForm, AddTriggerForm, AddActionForm, AddConditiForm },
  30 + emits: ['success', 'register'],
  31 + setup() {
  32 + const isUpdate = ref(true);
  33 + const getAllFormData = ref(null);
  34 + const getChildFormData = ref(null);
  35 + const [registerForm, { resetFields, validateFields, getFieldsValue }] = useForm({
  36 + labelWidth: 120,
  37 + schemas: formSchema,
  38 + showActionButtonGroup: false,
  39 + });
  40 +
  41 + const [registerDrawer, { setDrawerProps }] = useDrawerInner(async (data) => {
  42 + await resetFields();
  43 + setDrawerProps({ confirmLoading: false });
  44 + isUpdate.value = !!data?.isUpdate;
  45 + });
  46 + const getTitle = computed(() => (!unref(isUpdate) ? '新增场景联动' : '编辑场景联动'));
  47 + const getFormData = (v) => {
  48 + getChildFormData.value = { ...v };
  49 + // console.log('获取子组件的值', v);
  50 + };
  51 + async function handleSubmit() {
  52 + const res = await validateFields();
  53 + if (!res) return;
  54 + const values = await getFieldsValue();
  55 + getAllFormData.value = { ...values , ...getChildFormData.value};
  56 + console.log(getAllFormData.value);
  57 + }
  58 + return {
  59 + getFormData,
  60 + getAllFormData,
  61 + registerDrawer,
  62 + registerForm,
  63 + getTitle,
  64 + handleSubmit,
  65 + };
  66 + },
  67 + });
  68 +</script>
@@ -10,125 +10,161 @@ @@ -10,125 +10,161 @@
10 <BasicForm @register="registerForm"> 10 <BasicForm @register="registerForm">
11 <template #menu="{ model, field }"> 11 <template #menu="{ model, field }">
12 <BasicTree 12 <BasicTree
  13 + ref="tree"
13 v-model:value="model[field]" 14 v-model:value="model[field]"
14 :treeData="treeData" 15 :treeData="treeData"
15 :replaceFields="{ title: 'menuName' }" 16 :replaceFields="{ title: 'menuName' }"
16 - :checked-keys="roleMenus" 17 + :checkedKeys="roleMenus"
17 checkable 18 checkable
18 toolbar 19 toolbar
19 title="菜单分配" 20 title="菜单分配"
  21 + @check="handleCheckClick"
20 /> 22 />
21 </template> 23 </template>
22 </BasicForm> 24 </BasicForm>
23 </BasicDrawer> 25 </BasicDrawer>
24 </template> 26 </template>
25 <script lang="ts"> 27 <script lang="ts">
26 -import {defineComponent, ref, computed, unref} from 'vue';  
27 -import {BasicForm, useForm} from '/@/components/Form/index';  
28 -import {formSchema} from './role.data';  
29 -import {BasicDrawer, useDrawerInner} from '/@/components/Drawer';  
30 -import {BasicTree, TreeItem} from '/@/components/Tree'; 28 + import { defineComponent, ref, computed, unref, getCurrentInstance } from 'vue';
  29 + import { BasicForm, useForm } from '/@/components/Form/index';
  30 + import { formSchema } from './role.data';
  31 + import { BasicDrawer, useDrawerInner } from '/@/components/Drawer';
  32 + import { BasicTree, TreeItem } from '/@/components/Tree';
31 33
32 -const {t} = useI18n(); //加载国际化 34 + const { t } = useI18n(); //加载国际化
33 35
34 -// import { getMenuList } from '/@/api/demo/system'; 36 + // import { getMenuList } from '/@/api/demo/system';
35 37
36 -// 加载菜单数据  
37 -import {getMenuList, getMenusIdsByRoleId} from '/@/api/sys/menu';  
38 -import {useI18n} from "/@/hooks/web/useI18n";  
39 -import {RouteItem} from "/@/api/sys/model/menuModel";  
40 -import {saveOrUpdateRoleInfoWithMenu} from "/@/api/system/system"; 38 + // 加载菜单数据
  39 + import { getMenuList, getMenusIdsByRoleId } from '/@/api/sys/menu';
  40 + import { useI18n } from '/@/hooks/web/useI18n';
  41 + import { RouteItem } from '/@/api/sys/model/menuModel';
  42 + import { saveOrUpdateRoleInfoWithMenu } from '/@/api/system/system';
  43 + export default defineComponent({
  44 + name: 'RoleDrawer',
  45 + components: { BasicDrawer, BasicForm, BasicTree },
  46 + emits: ['success', 'register'],
  47 + setup(_, { emit }) {
  48 + const { proxy } = getCurrentInstance();
  49 + const isUpdate = ref<boolean>(true);
  50 + const treeData = ref<TreeItem[]>([]);
  51 + const roleMenus = ref<string[]>([]);
  52 + const allCheckedKeys = ref<string[]>();
  53 + const roleHalfCheckedKeys = ref<string[]>([]);
  54 + const roleId = ref<string>('');
  55 + const [registerForm, { resetFields, setFieldsValue, validate }] = useForm({
  56 + labelWidth: 90,
  57 + schemas: formSchema,
  58 + showActionButtonGroup: false,
  59 + });
41 60
42 -export default defineComponent({  
43 - name: 'RoleDrawer',  
44 - components: {BasicDrawer, BasicForm, BasicTree},  
45 - emits: ['success', 'register'],  
46 - setup(_, {emit}) {  
47 - const isUpdate = ref(true);  
48 - const treeData = ref<TreeItem[]>([]);  
49 - const roleMenus = ref<string[]>([]);  
50 - const roleId = ref(""); 61 + function processChildren(items: RouteItem[]) {
  62 + items.map((item) => {
  63 + item.menuName = t(item.meta.title);
  64 + item.icon = item.meta.icon;
  65 + item.key = item.id;
  66 + if (item.children) {
  67 + processChildren(item.children);
  68 + }
  69 + });
  70 + }
51 71
52 - const [registerForm, {resetFields, setFieldsValue, validate}] = useForm({  
53 - labelWidth: 90,  
54 - schemas: formSchema,  
55 - showActionButtonGroup: false,  
56 - }); 72 + /**
  73 + * 根据角色id获取所有的菜单ids----里面包含父级id---会造成回显数据时
  74 + * 存在父级id则默认勾选所有子级id
  75 + */
  76 + function useChildrenIdsRemoveParentId(str, arr) {
  77 + let index = arr.indexOf(str);
  78 + arr.splice(index, 1);
  79 + return arr;
  80 + }
57 81
58 - function processChildren(items: RouteItem[]) {  
59 - items.map((item) => {  
60 - item.menuName = t(item.meta.title);  
61 - item.icon = item.meta.icon;  
62 - item.key=item.id;  
63 - if (item.children) {  
64 - processChildren(item.children); 82 + const [registerDrawer, { setDrawerProps, closeDrawer }] = useDrawerInner(async (data) => {
  83 + resetFields();
  84 + roleId.value = '';
  85 + setDrawerProps({ confirmLoading: false });
  86 + // 需要在setFieldsValue之前先填充treeData,否则Tree组件可能会报key not exist警告
  87 + if (unref(treeData).length === 0) {
  88 + // 获取全部的菜单
  89 + const menuListModel = await getMenuList();
  90 + processChildren(menuListModel);
  91 + let treeValues: TreeItem[] = [];
  92 + menuListModel.map((item) => {
  93 + const data = {
  94 + menuName: t(item.meta.title),
  95 + icon: item.meta.icon,
  96 + key: item.id,
  97 + children: item.children as any as TreeItem[],
  98 + };
  99 + treeValues.push(data);
  100 + });
  101 + treeData.value = treeValues;
65 } 102 }
66 - });  
67 - }  
68 103
69 - const [registerDrawer, {setDrawerProps, closeDrawer}] = useDrawerInner(async (data) => {  
70 - resetFields();  
71 - roleId.value = "";  
72 - setDrawerProps({confirmLoading: false});  
73 - // 需要在setFieldsValue之前先填充treeData,否则Tree组件可能会报key not exist警告  
74 - if (unref(treeData).length === 0) {  
75 - const menuListModel = await getMenuList();  
76 - processChildren(menuListModel);  
77 - let treeValues = new Array<TreeItem>();  
78 - menuListModel.map((item) => {  
79 - const data = {  
80 - menuName: t(item.meta.title),  
81 - icon: item.meta.icon,  
82 - key: item.id,  
83 - children: item.children as any as TreeItem[], 104 + if (unref(isUpdate)) {
  105 + if (data.record) {
  106 + // // 通过角色id去获取角色对应的菜单的ids
  107 + roleMenus.value = await getMenusIdsByRoleId(data.record.id);
  108 + console.log(roleMenus.value);
  109 + console.log(treeData.value);
  110 + treeData.value.map((m) => {
  111 + roleMenus.value.map((m1) => {
  112 + if (m.key === m1) {
  113 + proxy.useChildrenIdsRemoveParentId(m1, roleMenus.value);
  114 + }
  115 + });
  116 + });
  117 + console.log(roleMenus.value);
  118 + proxy.$refs.tree.setCheckedKeys(roleMenus.value);
  119 + // console.log(roleMenus.value, 'roleMenus.value');
  120 + // // TODO: 角色回显问题:待解决
  121 + roleId.value = data.record.id;
84 } 122 }
85 - treeValues.push(data);  
86 - })  
87 - treeData.value = treeValues;  
88 - }  
89 - if (data.record) {  
90 - roleMenus.value = await getMenusIdsByRoleId(data.record.id);  
91 - console.log(roleMenus.value,"roleMenus.value")  
92 - roleId.value = data.record.id;  
93 - }  
94 - isUpdate.value = !!data?.isUpdate;  
95 - if (unref(isUpdate)) {  
96 - setFieldsValue({  
97 - ...data.record,  
98 - });  
99 - }  
100 - }); 123 + setFieldsValue({
  124 + ...data.record,
  125 + });
  126 + }
  127 + });
101 128
102 - const getTitle = computed(() => (!unref(isUpdate) ? '新增角色' : '编辑角色')); 129 + const getTitle = computed(() => (!unref(isUpdate) ? '新增角色' : '编辑角色'));
103 130
104 - async function handleSubmit() {  
105 - try {  
106 - const values = await validate();  
107 - setDrawerProps({confirmLoading: true});  
108 - const req = {  
109 - id: roleId.value,  
110 - name: values.name,  
111 - remark: values.remark,  
112 - status: values.status,  
113 - menu: [...values.menu] 131 + async function handleSubmit() {
  132 + try {
  133 + const values = await validate();
  134 + setDrawerProps({ confirmLoading: true });
  135 + const req = {
  136 + id: roleId.value,
  137 + name: values.name,
  138 + remark: values.remark,
  139 + status: values.status,
  140 + menu: allCheckedKeys.value as string[],
  141 + };
  142 + saveOrUpdateRoleInfoWithMenu(req).then(() => {
  143 + closeDrawer();
  144 + emit('success');
  145 + });
  146 + } finally {
  147 + setDrawerProps({ confirmLoading: false });
114 } 148 }
115 - saveOrUpdateRoleInfoWithMenu(req).then(()=>{  
116 - closeDrawer();  
117 - emit('success');  
118 - })  
119 - } finally {  
120 - setDrawerProps({confirmLoading: false});  
121 } 149 }
122 - } 150 + // Tree check事件
  151 + const handleCheckClick = (checkedKeys: string[], { halfCheckedKeys }) => {
  152 + allCheckedKeys.value = [...checkedKeys, ...halfCheckedKeys];
  153 + // 父节点
  154 + roleHalfCheckedKeys.value = halfCheckedKeys;
  155 + };
123 156
124 - return {  
125 - registerDrawer,  
126 - registerForm,  
127 - getTitle,  
128 - handleSubmit,  
129 - treeData,  
130 - roleMenus,  
131 - };  
132 - },  
133 -}); 157 + return {
  158 + allCheckedKeys,
  159 + registerDrawer,
  160 + registerForm,
  161 + getTitle,
  162 + handleSubmit,
  163 + treeData,
  164 + roleMenus,
  165 + handleCheckClick,
  166 + useChildrenIdsRemoveParentId,
  167 + };
  168 + },
  169 + });
134 </script> 170 </script>