- 更新测试场景描述:从强制穿洞改为智能避障 - 明确避障能力定义:根据环境自动选择策略 - 新增路径规划设计理念章节,说明RRT*算法的通用性 - 避免AI助手误解为必须执行特定路径形态 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
221 lines
8.5 KiB
Markdown
221 lines
8.5 KiB
Markdown
# CLAUDE.md
|
||
|
||
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
|
||
|
||
## 项目概述
|
||
|
||
这是一个**现实环境机械臂运作可行性测试项目**,用于验证真实工业机械臂在复杂环境中的作业能力。
|
||
|
||
### 核心测试需求
|
||
|
||
**主要目标**:验证机械臂能否在有障碍物的现实环境中完成精确作业任务
|
||
|
||
**测试场景**:机械臂从指定基座位置出发,到达取物点A,抓取物体,通过智能路径规划避开障碍物(包括但不限于穿越洞口),到达目标点B并释放物体
|
||
|
||
**现实对应**:
|
||
- 工厂环境中的跨区域物料传送
|
||
- 建筑工地的穿墙作业
|
||
- 危险环境中的精确物品递送
|
||
- 医疗手术中的精密器械传递
|
||
|
||
**可行性验证内容**:
|
||
1. **到达性分析**:机械臂工作空间是否覆盖所有任务点
|
||
2. **避障能力**:是否能规划出安全路径(根据环境自动选择直达、绕行或穿越策略)
|
||
3. **精度要求**:是否能在约束空间内完成精确操作
|
||
4. **安全性**:整个作业过程是否避免碰撞
|
||
|
||
## 技术栈
|
||
|
||
- **pybullet**: 物理仿真引擎
|
||
- **kdl**: 运动学/动力学库
|
||
- **AI RRT***: 路径规划算法
|
||
|
||
## 路径规划设计理念
|
||
|
||
系统采用通用RRT*算法,根据实际环境配置自动选择最优路径:
|
||
- 如果存在直达路径,选择直线(最高效)
|
||
- 如果有障碍阻挡,自动避障(可能穿洞或绕行)
|
||
- 不强制特定路径形态,由算法根据环境智能决策
|
||
|
||
## 配置管理原则
|
||
|
||
**配置管理遵循单一职责原则:**
|
||
|
||
### 跨文件共享配置(存储在 `config.json`)
|
||
- 机械臂模型路径从 `config.robot.model_path` 读取
|
||
- 墙体参数从 `config.wall` 读取
|
||
- 洞口参数从 `config.hole` 读取
|
||
- 任务点A、B从 `config.task_points` 读取
|
||
- 运送物体参数从 `config.transport_object` 读取
|
||
- 仿真参数从 `config.simulation` 读取
|
||
- 路径规划的碰撞检测和执行参数从 `config.path_planning` 读取
|
||
|
||
### 单文件专用配置(定义为文件内常量)
|
||
- **运动学求解参数**:在 `src/robot/kinematics.py` 中定义 `MAX_ITERATIONS`、`EPSILON`
|
||
- **RRT*算法参数**:在 `src/planning/ai_rrt_star.py` 中定义所有算法常量
|
||
- **路径优化参数**:在 `src/planning/path_optimizer.py` 中定义优化常量
|
||
- **GUI界面参数**:在 `src/gui/main_window.py` 中定义界面常量
|
||
- **洞口穿越参数**:在 `src/planning/hole_crossing.py` 中定义策略常量
|
||
|
||
**原则**:配置文件用于多文件共享,单文件使用的参数定义为文件内常量
|
||
|
||
## 项目架构
|
||
|
||
### 目录结构
|
||
- `config.json`: **核心配置文件**,包含所有运行参数
|
||
- `models/`: 机械臂模型文件目录
|
||
- `manual_robot.urdf`: 9自由度机械臂URDF配置文件
|
||
- `CLAUDE.md`: 项目开发指南
|
||
|
||
### 机械臂模型规范
|
||
- 使用URDF格式定义机械臂模型
|
||
- 遵循右手坐标系统:X轴(红色)、Y轴(绿色)、Z轴(蓝色)
|
||
- 关节轴向定义:
|
||
- `xyz="1 0 0"`: 绕X轴旋转
|
||
- `xyz="0 1 0"`: 绕Y轴旋转
|
||
- `xyz="0 0 1"`: 绕Z轴旋转
|
||
|
||
### 坐标系统
|
||
- 位置定义:`<origin xyz="x y z" rpy="roll pitch yaw"/>`
|
||
- xyz: 位置偏移(米)
|
||
- rpy: 旋转角度(弧度) - roll绕X轴,pitch绕Y轴,yaw绕Z轴
|
||
|
||
## 开发指导
|
||
|
||
### 核心功能模块
|
||
1. **机械臂控制模块**: 基于pybullet的仿真控制
|
||
2. **路径规划模块**: 使用RRT*算法进行避障路径规划
|
||
3. **运动学计算模块**: 使用kdl进行正逆运动学计算
|
||
4. **障碍物检测模块**: 碰撞检测和环境感知
|
||
|
||
## 业务流程(严格按此顺序执行)
|
||
|
||
### 1. 系统初始化
|
||
1. **读取配置文件**: 从 `config.json` 加载所有配置参数
|
||
2. **验证配置**: 检查所有必要参数是否存在且有效
|
||
3. **初始化pybullet仿真环境**: 使用 `config.simulation` 参数
|
||
|
||
### 2. 环境构建
|
||
1. **加载机械臂**: 使用 `config.robot.model_path` 指定的URDF文件
|
||
2. **设置机械臂基座**: 使用 `config.robot.base_position` 和 `base_orientation`
|
||
3. **创建墙体障碍**: 根据 `config.wall` 参数创建墙体
|
||
4. **创建洞口**: 在墙体中根据 `config.hole` 参数创建洞口
|
||
5. **放置运送物体**: 在 `config.transport_object.initial_position` 放置物体
|
||
|
||
### 3. 任务执行
|
||
1. **路径规划阶段1**: 机械臂基座 → A点(取物点)
|
||
2. **抓取物体**: 在A点抓取运送物体
|
||
3. **路径规划阶段2**: A点 → 穿越洞口 → B点(避障路径规划)
|
||
4. **运送物体**: 携带物体穿越障碍到达B点
|
||
5. **释放物体**: 在B点释放物体
|
||
|
||
### 4. 关键约束
|
||
- **配置驱动**: 所有参数必须从config.json读取
|
||
- **避障要求**: 机械臂和物体不能与墙体碰撞,只能通过洞口
|
||
- **路径平滑**: 使用RRT*算法确保路径可行且平滑
|
||
- **运动学约束**: 遵循机械臂的运动学限制
|
||
|
||
## 开发规范
|
||
|
||
### 配置文件使用规范
|
||
```python
|
||
# 正确的配置读取方式
|
||
import json
|
||
|
||
# 1. 必须首先读取配置文件
|
||
with open('config.json', 'r') as f:
|
||
config = json.load(f)
|
||
|
||
# 2. 从配置读取机械臂模型路径
|
||
robot_model_path = config['robot']['model_path']
|
||
|
||
# 3. 从配置读取所有其他参数
|
||
wall_params = config['wall']
|
||
hole_params = config['hole']
|
||
task_points = config['task_points']
|
||
transport_object = config['transport_object']
|
||
```
|
||
|
||
### 严禁的做法
|
||
```python
|
||
# ❌ 严禁硬编码路径和参数
|
||
robot_model = "models/manual_robot.urdf" # 错误!
|
||
wall_position = [2.0, 0.0, 1.0] # 错误!
|
||
```
|
||
|
||
### 测试验证
|
||
- 配置文件修改后,程序行为应相应改变
|
||
- 不同的机械臂模型应能正确加载
|
||
- 墙体和洞口参数变化应反映在仿真中
|
||
- A、B点位置调整应影响路径规划结果
|
||
|
||
## 已知问题
|
||
|
||
### 配置更新后路径规划组件未重新初始化(2025-09-13)✅ 已解决
|
||
**现象**:修改配置文件后运行路径规划,报错"Joint index out-of-range"。
|
||
|
||
**根本原因**:
|
||
- `on_config_applied`方法重新创建了`ArmController`但未重新初始化路径规划组件
|
||
- `CollisionChecker`仍持有旧的`arm_controller`引用,其`robot_id`已无效
|
||
- 使用无效的`robot_id`调用`p.resetJointState`导致索引越界错误
|
||
|
||
**解决方案**:
|
||
- 在重新创建`ArmController`后立即调用`_initialize_planning_components()`
|
||
- 确保路径规划组件使用新的`arm_controller`实例
|
||
|
||
**修复文件**:`src/gui/main_window.py`(第282行)
|
||
|
||
### KDL逆运动学崩溃(2025-09-11)✅ 已解决
|
||
**现象**:点击"Test Reachability"按钮后程序直接退出,无错误信息。
|
||
|
||
**根本原因**:C++对象生命周期问题
|
||
- `ik_vel_solver` 作为局部变量在函数结束后被销毁
|
||
- `ChainIkSolverPos_NR_JL` 内部持有已销毁对象的引用
|
||
- 调用 `CartToJnt` 时访问无效内存导致崩溃
|
||
|
||
**解决方案**:
|
||
- 将 `ik_vel_solver` 改为实例变量 `self.ik_vel_solver`
|
||
- 确保与 `ik_solver` 有相同的生命周期
|
||
- 移除违反编码规范的回退方案
|
||
|
||
**修复文件**:`src/robot/kinematics.py`
|
||
|
||
### 墙体洞口创建问题(2025-09-11)✅ 已解决
|
||
**现象**:
|
||
1. 修改洞口尺寸后墙体形状异常,呈现"凸"字形
|
||
2. 洞口尺寸变化不生效
|
||
3. 多次修改后墙体形状越来越怪异
|
||
|
||
**根本原因**:
|
||
1. **墙体分块设计错误**:上下墙体只有洞口宽度,左右墙体是全高,导致四角空缺
|
||
2. **未清理旧墙体**:每次重建墙体时新旧叠加,形状混乱
|
||
3. **cleanup函数不完整**:只清理了主墙体ID,未清理所有墙体部件
|
||
|
||
**解决方案**:
|
||
- 改为"上下全宽 + 左右洞口高度"的分块方式,避免四角空缺
|
||
- 添加 `_clear_wall()` 函数清理所有墙体部件
|
||
- 修复 `cleanup()` 函数调用 `_clear_wall()`
|
||
- 使用 `_wall_part_ids` 列表记录所有墙体部件ID
|
||
|
||
**修复文件**:`src/simulation/environment.py`
|
||
|
||
### 代码重复和一致性问题(2025-09-12)✅ 已解决
|
||
**现象**:
|
||
1. `path_executor.py` 中存在未使用的重复方法 `_move_to_configuration_reset()`
|
||
2. 空文件 `rrt_star.py` 增加项目混乱度
|
||
3. 需要验证KDL和PyBullet关节顺序转换的一致性
|
||
|
||
**根本原因**:
|
||
1. **代码重复**:两个功能相同的路径执行方法,违反DRY原则
|
||
2. **遗留文件**:空的 `rrt_star.py` 文件未清理
|
||
3. **架构复杂性**:需要确保关节顺序映射在所有地方正确使用
|
||
|
||
**解决方案**:
|
||
- 删除未使用的 `_move_to_configuration_reset()` 方法
|
||
- 删除空的 `rrt_star.py` 文件
|
||
- 验证确认关节顺序转换机制在全项目中使用一致
|
||
|
||
**修复文件**:
|
||
- `src/planning/path_executor.py` - 删除重复方法
|
||
- `src/planning/rrt_star.py` - 删除空文件
|
||
- 全项目关节顺序转换验证通过 |