ly-front/src/views/contentData/headerTop/index.vue

232 lines
6.1 KiB
Vue
Raw Normal View History

2025-03-31 15:26:29 +00:00
<template>
<div class="header">
<div class="header-left">
2025-06-18 15:08:37 +00:00
<div class="time_date">
{{ currentDate }} <span>{{ currentTime }}</span>
</div>
2025-03-31 15:26:29 +00:00
</div>
<div class="header-main">
<div class="textTile"></div>
2025-03-31 15:26:29 +00:00
</div>
2025-06-19 15:41:07 +00:00
<div class="header-menu">
<span>{{ leftText }}</span>
<span style="width: 20px"> | </span>
<span>{{ rightText }}</span>
</div>
<div v-if="showPermissionPrompt" class="permission-prompt">
<p>请允许地理位置权限以启用定位功能</p>
<p>您可以在浏览器地址栏设置中启用位置访问或点击下方按钮重试</p>
<button @click="retryTracking">重试定位</button>
</div>
2025-03-31 15:26:29 +00:00
</div>
</template>
<script>
import { mapGetters } from "vuex";
import { HomeSyncLocation } from "@/api/home";
import _ from "lodash";
2025-06-22 09:42:09 +00:00
import { fromLonLat } from "ol/proj";
2025-03-31 15:26:29 +00:00
export default {
name: "header-top",
props: {
homeData: {
type: Object,
default: () => ({})
}
},
data() {
return {
currentTime: "",
currentDate: "",
2025-06-19 15:41:07 +00:00
isAdmins: false,
leftText: "平台已连接",
rightText: "定位正常",
2025-06-22 09:42:09 +00:00
latitude: "",
longitude: "",
lastUpdated: "",
watchId: null,
timer: null,
2025-06-22 09:42:09 +00:00
showPermissionPrompt: false,
retryCount: 0
2025-03-31 15:26:29 +00:00
};
},
computed: {
...mapGetters(["positionPoint"])
2025-03-31 15:26:29 +00:00
},
mounted() {
console.log("组件挂载,启动定位");
2025-04-02 14:51:32 +00:00
this.isAdmins = JSON.parse(localStorage.getItem("isAdmin"));
2025-03-31 15:26:29 +00:00
this.updateTime();
this.startTracking();
this.timer = setInterval(() => {
this.updateTime();
}, 1000);
2025-06-22 09:42:09 +00:00
this.$on("retry-tracking", this.startTracking);
},
watch: {
positionPoint: {
2025-06-22 09:42:09 +00:00
handler(newVal) {
if (newVal && this.latitude && this.longitude) {
const newLocation = fromLonLat([this.longitude, this.latitude]);
this.$message.success(this.longitude + "," + this.latitude);
const zoomLevel = 13;
window.olMap.getView().animate({
center: newLocation,
zoom: zoomLevel
});
this.startTracking();
}
this.$store.commit("SET_POSITIONPOINT", false);
2025-06-22 09:42:09 +00:00
},
deep: true
}
2025-03-31 15:26:29 +00:00
},
methods: {
updateTime() {
const now = new Date();
this.currentTime = now.toLocaleTimeString();
this.currentDate = now.toLocaleDateString();
},
startTracking() {
console.log("启动定位");
if (!navigator.geolocation) {
this.$message.error("您的浏览器不支持地理位置功能");
this.leftText = "不支持定位";
this.rightText = "定位异常";
return;
}
this.watchId = navigator.geolocation.watchPosition(
(position) => this.handleSuccess(position),
(error) => this.handleError(error),
{
2025-06-22 09:42:09 +00:00
enableHighAccuracy: true,
timeout: 30000,
maximumAge: 10000
}
);
},
syncLocation: _.debounce(function (latitude, longitude) {
console.log("触发上报:", {
latitude,
longitude,
time: new Date().toLocaleString()
});
let params = {
lat: latitude,
lon: longitude,
userId: localStorage.getItem("userId")
};
HomeSyncLocation(params)
.then((res) => {
if (res.code === 0) {
this.leftText = "平台已连接";
this.rightText = "定位正常";
2025-06-22 09:42:09 +00:00
if (!latitude && res.data.fallbackLocation) {
this.handleSuccess({
coords: { latitude: this.latitude, longitude: this.longitude }
});
}
} else {
this.leftText = "平台连接失败";
this.rightText = "定位异常";
}
})
.catch((err) => {
this.leftText = "平台连接失败";
this.rightText = "定位异常";
});
}, 1000),
handleSuccess(position) {
this.latitude = position.coords.latitude;
this.longitude = position.coords.longitude;
this.lastUpdated = new Date().toLocaleString();
this.showPermissionPrompt = false;
2025-06-22 09:42:09 +00:00
this.retryCount = 0;
this.syncLocation(this.latitude, this.longitude);
},
handleError(error) {
let message = "";
2025-06-22 09:42:09 +00:00
this.retryCount = this.retryCount || 0;
switch (error.code) {
case error.PERMISSION_DENIED:
message = "请允许地理位置权限";
this.showPermissionPrompt = true;
this.$message.error("请在浏览器设置中启用地理位置权限");
break;
case error.POSITION_UNAVAILABLE:
message = "无法获取位置信息";
2025-06-22 09:42:09 +00:00
if (this.retryCount < 3) {
this.retryCount++;
setTimeout(() => this.startTracking(), 5000);
} else {
this.$message.error("多次尝试后仍无法定位,请检查设备设置");
}
break;
case error.TIMEOUT:
message = "获取位置超时";
2025-06-22 09:42:09 +00:00
if (this.retryCount < 3) {
this.retryCount++;
setTimeout(() => this.startTracking(), 5000);
} else {
this.$message.error("定位超时,请检查网络或 GPS 信号");
}
break;
default:
message = "未知错误";
}
this.leftText = message;
this.rightText = "定位异常";
},
retryTracking() {
this.showPermissionPrompt = false;
2025-06-22 09:42:09 +00:00
this.retryCount = 0;
this.startTracking();
}
},
beforeDestroy() {
if (this.watchId) {
navigator.geolocation.clearWatch(this.watchId);
}
if (this.timer) {
clearInterval(this.timer);
2025-03-31 15:26:29 +00:00
}
}
};
</script>
<style scoped>
.logo {
font-size: 20px;
font-weight: bold;
}
.time {
font-size: 14px;
}
.actions span {
margin-left: 10px;
cursor: pointer;
}
.permission-prompt {
position: fixed;
top: 20px;
right: 20px;
background: #fff;
padding: 15px;
border: 1px solid #ddd;
box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
2025-06-22 09:42:09 +00:00
z-index: 10000;
pointer-events: auto;
}
.permission-prompt p {
margin: 0 0 10px;
}
.permission-prompt button {
padding: 5px 10px;
background: #409eff;
color: #fff;
border: none;
cursor: pointer;
}
2025-03-31 15:26:29 +00:00
</style>