feat: 处理冲突

This commit is contained in:
zhanghao 2026-08-04 11:48:47 +08:00
commit b1e35350a2
3 changed files with 104 additions and 3 deletions

View File

@ -78,6 +78,14 @@ export function getAgvStatus(params) {
}) })
} }
export function getAgvStations(params) {
return request({
url: '/api/agv/listStations',
method: 'get',
params: params
})
}
export function getArmJointState(params) { export function getArmJointState(params) {
return request({ return request({
url: '/api/arm/getJointState', url: '/api/arm/getJointState',

View File

@ -328,6 +328,19 @@ function handler(params) {
], ],
outputType: 'json' outputType: 'json'
}, },
{
icon: videoSvg,
name: "AGV站点导航",
type: "serviceNode",
desc: "从AGV站点列表选择目标站点并导航",
action: 'AGV_MOVE_TO_STATION',
nodeType: 'EDGE',
nodeParams: [
{ name: "deviceId", type: "input", input: "", disabled: true },
{ name: "stationId", type: "input", input: "", componentType: 'select', selectOptions: [], forceSelect: true, disabled: true }
],
outputType: 'json'
},
{ {
icon: cameraSvg, icon: cameraSvg,
name: "通用指令", name: "通用指令",

View File

@ -161,6 +161,16 @@
<h4 :id="titleId" :class="titleClass">执行{{ nodeName }}节点</h4> <h4 :id="titleId" :class="titleClass">执行{{ nodeName }}节点</h4>
</div> </div>
</template> </template>
<div v-if="nodeAction === 'AGV_MOVE_TO_STATION'" class="single-node-station-tools">
<el-button
type="primary"
plain
:loading="stationLoading"
:disabled="!singleNodeTerminalId || !singleNodeDeviceId"
@click="loadSingleNodeStations"
>加载站点列表</el-button>
<span>{{ singleNodeTerminalId && singleNodeDeviceId ? '加载后从站点下拉框选择' : '请先填写终端ID和设备ID' }}</span>
</div>
<el-form <el-form
:inline="true" :inline="true"
:model="formData" :model="formData"
@ -256,6 +266,7 @@ import {
flowResume, flowResume,
flowStop, flowStop,
flowAction, flowAction,
getAgvStations,
} from "@/api/device/flow"; } from "@/api/device/flow";
import { getDetect } from "@/api/test/detect"; import { getDetect } from "@/api/test/detect";
import { import {
@ -878,13 +889,52 @@ const formData = reactive({
const rules = reactive({}); const rules = reactive({});
const executeForm = ref(); const executeForm = ref();
const nodeAction = ref(""); const nodeAction = ref("");
const stationLoading = ref(false);
const singleNodeTerminalId = computed(() =>
formData.nodeParams.find((item) => item.name === "terminalId")?.input
);
const singleNodeDeviceId = computed(() =>
formData.nodeParams.find((item) => item.name === "deviceId")?.input
);
const stationOptions = (stations) => (Array.isArray(stations) ? stations : [])
.filter((station) => station?.id !== undefined && station?.id !== null && String(station.id).trim())
.map((station) => {
const id = String(station.id).trim();
const description = station.description ? String(station.description).trim() : "";
return { value: id, label: description ? `${id} - ${description}` : id };
});
const loadSingleNodeStations = async () => {
stationLoading.value = true;
try {
const response = await getAgvStations({
terminalId: singleNodeTerminalId.value,
deviceId: singleNodeDeviceId.value,
});
const options = stationOptions(response?.data);
const stationParam = formData.nodeParams.find((item) => item.name === "stationId");
if (!stationParam) return;
stationParam.selectOptions = options;
stationParam.stationTerminalId = singleNodeTerminalId.value;
stationParam.stationDeviceId = singleNodeDeviceId.value;
if (!options.some((item) => item.value === stationParam.input)) stationParam.input = "";
if (options.length === 0) ElMessage.warning("当前AGV没有可用站点");
} catch (error) {
console.error("加载AGV站点列表失败:", error);
ElMessage.error("加载AGV站点列表失败");
} finally {
stationLoading.value = false;
}
};
const singleNodeExecution = (e) => { const singleNodeExecution = (e) => {
const { name, nodeType, nodeParams, action } = e.detail; const { name, nodeType, nodeParams, action } = e.detail;
console.log('nodeParams', nodeParams) const executionParams = JSON.parse(JSON.stringify(nodeParams || []));
nodeName.value = name; nodeName.value = name;
visible.value = true; visible.value = true;
nodeAction.value = action; nodeAction.value = action;
stationLoading.value = false;
if (nodeType === "EDGE") { if (nodeType === "EDGE") {
formData.nodeParams = [ formData.nodeParams = [
{ {
@ -893,14 +943,31 @@ const singleNodeExecution = (e) => {
name: "terminalId", name: "terminalId",
type: "input", type: "input",
}, },
...nodeParams, ...executionParams,
]; ];
} else { } else {
formData.nodeParams = nodeParams; formData.nodeParams = executionParams;
}
if (action === "AGV_MOVE_TO_STATION") {
const stationParam = formData.nodeParams.find((item) => item.name === "stationId");
if (stationParam) {
stationParam.input = "";
stationParam.selectOptions = [];
}
} }
}; };
const execute = async () => { const execute = async () => {
if (nodeAction.value === "AGV_MOVE_TO_STATION") {
const stationParam = formData.nodeParams.find((item) => item.name === "stationId");
const validStation = stationParam?.selectOptions?.some((item) => item.value === stationParam.input);
const correctSource = stationParam?.stationTerminalId === singleNodeTerminalId.value
&& stationParam?.stationDeviceId === singleNodeDeviceId.value;
if (!validStation || !correctSource) {
ElMessage.warning("请按当前终端和设备重新加载并选择站点");
return;
}
}
const result = await executeForm.value.validate(); const result = await executeForm.value.validate();
if (result) { if (result) {
const obj = {}; const obj = {};
@ -1102,6 +1169,19 @@ onUnmounted(() => {
<style lang="scss" scoped> <style lang="scss" scoped>
$flow-canvas-cursor: url("data:image/svg+xml,%3Csvg%20xmlns=%27http://www.w3.org/2000/svg%27%20width=%2724%27%20height=%2724%27%20viewBox=%270%200%2024%2024%27%3E%3Cpath%20d=%27M4%202.5v16l4.2-4%203.1%207.1%203.4-1.5-3.1-7.1h5.8z%27%20fill=%27%23fff%27%20stroke=%27%231f2937%27%20stroke-width=%271.8%27%20stroke-linejoin=%27round%27/%3E%3C/svg%3E") 4 3, default; $flow-canvas-cursor: url("data:image/svg+xml,%3Csvg%20xmlns=%27http://www.w3.org/2000/svg%27%20width=%2724%27%20height=%2724%27%20viewBox=%270%200%2024%2024%27%3E%3Cpath%20d=%27M4%202.5v16l4.2-4%203.1%207.1%203.4-1.5-3.1-7.1h5.8z%27%20fill=%27%23fff%27%20stroke=%27%231f2937%27%20stroke-width=%271.8%27%20stroke-linejoin=%27round%27/%3E%3C/svg%3E") 4 3, default;
.single-node-station-tools {
display: flex;
align-items: center;
gap: 12px;
margin-bottom: 16px;
padding: 10px 12px;
border: 1px solid #dfe6ef;
border-radius: 6px;
background: #f7f9fc;
color: #65758b;
font-size: 13px;
}
.page { .page {
width: 100%; width: 100%;
height: 100%; height: 100%;