瀏覽代碼

计量绑定重构

learshaw 2 天之前
父節點
當前提交
ec9d1eb1dd

+ 0 - 41
ems-ui-cloud/src/api/device/elecMeterH.js

@@ -55,48 +55,7 @@ export function getElecDayAvg(param) {
   })
 }
 
-// 查询用水计量-小时列表
-export function listWaterMeterH(query) {
-    return request({
-        url: '/ems/waterMeterH/list',
-        method: 'get',
-        params: query
-    })
-}
-
-// 查询用水计量-小时详细
-export function getWaterMeterH(id) {
-    return request({
-        url: '/ems/waterMeterH/' + id,
-        method: 'get'
-    })
-}
-
-// 新增用水计量-小时
-export function addWaterMeterH(data) {
-    return request({
-        url: '/ems/waterMeterH',
-        method: 'post',
-        data: data
-    })
-}
 
-// 修改用水计量-小时
-export function updateWaterMeterH(data) {
-    return request({
-        url: '/ems/waterMeterH',
-        method: 'put',
-        data: data
-    })
-}
-
-// 删除用水计量-小时
-export function delWaterMeterH(id) {
-    return request({
-        url: '/ems/waterMeterH/' + id,
-        method: 'delete'
-    })
-}
 
 /**
  * 条件查询用能指标

+ 55 - 0
ems-ui-cloud/src/api/device/waterMeterH.js

@@ -7,3 +7,58 @@ export function getWaterDayAvg(param) {
     params: param
   })
 }
+
+/**
+ * 查询设施用能统计数据
+ *
+ */
+export function getNumWaterMeterH(query) {
+  return request({
+    url: '/ems/waterMeterH/staByTime',
+    method: 'get',
+    params: query
+  })
+}
+
+// 查询用水计量-小时列表
+export function listWaterMeterH(query) {
+  return request({
+    url: '/ems/waterMeterH/list',
+    method: 'get',
+    params: query
+  })
+}
+
+// 查询用水计量-小时详细
+export function getWaterMeterH(id) {
+  return request({
+    url: '/ems/waterMeterH/' + id,
+    method: 'get'
+  })
+}
+
+// 新增用水计量-小时
+export function addWaterMeterH(data) {
+  return request({
+    url: '/ems/waterMeterH',
+    method: 'post',
+    data: data
+  })
+}
+
+// 修改用水计量-小时
+export function updateWaterMeterH(data) {
+  return request({
+    url: '/ems/waterMeterH',
+    method: 'put',
+    data: data
+  })
+}
+
+// 删除用水计量-小时
+export function delWaterMeterH(id) {
+  return request({
+    url: '/ems/waterMeterH/' + id,
+    method: 'delete'
+  })
+}

文件差異過大導致無法顯示
+ 690 - 565
ems-ui-cloud/src/views/basecfg/boundaryRel/index.vue


+ 289 - 45
ems-ui-cloud/src/views/devmgr/meterData/index.vue

@@ -6,14 +6,24 @@
           <el-input v-model="areaName" placeholder="请输入服务区名称" clearable size="small"
                     prefix-icon="el-icon-search"
                     style="margin-bottom: 20px"
+                    @input="filterTree"
           />
         </div>
         <div class="head-container">
           <el-tree :data="areaOptions" :props="defaultProps" :expand-on-click-node="false"
                    :filter-node-method="filterNode" ref="tree"
-                   node-key="id" default-expand-all highlight-current @node-click="handleNodeClick"
-          />
-
+                   node-key="id" default-expand-all highlight-current @node-click="handleNodeClick">
+            <!-- 自定义节点内容:字符标识+名称 -->
+            <template #default="{ data }">
+              <div class="tree-node">
+                <!-- 区域节点添加 ▶ 符号 -->
+                <span v-if="data.type === 'area'" class="node-symbol area-symbol">▶</span>
+                <!-- 设备节点添加 ◬ 符号 -->
+                <span v-if="data.type === 'device'" class="node-symbol device-symbol">◬</span>
+                <span class="node-label">{{ data.label }}</span>
+              </div>
+            </template>
+          </el-tree>
         </div>
       </el-col>
       <el-col :span="20" :xs="24">
