diff --git a/src/api/system/dept.js b/src/api/system/dept.js index fc943cd..b6f4f25 100644 --- a/src/api/system/dept.js +++ b/src/api/system/dept.js @@ -49,4 +49,11 @@ export function delDept(deptId) { url: '/system/dept/' + deptId, method: 'delete' }) -} \ No newline at end of file +} +// 查询余额 +export function getBalance(){ + return request({ + url: '/system/dept/getBalance', + method: 'get' + }) +} diff --git a/src/api/system/user.js b/src/api/system/user.js index f2f76ef..d1f1242 100644 --- a/src/api/system/user.js +++ b/src/api/system/user.js @@ -18,6 +18,15 @@ export function getUser(userId) { }) } +// 绑定APP用户 +export function bandAppUser(data) { + return request({ + url: '/system/user/bandAppUser', + method: 'put', + data: data + }) +} + // 新增用户 export function addUser(data) { return request({ diff --git a/src/api/system/withdraw.js b/src/api/system/withdraw.js new file mode 100644 index 0000000..4df9197 --- /dev/null +++ b/src/api/system/withdraw.js @@ -0,0 +1,44 @@ +import request from '@/utils/request' + +// 查询提现记录列表 +export function listWithdraw(query) { + return request({ + url: '/system/withdraw/list', + method: 'get', + params: query + }) +} + +// 查询提现记录详细 +export function getWithdraw(id) { + return request({ + url: '/system/withdraw/' + id, + method: 'get' + }) +} + +// 新增提现记录 +export function addWithdraw(data) { + return request({ + url: '/system/withdraw', + method: 'post', + data: data + }) +} + +// 修改提现记录 +export function updateWithdraw(data) { + return request({ + url: '/system/withdraw', + method: 'put', + data: data + }) +} + +// 删除提现记录 +export function delWithdraw(id) { + return request({ + url: '/system/withdraw/' + id, + method: 'delete' + }) +} diff --git a/src/api/user/user.js b/src/api/user/user.js index 7563daa..2ec7653 100644 --- a/src/api/user/user.js +++ b/src/api/user/user.js @@ -10,6 +10,16 @@ export function listUser(query) { }) } +// 根据手机号快速搜索用户列表 +export function fastSearch(query) { + return request({ + url: '/user/user/fast/search', + method: 'get', + params: query + }) +} + + // 查询用户详细 export function getUser(userId) { return request({ diff --git a/src/assets/icons/svg/withdraw.svg b/src/assets/icons/svg/withdraw.svg new file mode 100644 index 0000000..ba8161d --- /dev/null +++ b/src/assets/icons/svg/withdraw.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/src/components/AreaMap/index.vue b/src/components/AreaMap/index.vue index 0ed6e2b..adf08e9 100644 --- a/src/components/AreaMap/index.vue +++ b/src/components/AreaMap/index.vue @@ -58,7 +58,7 @@ export default { lat2: null }; }, - props: ["pathList", "dataId","lon","lat"], + props: ["pathList", "dataId","lon","lat","zoom"], mounted() { if (this.dataId) { this.start(); @@ -132,7 +132,7 @@ export default { this.map = new AMap.Map("container", { //设置地图容器id viewMode: "3D", //是否为3D地图模式 - zoom: 13, //初始化地图级别 + zoom: this.zoom?this.zoom:13, //初始化地图级别 center: [this.lon2, this.lat2], // 初始化地图中心点位置 }); this.map.setFitView(); diff --git a/src/components/Map/location/LocationMap.vue b/src/components/Map/location/LocationMap.vue index 4387d8e..74676e0 100644 --- a/src/components/Map/location/LocationMap.vue +++ b/src/components/Map/location/LocationMap.vue @@ -54,6 +54,10 @@ export default { type: String, default: '0' }, + deviceSn: { + type: String, + default: '' + } }, data() { return { @@ -124,7 +128,7 @@ export default { // 标点 this.removeAllMarker(); console.log("添加标记点") - this.addMarker(this.initLng, this.initLat, res.regeocode.formattedAddress, this.status, this.onlineStatus); + this.addMarker(this.initLng, this.initLat, this.deviceSn, this.status, this.onlineStatus); this.$emit('map-geo', res, this.initLng, this.initLat); // 地区 @@ -140,14 +144,35 @@ export default { }, addMarker(lng, lat, title,status,onlineStatus) { //创建一个 Marker 实例: + console.log("title==========="+title) let marker = new AMap.Marker({ position: new AMap.LngLat(lng, lat), //经纬度对象 icon: this.formarStatus(status,onlineStatus), title: title, + offset: new AMap.Pixel(-20, -40) }); //将创建的点标记添加到已有的地图实例: this.map.add(marker); this.markers.push(marker); + + // 创建一个 Text 实例来显示标题 + let text = new AMap.Text({ + text: title, + anchor: 'center', // 设置文本的锚点 + position: new AMap.LngLat(lng, lat), // 经纬度对象 + offset: new AMap.Pixel(0, -55), + style: { + 'background-color': '#1890ff', // 背景颜色为蓝色 + 'border': 'none', // 边框颜色与背景一致 + 'border-radius': '5px', // 圆角 5px + 'color': 'white', // 文字颜色为白色 + 'font-size': '14px', // 字体大小 + 'padding': '5px 10px' // 内边距,调整文本框的大小 + } + }); + + // 将文本标签添加到地图实例 + this.map.add(text); }, formarStatus(status,onlineStatus){ if(onlineStatus == "0"){ diff --git a/src/views/system/area/index.vue b/src/views/system/area/index.vue index d4a8f7e..02440b3 100644 --- a/src/views/system/area/index.vue +++ b/src/views/system/area/index.vue @@ -336,7 +336,7 @@ - + diff --git a/src/views/system/area/noparking.vue b/src/views/system/area/noparking.vue index 2ad66ae..23f0cc9 100644 --- a/src/views/system/area/noparking.vue +++ b/src/views/system/area/noparking.vue @@ -1,7 +1,7 @@ - + - + diff --git a/src/views/system/area/noriding.vue b/src/views/system/area/noriding.vue index 73855b9..e2ec05c 100644 --- a/src/views/system/area/noriding.vue +++ b/src/views/system/area/noriding.vue @@ -157,7 +157,7 @@ - + diff --git a/src/views/system/area/parking.vue b/src/views/system/area/parking.vue index 93706dd..981b6d8 100644 --- a/src/views/system/area/parking.vue +++ b/src/views/system/area/parking.vue @@ -85,6 +85,7 @@ + @@ -149,10 +150,15 @@ + + + + + - + @@ -244,7 +250,10 @@ export default { ], boundaryStr: [ { required: true, message: "边界不能为空", trigger: "blur" } - ] + ], + error: [ + { pattern: /^[0-9]*$/, message: "还车误差必须为正整数", trigger: "blur" } + ], } }; }, @@ -254,6 +263,13 @@ export default { this.getAreaList(); }, methods: { + formatDistance(row) { + if (typeof row.error === 'number') { + return `${row.error} 米`; + } else { + return '-'; + } + }, mapList(data){ let mapListJson = JSON.stringify(data); console.log("mapListJson:"+mapListJson); @@ -346,6 +362,8 @@ export default { const parkingId = row.parkingId || this.ids getParking(parkingId).then(response => { this.form = response.data; + this.areaLon = response.data.longitude; + this.areaLat = response.data.latitude; this.open = true; this.title = "修改停车区"; this.key++; diff --git a/src/views/system/device/index.vue b/src/views/system/device/index.vue index 2ee552d..85a3eea 100644 --- a/src/views/system/device/index.vue +++ b/src/views/system/device/index.vue @@ -373,6 +373,7 @@ :init-lng="form.longitude" :status="form.status" :online-status="form.onlineStatus" + :device-sn="form.sn" /> diff --git a/src/views/system/map/index.vue b/src/views/system/map/index.vue index a40bb57..99e911f 100644 --- a/src/views/system/map/index.vue +++ b/src/views/system/map/index.vue @@ -14,6 +14,7 @@ import globalConfig from "@/utils/config/globalConfig"; import {listDevice} from "@/api/system/device"; import {listArea} from "@/api/system/area"; + import { listParking } from '@/api/system/parking' export default { @@ -26,18 +27,55 @@ tips: null, // 运营区表格数据 areaList: [], + lon: null, + lat: null, + area:null, // 设备表格数据 deviceList: [], + parkingList: [], + noParkingList: [], + noridingList: [], type: null } }, mounted() { - this.initAMap(); + this.getAreaList(); }, unmounted() { this.map?.destroy(); }, methods: { + async getAreaList(){ + listArea().then(response => { + this.areaList = response.rows; + if (this.areaList.length > 0) { // 确保数组不为空 + const firstArea = this.areaList[0]; // 获取第一个元素 + this.area = firstArea; + console.log('第一个区域的信息:', firstArea); + this.lon = firstArea.longitude; + this.lat = firstArea.latitude; + console.log("area============="+JSON.stringify(this.area)) + listParking({areaId: this.area.areaId}).then(response => { + let list = response.rows; + list.forEach(item => { + if (item.type === '1') { + this.parkingList.push(item); + } else if (item.type === '2') { + this.noParkingList.push(item); + } else if (item.type === '3') { + this.noridingList.push(item); + } + }); + console.log("parkingList============="+JSON.stringify(this.parkingList)); + console.log("noParkingList============="+JSON.stringify(this.noParkingList)); + console.log("noriding============="+JSON.stringify(this.noridingList)); + this.initAMap(); + }); + }else{ + console.log('区域列表为空'); + } + }); + }, changeMapStyle(){ // 创建一个默认的图层组件 let defaultLayer = new AMap.TileLayer(); @@ -73,12 +111,29 @@ // 设置地图容器id viewMode: "3D", // 是否为3D地图模式 zoom: 13, // 初始化地图级别 - center: [120.356031,26.94088], //初始化地图中心点位置--大嵛山岛 + center: [this.lon,this.lat], //初始化地图中心点位置 }); //设备点标记 this.deviceMarker(); //运营区边界 - this.areaBoundary(); + this.areaList.forEach(area => { + this.addArea(JSON.parse(area.boundaryStr) || []); + }); + //停车区 + this.parkingList.forEach(parking => { + this.addParking(JSON.parse(parking.boundaryStr) || [],parking.parkingName,parking.longitude,parking.latitude); + this.addMarker2(parking,"https://lxnapi.ccttiot.com/FqcYf6ecsnbC0OT6YYAF5npgu-kh",parking.parkingName,"#1890ff"); + }); + //禁停区 + this.noParkingList.forEach(noparking => { + this.addNoParking(JSON.parse(noparking.boundaryStr) || []); + this.addMarker2(noparking,"https://lxnapi.ccttiot.com/FjKE5PWbnEnZUq3k-wVIvV4lv8Ab",noparking.parkingName,"#ff4444"); + }); + //禁行区 + this.noridingList.forEach(noriding => { + this.addNoriding(JSON.parse(noriding.boundaryStr) || [],noriding.parkingName,noriding.longitude,noriding.latitude); + this.addMarker2(noriding,"https://lxnapi.ccttiot.com/FmX1diEPPbFYe1vcUfKp6qbKzzh2",noriding.parkingName,"#ffcc00"); + }); setTimeout(() => { this.setFitView(); }, 1000); @@ -86,6 +141,38 @@ console.log(e); }); }, + addMarker2(parking, icon,title,color) { + let marker = new AMap.Marker({ + map: this.map, + icon: new AMap.Icon({ + image: icon, + size: new AMap.Size(38, 55), // 设置图标的宽高 + imageSize: new AMap.Size(38, 55) // 设置图标的实际显示尺寸 + }), + position: [parking.longitude, parking.latitude], + offset: new AMap.Pixel(-20, -50) + }); + + console.log("title============="+title) + // 创建一个 Text 实例来显示标题 + let text = new AMap.Text({ + text: title, + anchor: 'center', // 设置文本的锚点 + position: [parking.longitude, parking.latitude], + offset: new AMap.Pixel(0, -70), + style: { + 'background-color': color, // 背景颜色为蓝色 + 'border': 'none', // 边框颜色与背景一致 + 'border-radius': '5px', // 圆角 5px + 'color': 'white', // 文字颜色为白色 + 'font-size': '14px', // 字体大小 + 'padding': '5px 10px' // 内边距,调整文本框的大小 + } + }); + + // 将文本标签添加到地图实例 + this.map.add(text); + }, deviceMarker(){ listDevice({pageNum: 1,pageSize: 999}).then(response => { this.deviceList = response.rows; @@ -93,7 +180,7 @@ // 检查经纬度是否为空且为有效数字 if (device.longitude !== null && device.latitude !== null && !isNaN(device.longitude) && !isNaN(device.latitude)) { - this.addMarker(device.longitude, device.latitude, device.status, device.onlineStatus); + this.addMarker(device.longitude, device.latitude, device.status, device.onlineStatus,device.sn); } else { console.warn(`无效的经纬度值: 经度=${device.longitude}, 纬度=${device.latitude}`); } @@ -102,15 +189,7 @@ console.error('获取设备列表失败:', error); }); }, - areaBoundary(){ - listArea().then(response => { - this.areaList = response.rows; - this.areaList.forEach(area => { - this.addPolygon(JSON.parse(area.boundaryStr) || []); - }); - }); - }, - addMarker(lng, lat, status, onlineStatus) { + addMarker(lng, lat, status, onlineStatus,title) { function formarStatus(status,onlineStatus) { if(onlineStatus == "0"){ return globalConfig.icon.red; @@ -137,12 +216,31 @@ map: this.map, icon: formarStatus(status,onlineStatus), position: [lng, lat], - // offset: new AMap.Pixel(-13, -30) + offset: new AMap.Pixel(-20, -40) }); + + // 创建一个 Text 实例来显示标题 + let text = new AMap.Text({ + text: title, + anchor: 'center', // 设置文本的锚点 + position: [lng, lat], + offset: new AMap.Pixel(0, -55), + style: { + 'background-color': '#1890ff', // 背景颜色为蓝色 + 'border': 'none', // 边框颜色与背景一致 + 'border-radius': '5px', // 圆角 5px + 'color': 'white', // 文字颜色为白色 + 'font-size': '14px', // 字体大小 + 'padding': '5px 10px' // 内边距,调整文本框的大小 + } + }); + + // 将文本标签添加到地图实例 + this.map.add(text); }, - //添加多边形 - addPolygon(data) { + //添加运营区边界 + addArea(data) { let polygon = new AMap.Polygon({ path: data, fillColor: '#ccebc5', @@ -153,20 +251,124 @@ strokeStyle: 'dashed', strokeDasharray: [5, 5], }); + // polygon.on('mouseover', () => { + // polygon.setOptions({ + // fillOpacity: 0.7, + // fillColor: '#7bccc4' + // }) + // }) + // polygon.on('mouseout', () => { + // polygon.setOptions({ + // fillOpacity: 0.5, + // fillColor: '#ccebc5' + // }) + // }) + this.map.add(polygon); + }, + addParking(data,title,lon,lat) { + let polygon = new AMap.Polygon({ + path: data, + fillColor: '#ccebc5', + strokeOpacity: 1, + fillOpacity: 0.5, + strokeColor: '#3b7ed9', // 修改边界颜色为红色 + strokeWeight: 2, // 加粗边界 + strokeStyle: 'solid', + strokeDasharray: [5, 5], + }); polygon.on('mouseover', () => { polygon.setOptions({ fillOpacity: 0.7, - fillColor: '#7bccc4' - }) - }) + fillColor: '#71b7cc' // 鼠标悬浮时填充颜色为红色 + }); + }); polygon.on('mouseout', () => { polygon.setOptions({ fillOpacity: 0.5, - fillColor: '#ccebc5' - - }) - }) + fillColor: '#a7c1d0' // 鼠标移出时恢复填充颜色 + }); + }); this.map.add(polygon); + + // 创建文本标注 + // let text = new AMap.Text({ + // text: title, + // anchor: 'center', // 设置文本标注锚点位置 + // style: { + // 'background-color': 'transparent', // 背景透明 + // 'border': 'none', // 无边框 + // 'color': '#ff0000', // 文本颜色 + // 'font-size': '14px' + // }, + // position: [lon,lat] // 设置文本标注的位置 + // }); + // + // this.map.add(text); + }, + addNoParking(data) { + let polygon = new AMap.Polygon({ + path: data, + fillColor: '#ccebc5', + strokeOpacity: 1, + fillOpacity: 0.5, + strokeColor: '#ff0000', // 修改边界颜色为红色 + strokeWeight: 2, // 加粗边界 + strokeStyle: 'solid', + strokeDasharray: [5, 5], + }); + polygon.on('mouseover', () => { + polygon.setOptions({ + fillOpacity: 0.7, + fillColor: '#ff0000' // 鼠标悬浮时填充颜色为红色 + }); + }); + polygon.on('mouseout', () => { + polygon.setOptions({ + fillOpacity: 0.5, + fillColor: '#cc7b7b' // 鼠标移出时恢复填充颜色 + }); + }); + this.map.add(polygon); + }, + addNoriding(data,title,lon,lat) { + let polygon = new AMap.Polygon({ + path: data, + fillColor: '#ccebc5', + strokeOpacity: 1, + fillOpacity: 0.5, + strokeColor: '#ffcc00', // 修改边界颜色为红色 + strokeWeight: 2, // 加粗边界 + strokeStyle: 'solid', + strokeDasharray: [5, 5], + }); + polygon.on('mouseover', () => { + polygon.setOptions({ + fillOpacity: 0.7, + fillColor: '#FFEBA4FF' + }); + }); + polygon.on('mouseout', () => { + polygon.setOptions({ + fillOpacity: 0.5, + fillColor: '#ffeba4' + }); + }); + this.map.add(polygon); + + // 创建文本标注 + // let text = new AMap.Text({ + // text: title, + // anchor: 'center', // 设置文本标注锚点位置 + // style: { + // 'background-color': 'transparent', // 背景透明 + // 'border': 'none', // 无边框 + // 'color': '#ff0000', // 文本颜色 + // 'font-size': '14px' + // }, + // position: [lon,lat] // 设置文本标注的位置 + // }); + // + // this.map.add(text); } }, }; diff --git a/src/views/system/order/index.vue b/src/views/system/order/index.vue index 0199d75..e6a6c38 100644 --- a/src/views/system/order/index.vue +++ b/src/views/system/order/index.vue @@ -1,13 +1,15 @@ - - + + + + + + + + + 搜索 重置 @@ -298,6 +310,7 @@