Browse Source

地图功能-航线划设结果显示、空域栅格功能调整

gr 3 weeks ago
parent
commit
5acc5247bc

+ 2 - 2
src/assets/styles/index.scss

@@ -206,8 +206,8 @@
   left: var(--panel-left);
   left: var(--panel-left);
   top: var(--panel-gap);
   top: var(--panel-gap);
   visibility: visible;
   visibility: visible;
-  transition: left 0.5s ease-out;
-
+  transition: opacity 0.3s ease, transform 0.3s ease-out, left 0.5s ease-out;
+  
   &.collapse {
   &.collapse {
     left: var(--panel-gap);
     left: var(--panel-gap);
   }
   }

+ 255 - 281
src/views/home/cpns/FloatPanelKysg.vue

@@ -2,19 +2,19 @@
   <div class="slider-container" v-if="!layoutStore.footerCollapse">
   <div class="slider-container" v-if="!layoutStore.footerCollapse">
 
 
     <el-form v-model="form" inline class="top-form">
     <el-form v-model="form" inline class="top-form">
-      <el-form-item label="类型" prop="meshType">
+      <el-form-item label="类型:" prop="meshType">
         <el-radio-group v-model="form.meshType">
         <el-radio-group v-model="form.meshType">
           <el-radio label="二维" value="二维" />
           <el-radio label="二维" value="二维" />
           <el-radio label="三维" value="三维" />
           <el-radio label="三维" value="三维" />
         </el-radio-group>
         </el-radio-group>
       </el-form-item>
       </el-form-item>
       <el-form-item>
       <el-form-item>
-        <el-checkbox v-model="form.grade">三维评分</el-checkbox>
+        <el-checkbox v-model="form.grade">评分</el-checkbox>
       </el-form-item>
       </el-form-item>
       <el-form-item>
       <el-form-item>
         <el-checkbox v-model="form.deepShow">深度显示</el-checkbox>
         <el-checkbox v-model="form.deepShow">深度显示</el-checkbox>
       </el-form-item>
       </el-form-item>
-      <el-form-item label="范围" prop="meshRange">
+      <el-form-item label="范围:" prop="meshRange">
         <el-radio-group v-model="form.meshRange">
         <el-radio-group v-model="form.meshRange">
           <el-radio label="自适应" value="自适应" />
           <el-radio label="自适应" value="自适应" />
           <el-radio label="自定义" value="自定义" />
           <el-radio label="自定义" value="自定义" />
@@ -26,7 +26,7 @@
       </el-form-item>
       </el-form-item>
       <el-form-item v-if="form.meshRange === '行政区划'">
       <el-form-item v-if="form.meshRange === '行政区划'">
         <el-cascader v-model="form.district" @change="handleSelectDistrict" :options="districtList"
         <el-cascader v-model="form.district" @change="handleSelectDistrict" :options="districtList"
-          :props="cascaderProps" placeholder="请选择行政区划" />
+          :props="cascaderProps" placeholder="请选择行政区划" class=" w-32" />
       </el-form-item>
       </el-form-item>
     </el-form>
     </el-form>
 
 
@@ -34,8 +34,8 @@
     <div class="slider-bg single-slider">
     <div class="slider-bg single-slider">
       <div class="slider">
       <div class="slider">
         <div v-for="(point, index) in DenseData" :key="index" class="marker"
         <div v-for="(point, index) in DenseData" :key="index" class="marker"
-          :class="{ 'key-point': selectedPoint === index }"
-          :style="{ left: index * (100 / (DenseData.length - 1)) + '%' }" @click="selectPoint(index)">
+          :class="{ 'key-point': form.meshLevel === point.level }"
+          :style="{ left: index * (100 / (DenseData.length - 1)) + '%' }" @click="selectPoint(point)">
           <span class="label">{{ point.label }}</span>
           <span class="label">{{ point.label }}</span>
           <span class="des">{{ point.des }}</span>
           <span class="des">{{ point.des }}</span>
         </div>
         </div>
@@ -43,290 +43,217 @@
     </div>
     </div>
 
 
     <!-- 范围选择滑动条 -->
     <!-- 范围选择滑动条 -->
-    <div class="slider-bg range-slider">
-      <div class="slider">
-        <!-- 高亮背景 -->
-        <div class="range-highlight" v-if="rangeStart !== null && rangeEnd !== null" :style="{
-          left: rangeStart * (100 / (heightData.length - 1)) + 1.5 + '%',
-          width: (rangeEnd - rangeStart) * (100 / (heightData.length - 1)) + '%',
-        }"></div>
-        <!-- 数据点 -->
-        <div v-for="(point, index) in heightData" :key="index" class="marker" :class="{
-          'active': (rangeStart !== null && rangeEnd === null && index === rangeStart) || (rangeStart !== null && rangeEnd !== null && index >= rangeStart && index <= rangeEnd),
-          'hover': shouldHighlightOnHover(index),
-          'key-point': index === rangeStart || index === rangeEnd
-        }" :style="{ left: index * (100 / (heightData.length - 1)) + '%' }" @click="selectRange(index)"
-          @mouseover="handleMouseOver(index)" @mouseleave="handleMouseLeave">
-          <span class="label">{{ point.label }}</span>
-        </div>
-      </div>
-    </div>
+    <el-slider class="slider-bg range-slider" v-model="form.meshHeights" :min="0" :max="600" range :marks="marks"
+      tooltip-class="range-tooltip" placement="bottom" :format-tooltip="val=> val+'m'" />
+
   </div>
   </div>
 </template>
 </template>
 
 
-<script>
-import { ref, reactive, onMounted, onBeforeUnmount, watch } from 'vue';
+<script setup>
+import { ref, onBeforeUnmount, watch, reactive } from 'vue';
 import { addKysgScale, DrawPolygon, QueryDistrict, QueryCube, clearDraw } from "@/utils/map/addLayer.js";
 import { addKysgScale, DrawPolygon, QueryDistrict, QueryCube, clearDraw } from "@/utils/map/addLayer.js";
 import useLayoutStore from '@/store/layout';
 import useLayoutStore from '@/store/layout';
 import { useMapStore } from '@/store/map';
 import { useMapStore } from '@/store/map';
 import { GetDistrictTree } from '@/service/http';
 import { GetDistrictTree } from '@/service/http';