@@ -29,8 +39,8 @@
             <el-date-picker
               v-model="daterangeRecordTime"
               style="width: 240px"
-              value-format="yyyy-MM-dd HH:mm"
-              type="datetimerange"
+              value-format="yyyy-MM-dd"
+              type="daterange"
               range-separator="-"
               start-placeholder="开始日期"
               end-placeholder="结束日期"
@@ -44,13 +54,12 @@
           </el-form-item>
         </el-form>
 
-        <!-- 统计数据表格 -->
+        <!-- 用电统计数据表格 -->
         <el-card class="box-card" v-if="activeTab==='first' && numElecMeterHData">
           <div slot="header" class="clearfix">
             <span>用电统计</span>
           </div>
 
-
           <el-table :data="[numElecMeterHData]" border style="width: 100%">
             <!-- 第一行:用电量 -->
             <el-table-column label="" align="center">
@@ -58,9 +67,9 @@
                 <span>{{ '电量(千瓦时)' }}</span>
               </template>
             </el-table-column>
-            <el-table-column label="合计" align="center">
+            <el-table-column label="合计" align="center" class-name="total-column">
               <template slot-scope="scope">
-                <span>{{ scope.row.total.quantity ? scope.row.total.quantity.toFixed(2) : '0.00' }}</span>
+                <span class="total-value">{{ scope.row.total.quantity ? scope.row.total.quantity.toFixed(2) : '0.00' }}</span>
               </template>
             </el-table-column>
             <el-table-column label="平段" align="center">
@@ -91,9 +100,9 @@
                 <span>{{ '金额(元)' }}</span>
               </template>
             </el-table-column>
-            <el-table-column label="合计" align="center">
+            <el-table-column label="合计" align="center" class-name="total-column">
               <template slot-scope="scope">
-                <span>{{ scope.row.total.useCost ? scope.row.total.useCost.toFixed(2) : '0.00' }}</span>
+                <span class="total-value">{{ scope.row.total.useCost ? scope.row.total.useCost.toFixed(2) : '0.00' }}</span>
               </template>
             </el-table-column>
             <el-table-column label="平峰-金额(元)" align="center">
@@ -119,6 +128,40 @@
           </el-table>
         </el-card>
 
+        <!-- 用水统计数据表格 -->
+        <el-card class="box-card" v-if="activeTab==='second' && numWaterMeterHData">
+          <div slot="header" class="clearfix">
+            <span>用水统计</span>
+          </div>
+
+          <el-table :data="[numWaterMeterHData]" border style="width: 100%">
+            <!-- 第一行:用水量 -->
+            <el-table-column label="" align="center">
+              <template slot-scope="scope">
+                <span>{{ '水量(吨)' }}</span>
+              </template>
+            </el-table-column>
+            <el-table-column label="合计" align="center" class-name="total-column">
+              <template slot-scope="scope">
+                <span class="total-value">{{ scope.row.quantity ? scope.row.quantity.toFixed(2) : '0.00' }}</span>
+              </template>
+            </el-table-column>
+          </el-table>
+          <!-- 第二行:总金额 -->
+          <el-table :data="[numWaterMeterHData]" border style="width: 100%; margin-top: 10px" :show-header="false">
+            <el-table-column label="" align="center" >
+              <template slot-scope="scope">
+                <span>{{ '金额(元)' }}</span>
+              </template>
+            </el-table-column>
+            <el-table-column label="合计" align="center" class-name="total-column">
+              <template slot-scope="scope">
+                <span class="total-value">{{ scope.row.useCost ? scope.row.useCost.toFixed(2) : '0.00' }}</span>
+              </template>
+            </el-table-column>
+          </el-table>
+        </el-card>
+
         <el-table v-if="activeTab === 'first'" v-loading="loading" :data="elecMeterHList">
           <el-table-column label="表计名称" align="left" prop="deviceName" width="250px"/>
           <el-table-column label="表计编号" align="left" prop="deviceCode"/>
@@ -145,7 +188,6 @@
           </el-table-column>
         </el-table>
 
