2025-04-14 10:57:27 +08:00

591 lines
13 KiB
Vue

<template>
<div class="divHead">
<label :class="selRight==index?'divHeadSel':''" v-for="(item,index) in arrRight" :key="index"
@click="queryOrders">
{{item.name}}
</label>
</div>
<div style="">
<div class="divTag">
<uni-row>
<uni-col :span="8">
<label class="divbgColor mapFont"
style="padding: 5px 10px;border-radius:15px;font-weight: bold;border: 1px solid #80808061;"
@click="onShowDrawer">
<label style="margin-left: 5px;">
<uni-icons custom-prefix="iconfont" type="icon-ebikeqiehuan" :color="iconcolor"
:size="iconsize" />
</label>
切区
</label>
</uni-col>
<uni-col :span="14">
<label style="padding: 5px 15px;border-radius: 15px;background-color: #35374dc2;color: white;">
当前范围内可接单车辆
<label style="margin-left: 5px;">{{orderCount}}</label>
</label>
</uni-col>
</uni-row>
</div>
<div class="divLowerLeft">
<div class="divBtn">
<div style="padding: 10px 10px 5px 10px;">
<uni-icons custom-prefix="iconfont" type="icon-ebikejia" :color="iconcolor" :size="iconsize"
@click="onZoom('out')" />
</div>
<div style="padding: 5px 10px 10px 10px;">
<uni-icons custom-prefix="iconfont" type="icon-ebikejian" :color="iconcolor" :size="iconsize"
@click="onZoom('in')" />
</div>
</div>
<div class="divBtn">
<div class="divBtnTitle" @click="getLocation">
<uni-icons custom-prefix="iconfont" type="icon-ebikedingwei2" :color="iconcolor" :size="iconsize" />
<div>定位</div>
</div>
<div class="divBtnTitle" @click="refreshArea">
<uni-icons custom-prefix="iconfont" type="icon-ebikeshuaxin" :color="iconcolor" :size="iconsize" />
<div>刷新</div>
</div>
<div class="divBtnTitle" style="padding-bottom: 10px;" @click="()=>{showMore=!showMore}">
<uni-icons custom-prefix="iconfont" type="icon-ebikea-gengduo3x" :color="iconcolor"
:size="iconsize" />
<div>更多</div>
</div>
</div>
<div v-if="showMore" class="divLowerLeftMore">
<div class="divBtn divLowerLeftMoreBtn" @click="showRegionData">
<uni-icons custom-prefix="iconfont" type="icon-ebikeP" :color="showRegion?showColor:iconcolor"
:size="iconsize" />
<div :style="{color:showRegion?showColor:iconcolor}">站点</div>
</div>
<div class="divBtn divLowerLeftMoreBtn" @click="showBikeData">
<uni-icons custom-prefix="iconfont" type="icon-ebikedianpingchechongdianzhuang"
:color="showBike?showColor:iconcolor" :size="iconsize" />
<div :style="{color:showBike?showColor:iconcolor}">车辆</div>
</div>
</div>
</div>
<div class="divLowerRight">
<div @click="changeBatteries">
<uni-icons type="scan" :color="iconcolor" :size="iconsize" />
<div>批量换电</div>
</div>
</div>
<div class="divBottom">
<div class="divBottomBack">
<uni-row>
<uni-col :span="8">
<div class="divQuantity">
<div class="divQuantityCount" :style="{color:color_down}">2</div>
<div>
<label>
<uni-icons custom-prefix="iconfont" type="icon-ebikedianliang" :color="color_down"
:size="iconsize" />
</label>
低电量
</div>
</div>
</uni-col>
<uni-col :span="8">
<div class="divQuantity">
<div class="divQuantityCount" :style="{color:color_middle}">0</div>
<div>
<label><uni-icons custom-prefix="iconfont" type="icon-ebikedianliang1"
:color="color_middle" :size="iconsize" />
</label>
中电量
</div>
</div>
</uni-col>
<uni-col :span="8">
<div class="divQuantity">
<div class="divQuantityCount" :style="{color:color_high}">1</div>
<div>
<label><uni-icons custom-prefix="iconfont" type="icon-ebikedianliang2"
:color="color_high" :size="iconsize" />
</label>
高电量
</div>
</div>
</uni-col>
</uni-row>
<div style="padding-top: 10px;">
<uni-row>
<uni-col :span="6">
<div style="text-align: right;">电量筛选</div>
</uni-col>
<uni-col :span="16">
<slider show-value block-size="20" :value="quantityCount" :active-color="quantityColor"
:block-color="quantityColor" @change="quantityChange" />
</uni-col>
</uni-row>
</div>
</div>
</div>
<uni-drawer ref="showArea" mode="right" :width="300">
<div class="divArea">
<div v-for="(item,index) in arrAreaData" :key="index">
<div style="margin-bottom: 10px;padding-left: 10px;">
<label style="font-size: 1.2rem;">{{item.city}}</label>
</div>
<uni-row>
<uni-col :span="12" v-for="(data,indexd) in item.country" :key="indexd">
<div style="padding:2px 10px;margin-bottom:5px;">
<div style="line-height:30px;text-align:center;border-radius:20rpx;background-color:#8080801a;color:#056cec;"
@click="clickArea(data)">
{{data.name}}
</div>
</div>
</uni-col>
</uni-row>
</div>
</div>
</uni-drawer>
<map style="width: 100%;height: 100vh;" show-location id="mapRef" ref="mapRef" :scale="scale" :markers="markers"
:longitude="mapcenter.longitude" :latitude="mapcenter.latitude" :circles="circles" :polygons="polygons" />
</div>
</template>
<script setup>
import QQMapWX from "qqmap-wx-jssdk";
import * as map from "@/utils/map.js";
import {
ref,
onMounted,
getCurrentInstance
} from 'vue';
import {
showModelMessage
} from "@/utils/tools.js";
import * as api from "@/utils/api.js";
import {
findIndex,
find
} from "lodash";
var qqmapsdk = new QQMapWX({
key: map.sdkKey
});
//权限
const arrRight = ref([{
name: "换电",
lx: "changebatteries"
},
{
name: "调度",
lx: "deploy"
},
{
name: "维修",
lx: "maintenance"
},
{
name: "巡检",
lx: "xj"
},
{
name: "全部",
lx: "all"
}
]);
const selRight = ref(0);
const mapRef = ref("mapRef");
let mapContext = null;
const iconsize = 16;
const iconcolor = "#6f7777";
const showArea = ref(null);
const mapcenter = ref({
longitude: null,
latitude: null
});
const scale = ref(13);
const markers = ref([]); //点
const polygons = ref([]); //面
const polylines = ref([]); //线
const circles = ref([]); //圆
const orderCount = ref(0); //接单数量
const quantityCount = ref(100); // 电量
const color_down = "#EF4B4D"; //低电量
const color_middle = "#F29710"; //中电量
const color_high = "#3DB71A"; //高电量
const quantityColor = ref(color_high);
let locationPoint = null; //当前行政区划
const arrAreaData = ref(null); //行政区划
const mapData_opt = []; //运营区数据
let selArea = null; //选中行政区划
const showMore = ref(false); //显示更多
const showBike = ref(true); //显示车辆
const showRegion = ref(false); //显示站点
const showColor = "#1088FD";
//加载后
onMounted(() => {
mapContext = map.getMap("mapRef", getCurrentInstance());
getZone(() => {
//获取当前定位
map.getLoalcation(mapContext, (res) => {
const {
latitude: lat,
longitude: lng
} = res;
mapcenter.value = {
latitude: lat,
longitude: lng
};
map.reverseGeocoder(qqmapsdk, lng, lat, (res) => {
const {
ad_info: {
adcode,
city,
district
}
} = res;
const data = {
id: adcode,
name: district,
lat,
lng
};
locationPoint = {
city: "当前定位" + city,
country: [data]
}
const arrData=arrAreaData.value||[];
arrAreaData.value=arrData.splice(0, 0, locationPoint);
changeArea(data);
}, (res) => {
showModelMessage("切换区域失败!");
});
})
});
});
//获取行政区划
const getZone = (callback) => {
api.callOperateApi("ebikeRegion/getZone", null, "get").then((res) => {
const {
code,
data,
message
} = res;
if (code == 200) {
const arrData = [];
if (data && data.length > 0) {
data.map(item => {
const {
id,
name,
lng,
lat,
cityName
} = item;
let index = findIndex(arrData, {
city: cityName
});
let oData = arrData[index];
const obj = {
id,
name,
lat,
lng
};
if (index == "-1") {
index = 0;
oData = {
city: cityName,
country: [obj]
}
} else {
oData["country"].push(obj);
}
arrData[index] = oData;
});
}
if (locationPoint) {
arrData.splice(0, 0, locationPoint);
}
arrAreaData.value = arrData;
} else {
showModelMessage(message);
}
callback();
});
}
//定位
const getLocation = () => {
map.getLoalcation(mapContext, (res) => {
const {
latitude,
longitude
} = res;
})
}
//显示区域
const onShowDrawer = () => {
showArea.value.open();
}
//切换区域
const clickArea = (data) => {
changeArea(data);
showArea.value.close();
}
const changeArea = (data, refresh) => {
const {
id,
lng,
lat
} = data;
selArea = data;
const zoneId = id;
mapcenter.value = {
latitude: lat,
longitude: lng
};
let mapDataIndex = findIndex(mapData_opt, {
zoneId
});
if (!refresh) {
if (mapDataIndex > -1) {
loadMapData(mapData_opt[mapDataIndex]);
return;
}
}
uni.showLoading({
title: '加载中'
});
const params = {
zoneId
}
api.callOperateApi("ebikeRegion/getOperation", params, "get").then((res) => {
uni.hideLoading();
const {
code,
message,
data
} = res;
if (code == 200) {
const arrCircles = [];
const arrPolygons = [];
const arrRegionID = [];
data.map((item, index) => {
const {
shapeType,
regionId,
radius,
points
} = item;
arrRegionID.push(regionId);
const scolor = "#578FD4";
const fcolor = "#C0DAF5";
if (shapeType == 1) {
const {
longitude: lng,
latitude: lat
} = points[0];
arrCircles.push(map.addCirle(scolor, fcolor, lng, lat, radius));
} else if (shapeType == 2) {
const arrPoint = points.map(p => {
return {
longitude: p.longitude,
latitude: p.latitude
}
})
arrPolygons.push(map.addPolygon(scolor, fcolor, arrPoint));
}
});
let mapdata = {
zoneId,
arrCircles,
arrPolygons,
arrData: data
};
polygons.value = arrPolygons;
circles.value = arrCircles;
mapDataIndex = mapDataIndex == -1 ? mapData_opt.length : mapDataIndex;
mapData_opt[mapDataIndex] = mapdata;
//站点
if (arrRegionID.length == 0) return;
map.getRegionData(arrRegionID, (res) => {
const {
arrData,
arrCircles,
arrPolygons
} = res;
mapdata = {
...mapdata,
regionData: {
arrData,
arrCircles,
arrPolygons
}
};
mapData_opt[mapDataIndex] = mapdata;
loadMapRegionData(showRegion.value, mapdata);
//车辆
if (arrRegionID.length == 0) return;
map.getBikeData(arrRegionID, (res) => {
const {
arrData,
arrPoints
} = res;
mapdata = {
...mapdata,
bikeData: {
arrData,
arrPoints
}
};
mapData_opt[mapDataIndex] = mapdata;
loadMapBikeData(showBike.value, mapdata);
})
})
} else {
showModelMessage(message);
}
});
}
//地图数据
const loadMapData = (data) => {
loadMapBikeData(showBike.value, data);
loadMapRegionData(showRegion.value, data);
}
//显示隐藏车辆
const showBikeData = () => {
const show = !showBike.value
showBike.value = show;
const {
id
} = selArea;
const data = find(mapData_opt, {
zoneId: id
});
if (!data) return;
loadMapBikeData(show, data);
};
const loadMapBikeData = (show, data) => {
const {
bikeData
} = data;
if (show) {
if (bikeData) {
const {
arrData,
arrPoints
} = bikeData;
markers.value = arrPoints;
return;
}
}
markers.value = [];
}
//显示隐藏站点
const showRegionData = () => {
const show = !showRegion.value;
showRegion.value = show;
const {
id
} = selArea;
const data = find(mapData_opt, {
zoneId: id
});
if (!data) return;
loadMapRegionData(show,data);
}
const loadMapRegionData = (show, data) => {
const {
arrCircles,
arrPolygons,
regionData
} = data;
if (show) {
if (regionData) {
polygons.value = [...arrPolygons, ...regionData.arrPolygons];
circles.value = [...arrCircles, ...regionData.arrCircles];
return;
}
}
polygons.value = arrPolygons;
circles.value = arrCircles;
};
//刷新
const refreshArea = () => {
changeArea(selArea, true);
}
//缩放
const onZoom = (lx) => {
switch (lx) {
case "out":
scale.value = scale.value + 1;
break;
case "in":
scale.value = scale.value - 1;
break;
}
}
//电量筛选
const quantityChange = (e) => {
const {
detail: {
value
}
} = e;
quantityCount.value = value;
if (value <= 20) {
quantityColor.value = color_down;
} else if (value <= 60) {
quantityColor.value = color_middle;
} else {
quantityColor.value = color_high;
}
showModelMessage("该功能暂未实现!");
}
//批量换电
const changeBatteries = () => {
showModelMessage("该功能暂未实现!");
}
//查询工单
const queryOrders = (lx) => {
showModelMessage("该功能暂未实现!");
}
</script>
<style scoped>
@import url("home.css");
</style>