-import {geometryMeshEffect} from "@/utils/map/addTool.js";
-
-export default {
-  setup(props, { emit }) {
-    const mapStore = useMapStore()
-    const layoutStore = useLayoutStore()
-    const form = ref({
-      meshType: '二维',
-      grade: true,
-      deepShow:false,
-      meshRange: '自适应'
-    })
-
-    let lastEvaluation
-    let rings
-
-    const selectedPoint = ref(null); // 单点选择的索引
-    const rangeStart = ref(null); // 范围选择起点
-    const rangeEnd = ref(null); // 范围选择终点
-    const hoverIndex = ref(null); // 鼠标悬浮的索引
-
-    const districtList = ref([])
-
-    function handleSelectDistrict(val) {
-      QueryDistrict(val)
-    }
+import { geometryMeshEffect } from "@/utils/map/addTool.js";
+
+const mapStore = useMapStore()
+const layoutStore = useLayoutStore()
+
+const form = ref({
+  meshType: '二维',
+  grade: true,
+  deepShow: false,
+  meshRange: '自适应',
+  meshLevel: '',
+  meshHeights: [0, 0]
+})
+
+const marks = reactive({
+  0: '0m',
+  100: '100m',
+  200: '200m',
+  300: '300m',
+  400: '400m',
+  500: '500m',
+  600: '600m',
+})
+
+let lastEvaluation
+let rings
+
+const districtList = ref([])
+
+function handleSelectDistrict(val) {
+  QueryDistrict(val)
+}
 
 
-    const cascaderProps = {
-      expandTrigger: 'hover',
-      checkStrictly: true
-    }
+const cascaderProps = {
+  expandTrigger: 'hover',
+  checkStrictly: true
+}
 
 
-    watch(() => form.value.meshRange, (val) => {
-      console.log(val)
-      clearDraw()
-      clearQueryCube()
-      rings = null
-      if (val === '自适应') {
-        layoutStore.toggleGlobalLoading(true)
-        setTimeout(() => {
-          layoutStore.toggleGlobalLoading(false)
-        }, 3000);
-        addKysgScale(true)
-        clearPoints()
-      } else {
-        addKysgScale(false)
-        if (val === '行政区划' && !districtList.value.length) {
-          GetDistrictTree().then(res => {
-            if (!Array.isArray(res.data)) {
-              ElMessage({ offset: 90, type: 'warning', message: '行政区划获取失败' })
-              return
-            }
-            districtList.value = res.data
-          }).catch(() => {
-            ElMessage({ offset: 90, type: 'warning', message: '行政区划获取失败' })
-          })
+watch(() => form.value.meshRange, (val) => {
+  console.log(val)
+  clearDraw()
+  clearQueryCube()
+  rings = null
+  if (val === '自适应') {
+    layoutStore.toggleGlobalLoading(true)
+    setTimeout(() => {
+      layoutStore.toggleGlobalLoading(false)
+    }, 3000);
+    addKysgScale(true)
+    clearPoints()
+  } else {
+    addKysgScale(false)
+    if (val === '行政区划' && !districtList.value.length) {
+      GetDistrictTree().then(res => {
+        if (!Array.isArray(res.data)) {
+          ElMessage({ offset: 90, type: 'warning', message: '行政区划获取失败' })
+          return
         }
         }
-      }
-    }, { immediate: true })
-
-    watch(form, (val) => {
-      showGrid()
-    }, { deep: true })
-
-    function handleDraw() {
-      clearQueryCube();
-      getMesh("hide");
-      DrawPolygon({ hasZ: true })
+        districtList.value = res.data
+      }).catch(() => {
+        ElMessage({ offset: 90, type: 'warning', message: '行政区划获取失败' })
+      })
     }
     }
+  }
+}, { immediate: true })
+
+watch(form, (val) => {
+  showGrid()
+}, { deep: true })
+
+// watch(()=>form.value.meshHeights, (val) => {
+//   const sliderBtns = document.getElementsByClassName('el-slider__button-wrapper')
+//   if(!sliderBtns.length) return
+//   for(let i=0;i<sliderBtns.length;i++) {
+//     console.log(sliderBtns[i])
+//   }
+// }, { deep: true, immediate: true })
+
+function handleDraw() {
+  clearQueryCube();
+  getMesh("hide");
+  DrawPolygon({ hasZ: true })
+}
 
 
-    watch(() => mapStore.draw_geometry, (val) => {
-      rings = val?.rings
-      clearDraw();
-      getMesh("show");
-      showGrid()
-    }, { deep: true })
-
-    watch(() => mapStore.queryResult, (val) => {
-      rings = val[0].geometry.rings
-      showGrid()
-    }, { deep: true })
-
-    const DenseData = reactive([
-      // { label: '1/8″网格', level: 24, size: { x: 3.3055614085396883, y: 3.8513467134689563, z: 3.3678982462941303 }, des: '(3.9m)'},
-      { label: '1/4″网格', level: 23, size: { x: 6.7358, y: 7.7024, z: 6.6111 }, des: '(7m)' },
-      { label: '1/2″网格', level: 22, size: { x: 13.222978864358083, y: 15.406742669116284, z: 13.471596544164798 }, des: '(15m)' },
-      { label: '1′网格', level: 21, size: { x: 26.44107169853396, y: 30.815525255577086, z: 26.943221541824816 }, des: '(30.9m)' },
-      { label: '2′网格', level: 20, size: { x: 52.887881893650956, y: 61.627412608112536, z: 53.887012166300096 }, des: '(61m)' },
-      { label: '4′网格', level: 19, size: { x: 105.79869494173579, y: 123.43930203184209, z: 107.77356906534683 }, des: '(123.7m)' },
-      { label: '8′网格', level: 18, size: { x: 211.66439868324142, y: 246.49964316944533, z: 215.5489592181181 }, des: '(247.4m)' },
-      { label: '16′网格', level: 17, size: { x: 424.0518521273334, y: 492.09123171765896, z: 431.1052029077298 }, des: '(376.7m)' },
-      { label: '32′网格', level: 16, size: { x: 844.8477050379952, y: 990.1345935064928, z: 862.239544684298 }, des: '(746.4m)' },
-      { label: '1′网格', level: 15, size: { x: 1582.2726823222256, y: 1856.6079667204758, z: 1724.5956527210265 }, des: '(1850m)' },
-      // { label: '2′网格', level: 14, size: { x: 2984.4, y: 2984.4, z: 2984.4 }, des: '(2984.4m)'},
-    ]);
-
-    const heightData = reactive([
-      { label: "0m", value: 0 },
-      { label: "20m", value: 20 },
-      { label: "40m", value: 40 },
-      { label: "60m", value: 60 },
-      { label: "80m", value: 80 },
-      { label: "100m", value: 100 },
-      { label: "120m", value: 120 },
-      { label: "200m", value: 200 },
-      { label: "300m", value: 300 },
-      { label: "600m", value: 600 },
-      { label: "1000m", value: 1000 },
-    ]);
-
-    function clearPoints() {
-      selectedPoint.value = null
-      rangeStart.value = null
-      rangeEnd.value = null
-    }
+watch(() => mapStore.draw_geometry, (val) => {
+  rings = val?.rings
+  clearDraw();
+  getMesh("show");
+  showGrid()
+}, { deep: true })
+
+watch(() => mapStore.queryResult, (val) => {
+  rings = val[0].geometry.rings
+  showGrid()
+}, { deep: true })
+
+const DenseData = reactive([
+  // { label: '1/8″网格', level: 24, size: { x: 3.3055614085396883, y: 3.8513467134689563, z: 3.3678982462941303 }, des: '(3.9m)'},
+  { label: '1/4″网格', level: 23, size: { x: 6.7358, y: 7.7024, z: 6.6111 }, des: '(7m)' },
+  { label: '1/2″网格', level: 22, size: { x: 13.222978864358083, y: 15.406742669116284, z: 13.471596544164798 }, des: '(15m)' },
+  { label: '1′网格', level: 21, size: { x: 26.44107169853396, y: 30.815525255577086, z: 26.943221541824816 }, des: '(30.9m)' },
+  { label: '2′网格', level: 20, size: { x: 52.887881893650956, y: 61.627412608112536, z: 53.887012166300096 }, des: '(61m)' },
+  { label: '4′网格', level: 19, size: { x: 105.79869494173579, y: 123.43930203184209, z: 107.77356906534683 }, des: '(123.7m)' },
+  { label: '8′网格', level: 18, size: { x: 211.66439868324142, y: 246.49964316944533, z: 215.5489592181181 }, des: '(247.4m)' },
+  { label: '16′网格', level: 17, size: { x: 424.0518521273334, y: 492.09123171765896, z: 431.1052029077298 }, des: '(376.7m)' },
+  { label: '32′网格', level: 16, size: { x: 844.8477050379952, y: 990.1345935064928, z: 862.239544684298 }, des: '(746.4m)' },
+  { label: '1′网格', level: 15, size: { x: 1582.2726823222256, y: 1856.6079667204758, z: 1724.5956527210265 }, des: '(1850m)' },
+  // { label: '2′网格', level: 14, size: { x: 2984.4, y: 2984.4, z: 2984.4 }, des: '(2984.4m)'},
+]);
+
+function clearPoints() {
+  form.value.meshLevel = ''
+  form.value.meshHeights = [0, 0]
+}
 
 
-    // 单点选择逻辑
-    const selectPoint = (index) => {
-      selectedPoint.value = index;
-      showGrid()
-    };
-
-    // 范围选择逻辑
-    const selectRange = (index) => {
-      if (rangeStart.value === null || rangeEnd.value !== null) {
-        // 如果未选择起点或范围已完成,重新设置起点
-        rangeStart.value = index;
-        rangeEnd.value = null;
-      } else {
-        // 如果已经选择起点,设置终点
-        rangeEnd.value = index;
-        if (rangeEnd.value < rangeStart.value) {
-          // 保证起点小于终点
-          [rangeStart.value, rangeEnd.value] = [rangeEnd.value, rangeStart.value];
-        }
-      }
-      showGrid()
-    };
-
-    const handleMouseOver = (index) => {
-      hoverIndex.value = index;
-    };
-
-    const handleMouseLeave = () => {
-      hoverIndex.value = null;
-    };
-
-    const shouldHighlightOnHover = (index) => {
-      if ((hoverIndex.value !== null && rangeStart.value === null) || (rangeStart.value !== null && rangeEnd.value !== null)) {
-        // 如果未选择起点,只高亮当前悬浮的点
-        return index === hoverIndex.value;
-      } else if (hoverIndex.value !== null && rangeStart.value !== null && rangeEnd.value === null) {
-        // 如果已选择起点,且未选择终点,高亮起点到悬浮点之间的范围
-        return (
-          (index >= rangeStart.value && index <= hoverIndex.value) ||
-          (index <= rangeStart.value && index >= hoverIndex.value)
-        );
-      }
-      return false; // 不满足条件时,不高亮
-    };
+// 单点选择逻辑
+const selectPoint = (point) => {
+  form.value.meshLevel = point.level
+  showGrid()
+};
 
 
-    let timer_showGrid
+let timer_showGrid
 
 
-    // 显示网格
-    const showGrid = () => {
-      if (timer_showGrid) {
-        clearTimeout(timer_showGrid)
-      }
-      timer_showGrid = setTimeout(() => {
-        console.log('showGrid')
-        console.log('rings:',rings)
-        console.log('points',selectedPoint.value, rangeStart.value, rangeEnd.value)
-        if (!rings) return
-        if (selectedPoint.value===null || rangeStart.value===null || rangeEnd.value===null) return
-        clearQueryCube()
-        setTimeout(() => {
-          QueryCube({
-            id: 'query_cube_kysg',
-            evaluation: form.value.grade,
-            deepShow: form.value.deepShow,
-            show: true,
-            level: DenseData[selectedPoint.value].level,
-            minZ: heightData[rangeStart.value].value,
-            maxZ: heightData[rangeEnd.value].value,
-            rings: rings
-          })
-        }, 300);
-        lastEvaluation = form.value.grade
-      }, 1000)
-    };
-
-    function clearQueryCube() {
+// 显示网格
+const showGrid = () => {
+  if (timer_showGrid) {
+    clearTimeout(timer_showGrid)
+  }
+  timer_showGrid = setTimeout(() => {
+    console.log('showGrid')
+    console.log('rings:', rings)
+    console.log('form', form.value)
+    if (!rings) return
+    const { grade, deepShow, meshLevel, meshHeights } = form.value
+    if (!meshLevel || meshHeights.every(h => h === 0)) return
+    clearQueryCube()
+    setTimeout(() => {
       QueryCube({
       QueryCube({
         id: 'query_cube_kysg',
         id: 'query_cube_kysg',
-        evaluation: lastEvaluation,
-        show: false,
+        evaluation: grade,
+        deepShow: deepShow,
+        show: true,
+        level: meshLevel,
+        minZ: meshHeights[0],
+        maxZ: meshHeights[1],
+        rings: rings
       })
       })
-    }
+    }, 300);
+    lastEvaluation = grade
+  }, 1000)
+};
 
 
+function clearQueryCube() {
+  QueryCube({
+    id: 'query_cube_kysg',
+    evaluation: lastEvaluation,
+    show: false,
+  })
+}
 
 
-    //获取带高度三维体
-    function getMesh(status){
-      if(status == "hide"){
-        geometryMeshEffect({
-          id: 'sgzy_mesh',
-          status: "hide"
-        })
-        return
-      }
-      let height = heightData[rangeEnd.value].value - heightData[rangeStart.value].value;
-      let tempRings = [];
-      for(let i = 0; i < rings[0].length; i++){
-        tempRings.push([rings[0][i][0],rings[0][i][1],heightData[rangeStart.value].value - 0.01])
+//获取带高度三维体
+function getMesh(status) {
+  if (status == "hide") {
+    geometryMeshEffect({
+      id: 'sgzy_mesh',
+      status: "hide"
+    })
+    return
+  }
+  const [h1, h2] = form.value.meshHeights
+  console.log('h1&h2:', h1, h2)
+  let height = h2 - h1
+  let tempRings = [];
+  for (let i = 0; i < rings[0].length; i++) {
+    tempRings.push([rings[0][i][0], rings[0][i][1], h1 - 0.01])
+  }
+  debugger
+  geometryMeshEffect({
+    id: 'sgzy_mesh',
+    status: "show",
+    data: [{
+      type: 'polygon',
+      shape: {
+        height: height,
+        rings: [tempRings],
+        color: [0, 255, 0, 0.2]
       }
       }
-      debugger
-      geometryMeshEffect({
-        id: 'sgzy_mesh',
-        status:"show",
-        data: [{
-          type: 'polygon',
-          shape: {
-            height: height,
-            rings: [tempRings],
-            color: [0,255,0,0.2]
-          }
-        }]
-      })
+    }]
+  })
 
 
-    }
+}
 
 
-    onBeforeUnmount(() => {
-      addKysgScale(false);
-      getMesh("hide")
-      clearDraw()
-      clearQueryCube()
-    })
+onBeforeUnmount(() => {
+  addKysgScale(false);
+  getMesh("hide")
+  clearDraw()
+  clearQueryCube()
+})
 
 
-    return {
-      layoutStore,
-      form,
-      DenseData,
-      heightData,
-      selectedPoint,
-      rangeStart,
-      rangeEnd,
-      selectPoint,
-      selectRange,
-      handleMouseOver,
-      handleMouseLeave,
-      shouldHighlightOnHover,
-      handleDraw,
-      handleSelectDistrict,
-      cascaderProps,
-      districtList
-    };
-  },
-};
 </script>
 </script>
 
 
 <style lang="scss" scoped>
 <style lang="scss" scoped>
