上下求索
探索DirectX9.0)
posts - 30,  comments - 75,  trackbacks - 0
 

PhysX1

By sssa2000

 

今天正式开始接触PhysX,关于这个东西还是简单说几句。这是个很NB的物理引擎,Xbox360PS3都使用了这个东东。

 

PhysX这个引擎很好用,上手十分简单。简单说句,现在在他的官方主页上已经无法获得SDK ,必须要先注册提交申请,通过后才能下载。目前官方的最新版本似乎是2.5版本。我使用了以前下载的2.4.4版。

 

值得一提的是PhysX的文档相当的详细,从路径设置到Tutorials的代码解释都有,大家有空还是看看吧。我这也是照抄文档而已。

 

1 安装和设置

 

首先安装好后,要设置编译器路径:

Include文件:

SDKs\Foundation\include",

"SDKs\Physics\include"

"SDKs\PhysXLoader\include

"SDKs\NxCharacter\include"

"SDKs\Cooking\include"

 

Lib文件:

"SDKs\lib\win32\"

 

Ok,现在就可以正式的使用这个引擎的SDK来开发了。

 

2、概念

首先解释几个关于PhysX的概念:

要使用这个物理引擎模拟真实的物理现象,需要以下几个东西:

NxPhysicsSDKPhysics SDK对象,这个是进行物理模拟的最基础的东西。它提供了创建物理系统的接口,是个纯虚类。

 

NxScene      场景。可以把它看成是物理概念上的世界,负责管理所有的物体以及世界的重力等等。一个程序可以维护多个场景。

 

Descriptor:一个专门负责初始化的类。你可以用这个类初始化任何该物理引擎要用到的东西,当然Descriptor也有很多种,有专门负责SceneDescriptor,有专门负责初始化各个物体的Descriptor等等

NxMaterial:材质,描述物体的表面特征。

Actors 就是场景中的物体。也就是模拟的对象。

Joints   用于连接的物体的物体。

当然还有很多概念,例如液体,等等。但是对于刚开始的来说已经足够了。

 

另外,值得一提的是时间概念:和所有实时渲染的图形库一样,时间在这个实时的物理引擎中的作用也是不可缺少的。物理引擎将在指定的时间片内对需要的物理计算进行运算然后传递给图形接口绘制计算结果。

 

3、构建物理世界

NxPhysicsSDK*     gPhysicsSDK = NULL;

NxScene*          gScene = NULL;

NxActor* groundPlane = NULL;

NxActor* box = NULL;

首先建立SDK对象并初始化,然后分别是场景,物体。

void InitNx()

{

1、 使用NxCreatePhysicsSDK()建立SDK对象,并初始化全局变量。

2、 建立NxSceneDesc,也就是描述Scene的描述对象,将初始化的值赋给它,例如重力,风。

3、 使用NxSceneDesc建立ScenegPhysicsSDK->createScene(sceneDesc);

4、 建立并初始化NxMaterial

5、 建立2NxActorDesc,并使用它们建立2NxActor

6、 获取当前时间

7、 开始物理计算

}

罗列代码我就不做了,如果需要SDK的可以联系我,或者谁能提供一个空间放上去更加好。

 

值得注意的是建立2NxActor的过程,因为NxActor有众多的参数需要设置。]

 

4、进行物理模拟

我们需要在每次渲染之前进行物理运算然后将结果取出交给图形部分渲染。

 

使用引擎进行物理模拟很简单,我们初始化完世界以及设置好物体之后,我们只需要2句话就能让物理引擎自动进行相应的物理运算:

void StartPhysics()

{

     // Update the time step

     NxReal deltaTime = UpdateTime();

 

     // Start collision and dynamics for delta time since the last frame

    gScene->simulate(deltaTime);

     gScene->flushStream();

}

//=============================================================

void GetPhysicsResults()

{

     // Get results from gScene->simulate(deltaTime)

     while (!gScene->fetchResults(NX_RIGID_BODY_FINISHED, false));

}

注意使用fetchResults函数的时候最后传递的参数是false,这表明程序将以非阻塞的方式调用。如果使用阻塞方式调用的话,就一定会等到simulate有结果才返回。

 

所以每次渲染前先调用这2个函数然后再进行绘图:

void RenderCallback()

{

...

    if (gScene && !bPause) //是否暂停 或者是否需要绘制场景

    {

        GetPhysicsResults(); //获取上次模拟结果

        ProcessInputs();    //处理输入

        StartPhysics();     //根据输入进行新的运算

    }

}

 

5、动态的施加力

目前为止,程序已经能模拟在重力环境下的物理运动,以及和地面的碰撞监测。我们同样可以动态的施加任意方向的力给物体,只需要一句话即可:

 

NxVec3 gForceVec(0,0,0); //全局变量,用于描述力的方向和大小

NxReal gForceStrength = 150;

gForceVec = ApplyForceToActor(box,NxVec3(0,0,1),gForceStrength);//Z方向施力

 

这样处理按键的代码就显而易见了:

         switch (i)

         {

              // Force controls

              case 'i': { gForceVec = ApplyForceToActor(box,NxVec3(0,0,1),gForceStrength); break; }

              case 'k': { gForceVec = ApplyForceToActor(box,NxVec3(0,0,-1),gForceStrength); break; }

              case 'j': { gForceVec = ApplyForceToActor(box,NxVec3(1,0,0),gForceStrength); break; }

              case 'l': { gForceVec = ApplyForceToActor(box,NxVec3(-1,0,0),gForceStrength); break; }

              case 'u': { gForceVec = ApplyForceToActor(box,NxVec3(0,1,0),gForceStrength); break; }

              case 'm': { gForceVec = ApplyForceToActor(box,NxVec3(0,-1,0),gForceStrength); break; }

 

             // Return box to (0,5,0)

             case 't': { box->setGlobalPosition(NxVec3(0,5,0)); break; }

         }

 

 

