Jelajahi Sumber

feat:修改图表切换bug

wangsisi 5 hari lalu
induk
melakukan
e3331f186e

+ 19 - 5
src/views/warningHome/components/chart_components/barChart.vue

@@ -3,7 +3,7 @@
 </template>
 
 <script setup>
-import { onMounted, ref, watch } from "vue";
+import { onMounted, ref, watch, nextTick, onUpdated } from "vue";
 import * as echarts from "echarts";
 import { barOption } from "./chartOption.js";
 import { deepClone } from "@/common/commonFun";
@@ -61,12 +61,12 @@ const initData = () => {
                 },
             ];
         } else {
+            // 移除 dataZoom
+            delete newOption.dataZoom;
             // 数据项较少时,恢复默认的 bottom 值
             newOption.grid.bottom = 10;
             // 数据项少时,可以旋转标签以避免重叠
             newOption.xAxis.axisLabel.rotate = dataLength >= 5 ? 30 : 0;
-            // 移除 dataZoom
-            delete newOption.dataZoom;
         }
     } else {
         // 数据为空时,清空图表
@@ -82,7 +82,8 @@ const initData = () => {
     // 更新 yAxis 的 formatter
     newOption.yAxis.axisLabel.formatter = props.yAxisFormatter;
 
-    myChart.setOption(newOption);
+    // 使用 notMerge: true 完全替换配置,确保切换时正确更新
+    myChart.setOption(newOption, { notMerge: true });
 };
 
 // 监听数据变化,更新图表
@@ -90,7 +91,11 @@ watch(
     () => [props.chartData, props.yAxisFormatter],
     () => {
         if (myChart) {
-            initData();
+            nextTick(() => {
+                initData();
+                // 确保图表正确渲染
+                myChart.resize();
+            });
         }
     },
     { deep: true }
@@ -100,6 +105,15 @@ onMounted(() => {
     myChart = echarts.init(chartDom.value);
     initData();
 });
+
+// 组件更新后,确保图表正确渲染
+onUpdated(() => {
+    if (myChart && chartDom.value) {
+        nextTick(() => {
+            myChart.resize();
+        });
+    }
+});
 </script>
 
 <style lang="scss" scoped>

+ 55 - 68
src/views/warningHome/components/chart_components/chartList.vue

@@ -4,7 +4,7 @@
             <chart-box :name="`${props.areaName}作物种植面积占比`">
                 <div class="box-content">
                     <div class="chart-dom">
-                        <pie-chart :chartData="pieChartData" :totalArea="totalArea"></pie-chart>
+                        <pie-chart :key="`pie-${activeBaseTab}`" :chartData="pieChartData" :totalArea="totalArea"></pie-chart>
                     </div>
                     <div class="box-bg">
                         <div class="legend-list">
@@ -22,31 +22,31 @@
                 </div>
             </chart-box>
         </div>
-        <div class="chart-item">
-            <chart-box :name="twoTitle">
+        <div class="chart-item" v-show="activeBaseTab === '物候期分布' || activeBaseTab === '预警分布'">
+            <chart-box :name="`${props.areaName}小麦物候进程分布`">
                 <div class="box-content">
                     <div class="chart-dom">
-                        <bar-chart :key="0" :chartData="regionChartData"></bar-chart>
+                        <bar-chart :key="`region-${activeBaseTab}`" :chartData="regionChartData"></bar-chart>
                     </div>
                     <div class="box-bg">{{ regionSummaryText }}</div>
                 </div>
             </chart-box>
         </div>
-        <div class="chart-item" v-if="activeBaseTab === '作物分布'">
+        <div class="chart-item" v-show="activeBaseTab === '作物分布'">
             <chart-box name="近三年主要作物种植面积变化趋势">
                 <div class="box-content">
                     <div class="chart-dom">
-                        <line-chart :chartData="areaTrendChartData"></line-chart>
+                        <line-chart :key="`trend-${activeBaseTab}`" :chartData="areaTrendChartData"></line-chart>
                     </div>
                     <div class="box-bg">暂无数据</div>
                 </div>
             </chart-box>
         </div>
         <div class="chart-item">
-            <chart-box :name="threeTitle">
+            <chart-box :name="threeTitle"> 
                 <div class="box-content">
                     <div class="chart-dom">
-                        <bar-chart :key="1" :chartData="yieldChartData" :yAxisFormatter="yAxisFormatter"></bar-chart>
+                        <bar-chart :key="`yield-${activeBaseTab}`" :chartData="yieldChartData" :yAxisFormatter="yAxisFormatter"></bar-chart>
                     </div>
                     <div class="box-bg">{{ yieldSummaryText }}</div>
                 </div>
@@ -59,7 +59,7 @@
 import chartBox from "@/components/chartBox.vue";
 import pieChart from "./pieChart.vue";
 import lineChart from "./lineChart.vue";
-import { computed, ref, watch } from "vue";
+import { computed, ref, watch,onMounted} from "vue";
 import { pieOption } from "./chartOption.js";
 import barChart from "./barChart.vue";
 
@@ -127,7 +127,6 @@ const legendData = computed(() => {
     });
 });
 
