NxOgre 笔记
http://blog.csdn.net/eplaylity/article/details/4726216
1. 去NV官网下载并安装PhysX的SDK。
(好像还要安装PhysX系统软件以便运行时需要,因为我前段时间安装了JX3,就不用了)
2. 设置PhysX SDK头文件及库的搜索路径设置环境变量PHYSX_DIR。
(我的是D:/Program Files/NVIDIA Corporation/NVIDIA PhysX SDK/v2.8.1)
因为要用到头文件搜素路径:
-SDKs/Physics/include
-SDKs/Foundation/include
-SDKs/Cooking/include
-SDKs/PhysXLoader/include
以及链接库搜索路径:
-SDKs/lib/win32
-SDKs/Physics/lib/win32/Release(无效)
-SDKs/Cooking/lib/win32/Release(无效)
3. 下载编译BloodyMess(最新版),或Bleeding(稳定版)
一共三个项目:
NxOgre
GLUTRenderSystem
OGRE3DRenderSystem
NxOgre是核心项目,后面两个是两个渲染系统特例。
1. 单位声明
NxOgre使用“米-千克-第二 系统”,以米为长度单位,千克为质量单位,秒为时间单位。
2. 初始化代码
2.1 最顶层类World,单实例。最大容纳32个Scene。不同场景之间的物体不能交互。
2.2 每个场景都有很多Actor,这个数目仅受限于你的机器配置。这些Actor在World中表现成一个物理对象,但他们都是不可见的。
想看到他们,需要使用一个Body,一个简单的Actor,它通过RenderSystem渲染到你的屏幕。
BloodyMess内建了几个渲染系统,包括OpenGL和Ogre,但这并不是要限制你创建自己的渲染系统。
2.3 NxOgre的另一个重要元素就是TimeController。它控制着World中的Actor所逝去的时间。
2.4 为了使用NxOgre及其指定的Ogre渲染类,头文件及链接库
#include <NxOgre.h>
#include <NxOgreOGRE3D.h>
NxOgre.lib
NxOgreOGRE3D.lib
2.5 在类的保护区域,声明世界、场景、和渲染系统的变量
NxOgre::World *mWorld;
NxOgre::Scene *mScene;
OGRE3DRenderSystem *mRenderSystem; // 并非属于NxOgre名称空间
2.6 在createScene()函数中初始化世界
mWorld = NxOgre::World::createWorld();
// 通过场景描述符,初始化场景
NxOgre::SceneDescription sceneDesc;
sceneDesc.mGravity = NxOgre::Vec3(0,-9.8f,0);
sceneDesc.mName = "BloodyMessTutorial2";
mScene = mWorld->createScene(sceneDesc);
// 指定一些应用到整个场景的默认物理量
mScene->getMaterial(0)->setStaticFriction(0.5); // 静摩擦系数
mScene->getMaterial(0)->setDynamicFriction(0.5); // 动摩擦系数
mScene->getMaterial(0)->setRestitution(0.1); // 恢复系数
mRenderSystem = new OGRE3DRenderSystem(mScene);
// 添加物体,外形为1x1x1的盒子,位置是Y正方向上20米
OGRE3DBody *mCube;
mCube = mRenderSystem->createBody(new NxOgre::Box(1,1,1),NxOgre::Vec3(0,20,0),"cube.1m.mesh");
2.7 获取运动需要每一帧都在FrameListener中advance我们的TimeController。
NxOgre::TimeController::getSingleton()->advance(evt.timeSinceLastFrame);
2.8 物理交互作用
OGRE3DBody *mCubeTwo;
mCubeTwo = mRenderSystem->createBody(new NxOgre::Box(1,1,1),NxOgre::Vec3(20,35,0),"cube.1m.mesh");
mCubeTwo->addForce(NxOgre::Vec3(-800,-200,0));
// 创建一个地面平面,这是一个actor,有无限尺寸,不能被移动
mScene->createSceneGeometry(new NxOgre::PlaneGeometry(0,NxOgre::Vec3(0,1,0)),Matrix44_Identity);
// 创建一个OGRE渲染的可见平面,因为NxOgre中的actor是不可见的
MovablePlane *plane = new MovablePlane("Plane");
plane->d = 0;
plane->normal = Vector3::UNIT_Y;
MeshManager::getSingleton().createPlane("PlaneMesh",ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME,
*plane,120,120,1,1,true,1,3,3,Vector3::UNIT_Z);
Entity *planeEnt = mSceneMgr->creatEntity("PlaneEntity","PlaneMesh");
planeEnt->setMaterialName("Examples/Rockwall");
SceneNode *mPlaneNode = mSceneMgr->getRootScenNode()->createChildSceneNode();
mPlaneNode->attachObject(planeEnt);
mPlaneNode->scale(100,100,100);
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_2
1. 一个全局的VisualDebugger实例,以RenderableType_VisualDebugger创建一个可渲染对象。
将此渲染对象绑定到一个SceneNode上,然后,每一帧VisualDebugger::draw()/SceneNode::needUpdate()
这个好像在OGRE3DRenderSystem的advance()里有封装。
2. SceneNode继承了Node的needUpdate()来标识这个节点及其父节点的状态更新。
3. 实现步骤
// 创建OGRE3DRenderable对象
new OGRE3DRenderable(NxOgre::Enums::RenderableType_VisualDebugger);
// 为可视化调试器设置可渲染对象,并将可渲染对象绑定到场景节点
NxOgre::VisualDebugger::setRenderable();
SceneNode::attachObject();
// 设置可视化调试器的可视化模式
VisualDebugger::setVisualisationMode(NxOgre::Enums::VisualDebugger_ShowAll);
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_3
1. Volume是一个任意形状的不可见的物理对象。并且不能动。常被用作trigger。
当一个物理对象进入/没入/离开它时,会触发一个程序指定的动作。
2. 在场景中创建一个Volume步骤
2.1 外形,比如,一个5x5x5的盒子
2.2 位置
2.3 一个Callback类的对象
2.4 回调行为(事件发生时调用onVolumeEvent())
NxOgre::Scene::createVolume(new NxOgre::Box(5),
NxOgre::Matrix44(NxOgre::Vec3(0,0,0)),
this,NxOgre::Enums::VolumeCollisionType_All);
3. 创建当一个Actor触发的回调函数
void onVolumeEvent(NxOgre::Volume* volume, NxOgre::Shape* volumeShape, NxOgre::RigidBody* rigidBody,
NxOgre::Shape* rigidBodyShape, unsigned int collisionEvent)
{
if(collisionEvent == NxOgre::Enums::VolumeCollisionType_OnEnter)
{
NxOgre::Actor* actor = static_cast<NxOgre::Actor*>(rigidBody);
float y = (9.81 * actor->getMass()) // 抵消重力
+ (-actor->getLinearVelocity().y * actor->getMass()) // 抵消竖直速度
+ (10 - actor->getGlobalPosition().y * actor->getMass()); // 添加一些向上移动的力
actor->addForce(NxOgre::Vec3(0, y, 0), NxOgre::Enums::ForceMode_Impulse);
}
}
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_4
1. Kinematics是些特殊的物理对象,它可以影响别的物体,却却不受别的物体影响。
他们可见、可移动,是升降机的一种最佳实现。
2. NxOgre中,Actor只是一个物理对象的物理表达,是不可见的。
然而,一个Body是一个Actor加上一个可视化的东西(比如,通过Ogre的Entity).
KinematicActor与KinematicBody也是同样的关系。
3. 移动、设置KinematicBody的位置
KinematicBody::moveGlobalPosition(NxOgre::Vec3&);
KinematicBody::setGlobalPosition(NxOgre::Vec3&);
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_5
1. 凸面体与三角网格
三角网格可以很完美地表现一个OGRE模型的物理外形。
OGRE模型和Flour所生成的三角网格就外形而言完全等同,
为了性能起见,一般使用凸面体做物理碰撞。
NxOgre中凸面体最多256个顶点,作为一个大包装盒把要进行碰撞检测的对象包围起来。
2. Flour是一个可以把OGRE模型转换成NxOgre格式的小工具。
包括,特殊的mesh、skeleton和heightfield。
3. 使用Flour生成.nxs文件
flour convert in:Stairs.mesh, into:triangle, out:Stairs.nxs
flour convert in:Barrel.mesh, into:convex, out:Barrel.nxs
4. BloodyMess使用自己的资源系统来处理所有类型的文档:文件夹、zip压缩文档、URL。
NxOgre::ResourceSystem::getSingleton()->openArchive("media","file:media");
NxOgre::ResourceSystem::getSingleton()->openArchive("media","file:D:/Projects/BloodyMess Tutorials/media");
(注意:文件路径可以使用相对或绝对路径,"/" 也可以用 "//"替换)
5. 使用资源系统加载模型
NxOgre::Mesh* convexMesh = NxOgre::MeshManager::getSingleton()->load("media:Barrel.nxs");
NxOgre::Mesh* triangleMesh = NxOgre::MesnManager::getSingleton()->load("media::Stairs.nxs");
6. 使用已加载的模型,创建凸面体和三角几何
NxOgre::Convex* convex = new NxOgre::Convex(convexMesh);
NxOgre::TriangleGeometry* triangleGeometry = new NxOgre::TriangleGeometry(triangleMesh);
7. 将模型加入到场景
// 使用Convex作为外形,创建一个OGRE3DBody。
OGRE3DBody* convexBody = mRenderSystem->createBody(convex,NxOgre::Vec3(0,30,0),"Barrel.mesh");
convexBody->setGlobalOrientation(NxOgre::Matrix33(NxOgre::Vec4(0,45,0,45)));
// 通过TriangleGeometry,创建场景几何。
mScene->createSceneGeometry(triangleGeometry,NxOgre::Matrix44(NxOgre::Vec3(0,5,0)));
// 通过Entity,可视化创建的场景几何。
Ogre::Entity *triangleEntity = mSceneMgr->createEntity("trianlgeEntity","Stairs.mesh");
Ogre::SceneNode* triangleNode = mSceneMgr->getRootSceneNode()->createChildSceneNode();
triangleNode->attachObject(triangleEntity);
triangleNode->setPosition(Vector3(0,5,0));
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_7
http://blog.csdn.net/eplaylity/article/details/4726216
1. 去NV官网下载并安装PhysX的SDK。
(好像还要安装PhysX系统软件以便运行时需要,因为我前段时间安装了JX3,就不用了)
2. 设置PhysX SDK头文件及库的搜索路径设置环境变量PHYSX_DIR。
(我的是D:/Program Files/NVIDIA Corporation/NVIDIA PhysX SDK/v2.8.1)
因为要用到头文件搜素路径:
-SDKs/Physics/include
-SDKs/Foundation/include
-SDKs/Cooking/include
-SDKs/PhysXLoader/include
以及链接库搜索路径:
-SDKs/lib/win32
-SDKs/Physics/lib/win32/Release(无效)
-SDKs/Cooking/lib/win32/Release(无效)
3. 下载编译BloodyMess(最新版),或Bleeding(稳定版)
一共三个项目:
NxOgre
GLUTRenderSystem
OGRE3DRenderSystem
NxOgre是核心项目,后面两个是两个渲染系统特例。
1. 单位声明
NxOgre使用“米-千克-第二 系统”,以米为长度单位,千克为质量单位,秒为时间单位。
2. 初始化代码
2.1 最顶层类World,单实例。最大容纳32个Scene。不同场景之间的物体不能交互。
2.2 每个场景都有很多Actor,这个数目仅受限于你的机器配置。这些Actor在World中表现成一个物理对象,但他们都是不可见的。
想看到他们,需要使用一个Body,一个简单的Actor,它通过RenderSystem渲染到你的屏幕。
BloodyMess内建了几个渲染系统,包括OpenGL和Ogre,但这并不是要限制你创建自己的渲染系统。
2.3 NxOgre的另一个重要元素就是TimeController。它控制着World中的Actor所逝去的时间。
2.4 为了使用NxOgre及其指定的Ogre渲染类,头文件及链接库
#include <NxOgre.h>
#include <NxOgreOGRE3D.h>
NxOgre.lib
NxOgreOGRE3D.lib
2.5 在类的保护区域,声明世界、场景、和渲染系统的变量
NxOgre::World *mWorld;
NxOgre::Scene *mScene;
OGRE3DRenderSystem *mRenderSystem; // 并非属于NxOgre名称空间
2.6 在createScene()函数中初始化世界
mWorld = NxOgre::World::createWorld();
// 通过场景描述符,初始化场景
NxOgre::SceneDescription sceneDesc;
sceneDesc.mGravity = NxOgre::Vec3(0,-9.8f,0);
sceneDesc.mName = "BloodyMessTutorial2";
mScene = mWorld->createScene(sceneDesc);
// 指定一些应用到整个场景的默认物理量
mScene->getMaterial(0)->setStaticFriction(0.5); // 静摩擦系数
mScene->getMaterial(0)->setDynamicFriction(0.5); // 动摩擦系数
mScene->getMaterial(0)->setRestitution(0.1); // 恢复系数
mRenderSystem = new OGRE3DRenderSystem(mScene);
// 添加物体,外形为1x1x1的盒子,位置是Y正方向上20米
OGRE3DBody *mCube;
mCube = mRenderSystem->createBody(new NxOgre::Box(1,1,1),NxOgre::Vec3(0,20,0),"cube.1m.mesh");
2.7 获取运动需要每一帧都在FrameListener中advance我们的TimeController。
NxOgre::TimeController::getSingleton()->advance(evt.timeSinceLastFrame);
2.8 物理交互作用
OGRE3DBody *mCubeTwo;
mCubeTwo = mRenderSystem->createBody(new NxOgre::Box(1,1,1),NxOgre::Vec3(20,35,0),"cube.1m.mesh");
mCubeTwo->addForce(NxOgre::Vec3(-800,-200,0));
// 创建一个地面平面,这是一个actor,有无限尺寸,不能被移动
mScene->createSceneGeometry(new NxOgre::PlaneGeometry(0,NxOgre::Vec3(0,1,0)),Matrix44_Identity);
// 创建一个OGRE渲染的可见平面,因为NxOgre中的actor是不可见的
MovablePlane *plane = new MovablePlane("Plane");
plane->d = 0;
plane->normal = Vector3::UNIT_Y;
MeshManager::getSingleton().createPlane("PlaneMesh",ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME,
*plane,120,120,1,1,true,1,3,3,Vector3::UNIT_Z);
Entity *planeEnt = mSceneMgr->creatEntity("PlaneEntity","PlaneMesh");
planeEnt->setMaterialName("Examples/Rockwall");
SceneNode *mPlaneNode = mSceneMgr->getRootScenNode()->createChildSceneNode();
mPlaneNode->attachObject(planeEnt);
mPlaneNode->scale(100,100,100);
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_2
1. 一个全局的VisualDebugger实例,以RenderableType_VisualDebugger创建一个可渲染对象。
将此渲染对象绑定到一个SceneNode上,然后,每一帧VisualDebugger::draw()/SceneNode::needUpdate()
这个好像在OGRE3DRenderSystem的advance()里有封装。
2. SceneNode继承了Node的needUpdate()来标识这个节点及其父节点的状态更新。
3. 实现步骤
// 创建OGRE3DRenderable对象
new OGRE3DRenderable(NxOgre::Enums::RenderableType_VisualDebugger);
// 为可视化调试器设置可渲染对象,并将可渲染对象绑定到场景节点
NxOgre::VisualDebugger::setRenderable();
SceneNode::attachObject();
// 设置可视化调试器的可视化模式
VisualDebugger::setVisualisationMode(NxOgre::Enums::VisualDebugger_ShowAll);
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_3
1. Volume是一个任意形状的不可见的物理对象。并且不能动。常被用作trigger。
当一个物理对象进入/没入/离开它时,会触发一个程序指定的动作。
2. 在场景中创建一个Volume步骤
2.1 外形,比如,一个5x5x5的盒子
2.2 位置
2.3 一个Callback类的对象
2.4 回调行为(事件发生时调用onVolumeEvent())
NxOgre::Scene::createVolume(new NxOgre::Box(5),
NxOgre::Matrix44(NxOgre::Vec3(0,0,0)),
this,NxOgre::Enums::VolumeCollisionType_All);
3. 创建当一个Actor触发的回调函数
void onVolumeEvent(NxOgre::Volume* volume, NxOgre::Shape* volumeShape, NxOgre::RigidBody* rigidBody,
NxOgre::Shape* rigidBodyShape, unsigned int collisionEvent)
{
if(collisionEvent == NxOgre::Enums::VolumeCollisionType_OnEnter)
{
NxOgre::Actor* actor = static_cast<NxOgre::Actor*>(rigidBody);
float y = (9.81 * actor->getMass()) // 抵消重力
+ (-actor->getLinearVelocity().y * actor->getMass()) // 抵消竖直速度
+ (10 - actor->getGlobalPosition().y * actor->getMass()); // 添加一些向上移动的力
actor->addForce(NxOgre::Vec3(0, y, 0), NxOgre::Enums::ForceMode_Impulse);
}
}
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_4
1. Kinematics是些特殊的物理对象,它可以影响别的物体,却却不受别的物体影响。
他们可见、可移动,是升降机的一种最佳实现。
2. NxOgre中,Actor只是一个物理对象的物理表达,是不可见的。
然而,一个Body是一个Actor加上一个可视化的东西(比如,通过Ogre的Entity).
KinematicActor与KinematicBody也是同样的关系。
3. 移动、设置KinematicBody的位置
KinematicBody::moveGlobalPosition(NxOgre::Vec3&);
KinematicBody::setGlobalPosition(NxOgre::Vec3&);
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_5
1. 凸面体与三角网格
三角网格可以很完美地表现一个OGRE模型的物理外形。
OGRE模型和Flour所生成的三角网格就外形而言完全等同,
为了性能起见,一般使用凸面体做物理碰撞。
NxOgre中凸面体最多256个顶点,作为一个大包装盒把要进行碰撞检测的对象包围起来。
2. Flour是一个可以把OGRE模型转换成NxOgre格式的小工具。
包括,特殊的mesh、skeleton和heightfield。
3. 使用Flour生成.nxs文件
flour convert in:Stairs.mesh, into:triangle, out:Stairs.nxs
flour convert in:Barrel.mesh, into:convex, out:Barrel.nxs
4. BloodyMess使用自己的资源系统来处理所有类型的文档:文件夹、zip压缩文档、URL。
NxOgre::ResourceSystem::getSingleton()->openArchive("media","file:media");
NxOgre::ResourceSystem::getSingleton()->openArchive("media","file:D:/Projects/BloodyMess Tutorials/media");
(注意:文件路径可以使用相对或绝对路径,"/" 也可以用 "//"替换)
5. 使用资源系统加载模型
NxOgre::Mesh* convexMesh = NxOgre::MeshManager::getSingleton()->load("media:Barrel.nxs");
NxOgre::Mesh* triangleMesh = NxOgre::MesnManager::getSingleton()->load("media::Stairs.nxs");
6. 使用已加载的模型,创建凸面体和三角几何
NxOgre::Convex* convex = new NxOgre::Convex(convexMesh);
NxOgre::TriangleGeometry* triangleGeometry = new NxOgre::TriangleGeometry(triangleMesh);
7. 将模型加入到场景
// 使用Convex作为外形,创建一个OGRE3DBody。
OGRE3DBody* convexBody = mRenderSystem->createBody(convex,NxOgre::Vec3(0,30,0),"Barrel.mesh");
convexBody->setGlobalOrientation(NxOgre::Matrix33(NxOgre::Vec4(0,45,0,45)));
// 通过TriangleGeometry,创建场景几何。
mScene->createSceneGeometry(triangleGeometry,NxOgre::Matrix44(NxOgre::Vec3(0,5,0)));
// 通过Entity,可视化创建的场景几何。
Ogre::Entity *triangleEntity = mSceneMgr->createEntity("trianlgeEntity","Stairs.mesh");
Ogre::SceneNode* triangleNode = mSceneMgr->getRootSceneNode()->createChildSceneNode();
triangleNode->attachObject(triangleEntity);
triangleNode->setPosition(Vector3(0,5,0));
教程原文
http://www.ogre3d.org/wiki/index.php/BloodyMess_Tutorial_7