6、画出物体

目前所有的物体的信息都位于Actor中。所以我们需要获取所有的Actor。用循环分别画出。

void RenderActors(bool shadows)

{

    NxU32 nbActors = gScene->getNbActors(); //number

    NxActor** actors = gScene->getActors(); //Actor的数组

    while (nbActors--)

    {

        NxActor* actor = *actors++;

        DrawActor(actor);

        if (shadows)        // 处理阴影

        {

              DrawActorShadow(actor);

        }

    }

}

 

7、清理工作

void ReleaseNx()

{

    if (gScene)

    {

        GetPhysicsResults(); // 确保没有fetchResults在等待运行结果

        gPhysicsSDK->releaseScene(*gScene);

    }

    if (gPhysicsSDK) gPhysicsSDK->release();

}

 

void ResetNx()       //重置

{

    ReleaseNx();

    InitNx();

}

 

End

我觉得其实搞清楚物理引擎的工作流程比理解其中细节更加重要,其实PhysX事例中附带的图形部分的代码也很有意思,不过重点不在那罢了。

 

有一点我觉得还是不太理解,整个程序的物体的信息都是保存在Sence中的Actor里面的,包括最后的渲染都需要从Actor里面取得,如果游戏中的几何物体很复杂而且很多的话我觉得还是不太妥当,当然这仅仅是第一次接触PhysX,应该会有更加好的方法来组织数据。

 

初次接触,错误难免,望指正。不胜感激!

 

 

2006-10-18

posted on 2006-10-18 17:20 大河马和小魔鱼 阅读(2761) 评论(11)  编辑 收藏 所属分类: OpenGL

FeedBack:
2006-10-25 13:41 | Johnson      
遗憾的是,商业使用Novadex要收费
  回复  引用  查看    
2006-10-26 10:29 | yanglin [未注册用户]
PhysX在pc平台上已经免费了,你只要以公司的名义和他签订合同就可以了
  回复  引用    
2006-12-07 17:47 | kane[匿名] [未注册用户]
hi,您好,我最近也在研究PhysX,有机会可以交流一下,MSN:wukaikane@hotmail.com
  回复  引用    
2006-12-07 17:51 | kane[匿名] [未注册用户]
BTW,我也是比较关心你说的最后一点,就是如何进行物体和物体之间的快速碰撞,也就是说如何把剔除,如使用Object Tree(可以用octree)在Broad phase阶段剔除掉不可碰撞的物体,问题就是如何把物理引擎和object Tree结合起来

  回复  引用    
2006-12-07 17:57 | kane[匿名] [未注册用户]
另外 渲染模型和显示模型肯定是两套模型,我觉得啊
  回复  引用    
2006-12-09 16:29 | kane[匿名] [未注册用户]
又仔细看了看它的教程,发现很多新东西,PMap我觉得就是碰撞模型,不知道对不,另外,碰撞引擎已经提供了Broad Phase检测,那么我们还需要提供object tree 去剔除不可碰撞的物体呢?
  回复  引用    
#7楼 [楼主]
2006-12-11 09:45 | 大河马和小魔鱼      
一般情况,不需要再提供object tree了,当然如果是巨量的碰撞那又是另外一回事了。

Novodex的速度上其实并没多大优势,ODE,Bullet速度都比他快。
要是Bullet的文档也有这么好就好了
  回复  引用  查看    
2006-12-21 14:13 | banjamin [未注册用户]
很好,我也在学这个引擎!
关于楼主说的最后的那个问题,我想说说我的想法:
1、现实中物理引擎和渲染引擎是分开的。
2、物理引擎使用粗糙模型,渲染引擎用精细模型。
3、物理引擎计算Actor运动后的最新位置及旋转角度。渲染引擎从物理引擎中取得该模型的平移旋转矩阵,与模型的顶点相乘后,作最终渲染。
这样既可以保证物理运算的快速,又可以保证模型的精细。

以上是一些个人的看法,不一定正确。欢迎各位同道的朋友加入:PhysX物理引擎QQ群(23970405),一起研究学习。
  回复  引用    
2007-01-04 13:41 | Kane[匿名] [未注册用户]
后来仔细看了看文档,确实在physx内部,已经帮做好了,并且内部有octree来作broadphase
楼上的想法和我一样哦
现在就是不知道怎么使用mayaplugin将maya和引擎结合起来,摸索中……

bullet的文档………………
哈哈,现在用hadrware,不错的说:)
  回复  引用    
2007-02-27 14:03 | PhysDev [未注册用户]
物理开发网,www.physdev.com是一个专门讨论物理编程的网站,欢迎交流
  回复  引用    
2007-05-18 08:55 | ic.expert [未注册用户]
emule上面可以下在~~~最新版
  回复  引用    

标题  
姓名  
主页
Email (博主才能看到) 
验证码 *  看不清,换一张 [登录][注册]
内容(请不要发表任何与政治相关的内容)  
  登录  使用高级评论  新用户注册  返回页首  恢复上次提交      
"五向定位"职业成长路线公开课(上海、南京、大连)
Google站内搜索


相关链接:
 





<2006年10月>
24252627282930
1234567
891011121314
15161718192021
22232425262728
2930311234

与我联系

搜索

 

常用链接

留言簿(13)

我参与的团队

随笔分类

随笔档案

最新评论

  • 1. re: Export利器:IGame
  • 你好,你知道怎么用IGame导出骨骼和动画吗?我正在做这个,现在几乎被搞糊涂了
  • --dolaham

阅读排行榜

评论排行榜