@@ -342,7 +269,8 @@ export default {
   visibility: visible;
   visibility: visible;
 }
 }
 
 
-.top-form {
+:deep(.top-form) {
+  height: 55px;
   display: flex;
   display: flex;
   flex-wrap: nowrap;
   flex-wrap: nowrap;
   align-items: center;
   align-items: center;
@@ -351,6 +279,10 @@ export default {
   .el-form-item {
   .el-form-item {
     margin-right: 10px;
     margin-right: 10px;
   }
   }
+
+  .el-radio-group {
+    flex-wrap: nowrap;
+  }
 }
 }
 
 
 .type-list {
 .type-list {
@@ -374,7 +306,6 @@ export default {
 .slider {
 .slider {
   position: relative;
   position: relative;
   height: 100%;
   height: 100%;
-  /* background-color: #2a2f3a; */
 }
 }
 
 
 .marker {
 .marker {
@@ -440,14 +371,6 @@ export default {
   color: #9DAAC7;
   color: #9DAAC7;
 }
 }
 
 
-.range-highlight {
-  position: absolute;
-  top: 3px;
-  height: 80%;
-  background-color: rgba(255, 212, 0, 0.2);
-  z-index: 1;
-}
-
 .single-slider {
 .single-slider {
   margin-top: 50px;
   margin-top: 50px;
 
 
@@ -460,15 +383,66 @@ export default {
   }
   }
 }
 }
 
 
-.range-slider {
+:deep(.range-slider) {
   margin-top: 53px;
   margin-top: 53px;
+  --el-slider-height: 22px;
 
 
-  .slider .marker {
-    z-index: 2;
+  .el-slider__runway {
+    background: none;
+
+    .el-slider__bar {
+      background: linear-gradient(0deg, rgba(255, 212, 0, 0.2) 0%, rgba(255, 212, 0, 0.6) 40%, rgba(255, 212, 0, 0.7) 50%, rgba(255, 212, 0, 0.6) 60%, rgba(255, 212, 0, 0.2) 100%);
+    }
+
+    .el-slider__button-wrapper {
+      top: -6px;
+
+      pointer-events: none;
+
+      .el-slider__button {
+        width: 14px;
+        height: 14px;
+        border-radius: 0;
+        transform: rotateZ(45deg);
+        box-shadow: 0 0 2px 3px #ffd9003e;
+        background-color: #ffd700;
+        border-color: #FFFCF5;
+        border-width: 2px;
+      }
+    }
+
+    .el-slider__marks .el-slider__marks-text {
+      top: -43px;
+      font-size: 16px;
+      color: #9DAAC7;
+    }
+
+    .el-slider__marks-stop {
+      top: 7px;
+      width: 8px;
+      height: 8px;
+      transform: translateX(-50%) rotateZ(45deg);
+      border: 2px solid #6495ed;
+      border-radius: 0;
+      background: transparent;
+    }
   }
   }
 
 
-  .label {
-    top: -25px;
+}
+</style>
+
+<style lang="scss">
+.range-tooltip {
+  // display: block !important;
+  background: none !important;
+  border: none !important;
+  margin-top: -7px;
+  span {
+    color: #ddd;
+    font-size: 16px;
+  }
+  .el-popper__arrow {
+    display: none;
   }
   }
 }
 }
 </style>
 </style>

+ 474 - 0
src/views/home/cpns/FloatPanelKysg_old.vue

@@ -0,0 +1,474 @@
+<template>
+  <div class="slider-container" v-if="!layoutStore.footerCollapse">
+
+    <el-form v-model="form" inline class="top-form">
+      <el-form-item label="类型" prop="meshType">
+        <el-radio-group v-model="form.meshType">
+          <el-radio label="二维" value="二维" />
+          <el-radio label="三维" value="三维" />
+        </el-radio-group>
+      </el-form-item>
+      <el-form-item>
+        <el-checkbox v-model="form.grade">三维评分</el-checkbox>
+      </el-form-item>
+      <el-form-item>
+        <el-checkbox v-model="form.deepShow">深度显示</el-checkbox>
+      </el-form-item>
+      <el-form-item label="范围" prop="meshRange">
+        <el-radio-group v-model="form.meshRange">
+          <el-radio label="自适应" value="自适应" />
+          <el-radio label="自定义" value="自定义" />
+          <el-radio label="行政区划" value="行政区划" />
+        </el-radio-group>
+      </el-form-item>
+      <el-form-item v-if="form.meshRange === '自定义'">
+        <el-button class="btn-secondary" @click="handleDraw">绘制</el-button>
+      </el-form-item>
+      <el-form-item v-if="form.meshRange === '行政区划'">
+        <el-cascader v-model="form.district" @change="handleSelectDistrict" :options="districtList"
+          :props="cascaderProps" placeholder="请选择行政区划" />
+      </el-form-item>
+    </el-form>
+
+    <!-- 单点选择滑动条 -->
+    <div class="slider-bg single-slider">
+      <div class="slider">
+        <div v-for="(point, index) in DenseData" :key="index" class="marker"
+          :class="{ 'key-point': selectedPoint === index }"
+          :style="{ left: index * (100 / (DenseData.length - 1)) + '%' }" @click="selectPoint(index)">
+          <span class="label">{{ point.label }}</span>
+          <span class="des">{{ point.des }}</span>
+        </div>
+      </div>
+    </div>
+
+    <!-- 范围选择滑动条 -->
+    <div class="slider-bg range-slider">
+      <div class="slider">
+        <!-- 高亮背景 -->
+        <div class="range-highlight" v-if="rangeStart !== null && rangeEnd !== null" :style="{
+          left: rangeStart * (100 / (heightData.length - 1)) + 1.5 + '%',
+          width: (rangeEnd - rangeStart) * (100 / (heightData.length - 1)) + '%',
+        }"></div>
+        <!-- 数据点 -->
+        <div v-for="(point, index) in heightData" :key="index" class="marker" :class="{
+          'active': (rangeStart !== null && rangeEnd === null && index === rangeStart) || (rangeStart !== null && rangeEnd !== null && index >= rangeStart && index <= rangeEnd),
+          'hover': shouldHighlightOnHover(index),
+          'key-point': index === rangeStart || index === rangeEnd
+        }" :style="{ left: index * (100 / (heightData.length - 1)) + '%' }" @click="selectRange(index)"
+          @mouseover="handleMouseOver(index)" @mouseleave="handleMouseLeave">
+          <span class="label">{{ point.label }}</span>
+        </div>
+      </div>
+    </div>
+  </div>
+</template>
+
+<script>
+import { ref, reactive, onMounted, onBeforeUnmount, watch } from 'vue';
+import { addKysgScale, DrawPolygon, QueryDistrict, QueryCube, clearDraw } from "@/utils/map/addLayer.js";
+import useLayoutStore from '@/store/layout';
+import { useMapStore } from '@/store/map';
+import { GetDistrictTree } from '@/service/http';
+import {geometryMeshEffect} from "@/utils/map/addTool.js";
+
+export default {
+  setup(props, { emit }) {
+    const mapStore = useMapStore()
+    const layoutStore = useLayoutStore()
+    const form = ref({
+      meshType: '二维',
+      grade: true,
+      deepShow:false,
+      meshRange: '自适应'
+    })
+
+    let lastEvaluation
+    let rings
+
+    const selectedPoint = ref(null); // 单点选择的索引
+    const rangeStart = ref(null); // 范围选择起点
+    const rangeEnd = ref(null); // 范围选择终点
+    const hoverIndex = ref(null); // 鼠标悬浮的索引
+
+    const districtList = ref([])
+
+    function handleSelectDistrict(val) {
+      QueryDistrict(val)
+    }
+
+    const cascaderProps = {
+      expandTrigger: 'hover',
+      checkStrictly: true
+    }
+
+    watch(() => form.value.meshRange, (val) => {
+      console.log(val)
+      clearDraw()
+      clearQueryCube()
+      rings = null
+      if (val === '自适应') {
+        layoutStore.toggleGlobalLoading(true)
+        setTimeout(() => {
+          layoutStore.toggleGlobalLoading(false)
+        }, 3000);
+        addKysgScale(true)
+        clearPoints()
+      } else {
+        addKysgScale(false)
+        if (val === '行政区划' && !districtList.value.length) {
+          GetDistrictTree().then(res => {
+            if (!Array.isArray(res.data)) {
+              ElMessage({ offset: 90, type: 'warning', message: '行政区划获取失败' })
+              return
+            }
+            districtList.value = res.data
+          }).catch(() => {
+            ElMessage({ offset: 90, type: 'warning', message: '行政区划获取失败' })
+          })
+        }
+      }
+    }, { immediate: true })
+
+    watch(form, (val) => {
+      showGrid()
+    }, { deep: true })
+
+    function handleDraw() {
+      clearQueryCube();
+      getMesh("hide");
+      DrawPolygon({ hasZ: true })
+    }
+
+    watch(() => mapStore.draw_geometry, (val) => {
+      rings = val?.rings
+      clearDraw();
+      getMesh("show");
+      showGrid()
+    }, { deep: true })
+
+    watch(() => mapStore.queryResult, (val) => {
+      rings = val[0].geometry.rings
+      showGrid()
+    }, { deep: true })
+
+    const DenseData = reactive([
+      // { label: '1/8″网格', level: 24, size: { x: 3.3055614085396883, y: 3.8513467134689563, z: 3.3678982462941303 }, des: '(3.9m)'},
+      { label: '1/4″网格', level: 23, size: { x: 6.7358, y: 7.7024, z: 6.6111 }, des: '(7m)' },
+      { label: '1/2″网格', level: 22, size: { x: 13.222978864358083, y: 15.406742669116284, z: 13.471596544164798 }, des: '(15m)' },
+      { label: '1′网格', level: 21, size: { x: 26.44107169853396, y: 30.815525255577086, z: 26.943221541824816 }, des: '(30.9m)' },
+      { label: '2′网格', level: 20, size: { x: 52.887881893650956, y: 61.627412608112536, z: 53.887012166300096 }, des: '(61m)' },
+      { label: '4′网格', level: 19, size: { x: 105.79869494173579, y: 123.43930203184209, z: 107.77356906534683 }, des: '(123.7m)' },
+      { label: '8′网格', level: 18, size: { x: 211.66439868324142, y: 246.49964316944533, z: 215.5489592181181 }, des: '(247.4m)' },
+      { label: '16′网格', level: 17, size: { x: 424.0518521273334, y: 492.09123171765896, z: 431.1052029077298 }, des: '(376.7m)' },
+      { label: '32′网格', level: 16, size: { x: 844.8477050379952, y: 990.1345935064928, z: 862.239544684298 }, des: '(746.4m)' },
+      { label: '1′网格', level: 15, size: { x: 1582.2726823222256, y: 1856.6079667204758, z: 1724.5956527210265 }, des: '(1850m)' },
+      // { label: '2′网格', level: 14, size: { x: 2984.4, y: 2984.4, z: 2984.4 }, des: '(2984.4m)'},
+    ]);
+
+    const heightData = reactive([
+      { label: "0m", value: 0 },
+      { label: "20m", value: 20 },
+      { label: "40m", value: 40 },
+      { label: "60m", value: 60 },
+      { label: "80m", value: 80 },
+      { label: "100m", value: 100 },
+      { label: "120m", value: 120 },
+      { label: "200m", value: 200 },
+      { label: "300m", value: 300 },
+      { label: "600m", value: 600 },
+      { label: "1000m", value: 1000 },
+    ]);
+
+    function clearPoints() {
+      selectedPoint.value = null
+      rangeStart.value = null
+      rangeEnd.value = null
+    }
+
+    // 单点选择逻辑
+    const selectPoint = (index) => {
+      selectedPoint.value = index;
+      showGrid()
+    };
+
+    // 范围选择逻辑
+    const selectRange = (index) => {
+      if (rangeStart.value === null || rangeEnd.value !== null) {
+        // 如果未选择起点或范围已完成,重新设置起点
+        rangeStart.value = index;
+        rangeEnd.value = null;
+      } else {
+        // 如果已经选择起点,设置终点
+        rangeEnd.value = index;
+        if (rangeEnd.value < rangeStart.value) {
+          // 保证起点小于终点
+          [rangeStart.value, rangeEnd.value] = [rangeEnd.value, rangeStart.value];
+        }
+      }
+      showGrid()
+    };
+
+    const handleMouseOver = (index) => {
+      hoverIndex.value = index;
+    };
+
+    const handleMouseLeave = () => {
+      hoverIndex.value = null;
+    };
+
+    const shouldHighlightOnHover = (index) => {
+      if ((hoverIndex.value !== null && rangeStart.value === null) || (rangeStart.value !== null && rangeEnd.value !== null)) {
+        // 如果未选择起点,只高亮当前悬浮的点
+        return index === hoverIndex.value;
+      } else if (hoverIndex.value !== null && rangeStart.value !== null && rangeEnd.value === null) {
+        // 如果已选择起点,且未选择终点,高亮起点到悬浮点之间的范围
+        return (
+          (index >= rangeStart.value && index <= hoverIndex.value) ||
+          (index <= rangeStart.value && index >= hoverIndex.value)
+        );
+      }
+      return false; // 不满足条件时,不高亮
+    };
+
+    let timer_showGrid
+
+    // 显示网格
+    const showGrid = () => {
+      if (timer_showGrid) {
+        clearTimeout(timer_showGrid)
+      }
+      timer_showGrid = setTimeout(() => {
+        console.log('showGrid')
+        console.log('rings:',rings)
+        console.log('points',selectedPoint.value, rangeStart.value, rangeEnd.value)
+        if (!rings) return
+        if (selectedPoint.value===null || rangeStart.value===null || rangeEnd.value===null) return
+        clearQueryCube()
+        setTimeout(() => {
+          QueryCube({
+            id: 'query_cube_kysg',
+            evaluation: form.value.grade,
+            deepShow: form.value.deepShow,
+            show: true,
+            level: DenseData[selectedPoint.value].level,
+            minZ: heightData[rangeStart.value].value,
+            maxZ: heightData[rangeEnd.value].value,
+            rings: rings
+          })
+        }, 300);
+        lastEvaluation = form.value.grade
+      }, 1000)
+    };
+
+    function clearQueryCube() {
+      QueryCube({
+        id: 'query_cube_kysg',
+        evaluation: lastEvaluation,
+        show: false,
+      })
+    }
+
+
+    //获取带高度三维体
+    function getMesh(status){
+      if(status == "hide"){
+        geometryMeshEffect({
+          id: 'sgzy_mesh',
+          status: "hide"
+        })
+        return
+      }
+      let height = heightData[rangeEnd.value].value - heightData[rangeStart.value].value;
+      let tempRings = [];
+      for(let i = 0; i < rings[0].length; i++){
+        tempRings.push([rings[0][i][0],rings[0][i][1],heightData[rangeStart.value].value - 0.01])
+      }
+      debugger
+      geometryMeshEffect({
+        id: 'sgzy_mesh',
+        status:"show",
+        data: [{
+          type: 'polygon',
+          shape: {
+            height: height,
+            rings: [tempRings],
+            color: [0,255,0,0.2]
+          }
+        }]
+      })
+
+    }
+
+    onBeforeUnmount(() => {
+      addKysgScale(false);
+      getMesh("hide")
+      clearDraw()
+      clearQueryCube()
+    })
+
+    return {
+      layoutStore,
+      form,
+      DenseData,
+      heightData,
+      selectedPoint,
+      rangeStart,
+      rangeEnd,
+      selectPoint,
+      selectRange,
+      handleMouseOver,
+      handleMouseLeave,
+      shouldHighlightOnHover,
+      handleDraw,
+      handleSelectDistrict,
+      cascaderProps,
+      districtList
+    };
+  },
+};
+</script>
+
+<style lang="scss" scoped>
+.slider-container {
+  position: absolute;
+  top: calc(var(--aside-height) - 246px - var(--footer-height));
+  left: calc(50% - 448px);
+  width: 896px;
+  height: 260px;
+  background: rgba(0, 10, 30, 0.6);
+  box-shadow: 0px 1px 6px 0px rgba(37, 37, 37, 0.6);
+  border: 1px solid #98baffb6;
+  visibility: visible;
+}
+
+.top-form {
+  display: flex;
+  flex-wrap: nowrap;
+  align-items: center;
+  margin: 15px 12px 0;
+
+  .el-form-item {
+    margin-right: 10px;
+  }
+}
+
+.type-list {
+  width: 100%;
+  height: 60px;
+  display: flex;
+  flex-direction: row;
+  justify-content: center;
+  align-items: center;
+}
+
+.slider-bg {
+  width: calc(100% - 10px);
+  height: 25px;
+  background: url('../../../assets/images/page/slider-bg.png') no-repeat;
+  background-size: 100% 100%;
+  padding: 0 70px 0 60px;
+  margin-right: 10px;
+}
+
+.slider {
+  position: relative;
+  height: 100%;
+  /* background-color: #2a2f3a; */
+}
+
+.marker {
+  position: absolute;
+  width: 25px;
+  height: 25px;
+  cursor: pointer;
+  transition: background-color 0.3s;
+
+  &::before {
+    content: '';
+    position: absolute;
+    display: block;
+    top: 9px;
+    left: 8px;
+    width: 8px;
+    height: 8px;
+    transform: rotateZ(45deg);
+    border: 2px solid #6495ed;
+  }
+
+  &.active::before {
+    border-color: #ffd700;
+  }
+
+  &.hover::before {
+    background-color: #ffd700;
+  }
+
+  &.key-point {
+    span {
+      font-weight: bold;
+      font-size: 18px;
+      color: #FFFFFF;
+    }
+
+    &::before {
+      border-color: #FFFCF5;
+      box-shadow: 0 0 4px 5px #ffd90062;
+      background-color: #ffd700;
+    }
+  }
+
+}
+
+.label {
+  position: absolute;
+  top: -45px;
+  left: 50%;
+  transform: translateX(-50%);
+  white-space: nowrap;
+  font-size: 16px;
+  color: #9DAAC7;
+}
+
+.des {
+  position: absolute;
+  top: -25px;
+  left: 50%;
+  transform: translateX(-50%);
+  white-space: nowrap;
+  font-size: 14px;
+  color: #9DAAC7;
+}
+
+.range-highlight {
+  position: absolute;
+  top: 3px;
+  height: 80%;
+  background-color: rgba(255, 212, 0, 0.2);
+  z-index: 1;
+}
+
+.single-slider {
+  margin-top: 50px;
+
+  .label {
+    font-size: 14px;
+  }
+
+  .key-point span {
+    font-size: 16px;
+  }
+}
+
+.range-slider {
+  margin-top: 53px;
+
+  .slider .marker {
+    z-index: 2;
+  }
+
+  .label {
+    top: -25px;
+  }
+}
+</style>

+ 232 - 179
src/views/home/cpns/PanelHxhs.vue

@@ -9,7 +9,7 @@
 
 
     <div class="flex-1 relative mb-4">
     <div class="flex-1 relative mb-4">
       <Transition name="emerge-left">
       <Transition name="emerge-left">
-        <el-form ref="formRef"  v-show="currentStep === 0"  :model="form" :rules="rules" label-position="left"
+        <el-form ref="formRef" v-show="currentStep === 0" :model="form" :rules="rules" label-position="left"
           size="large" class="p-form p-main">
           size="large" class="p-form p-main">
           <el-form-item label="名称" prop="name">
           <el-form-item label="名称" prop="name">
             <el-input v-model="form.name" clearable></el-input>
             <el-input v-model="form.name" clearable></el-input>
@@ -36,19 +36,19 @@
               <el-radio label="导入航线" value="03" />
               <el-radio label="导入航线" value="03" />
             </el-radio-group>
             </el-radio-group>
           </el-form-item>
           </el-form-item>
-          <div v-if="form.dataType === '01'" @click="changeDataType()"  class="msg-draw">
+          <div v-if="form.dataType === '01'" @click="changeDataType()" class="msg-draw">
             <img src="../../../assets/images/page/icon-draw.png" alt="">
             <img src="../../../assets/images/page/icon-draw.png" alt="">
             <span>重新绘制</span>
             <span>重新绘制</span>
           </div>
           </div>
           <template v-if="form.dataType === '02'">
           <template v-if="form.dataType === '02'">
             <el-form-item label="起飞场" prop="fromPort">
             <el-form-item label="起飞场" prop="fromPort">
-              <el-select v-model="form.fromPort" @change="showPort('fromPort')"  placeholder="">
+              <el-select v-model="form.fromPort" @change="showPort('fromPort')" placeholder="">
                 <el-option v-for="item in portOptions" :key="item.value" :label="item.label" :value="item.value"
                 <el-option v-for="item in portOptions" :key="item.value" :label="item.label" :value="item.value"
                   :disabled="item.value === form.toPort" />
                   :disabled="item.value === form.toPort" />
               </el-select>
               </el-select>
             </el-form-item>
             </el-form-item>
             <el-form-item label="降落场" prop="toPort">
             <el-form-item label="降落场" prop="toPort">
-              <el-select v-model="form.toPort" @change="showPort('toPort')"  placeholder="">
+              <el-select v-model="form.toPort" @change="showPort('toPort')" placeholder="">
                 <el-option v-for="item in portOptions" :key="item.value" :label="item.label" :value="item.value"
                 <el-option v-for="item in portOptions" :key="item.value" :label="item.label" :value="item.value"
                   :disabled="item.value === form.fromPort" />
                   :disabled="item.value === form.fromPort" />
               </el-select>
               </el-select>
@@ -94,13 +94,13 @@
               end="23:45" class="flex-1" />
               end="23:45" class="flex-1" />
           </el-form-item>
           </el-form-item>
           <el-form-item label="网格查询">
           <el-form-item label="网格查询">
-<!--            <el-checkbox v-model="form.grade">评分</el-checkbox>-->
+            <!--            <el-checkbox v-model="form.grade">评分</el-checkbox>-->
             <el-button class="btn-secondary ml-4" @click="queryCube()">查询网格</el-button>
             <el-button class="btn-secondary ml-4" @click="queryCube()">查询网格</el-button>
             <el-button class="btn-secondary ml-4" @click="closeCube()">关闭网格</el-button>
             <el-button class="btn-secondary ml-4" @click="closeCube()">关闭网格</el-button>
           </el-form-item>
           </el-form-item>
-<!--          <el-form-item label="辅助规划">-->
-<!--            <el-button class="btn-secondary" @click="getAutoPath()" >辅助规划</el-button>-->
-<!--          </el-form-item>-->
+          <!--          <el-form-item label="辅助规划">-->
+          <!--            <el-button class="btn-secondary" @click="getAutoPath()" >辅助规划</el-button>-->
+          <!--          </el-form-item>-->
         </el-form>
         </el-form>
       </Transition>
       </Transition>
       <Transition name="emerge-right">
       <Transition name="emerge-right">
@@ -108,7 +108,9 @@
           <ul class="list-plans flex justify-evenly mb-4">
           <ul class="list-plans flex justify-evenly mb-4">
             <li v-for="item in plans" class="pt-7 cursor-pointer hover:brightness-125"
             <li v-for="item in plans" class="pt-7 cursor-pointer hover:brightness-125"
               :class="{ 'active': item.id === currentPlan }" @click="handlePickPlan(item)">
               :class="{ 'active': item.id === currentPlan }" @click="handlePickPlan(item)">
-              <div class="text-base"><span class="tuli" :style="{backgroundColor:item.color}"></span>{{ item.feature }}</div>
+              <div class="text-base"><span class="tuli" :style="{ backgroundColor: item.color }"></span>{{ item.feature
+                }}
+              </div>
               <div class="text-sm py-1">距离&nbsp;<span class="num">{{ item.distance }}</span>&nbsp;公里</div>
               <div class="text-sm py-1">距离&nbsp;<span class="num">{{ item.distance }}</span>&nbsp;公里</div>
               <div class="text-sm">风险度:<span class="num">{{ item.risk }}</span></div>
               <div class="text-sm">风险度:<span class="num">{{ item.risk }}</span></div>
             </li>
             </li>
@@ -121,39 +123,44 @@
 
 
           <div v-if="isSafe" class="msg-safe mb-2">当前计划无冲突!</div>
           <div v-if="isSafe" class="msg-safe mb-2">当前计划无冲突!</div>
 
 
-          <div v-for="item in results" :key="item.title" class="mb-3">
-            <div class="title-sub">
-              {{ item.title }}
-              <div class="flex-1 flex justify-between items-center pl-2">
-                <span class="risk-label" :class="item.level === '低风险' ? 'green' : 'orange'">{{ item.level
-                  }}</span>
-                <span class="btn-inline">重新评估</span>
+          <template v-else>
+            <div v-for="item in results" :key="item.title" class="mb-3">
+              <div class="title-sub">
+                {{ item.title }}
+                <div class="flex-1 flex justify-between items-center pl-2">
+                  <span v-if="item.level" class="risk-label"
+                    :class="riskTypes.find(i => i.value === item.level).color">{{
+                      riskTypes.find(i => i.value === item.level).label
+                    }}</span>
+                  <i v-else></i>
+                  <span class="btn-inline" @click="handleReInspect">重新评估</span>
+                </div>
               </div>
               </div>
+              <table class="table-default stripe mt-2">
+                <thead>
+                  <tr>
+                    <th v-for="th in item.cols">{{ th }}</th>
+                    <th class="w-20">地图显示</th>
+                  </tr>
+                </thead>
+                <tbody>
+                  <tr v-for="row in item.details">
+                    <td v-for="key in Object.keys(item.cols)">{{ row[key] }}</td>
+                    <td class="w-20">
+                      <el-checkbox size="large" v-model="row.display"></el-checkbox>
+                    </td>
+                  </tr>
+                </tbody>
+              </table>
             </div>
             </div>
-            <table class="table-default stripe mt-2">
-              <thead>
-                <tr>
-                  <th v-for="th in item.cols">{{ th }}</th>
-                  <th class="w-20">地图显示</th>
-                </tr>
-              </thead>
-              <tbody>
-                <tr v-for="row in item.details">
-                  <td v-for="key in Object.keys(item.cols)">{{ row[key] }}</td>
-                  <td class="w-20">
-                    <el-checkbox size="large" v-model="row.display"></el-checkbox>
-                  </td>
-                </tr>
-              </tbody>
-            </table>
-          </div>
+          </template>
         </div>
         </div>
       </Transition>
       </Transition>
     </div>
     </div>
 
 
 
 
     <div class="text-center">
     <div class="text-center">
-      <el-button v-if="currentStep === 0" :disabled="!hasDraw"  class="btn-main" @click="toNext">下一步</el-button>
+      <el-button v-if="currentStep === 0" :disabled="!hasDraw" class="btn-main" @click="toNext">下一步</el-button>
       <template v-if="currentStep === 1">
       <template v-if="currentStep === 1">
         <el-button class="btn-main" @click="toPrev">上一步</el-button>
         <el-button class="btn-main" @click="toPrev">上一步</el-button>
         <el-button class="btn-main" @click="handlePreview">计划预演</el-button>
         <el-button class="btn-main" @click="handlePreview">计划预演</el-button>
@@ -165,12 +172,13 @@
 </template>
 </template>
 
 
 <script setup>
 <script setup>
-import {ref, onMounted, watch, onBeforeUnmount, computed} from 'vue';
-import {routePlanAll, saveRoute, searchQJCList} from "@/service/panelHxhs.js";
-import {geometryMeshEffect, getPathCube, showAndRedrawPath} from "@/utils/map/addTool.js";
+import { ref, onMounted, watch, onBeforeUnmount, computed } from 'vue';
+import { routePlanAll, saveRoute, searchQJCList } from "@/service/panelHxhs.js";
+import { geometryMeshEffect, getPathCube, showAndRedrawPath } from "@/utils/map/addTool.js";
 import useLayoutStore from '@/store/layout'
 import useLayoutStore from '@/store/layout'
-import {useMapStore} from "@/store/map.js";
-import {ElMessage} from "element-plus";
+import { useMapStore } from "@/store/map.js";
+import { riskTypes } from '@/utils/options';
+
 const currentStep = ref(0)
 const currentStep = ref(0)
 let currentPath = []; // 当前规划路径
 let currentPath = []; // 当前规划路径
 let allPathArr = []; // 所有路径
 let allPathArr = []; // 所有路径
@@ -183,7 +191,7 @@ const form = ref({
   dataType: '02',
   dataType: '02',
   height1: 60,
   height1: 60,
   height2: 80,
   height2: 80,
-  radius:5
+  radius: 5
 })
 })
 
 
 const portOptions = []
 const portOptions = []
