From d5bf590fac41ef1003b71456f0ed51eae2d2d45c Mon Sep 17 00:00:00 2001 From: 董国庆 <364620639@qq.com> Date: 星期三, 05 三月 2025 10:38:16 +0800 Subject: [PATCH] 首页页面 --- src/view/home/index.vue | 683 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 files changed, 677 insertions(+), 6 deletions(-) diff --git a/src/view/home/index.vue b/src/view/home/index.vue index 9ebfa7b..501e9d7 100644 --- a/src/view/home/index.vue +++ b/src/view/home/index.vue @@ -1,6 +1,144 @@ <template> <div class="flex homePage"> - <div class="leftMap"></div> + <!-- 头部 --> + <div class="mapTop"> + <!-- 车辆统计 --> + <div class="carCount"> + <div class="title">车辆统计</div> + <div class="fir"> + <div class="countCard"> + <img class="iconImg" src="../../assets//homeImg/img1.png" /> + <div> + <div class="name">出租车(辆)</div> + <div class="num">888</div> + </div> + </div> + <div class="countCard"> + <img class="iconImg" src="../../assets//homeImg/img2.png" /> + <div> + <div class="name">网约车(辆)</div> + <div class="num">888</div> + </div> + </div> + <div class="countCard"> + <img class="iconImg" src="../../assets//homeImg/img3.png" /> + <div> + <div class="name">客运(辆)</div> + <div class="num">888</div> + </div> + </div> + </div> + <div class="sec"> + <div class="countCard"> + <img class="iconImg" src="../../assets//homeImg/img4.png" /> + <div> + <div class="name">郊游(辆)</div> + <div class="num">888</div> + </div> + </div> + <div class="countCard"> + <img class="iconImg" src="../../assets//homeImg/img5.png" /> + <div> + <div class="name">公交车(辆)</div> + <div class="num">888</div> + </div> + </div> + <div class="countCard"> + <img class="iconImg" src="../../assets//homeImg/img6.png" /> + <div> + <div class="name">危险品(辆)</div> + <div class="num">888</div> + </div> + </div> + <div class="countCard"> + <img class="iconImg" src="../../assets//homeImg/img7.png" /> + <div> + <div class="name">货运(辆)</div> + <div class="num">888</div> + </div> + </div> + </div> + </div> + <!-- 车辆状态 --> + <div class="carStatus"> + <div class="title">车辆状态</div> + <div class="statusFir"> + <div class="statusCard"> + <div class="statusLeft"> + <div class="name">在线</div> + <div class="num">8888</div> + </div> + <el-progress + type="circle" + :width="20" + :show-text="false" + stroke-linecap="butt" + :percentage="25" + color="rgba(91, 143, 249, 1)" + define-back-color="rgba(91, 143, 249, 0.25)" + class="progressCard" + ></el-progress> + </div> + <div class="statusLine"></div> + <div class="statusCard"> + <div class="statusLeft"> + <div class="name">离线</div> + <div class="num">8888</div> + </div> + <el-progress + type="circle" + :width="20" + :show-text="false" + stroke-linecap="butt" + :percentage="25" + color="rgba(93, 112, 146, 1)" + define-back-color="rgba(93, 112, 146, 0.25)" + class="progressCard" + ></el-progress> + </div> + </div> + <div class="statusSec"> + <div class="statusCard"> + <div class="statusLeft"> + <div class="name">故障</div> + <div class="num">8888</div> + </div> + <el-progress + type="circle" + :width="20" + :show-text="false" + stroke-linecap="butt" + :percentage="25" + color="rgba(253, 83, 118, 1)" + define-back-color="rgba(253, 83, 118, 0.25)" + class="progressCard" + ></el-progress> + </div> + <div class="statusLine"></div> + <div class="statusCard"> + <div class="statusLeft"> + <div class="name">异常</div> + <div class="num">8888</div> + </div> + <el-progress + type="circle" + :width="20" + :show-text="false" + stroke-linecap="butt" + :percentage="25" + color="rgba(246, 189, 22, 1)" + define-back-color="rgba(246, 189, 22, 0.25)" + class="progressCard" + ></el-progress> + </div> + </div> + </div> + </div> + <!-- 左边 地图 --> + <div class="leftMap"> + <div class="mapContainer" id="mapContainer"></div> + </div> + <!-- 右边 内容 --> <div class="right"> <div class="firCard"> <div class="companyCard"> @@ -68,6 +206,8 @@ <script> import * as echarts from "echarts"; +import html2canvas from 'html2canvas'; +import AMapLoader from "@amap/amap-jsapi-loader"; export default { data() { return { @@ -86,12 +226,280 @@ { name: "滴滴网约车客运公司", value: 10 }, { name: "滴滴网约车客运公司", value: 0 }, ], //预警排行榜数据 + + map: null, //地图实例 + + carList: [], //车辆列表数据 }; }, - onload() {}, + created() { + //初始化窗口点击事件 + window.toCarDetail = (record) => { + console.log("111111111111222222", record); + this.toCarDetail(record); + }; + window.fullScreen = () => { + this.fullScreen(); + }; + window.shotScreen = () => { + this.shotScreen(); + }; + }, + onload() { + // if (this.carList.length > 0) { + // } + }, + mounted() { + let arr = [ + { + vehicleType: "出租车", + vehicleInfo: { + licensePlate: "川A12345", + vehicleModel: "BYD E6", + color: "Red", + }, + + latitude: 31.523333, + longitude: 105.444444, + }, + { + vehicleType: "公交车", + vehicleInfo: { + licensePlate: "川A67890", + vehicleModel: "Yutong ZK6120", + color: "Blue", + }, + + latitude: 31.512222, + longitude: 105.432111, + }, + { + vehicleType: "郊游", + vehicleInfo: { + licensePlate: "川A34567", + vehicleModel: "Toyota Coaster", + color: "White", + }, + + latitude: 31.498889, + longitude: 105.421111, + }, + { + vehicleType: "春运", + vehicleInfo: { + licensePlate: "川A90123", + vehicleModel: "King Long XMQ6120", + color: "Yellow", + }, + + latitude: 31.485556, + longitude: 105.412222, + }, + { + vehicleType: "快递物流车", + vehicleInfo: { + licensePlate: "川A45678", + vehicleModel: "JAC HFC5041", + color: "Green", + }, + + latitude: 31.472222, + longitude: 105.402111, + }, + { + vehicleType: "网约车", + vehicleInfo: { + licensePlate: "川A11111", + vehicleModel: "Geely GC2", + color: "Black", + }, + + latitude: 31.462222, + longitude: 105.392111, + }, + { + vehicleType: "客运", + vehicleInfo: { + licensePlate: "川A22222", + vehicleModel: "Yutong ZK6120", + color: "Gray", + }, + + latitude: 31.452222, + longitude: 105.382111, + }, + ]; + this.carList = arr; + + this.initMap(); + setTimeout(() => { + this.addMarker(this.carList, [105.444444, 31.523333]); + }, 1000); + }, methods: { - handleSelect(key, keyPath) { - console.log(key, keyPath); + // 初始化地图 + initMap() { + window._AMapSecurityConfig = { + securityJsCode: "37ce61ae86efa5ad82b649a277f5097c", + }; + AMapLoader.load({ + key: "67968c82f27c7e2cb9f40c1a9aa3042b", + version: "2.0", + plugins: [ + "AMap.ToolBar", + "AMap.AutoComplete", + "AMap.Geocoder", + "AMap.MarkerCluster", + ], + }) + .then((AMap) => { + this.map = new AMap.Map("mapContainer", { + center: [105.574542, 30.5061493], + zoom: 15, + }); + }) + .catch((e) => { + console.log(e); + }); + }, + + // 地图点位渲染 + addMarker(arr, centerList) { + this.map = new AMap.Map("mapContainer", { + resizeEnable: true, + zoom: 15, + center: centerList || [105.444444, 31.523333], + }); + + // var cluster; + // var _renderClusterMarker = function (context) { + // //context 为回调参数, + // //包含如下属性 marker:当前聚合点,count:当前聚合点内的点数量 + // var clusterCount = context.count; //聚合点内点数量 + // context.marker.setContent("<div>" + clusterCount + "</div>"); + // }; + // var renderMarker = function (context) { + // //context 为回调参数, + // var clusterCount = context.count; + // //包含如下属性 marker:当前聚合点,count:当前聚合点内的点数量 + // context.marker.setContent("<div>" + clusterCount + "</div>"); + // }; + // if (cluster) { + // cluster.setMap(null); + // } + // if (arr.length > 0) { + // let points = arr.map((item) => { + // return { + // lnglat: [Number(item.longitude), Number(item.latitude)], + // }; + // }); + // cluster = new AMap.MarkerCluster(this.map, points, { + // gridSize: 60, + // renderClusterMarker: _renderClusterMarker, //上述步骤的自定义聚合点样式 + // renderMarker: renderMarker, //上述步骤的自定义非聚合点样式 + // }); + // } + + var infoWindow = new AMap.InfoWindow({ + offset: new AMap.Pixel(30, 30), + autoMove: true, + anchor: "top-center", + }); + if (arr.length > 0) { + const iconMap = { + 出租车: { + icon: require("../../assets/homeImg/taxi.png"), + size: new AMap.Size(75, 37), + }, + 公交车: { + icon: require("../../assets/homeImg/bus.png"), + size: new AMap.Size(62, 34), + }, + 郊游: { + icon: require("../../assets/homeImg/risk.png"), + size: new AMap.Size(69, 32), + }, + 春运: { + icon: require("../../assets/homeImg/outing.png"), + size: new AMap.Size(61, 31), + }, + 快递物流车: { + icon: require("../../assets/homeImg/expressage.png"), + size: new AMap.Size(60, 31), + }, + 网约车: { + icon: require("../../assets/homeImg/online.png"), + size: new AMap.Size(75, 33), + }, + 客运: { + icon: require("../../assets/homeImg/passenger.png"), + size: new AMap.Size(69, 31), + }, + }; + arr.forEach((item, index) => { + const iconConfig = iconMap[item.vehicleType]; + let marker = new AMap.Marker({ + position: [Number(item.longitude), Number(item.latitude)], //经纬度对象,也可以是经纬度构成的一维数组[116.39, 39.9] + map: this.map, + zooms: [5, 20], + icon: new AMap.Icon({ + size: iconConfig.size, + image: iconConfig.icon, + imageSize: iconConfig.size, + // 图标取图偏移量 + imageOffset: new AMap.Pixel(0, 0), + }), + }); + marker.content = this.listRender(item); + marker.on("click", (e) => { + infoWindow.setContent(e.target.content); + infoWindow.open(this.map, e.target.getPosition()); + }); + }); + } + }, + listRender(record) { + return `<div style="background: #ffffff; padding: 24px 20px;z-index: 999"> + <div style="position: relative; width: 460px; height: 330px"> + <img + style="width: 460px; height: 330px; border-radius: 9px" id="monitoringCard" + src="https://zos.alipayobjects.com/rmsportal/jkjgkEfvpUPVyRjUImniVslZfWPnJuuZ.png" + /> + <div style="position: absolute; right: 11px; top: 10px"> + <!-- 全屏 --> + <div + style=" display: flex;flex-direction: column;align-items: center;justify-content: center; + background: #ffffff; padding: 3px 10px; border-radius: 6px;margin-bottom: 10px;" onclick="fullScreen()" > + <img + style="width: 20px; height: 20px" src="${require("../../assets//homeImg/full.png")}" /> + <div style="font-size: 12px;font-weight: 400; line-height: 17px; color: rgba(0, 0, 0, 0.88); " > 全屏</div> + </div> + <!-- 截屏 --> + <div + style="display: flex;flex-direction: column;align-items: center; justify-content: center; + background: #ffffff;padding: 3px 10px;border-radius: 6px; " onclick="shotScreen()"> + <img style="width: 20px; height: 20px" src="${require("../../assets//homeImg/slot.png")}" /> + <div style="font-size: 12px; font-weight: 400; line-height: 17px; color: rgba(0, 0, 0, 0.88);"> 截屏</div> + </div> + </div> + </div> + <div style="display: flex;justify-content: space-between;margin-top: 15px;margin-bottom: 12px;"> + <div style=" font-weight: 500;font-size: 18px;color: rgba(0, 0, 0, 0.85);line-height: 25px; "> 车牌号:川A 88888 </div> + <div style="font-weight: 500; font-size: 18px;color: rgba(0, 0, 0, 0.85);line-height: 25px;" > 驾驶员:李雷</div> + </div> + <div style="display: flex; justify-content: space-between"> + <div style=" font-weight: 500; font-size: 14px; color: rgba(0, 0, 0, 0.65);line-height: 26px;">位置:涪江文化广场</div> + <div style="font-weight: 500;font-size: 14px; color: rgba(0, 0, 0, 0.65);line-height: 26px; "> 经纬度:104.004284.30.579328</div> + </div> + <div style="display: flex; justify-content: space-between"> + <div style="font-weight: 500;font-size: 14px; color: rgba(0, 0, 0, 0.65);line-height: 26px; " > 当前时速:104km/h </div> + <div style="font-weight: 500;font-size: 14px; color: rgba(0, 0, 0, 0.65);line-height: 26px; "> 驾驶时长:5小时15分钟 </div> + </div> + <div style="margin-top: 14px;display: flex;justify-content: flex-end;align-items: center;cursor: pointer;" onclick="toCarDetail(${"111"})" > + <div style="font-weight: 400;font-size: 18px; color: rgba(22, 119, 255, 1);line-height: 25px; ">车辆详情</div> + <img style="width:18px;height: 18px;margin-left: 8px;" src="${require("../../assets//homeImg/right.png")}" /> + </div> + </div>`; }, // 获取预警情况统计 getCountList() { @@ -232,6 +640,38 @@ }, // 获取预警排行榜数据 getRankList() {}, + // 跳转车辆详情 + toCarDetail() { + console.log("跳转车辆详情"); + }, + fullScreen() { + console.log("全屏"); + }, + shotScreen() { + console.log("截图"); + setTimeout(() => { + let targetDom = document.querySelector("#monitoringCard"); + console.log('targetDom',targetDom) + html2canvas(targetDom, { + height: document.querySelector("#monitoringCard").scrollHeight, + windowHeight: document.querySelector("#monitoringCard").scrollHeight, + backgroundColor: null, //画出来的图片有白色的边框,不要可设置背景为透明色(null) + useCORS: true, //支持图片跨域 + scale: 2, //设置放大的倍数 + }).then((canvas) => { + let url = canvas.toDataURL("image/png"); // toDataURL: 图片格式转成 base64 + this.downloadImage(url); + }); + }, 10); + }, + downloadImage(base64) { + const link = document.createElement("a"); + link.href = base64; + link.download = "image.png"; // 你希望下载的文件名 + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); + }, }, }; </script> @@ -239,11 +679,210 @@ <style scoped lang="less"> .homePage { display: flex; + height: 100vh; + position: relative; + .leftMap { - width: 100%; + // width: 100%; height: 100%; flex: 1; + display: flex; + position: relative; + + #mapContainer { + flex: 1; + width: 100%; + height: 100%; + } } + .mapTop { + z-index: 99; + position: absolute; + top: 20px; + left: 20px; + right: 513px; + display: flex; + justify-content: space-between; + width: calc(100% - 570px); + + .title { + font-weight: 600; + font-size: 18px; + color: #000000; + line-height: 25px; + text-transform: none; + text-align: center; + } + + .carCount { + flex: 8; + background: #ffffff; + box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.2); + border-radius: 10px; + padding: 14px 20px 20px 20px; + margin-right: 20px; + + .fir { + display: flex; + justify-content: space-between; + margin-bottom: 10px; + margin-top: 11px; + + .countCard { + margin-right: 20px; + } + + .countCard:last-child { + margin-right: none; + } + } + + .sec { + display: flex; + justify-content: space-between; + + .countCard { + margin-right: 15px; + } + + .countCard:last-child { + margin-right: none; + } + } + + .countCard { + flex: 1; + background: linear-gradient( + 180deg, + rgba(246, 246, 252, 0) 0%, + #f3f4f8 100% + ); + box-shadow: inset 0px -1px 4px 0px #ffffff; + border-radius: 10px; + border: 1px solid #f1f1f1; + padding: 14px 20px 18px 14px; + display: flex; + justify-content: space-between; + + .iconImg { + width: 30px; + height: 30px; + border-radius: 10px; + } + + .iconImg:nth-child(1) { + box-shadow: 0px 7px 14px 0px rgba(14, 110, 253, 0.4); + } + + .iconImg:nth-child(2) { + box-shadow: 0px 7px 14px 0px rgba(255, 102, 39, 0.5); + } + + .iconImg:nth-child(3) { + box-shadow: 0px 7px 14px 0px rgba(254, 41, 94, 0.5); + } + + .iconImg:nth-child(4) { + box-shadow: 0px 7px 14px 0px rgba(248, 204, 65, 0.5); + } + + .iconImg:nth-child(5) { + box-shadow: 0px 7px 14px 0px rgba(2, 179, 118, 0.5); + } + + .iconImg:nth-child(6) { + box-shadow: 0px 7px 14px 0px rgba(169, 14, 253, 0.4); + } + + .iconImg:nth-child(7) { + box-shadow: 0px 7px 14px 0px rgba(109, 200, 236, 0.5); + } + + .name { + font-weight: 500; + font-size: 12px; + color: rgba(0, 0, 0, 0.6); + line-height: 17px; + margin-top: 2px; + } + + .num { + font-weight: 900; + font-size: 16px; + color: rgba(0, 0, 0, 0.8); + line-height: 19px; + text-align: right; + margin-top: 1px; + } + } + } + + .carStatus { + flex: 5; + background: #ffffff; + box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.2); + border-radius: 10px; + padding: 14px 84px 20px 84px; + + .statusFir { + margin-top: 23px; + margin-bottom: 28px; + display: flex; + justify-content: space-between; + align-content: center; + } + + .statusSec { + display: flex; + justify-content: space-between; + align-content: center; + } + + .statusCard { + display: flex; + align-content: center; + + .statusLeft { + margin-right: 9px; + display: flex; + flex-direction: column; + justify-content: center; + + .name { + font-weight: 500; + font-size: 12px; + color: rgba(0, 0, 0, 0.6); + line-height: 17px; + } + + .num { + font-weight: 900; + font-size: 16px; + color: rgba(0, 0, 0, 0.8); + line-height: 19px; + } + } + + .progressCard { + width: 56px; + height: 56px; + + ::v-deep .el-progress-circle { + width: 56px !important; + height: 56px !important; + } + } + } + + .statusLine { + width: 1px; + height: 46px; + border: 1px solid #dedede; + box-sizing: border-box; + } + } + } + .right { width: 493px; height: calc(100% - 20px); @@ -252,6 +891,7 @@ box-shadow: 0px 0px 10px 0px rgba(0, 0, 0, 0.2); border-radius: 10px 10px 0px 0px; padding: 20px; + .title { margin-top: 30px; font-weight: 600; @@ -261,15 +901,18 @@ text-transform: none; margin-bottom: 10px; } + .firCard { display: flex; justify-content: space-between; + .companyCard { width: 140px; height: 90px; background: #f4f4ff; border-radius: 0px 10px 10px 0px; position: relative; + .lineCard { position: absolute; left: 0; @@ -279,6 +922,7 @@ background: #0e6efd; border-radius: 2px; } + .name { margin: 18px 0 12px 19px; @@ -286,6 +930,7 @@ color: rgba(0, 0, 0, 0.6); line-height: 17px; } + .value { margin-bottom: 22px; text-align: center; @@ -296,10 +941,12 @@ } } } + .todayWarn { .warnList { height: 134px; overflow-y: auto; + .warnItem { height: 26px; background: rgba(39, 129, 255, 0.06); @@ -308,6 +955,7 @@ display: flex; align-content: center; margin-bottom: 10px; + .grade { height: 22px; background: #e6f4ff; @@ -322,25 +970,31 @@ color: #1677ff; line-height: 20px; } + .info { font-size: 12px; color: rgba(0, 0, 0, 0.8); line-height: 26px; } } + .warnItem:last-child { margin-bottom: 0 !important; } + .oneWarn { background: rgba(255, 77, 79, 0.06); + .grade { background: #fff1f0; border: 1px solid #ffccc7; color: rgba(255, 77, 79, 1); } } + .twoWarn { background: rgba(250, 173, 20, 0.06); + .grade { background: #fffbe6; border-radius: 4px; @@ -348,16 +1002,20 @@ color: rgba(250, 173, 20, 1); } } + .threeWarn { background: rgba(39, 129, 255, 0.06); + .grade { background: #e6f4ff; border: 1px solid #bae0ff; color: #1677ff; } } + .fourWarn { background: rgba(82, 196, 26, 0.06); + .grade { background: #f6ffed; border-radius: 4px; @@ -382,12 +1040,15 @@ background-color: #aaa; } } + .warnCount { position: relative; + .countChart { width: 453px; height: 150px; } + .noData { display: flex; flex-direction: column; @@ -400,15 +1061,19 @@ height: 150px; } } + .warnRank { position: relative; + .rankChart { width: 453px; height: 300px; + .rankItem { display: flex; align-content: center; margin-bottom: 14px; + .left { flex: 2; padding-right: 25px; @@ -418,28 +1083,34 @@ line-height: 17px; text-align: right; } + .rankRight { flex: 5; height: 15px; background: rgba(93, 112, 146, 0.2); border-radius: 8px; + .rank { height: 15px; border-radius: 8px; - background: rgba(93,112,146,0.6); + background: rgba(93, 112, 146, 0.6); } } + .rankColor { background: rgba(91, 143, 249, 0.2); + .rank { background: rgba(91, 143, 249, 0.85); } } } + .rankItem:last-child { margin-bottom: 0 !important; } } + .noData { display: flex; flex-direction: column; -- Gitblit v1.7.1