iot对接
This commit is contained in:
parent
28f8908644
commit
c689a77849
19
index.html
19
index.html
|
|
@ -1,15 +1,20 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<link rel="icon" href="/favicon.jpg">
|
||||
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<!-- 贵州 -->
|
||||
<title>智联装备云控平台</title>
|
||||
</head>
|
||||
<body>
|
||||
<div id="app"></div>
|
||||
<script type="module" src="/src/main.ts"></script>
|
||||
<script type="text/javascript" src="https://api.map.baidu.com/api?v=3.0&ak=cClgLBaLgGUdQDilX9dGvieL"></script>
|
||||
</body>
|
||||
</head>
|
||||
<body>
|
||||
<div id="app"></div>
|
||||
<script type="module" src="/src/main.ts"></script>
|
||||
<script type="text/javascript"
|
||||
src="https://api.map.baidu.com/api?type=webgl&v=1.0&ak=XS1NJt7EsW7mVN48hMXDwMndxRJzSw30"></script>
|
||||
<link href="//mapopen.bj.bcebos.com/github/BMapGLLib/DrawingManager/src/DrawingManager.min.css" rel="stylesheet">
|
||||
|
||||
<script src="//mapopen.bj.bcebos.com/github/BMapGLLib/DrawingManager/src/DrawingManager.min.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
|
|||
|
|
@ -1,23 +1,15 @@
|
|||
<script setup lang="ts">
|
||||
import EquipCard from 'components/equipCard.vue'
|
||||
import EquipCardNew from 'components/equipCardNew/index.vue'
|
||||
import NavMenu from 'components/Navmenu/index.vue'
|
||||
import { getGoodsClassListApi, getCompanyListApi, getSwiperListApi } from 'http/api/home'
|
||||
import { useStore } from 'store/user'
|
||||
import { mainStore } from 'store/main'
|
||||
import { getHotList } from 'http/api/equip'
|
||||
import { loginNewApi } from 'http/api/home/index'
|
||||
import { getUserInfoAPI } from 'http/api/login/index'
|
||||
import { ElMessage } from 'element-plus'
|
||||
import { wgs84ToBd09Direct } from 'utils/map'
|
||||
import { getMapData, mapLoginApi, getIotListApi, getBadgeInfoApi } from 'http/api/map'
|
||||
import { ElMessage, ElMessageBox } from 'element-plus'
|
||||
import { getMapData } from 'http/api/map'
|
||||
import icon1 from '@/assets/img/work-card.jpg'
|
||||
import icon2 from '@/assets/img/IOT.jpg'
|
||||
|
||||
const router: any = useRouter()
|
||||
const userStore = useStore()
|
||||
const store: any = mainStore()
|
||||
const tokenNew = localStorage.getItem('tokenNew')
|
||||
const companyList: any = ref([])
|
||||
const classList: any = ref([])
|
||||
const selectOptions = ref<boolean>(false) // 分类
|
||||
|
|
@ -30,11 +22,21 @@ const mapWorkCardData: any = ref({}) // 工牌信息数据
|
|||
let timer: any = ref()
|
||||
// 标记点
|
||||
const points: any = ref([])
|
||||
const iot: any = ref([])
|
||||
const mapData = ref()
|
||||
const tagData: any = ref()
|
||||
const tagIndex: any = ref()
|
||||
|
||||
// 地图实例
|
||||
const map: any = ref(null)
|
||||
// 绘制状态
|
||||
const isDrawing = ref(false)
|
||||
// 地理围栏列表
|
||||
const geoFences = ref([])
|
||||
// 绘制工具实例
|
||||
const drawingManager = ref(null)
|
||||
// 控制绘制工具栏显示
|
||||
const showDrawingControls = ref(false)
|
||||
|
||||
// 监听 mapDialog
|
||||
watch(
|
||||
() => mapDialog.value,
|
||||
|
|
@ -46,82 +48,29 @@ watch(
|
|||
},
|
||||
)
|
||||
|
||||
// 登录
|
||||
const loginApi = async () => {
|
||||
try {
|
||||
const res: any = await mapLoginApi({})
|
||||
console.log('🚀 ~ loginApi ~ res:', res)
|
||||
} catch (error) {
|
||||
console.log('🚀 ~ loginApi ~ error:', error)
|
||||
getMapDataList()
|
||||
}
|
||||
}
|
||||
// 获取地图数据
|
||||
const getMapDataList = async () => {
|
||||
try {
|
||||
await getMapData()
|
||||
} catch (res: any) {
|
||||
console.log('--------------', res)
|
||||
console.log('🚀 ~ getMapDataList ~ res:', res)
|
||||
if (res && res.length > 0) {
|
||||
const point = res.map((item: any) => {
|
||||
const longitudeNum = Number(item.longitude)
|
||||
const latitudeNum = Number(item.latitude)
|
||||
console.log(longitudeNum, latitudeNum)
|
||||
let { longitude, latitude } = wgs84ToBd09Direct(latitudeNum, longitudeNum)
|
||||
console.log('🚀 ~ getMapDataList ~ longitude:', longitude, latitude)
|
||||
return {
|
||||
id: item.uuid,
|
||||
lng: longitude,
|
||||
lat: latitude,
|
||||
lng: latitudeNum,
|
||||
lat: longitudeNum,
|
||||
item: item,
|
||||
isWork: false,
|
||||
}
|
||||
})
|
||||
points.value = [...JSON.parse(JSON.stringify(points.value)), ...point]
|
||||
}
|
||||
//getWorkData()
|
||||
initMap()
|
||||
}
|
||||
}
|
||||
|
||||
// 获取工牌信息
|
||||
const getWorkData = async () => {
|
||||
try {
|
||||
await getIotListApi()
|
||||
} catch (res: any) {
|
||||
console.log('🚀 ~ getWorkData ~ res:', res)
|
||||
if (res.errorCode != 200) {
|
||||
initMap()
|
||||
return
|
||||
}
|
||||
const point = res.devices.map((item: any) => {
|
||||
return {
|
||||
id: item.user_id,
|
||||
lng: item.jingdu,
|
||||
lat: item.weidu,
|
||||
isWork: true,
|
||||
}
|
||||
})
|
||||
// 数组合并
|
||||
points.value = [...JSON.parse(JSON.stringify(points.value)), ...point]
|
||||
console.log('🚀 ~ getWorkData ~ points.value:', points.value)
|
||||
initMap()
|
||||
}
|
||||
}
|
||||
|
||||
// 获取工牌详情
|
||||
const getWorkCardDetails = async (id: any) => {
|
||||
try {
|
||||
await getBadgeInfoApi(id)
|
||||
} catch (res: any) {
|
||||
console.log('🚀 ~ getWorkCardDetails ~ res:', res)
|
||||
if (res.errorCode != 200) {
|
||||
return
|
||||
}
|
||||
mapWorkCardData.value = res.data[0]
|
||||
}
|
||||
}
|
||||
|
||||
// 获取公司名称
|
||||
const getCompanyListData = async () => {
|
||||
|
|
@ -157,29 +106,9 @@ const onSharedHallByCompany = (companyId: any, name: any) => {
|
|||
})
|
||||
}
|
||||
|
||||
const handlerGoodsDetails = (...arg: any) => {
|
||||
const arr = arg.map((key: any, index: number) => {
|
||||
return {
|
||||
level: index + 1 + '',
|
||||
typeId: key.id,
|
||||
typeName: key.name,
|
||||
}
|
||||
})
|
||||
|
||||
router.push({
|
||||
name: 'equipList',
|
||||
state: { typeTag: arr },
|
||||
})
|
||||
}
|
||||
|
||||
const hotDeviceList: any = ref([])
|
||||
|
||||
/* 获取热搜装备 */
|
||||
const getHotDeviceList = async () => {
|
||||
const res: any = await getHotList({ pageSize: 3 })
|
||||
hotDeviceList.value = res.data
|
||||
}
|
||||
|
||||
/* 热搜卡片点击跳转至详情页 */
|
||||
const onClick = (val: any) => {
|
||||
router.push({
|
||||
|
|
@ -213,16 +142,6 @@ const getSwiperListData = async () => {
|
|||
// console.log(res, '轮播图信息')
|
||||
}
|
||||
|
||||
const onClickSwiper = (item: any) => {
|
||||
if (item.slideLink) {
|
||||
const link = item.slideLink.startsWith('http')
|
||||
? item.slideLink
|
||||
: `https://${item.slideLink}`
|
||||
window.open(link, '_blank')
|
||||
} else {
|
||||
router.push({ name: 'equipList' })
|
||||
}
|
||||
}
|
||||
|
||||
getSwiperListData()
|
||||
|
||||
|
|
@ -242,7 +161,6 @@ const formatUtcTimeV2 = (utcTime: any, date: any) => {
|
|||
const utcDate = new Date(Date.UTC(year, month, day, hours, minutes, seconds))
|
||||
|
||||
// 转换为北京时间 (UTC+8)
|
||||
// const beijingOffset = 8 * 60 * 60 * 1000; // 8小时的毫秒数
|
||||
const beijingTime = new Date(utcDate.getTime())
|
||||
|
||||
// 格式化输出
|
||||
|
|
@ -259,7 +177,6 @@ const formatUtcTimeV2 = (utcTime: any, date: any) => {
|
|||
.replace(/\//g, '-')} (北京时间)`
|
||||
}
|
||||
|
||||
|
||||
// 定位状态类型定义
|
||||
type PositionStatus = 'A' | 'V' | string
|
||||
|
||||
|
|
@ -275,7 +192,6 @@ type PositionSource = 'gnss' | 'lbs' | 'wifi' | string
|
|||
const typeMap = {
|
||||
'2': '小型数据终端',
|
||||
'3': '智能工牌',
|
||||
|
||||
}
|
||||
|
||||
// 获取type对应的名称
|
||||
|
|
@ -342,31 +258,213 @@ const getPositionSourceText = (source: PositionSource): string => {
|
|||
return sourceMap[source] || (source || '-')
|
||||
}
|
||||
|
||||
// 初始化绘制工具
|
||||
const initDrawingTool = (): void => {
|
||||
if (!window.BMapGLLib) {
|
||||
console.error('BMapLib 未加载,请确保已引入百度地图绘制库')
|
||||
ElMessage.error('地图绘制功能加载失败,请刷新页面重试')
|
||||
return
|
||||
}
|
||||
|
||||
try {
|
||||
// 创建绘制管理器
|
||||
drawingManager.value = new BMapGLLib.DrawingManager(map.value, {
|
||||
isOpen: false,
|
||||
drawingType: BMAP_DRAWING_MARKER,
|
||||
enableDrawingTool: true,
|
||||
enableCalculate: true,
|
||||
drawingToolOptions: {
|
||||
anchor: BMAP_ANCHOR_TOP_RIGHT,
|
||||
offset: new BMapGL.Size(5, 5),
|
||||
drawingModes: [
|
||||
BMAP_DRAWING_CIRCLE,
|
||||
BMAP_DRAWING_POLYGON,
|
||||
BMAP_DRAWING_RECTANGLE,
|
||||
],
|
||||
},
|
||||
...getDrawingStyleOptions(), // 统一样式配置
|
||||
})
|
||||
|
||||
// 添加绘制完成事件监听
|
||||
drawingManager.value.addEventListener('overlaycomplete', handleDrawingComplete)
|
||||
|
||||
ElMessage.success('绘制工具初始化成功')
|
||||
} catch (error) {
|
||||
console.error('初始化绘制工具失败:', error)
|
||||
ElMessage.error('绘制工具初始化失败')
|
||||
}
|
||||
}
|
||||
|
||||
// 获取绘制样式配置
|
||||
const getDrawingStyleOptions = () => {
|
||||
const commonStyle = {
|
||||
strokeColor: '#FF0000',
|
||||
fillColor: '#FF0000',
|
||||
strokeWeight: 2,
|
||||
strokeOpacity: 0.8,
|
||||
fillOpacity: 0.2,
|
||||
}
|
||||
|
||||
return {
|
||||
circleOptions: commonStyle,
|
||||
rectangleOptions: commonStyle,
|
||||
polygonOptions: commonStyle,
|
||||
}
|
||||
}
|
||||
|
||||
// 处理绘制完成事件
|
||||
const handleDrawingComplete = (e: any): void => {
|
||||
console.log('绘制完成事件详情:', e)
|
||||
|
||||
// 显示围栏对话框
|
||||
showFenceDialog(e.overlay, e.drawingMode)
|
||||
|
||||
// 关闭绘制模式
|
||||
drawingManager.value.close()
|
||||
}
|
||||
|
||||
// 生成默认围栏名称
|
||||
const generateDefaultFenceName = (shapeType: string, fenceCount: number): string => {
|
||||
const shapeNames: Record<string, string> = {
|
||||
'polygon': '多边形围栏',
|
||||
'rectangle': '矩形围栏',
|
||||
'circle': '圆形围栏',
|
||||
}
|
||||
|
||||
const baseName = shapeNames[shapeType] || '围栏'
|
||||
return `${baseName}${fenceCount + 1}`
|
||||
}
|
||||
|
||||
// 创建围栏数据
|
||||
const createFenceData = (overlay: any, shapeType: string, fenceName: string): any => {
|
||||
const baseData = {
|
||||
id: Date.now(),
|
||||
name: fenceName,
|
||||
calculate: overlay.calculate,
|
||||
shapeType: shapeType,
|
||||
overlay: overlay,
|
||||
}
|
||||
|
||||
switch (shapeType) {
|
||||
case 'circle':
|
||||
return {
|
||||
...baseData,
|
||||
center: overlay.getCenter(),
|
||||
radius: overlay.getRadius(),
|
||||
}
|
||||
case 'polygon':
|
||||
case 'rectangle':
|
||||
return {
|
||||
...baseData,
|
||||
points: overlay.points,
|
||||
}
|
||||
default:
|
||||
return baseData
|
||||
}
|
||||
}
|
||||
|
||||
// 显示围栏对话框
|
||||
const showFenceDialog = (overlay: any, shapeType: string): void => {
|
||||
const defaultName = generateDefaultFenceName(shapeType, geoFences.value.length)
|
||||
ElMessageBox.prompt('请输入地理围栏名称:', '创建地理围栏', {
|
||||
confirmButtonText: '确定',
|
||||
cancelButtonText: '取消',
|
||||
inputValue: defaultName,
|
||||
inputPlaceholder: '请输入围栏名称',
|
||||
inputValidator: validateFenceName,
|
||||
})
|
||||
.then(({ value }) => {
|
||||
const fenceName = value.trim()
|
||||
const fenceData = createFenceData(overlay, shapeType, fenceName)
|
||||
|
||||
// 绑定事件并保存围栏
|
||||
bindOverlayEvents(overlay, fenceData)
|
||||
saveFence(fenceData)
|
||||
|
||||
ElMessage.success(`围栏"${fenceName}"创建成功`)
|
||||
})
|
||||
.catch((error) => {
|
||||
handleFenceCreationCancel(overlay, error)
|
||||
})
|
||||
}
|
||||
|
||||
// 验证围栏名称
|
||||
const validateFenceName = (value: string): boolean | string => {
|
||||
if (!value || value.trim() === '') {
|
||||
return '围栏名称不能为空'
|
||||
}
|
||||
if (value.length > 20) {
|
||||
return '围栏名称不能超过20个字符'
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
// 处理围栏创建取消
|
||||
const handleFenceCreationCancel = (overlay: any, error: any): void => {
|
||||
console.log('用户取消创建围栏:', error)
|
||||
// 清理已绘制的覆盖物
|
||||
if (overlay && map.value) {
|
||||
map.value.removeOverlay(overlay)
|
||||
}
|
||||
// 不显示取消消息如果是用户主动取消
|
||||
if (error !== 'cancel') {
|
||||
ElMessage.info('已取消创建围栏')
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定覆盖物事件
|
||||
const bindOverlayEvents = (overlay: any, fence: any): void => {
|
||||
overlay.addEventListener('click', (e: any) => {
|
||||
showFenceInfo(fence)
|
||||
})
|
||||
}
|
||||
|
||||
// 保存围栏数据
|
||||
const saveFence = (fenceData: any): void => {
|
||||
// 这里可以添加保存到状态管理或后端的逻辑
|
||||
geoFences.value.push(fenceData)
|
||||
}
|
||||
|
||||
|
||||
// 显示围栏信息
|
||||
const showFenceInfo = (fence) => {
|
||||
console.log(fence)
|
||||
ElMessageBox.confirm(
|
||||
`围栏名称: ${fence.name}`,
|
||||
'地理围栏信息',
|
||||
{
|
||||
confirmButtonText: '删除围栏',
|
||||
cancelButtonText: '查看详情',
|
||||
type: 'info',
|
||||
},
|
||||
).then(() => {
|
||||
map.value.removeOverlay(fence.overlay)
|
||||
}).catch(() => {
|
||||
|
||||
})
|
||||
}
|
||||
|
||||
const initMap = () => {
|
||||
if (window.BMap) {
|
||||
const map = new BMap.Map(mapContainer.value)
|
||||
const point = new BMap.Point(106.674974, 26.489328) // 默认贵州贵阳
|
||||
if (window.BMapGL) {
|
||||
map.value = new BMapGL.Map(mapContainer.value)
|
||||
const point = new BMapGL.Point(106.674974, 26.489328) // 默认贵州贵阳
|
||||
|
||||
// 添加标记点
|
||||
points.value.forEach((item: any) => {
|
||||
const point = new BMap.Point(item.lng, item.lat)
|
||||
const point = new BMapGL.Point(item.lng, item.lat)
|
||||
let icon = null
|
||||
if (item.item.type == '3') {
|
||||
icon = new BMap.Icon(icon1, new BMap.Size(30, 30), {
|
||||
imageSize: new BMap.Size(30, 30),
|
||||
icon = new BMapGL.Icon(icon1, new BMapGL.Size(30, 30), {
|
||||
imageSize: new BMapGL.Size(30, 30),
|
||||
})
|
||||
} else {
|
||||
icon = new BMap.Icon(icon2, new BMap.Size(30, 30), {
|
||||
imageSize: new BMap.Size(30, 30),
|
||||
icon = new BMapGL.Icon(icon2, new BMapGL.Size(30, 30), {
|
||||
imageSize: new BMapGL.Size(30, 30),
|
||||
})
|
||||
}
|
||||
const marker = icon ? new BMap.Marker(point, { icon }) : new BMap.Marker(point)
|
||||
map.addOverlay(marker)
|
||||
// const label = new BMap.Label(item.name, { offset: new BMap.Size(20, -10) })
|
||||
// marker.setLabel(label) // 设置标记点名称
|
||||
const marker = icon ? new BMapGL.Marker(point, { icon }) : new BMapGL.Marker(point)
|
||||
map.value.addOverlay(marker)
|
||||
marker.addEventListener('click', () => {
|
||||
// 点击标记点事件
|
||||
console.log('点击了标记点', item)
|
||||
if (item.item.type == '3') {
|
||||
//getWorkCardDetails(item.id)
|
||||
mapWorkCard.value = true
|
||||
|
|
@ -377,18 +475,22 @@ const initMap = () => {
|
|||
mapData.value = item.item
|
||||
tagData.value = mapData.value.aphase
|
||||
tagIndex.value = 1
|
||||
timer.value = setInterval(() => {
|
||||
loginApi()
|
||||
}, 180000)
|
||||
}
|
||||
})
|
||||
})
|
||||
map.addControl(new BMap.NavigationControl()) // 添加平移缩放控件
|
||||
map.centerAndZoom(point, 11) // 设置地图中心点及缩放级别
|
||||
map.enableScrollWheelZoom(true) // 启用滚轮缩放
|
||||
// 将贵阳整个地图放大到级别 7
|
||||
|
||||
// 初始化绘制工具
|
||||
initDrawingTool()
|
||||
|
||||
//map.value.addControl(new BMapGL.NavigationControl()) // 添加平移缩放控件
|
||||
map.value.centerAndZoom(point, 11) // 设置地图中心点及缩放级别
|
||||
map.value.enableScrollWheelZoom(true) // 启用滚轮缩放
|
||||
|
||||
ElMessage.success('地图初始化成功')
|
||||
|
||||
} else {
|
||||
console.error('BMap 未加载')
|
||||
ElMessage.error('地图加载失败,请检查网络连接')
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -406,35 +508,7 @@ const handleTag = (tag: number) => {
|
|||
}
|
||||
|
||||
onMounted(async () => {
|
||||
loginApi()
|
||||
if (!tokenNew) {
|
||||
const origin = window.location.href
|
||||
|
||||
console.log(origin.split('ticket=')[1], 'origin')
|
||||
|
||||
if (origin.indexOf('ticket') != -1) {
|
||||
// console.log('origin.split爱玩送ticket')
|
||||
const res: any = await loginNewApi({
|
||||
ticket: origin.split('ticket=')[1].split('#/')[0],
|
||||
sysType: 0,
|
||||
})
|
||||
|
||||
store.setToken(res.data.access_token)
|
||||
localStorage.setItem('tokenNew', res.data.access_token)
|
||||
const result: any = await getUserInfoAPI()
|
||||
store.setUserInfo(result.user)
|
||||
const roles = result.roles
|
||||
const isAdmin = roles.some((e: any) => e == 'admin')
|
||||
|
||||
if (isAdmin) {
|
||||
localStorage.setItem('rolesType', '3')
|
||||
} else {
|
||||
localStorage.setItem('rolesType', '1')
|
||||
}
|
||||
userStore.editcurrentMenuItem('goodsManagement')
|
||||
// 跳转登录页面
|
||||
}
|
||||
}
|
||||
getMapDataList()
|
||||
})
|
||||
</script>
|
||||
|
||||
|
|
@ -572,7 +646,8 @@ onMounted(async () => {
|
|||
<div class="iot-data-container">
|
||||
<!-- 1.1 设备基本信息分区 -->
|
||||
<div class="data-section">
|
||||
<h3 class="section-heading">一、设备基础信息 <span class="item-value">({{ mapData.uuid || '-' }})</span></h3>
|
||||
<h3 class="section-heading">一、设备基础信息 <span class="item-value">({{ mapData.uuid || '-' }})</span>
|
||||
</h3>
|
||||
<el-row :gutter="30" class="section-content">
|
||||
<el-col :span="8">
|
||||
<div class="data-item">
|
||||
|
|
@ -836,49 +911,65 @@ onMounted(async () => {
|
|||
<el-col :span="6">
|
||||
<div class="data-item">
|
||||
<span class="item-label">电压</span>
|
||||
<span class="item-value">{{ tagData?.voltage ? `${Number(tagData.voltage).toFixed(2)} V` : '-' }}</span>
|
||||
<span
|
||||
class="item-value">{{ tagData?.voltage ? `${Number(tagData.voltage).toFixed(2)} V` : '-'
|
||||
}}</span>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="6">
|
||||
<div class="data-item">
|
||||
<span class="item-label">电流</span>
|
||||
<span class="item-value">{{ tagData?.current ? `${Number(tagData.current).toFixed(2)} A` : '-' }}</span>
|
||||
<span
|
||||
class="item-value">{{ tagData?.current ? `${Number(tagData.current).toFixed(2)} A` : '-'
|
||||
}}</span>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="6">
|
||||
<div class="data-item">
|
||||
<span class="item-label">有功功率</span>
|
||||
<span class="item-value">{{ tagData?.activePower ? `${Number(tagData.activePower).toFixed(2)} W` : '-' }}</span>
|
||||
<span
|
||||
class="item-value">{{ tagData?.activePower ? `${Number(tagData.activePower).toFixed(2)} W` : '-'
|
||||
}}</span>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="6">
|
||||
<div class="data-item">
|
||||
<span class="item-label">无功功率</span>
|
||||
<span class="item-value">{{ tagData?.reactivePower ? `${Number(tagData.reactivePower).toFixed(2)} VAR` : '-' }}</span>
|
||||
<span
|
||||
class="item-value">{{ tagData?.reactivePower ? `${Number(tagData.reactivePower).toFixed(2)} VAR` : '-'
|
||||
}}</span>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="6">
|
||||
<div class="data-item">
|
||||
<span class="item-label">功率因素</span>
|
||||
<span class="item-value">{{ tagData?.powerFactor ? `${Number(tagData.powerFactor).toFixed(2)}` : '-' }}</span>
|
||||
<span
|
||||
class="item-value">{{ tagData?.powerFactor ? `${Number(tagData.powerFactor).toFixed(2)}` : '-'
|
||||
}}</span>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="6">
|
||||
<div class="data-item">
|
||||
<span class="item-label">频率</span>
|
||||
<span class="item-value">{{ tagData?.frequency ? `${Number(tagData.frequency).toFixed(2)} Hz` : '-' }}</span>
|
||||
<span
|
||||
class="item-value">{{ tagData?.frequency ? `${Number(tagData.frequency).toFixed(2)} Hz` : '-'
|
||||
}}</span>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="6">
|
||||
<div class="data-item">
|
||||
<span class="item-label">正向有功</span>
|
||||
<span class="item-value">{{ tagData?.forwardActiveEnergy ? `${Number(tagData.forwardActiveEnergy).toFixed(2)} kWh` : '-' }}</span>
|
||||
<span
|
||||
class="item-value">{{ tagData?.forwardActiveEnergy ? `${Number(tagData.forwardActiveEnergy).toFixed(2)} kWh` : '-'
|
||||
}}</span>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="6">
|
||||
<div class="data-item">
|
||||
<span class="item-label">正向无功</span>
|
||||
<span class="item-value">{{ tagData?.forwardReactiveEnergy ? `${Number(tagData.forwardReactiveEnergy).toFixed(2)} kvarh` : '-' }}</span>
|
||||
<span
|
||||
class="item-value">{{ tagData?.forwardReactiveEnergy ? `${Number(tagData.forwardReactiveEnergy).toFixed(2)} kvarh` : '-'
|
||||
}}</span>
|
||||
</div>
|
||||
</el-col>
|
||||
</el-row>
|
||||
|
|
@ -892,44 +983,6 @@ onMounted(async () => {
|
|||
</template>
|
||||
</el-dialog>
|
||||
|
||||
<!-- <!– 工牌信息弹框 –>-->
|
||||
<!-- <el-dialog v-model="mapWorkCard" title="工牌信息" width="50%">-->
|
||||
<!-- <el-row :gutter="20" class="work-card">-->
|
||||
<!-- <el-col :span="12" :offset="0">设备名称: {{ mapWorkCardData.user_name }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">最近定位时间: {{ mapWorkCardData.sys_time }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">最近位置更新时间: {{ mapWorkCardData.datetime }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">最近信号时间: {{ mapWorkCardData.heart_time }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">超速设置值: {{ mapWorkCardData.sudu }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">状态: {{ mapWorkCardData.status }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">激活时间: {{ mapWorkCardData.use_time }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">电话: {{ mapWorkCardData.tel }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">车牌号: {{ mapWorkCardData.sex }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">设备号: {{ mapWorkCardData.sim_id }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">手机号码: {{ mapWorkCardData.phone }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">设备ID: {{ mapWorkCardData.user_id }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">型号: {{ mapWorkCardData.product_type }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">图标序号: {{ mapWorkCardData.iconType }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">用户到期时间: {{ mapWorkCardData.out_time }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">经度: {{ mapWorkCardData.jingdu }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">iccid: {{ mapWorkCardData.su }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">联系人: {{ mapWorkCardData.owner }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">经纬度: {{ mapWorkCardData.jingwei }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0"-->
|
||||
<!-- >离线报警开关: {{ mapWorkCardData.alarm != 0 ? '开' : '关' }}-->
|
||||
<!-- </el-col-->
|
||||
<!-- >-->
|
||||
<!-- <el-col :span="12" :offset="0">服务商描述: {{ mapWorkCardData.deviceRemark }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">设备软件版本号: {{ mapWorkCardData.macVersion }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">视频地址: {{ mapWorkCardData.VideoConfig }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">高温报警值: {{ mapWorkCardData.HighTempAlarm }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">低温报警值: {{ mapWorkCardData.LowTempAlarm }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">厂商编码: {{ mapWorkCardData.VendorCode }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">业主ID: {{ mapWorkCardData.OwnerId }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">终端类型: {{ mapWorkCardData.TerminalType }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">设备编码: {{ mapWorkCardData.DeviceCode }}</el-col>-->
|
||||
<!-- <el-col :span="12" :offset="0">备注: {{ mapWorkCardData.remark }}</el-col>-->
|
||||
<!-- </el-row>-->
|
||||
<!-- </el-dialog>-->
|
||||
<el-dialog
|
||||
v-model="mapWorkCard"
|
||||
title="工牌"
|
||||
|
|
@ -942,7 +995,8 @@ onMounted(async () => {
|
|||
<div class="iot-data-container">
|
||||
<!-- 1. 设备基础信息区 -->
|
||||
<div class="data-section">
|
||||
<h3 class="section-heading">一、设备基础信息<span class="item-value">({{ mapWorkCardData.uuid || '-' }})</span></h3>
|
||||
<h3 class="section-heading">一、设备基础信息<span class="item-value">({{ mapWorkCardData.uuid || '-'
|
||||
}})</span></h3>
|
||||
<el-row :gutter="30" class="section-content">
|
||||
<el-col :span="8">
|
||||
<div class="data-item">
|
||||
|
|
@ -1119,7 +1173,6 @@ onMounted(async () => {
|
|||
</div>
|
||||
</div>
|
||||
</el-dialog>
|
||||
|
||||
</template>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
|
|
@ -1324,6 +1377,78 @@ onMounted(async () => {
|
|||
margin-top: 20px;
|
||||
flex: 1;
|
||||
border-radius: 8px;
|
||||
position: relative;
|
||||
|
||||
.drawing-controls {
|
||||
position: absolute;
|
||||
top: 10px;
|
||||
left: 10px;
|
||||
z-index: 1000;
|
||||
background: rgba(255, 255, 255, 0.9);
|
||||
padding: 10px;
|
||||
border-radius: 6px;
|
||||
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
|
||||
display: flex;
|
||||
gap: 8px;
|
||||
flex-wrap: wrap;
|
||||
max-width: 300px;
|
||||
}
|
||||
|
||||
.fence-list {
|
||||
position: absolute;
|
||||
top: 70px;
|
||||
left: 10px;
|
||||
z-index: 1000;
|
||||
background: rgba(255, 255, 255, 0.95);
|
||||
padding: 10px;
|
||||
border-radius: 6px;
|
||||
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.1);
|
||||
max-width: 250px;
|
||||
max-height: 300px;
|
||||
overflow-y: auto;
|
||||
|
||||
h4 {
|
||||
margin: 0 0 10px 0;
|
||||
font-size: 14px;
|
||||
color: #333;
|
||||
border-bottom: 1px solid #eee;
|
||||
padding-bottom: 5px;
|
||||
}
|
||||
|
||||
.fence-item {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
padding: 8px;
|
||||
margin-bottom: 5px;
|
||||
background: #f8f9fa;
|
||||
border-radius: 4px;
|
||||
cursor: pointer;
|
||||
transition: background-color 0.2s;
|
||||
|
||||
&:hover {
|
||||
background: #e9ecef;
|
||||
}
|
||||
|
||||
.fence-name {
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
color: #333;
|
||||
}
|
||||
|
||||
.fence-points {
|
||||
font-size: 11px;
|
||||
color: #666;
|
||||
background: #dee2e6;
|
||||
padding: 2px 6px;
|
||||
border-radius: 10px;
|
||||
}
|
||||
}
|
||||
|
||||
.fence-item:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1527,4 +1652,4 @@ onMounted(async () => {
|
|||
background-color: #f1f1f1;
|
||||
border-radius: 4px;
|
||||
}
|
||||
</style>
|
||||
</style>
|
||||
Loading…
Reference in New Issue