@@ -197,47 +205,42 @@ const formRef = ref(null)
 const results = ref([
 const results = ref([
   {
   {
     title: '空域评估',
     title: '空域评估',
-    level: '低风险',
-    cols: { areaName: '冲突空域', height: '冲突高度' },
-    details: [
-      { areaName: '虹桥机场净空区', height: '112-120', display: false },
-      { areaName: '虹桥机场净空区', height: '112-120', display: false },
-    ]
+    level: null,
+    cols: { areaName: '冲突空域', time: '冲突时段', height: '冲突高度' },
+    details: []
   },
   },
   {
   {
     title: '计划冲突',
     title: '计划冲突',
-    level: '低风险',
-    cols: { areaName: '冲突空域', height: '冲突高度' },
-    details: [
-      { areaName: '合生汇-黄兴公园美团飞行计划', height: '112-120', display: false },
-      { areaName: '合生汇-黄兴公园美团飞行计划', height: '112-120', display: false },
-    ]
+    level: null,
+    cols: { areaName: '冲突空域', time: '冲突时段', height: '冲突高度' },
+    details: []
   },
   },
   {
   {
     title: '障碍物分析',
     title: '障碍物分析',
-    level: '高风险',
+    level: null,
     cols: { object: '冲突空域', height: '冲突高度' },
     cols: { object: '冲突空域', height: '冲突高度' },
-    details: [
-      { object: '建筑物', height: '112-120', display: false },
-      { object: '建筑物', height: '112-120', display: false },
-    ]
+    details: []
   },
   },
   {
   {
     title: '地面安全评估',
     title: '地面安全评估',
-    level: '高风险',
+    level: null,
     cols: { element: '要素', coverage: '覆盖率' },
     cols: { element: '要素', coverage: '覆盖率' },
-    details: [
-      { element: '路面', coverage: '40%', display: false },
-      { element: '道路', coverage: '20%', display: false },
-      { element: '综合占比', coverage: '60%', display: false },
-    ]
+    details: []
   }
   }
 ])
 ])
 
 