-
         <el-table v-if="activeTab === 'second'" v-loading="loading" :data="waterMeterHList">
           <el-table-column type="selection" width="55" align="center"/>
           <el-table-column label="表计名称" align="left" prop="deviceName" width="250"/>
@@ -222,14 +264,8 @@
 </template>
 
 <script>
-import {
-  listElecMeterH,
-  delElecMeterH,
-  addElecMeterH,
-  updateElecMeterH,
-  listWaterMeterH,
-  getNumElecMeterH
-} from '@/api/device/elecMeterH'
+import { listElecMeterH, delElecMeterH, addElecMeterH, updateElecMeterH, getNumElecMeterH } from '@/api/device/elecMeterH'
+import { listWaterMeterH, getNumWaterMeterH } from '@/api/device/waterMeterH'
 import { getDeviceTree } from '@/api/device/meterDevice'
 
 export default {
@@ -238,6 +274,8 @@ export default {
     return {
       // 存储用电统计数据
       numElecMeterHData: null,
+      // 存储用水统计数据
+      numWaterMeterHData: null,
       activeTab: 'first',
       // 遮罩层
       loading: true,
@@ -308,8 +346,11 @@ export default {
     }
   },
   created() {
+    // 初始化默认查询时间范围
+    this.initDefaultDateRange();
+
     this.getAreaTreeSelect().then(() => {
-      /** 获取第一个有效的树节点*/
+      /** 获取第一个有效的设备节点 */
       const firstValidNode = this.findFirstValidNode(this.areaOptions);
       if (firstValidNode) {
         this.queryParams.deviceCode = firstValidNode.id;
@@ -320,39 +361,78 @@ export default {
     });
   },
   methods: {
+    // 初始化默认查询时间范围:当月1号到今天
+    initDefaultDateRange() {
+      const today = new Date();
+      const currentYear = today.getFullYear();
+      const currentMonth = today.getMonth();
+
+      // 当月1号
+      const startDate = new Date(currentYear, currentMonth, 1);
+
+      // 当天
+      const endDate = new Date(today);
+
+      // 格式化为日期字符串 yyyy-MM-dd
+      const formatDate = (date) => {
+        const year = date.getFullYear();
+        const month = (date.getMonth() + 1).toString().padStart(2, '0');
+        const day = date.getDate().toString().padStart(2, '0');
+        return `${year}-${month}-${day}`;
+      };
+
+      this.daterangeRecordTime = [formatDate(startDate), formatDate(endDate)];
+    },
+
     handleTabChange() {
       if (this.activeTab === 'first') {
         // 电表读数
-        this.queryParams.meterCls = '45'
-        this.getElecList()
+        this.queryParams.meterCls = '45';
       } else if (this.activeTab === 'second') {
         // 水表读数
-        this.queryParams.meterCls = '70'
-        this.getWaterList()
-
+        this.queryParams.meterCls = '70';
       }
-      this.getAreaTreeSelect()
-      this.handleQuery()
+
+      // 重新加载树结构并重置设备选择
+      this.getAreaTreeSelect().then(() => {
+        // 切换tab后重新选择第一个设备节点
+        const firstValidNode = this.findFirstValidNode(this.areaOptions);
+        if (firstValidNode) {
+          this.queryParams.deviceCode = firstValidNode.id;
+          this.handleQuery();
+        } else {
+          // 如果没有找到设备节点,则清空数据
+          if (this.activeTab === 'first') {
+            this.getElecList();
+          } else {
+            this.getWaterList();
+          }
+        }
+      });
     },
+
     // 筛选节点
     filterNode(value, data) {
       if (!value) return true
       return data.label.indexOf(value) !== -1
     },
+    // 过滤树节点
+    filterTree() {
+      this.$refs.tree.filter(this.areaName);
+    },
     // 节点单击事件
     handleNodeClick(data) {
-      if (data.id === null) {
-        this.$message.warning('该节点不是设备不可点击');
-        return;
+      // 仅处理设备节点
+      if (data.type === 'device') {
+        this.queryParams.deviceCode = data.id;
+        this.handleQuery();
       }
-      this.queryParams.deviceCode = data.id
-      this.handleQuery()
-
+      // 区域节点不做处理
     },
-    /**第一个 id 非 null 的节点*/
+    /** 查找第一个设备节点 */
     findFirstValidNode(nodes) {
       for (const node of nodes) {
-        if (node.id !== null) {
+        if (node.type === 'device') {
           return node;
         }
         if (node.children && node.children.length > 0) {
@@ -362,12 +442,36 @@ export default {
       }
       return null;
     },
-    /**树结构*/
+    /** 树结构加载 */
     async getAreaTreeSelect() {
       await getDeviceTree(0, this.queryParams.meterCls, 0).then(response => {
-        this.areaOptions = response.data
+        this.areaOptions = response.data;
+        // 为树节点添加类型标识以便样式控制
+        this.$nextTick(() => {
+          this.addTypeToNodeAttrs();
+        });
       })
     },
+    /** 为树节点DOM添加type属性用于样式控制 */
+    addTypeToNodeAttrs() {
+      if (!this.$refs.tree) return;
+
+      const addAttr = (nodes) => {
+        nodes.forEach(node => {
+          if (node.data && node.data.type) {
+            const el = this.$refs.tree.$el.querySelector(`[data-node-key="${node.key}"] .el-tree-node__content`);
+            if (el) {
+              el.setAttribute('data-type', node.data.type);
+            }
+          }
+          if (node.children && node.children.length > 0) {
+            addAttr(node.children);
+          }
+        });
+      };
+
+      addAttr(this.$refs.tree.store.root.children);
+    },
 
     formatDateTime(dateTime) {
       if (!dateTime) return ''
@@ -425,20 +529,29 @@ export default {
 
     /** 搜索按钮操作 */
     handleQuery() {
-      this.queryParams.startRecTime = this.daterangeRecordTime[0]
-      this.queryParams.endRecTime = this.daterangeRecordTime[1]
+      // 处理日期范围,自动拼接时分秒
+      if (this.daterangeRecordTime && this.daterangeRecordTime.length === 2) {
+        this.queryParams.startRecTime = this.daterangeRecordTime[0] + ' 00:00:00';
+        this.queryParams.endRecTime = this.daterangeRecordTime[1] + ' 23:59:59';
+      } else {
+        this.queryParams.startRecTime = null;
+        this.queryParams.endRecTime = null;
+      }
+
       if (this.activeTab === 'first') {
         this.queryParams.meterCls = '45'
-       // this.queryParams.pageNum = 1
         this.getElecList()
+        // 获取用电统计数据
+        this.getNumElecMeterH();
       } else if (this.activeTab === 'second') {
         this.queryParams.meterCls = '70'
-       // this.queryParams.pageNum = 1
         this.getWaterList()
+        // 获取用水统计数据
+        this.getNumWaterMeterH();
       }
-      // 获取统计数据
-      this.getNumElecMeterH();
     },
+
+    // 获取用电统计数据
     async getNumElecMeterH() {
       const query = {
         deviceCode: this.queryParams.deviceCode,
@@ -449,13 +562,31 @@ export default {
         const response = await getNumElecMeterH(query);
         this.numElecMeterHData = response.data;
       } catch (error) {
-        this.$message.error("获取统计数据失败");
+        this.$message.error("获取用电统计数据失败");
+      }
+    },
+
+    // 获取用水统计数据
+    async getNumWaterMeterH() {
+      const query = {
+        deviceCode: this.queryParams.deviceCode,
+        startRecTime: this.queryParams.startRecTime,
+        endRecTime: this.queryParams.endRecTime,
+      };
+      try {
+        const response = await getNumWaterMeterH(query);
+        this.numWaterMeterHData = response.data;
+      } catch (error) {
+        this.$message.error("获取用水统计数据失败");
       }
     },
+
     /** 重置按钮操作 */
     resetQuery() {
       this.daterangeRecordTime = []
       this.resetForm('queryForm')
+      // 重置时重新初始化默认时间范围
+      this.initDefaultDateRange();
       this.handleQuery()
     },
     /** 新增按钮操作 */
@@ -502,3 +633,116 @@ export default {
   }
 }
 </script>
+
+<style scoped>
+/* 树节点样式 */
+.tree-node {
+  display: flex;
+  align-items: center;
+  gap: 6px; /* 符号与文字之间的间距 */
+  height: 100%;
+}
+
+/* 字符标识样式 */
+.node-symbol {
+  display: inline-block;
+  width: 16px; /* 固定宽度确保对齐 */
+  text-align: center;
+}
+
+/* 区域节点符号样式 */
+.area-symbol {
+  color: #666; /* 深灰色 */
+}
+
+/* 设备节点符号样式 */
+.device-symbol {
+  color: #337ab7; /* 蓝色 */
+}
+
+.node-label {
+  vertical-align: middle;
+}
+
+/* 鼠标样式控制 */
+.el-tree-node__content[data-type="area"] {
+  cursor: not-allowed;
+  opacity: 0.9;
+}
+
+.el-tree-node__content[data-type="device"] {
+  cursor: pointer;
+}
+
+/* 优化树节点hover效果 */
+.el-tree-node__content:hover {
+  background-color: #f5f7fa;
+}
+
+.el-tree-node__content[data-type="area"]:hover {
+  background-color: #f5f7fa;
+}
+
+/* 强调合计列的样式 - 若依框架适配 */
+/deep/ .total-column {
+  background-color: #f0f9ff !important;
+}
+
+/deep/ .total-column .cell {
+  position: relative;
+  padding-left: 12px !important;
+}
+
+/deep/ .total-column .cell::before {
+  content: '';
+  position: absolute;
+  left: 0;
+  top: 50%;
+  transform: translateY(-50%);
+  width: 4px;
+  height: 60%;
+  background-color: #409eff;
+  border-radius: 2px;
+}
+
+.total-value {
+  font-weight: bold !important;
+  font-size: 16px !important;
+  color: #2c3e50 !important;
+  display: inline-block;
+}
+
+.total-value::before {
+  content: '[';
+  margin-right: 2px;
+  color: #409eff !important;
+  font-weight: bold !important;
+  font-size: 16px;
+}
+
+.total-value::after {
+  content: ']';
+  margin-left: 2px;
+  color: #409eff !important;
+  font-weight: bold !important;
+  font-size: 16px;
+}
+
+/* 若依框架下的表格样式增强 */
+/deep/ .el-table .total-column {
+  background-color: #f0f9ff !important;
+}
+
+/deep/ .el-table .total-column td {
+  background-color: #f0f9ff !important;
+  font-weight: bold;
+}
+
+/* 确保样式在若依主题下生效 */
+.app-container /deep/ .el-table .total-column {
+  background-color: #f0f9ff !important;
+}
+
+.app-container /deep/ .el-table .total-column .cell {
+  font-weight: bold !important;
+}

+ 0 - 23
ems-ui-cloud/src/views/mgr/poweruse.vue

@@ -28,19 +28,6 @@
             </div>
           </div>
         </div>
-        <div>
-          <div class="ctl-container">
-            <SubTitle title="平均功率-15分钟" />
-            <el-date-picker v-model="powerDate" type="datetimerange" @change="getPowerChart"
-              :picker-options="pickerOptions" value-format="yyyy-MM-dd hh:mm:ss" range-separator="至"
-              start-placeholder="开始日期" end-placeholder="结束日期" align="right">
-            </el-date-picker>
-          </div>
-          <!--柱状图-->
-          <div class="container-block" style="margin-top: 20px;">
-            <BaseChart width="100%" height="350px" :option="powerLineOptions" />
-          </div>
-        </div>
 
       </el-tab-pane>
       <el-tab-pane v-for="item in facsCategoryOptions" :key="item.code" :label="item.name" :name="item.code">
@@ -95,16 +82,6 @@
             <div class="container-block" style="margin-top: 20px;">
               <BaseChart width="100%" height="300px" :option="barChartOptions" />
             </div>
-            <div>
-              <div class="ctl-container">
-                <SubTitle title="平均功率-15分钟" />
-              </div>
-              <!--柱状图-->
-              <div class="container-block" style="margin-top: 20px;">
-                <BaseChart width="100%" height="350px" v-if="activeName !== 'summery'"
-                  :option="equipPowerLineOptions" />
-              </div>
-            </div>
           </div>
         </el-col>
       </el-tab-pane>

部分文件因文件數量過多而無法顯示