-const twoTitle = ref(`${props.areaName}作物区域占比`);
 const threeTitle = ref(`${props.areaName}作物预估产量对比`);
 
 // 监听 activeBaseTab 变化
@@ -148,18 +147,60 @@ watch(
     }
 );
 
+const currentYear = ref(2025);
+const currentQuarter = ref(1);
+
+// 监听 areaName 变化,更新标题
+watch(
+    () => props.areaName,
+    () => {
+        if (props.activeBaseTab === "物候期分布") {
+            threeTitle.value = `${props.areaName}小麦预告产量统计`;
+        } else if (props.activeBaseTab === "作物分布") {
+            threeTitle.value = `${props.areaName}作物预估产量对比`;
+        }
+    }
+);
+
+onMounted(() => {
+    // 初始化时调用一次
+    initData();
+    // eventBus.off("weatherTime:changeTime");
+    // eventBus.on("weatherTime:changeTime", ({index, year, quarter}) => {
+    //     currentYear.value = year;
+    //     currentQuarter.value = quarter;
+    //     initData() 
+    // });
+});
+
 const initData = () => {
+    // 切换 tab 时,先清空所有图表数据,避免显示旧数据
+    fetchStatSpeciesAreaYield();
     if (props.activeBaseTab === "物候期分布") {
-        twoTitle.value = `${props.areaName}小麦物候进程分布`;
+        // 清空其他 tab 的数据
+        pieChartData.value = [];
+        totalArea.value = 0;
+        areaTrendChartData.value = { xAxisData: [], series: [] };
+        
         threeTitle.value = `${props.areaName}小麦预告产量统计`;
         fetchStatPhenologyRatio();
         fetchStatRegionYieldRatio();
     } else if (props.activeBaseTab === "作物分布") {
-        twoTitle.value = `${props.areaName}作物区域占比`;
+        // 清空物候期分布的数据
+        regionChartData.value = { categories: [], values: [] };
+        regionSummaryText.value = "暂无数据";
+        
         threeTitle.value = `${props.areaName}作物预估产量对比`;
-        fetchStatSpeciesAreaYield();
-        fetchStatRegionAreaRatio();
         fetchAreaTrend();
+    } else {
+        // // 其他 tab(预警分布、农场分布、农服管理)时,清空所有图表数据
+        // pieChartData.value = [];
+        // totalArea.value = 0;
+        // regionChartData.value = { categories: [], values: [] };
+        // areaTrendChartData.value = { xAxisData: [], series: [] };
+        // yieldChartData.value = { categories: [], values: [] };
+        // regionSummaryText.value = "暂无数据";
+        // yieldSummaryText.value = "暂无数据";
     }
 };
 
@@ -364,60 +405,6 @@ const fetchAreaTrend = () => {
     });
 };
 
