接口调试
This commit is contained in:
parent
6e407d15cd
commit
0fde5f9126
|
|
@ -4,4 +4,5 @@ VITE_APP_content = 机器人
|
|||
VITE_APP_baseApiURL = https://s.dumogu.top/api
|
||||
# 路由的base api
|
||||
VITE_APP_routeBasePath = /
|
||||
VITE_APP_biuldBase = /
|
||||
VITE_APP_biuldBase = /
|
||||
VITE_APP_imgPreviewUrl = http://192.168.0.38:21999/robot
|
||||
|
|
@ -19,6 +19,11 @@ export const addMarkerApi = (data) => {
|
|||
return service.post('/robot-screen-api/robot/instruct/addPoint', data)
|
||||
}
|
||||
|
||||
// 删除巡视点位接口
|
||||
export const deleteMarkerApi = (data) => {
|
||||
return service.post('/robot-screen-api/robot/instruct/delPoint', data)
|
||||
}
|
||||
|
||||
// 获取全部已经添加的点位
|
||||
export const getMarkerListAllApi = (data) => {
|
||||
return service.post('/robot-screen-api/robot/instruct/getPointList', data)
|
||||
|
|
@ -59,7 +64,57 @@ export const addPersonApi = (data) => {
|
|||
return service.post('/robot-screen-api/robot/sbdUser/addSbdUser', data)
|
||||
}
|
||||
|
||||
// 获取人员列表
|
||||
export const getPersonListApi = (data) => {
|
||||
return service.get('/robot-screen-api/robot/instruct/list', { params: data })
|
||||
// 修改人员
|
||||
export const updatePersonApi = (data) => {
|
||||
return service.post('/robot-screen-api/robot/sbdUser/updateSbdUser', data)
|
||||
}
|
||||
|
||||
// 删除人员
|
||||
export const deletePersonApi = (data) => {
|
||||
return service.post('/robot-screen-api/robot/sbdUser/delUser', data)
|
||||
}
|
||||
|
||||
// 人员详情
|
||||
export const getDetailsApi = (data) => {
|
||||
return service.get('/robot-screen-api/robot/sbdUser/getDetails', { params: data })
|
||||
}
|
||||
|
||||
// 现场定点巡检拍照 一级列表
|
||||
export const getImageLimitApi = (data) => {
|
||||
return service.get('/robot-screen-api/robot/image/getImageLimit', { params: data })
|
||||
}
|
||||
|
||||
// 现场定点巡检拍照 二级页面列表
|
||||
export const getImagePageListApi = (data) => {
|
||||
return service.get('/robot-screen-api/robot/image/getImagePageList', { params: data })
|
||||
}
|
||||
|
||||
// 智能对比一级页面数据
|
||||
export const getTaskStatisticsApi = (data = {}) => {
|
||||
return service.get('/robot-screen-api/robot/image/getTaskStatistics', { params: data })
|
||||
}
|
||||
|
||||
// 操作面板内上传音频文件接口
|
||||
export const uploadAudioApi = (data) => {
|
||||
return service.post('/robot-screen-api/robot/instruct/addVideoFile', data)
|
||||
}
|
||||
|
||||
// 操作面板内获取音频文件信息
|
||||
export const getAudioInfoApi = (data) => {
|
||||
return service.post('/robot-screen-api/robot/instruct/getVideoList', data)
|
||||
}
|
||||
|
||||
// 人员动态 一级页面列表接口
|
||||
export const getUserListLimitApi = (data) => {
|
||||
return service.post('/robot-screen-api/robot/sbdUser/getUserListLimit', data)
|
||||
}
|
||||
|
||||
// 人员动态 二级级页面人员动态列表接口
|
||||
export const getUserListPageApi = (data) => {
|
||||
return service.get('/robot-screen-api/robot/sbdUser/getUserList', { params: data })
|
||||
}
|
||||
|
||||
// 人员动态 二级级页面人员信息列表接口
|
||||
export const getUserInfoListApi = (data) => {
|
||||
return service.get('/robot-screen-api/robot/sbdUser/list', { params: data })
|
||||
}
|
||||
|
|
|
|||
|
|
@ -19,13 +19,15 @@ export const getDeviceUrlApi = (data) => {
|
|||
export const changeDeviceCameraApi = (data) => {
|
||||
return service.post('/third-party/PTZ/C_PTZ_Turn?token=' + data.token, data)
|
||||
}
|
||||
|
||||
// 调整设备的摄像机放大图像
|
||||
export const changeDeviceCameraZoomInApi = (data) => {
|
||||
return service.post('/third-party/PTZ/C_PTZ_ZoomInPicture?token=' + data.token, data)
|
||||
}
|
||||
|
||||
// 调整设备的摄像机缩小图像
|
||||
export const changeDeviceCameraZoomOutApi = (data) => {
|
||||
return service.post('/third-party/PTZ//C_PTZ_ZoomOutPicture?token=' + data.token, data)
|
||||
return service.post('/third-party/PTZ/C_PTZ_ZoomOutPicture?token=' + data.token, data)
|
||||
}
|
||||
|
||||
// 停止设备缩放
|
||||
|
|
|
|||
|
|
@ -11,41 +11,43 @@
|
|||
<div class="marquee-track" :style="{ width: trackWidth }">
|
||||
<div
|
||||
class="marquee-item"
|
||||
v-for="item in items"
|
||||
v-for="item in imgOuterList"
|
||||
:key="item.id"
|
||||
:style="{ width: imgWidth + 'px' }"
|
||||
>
|
||||
<n-image
|
||||
:width="imgWidth"
|
||||
:height="imgHeight"
|
||||
:src="item.image"
|
||||
:src="imgPreviewUrl + item.image"
|
||||
class="item-image"
|
||||
/>
|
||||
<div class="marquee-item-title">途径点{{ item.id }}</div>
|
||||
<div class="marquee-item-time">{{ item.time }}</div>
|
||||
<div class="type-container" :class="item.status">
|
||||
{{ item.status === 'arrived' ? '已到达' : '未到达' }}
|
||||
<div class="marquee-item-title">{{ item?.pointName }}</div>
|
||||
<div class="marquee-item-time">{{ item?.taskTime }}</div>
|
||||
<div class="type-container arrived">
|
||||
<!-- {{ item.status === 'arrived' ? '已到达' : '未到达' }} -->
|
||||
已到达
|
||||
</div>
|
||||
</div>
|
||||
<!-- 克隆元素实现无缝循环 -->
|
||||
<div
|
||||
class="marquee-item"
|
||||
v-for="item in items"
|
||||
v-for="item in imgOuterList"
|
||||
:key="`clone-${item.id}`"
|
||||
v-if="items.length > 4"
|
||||
v-if="imgOuterList.length > 4"
|
||||
:style="{ width: imgWidth + 'px' }"
|
||||
>
|
||||
<n-image
|
||||
:width="imgWidth"
|
||||
:height="imgHeight"
|
||||
:src="item.image"
|
||||
:src="imgPreviewUrl + item.image"
|
||||
object-fit="cover"
|
||||
class="item-image"
|
||||
/>
|
||||
<div class="marquee-item-title">途径点{{ item.id }}</div>
|
||||
<div class="marquee-item-time">{{ item.time }}</div>
|
||||
<div class="type-container" :class="item.status">
|
||||
{{ item.status === 'arrived' ? '已到达' : '未到达' }}
|
||||
<div class="marquee-item-title">{{ item?.pointName }}</div>
|
||||
<div class="marquee-item-time">{{ item?.taskTime }}</div>
|
||||
<div class="type-container arrived">
|
||||
<!-- {{ item.status === 'arrived' ? '已到达' : '未到达' }} -->
|
||||
已到达
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -83,16 +85,31 @@
|
|||
size="small"
|
||||
label-placement="left"
|
||||
style="margin-top: 10px"
|
||||
:model="innerQueryParams"
|
||||
>
|
||||
<n-form-item>
|
||||
<n-date-picker type="daterange" clearable style="width: 240px" />
|
||||
</n-form-item>
|
||||
<n-form-item>
|
||||
<n-input placeholder="输入途经点" clearable style="width: 240px" />
|
||||
<n-date-picker
|
||||
clearable
|
||||
type="daterange"
|
||||
style="width: 240px"
|
||||
v-model:formatted-value="ranger"
|
||||
formatted-value="['YYYY-MM-DD HH:mm:ss', 'YYYY-MM-DD HH:mm:ss']"
|
||||
/>
|
||||
</n-form-item>
|
||||
|
||||
<n-button type="info"> 查询</n-button>
|
||||
<n-button color="#6E90A9" style="margin-left: 8px"> 重置 </n-button>
|
||||
<n-form-item>
|
||||
<n-input
|
||||
clearable
|
||||
placeholder="输入途经点"
|
||||
style="width: 240px"
|
||||
v-model:value="innerQueryParams.pointName"
|
||||
/>
|
||||
</n-form-item>
|
||||
|
||||
<n-button type="info" @click="getImageInnerData"> 查询</n-button>
|
||||
<n-button color="#6E90A9" style="margin-left: 8px" @click="onHandleReset">
|
||||
重置
|
||||
</n-button>
|
||||
</n-form>
|
||||
|
||||
<!-- 内容区域 -->
|
||||
|
|
@ -100,7 +117,7 @@
|
|||
<!-- 分页 -->
|
||||
|
||||
<div
|
||||
v-for="item in 7"
|
||||
v-for="item in imgInnerList"
|
||||
:key="item"
|
||||
class="table-item"
|
||||
:style="{ width: tableItemWidth + 'px' }"
|
||||
|
|
@ -110,22 +127,24 @@
|
|||
height="170"
|
||||
object-fit="cover"
|
||||
class="item-image"
|
||||
src="https://img1.baidu.com/it/u=3294211986,2810142789&fm=253&fmt=auto&app=138&f=JPEG?w=500&h=500"
|
||||
:src="imgPreviewUrl + item?.image"
|
||||
/>
|
||||
<div class="table-item-title">
|
||||
<span>途经点</span>
|
||||
<span>2025-06-01 10:00:00</span>
|
||||
<span>{{ item?.pointName }}</span>
|
||||
<span>{{ item?.taskTime }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
|
||||
<n-pagination
|
||||
v-model:page="page"
|
||||
v-model:page-size="pageSize"
|
||||
:page-count="100"
|
||||
show-size-picker
|
||||
:item-count="innerTotal"
|
||||
:page-sizes="[10, 20, 30, 40]"
|
||||
@update:page="pageNumChange"
|
||||
@update:page-size="pageSizeChange"
|
||||
v-model:page="innerQueryParams.pageNum"
|
||||
v-model:page-size="innerQueryParams.pageSize"
|
||||
/>
|
||||
</div>
|
||||
</n-card>
|
||||
|
|
@ -135,62 +154,31 @@
|
|||
<script setup scoped>
|
||||
import TitleBackground from '@/components/TitleBackground/index.vue'
|
||||
import { ref, onMounted, onUnmounted } from 'vue'
|
||||
import { getImageLimitApi, getImagePageListApi } from '@/api/home'
|
||||
|
||||
import imgSrc from '@/assets/demo.png'
|
||||
|
||||
const morePanelVisible = ref(false)
|
||||
const searchForm = ref({})
|
||||
const marqueeContainer = ref(null)
|
||||
const trackWidth = ref('auto')
|
||||
const imageHeight = ref('0px')
|
||||
const itemMargin = 10 // 右边距10px
|
||||
const page = ref(1)
|
||||
const pageSize = ref(10)
|
||||
const imgHeight = ref(0)
|
||||
const imgWidth = ref(0)
|
||||
const tableItemWidth = ref(0)
|
||||
const marqueeOuterRef = ref(null)
|
||||
const tableContainerRef = ref(null)
|
||||
const imgOuterList = ref([]) // 一级页面数据
|
||||
const imgInnerList = ref([]) // 二级页面数据
|
||||
const innerTotal = ref(0)
|
||||
const ranger = ref(null)
|
||||
const imgPreviewUrl = ref('http://192.168.0.38:21999/robot') // 图片预览地址
|
||||
|
||||
// 模拟数据
|
||||
const items = ref([
|
||||
{
|
||||
id: 1,
|
||||
time: '14:23:56',
|
||||
status: 'arrived',
|
||||
image: imgSrc,
|
||||
},
|
||||
{
|
||||
id: 2,
|
||||
time: '15:10:22',
|
||||
status: 'not-arrived',
|
||||
image: 'https://07akioni.oss-cn-beijing.aliyuncs.com/07akioni.jpeg',
|
||||
},
|
||||
{
|
||||
id: 1,
|
||||
time: '14:23:56',
|
||||
status: 'arrived',
|
||||
image: imgSrc,
|
||||
},
|
||||
{
|
||||
id: 2,
|
||||
time: '15:10:22',
|
||||
status: 'not-arrived',
|
||||
image: 'https://07akioni.oss-cn-beijing.aliyuncs.com/07akioni.jpeg',
|
||||
},
|
||||
{
|
||||
id: 1,
|
||||
time: '14:23:56',
|
||||
status: 'arrived',
|
||||
image: imgSrc,
|
||||
},
|
||||
{
|
||||
id: 2,
|
||||
time: '15:10:22',
|
||||
status: 'not-arrived',
|
||||
image: 'https://07akioni.oss-cn-beijing.aliyuncs.com/07akioni.jpeg',
|
||||
},
|
||||
])
|
||||
const innerQueryParams = ref({
|
||||
pageNum: 1,
|
||||
pageSize: 8,
|
||||
startDay: '', // 开始时间
|
||||
endDay: '', // 结束时间
|
||||
pointName: '', // 途经点
|
||||
})
|
||||
|
||||
// 计算并启动跑马灯
|
||||
const setupMarquee = () => {
|
||||
|
|
@ -218,23 +206,61 @@ const setupMarquee = () => {
|
|||
document.documentElement.style.setProperty('--animation-duration', `${animationDuration}s`)
|
||||
}
|
||||
|
||||
const pageNumChange = (pageNum) => {
|
||||
innerQueryParams.value.pageNum = pageNum
|
||||
getImageInnerData()
|
||||
}
|
||||
|
||||
const pageSizeChange = (pageSize) => {
|
||||
innerQueryParams.value.pageSize = pageSize
|
||||
getImageInnerData()
|
||||
}
|
||||
|
||||
// 获取二级页面数据
|
||||
const getImageInnerData = async () => {
|
||||
const [startDay, endDay] = ranger?.value || []
|
||||
innerQueryParams.value.startDay = startDay || ''
|
||||
innerQueryParams.value.endDay = endDay || ''
|
||||
|
||||
const { data: res } = await getImagePageListApi(innerQueryParams.value)
|
||||
imgInnerList.value = res?.rows
|
||||
innerTotal.value = res?.total
|
||||
}
|
||||
|
||||
// 更多按钮点击
|
||||
const onHandleMore = () => {
|
||||
morePanelVisible.value = true
|
||||
|
||||
nextTick(() => {
|
||||
// setupMarquee()
|
||||
|
||||
const tableContainer = tableContainerRef.value
|
||||
|
||||
tableItemWidth.value = (tableContainer.clientWidth - 40) / 4
|
||||
console.log(tableContainer.clientWidth, 'tableContainer')
|
||||
getImageInnerData()
|
||||
})
|
||||
}
|
||||
|
||||
// 获取轮播图数据
|
||||
const getImageLimitData = async () => {
|
||||
const { data: res } = await getImageLimitApi({})
|
||||
imgOuterList.value = res?.data
|
||||
}
|
||||
|
||||
// 重置按钮
|
||||
const onHandleReset = () => {
|
||||
ranger.value = null
|
||||
innerQueryParams.value = {
|
||||
page: 1,
|
||||
pageSize: 10,
|
||||
startTime: '',
|
||||
endTime: '',
|
||||
pointName: '',
|
||||
}
|
||||
|
||||
getImageInnerData()
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
setupMarquee()
|
||||
window.addEventListener('resize', setupMarquee)
|
||||
getImageLimitData()
|
||||
nextTick(() => {
|
||||
const container = marqueeContainer.value
|
||||
imgWidth.value = (container.clientWidth - 40) / 4
|
||||
|
|
@ -380,6 +406,7 @@ onUnmounted(() => {
|
|||
|
||||
.table-container {
|
||||
// height: 75%;
|
||||
// min-height: 50vh;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
color: #fff;
|
||||
|
|
|
|||
|
|
@ -75,34 +75,29 @@
|
|||
<!-- 上下左右控制按钮 -->
|
||||
<img
|
||||
class="arrow-top hand-direction"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
alt=""
|
||||
@click="handleChangeCamera('up')"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
/>
|
||||
<img
|
||||
class="arrow-right hand-direction"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
alt=""
|
||||
@click="handleChangeCamera('right')"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
/>
|
||||
<img
|
||||
class="arrow-bottom hand-direction"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
alt=""
|
||||
@click="handleChangeCamera('down')"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
/>
|
||||
<img
|
||||
class="arrow-left hand-direction"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
alt=""
|
||||
@click="handleChangeCamera('left')"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
/>
|
||||
|
||||
<!-- 中间的按钮 -->
|
||||
<div class="row-3-item-1-center">
|
||||
<img
|
||||
class="center-icon"
|
||||
alt=""
|
||||
:src="isStopLeft ? stopImg : startImg"
|
||||
@click="handleChangeCamera('stop')"
|
||||
/>
|
||||
|
|
@ -118,15 +113,13 @@
|
|||
<div class="add-reduce-btn">
|
||||
<span>缩放</span>
|
||||
<img
|
||||
src="@/assets/home-imgs/control-2-add.png"
|
||||
alt=""
|
||||
style="margin-bottom: 2px"
|
||||
@click="handleChangeZoomCamera('ZoomIn')"
|
||||
src="@/assets/home-imgs/control-2-add.png"
|
||||
/>
|
||||
<img
|
||||
src="@/assets/home-imgs/control-2-reduce.png"
|
||||
alt=""
|
||||
@click="handleChangeZoomCamera('ZoomOut')"
|
||||
src="@/assets/home-imgs/control-2-reduce.png"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -135,8 +128,8 @@
|
|||
<div class="row-3-item-2" ref="container">
|
||||
<!-- 上下滑动调节 -->
|
||||
<span
|
||||
class="up-down-box"
|
||||
ref="draggable"
|
||||
class="up-down-box"
|
||||
@mousedown="startDrag"
|
||||
:style="{ top: currentTop + 'px' }"
|
||||
/>
|
||||
|
|
@ -146,35 +139,30 @@
|
|||
<div class="row-3-item-3">
|
||||
<!-- 上下左右控制按钮 -->
|
||||
<img
|
||||
@click="handleChangeRobot('5')"
|
||||
class="arrow-top"
|
||||
@click="handleChangeRobot('5')"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
alt=""
|
||||
/>
|
||||
<img
|
||||
@click="handleChangeRobot('8')"
|
||||
class="arrow-right"
|
||||
@click="handleChangeRobot('8')"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
alt=""
|
||||
/>
|
||||
<img
|
||||
@click="handleChangeRobot('6')"
|
||||
class="arrow-bottom"
|
||||
@click="handleChangeRobot('6')"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
alt=""
|
||||
/>
|
||||
<img
|
||||
@click="handleChangeRobot('7')"
|
||||
class="arrow-left"
|
||||
@click="handleChangeRobot('7')"
|
||||
src="@/assets/home-imgs/control-2-arrow.png"
|
||||
alt=""
|
||||
/>
|
||||
|
||||
<div class="row-3-item-1-center">
|
||||
<img
|
||||
class="center-icon"
|
||||
:src="isStopRight ? startImg : stopImg"
|
||||
alt=""
|
||||
@click="handleChangeRobot('9')"
|
||||
/>
|
||||
</div>
|
||||
|
|
@ -189,10 +177,10 @@
|
|||
<n-grid-item :span="3">
|
||||
<div>
|
||||
<n-radio
|
||||
:checked="checkedValue === '关'"
|
||||
value="关"
|
||||
name="basic-demo"
|
||||
@change="handleChange1"
|
||||
:checked="checkedValue === '关'"
|
||||
>
|
||||
关
|
||||
</n-radio>
|
||||
|
|
@ -201,10 +189,10 @@
|
|||
<n-grid-item :span="3">
|
||||
<div>
|
||||
<n-radio
|
||||
:checked="checkedValue === '闪烁'"
|
||||
value="闪烁"
|
||||
name="basic-demo"
|
||||
@change="handleChange2"
|
||||
:checked="checkedValue === '闪烁'"
|
||||
>
|
||||
闪烁
|
||||
</n-radio>
|
||||
|
|
@ -213,10 +201,10 @@
|
|||
<n-grid-item :span="3">
|
||||
<div class="row-4-item">
|
||||
<n-radio
|
||||
:checked="checkedValue === '运动时闪烁'"
|
||||
value="运动时闪烁"
|
||||
name="basic-demo"
|
||||
@change="handleChange3"
|
||||
:checked="checkedValue === '运动时闪烁'"
|
||||
>
|
||||
运动时闪烁
|
||||
</n-radio>
|
||||
|
|
@ -243,7 +231,7 @@
|
|||
:options="selectOptions"
|
||||
/> -->
|
||||
|
||||
<n-select
|
||||
<!-- <n-select
|
||||
:options="selectOptions"
|
||||
size="small"
|
||||
:dropdown-style="{
|
||||
|
|
@ -251,9 +239,34 @@
|
|||
boxShadow: '0 4px 6px -1px rgba(0, 0, 0, 0.1)',
|
||||
color: '#fff',
|
||||
}"
|
||||
/>
|
||||
/> -->
|
||||
|
||||
<!-- <n-button type="info" size="small">请上传</n-button> -->
|
||||
|
||||
<n-upload
|
||||
:accept="audioMimeTypes"
|
||||
:show-file-list="false"
|
||||
:default-upload="false"
|
||||
@before-upload="beforeUpload"
|
||||
@change="handleChangeUpload"
|
||||
v-if="!audioInfo"
|
||||
>
|
||||
<n-button type="info" size="small">请上传</n-button>
|
||||
</n-upload>
|
||||
|
||||
<n-popselect
|
||||
trigger="click"
|
||||
v-model:value="audioValue"
|
||||
:options="audioOptions"
|
||||
@update:value="handleChangeAudio"
|
||||
v-else
|
||||
>
|
||||
<n-button type="info" size="small">
|
||||
{{ audioInfo?.fileName }}
|
||||
</n-button>
|
||||
</n-popselect>
|
||||
</div>
|
||||
<div style="margin-top: 16px">
|
||||
<!-- <div style="margin-top: 16px">
|
||||
<n-radio
|
||||
:checked="checkedValue === '循环播放'"
|
||||
value="循环播放"
|
||||
|
|
@ -262,7 +275,7 @@
|
|||
>
|
||||
循环播放
|
||||
</n-radio>
|
||||
</div>
|
||||
</div> -->
|
||||
</div>
|
||||
</n-grid-item>
|
||||
<n-grid-item :span="6">
|
||||
|
|
@ -277,7 +290,7 @@
|
|||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row-5-item-1" style="margin-top: 16px">
|
||||
<!-- <div class="row-5-item-1" style="margin-top: 16px">
|
||||
<img src="@/assets/home-imgs/control-3-video.png" alt="" />
|
||||
<div style="width: 60%">
|
||||
<n-slider
|
||||
|
|
@ -286,7 +299,7 @@
|
|||
:format-tooltip="formatTooltip"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div> -->
|
||||
</div>
|
||||
</n-grid-item>
|
||||
</n-grid>
|
||||
|
|
@ -303,19 +316,21 @@
|
|||
</n-grid-item>
|
||||
</n-grid>
|
||||
</div>
|
||||
|
||||
<n-modal v-model:show="selectPlayType"> 播放类型 </n-modal>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { ref, onMounted } from 'vue'
|
||||
import { ref, onMounted, h } from 'vue'
|
||||
|
||||
import {
|
||||
changeDeviceCameraApi,
|
||||
stopDeviceCameraApi,
|
||||
changeDeviceCameraApi,
|
||||
stopDeviceCameraZoomApi,
|
||||
changeDeviceCameraZoomInApi,
|
||||
changeDeviceCameraZoomOutApi,
|
||||
stopDeviceCameraZoomApi,
|
||||
} from '@/utils/initLogin'
|
||||
import { handleRobotActionApi } from '@/api/home'
|
||||
import { handleRobotActionApi, uploadAudioApi, getAudioInfoApi } from '@/api/home'
|
||||
import { useRobotDataStore } from '@/store/robot'
|
||||
import { getRobotTokenFn, getRobotDeviceListFn } from '@/utils/getRobotInfo.js'
|
||||
import {
|
||||
|
|
@ -324,16 +339,17 @@ import {
|
|||
BatteryFullSharp,
|
||||
BatteryChargingSharp,
|
||||
} from '@vicons/ionicons5'
|
||||
import { useMessage } from 'naive-ui'
|
||||
import { useMessage, useDialog, NRadio, NRadioGroup, NInputNumber, NSpace } from 'naive-ui'
|
||||
import { debounce } from 'lodash'
|
||||
|
||||
import stopImg from '@/assets/home-imgs/control-2-stop.png'
|
||||
import startImg from '@/assets/home-imgs/control-2-start.png'
|
||||
|
||||
const dialog = useDialog()
|
||||
const message = useMessage()
|
||||
const robotData = useRobotDataStore()
|
||||
const isStopLeft = ref(true)
|
||||
const isStopRight = ref(false)
|
||||
const robotData = useRobotDataStore()
|
||||
const message = useMessage()
|
||||
const upDownHeight = ref(30)
|
||||
const container = ref(null)
|
||||
const draggable = ref(null)
|
||||
|
|
@ -347,17 +363,79 @@ const deviceToken = ref('')
|
|||
const deviceInfo = ref({})
|
||||
const isZoom = ref(false)
|
||||
const robotBaseInfo = ref({})
|
||||
const selectOptions = ref([
|
||||
const selectPlayType = ref(false)
|
||||
|
||||
const audioValue = ref('')
|
||||
const audioInfo = ref(null)
|
||||
const audioMimeTypes = ref(
|
||||
'.pcm,.wav,.aac,audio/wav,audio/x-wav,audio/x-aiff,audio/aac,audio/x-aac',
|
||||
)
|
||||
|
||||
const audioOptions = ref([
|
||||
{
|
||||
label: '录音1',
|
||||
value: '录音1',
|
||||
label: '播放',
|
||||
value: '播放',
|
||||
},
|
||||
{
|
||||
label: '录音2',
|
||||
value: '录音2',
|
||||
label: '删除',
|
||||
value: '删除',
|
||||
},
|
||||
{
|
||||
label: '暂停',
|
||||
value: '暂停',
|
||||
},
|
||||
])
|
||||
|
||||
const beforeUpload = ({ file }) => {
|
||||
const allowedExtensions = ['.pcm', '.wav', '.aac']
|
||||
const fileName = file.name.toLowerCase()
|
||||
const isValid = allowedExtensions.some((ext) => fileName.endsWith(ext))
|
||||
|
||||
if (!isValid) {
|
||||
message.error('只能上传 PCM、WAV、AAC 格式的音频文件')
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
// 上传音频
|
||||
const handleChangeUpload = async (e) => {
|
||||
const file = e.file
|
||||
const formData = new FormData()
|
||||
formData.append('file', file.file)
|
||||
formData.append('puid', deviceInfo.value?.puId)
|
||||
|
||||
const { data: res } = await uploadAudioApi(formData)
|
||||
|
||||
if (res.code == 200) {
|
||||
message.success('上传音频文件成功')
|
||||
|
||||
getAudioInfo()
|
||||
} else {
|
||||
message.error('上传音频文件失败')
|
||||
}
|
||||
}
|
||||
|
||||
// 获取音频信息
|
||||
const getAudioInfo = async () => {
|
||||
const { data: res } = await getAudioInfoApi({
|
||||
puid: deviceInfo.value?.puId,
|
||||
})
|
||||
|
||||
if (res.code == 200) {
|
||||
audioInfo.value = res?.data
|
||||
}
|
||||
}
|
||||
|
||||
const handleChangeAudio = (e) => {
|
||||
// console.log(e, '选择音频操作')
|
||||
if (e === '播放') {
|
||||
// showPlayTypeDialog()
|
||||
|
||||
selectPlayType.value = true
|
||||
}
|
||||
}
|
||||
|
||||
// 计算当前高度百分比(0-100)
|
||||
const currentHeight = computed(() => {
|
||||
if (!container.value) return 0
|
||||
|
|
@ -431,9 +509,9 @@ const formatTooltip = (value) => {
|
|||
const handleStopDeviceCameraZoom = async () => {
|
||||
isZoom.value = false
|
||||
const res = await stopDeviceCameraZoomApi({
|
||||
idx: 0,
|
||||
token: deviceToken.value,
|
||||
puid: '201115200268437643',
|
||||
idx: 0,
|
||||
})
|
||||
|
||||
console.log(res, '停止位置---')
|
||||
|
|
@ -444,7 +522,6 @@ const handleChangeCamera = debounce(async (motion) => {
|
|||
if (motion === 'stop' && isZoom.value) {
|
||||
isStopLeft.value = true
|
||||
handleStopDeviceCameraZoom()
|
||||
|
||||
return
|
||||
}
|
||||
if (motion === 'stop') {
|
||||
|
|
@ -517,7 +594,6 @@ const getRobotBaseInfo = async () => {
|
|||
puId: deviceInfo.value?.puId,
|
||||
type: '1',
|
||||
})
|
||||
console.log(res, '获取机器人的基础信息---')
|
||||
|
||||
robotBaseInfo.value = res.data
|
||||
}
|
||||
|
|
@ -527,8 +603,8 @@ onMounted(async () => {
|
|||
const device = await getRobotDeviceListFn() // 获取设备信息
|
||||
deviceToken.value = token
|
||||
deviceInfo.value = device
|
||||
|
||||
getRobotBaseInfo()
|
||||
getAudioInfo()
|
||||
})
|
||||
</script>
|
||||
<style lang="scss" scoped>
|
||||
|
|
|
|||
|
|
@ -83,7 +83,7 @@ import { NIcon } from 'naive-ui'
|
|||
import { throttle } from 'lodash'
|
||||
import { AddCircleOutline, RemoveCircleOutline } from '@vicons/ionicons5'
|
||||
import { getRobotDeviceListFn, getRobotMapInfoFn } from '@/utils/getRobotInfo'
|
||||
import { getMarkerListAllApi } from '@/api/home'
|
||||
import { getMarkerListAllApi, deleteMarkerApi } from '@/api/home'
|
||||
import { useMessage } from 'naive-ui'
|
||||
|
||||
const modalTitle = ref('预置位配置') // 模态框标题
|
||||
|
|
@ -424,6 +424,7 @@ const handleModifyPoint = () => {
|
|||
markerAngle: point.markerAngle,
|
||||
markerPreset: point.markerPreset,
|
||||
id: point.id,
|
||||
isAdd: point.isAdd,
|
||||
}
|
||||
emits('onHandleAddMarker', markerInfo)
|
||||
}
|
||||
|
|
@ -431,9 +432,20 @@ const handleModifyPoint = () => {
|
|||
}
|
||||
|
||||
// 删除点位
|
||||
const handleDeletePoint = () => {
|
||||
const handleDeletePoint = async () => {
|
||||
if (selectedPointIndex.value >= 0) {
|
||||
devicePoints.value.splice(selectedPointIndex.value, 1)
|
||||
if (devicePoints.value[selectedPointIndex.value].isAdd) {
|
||||
devicePoints.value.splice(selectedPointIndex.value, 1)
|
||||
} else {
|
||||
// 调后台接口删除
|
||||
const { data: res } = await deleteMarkerApi({
|
||||
id: devicePoints.value[selectedPointIndex.value].id,
|
||||
})
|
||||
if (res.code == 200) {
|
||||
// 重新获取所有点位
|
||||
devicePoints.value.splice(selectedPointIndex.value, 1)
|
||||
}
|
||||
}
|
||||
}
|
||||
closeContextMenu()
|
||||
}
|
||||
|
|
@ -450,6 +462,7 @@ const addDevicePoint = (x, y, y1) => {
|
|||
markerName: '',
|
||||
markerAngle: '', // 角度
|
||||
markerPreset: '', // 摄像头预置位
|
||||
isAdd: true,
|
||||
})
|
||||
}
|
||||
|
||||
|
|
@ -470,6 +483,7 @@ const handlePointClick = (point, index) => {
|
|||
markerName: point.markerName,
|
||||
markerAngle: point.markerAngle,
|
||||
markerPreset: point.markerPreset,
|
||||
isAdd: point.isAdd,
|
||||
}
|
||||
emits('onHandleAddMarker', markerInfo)
|
||||
}
|
||||
|
|
@ -501,6 +515,7 @@ const getMarkerListAll = async () => {
|
|||
markerY1: logicalY1,
|
||||
markerName: item.pointName,
|
||||
markerAngle: item.theta,
|
||||
isAdd: false,
|
||||
})
|
||||
})
|
||||
}
|
||||
|
|
|
|||
|
|
@ -21,21 +21,21 @@
|
|||
<n-grid
|
||||
x-gap="12"
|
||||
:cols="4"
|
||||
v-for="item in 10"
|
||||
:key="item"
|
||||
v-for="(item, index) in outerUserList"
|
||||
:key="index"
|
||||
class="person-tb-content-grid"
|
||||
:class="{ active: item % 2 === 0 }"
|
||||
:class="{ active: index % 2 === 0 }"
|
||||
>
|
||||
<!-- 网格内容保持不变 -->
|
||||
<n-gi>
|
||||
<div class="person-item">16:30:30</div>
|
||||
<div class="person-item">{{ item?.createTime.split(' ')[1] }}</div>
|
||||
</n-gi>
|
||||
<n-gi>
|
||||
<div class="person-item">
|
||||
<n-image
|
||||
width="60"
|
||||
height="50"
|
||||
src="https://img1.baidu.com/it/u=3294211986,2810142789&fm=253&fmt=auto&app=138&f=JPEG?w=500&h=500"
|
||||
:src="imgPreviewUrl + item?.dataImage"
|
||||
>
|
||||
<template #error>
|
||||
<n-icon :size="100" color="lightGrey">
|
||||
|
|
@ -46,10 +46,10 @@
|
|||
</div>
|
||||
</n-gi>
|
||||
<n-gi>
|
||||
<div class="person-item">张三</div>
|
||||
<div class="person-item">{{ item?.userName || '-' }}</div>
|
||||
</n-gi>
|
||||
<n-gi>
|
||||
<div class="person-item">电工</div>
|
||||
<div class="person-item">{{ item?.workType || '-' }}</div>
|
||||
</n-gi>
|
||||
</n-grid>
|
||||
</div>
|
||||
|
|
@ -102,25 +102,43 @@
|
|||
v-if="activeIndex === 0"
|
||||
>
|
||||
<n-form-item>
|
||||
<n-date-picker type="daterange" clearable style="width: 240px" />
|
||||
<n-date-picker
|
||||
clearable
|
||||
type="daterange"
|
||||
style="width: 240px"
|
||||
v-model:formatted-value="ranger_1"
|
||||
formatted-value="['YYYY-MM-DD HH:mm:ss', 'YYYY-MM-DD HH:mm:ss']"
|
||||
/>
|
||||
</n-form-item>
|
||||
<n-form-item>
|
||||
<n-input placeholder="输入途经点" clearable style="width: 240px" />
|
||||
<n-input
|
||||
clearable
|
||||
placeholder="人员姓名"
|
||||
style="width: 240px"
|
||||
v-model:value="innerQueryParams_1.userName"
|
||||
/>
|
||||
</n-form-item>
|
||||
<n-form-item>
|
||||
<n-input placeholder="类型" clearable style="width: 240px" />
|
||||
<n-input
|
||||
clearable
|
||||
placeholder="工种"
|
||||
style="width: 240px"
|
||||
v-model:value="innerQueryParams_1.workType"
|
||||
/>
|
||||
</n-form-item>
|
||||
|
||||
<n-button type="info"> 查询</n-button>
|
||||
<n-button color="#6E90A9" style="margin-left: 8px"> 重置 </n-button>
|
||||
<n-button type="info" @click="getUserListPageFn"> 查询</n-button>
|
||||
<n-button color="#6E90A9" style="margin-left: 8px" @click="onHandleReset_1">
|
||||
重置
|
||||
</n-button>
|
||||
</n-form>
|
||||
|
||||
<!-- 内容区域 -->
|
||||
<n-data-table
|
||||
:data="data"
|
||||
:data="tableData_1"
|
||||
:scroll-x="10"
|
||||
flex-height
|
||||
:columns="columns"
|
||||
:columns="tableColumns_1"
|
||||
:style="{ height: `70%` }"
|
||||
v-if="activeIndex === 0"
|
||||
/>
|
||||
|
|
@ -134,17 +152,35 @@
|
|||
v-if="activeIndex === 1"
|
||||
>
|
||||
<n-form-item>
|
||||
<n-date-picker type="daterange" clearable style="width: 240px" />
|
||||
<n-date-picker
|
||||
clearable
|
||||
type="daterange"
|
||||
style="width: 240px"
|
||||
v-model:formatted-value="ranger_2"
|
||||
formatted-value="['YYYY-MM-DD HH:mm:ss', 'YYYY-MM-DD HH:mm:ss']"
|
||||
/>
|
||||
</n-form-item>
|
||||
<n-form-item>
|
||||
<n-input placeholder="输入途经点" clearable style="width: 240px" />
|
||||
<n-input
|
||||
clearable
|
||||
placeholder="人员姓名"
|
||||
style="width: 240px"
|
||||
v-model:value="innerQueryParams_2.userName"
|
||||
/>
|
||||
</n-form-item>
|
||||
<n-form-item>
|
||||
<n-input placeholder="类型" clearable style="width: 240px" />
|
||||
<n-input
|
||||
clearable
|
||||
placeholder="工种"
|
||||
style="width: 240px"
|
||||
v-model:value="innerQueryParams_2.workType"
|
||||
/>
|
||||
</n-form-item>
|
||||
|
||||
<n-button type="info"> 查询</n-button>
|
||||
<n-button color="#6E90A9" style="margin-left: 8px"> 重置 </n-button>
|
||||
<n-button type="info" @click="getProjectPersonList"> 查询</n-button>
|
||||
<n-button color="#6E90A9" style="margin-left: 8px" @click="onHandleReset_2">
|
||||
重置
|
||||
</n-button>
|
||||
<n-button type="info" style="margin-left: 10px" @click="onHandleAddPerson">
|
||||
新增项目部人员
|
||||
</n-button>
|
||||
|
|
@ -152,22 +188,37 @@
|
|||
|
||||
<!-- 内容区域 -->
|
||||
<n-data-table
|
||||
:data="data"
|
||||
:scroll-x="10"
|
||||
flex-height
|
||||
:columns="columns"
|
||||
:scroll-x="10"
|
||||
:data="tableData_2"
|
||||
:columns="tableColumns_2"
|
||||
:style="{ height: `70%` }"
|
||||
v-if="activeIndex === 1"
|
||||
/>
|
||||
|
||||
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
|
||||
<n-pagination
|
||||
:page-count="100"
|
||||
show-size-picker
|
||||
v-model:page="page"
|
||||
v-if="activeIndex === 0"
|
||||
v-model:page-size="pageSize"
|
||||
:item-count="tableTotal_1"
|
||||
:page-sizes="[10, 20, 30, 40]"
|
||||
v-model:page="innerQueryParams_1.pageNum"
|
||||
v-model:page-size="innerQueryParams_1.pageSize"
|
||||
@update:page="onHandlePage_1Change"
|
||||
@update:page-size="onHandlePageSize_1Change"
|
||||
/>
|
||||
</div>
|
||||
|
||||
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
|
||||
<n-pagination
|
||||
show-size-picker
|
||||
v-if="activeIndex === 1"
|
||||
:item-count="tableTotal_2"
|
||||
:page-sizes="[10, 20, 30, 40]"
|
||||
v-model:page="innerQueryParams_2.pageNum"
|
||||
v-model:page-size="innerQueryParams_2.pageSize"
|
||||
@update:page="onHandlePage_2Change"
|
||||
@update:page-size="onHandlePageSize_2Change"
|
||||
/>
|
||||
</div>
|
||||
</n-card>
|
||||
|
|
@ -187,7 +238,7 @@
|
|||
style="font-size: 20px; font-weight: 600; letter-spacing: 2px"
|
||||
gradient="linear-gradient(90deg, #CDF7FD 0%, #DAFAFE 20%, #CDF7FD 40%, #DAFAFE 60%, #CDF7FD 80%, #DAFAFE 100%)"
|
||||
>
|
||||
新增项目部人员
|
||||
{{ addOrEditPersonForm.id ? '编辑项目部人员' : '新增项目部人员' }}
|
||||
</n-gradient-text>
|
||||
|
||||
<img
|
||||
|
|
@ -214,6 +265,13 @@
|
|||
v-model:value="addOrEditPersonForm.userName"
|
||||
/>
|
||||
</n-form-item>
|
||||
<n-form-item label="身份证" path="idCard">
|
||||
<n-input
|
||||
clearable
|
||||
placeholder="身份证"
|
||||
v-model:value="addOrEditPersonForm.idCard"
|
||||
/>
|
||||
</n-form-item>
|
||||
|
||||
<n-form-item label="联系方式">
|
||||
<n-input
|
||||
|
|
@ -237,15 +295,19 @@
|
|||
<n-form-item label="性别">
|
||||
<n-radio-group v-model:value="addOrEditPersonForm.sex">
|
||||
<n-radio value="1">男</n-radio>
|
||||
<n-radio value="2">女</n-radio>
|
||||
<n-radio value="0">女</n-radio>
|
||||
</n-radio-group>
|
||||
</n-form-item>
|
||||
|
||||
<n-form-item label="人脸照片" path="facePhoto">
|
||||
<n-upload
|
||||
:max="1"
|
||||
:default-upload="false"
|
||||
list-type="image-card"
|
||||
accept=".jpg,.jpeg,.png"
|
||||
@preview="handlePreview"
|
||||
@before-upload="beforeUpload"
|
||||
:default-file-list="previewFileList"
|
||||
v-model:file-list="addOrEditPersonForm.facePhoto"
|
||||
>
|
||||
</n-upload>
|
||||
|
|
@ -258,24 +320,38 @@
|
|||
</n-card>
|
||||
</n-modal>
|
||||
|
||||
<n-modal preset="card" v-model:show="showModal" style="width: 600px" title="一张很酷的图片">
|
||||
<n-modal preset="card" v-model:show="showModal" style="width: 600px">
|
||||
<img :src="previewImageUrl" style="width: 100%" />
|
||||
</n-modal>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { NTag, NImage, useMessage } from 'naive-ui'
|
||||
import { NButton, NImage, useMessage, useDialog } from 'naive-ui'
|
||||
import TitleBackground from '@/components/TitleBackground/index.vue'
|
||||
import { ref, onMounted, onUpdated, nextTick, h } from 'vue'
|
||||
import { addPersonApi, getPersonListApi } from '@/api/home'
|
||||
import {
|
||||
addPersonApi,
|
||||
getUserInfoListApi,
|
||||
getUserListLimitApi,
|
||||
getUserListPageApi,
|
||||
getDetailsApi,
|
||||
updatePersonApi,
|
||||
deletePersonApi,
|
||||
} from '@/api/home'
|
||||
|
||||
const morePanelVisible = ref(false) // 更多数据弹框
|
||||
const addPersonPanelVisible = ref(false) // 新增项目部人员弹框
|
||||
const addPersonFormRef = ref(null) // 新增项目部人员表单
|
||||
const contentContainer = ref(null) // 人员动态内容区域
|
||||
const shouldScroll = ref(false) // 是否需要滚动
|
||||
const activeIndex = ref(0) // 当前选中的tab
|
||||
const activeIndex = ref(1) // 当前选中的tab
|
||||
const message = useMessage()
|
||||
const dialog = useDialog()
|
||||
const outerUserList = ref([]) // 外侧一级列表数据
|
||||
const imgPreviewUrl = ref('http://192.168.0.38:21999/robot') // 图片预览地址
|
||||
const ranger_1 = ref(null) // 人员动态时间选择器
|
||||
const ranger_2 = ref(null) // 人员信息时间选择器
|
||||
const previewFileList = ref([]) // 预览文件列表
|
||||
const addOrEditPersonForm = ref({
|
||||
userName: '', // 姓名
|
||||
mobile: '', // 联系方式
|
||||
|
|
@ -283,6 +359,8 @@ const addOrEditPersonForm = ref({
|
|||
age: '', // 年龄
|
||||
sex: '', // 性别
|
||||
workType: '', // 工种
|
||||
id: null, // 人员id
|
||||
idCard: '', // 身份证
|
||||
})
|
||||
|
||||
const tapsBtns = ref([
|
||||
|
|
@ -297,96 +375,25 @@ const tapsBtns = ref([
|
|||
// 新增项目部人员表单验证规则
|
||||
const addProjectPersonFormRules = ref({
|
||||
userName: [{ required: true, message: '请输入姓名' }],
|
||||
idCard: [
|
||||
{ required: true, message: '请输入姓名' },
|
||||
{
|
||||
pattern: /^[1-9]\d{5}(18|19|20)\d{2}(0[1-9]|1[0-2])(0[1-9]|[12]\d|3[0-1])\d{3}[0-9Xx]$/,
|
||||
message: '请输入正确的身份证号',
|
||||
},
|
||||
],
|
||||
mobile: [{ pattern: /^1[3-9]\d{9}$/, message: '请输入正确的手机号' }],
|
||||
facePhoto: [{ required: true, message: '请上传人脸照片' }],
|
||||
})
|
||||
|
||||
const previewFileList = ref([])
|
||||
// 获取人员动态列表 外侧一级列表
|
||||
const getUserListLimitFn = async () => {
|
||||
const { data: res } = await getUserListLimitApi({})
|
||||
|
||||
const page = ref(1)
|
||||
const pageSize = ref(10)
|
||||
|
||||
// 列表表头数据源
|
||||
const columns = ref([
|
||||
{
|
||||
title: '日期时间',
|
||||
key: 'age',
|
||||
align: 'center',
|
||||
},
|
||||
{
|
||||
title: '图片',
|
||||
key: 'tags',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
const tags = row.tags.map((tagKey) => {
|
||||
return h(
|
||||
NImage,
|
||||
{
|
||||
width: '60px',
|
||||
height: '60px',
|
||||
src: 'https://gw.alipayobjects.com/zos/antfincdn/aPkFc8Sj7n/method-draw-image.svg',
|
||||
fit: 'cover',
|
||||
},
|
||||
{
|
||||
default: () => tagKey,
|
||||
},
|
||||
)
|
||||
})
|
||||
return tags
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '姓名',
|
||||
key: 'age',
|
||||
align: 'center',
|
||||
},
|
||||
{
|
||||
title: '年龄',
|
||||
key: 'age',
|
||||
align: 'center',
|
||||
},
|
||||
{
|
||||
title: '工种',
|
||||
key: 'age',
|
||||
align: 'center',
|
||||
},
|
||||
])
|
||||
|
||||
// 列表数据源
|
||||
const data = ref([
|
||||
{
|
||||
age: '2025-06-01 10:00:00',
|
||||
tags: ['nice'],
|
||||
},
|
||||
{
|
||||
age: '2025-06-01 10:00:00',
|
||||
tags: ['nice'],
|
||||
},
|
||||
{
|
||||
age: '2025-06-01 10:00:00',
|
||||
tags: ['nice'],
|
||||
},
|
||||
{
|
||||
age: '2025-06-01 10:00:00',
|
||||
tags: ['nice'],
|
||||
},
|
||||
{
|
||||
age: '2025-06-01 10:00:00',
|
||||
tags: ['nice'],
|
||||
},
|
||||
{
|
||||
age: '2025-06-01 10:00:00',
|
||||
tags: ['nice'],
|
||||
},
|
||||
{
|
||||
age: '2025-06-01 10:00:00',
|
||||
tags: ['nice'],
|
||||
},
|
||||
{
|
||||
age: '2025-06-01 10:00:00',
|
||||
tags: ['nice'],
|
||||
},
|
||||
])
|
||||
if (res.code == 200) {
|
||||
outerUserList.value = res?.data
|
||||
}
|
||||
}
|
||||
|
||||
// 计算是否需要滚动
|
||||
const checkIfShouldScroll = () => {
|
||||
|
|
@ -406,18 +413,119 @@ const checkIfShouldScroll = () => {
|
|||
}
|
||||
}
|
||||
|
||||
// 在组件挂载和更新后检查滚动状态
|
||||
onMounted(() => {
|
||||
nextTick(checkIfShouldScroll)
|
||||
const tableData_1 = ref([])
|
||||
const tableTotal_1 = ref(0)
|
||||
const tableColumns_1 = ref([
|
||||
{
|
||||
title: '序号',
|
||||
key: 'index',
|
||||
align: 'center',
|
||||
width: 60,
|
||||
render(row, index) {
|
||||
return index + 1
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '日期时间',
|
||||
key: 'createTime',
|
||||
align: 'center',
|
||||
},
|
||||
{
|
||||
title: '动态图片',
|
||||
key: 'dataImage',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return h(NImage, {
|
||||
width: '60px',
|
||||
height: '60px',
|
||||
src: imgPreviewUrl.value + row.dataImage,
|
||||
fit: 'cover',
|
||||
})
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '人脸图片',
|
||||
key: 'image',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return h(NImage, {
|
||||
width: '60px',
|
||||
height: '60px',
|
||||
src: imgPreviewUrl.value + row.image,
|
||||
fit: 'cover',
|
||||
})
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '姓名',
|
||||
key: 'userName',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return row.userName || '-'
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '年龄',
|
||||
key: 'age',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return row.age || '-'
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '工种',
|
||||
key: 'workType',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return row.workType || '-'
|
||||
},
|
||||
},
|
||||
])
|
||||
|
||||
const innerQueryParams_1 = ref({
|
||||
pageNum: 1,
|
||||
pageSize: 10,
|
||||
startDay: '',
|
||||
endDay: '',
|
||||
userName: '',
|
||||
workType: '',
|
||||
})
|
||||
|
||||
onUpdated(() => {
|
||||
nextTick(checkIfShouldScroll)
|
||||
})
|
||||
// 获取人员动态列表数据
|
||||
const getUserListPageFn = async () => {
|
||||
const [startDay, endDay] = ranger_1?.value || []
|
||||
innerQueryParams_1.value.startDay = startDay || ''
|
||||
innerQueryParams_1.value.endDay = endDay || ''
|
||||
const { data: res } = await getUserListPageApi(innerQueryParams_1.value)
|
||||
if (res.code == 200) {
|
||||
tableData_1.value = res?.rows
|
||||
tableTotal_1.value = res?.total
|
||||
}
|
||||
}
|
||||
|
||||
// 更多按钮点击事件
|
||||
const onHandleMore = () => {
|
||||
morePanelVisible.value = true
|
||||
const onHandleReset_1 = () => {
|
||||
ranger_1.value = null
|
||||
innerQueryParams_1.value = {
|
||||
pageNum: 1,
|
||||
pageSize: 10,
|
||||
startDay: '',
|
||||
endDay: '',
|
||||
userName: '',
|
||||
workType: '',
|
||||
}
|
||||
getUserListPageFn()
|
||||
}
|
||||
|
||||
// 人员动态列表 分页
|
||||
const onHandlePage_1Change = (page) => {
|
||||
innerQueryParams_1.value.pageNum = page
|
||||
getUserListPageFn()
|
||||
}
|
||||
|
||||
// 人员动态列表 分页大小
|
||||
const onHandlePageSize_1Change = (pageSize) => {
|
||||
innerQueryParams_1.value.pageSize = pageSize
|
||||
getUserListPageFn()
|
||||
}
|
||||
|
||||
// 新增项目部人员
|
||||
|
|
@ -430,21 +538,42 @@ const onHandleAddPerson = () => {
|
|||
const onHandleSavePerson = () => {
|
||||
addPersonFormRef.value.validate().then(async (valid) => {
|
||||
if (valid) {
|
||||
// 组装参数 定义一个formData
|
||||
const formData = new FormData()
|
||||
|
||||
// 组装参数 定义一个formData
|
||||
for (const key in addOrEditPersonForm.value) {
|
||||
const value = addOrEditPersonForm.value[key]
|
||||
if (value === undefined || value === null) continue
|
||||
|
||||
if (key === 'facePhoto') {
|
||||
formData.append('file', addOrEditPersonForm.value.facePhoto[0].file)
|
||||
if (Array.isArray(value) && value.length > 0) {
|
||||
const photo = value[0]
|
||||
if (!photo.id || photo.id !== 996) {
|
||||
if (photo.file) {
|
||||
formData.append('file', photo.file)
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (key === 'id' && value) {
|
||||
formData.append('id', value)
|
||||
} else {
|
||||
formData.append(key, addOrEditPersonForm.value[key])
|
||||
formData.append(key, value)
|
||||
}
|
||||
}
|
||||
const { data: res } = await addPersonApi(formData)
|
||||
|
||||
const API = addOrEditPersonForm.value.id ? updatePersonApi : addPersonApi
|
||||
const { data: res } = await API(formData)
|
||||
if (res.code === 200) {
|
||||
message.success('人员新增成功')
|
||||
message.success(addOrEditPersonForm.value.id ? '人员编辑成功' : '人员新增成功')
|
||||
addOrEditPersonForm.value.id = null
|
||||
addOrEditPersonForm.value.facePhoto = []
|
||||
previewFileList.value = []
|
||||
addOrEditPersonForm.value.userName = ''
|
||||
addOrEditPersonForm.value.mobile = ''
|
||||
addOrEditPersonForm.value.idCard = ''
|
||||
addOrEditPersonForm.value.age = ''
|
||||
addOrEditPersonForm.value.sex = ''
|
||||
addOrEditPersonForm.value.workType = ''
|
||||
addPersonPanelVisible.value = false
|
||||
getProjectPersonList()
|
||||
} else {
|
||||
message.error(res.message)
|
||||
}
|
||||
|
|
@ -452,6 +581,207 @@ const onHandleSavePerson = () => {
|
|||
})
|
||||
}
|
||||
|
||||
const innerQueryParams_2 = ref({
|
||||
pageNum: 1,
|
||||
pageSize: 10,
|
||||
startDay: '',
|
||||
endDay: '',
|
||||
userName: '',
|
||||
workType: '',
|
||||
})
|
||||
|
||||
const btnList = ref([
|
||||
{
|
||||
label: '编辑',
|
||||
type: 'info',
|
||||
btnType: 1,
|
||||
},
|
||||
{
|
||||
label: '删除',
|
||||
type: 'info',
|
||||
btnType: 2,
|
||||
},
|
||||
])
|
||||
|
||||
const tableData_2 = ref([])
|
||||
const tableTotal_2 = ref(0)
|
||||
const tableColumns_2 = ref([
|
||||
{
|
||||
title: '序号',
|
||||
key: 'index',
|
||||
align: 'center',
|
||||
width: 60,
|
||||
render(row, index) {
|
||||
return index + 1
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '日期时间',
|
||||
key: 'createTime',
|
||||
align: 'center',
|
||||
},
|
||||
{
|
||||
title: '人脸照片',
|
||||
key: 'image',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return h(NImage, {
|
||||
width: '60px',
|
||||
height: '60px',
|
||||
src: imgPreviewUrl.value + row.image,
|
||||
fit: 'cover',
|
||||
})
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '姓名',
|
||||
key: 'userName',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return row.userName || '-'
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '性别',
|
||||
key: 'sex',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return row.sex == 1 ? '男' : '女' || '-'
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '年龄',
|
||||
key: 'age',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return row.age || '-'
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '工种',
|
||||
key: 'workType',
|
||||
align: 'center',
|
||||
render(row) {
|
||||
return row.workType || '-'
|
||||
},
|
||||
},
|
||||
{
|
||||
title: '操作',
|
||||
align: 'center',
|
||||
// 增加编辑和删除
|
||||
render(row) {
|
||||
const buttonS = btnList.value.map((btn) => {
|
||||
return h(
|
||||
NButton,
|
||||
{
|
||||
size: 'small',
|
||||
type: btn.type,
|
||||
style: {
|
||||
marginRight: '4px',
|
||||
},
|
||||
onClick: () => onHandleBtn(row, btn.btnType),
|
||||
},
|
||||
{ default: () => btn.label },
|
||||
)
|
||||
})
|
||||
return buttonS
|
||||
},
|
||||
},
|
||||
])
|
||||
|
||||
// 获取人员信息
|
||||
const getProjectPersonList = async () => {
|
||||
const [startDay, endDay] = ranger_2?.value || []
|
||||
innerQueryParams_2.value.startDay = startDay || ''
|
||||
innerQueryParams_2.value.endDay = endDay || ''
|
||||
const { data: res } = await getUserInfoListApi(innerQueryParams_2.value)
|
||||
|
||||
if (res.code == 200) {
|
||||
tableData_2.value = res?.rows
|
||||
tableTotal_2.value = res?.total
|
||||
}
|
||||
}
|
||||
|
||||
// 获取人员详情
|
||||
const getPersonDetails = async (id) => {
|
||||
const { data: res } = await getDetailsApi({ id })
|
||||
if (res.code == 200) {
|
||||
console.log(res.data)
|
||||
}
|
||||
}
|
||||
|
||||
// 操作按钮
|
||||
const onHandleBtn = (row, btnType) => {
|
||||
console.log(row, btnType)
|
||||
|
||||
if (btnType == 1) {
|
||||
const { id, age, sex, workType, userName, mobile, image, idCard } = row
|
||||
addOrEditPersonForm.value.age = age
|
||||
addOrEditPersonForm.value.sex = sex
|
||||
addOrEditPersonForm.value.workType = workType
|
||||
addOrEditPersonForm.value.userName = userName
|
||||
addOrEditPersonForm.value.mobile = mobile
|
||||
addOrEditPersonForm.value.idCard = idCard
|
||||
addOrEditPersonForm.value.id = id
|
||||
addOrEditPersonForm.value.facePhoto = [
|
||||
{ url: imgPreviewUrl.value + image, id: 996, name: '我很帅.png', status: 'finished' },
|
||||
]
|
||||
previewFileList.value = [
|
||||
{
|
||||
id: 996,
|
||||
name: '我很帅.png',
|
||||
status: 'finished',
|
||||
url: imgPreviewUrl.value + image,
|
||||
},
|
||||
]
|
||||
addPersonPanelVisible.value = true
|
||||
} else if (btnType == 2) {
|
||||
dialog.success({
|
||||
title: '温馨提示',
|
||||
content: '确定要删除该人员吗?',
|
||||
positiveText: '确定',
|
||||
negativeText: '取消',
|
||||
draggable: true,
|
||||
onPositiveClick: async () => {
|
||||
const { data: res } = await deletePersonApi({
|
||||
id: row.id,
|
||||
})
|
||||
|
||||
if (res.code == 200) {
|
||||
message.success('删除成功')
|
||||
getProjectPersonList()
|
||||
}
|
||||
},
|
||||
onNegativeClick: () => {},
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
const onHandleReset_2 = () => {
|
||||
ranger_2.value = null
|
||||
innerQueryParams_2.value = {
|
||||
pageNum: 1,
|
||||
pageSize: 10,
|
||||
startDay: '',
|
||||
endDay: '',
|
||||
userName: '',
|
||||
workType: '',
|
||||
}
|
||||
getProjectPersonList()
|
||||
}
|
||||
|
||||
// 人员信息列表 分页
|
||||
const onHandlePage_2Change = (page) => {
|
||||
innerQueryParams_2.value.pageNum = page
|
||||
getProjectPersonList()
|
||||
}
|
||||
|
||||
// 人员信息列表 分页大小
|
||||
const onHandlePageSize_2Change = (pageSize) => {
|
||||
innerQueryParams_2.value.pageSize = pageSize
|
||||
getProjectPersonList()
|
||||
}
|
||||
|
||||
// 人脸照片预览
|
||||
const showModal = ref(false)
|
||||
const previewImageUrl = ref('')
|
||||
|
|
@ -460,9 +790,43 @@ const handlePreview = (file) => {
|
|||
showModal.value = true
|
||||
}
|
||||
|
||||
const beforeUpload = (file) => {
|
||||
const allowedTypes = ['image/jpeg', 'image/png']
|
||||
if (!allowedTypes.includes(file.file.type)) {
|
||||
message.error('仅支持 JPG/PNG/JPEG格式的图片')
|
||||
return false
|
||||
}
|
||||
|
||||
// 可选:限制文件大小(例如 5MB)
|
||||
const maxSize = 5 * 1024 * 1024
|
||||
if (file.file.size > maxSize) {
|
||||
message.error('图片大小不能超过5MB')
|
||||
return false
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
const onHandleTabs = (index) => {
|
||||
activeIndex.value = index
|
||||
}
|
||||
|
||||
// 更多按钮点击事件
|
||||
const onHandleMore = () => {
|
||||
getUserListPageFn()
|
||||
getProjectPersonList()
|
||||
morePanelVisible.value = true
|
||||
}
|
||||
|
||||
// 在组件挂载和更新后检查滚动状态
|
||||
onMounted(() => {
|
||||
nextTick(checkIfShouldScroll)
|
||||
getUserListLimitFn()
|
||||
})
|
||||
|
||||
onUpdated(() => {
|
||||
nextTick(checkIfShouldScroll)
|
||||
})
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
|
|
|
|||
|
|
@ -8,15 +8,22 @@
|
|||
|
||||
<!-- 内容区域 -->
|
||||
<div class="content-container">
|
||||
<div class="content-item" v-for="item in 4" :key="item" :class="`item-${item}`">
|
||||
<div
|
||||
class="content-item"
|
||||
:key="item.title"
|
||||
v-for="(item, index) in compareList"
|
||||
:class="`item-${index + 1}`"
|
||||
>
|
||||
<div>
|
||||
<span style="padding-left: 10px; font-size: 16px"> 巡检次数 </span>
|
||||
<span style="padding-left: 10px; font-size: 16px"> {{ item.title }} </span>
|
||||
<span style="padding-left: 10px; font-size: 14px"> 总数: </span>
|
||||
<span> 100 </span>
|
||||
<span> {{ item.total }} </span>
|
||||
</div>
|
||||
<div>
|
||||
<span style="padding-left: 10px; font-size: 18px; font-weight: bold"> 26 </span>
|
||||
<span style="font-size: 14px"> 次 </span>
|
||||
<span style="padding-left: 10px; font-size: 18px; font-weight: bold">
|
||||
{{ item.amount }}
|
||||
</span>
|
||||
<span style="font-size: 14px; margin-left: 4px"> {{ item.unit }} </span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
@ -68,6 +75,7 @@
|
|||
<script setup>
|
||||
import { NTag } from 'naive-ui'
|
||||
import { ref, onMounted, onUpdated, nextTick, h } from 'vue'
|
||||
import { getTaskStatisticsApi } from '@/api/home'
|
||||
import TapsOne from './taps-one.vue'
|
||||
import TapsTwo from './taps-two.vue'
|
||||
import TapsThree from './taps-three.vue'
|
||||
|
|
@ -79,6 +87,13 @@ const page = ref(1)
|
|||
const pageSize = ref(10)
|
||||
const activeIndex = ref(0)
|
||||
const currentComponent = ref('comp-a')
|
||||
|
||||
const compareList = ref([
|
||||
{ title: '巡检次数', total: 58, amount: 26, unit: '次' },
|
||||
{ title: '巡检照片', total: 100, amount: 100, unit: '张' },
|
||||
{ title: '比对次数', total: 100, amount: 100, unit: '次' },
|
||||
{ title: '异常数量', total: 100, amount: 100, unit: '项' },
|
||||
])
|
||||
const componentMap = {
|
||||
'comp-a': TapsOne,
|
||||
'comp-b': TapsTwo,
|
||||
|
|
@ -152,6 +167,26 @@ const data = ref([
|
|||
},
|
||||
])
|
||||
|
||||
// 获取智能对比数据
|
||||
const getTaskStatisticsData = async () => {
|
||||
const { data: res } = await getTaskStatisticsApi()
|
||||
console.log(res, 'res智能对比数据')
|
||||
const { allErr, allImage, allSimilarity, allTask, dayErr, dayImage, daySimilarity, todayTask } =
|
||||
res?.data
|
||||
|
||||
compareList.value[0].total = allTask
|
||||
compareList.value[1].total = allImage
|
||||
compareList.value[2].total = allSimilarity
|
||||
compareList.value[3].total = allErr
|
||||
|
||||
compareList.value[0].amount = todayTask
|
||||
compareList.value[1].amount = dayImage
|
||||
compareList.value[2].amount = daySimilarity
|
||||
compareList.value[3].amount = dayErr
|
||||
}
|
||||
|
||||
getTaskStatisticsData()
|
||||
|
||||
const onHandleMore = () => {
|
||||
console.log('更多')
|
||||
morePanelVisible.value = true
|
||||
|
|
|
|||
|
|
@ -20,18 +20,18 @@
|
|||
|
||||
<!-- 内容区域 -->
|
||||
<n-data-table
|
||||
:columns="columns"
|
||||
:data="data"
|
||||
flex-height
|
||||
:columns="columns"
|
||||
:scroll-x="10"
|
||||
:style="{ height: `75%` }"
|
||||
flex-height
|
||||
/>
|
||||
<div style="margin-top: 10px; display: flex; justify-content: flex-end">
|
||||
<n-pagination
|
||||
v-model:page="page"
|
||||
v-model:page-size="pageSize"
|
||||
:page-count="100"
|
||||
show-size-picker
|
||||
v-model:page="page"
|
||||
v-model:page-size="pageSize"
|
||||
:page-sizes="[10, 20, 30, 40]"
|
||||
/>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -65,8 +65,8 @@ export default defineConfig(({ mode }) => {
|
|||
open: true,
|
||||
proxy: {
|
||||
'/robot-screen-api': {
|
||||
// target: 'http://192.168.0.38:21999', // 郝志权测试环境
|
||||
target: 'http://192.168.0.14:58080', // 测试环境
|
||||
target: 'http://192.168.0.38:21999', // 郝志权测试环境
|
||||
// target: 'http://192.168.0.14:58080', // 测试环境
|
||||
changeOrigin: true,
|
||||
rewrite: (p) => p.replace(/^\/robot-screen-api/, ''),
|
||||
},
|
||||
|
|
|
|||
Loading…
Reference in New Issue