自动推导URDF运动学链

This commit is contained in:
zhangshun
2026-06-16 12:34:17 +08:00
parent a3efcd66a5
commit c2d79a74b9
3 changed files with 149 additions and 3 deletions

View File

@@ -142,6 +142,51 @@ function buildInverseRequest(command, robotUuid, poseStr, qInitStr, extra = {})
};
}
// 构造 link 名称被整体替换的 URDF用于验证初始化能自动推导运动学链。
function buildRenamedUrdfFromDocs() {
const urdfPath = path.join(rootDir, "docs", "urdf.xml");
return fs
.readFileSync(urdfPath, "utf8")
.replaceAll("base_link-base", "renamed_root_link-renamed_world")
.replaceAll("base_link", "renamed_root_link")
.replaceAll("tool0", "renamed_tcp")
.replaceAll('link name="base"', 'link name="renamed_world"')
.replaceAll('parent link="base"', 'parent link="renamed_world"');
}
// 注册改名后的 URDF 并执行一次 FK确认底层不再依赖固定 base/tool0。
async function runRenamedUrdfChainCase(module) {
const robotUuid = "renamed_chain_robot";
const urdfBase64 = Buffer.from(buildRenamedUrdfFromDocs(), "utf8").toString("base64");
const initResponse = callBusinessApi(module, {
msg: "init renamed urdf",
req_code: "AUTO_RENAMED_INIT",
req_from: "wasm_test",
req_cmd: "Cmd_InitRobot",
req_param: {
robot_uuid: robotUuid,
urdf_base64: urdfBase64,
force_update: true,
},
});
ensure(initResponse.success === true, "renamed URDF init request failed");
ensure(getByPath(initResponse, "res_data.success") === true, "renamed URDF init result is not successful");
const forwardResponse = callBusinessApi(module, buildForwardRequest(robotUuid, [0, 0, 0, 0, 0, 0]));
ensure(forwardResponse.success === true, "renamed URDF forward request failed");
ensure(getByPath(forwardResponse, "res_data.success") === true, "renamed URDF forward result is not successful");
ensure(Array.isArray(getByPath(forwardResponse, "res_data.position")), "renamed URDF forward position is missing");
return {
details: {
position: getByPath(forwardResponse, "res_data.position"),
orientation: getByPath(forwardResponse, "res_data.orientation"),
},
};
}
function assertStaticCase(response, assertions) {
for (const assertion of assertions) {
const actual = getByPath(response, assertion.path);
@@ -353,6 +398,10 @@ const suite = [
{ path: "res_data.OPERATION.OPERATION.frames", lengthEquals: 2 },
],
},
{
id: "kinematics_renamed_urdf_chain",
type: "renamed_urdf_chain",
},
{
id: "spc_basic_5x30",
type: "static",
@@ -522,6 +571,8 @@ async function runCase(module, testCase) {
return runRoundtripSingleCase(module, testCase);
case "roundtrip_path":
return runRoundtripPathCase(module, testCase);
case "renamed_urdf_chain":
return runRenamedUrdfChainCase(module, testCase);
default:
throw new Error(`Unknown test type: ${testCase.type}`);
}