-const fetchStatRegionAreaRatio = () => {
-    const params = {
-        speciesId: "1",
-        adminCode: props.areaCode,
-        adminLevel: "",
-    };
-    VE_API.warning.fetchStatRegionAreaRatio(params).then((res) => {
-        if (res.code === 0 && res.data && res.data.length > 0) {
-            // 转换接口数据为图表格式
-            const categories = res.data.map((item) => item.adminName);
-            const values = res.data.map((item) => (item.areaRatio * 100).toFixed(2)); // 转换为百分比,保留两位小数
-
-            // 更新图表数据
-            regionChartData.value = {
-                categories,
-                values: values.map((v) => parseFloat(v)), // 转换为数字
-            };
-
-            // 找到最大占比的区域
-            let maxRatio = 0;
-            let maxRegion = "";
-            res.data.forEach((item) => {
-                if (item.areaRatio > maxRatio) {
-                    maxRatio = item.areaRatio;
-                    maxRegion = item.adminName;
-                }
-            });
-
-            // 更新摘要文字
-            if (maxRegion) {
-                const maxPercent = (maxRatio * 100).toFixed(1);
-                regionSummaryText.value = `${maxRegion}的作物种植面积最大,占比${maxPercent}%`;
-            } else {
-                regionSummaryText.value = "暂无数据";
-            }
-        } else {
-            // 接口返回空数据时,清空图表数据
-            regionChartData.value = {
-                categories: [],
-                values: [],
-            };
-            regionSummaryText.value = "暂无数据";
-        }
-    }).catch((error) => {
-        console.error("获取区域面积占比数据失败:", error);
-        // 错误时也清空数据
-        regionChartData.value = {
-            categories: [],
-            values: [],
-        };
-        regionSummaryText.value = "暂无数据";
-    });
-};
-
 const fetchStatSpeciesAreaYield = () => {
     const params = {
         year: 2025,

+ 17 - 3
src/views/warningHome/components/chart_components/lineChart.vue

@@ -3,7 +3,7 @@
 </template>
 
 <script setup>
-import { onMounted, ref, watch } from "vue";
+import { onMounted, ref, watch, nextTick, onUpdated } from "vue";
 import * as echarts from "echarts";
 import { lineOption } from "./chartOption.js";
 import { deepClone } from "@/common/commonFun";
@@ -34,7 +34,8 @@ const initData = () => {
         newOption.series = [];
     }
     
-    myChart.setOption(newOption);
+    // 使用 notMerge: true 完全替换配置,确保切换时正确更新
+    myChart.setOption(newOption, { notMerge: true });
 };
 
 // 监听数据变化,更新图表
@@ -42,7 +43,11 @@ watch(
     () => props.chartData,
     () => {
         if (myChart) {
-            initData();
+            nextTick(() => {
+                initData();
+                // 确保图表正确渲染
+                myChart.resize();
+            });
         }
     },
     { deep: true }
@@ -53,6 +58,15 @@ onMounted(() => {
     initData();
 });
 
+// 组件更新后,确保图表正确渲染
+onUpdated(() => {
+    if (myChart && chartDom.value) {
+        nextTick(() => {
+            myChart.resize();
+        });
+    }
+});
+
 </script>
 
 <style lang="scss" scoped>

+ 17 - 3
src/views/warningHome/components/chart_components/pieChart.vue

@@ -3,7 +3,7 @@
 </template>
 
 <script setup>
-import { onMounted, ref, watch } from "vue";
+import { onMounted, ref, watch, nextTick, onUpdated } from "vue";
 import * as echarts from "echarts";
 import { pieOption } from "./chartOption.js";
 import { deepClone } from "@/common/commonFun";
@@ -52,7 +52,8 @@ const initData = () => {
         };
     }
     
-    myChart.setOption(newOption);
+    // 使用 notMerge: true 完全替换配置,确保切换时正确更新
+    myChart.setOption(newOption, { notMerge: true });
 };
 
 // 监听数据变化,更新图表
@@ -60,7 +61,11 @@ watch(
     () => [props.chartData, props.totalArea],
     () => {
         if (myChart) {
-            initData();
+            nextTick(() => {
+                initData();
+                // 确保图表正确渲染
+                myChart.resize();
+            });
         }
     },
     { deep: true }
@@ -71,6 +76,15 @@ onMounted(() => {
     initData();
 });
 
+// 组件更新后,确保图表正确渲染
+onUpdated(() => {
+    if (myChart && chartDom.value) {
+        nextTick(() => {
+            myChart.resize();
+        });
+    }
+});
+
 </script>
 
 <style lang="scss" scoped>

+ 2 - 2
src/views/warningHome/components/mapLegend.vue

@@ -1,5 +1,5 @@
 <template>
-    <div class="map-legend">
+    <div class="map-legend" v-show="type !== '作物分布'">
         <div
             v-for="(item, index) in legendObj[type]"
             :key="`${type}-${item.label}-${index}`"
@@ -48,7 +48,7 @@ const legendObj = {
 <style lang="scss" scoped>
 .map-legend {
     position: fixed;
-    bottom: 18px;
+    bottom: 40px;
     right: 430px;
     padding: 6px 20px;
     display: flex;

+ 5 - 5
src/views/warningHome/index.vue

@@ -21,7 +21,7 @@
                         <div class="data-box" :class="{ active: activeBoxName === '面积' }">
                             <div class="data-value">
                                 <span>{{ regionCropData.plantArea }}</span
-                                >
+                                >亩
                             </div>
                             <div class="data-name">种植面积</div>
                         </div>
@@ -36,7 +36,7 @@
                         <div class="data-box" :class="{ active: activeBoxName === '产量' }">
                             <div class="data-value">
                                 <span>{{ regionCropData.expectYield }}</span
-                                >
+                                >吨
                             </div>
                             <div class="data-name">预估产量</div>
                         </div>
@@ -73,14 +73,14 @@
                     </template>
                 </el-tree>
             </div>
-            <div v-show="panelType === 0" class="warning-r right chart-wrap yes-events">
+            <div v-if="panelType === 0" class="warning-r right chart-wrap yes-events">
                 <chart-list :activeBaseTab="activeBaseTab" :areaCode="selectedAreaCode" :areaName="selectedAreaName"></chart-list>
                 <!-- <farmInfoGroup></farmInfoGroup> -->
             </div>
-            <div v-show="panelType === 1" class="warning-r right yes-events">
+            <div v-if="panelType === 1" class="warning-r right yes-events">
                 <farmInfoGroup></farmInfoGroup>
             </div>
-            <div v-show="panelType === 2" class="warning-r right yes-events">
+            <div v-if="panelType === 2" class="warning-r right yes-events">
                 <service-list></service-list>
             </div>
             <!-- 地图图例 -->