Explorar el Código

fix: 对接图例

lxf hace 2 semanas
padre
commit
1b44665d2d

+ 4 - 0
src/api/modules/layer.js

@@ -9,4 +9,8 @@ export default {
         url: config.base_url + "land_river/list",
         type: "get",
     },
+    legendList: {
+        url: config.base_url + "land_legend/get_by_code",
+        type: "get",
+    },
 }

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

@@ -8,12 +8,12 @@
             <!-- 父级:可勾选 -->
             <div class="category-header" @click="toggleExpand(category)">
                 <el-icon class="expand-icon" :class="{ expanded: category.expanded }"><CaretRight /></el-icon>
-                <el-checkbox
+                <!-- <el-checkbox
                     v-model="category.checked"
                     @change="handleCategoryChange(category)"
                     @click.stop
                     class="category-checkbox"
-                />
+                /> -->
                 <span class="category-name">{{ category.name }}</span>
             </div>
             <!-- 子级:仅显示 -->

+ 125 - 0
src/views/warningHome/components/legend.vue

@@ -0,0 +1,125 @@
+<template>
+    <div class="land-use-legend yes-events">
+        <div
+            v-for="item in legendData"
+            :key="item.id"
+            class="legend-category"
+        >
+            <div class="category-header">
+                <span
+                    class="color-dot"
+                    :style="{ background: item.color }"
+                ></span>
+                <span class="category-name">{{ item.name }}</span>
+            </div>
+        </div>
+    </div>
+</template>
+
+<script setup>
+import { ref } from "vue";
+
+
+const legendData = ref([]);
+const updateData = (data) => {
+    legendData.value = data;
+}
+
+defineExpose({
+    updateData,
+});
+
+</script>
+
+<style lang="scss" scoped>
+.land-use-legend {
+    position: fixed;
+    right: 35px;
+    bottom: 35px;
+    background: rgba(29, 29, 29, 0.86);
+    border: 1px solid rgba(255, 212, 137, 0.3);
+    border-radius: 8px;
+    padding: 16px;
+    // min-width: 170px;
+    max-height: 80vh;
+    z-index: 10;
+    color: #fff;
+
+    .legend-category {
+        margin-bottom: 6px;
+
+        &:last-child {
+            margin-bottom: 0;
+        }
+    }
+
+    .category-header {
+        display: flex;
+        align-items: center;
+        cursor: pointer;
+
+        .category-checkbox {
+            margin-right: 8px;
+            ::v-deep {
+                .el-checkbox__inner {
+                    background-color: rgba(255, 212, 137, 0.3);
+                    border-color: rgba(255, 212, 137, 0.6);
+                    width: 16px;
+                    height: 16px;
+                }
+                .el-checkbox__input.is-checked .el-checkbox__inner {
+                    background-color: #f7be5a;
+                    border-color: #f7be5a;
+                    &::after {
+                        border-color: #000;
+                        border-width: 2px;
+                        left: 5px;
+                        top: 1px;
+                        transform: rotate(45deg) scaleY(1);
+                    }
+                }
+            }
+        }
+
+        .expand-icon {
+            margin-right: 8px;
+            display: inline-block;
+            transition: transform 0.3s;
+            color: rgba(255, 212, 137, 0.6);
+            font-size: 18px;
+            text-align: center;
+            line-height: 1;
+
+            &.expanded {
+                transform: rotate(90deg);
+            }
+        }
+
+        .category-name {
+            font-size: 14px;
+            color: rgba(255, 212, 137, 0.9);
+        }
+    }
+
+    .category-children {
+        margin-left: 47px;
+        padding-left: 0;
+
+        .child-item {
+            display: flex;
+            align-items: center;
+            padding: 5px 0;
+            font-size: 14px;
+            color: rgba(255, 255, 255, 0.8);
+
+        }
+    }
+    .color-dot {
+        width: 12px;
+        height: 12px;
+        margin-right: 6px;
+        border-radius: 2px;
+    }
+}
+</style>
+

+ 32 - 3
src/views/warningHome/index.vue

@@ -17,7 +17,8 @@
             <div class="btn-common smart-farm-btn yes-events" @click="handleSmartFarmClick">智慧农场</div>
             <!-- 地图图例 -->
             <!-- <map-legend></map-legend> -->
-            <land-use-legend @change="handleLegendChange"></land-use-legend>
+            <!-- <land-use-legend @change="handleLegendChange"></land-use-legend> -->
+            <landUseLegend ref="legendRef"></landUseLegend>
             <div class="show-point yes-events" v-show="showPoint" @click="handleShowPointClick"></div>
         </div>
     </div>
@@ -31,7 +32,8 @@ import StaticMapLayers from "@/components/static_map_change/Layers.js";
 import StaticMapPointLayers from "@/components/static_map_change/pointLayer.js"
 import { onMounted, onUnmounted, ref, nextTick } from "vue";
 import fnHeader from "@/components/fnHeader.vue";
-import landUseLegend from "./components/landUseLegend.vue";
+// import landUseLegend from "./components/landUseLegend.vue";
+import landUseLegend from "./components/legend.vue";
 import WarningMap from "./warningMap";
 import trackDialog from "./components/trackDialog.vue";
 import AlarmLayer from "./map/alarmLayer";
@@ -72,9 +74,22 @@ const isLandRecognition = ref(false);
 const baseTabs = ["物候期分布", "长势等级", "水利", "灌渠与泵站", "资源", "导出报告"];
 const activeBaseTab = ref("物候期分布");
 
+const legendKeys = {
+    "物候期分布": "phenology",
+    "长势等级": "growth_status",
+    "水利": "water_conservancy",
+    "资源": "facility",
+}
+
 const warningLayers = ref({});
 const showPoint = ref(false)
 const handleBaseTabClick = (tab) => {
+    const legendKey = legendKeys[tab];
+    if (legendKey) {
+        nextTick(() => {
+            getLegendData(legendKey);
+        });
+    }
     activeBaseTab.value = tab;
     showPoint.value = false
     staticMapPointLayers.hidePoint()
@@ -104,6 +119,20 @@ const handleShowPointClick = () => {
     eventBus.emit("chat:showTrackDialog")
 }
 
+const legendRef = ref(null);
+const getLegendData = async (code) => {
+    const { data } = await VE_API.layer.legendList({ code });
+    // 接口返回的是带有 content 字段的对象,content 为 JSON 字符串,这里需要先解析
+    try {
+        const list = data && data.content ? JSON.parse(data.content) : [];
+        console.log('list', list);
+        legendRef.value && legendRef.value.updateData(Array.isArray(list) ? list : []);
+    } catch (e) {
+        console.error("解析图例 content 失败:", e, data);
+        legendRef.value && legendRef.value.updateData([]);
+    }
+};
+
 onMounted(async () => {
     // 使用 nextTick 确保 DOM 已经渲染完成,地图容器有正确的尺寸
     await nextTick();
@@ -234,7 +263,7 @@ const getWaterData = async () => {
     const { data } = await VE_API.layer.waterList();
     waterLayer.initData(data);
 
-    const { data: riverData } = await VE_API.layer.riverList();
+    const { data: riverData } = await VE_API.layer.riverList({}, {global: false});
     waterLayer.initRiver(riverData);
 };