Compare commits

..

2 Commits

7 changed files with 276 additions and 182 deletions

View File

@ -30,6 +30,11 @@ export const updateTask = (data) => {
return request.put({ url: '/system/robot/task/close', data })
}
//更新优先级
export const updateRobotTask = (data) => {
return request.put({ url: '/system/robot/task/update', data })
}
//获得机器人任务主表分页
export const getTaskPageList = async (data) => {
return await request.post({ url: `/system/robot/task/page`, data })

View File

@ -44,7 +44,7 @@ import VueDOMPurifyHTML from 'vue-dompurify-html' // 解决v-html 的安全隐
import VueDragResizeRotate from '@gausszhou/vue3-drag-resize-rotate'
import '@gausszhou/vue3-drag-resize-rotate/lib/bundle.esm.css'
import * as ElementPlusIconsVue from '@element-plus/icons-vue'
import { vDrag } from './utils/drag';
import { vDrag } from './utils/drag'
// 创建实例
const setupAll = async () => {
const app = createApp(App)
@ -69,11 +69,10 @@ const setupAll = async () => {
await router.isReady()
// 注册全局指令
app.directive('drag', vDrag);
app.directive('drag', vDrag)
app.use(VueDOMPurifyHTML)
app.use(VueDragResizeRotate)
app.mount('#app')
}
setupAll()

View File

@ -333,7 +333,6 @@
>
<!-- 1 路径点 -->
<el-tooltip
class="box-item"
effect="dark"
:content="item.sortNum || '节点未保存'"
placement="top"
@ -461,18 +460,26 @@
:x2="Number(curve.endPointX)"
:y2="Number(curve.endPointY)"
:stroke="curve.isSelected ? '#f48924' : '#00329F'"
:marker-start="curve.direction === 2 ? 'url(#double-arrow-start)' : ''"
marker-end="url(#single-arrow)"
stroke-width="4"
stroke-width="3"
@click="handleChooseRoute(curve, index)"
@dblclick="handleEditRoute(curve, index)"
/>
<text
:x="(Number(curve.startPointX) + Number(curve.endPointX)) / 2"
:y="(Number(curve.startPointY) + Number(curve.endPointY) - 18) / 2"
font-size="11"
text-anchor="middle"
fill="black"
v-if="curve.isSelected"
>
{{ calculateRouteLength(curve) }}
</text>
<path
v-if="curve.isSelected"
:d="getLineMidArrowPath(curve)"
stroke="none"
fill="black"
stroke-width="4"
stroke-width="3"
:marker-start="curve.direction === 2 ? 'url(#backward-arrow)' : ''"
:marker-end="
curve.direction === 2 ? 'url(#forward-arrow)' : 'url(#forward-arrow)'
@ -482,21 +489,31 @@
<template v-else>
<path
id="curvePath"
:d="getCurvePath(curve)"
:stroke="curve.isSelected ? '#f48924' : '#00329F'"
stroke-width="4"
stroke-width="3"
fill="none"
:marker-start="curve.direction === 2 ? 'url(#double-arrow-start)' : ''"
marker-end="url(#single-arrow)"
@click="handleChooseRoute(curve, index)"
@dblclick="handleEditRoute(curve, index)"
/>
<!-- <text
:x="computedCurveTextX(curve)"
:y="computedCurveTextY(curve)"
font-size="12"
text-anchor="middle"
fill="black"
v-if="curve.isSelected"
>
{{ calculateRouteLength(curve) }}
</text> -->
<path
v-if="curve.isSelected"
:d="getBezierMidArrowPath(curve)"
stroke="none"
fill="black"
stroke-width="4"
stroke-width="3"
:marker-start="curve.direction === 2 ? 'url(#backward-arrow)' : ''"
:marker-end="
curve.direction === 2 ? 'url(#forward-arrow)' : 'url(#forward-arrow)'
@ -911,6 +928,7 @@ const mapClick = (e) => {
rotatable: false,
lockAspectRatio: false, //
mapImageUrl: '',
locationYaw: 0, //
type: 1, //1
dataList: [], //
dataObj: {} //
@ -1524,6 +1542,7 @@ const replicationNode = () => {
lockAspectRatio: copyMapItem.lockAspectRatio,
layerSelectionShow: copyMapItem.layerSelectionShow,
mapImageUrl: copyMapItem.mapImageUrl,
locationYaw: copyMapItem.locationYaw,
areaId: null,
locationNumber: copyMapItem.locationNumber || null
}
@ -1644,7 +1663,8 @@ const markFormSubmit = async () => {
mapImageUrl: '',
type: 1, //1
dataList: [], //
dataObj: {} //
dataObj: {}, //
locationYaw: 0 //
})
addEditHistory()
}
@ -1999,7 +2019,6 @@ const clickDrawSelectionArea = () => {
item.actualLocationY = actualPoint.actualLocationY
}
})
console.log(state.allMapPointInfo)
state.mapRouteList.forEach((item) => {
if (idNameMap[item.startingPointId]) {
let actualPoint = disposeEventPoint(
@ -2027,41 +2046,54 @@ const clickDrawSelectionArea = () => {
}
// 线
const mapPointsToLine = (points) => {
if (points.length < 2) {
return points
// locationX
// let minXPoint = points[0]
// let maxXPoint = points[0]
// points.forEach((point) => {
// if (point.locationX < minXPoint.locationX) {
// minXPoint = point
// }
// if (point.locationX > maxXPoint.locationX) {
// maxXPoint = point
// }
// })
// sortNum
let minXPoint = points[0]
let maxXPoint = points[0]
for (let i = 1; i < points.length; i++) {
if (points[i].sortNum < minXPoint.sortNum) {
minXPoint = points[i]
}
if (points[i].sortNum > maxXPoint.sortNum) {
maxXPoint = points[i]
}
}
//
const firstPoint = points[0]
const lastPoint = points[points.length - 1]
// 线
const dx = lastPoint.locationX - firstPoint.locationX
const dy = lastPoint.locationY - firstPoint.locationY
const dx = maxXPoint.locationX - minXPoint.locationX
const dy = maxXPoint.locationY - minXPoint.locationY
// 线
if (dx === 0) {
// 线
return points.map((point, index) => {
if (index === 0 || index === points.length - 1) {
return points.map((point) => {
if (point === minXPoint || point === maxXPoint) {
return point
}
return {
...point,
locationX: firstPoint.locationX,
locationY: point.locationY
locationX: minXPoint.locationX
}
})
}
const slope = dy / dx
// 线
const intercept = firstPoint.locationY - slope * firstPoint.locationX
// 线
return points.map((point, index) => {
if (index === 0 || index === points.length - 1) {
const slope = dy / dx
const intercept = minXPoint.locationY - slope * minXPoint.locationX
return points.map((point) => {
if (point === minXPoint || point === maxXPoint) {
return point
}
const newY = slope * point.locationX + intercept
//
return {
...point,
locationY: newY
@ -2248,6 +2280,14 @@ const computedLineWidth = computed(() => {
return 0
})
//线
const calculateRouteLength = (item) => {
const dx = item.startPointX - item.endPointX
const dy = item.startPointY - item.endPointY
const length = Math.sqrt(dx * dx + dy * dy) * Number(imgBgObj.resolution)
return length.toFixed(2)
}
//
const measureDistancesClick = (event) => {
//
@ -2271,7 +2311,7 @@ const measureDistancesClick = (event) => {
state.measureDistancesPoints[0],
state.measureDistancesPoints[1]
)
state.measureDistancesNum = distancesNum * 0.05
state.measureDistancesNum = distancesNum * Number(imgBgObj.resolution)
}
}
}
@ -2552,6 +2592,28 @@ const getBezierMidArrowPath = (item) => {
return `M ${prevPoint.x} ${prevPoint.y} L ${midPoint.x} ${midPoint.y}`
}
// 线 x
const computedCurveTextX = (item) => {
return (
(Number(item.startPointX) +
Number(item.beginControlX) +
Number(item.endControlX) +
Number(item.endPointX)) /
4
)
}
// 线 y
const computedCurveTextY = (item) => {
return (
(Number(item.startPointY) +
Number(item.beginControlY) +
Number(item.endControlY) +
Number(item.endPointY)) /
4
)
}
document.onmousedown = function (e) {
//
if (e.button == 2) {

View File

@ -95,7 +95,7 @@
</el-col>
<el-col :span="12">
<el-form-item label="方向" prop="direction" required>
<el-select v-model="form.direction" placeholder="请选择方向">
<el-select v-model="form.direction" placeholder="请选择方向" @change="directionChange">
<el-option label="单向" :value="1" />
<el-option label="双向" :value="2" />
</el-select>
@ -174,10 +174,12 @@
<el-col :span="12">
<el-form-item label="车头朝向" prop="toward" required>
<el-select v-model="form.toward" placeholder="请选择车头朝向">
<el-option label="正正" :value="0" />
<el-option label="正反" :value="1" />
<el-option label="反正" :value="2" />
<el-option label="反反" :value="3" />
<el-option
v-for="(item, index) in towardList"
:key="index"
:label="item.label"
:value="item.value"
/>
</el-select> </el-form-item
></el-col>
</el-row>
@ -233,6 +235,13 @@ const form = ref({
const open = (item) => {
dialogFormVisible.value = true
form.value = item
if (form.value.direction == 1) {
//
towardList.value = unidirectional
} else {
//
towardList.value = bidirectional
}
}
const dialogClose = () => {
@ -292,6 +301,47 @@ const methodChange = (e) => {
}
}
//
const towardList = ref([])
const unidirectional = [
{
value: 0,
label: '正'
},
{
value: 1,
label: '反'
}
] //
const bidirectional = [
{
value: 0,
label: '正正'
},
{
value: 1,
label: '正反'
},
{
value: 2,
label: '反正'
},
{
value: 3,
label: '反反'
}
] //
const directionChange = (e) => {
form.value.toward = 0
if (e == 1) {
//
towardList.value = unidirectional
} else {
//
towardList.value = bidirectional
}
}
//x y
const disposeEventPoint = (x, y) => {
const actualLocationX =

View File

@ -324,6 +324,7 @@
:resizable="!state.prohibitedOperation && item.resizable"
:rotatable="!state.prohibitedOperation && item.rotatable"
:lock-aspect-ratio="item.lockAspectRatio"
:scaleRatio="state.imageChangeMultiple"
style="border: none; z-index: 999"
>
<!-- 节点合集 -->
@ -421,7 +422,7 @@
:x2="Number(state.currentDrawX)"
:y2="Number(state.currentDrawY)"
stroke="#00329F"
stroke-width="4"
stroke-width="3"
/>
<template v-if="state.mapRouteList.length > 0">
<template v-for="(curve, index) in state.mapRouteList" :key="index">
@ -460,18 +461,26 @@
:x2="Number(curve.endPointX)"
:y2="Number(curve.endPointY)"
:stroke="curve.isSelected ? '#f48924' : '#00329F'"
:marker-start="curve.direction === 2 ? 'url(#double-arrow-start)' : ''"
marker-end="url(#single-arrow)"
stroke-width="4"
stroke-width="3"
@click="handleChooseRoute(curve, index)"
@dblclick="handleEditRoute(curve, index)"
/>
<text
:x="(Number(curve.startPointX) + Number(curve.endPointX)) / 2"
:y="(Number(curve.startPointY) + Number(curve.endPointY) - 18) / 2"
font-size="12"
text-anchor="middle"
fill="black"
v-if="curve.isSelected"
>
{{ calculateRouteLength(curve) }}
</text>
<path
v-if="curve.isSelected"
:d="getLineMidArrowPath(curve)"
stroke="none"
fill="black"
stroke-width="4"
stroke-width="3"
:marker-start="curve.direction === 2 ? 'url(#backward-arrow)' : ''"
:marker-end="
curve.direction === 2 ? 'url(#forward-arrow)' : 'url(#forward-arrow)'
@ -481,21 +490,31 @@
<template v-else>
<path
id="curvePath"
:d="getCurvePath(curve)"
:stroke="curve.isSelected ? '#f48924' : '#00329F'"
stroke-width="4"
stroke-width="3"
fill="none"
:marker-start="curve.direction === 2 ? 'url(#double-arrow-start)' : ''"
marker-end="url(#single-arrow)"
@click="handleChooseRoute(curve, index)"
@dblclick="handleEditRoute(curve, index)"
/>
<!-- <text
:x="computedCurveTextX(curve)"
:y="computedCurveTextY(curve)"
font-size="12"
text-anchor="middle"
fill="black"
v-if="curve.isSelected"
>
{{ calculateRouteLength(curve) }}
</text> -->
<path
v-if="curve.isSelected"
:d="getBezierMidArrowPath(curve)"
stroke="none"
fill="black"
stroke-width="4"
stroke-width="3"
:marker-start="curve.direction === 2 ? 'url(#backward-arrow)' : ''"
:marker-end="
curve.direction === 2 ? 'url(#forward-arrow)' : 'url(#forward-arrow)'
@ -2262,6 +2281,14 @@ const computedLineWidth = computed(() => {
return 0
})
//线
const calculateRouteLength = (item) => {
const dx = item.startPointX - item.endPointX
const dy = item.startPointY - item.endPointY
const length = Math.sqrt(dx * dx + dy * dy) * Number(imgBgObj.resolution)
return length.toFixed(2)
}
//
const measureDistancesClick = (event) => {
//
@ -2285,7 +2312,7 @@ const measureDistancesClick = (event) => {
state.measureDistancesPoints[0],
state.measureDistancesPoints[1]
)
state.measureDistancesNum = distancesNum * 0.05
state.measureDistancesNum = distancesNum * Number(imgBgObj.resolution)
}
}
}
@ -2566,6 +2593,28 @@ const getBezierMidArrowPath = (item) => {
return `M ${prevPoint.x} ${prevPoint.y} L ${midPoint.x} ${midPoint.y}`
}
// 线 x
const computedCurveTextX = (item) => {
return (
(Number(item.startPointX) +
Number(item.beginControlX) +
Number(item.endControlX) +
Number(item.endPointX)) /
4
)
}
// 线 y
const computedCurveTextY = (item) => {
return (
(Number(item.startPointY) +
Number(item.beginControlY) +
Number(item.endControlY) +
Number(item.endPointY)) /
4
)
}
document.onmousedown = function (e) {
//
if (e.button == 2) {

View File

@ -1,130 +1,60 @@
<template>
<div
@mousedown="startSelection"
@mousemove="updateSelection"
@mouseup="endSelection"
style="position: relative; width: 100vw; height: 100vh"
>
<!-- 绘制所有框选区域 -->
<div>
<button @click="scale *= 1.1">放大</button>
<button @click="scale /= 1.1">缩小</button>
<div
v-for="(rect, index) in selectionRects"
:key="index"
:style="{
position: 'absolute',
left: `${rect.left}px`,
top: `${rect.top}px`,
width: `${rect.width}px`,
height: `${rect.height}px`,
backgroundColor: 'rgba(0, 0, 255, 0.2)',
border: '1px solid blue'
}"
></div>
<!-- 绘制点位 -->
<div
v-for="(point, index) in points"
:key="index"
:style="{
position: 'absolute',
left: `${point.x}px`,
top: `${point.y}px`,
width: '10px',
height: '10px',
backgroundColor: selectedPoints.includes(point) ? 'red' : 'green',
borderRadius: '50%'
}"
></div>
<!-- 确认按钮 -->
<button @click="confirmSelection" style="position: fixed; bottom: 20px; right: 20px">
确认
</button>
ref="containerRef"
:style="{ transform: `scale(${scale})` }"
@mousemove="handleMouseMove"
class="scalable-container"
>
<div :style="{ left: `${mouseX}px`, top: `${mouseY}px` }" class="cursor"></div>
</div>
</div>
</template>
<script>
import { ref } from 'vue'
<script setup>
import { ref, onMounted } from 'vue'
export default {
setup() {
const points = ref([
{ x: 10, y: 10 },
{ x: 30, y: 100 },
{ x: 40, y: 40 },
{ x: 230, y: 400 },
{ x: 750, y: 640 }
])
const containerRef = ref(null)
const scale = ref(1)
const mouseX = ref(0)
const mouseY = ref(0)
const isSelecting = ref(false)
const startPos = ref({ x: 0, y: 0 })
const currentRect = ref({ left: 0, top: 0, width: 0, height: 0 })
const selectionRects = ref([]) //
const selectedPoints = ref([]) //
const selectedPointsInOrder = ref([]) //
const handleMouseMove = (event) => {
const rect = containerRef.value.getBoundingClientRect()
const offsetX = event.clientX - rect.left
const offsetY = event.clientY - rect.top
//
const startSelection = (event) => {
isSelecting.value = true
startPos.value = { x: event.clientX, y: event.clientY }
currentRect.value = { left: event.clientX, top: event.clientY, width: 0, height: 0 }
}
//
const updateSelection = (event) => {
if (isSelecting.value) {
currentRect.value = {
left: Math.min(startPos.value.x, event.clientX),
top: Math.min(startPos.value.y, event.clientY),
width: Math.abs(event.clientX - startPos.value.x),
height: Math.abs(event.clientY - startPos.value.y)
}
}
}
//
const endSelection = () => {
if (isSelecting.value) {
isSelecting.value = false
selectionRects.value.push({ ...currentRect.value }) //
checkPointsInSelection(currentRect.value) //
}
}
//
const checkPointsInSelection = (rect) => {
points.value.forEach((point) => {
if (
point.x >= rect.left &&
point.x <= rect.left + rect.width &&
point.y >= rect.top &&
point.y <= rect.top + rect.height &&
!selectedPoints.value.includes(point) //
) {
selectedPoints.value.push(point)
selectedPointsInOrder.value.push(point) //
}
})
}
//
const confirmSelection = () => {
console.log('Selected Points in Order:', selectedPointsInOrder.value)
//
selectionRects.value = []
selectedPoints.value = []
selectedPointsInOrder.value = []
}
return {
points,
isSelecting,
selectionRects,
selectedPoints,
startSelection,
updateSelection,
endSelection,
confirmSelection
}
}
//
mouseX.value = offsetX / scale.value
mouseY.value = offsetY / scale.value
}
onMounted(() => {
//
const rect = containerRef.value.getBoundingClientRect()
mouseX.value = rect.width / 2
mouseY.value = rect.height / 2
})
</script>
<style scoped>
.scalable-container {
position: relative;
width: 200px;
height: 200px;
border: 1px solid #ccc;
margin-top: 20px;
transform-origin: top left;
transition: transform 0.3s;
}
.cursor {
position: absolute;
width: 10px;
height: 10px;
background-color: red;
border-radius: 50%;
}
</style>

View File

@ -216,7 +216,7 @@ const message = useMessage() // 消息弹窗
const { t } = useI18n() //
const { push } = useRouter()
const route = useRoute();
const route = useRoute()
const loading = ref(true) //
const total = ref(0) //
const list = ref([]) //
@ -309,7 +309,7 @@ const modifyPriority = (mainItem, item) => {
}
const priorityNumChange = async (mainItem, item) => {
try {
await MapTaskAPi.updateTask({
await MapTaskAPi.updateRobotTask({
id: mainItem.id,
priority: priorityNum.value,
montageTask: mainItem.montageTask,
@ -338,20 +338,19 @@ const getCanUseRobotList = async () => {
robotList.value = await MapTaskAPi.getCanUseRobot()
}
//
const findPropertyValue = (arr, targetValue, compareProp, returnProp) =>{
for (let i = 0; i < arr.length; i++) {
if (arr[i][compareProp] === targetValue) {
return arr[i][returnProp];
}
const findPropertyValue = (arr, targetValue, compareProp, returnProp) => {
for (let i = 0; i < arr.length; i++) {
if (arr[i][compareProp] === targetValue) {
return arr[i][returnProp]
}
return undefined;
}
return undefined
}
/** 初始化 **/
onMounted(() => {
if(route.query.type){
let data = getIntDictOptions(DICT_TYPE.ROBOT_TASK_STATUS)
queryParams.taskStatus = findPropertyValue(data, route.query.type, 'label', 'value')
if (route.query.type) {
let data = getIntDictOptions(DICT_TYPE.ROBOT_TASK_STATUS)
queryParams.taskStatus = findPropertyValue(data, route.query.type, 'label', 'value')
}
getList()
getCanUseRobotList()