+function handleReInspect() {
+  layoutStore.toggleGlobalLoading(true)
+  closeCube()
+  setTimeout(() => {
+    queryCube()
+  }, 500);
+}
+
 let plans = ref([
 let plans = ref([
-  { id: '1',name:'originalPath', feature: '接近原方案',color:'#FFA500',  distance: '', risk: '50' },
-  { id: '2',name:'safePath',  feature: '地面风险较低',color:'#00FF00',  distance: '', risk: '10' },
-  { id: '3',name:'shortestPath',  feature: '距离最短',color:'#FFA5FF',  distance: '', risk: '50' },
+  { id: '1', name: 'originalPath', feature: '接近原方案', color: '#FFA500', distance: '', risk: '50' },
+  { id: '2', name: 'safePath', feature: '地面风险较低', color: '#00FF00', distance: '', risk: '10' },
+  { id: '3', name: 'shortestPath', feature: '距离最短', color: '#FFA5FF', distance: '', risk: '50' },
 ])
 ])
 
 
 const isSafe = computed(() => {
 const isSafe = computed(() => {
@@ -246,10 +249,56 @@ const isSafe = computed(() => {
 
 
 const hasDraw = ref(false)
 const hasDraw = ref(false)
 
 
+function formatResult(res) {
+  console.log('formatResult:', res)
+  const { groundSafety, lineConflictArray, obstacle, spaceConflictArray, spaceRisk, lineRisk } = res
+
+  results.value[0].level = spaceRisk
+  results.value[1].level = lineRisk
+  results.value[2].level = obstacle.risk
+  results.value[3].level = groundSafety.risk
+
+  results.value[0].details = spaceConflictArray.map(i => ({
+    areaName: i.gridName,
+    height: i.heightRange,
+    time: i.conflictTime,
+    display: false
+  }))
+
+  results.value[1].details = lineConflictArray.map(i => ({
+    areaName: i.gridName,
+    height: i.heightRange,
+    time: i.conflictTime,
+    display: false
+  }))
+
+  results.value[2].details = [
+    { time: '01-249:00-01-25 10-00', object: '建筑物', height: obstacle.buildingConflictHeight, display: false },
+    { time: '01-249:00-01-25 10-00', object: '建筑物缓冲区', height: obstacle.buildingBufferConflictHeight, display: false },
+  ]
+
+  const toPercent = (num) => {
+    return Math.round(num * 100) + '%'
+  }
+
+  results.value[3].details = [
+    { element: '道路', coverage: toPercent(groundSafety.road), display: false },
+    { element: '河流', coverage: toPercent(groundSafety.river), display: false },
+    { element: '绿化', coverage: toPercent(groundSafety.green), display: false },
+    { element: '综合占比', coverage: toPercent(groundSafety.road + groundSafety.river + groundSafety.green), display: false },
+  ]
+
+  layoutStore.toggleGlobalLoading(false)
+}
+
 
 
 function handlePickPlan(plan) {
 function handlePickPlan(plan) {
   currentPlan.value = plan.id;
   currentPlan.value = plan.id;
   showAllPathByType()
   showAllPathByType()
+
+  const conflicts = allPathArr[plan.name]?.conflicts
+  if (!conflicts) return
+  formatResult(conflicts.gridConflict)
 }
 }
 
 
 const currentPlan = ref('1');
 const currentPlan = ref('1');
@@ -266,19 +315,19 @@ function toNext() {
 function toPrev() {
 function toPrev() {
   currentStep.value = 0
   currentStep.value = 0
   getPathCube({
   getPathCube({
-    status:"hide",
+    status: "hide",
   })
   })
   hasDraw.value = false;
   hasDraw.value = false;
   showAndRedrawPath({
   showAndRedrawPath({
-    status:"hide",
+    status: "hide",
   });
   });
   geometryMeshEffect({
   geometryMeshEffect({
     id: "fromPort",
     id: "fromPort",
-    status:"hide"
+    status: "hide"
   })
   })
   geometryMeshEffect({
   geometryMeshEffect({
     id: "toPort",
     id: "toPort",
-    status:"hide"
+    status: "hide"
   })
   })
   geometryMeshEffect({
   geometryMeshEffect({
     "status": "hide",
     "status": "hide",
@@ -290,20 +339,20 @@ function toPrev() {
 function handleSave() {
 function handleSave() {
   saveRoute({
   saveRoute({
     ...form.value,
     ...form.value,
-    shape: JSON.stringify({paths:[currentPath]})
-  }).then(res =>{
-    if(res.data.code == 200 && res.data.msg == "success"){
+    shape: JSON.stringify({ paths: [currentPath] })
+  }).then(res => {
+    if (res.data.code == 200 && res.data.msg == "success") {
       ElMessage({
       ElMessage({
         type: 'success',
         type: 'success',
         message: '保存成功'
         message: '保存成功'
       })
       })
-    }else{
+    } else {
       ElMessage({
       ElMessage({
         type: 'error',
         type: 'error',
         message: '保存失败'
         message: '保存失败'
       })
       })
     }
     }
-  }).catch(()=>{
+  }).catch(() => {
     ElMessage({
     ElMessage({
       type: 'error',
       type: 'error',
       message: '保存失败'
       message: '保存失败'
@@ -316,10 +365,10 @@ function handlePreview() {
 }
 }
 
 
 //获取起降数据
 //获取起降数据
-function getQJCList(){
-  searchQJCList().then(res=>{
+function getQJCList() {
+  searchQJCList().then(res => {
     let data = res.data.data;
     let data = res.data.data;
-    data.forEach((item)=>{
+    data.forEach((item) => {
       portOptions.push({
       portOptions.push({
         label: item.name,
         label: item.name,
         value: item.id,
         value: item.id,
@@ -330,15 +379,15 @@ function getQJCList(){
   })
   })
 }
 }
 
 
-function showPort(id){
+function showPort(id) {
   geometryMeshEffect({
   geometryMeshEffect({
     id: id,
     id: id,
-    status:"show",
+    status: "show",
     data: [{
     data: [{
-      type: portOptions.find((item)=>item.value ==form.value[id]).geoType,
+      type: portOptions.find((item) => item.value == form.value[id]).geoType,
       shape: {
       shape: {
-        ...JSON.parse(portOptions.find((item)=>item.value ==form.value[id]).shape),
-        color: [0,255,0,0.7]
+        ...JSON.parse(portOptions.find((item) => item.value == form.value[id]).shape),
+        color: [0, 255, 0, 0.7]
       }
       }
     }]
     }]
   })
   })
@@ -346,190 +395,191 @@ function showPort(id){
 }
 }
 
 
 //起降场选择完成生成原始直线
 //起降场选择完成生成原始直线
-function showOriginPath(){
-  if(form.value.fromPort && form.value.toPort){
-    let formPoint = JSON.parse(portOptions.find((item)=>item.value ==form.value.fromPort).shape).point;
-    let toPoint = JSON.parse(portOptions.find((item)=>item.value ==form.value.toPort).shape).point;
+function showOriginPath() {
+  if (form.value.fromPort && form.value.toPort) {
+    let formPoint = JSON.parse(portOptions.find((item) => item.value == form.value.fromPort).shape).point;
+    let toPoint = JSON.parse(portOptions.find((item) => item.value == form.value.toPort).shape).point;
     debugger
     debugger
     currentPath = [
     currentPath = [
-      [formPoint.x, formPoint.y,formPoint.z],
-      [formPoint.x, formPoint.y,(form.value.height1 * 1 + form.value.height2 * 1)/2],
-      [(formPoint.x + toPoint.x)/2, (formPoint.y + toPoint.y)/2,(form.value.height1 * 1 + form.value.height2 * 1)/2],
-      [toPoint.x, toPoint.y,(form.value.height1 * 1 + form.value.height2 * 1)/2],
-      [toPoint.x, toPoint.y,toPoint.z]
+      [formPoint.x, formPoint.y, formPoint.z],
+      [formPoint.x, formPoint.y, (form.value.height1 * 1 + form.value.height2 * 1) / 2],
+      [(formPoint.x + toPoint.x) / 2, (formPoint.y + toPoint.y) / 2, (form.value.height1 * 1 + form.value.height2 * 1) / 2],
+      [toPoint.x, toPoint.y, (form.value.height1 * 1 + form.value.height2 * 1) / 2],
+      [toPoint.x, toPoint.y, toPoint.z]
     ]
     ]
     hasDraw.value = true;
     hasDraw.value = true;
     showAndRedrawPath({
     showAndRedrawPath({
-      status:"show",
-      path:currentPath
+      status: "show",
+      path: currentPath
     });
     });
   }
   }
 }
 }
 
 
 
 
 //查询网格
 //查询网格
-function queryCube(){
+function queryCube() {
   getPathCube({
   getPathCube({
-    status:"show",
-    paths:[currentPath]
+    status: "show",
+    paths: [currentPath]
   })
   })
 }
 }
 
 
 //关闭网格
 //关闭网格
-function closeCube(){
+function closeCube() {
   getPathCube({
   getPathCube({
-    status:"hide"
+    status: "hide"
   })
   })
 }
 }
 
 
 
 
 //辅助规划
 //辅助规划
-function getAutoPath(){
-    let paramsPaths = [];
-    currentPath.forEach((item) =>{
-      paramsPaths.push({
-        x:item[0],
-        y:item[1],
-        z:item[2]
-      })
+function getAutoPath() {
+  let paramsPaths = [];
+  currentPath.forEach((item) => {
+    paramsPaths.push({
+      x: item[0],
+      y: item[1],
+      z: item[2]
     })
     })
-    layoutStore.toggleGlobalLoading(true)
-    routePlanAll({
-      height1: form.value.height1,
-      height2: form.value.height2,
-      paths:paramsPaths
-    }).then(res=>{
-      layoutStore.toggleGlobalLoading(false)
-      debugger
-      let data = res.data.data;
-      allPathArr = data;
-      plans.value.forEach((item)=>{
-        item.distance = (data[item.name].length/1000).toFixed(2)
-      });
-      showAllPathByType();
+  })
+  layoutStore.toggleGlobalLoading(true)
+  routePlanAll({
+    height1: form.value.height1,
+    height2: form.value.height2,
+    paths: paramsPaths
+  }).then(res => {
+    debugger
+    let data = res.data.data;
+    allPathArr = data;
+    plans.value.forEach((item) => {
+      item.distance = (data[item.name].length / 1000).toFixed(2)
     });
     });
+    handlePickPlan(plans.value[0])
+  }).finally(() => {
+    layoutStore.toggleGlobalLoading(false)
+  })
 }
 }
 
 
 
 
-function showAllPathByType(){
+function showAllPathByType() {
   let otherPathArr = [];
   let otherPathArr = [];
-  if(currentPlan.value == 1){ //接近原路线
-    if(allPathArr.safePath.path.length > 0){
+  if (currentPlan.value == 1) { //接近原路线
+    if (allPathArr.safePath.path.length > 0) {
       otherPathArr.push({
       otherPathArr.push({
         "name": "安全路径",
         "name": "安全路径",
         "type": "polyline",
         "type": "polyline",
-        "shape":{
+        "shape": {
           "radius": 10,
           "radius": 10,
           "paths": allPathArr.safePath.path,
           "paths": allPathArr.safePath.path,
-          "color": [0,255,0,0.3]
+          "color": [0, 255, 0, 0.3]
         }
         }
       })
       })
     }
     }
-    if(allPathArr.shortestPath.path.length > 0){
+    if (allPathArr.shortestPath.path.length > 0) {
       otherPathArr.push({
       otherPathArr.push({
         "name": "贴合路径",
         "name": "贴合路径",
         "type": "polyline",
         "type": "polyline",
-        "shape":{
+        "shape": {
           "radius": 10,
           "radius": 10,
           "paths": allPathArr.shortestPath.path,
           "paths": allPathArr.shortestPath.path,
-          "color": [255,165,255,0.3]
+          "color": [255, 165, 255, 0.3]
         }
         }
       })
       })
     }
     }
     showAndRedrawPath({
     showAndRedrawPath({
-      status:"show",
-      path:allPathArr.originalPath.path,
-      color:[255,234,0,0.7]
+      status: "show",
+      path: allPathArr.originalPath.path,
+      color: [255, 234, 0, 0.7]
     });
     });
     currentPath = allPathArr.shortestPath.path;
     currentPath = allPathArr.shortestPath.path;
-  }else if(currentPlan.value == 2){  //安全
-    if(allPathArr.shortestPath.path.length > 0){
+  } else if (currentPlan.value == 2) {  //安全
+    if (allPathArr.shortestPath.path.length > 0) {
       otherPathArr.push({
       otherPathArr.push({
         "name": "最短路径",
         "name": "最短路径",
         "type": "polyline",
         "type": "polyline",
-        "shape":{
+        "shape": {
           "radius": 10,
           "radius": 10,
           "paths": allPathArr.shortestPath.path,
           "paths": allPathArr.shortestPath.path,
-          "color": [255,165,255,0.3]
+          "color": [255, 165, 255, 0.3]
         }
         }
       })
       })
     }
     }
-    if(allPathArr.originalPath.path.length > 0){
+    if (allPathArr.originalPath.path.length > 0) {
       otherPathArr.push({
       otherPathArr.push({
         "name": "贴合路径",
         "name": "贴合路径",
         "type": "polyline",
         "type": "polyline",
-        "shape":{
+        "shape": {
           "radius": 10,
           "radius": 10,
           "paths": allPathArr.originalPath.path,
           "paths": allPathArr.originalPath.path,
-          "color": [255,234,0,0.3]
+          "color": [255, 234, 0, 0.3]
         }
         }
       })
       })
     }
     }
     showAndRedrawPath({
     showAndRedrawPath({
-      status:"show",
-      path:allPathArr.safePath.path,
-      color:[0,255,0,0.7]
+      status: "show",
+      path: allPathArr.safePath.path,
+      color: [0, 255, 0, 0.7]
     });
     });
     currentPath = allPathArr.safePath.path;
     currentPath = allPathArr.safePath.path;
-  }else if(currentPlan.value == 3){  //最短
-    if(allPathArr.safePath.path.length > 0){
+  } else if (currentPlan.value == 3) {  //最短
+    if (allPathArr.safePath.path.length > 0) {
       otherPathArr.push({
       otherPathArr.push({
         "name": "安全路径",
         "name": "安全路径",
         "type": "polyline",
         "type": "polyline",
-        "shape":{
+        "shape": {
           "radius": 10,
           "radius": 10,
           "paths": allPathArr.safePath.path,
           "paths": allPathArr.safePath.path,
-          "color": [0,255,0,0.3]
+          "color": [0, 255, 0, 0.3]
         }
         }
       })
       })
     }
     }
-    if(allPathArr.originalPath.path.length > 0){
+    if (allPathArr.originalPath.path.length > 0) {
       otherPathArr.push({
       otherPathArr.push({
         "name": "贴合路径",
         "name": "贴合路径",
         "type": "polyline",
         "type": "polyline",
-        "shape":{
+        "shape": {
           "radius": 10,
           "radius": 10,
           "paths": allPathArr.originalPath.path,
           "paths": allPathArr.originalPath.path,
-          "color": [255,234,0,0.3]
+          "color": [255, 234, 0, 0.3]
         }
         }
       })
       })
     }
     }
     showAndRedrawPath({
     showAndRedrawPath({
-      status:"show",
-      path:allPathArr.shortestPath.path,
-      color:[ 225,165,255,0.7]
+      status: "show",
+      path: allPathArr.shortestPath.path,
+      color: [225, 165, 255, 0.7]
     });
     });
     currentPath = allPathArr.shortestPath.path;
     currentPath = allPathArr.shortestPath.path;
   }
   }
   geometryMeshEffect({
   geometryMeshEffect({
     "status": "show",
     "status": "show",
     "id": "drawAllPathOne",
     "id": "drawAllPathOne",
-    "data":otherPathArr
+    "data": otherPathArr
   })
   })
 }
 }
 
 
-function getDrawGeometry(){
-  if(mapStore.draw_geometry){
-    if(autoHeight){
+function getDrawGeometry() {
+  if (mapStore.draw_geometry) {
+    if (autoHeight) {
       let path = mapStore.draw_geometry.paths[0];
       let path = mapStore.draw_geometry.paths[0];
       let flyPathArr = [path[0]];
       let flyPathArr = [path[0]];
       path.forEach((item) => {
       path.forEach((item) => {
-        flyPathArr.push([item[0],item[1],(form.value.height1*1 + form.value.height2*1)/2 ]);
+        flyPathArr.push([item[0], item[1], (form.value.height1 * 1 + form.value.height2 * 1) / 2]);
       });
       });
-      flyPathArr.push([path[path.length-1][0],path[path.length-1][1],0]);
+      flyPathArr.push([path[path.length - 1][0], path[path.length - 1][1], 0]);
       hasDraw.value = true;
       hasDraw.value = true;
       showAndRedrawPath({
       showAndRedrawPath({
-        status:"show",
-        path:flyPathArr
+        status: "show",
+        path: flyPathArr
       });
       });
       autoHeight = false;
       autoHeight = false;
       currentPath = flyPathArr;
       currentPath = flyPathArr;
-    }else{
-      if(currentPlan.value == 1){  //最接近原航线,替换原航线数据
+    } else {
+      if (currentPlan.value == 1) {  //最接近原航线,替换原航线数据
         allPathArr.originalPath.path = mapStore.draw_geometry.paths[0];
         allPathArr.originalPath.path = mapStore.draw_geometry.paths[0];
-      }else if(currentPlan.value == 2){   //最安全
+      } else if (currentPlan.value == 2) {   //最安全
         allPathArr.safePath.path = mapStore.draw_geometry.paths[0];
         allPathArr.safePath.path = mapStore.draw_geometry.paths[0];
-      }else if(currentPlan.value == 3){   //最短
+      } else if (currentPlan.value == 3) {   //最短
         allPathArr.shortestPath.path = mapStore.draw_geometry.paths[0];
         allPathArr.shortestPath.path = mapStore.draw_geometry.paths[0];
       }
       }
       currentPath = mapStore.draw_geometry.paths[0];
       currentPath = mapStore.draw_geometry.paths[0];
@@ -537,41 +587,41 @@ function getDrawGeometry(){
   }
   }
 }
 }
 
 
-function changeDataType(){
-  if(form.value.dataType == '01'){ //手动
+function changeDataType() {
+  if (form.value.dataType == '01') { //手动
     autoHeight = true;
     autoHeight = true;
     hasDraw.value = true;
     hasDraw.value = true;
     showAndRedrawPath({
     showAndRedrawPath({
-      status:"show",
-      radius:form.value.radius
+      status: "show",
+      radius: form.value.radius
     });
     });
     geometryMeshEffect({
     geometryMeshEffect({
       id: "fromPort",
       id: "fromPort",
-      status:"hide"
+      status: "hide"
     })
     })
     geometryMeshEffect({
     geometryMeshEffect({
       id: "toPort",
       id: "toPort",
-      status:"hide"
+      status: "hide"
     })
     })
-  }else if(form.value.dataType == "02"){ //自动
+  } else if (form.value.dataType == "02") { //自动
     autoHeight = false;
     autoHeight = false;
     hasDraw.value = false;
     hasDraw.value = false;
     showAndRedrawPath({
     showAndRedrawPath({
-      status:"hide"
+      status: "hide"
     });
     });
-  }else if(form.value.dataType == "03"){  //导入航线
+  } else if (form.value.dataType == "03") {  //导入航线
     autoHeight = false;
     autoHeight = false;
     hasDraw.value = false;
     hasDraw.value = false;
     showAndRedrawPath({
     showAndRedrawPath({
-      status:"hide"
+      status: "hide"
     });
     });
     geometryMeshEffect({
     geometryMeshEffect({
       id: "fromPort",
       id: "fromPort",
-      status:"hide"
+      status: "hide"
     })
     })
     geometryMeshEffect({
     geometryMeshEffect({
       id: "toPort",
       id: "toPort",
-      status:"hide"
+      status: "hide"
     })
     })
   }
   }
 }
 }
@@ -580,7 +630,7 @@ function changeDataType(){
 
 
 
 
 
 
-onMounted(()=>{
+onMounted(() => {
   getQJCList()
   getQJCList()
 })
 })
 
 
@@ -591,7 +641,8 @@ watch(() => mapStore.draw_geometry, (val) => {
 })
 })
 
 
 watch(() => mapStore.cubeResult, (val) => {
 watch(() => mapStore.cubeResult, (val) => {
-  //showConflict()
+  formatResult(val)
+  layoutStore.toggleGlobalLoading(false)
 }, { deep: true })
 }, { deep: true })
 
 
 
 
@@ -636,12 +687,14 @@ onBeforeUnmount(() => {
       background: url('../../../assets/images/page/bg-plan.png');
       background: url('../../../assets/images/page/bg-plan.png');
       background-size: 100% !important;
       background-size: 100% !important;
       text-align: center;
       text-align: center;
-      .tuli{
+
+      .tuli {
         display: inline-block;
         display: inline-block;
         margin-right: 4px;
         margin-right: 4px;
         width: 10px;
         width: 10px;
         height: 10px;
         height: 10px;
       }
       }
+
       .num {
       .num {
         color: #8CBCFF;
         color: #8CBCFF;
       }
       }