<template> <div class="app-container flex" id="container"> <div class="left-nopx flex"> <div @click="(e) => selectEchart(e, '1')" :class="{ active: curEchart === '1' }"> <p class="title"> <span>年径流总量控制率</span> <span class="title_two">(合理性)</span> <el-popover placement="right" trigger="hover" :width="320" popper-class="noPadding" > <div class="popoverContent"> <div class="popoverContent_T">说明</div> <div class="popoverContent_M"> <div class="popoverContent_M_I">设计年径流总量控制率</div> <span>低于目标年径流总量控制率,评【差】</span> <br /> <span>高于目标年径流总量控制率5%以内,评【中】</span> <br /> <span>高于目标年径流总量控制率10%以内,评【良】</span> <br /> <span>高于目标年径流总量控制率10%以上,评【优】</span> <br /> <span>包含下限、不包含上限</span> </div> </div> <template #reference> <slot name="reference"> <img class="popoverIcon" src="../assets/images/icon.png" alt=""> </slot> </template> </el-popover> </p> <top v-if="isChart1" :data="LeftTop" @select-echart="() => selectEchart(null, '1')"></top> </div> <div @click="(e) => selectEchart(e, '2')" :class="{ active: curEchart === '2' }"> <p class="title"> <span>年径流污染控制率</span> <span class="title_two">(合理性)</span> <el-popover placement="right" trigger="hover" :width="320" popper-class="noPadding" > <div class="popoverContent"> <div class="popoverContent_T">说明</div> <div class="popoverContent_M"> <div class="popoverContent_M_I">设计年径流污染控制率</div> <span>低于目标年径流污染控制率,评【差】</span> <br /> <span>高于目标年径流污染控制率5%以内,评【中】</span> <br /> <span>高于目标年径流污染控制率10%以内,评【良】</span> <br /> <span>高于目标年径流污染控制率10%以上,评【优】</span> <br /> <span>包含下限、不包含上限</span> </div> </div> <template #reference> <slot name="reference"> <img class="popoverIcon" src="../assets/images/icon.png" alt=""> </slot> </template> </el-popover> </p> <top v-if="isChart1" :data="LeftCenter" @select-echart="() => selectEchart(null, '2')"></top> </div> <div @click="(e) => selectEchart(e, '3')" :class="{ active: curEchart === '3' }"> <p class="title"> <span>硬质地面率</span> <span class="title_two">(合理性)</span> <el-popover placement="right" trigger="hover" :width="280" popper-class="noPadding" > <div class="popoverContent"> <div class="popoverContent_T">说明</div> <div class="popoverContent_M"> <div class="popoverContent_M_I">设计的硬质地面率</div> <span>高于目标硬质地面率,评【差】</span> <br /> <span>低于目标硬质地面率5%以内,评【中】</span> <br /> <span>低于目标硬质地面率10%以内,评【良】</span> <br /> <span>低于目标硬质地面率10%以上,评【优】</span> <br /> <span>包含下限、不包含上限</span> <br /><br /> <span>除绿地、透水铺装、绿色屋顶外,均为硬质地面</span> </div> </div> <template #reference> <slot name="reference"> <img class="popoverIcon" src="../assets/images/icon.png" alt=""> </slot> </template> </el-popover> <span class="title_two all" >总数 <span class="all_num" v-if="isChart1">{{ LeftFoot.all }}</span >个</span > </p> <foot v-if="isChart1" :data="LeftFoot" @select-echart="() => selectEchart(null, '3')"></foot> </div> </div> <div class="center-nopx"> <ul class="center_ul-nopx flex"> <li v-for="(i, index) in centerData.yData" @click="changeClick(i, index, '8')" :class="{ changeTittle: i == changeDate }"> <div> <el-icon :size="22" :color="i" v-for="i in i.color" v-if="i.isStar"><StarFilled /></el-icon> <div class="label" v-if="index == 0"> <img style="margin: -3px 3px" v-if="index == 0" src="../assets/icons/monitor/xmpg_icon.png" alt="" /> <span>{{ i.label }}</span> <el-popover placement="right" trigger="hover" :width="280" popper-class="noPadding" > <div class="popoverContent"> <div class="popoverContent_T">说明</div> <div class="popoverContent_M"> <div class="popoverContent_M_I">项目评估</div> <span>控制项存在不达标,项目工程【不达标】</span> <br /><br /> <span>控制项全部达标</span> <br /> <span>得分项80以上,评【三星】</span> <br /> <span>得分项70以上,评【二星】</span> <br /> <span>得分项60以上,评【一星】</span> <br /> <span>得分项60以下,【无星级】</span> </div> </div> <template #reference> <slot name="reference"> <img class="popoverIcon" src="../assets/images/icon.png" alt=""> </slot> </template> </el-popover> </div> <div v-if="index == 0" style="text-align: right">总数 <span class="value">{{ i.value }}</span> 个</div> <div v-else style="margin-top: 4px"> <div style="margin-bottom: 4px;"> <img style="margin-left: 20px" v-if="index == 5" src="../assets/icons/monitor/erroir.png" alt="" /> </div> {{ i.label }} <span class="value"> {{ i.value }}</span> <span>个</span> </div> </div> </li> </ul> <div class="xmpgdj flex" v-show="!!tips"> <img src="../assets/icons/monitor/dq_icon.png" alt="" /> <div>{{ tips }}</div> </div> <div class="legend"> <div class="legend_item" v-for="item in legends"> <span :class="item.class" class="icon"></span> <span>{{ item.name }}</span> </div> </div> </div> <div class="right-nopx flex"> <div> <p class="title"> <span>投资及分布合理性</span> <span class="title_two all" >总数 <span class="all_num">{{ rightTopRef.all }}</span >个</span > <el-popover placement="right" trigger="hover" :width="420" popper-class="noPadding" > <div class="popoverContent"> <div class="popoverContent_T">说明</div> <div class="popoverContent_M"> <div class="popoverContent_M_I">建设工程投产比(海绵投资金额 / 设计设施调蓄量)</div> <span>在推荐投产比上下2.5%以内,评【优】</span> <br /> <span>推荐推荐投产比上下5%以内,评【良】</span> <br /> <span>推荐推荐投产比上下10%以内,评【中】</span> <br /> <span>推荐推荐投产比上下10%以上,评【差】</span> <br /> <span>包含下限、不包含上限</span> <br /><br /> <span>推荐投产比:取系统中填报项目投产比的平均值</span> </div> <div class="popoverContent_M"> <div class="popoverContent_M_I">设施分布合理性</div> <span>用计算每个分区的设计调蓄量对应的年径流总量控制率</span> <br /> <span>当80%(包含)以上的分区年径流总量控制率达标时,评【优】</span> <br /> <span>当60%(包含)以上的分区年径流总量控制率达标时,评【良】</span> <br /> <span>当50%(包含)以上的分区年径流总量控制率达标时,评【中】</span> <br /> <span>当40%(包含)以上的分区年径流总量控制率达标时,评【差】</span> <br /> <span>包含下限、不包含上限</span> <br /><br /> <span>年径流总量控制为差的,此项不参与评级。提示:年径流总量控制未达标,不具备评价设施分布合理性评价条件</span> </div> </div> <template #reference> <slot name="reference"> <img class="popoverIcon" src="../assets/images/icon.png" alt=""> </slot> </template> </el-popover> </p> <rightTop v-if="isChart1" :data="rightTopRef" :legend="true" @select-echart="(type) => selectEchart(null, type)" ref="rightTopRefs" ></rightTop> </div> <div @click="(e) => selectEchart(e, '4')" :class="{ active: curEchart === '4' }"> <p class="title"> <span>处置客水</span> <span class="title_two all" >总数 <span class="all_num">{{ rightCenterRef.all }}</span >个</span > <el-popover placement="right" trigger="hover" :width="420" popper-class="noPadding" > <div class="popoverContent"> <div class="popoverContent_T">说明</div> <div class="popoverContent_M"> <div class="popoverContent_M_I">处置客水</div> <span>在目标调蓄量以上(包含),5%以内(不包含)评【中】</span> <br /> <span>在目标调蓄量*5%以上(包含),10%以内(不包含)评【良】</span> <br /> <span>在目标调蓄量*10%以上(包含)评【优】</span> <br /> <span>包含下限、不包含上限</span> <br /><br /> <span>年径流总量控制为差的,此项不参与评级。提示:年径流总量控制未达标,不具备处置客水条件</span> </div> </div> <template #reference> <slot name="reference"> <img class="popoverIcon" src="../assets/images/icon.png" alt=""> </slot> </template> </el-popover> </p> <rightTop v-if="isChart1" :data="rightCenterRef" :legend="false" @select-echart="() => selectEchart(null, '4')"></rightTop> </div> <div @click="(e) => selectEchart(e, '7')" :class="{ active: curEchart === '7' }"> <p class="title"> <span>竖向合理性</span> <!-- <span class="title_two all" >总数 <span class="all_num">{{ LeftFoot.all }}</span >个</span > --> <el-popover placement="right" trigger="hover" :width="420" popper-class="noPadding" > <div class="popoverContent"> <div class="popoverContent_T">说明</div> <div class="popoverContent_M"> <div class="popoverContent_M_I">竖向合理性</div> <span>比较每个分区的服务面和设施高程,当存在不合理时,该分区竖向不合理</span> <br /> <span>当存在竖向不合理的分区时,评【存在不合理】</span> <br /> <span>当分区竖向全部合理时,评【合理】</span> </div> </div> <template #reference> <slot name="reference"> <img class="popoverIcon" src="../assets/images/icon.png" alt=""> </slot> </template> </el-popover> </p> <top v-if="isChart1" :data="rightFootRef" @select-echart="() => selectEchart(null, '7')"></top> </div> </div> <mapBox id="map" ref="mapRef" :isShowTool="false" @clickMap="clickMap" /> </div> <el-dialog v-model="rationalityData.visible" title="项目合理性" :close-on-click-modal="false" width="85%" :before-close="close" > <rationality :id="approveId" v-if="approveId" /> </el-dialog> <el-dialog v-model="evaluateData.visible" title="项目工程评估控制项" :close-on-click-modal="false" width="70%" :before-close="close" > <evaluate :id="evaluateId" v-if="evaluateId" /> </el-dialog> </template> <script setup> import { ref, reactive, computed, getCurrentInstance } from 'vue'; import mapBox from '@/components/Map'; import top from './home/leftComp/top'; import foot from './home/leftComp/foot'; import rightTop from './home/rightComp/top'; import { LeftTop, LeftCenter, LeftFoot, rightCenterRef, rightTopRef, rightFootRef, centerData } from './home/leftComp/index'; import { getHomePage } from '@/api/home' import rationality from './home/rationality' import evaluate from './home/evaluate' const { proxy } = getCurrentInstance() const isChart1 = ref(false); const changeDate = ref(null); const curEchart = ref('') const rightTopRefs = ref() let entiretyData = null const rationalityData = reactive({ visible: false }) const evaluateData = reactive({ visible: false }) const approveId = ref('1697084952290426881') const evaluateId = ref('1698943161636700162') const type1 = [ { name: '优', class: 'green' }, { name: '良', class: 'blue' }, { name: '中', class: 'yellow' }, { name: '差', class: 'red' }, ] const type2= [ { name: '三星', class: 'green' }, { name: '二星', class: 'blue' }, { name: '一星', class: 'yellow' }, { name: '无星', class: 'red' }, { name: '未达标', class: 'red1' } ] const type3 = [ { name: '优', class: 'green' }, { name: '良', class: 'blue' }, { name: '中', class: 'yellow' }, ] const type4 = [ { name: '合理', class: 'green' }, { name: '存在不合理', class: 'red' }, ] const legends = ref([]) const tipMap = new Map([ ['1', '年径流总量控制率合理性'], ['2', '年径流污染控制率合理性'], ['3', '硬质地面率合理性'], ['4', '处置客水情况'], ['5', '投资合理性'], ['6', '分布合理性'], ['7', '竖向合理性'], ['8', '项目评估等级'] ]) const tips = ref('') const close = () => { approveId.value = '' evaluateId.value = '' rationalityData.visible = false evaluateData.visible = false } //切换星级 const changeClick = async (v, index, queryType) => { curEchart.value = '' rightTopRefs.value.restSelect() if(changeDate.value && changeDate.value === v){ changeDate.value = null draw(null, '8') } else { changeDate.value = v const params = { queryType, param: index === 0 ? '' : v.label } const res = await getHomePage(params) if(res?.code !== 200) return draw(res?.data?.[0] || null, '8') } setLegend(changeDate.value ? queryType : '') setTips(changeDate.value ? queryType : '') }; const initData = async () => { const res = await getHomePage() if(res?.code !== 200) return console.log(res) entiretyData = res.data if(!entiretyData) return const data1 = entiretyData.find(item => item.queryType === '1') console.log(data1) LeftTop.value.xData = data1.echarts.xaxis.map((item, i) => ({ name: item, value: data1.echarts.yaxis[i] })) const data2 = entiretyData.find(item => item.queryType === '2') console.log(data2) LeftCenter.value.xData = data2.echarts.xaxis.map((item, i) => ({ name: item, value: data2.echarts.yaxis[i] })) const data3 = entiretyData.find(item => item.queryType === '3') console.log(data3) LeftFoot.value.xData = data3.echarts.xaxis LeftFoot.value.yData = data3.echarts.yaxis LeftFoot.value.all = LeftFoot.value.yData.reduce((n,v)=>{ return n += v }, 0) const data4 = entiretyData.find(item => item.queryType === '4') console.log(data4) rightCenterRef.value.xData = data4.echarts.xaxis rightCenterRef.value.yData = data4.echarts.yaxis rightCenterRef.value.all = rightCenterRef.value.yData.reduce((n,v)=>{ return n += v }, 0) const data7 = entiretyData.find(item => item.queryType === '7') console.log(data7) rightFootRef.value.xData = data7.echarts.xaxis.map((item, i) => ({ name: item, value: data7.echarts.yaxis[i] })) const data5 = entiretyData.find(item => item.queryType === '5') const data6 = entiretyData.find(item => item.queryType === '6') console.log(data5, data6) rightTopRef.value.xData = data5.echarts.xaxis rightTopRef.value.yData = data6.echarts.yaxis rightTopRef.value.defaultData = data5.echarts.yaxis rightTopRef.value.all = data5.projectCount const data8 = entiretyData.find(item => item.queryType === '8') console.log(data8) const centerYdata = JSON.parse(JSON.stringify(centerData.value.yData)) const totalItem = centerYdata.shift() const colors = centerYdata.map(item => item.color) const result= data8.echarts.xaxis.map((item, i) => ({ label: item, value: data8.echarts.yaxis[i], isStar: i < data8.echarts.xaxis.length - 1, color: colors[i] })) totalItem.value = result.reduce((n, v) => (n += v.value), 0) result.unshift({ ...totalItem, isStar: false }) console.log('result------', result) centerData.value.yData = result isChart1.value = true; setTimeout(() => { curEchart.value = '1' const data = entiretyData.find(item => item.queryType === curEchart.value) draw(data, curEchart.value) setLegend(curEchart.value) setTips(curEchart.value) }, 500) } const selectEchart = (e, queryType) => { if(e && e.target.localName === 'canvas') return changeDate.value = null if(['5', '6', ''].includes(queryType)){ curEchart.value = queryType } else { rightTopRefs.value.restSelect() if(curEchart.value && curEchart.value === queryType){ curEchart.value = '' } else { curEchart.value = queryType } } const data = entiretyData.find(item => item.queryType === curEchart.value) draw(data, curEchart.value) setLegend(curEchart.value) setTips(curEchart.value) } const draw = (data, queryType) => { console.log(data) proxy.$refs.mapRef.clear() setTimeout(() => { let mapData = [] if(data) { const colorObj = { '优': 'rgba(134, 216, 130, 0.8)', '良': 'rgb(21, 154, 255, 0.8)', '中': 'rgb(248, 170, 69, 0.8)', '差': 'rgb(255, 105, 105, 0.8)', '三星': 'rgba(134, 216, 130, 0.8)', '二星': 'rgb(21, 154, 255, 0.8)', '一星': 'rgb(248, 170, 69, 0.8)', '无星级': 'rgb(255, 105, 105, 0.8)', '未达标': 'rgb(255, 0, 0, 0.8)', '合理': 'rgba(134, 216, 130, 0.8)', '存在不合理': 'rgb(255, 105, 105, 0.8)' } mapData = data.homePageProjectInfoList.filter(item => item.sectionType) .filter(item => item.geometrys) .filter(item => item.ownType && item.ownType !== '-') .map(item => { let options = {} if (item.sectionType === 'point') { options = { // type: NewFiberMap.Enum.VectorType.ICON, type: NewFiberMap.Enum.VectorType.SPECIAL_CIRCLE, id: item.sectionType, data: { ...item, queryType }, name:(item.projectName || "").substr(0,10) + (item.projectName.length > 10 ? ".....":''), style: { radius: 10, clampToGround: false, material: new NewFiberMap.Material.CircleDiffuseMaterialProperty({ color: Cesium.Color.fromCssColorString(colorObj[item.ownType] || 'rgba(128, 128, 128, 1)'), speed: 20, }), }, labelOptions: { font: "17px PingFang SC", style: Cesium.LabelStyle.FILL_AND_OUTLINE, outlineColor: 'rgba(20,83,154,1)', outline: true, outlineWidth: 3, color: "#ffffff", pixelOffset: [0, -6], distanceDisplayCondition: [0, 2100000], }, geometrys: item.geometrys, } } else if (item.sectionType === 'line') { options = { type: NewFiberMap.Enum.VectorType.POLYLINE, id: item.sectionType, data: { ...item, queryType }, name:(item.projectName || "").substr(0,10) + (item.projectName.length > 10 ? ".....":''), geometrys: item.geometrys, style: { width: 5, material: colorObj[item.ownType] || 'rgba(128, 128, 128, 1)', color: colorObj[item.ownType] || 'rgba(128, 128, 128, 1)', clampToGround: true }, labelOptions: { font: "17px PingFang SC", style: Cesium.LabelStyle.FILL_AND_OUTLINE, outlineColor: 'rgba(20,83,154,1)', outline: true, outlineWidth: 3, color: "#ffffff", pixelOffset: [0, -6], distanceDisplayCondition: [0, 2100000], }, } } else if (item.sectionType === 'area') { options = { type: NewFiberMap.Enum.VectorType.POLYGON, style: { material: colorObj[item.ownType] || 'rgba(128, 128, 128, 1)', color: colorObj[item.ownType] || 'rgba(128, 128, 128, 1)' }, geometrys: item.geometrys, id: item.sectionType, data: { ...item, queryType }, name:(item.projectName || "").substr(0,10) + (item.projectName.length > 10 ? ".....":''), labelOptions: { font: "17px PingFang SC", style: Cesium.LabelStyle.FILL_AND_OUTLINE, outlineColor: 'rgba(20,83,154,1)', outline: true, outlineWidth: 3, color: "#ffffff", pixelOffset: [0, -6], distanceDisplayCondition: [0, 2100000], }, } } return options }) if(queryType === '8'){ mapData = mapData.filter(item => item.data.evaluateId) } else { mapData = mapData.filter(item => item.data.approveId) } } else { approveId.value = '' evaluateId.value = '' } if(!mapData.length) return let geojson = NewFiberMap.Data.ToGeoJSON.beansWktToGeoJson(mapData); toCenterByGeoJson(geojson); newfiberMap.geojsonToMap(geojson); }, 100) } const toCenterByGeoJson = (geojson) => { let coords = turf.getCoords(geojson.features[0].geometry).flat(); let flag = geojson.features.length == 1 && coords.length == 2; if (!!geojson.features.length && !flag) { newfiberMap.getMap().camera.flyTo({destination: new Cesium.Rectangle.fromDegrees(...turf.bbox(turf.transformScale(turf.bboxPolygon(turf.bbox(geojson)), 2)))}); } else { newfiberMap.setCenter({ "roll": 0.01658908985506884, "pitch": -87.24924906709752, "heading": 5.026928271138224, "lng": coords[0], "lat": coords[1], "height": 943.5996932813425 }) } } const clickMap = (feature) => { let geojson = turf.featureCollection(newfiberMap.getLayers([feature.key]).filter(i => !!i.properties).filter(i => i.properties.getValue().name == feature.name).map(i => turf.feature(Terraformer.WKT.parse(i.properties.getValue().geometrys)))); if(!!geojson.features.length) toCenterByGeoJson(geojson); if(!feature.properties?.data?._value) return proxy.$modal.msgError('数据异常!') const data = feature.properties.data._value if(data.queryType === '8'){ evaluateId.value = data.evaluateId evaluateData.visible = true } else { approveId.value = data.approveId rationalityData.visible = true } } const setLegend = (type) => { if(!type) return legends.value = [] if(type === '4'){ legends.value = type3 } else if(type === '7') { legends.value = type4 } else if(type=== '8') { legends.value = type2 } else { legends.value = type1 } } const setTips = (type) => { tips.value = tipMap.get(type) || '' } onMounted(() => { initData(); }); </script> <style scoped lang="scss"> @import './home/index.scss' </style>