资讯详情

揭秘PhysX源码架构:从接口到求解的完整脉络

📅 2026/10/8 19:11:13 | 华诺云谱 👁 阅读
揭秘PhysX源码架构:从接口到求解的完整脉络
阅读 PhysX 源码建议先建立一张地图公共接口 ↓ API 实现与对象管理 ↓ 场景模拟控制 ↓ 碰撞检测 / 动力学求解 / 场景查询 ↓ 任务系统、内存和基础设施下面以PhysX 5.x 开源仓库的典型布局为例。不同版本的目录会有增删内部符号也可能变化源码分析时应固定一个 tag 或 commit。官方仓库https://github.com/NVIDIA-Omniverse/PhysX一、源码树总览下面是用于阅读导航的核心目录节选不是某个版本的完整目录清单PhysX/ ├── README.md ├── LICENSE.md ├── ... 仓库工具、依赖管理和构建入口 │ └── physx/ ├── include/ 对外公开的 C API │ ├── PxPhysicsAPI.h │ ├── PxPhysics.h │ ├── PxScene.h │ ├── PxActor.h │ ├── PxRigidActor.h │ ├── PxRigidBody.h │ ├── PxRigidDynamic.h │ ├── PxRigidStatic.h │ ├── PxShape.h │ ├── geometry/ │ ├── foundation/ │ ├── extensions/ │ └── ... │ ├── source/ 核心实现 │ ├── physx/ │ │ └── src/ Np* 等公共 API 实现 │ │ │ ├── simulationcontroller/ │ ├── lowlevel/ │ ├── lowlevelaabb/ │ ├── lowleveldynamics/ │ ├── geomutils/ │ ├── scenequery/ │ │ │ ├── physxcooking/ │ ├── physxextensions/ │ ├── physxcharacterkinematic/ │ ├── physxmetadata/ │ │ │ ├── foundation/ │ ├── common/ │ ├── task/ │ ├── pvd/ │ └── ... │ ├── snippets/ 小型示例程序 ├── samples/ 示例工程是否包含依版本而定 └── ... 构建配置、工具和文档等注意两个容易混淆的路径physx/include/是用户调用的 API而physx/source/physx/src/是这些 API 的内部实现入口之一。二、include公共接口层这里定义应用程序能调用的接口。核心对象文件用途PxPhysics.h创建场景、刚体、Shape、材质等PxScene.h场景管理、模拟、查询PxActor.h场景对象基础接口PxRigidActor.h刚体与 Shape 的连接PxRigidBody.h质量、惯性、速度、力等PxRigidDynamic.h动态刚体与运动学控制PxRigidStatic.h静态刚体PxShape.h几何、材质、过滤与形状标志例如PxRigidDynamic*bodyphysics-createRigidDynamic(pose);公共头文件告诉你参数是否合法对象由谁释放何时可以调用调用是否唤醒刚体哪些场景状态下禁止修改。读源码之前先读接口注释。接口契约往往比内部算法更能解释实际使用中的问题。三、source/physx/srcAPI 实现与对象管理常见文件包括NpPhysics.cpp NpScene.cpp NpRigidDynamic.cpp NpRigidStatic.cpp NpShape.cppNp*类通常是公共接口的具体实现。例如PxRigidDynamic ↑ 实现其接口 NpRigidDynamic这一层主要负责参数检查读写访问检查API 对象生命周期Actor 与 Shape 的绑定场景加入和移除将修改传递给内部模拟系统调试工具相关通知。推荐阅读入口NpPhysics::createRigidDynamic() NpScene::addActor() NpScene::simulate() NpScene::fetchResults()部分实现可能分散在头文件、公共模板或共享基类中所以不要假定一个 API 的全部逻辑都在同名.cpp内。四、simulationcontroller场景模拟控制层常见前缀Sc常见内部类型包括Sc::Scene Sc::BodyCore Sc::BodySim Sc::ShapeCore Sc::ShapeSim它连接“API 层的对象”与“底层实际参与计算的数据”。Core 与 Sim 的理解方式可以粗略理解为Core对象的核心属性和状态 Sim 对象加入场景后的模拟表示例如一个尚未加入场景的刚体仍然可以拥有质量、速度、位姿等属性但它不需要立刻具有完整的场景交互关系。加入场景后还需要组织包围盒接触交互岛屿连接激活与睡眠求解所需数据。因此不能简单把一个PxRigidDynamic看成“从 API 一直传到求解器的同一个数据结构”。4.x 中还常能看到Scb缓冲相关实现。分析其更新时序时不要直接套用到所有 5.x 版本。五、碰撞相关目录碰撞检测的主要工作分布在多个模块中而不是全部放在一个collision/目录下。1.lowlevelaabb包围盒与宽相检测常见前缀Bp负责的核心问题是哪些形状有可能发生碰撞概念流程Shape 的世界空间包围盒 ↓ Broad Phase ↓ 新增、保持或消失的候选重叠对这里值得关注AABB 管理宽相算法对象插入与移除候选对的增量更新。2.geomutils几何算法库常见前缀Gu主要包含几何相交测试距离计算射线与几何求交Sweep、Overlap 的几何实现接触生成凸体、三角网格、高度场相关算法持久接触流形相关实现。例如球体 vs 盒体 凸体 vs 凸体 胶囊 vs 三角网格要研究“接触点究竟怎么算出来”这里是重点。3.lowlevel底层碰撞流水线与数据组织这里包含底层碰撞任务、接触管理及相关数据处理代码。可以把两者的区别理解为geomutils 几何算法怎么做 lowlevel 等模块 如何把许多碰撞对组织起来执行这些算法这是概念划分不是严格的源码边界。六、lowleveldynamics动力学与约束求解常见前缀Dy这是研究物理响应的核心目录。主要关注Solver Body接触约束准备关节约束准备约束批处理PGS/TGS 求解冲量和速度更新刚体状态积分Articulation 动力学。典型数据流刚体状态 接触数据 关节数据 ↓ 约束准备 ↓ 排序与批处理 ↓ 迭代求解 ↓ 速度、冲量和位姿等结果阅读时建议先理解数学与数据结构再进入 SIMD 优化实现。否则很容易看到大量向量操作却不知道它们对应哪条约束方程。七、scenequery场景查询系统常见前缀Sq对应 APIscene-raycast(...);scene-sweep(...);scene-overlap(...);这一模块主要解决如何从场景里的大量 Shape 中高效找出需要执行几何测试的对象它负责查询结构的组织、维护和遍历具体的几何测试则会使用geomutils等模块。场景级查询 ↓ 查询加速结构筛选候选 Shape ↓ 具体几何测试 ↓ 过滤、命中结果收集Scene Query 的加速结构不能直接等同于模拟碰撞的 Broad Phase。两者需求不同也有不同的更新与过滤机制。八、资源处理与扩展目录physxcooking负责网格资源预处理例如凸包构建三角网格处理加速结构构建资源有效性检查。重点区分Cooking生成适合物理使用的资源 Runtime加载资源并执行模拟或查询physxextensions包含建立在核心 API 上的扩展能力常见关节质量与惯性计算工具刚体辅助操作序列化相关扩展。例如PxRigidBodyExt::updateMassAndInertia(...)就应从这里查找实现。physxcharacterkinematic角色控制器相关实现例如胶囊控制器盒体控制器台阶与斜坡处理控制器移动中的碰撞处理。Character Controller 不等于一个普通动态刚体。它有专门的移动和碰撞处理逻辑。physxmetadata包含对象属性、序列化或工具使用的元数据相关设施。它不是刚体模拟主流水线但在对象持久化与工具集成中很重要。九、基础设施目录目录主要用途foundation内存、错误报告、平台基础设施等common多模块共享的内部工具和数据结构task任务依赖与调度接口pvdPhysX Visual Debugger 相关支持其中task值得特别注意。一次scene-simulate(dt);并不只是执行一个很长的串行函数更重要的是构建和提交具有依赖关系的模拟任务。任务 A ──┐ ├──→ 任务 C ──→ 任务 D 任务 B ──┘因此仅靠单线程断点看到的调用栈未必能反映完整模拟流程还需要观察任务及其 continuation 关系。十、推荐的源码阅读路线结合前面的“PhysX 物理对象”建议先追踪一个动态盒子。路线一对象生命周期PxPhysics::createRigidDynamic() ↓ NpPhysics / NpRigidDynamic ↓ 创建并附着 NpShape ↓ NpScene::addActor() ↓ 建立内部场景模拟表示 ↓ release()重点所有权、引用计数、状态检查与资源释放。路线二一帧模拟NpScene::simulate() ↓ 场景控制与任务组织 ↓ 包围盒、宽相、接触生成 ↓ 岛屿与约束组织 ↓ 动力学求解 ↓ NpScene::fetchResults()这是导航图不是精确调用栈。路线三一次射线查询PxScene::raycast() ↓ API 查询入口 ↓ SceneQuery 加速结构 ↓ GeomUtils 几何求交 ↓ 结果收集相比整帧模拟射线查询路径通常更适合初次深入算法实现。十一、实用搜索方式在仓库根目录使用ripgrep# 定位动态刚体 API 的具体实现rg-nNpPhysics::createRigidDynamicphysx/source# 找场景模拟入口rg-nNpScene::simulate|NpScene::fetchResultsphysx/source# 找刚体与形状的内部模拟表示rg-nclass BodySim|class ShapeSimphysx/source# 找质量与惯性辅助函数rg-nupdateMassAndInertiaphysx/source/physxextensions# 找一个 API 在示例中的使用方式rg-nsetKinematicTargetphysx/snippets推荐始终按这个顺序分析先看include中的契约再看snippets中的用法然后追踪Np实现最后进入碰撞和求解模块。这样能避免一开始就陷入底层优化代码却没有建立完整的数据流和对象生命周期认知。
📝

华诺云谱内容团队

资深建站顾问 · 行业研究员

10年+企业数字化服务经验,专注智能建站、SEO优化与品牌营销,持续输出建站技巧、行业洞察与营销干货,已帮助5000+企业实现数字化增长。

你可能需要的服务

订阅华诺云谱资讯周报

每周一封,精选建站技巧、SEO与营销干货,直达邮箱。已有 8,000+ 企业主订阅,助你少走弯路。

↑