<template> <div class="container"> <Breadcrumb :items="['系统管理', '公告设置']" /> <a-card class="general-card" title=" "> <a-row> <a-col :flex="1"> <a-form :model="formModel" :label-col-props="{ span: 6 }" :wrapper-col-props="{ span: 18 }" label-align="right" > <a-row :gutter="18"> <a-col :span="9"> <a-form-item field="name" label='名称' > <a-input v-model="formModel.name" style="width: 360px" placeholder='请输入设备名称' /> </a-form-item> </a-col> <a-col :span="10"> <a-form-item field="status" label='状态'> <a-input v-model="formModel.status" style="width: 360px" placeholder='请输入设备状态' /> </a-form-item> </a-col> <a-col :span="9"> <a-form-item field="isOnline" label='在线' > <a-select v-model="formModel.isOnline" style="width: 360px" placeholder='请选择是否在线' :options="statusOptions" /> </a-form-item> </a-col> </a-row> </a-form> </a-col> <a-divider style="height: 84px" direction="vertical" /> <a-col :flex="'86px'" style="text-align: right"> <a-space direction="vertical" :size="18"> <a-button type="primary" @click="search"> <template #icon> <icon-search /> </template> 查询 </a-button> <a-button @click="reset"> <template #icon> <icon-refresh /> </template> 重置 </a-button> </a-space> </a-col> </a-row> <a-divider style="margin-top: 0" /> <a-row> <a-col :span="12"> <a-space> <DeviceEdit ref="createUserRef" :is-create="true" @refresh="search" /> </a-space> </a-col> <a-col :span="12" style=" display: flex; align-items: center; justify-content: end; padding-bottom: 20px; " > <a-tooltip content='刷新'> <div class="action-icon" @click="search"> <icon-refresh size="18" /> </div> </a-tooltip> <a-dropdown @select="handleSelectDensity"> <a-tooltip content='密度'> <div class="action-icon"><icon-line-height size="18" /></div> </a-tooltip> <template #content> <a-doption v-for="item in densityList" :key="item.value" :value="item.value" :class="{ active: item.value === size }" > <span>{{ item.name }}</span> </a-doption> </template> </a-dropdown> <a-tooltip content='列设置'> <a-popover trigger="click" position="bl" @popup-visible-change="popupVisibleChange" > <div class="action-icon"><icon-settings size="18" /></div> <template #content> <div id="tableSetting"> <div v-for="(item, index) in showColumns" :key="item.dataIndex" class="setting" > <div style="margin-right: 4px; cursor: move"> <icon-drag-arrow /> </div> <div> <a-checkbox v-model="item.checked" @change=" handleChange($event, item as TableColumnData, index) " > </a-checkbox> </div> <div class="title"> {{ item.title === '#' ? '序列号' : item.title }} </div> </div> </div> </template> </a-popover> </a-tooltip> </a-col> </a-row> <a-table row-key="id" :loading="loading" :pagination="false" :columns="(cloneColumns as TableColumnData[])" :data="renderData" :bordered="false" :size="size" style="margin-bottom: 40px" @page-change="onPageChange" > <template #id="{ record }"> <span>{{ record.id }}</span> </template> <template #online="{ record }"> {{ record.online == true? '是' : '否' }} </template> <template #operations="{ record }"> <a-button type="outline" size="small" status="success" style="padding: 7px; margin-right: 10px" @click="openDetail(record.id)" > <template #icon><icon-list /></template> 详情 </a-button> <DeviceEdit ref="editUserRef" :prem="record" :is-create="false" @refresh="fetchData" /> <a-popconfirm content='确认删除此设备?' type="error" @ok="handleDelete(record.id)" > <a-button v-permission="['iot:device:delete']" type="outline" size="small" status="danger" style="padding: 7px;margin-right: 10px" > <template #icon><icon-delete /></template> 删除 </a-button> </a-popconfirm> </template> </a-table> <a-pagination style="float: right; position: relative; right: 1px; bottom: 25px" :total="pagination.total" :size="size" show-total show-jumper show-page-size @page-size-change="onSizeChange" @change="onPageChange" /> </a-card> </div> </template> <script lang="ts" setup> import { computed, onMounted, ref, watch } from 'vue'; import useLoading from '@/hooks/loading'; import usePagination from '@/hooks/pagination'; import type { SelectOptionData } from '@arco-design/web-vue/es/select/interface'; import type { TableColumnData } from '@arco-design/web-vue/es/table/interface'; import useTableOption from '@/hooks/table-option'; import { Message } from '@arco-design/web-vue'; import { useRouter } from 'vue-router'; import { deleteDevice, DeviceRecord, queryDeviceList } from '@/api/device'; import DeviceEdit from '@/views/iot/device/components/device-edit.vue'; const generateFormModel = () => { return { name:'', status:'', isOnline:'', }; }; const { loading, setLoading } = useLoading(true); const { pagination,setPagination } = usePagination(); const renderData = ref<[]>([]); const formModel = ref(generateFormModel()); const router = useRouter(); const { cloneColumns, showColumns, densityList, size, handleSelectDensity, handleChange, popupVisibleChange, deepClone, } = useTableOption(); const columns = computed<TableColumnData[]>(() => [ { title: 'ID', dataIndex: 'id', slotName: 'id', width: 60, }, { title: '名称', dataIndex: 'name', }, { title: '状态', dataIndex: 'state', slotName: 'state', }, { title: '在线状态', dataIndex: 'online', slotName:'online', sortable: { sortDirections: ['ascend', 'descend'], }, }, { title: '操作', dataIndex: 'operations', slotName: 'operations', }, ]); const statusOptions = computed<SelectOptionData[]>(() => [ { label: '是', value: 'true', }, { label: '否', value: 'false', }, ]); // 获取设备列表 const fetchData = async ( params = { size: 10, current: 1 } ) => { setLoading(true); try { const res: any = await queryDeviceList(params); renderData.value = res.data.records; setPagination(res.data); } catch (err) { // you can report use errorHandler or other } finally { setLoading(false); } }; // 查询 const search = () => { fetchData({ ...pagination.value, ...formModel.value, } as unknown as DeviceRecord); }; // 分页发生改变 const onPageChange = (current: number) => { pagination.value.page = current; pagination.value.current = current; search(); }; // 数据条数改变 const onSizeChange = (Size: number) => { pagination.value.size = Size; search(); }; // 重置 const reset = () => { formModel.value = generateFormModel(); }; // 打开详情 function openDetail(id:number): void{ const url = router.resolve({ name: 'deviceDetail', params: {id} }).href; router.push(url); } // 删除 const handleDelete = async (id: number) => { const res = await deleteDevice(id); if (res.status === 200) { Message.success({ content: '删除成功', duration: 5 * 1000, }); search(); } }; onMounted(() => { search(); }); watch(() => columns.value, deepClone, { deep: true, immediate: true }); </script> <style scoped lang="less"> .container { padding: 0 20px 20px 20px; } :deep(.arco-table-th) { &:last-child { .arco-table-th-item-title { margin-left: 16px; } } } .action-icon { margin-left: 12px; cursor: pointer; } .active { color: #0960bd; background-color: #e3f4fc; } .setting { display: flex; align-items: center; width: 200px; .title { margin-left: 12px; cursor: pointer; } } </style>