ogre3D学习基础17 --- 如何手动创建ogre程序

时间:2022-12-22 07:48:37

建立自己的Ogre程序

一直以来都是使用ExampleApplication.h来写程序,现在来看看它到底有什么神奇的地方。

  首先,我们新建一个win32空项目

  然后配置环境

  最后新建define.cpp、define.h、main.cpp

 具体过程如下

第一,在define.h中包含头文件,这里需要Orge.h文件,然后添加如下代码

#include "Ogre.h"

class MyApplication

{

public:

MyApplication();

~MyApplication();

void go();

protected:

bool setup();//设置环境

void setupResources();//设置资源

bool configure();//配置窗口

void chooseSceneManager();//选择场景

void createCamera();//创建摄像机

void createViewports();//创建视口

void loadResources();//加载资源

void createScene();//创建场景

void renderOneFrame();

private:

Ogre::Root*mRoot;//根节点

Ogre::RenderWindow*mWindow;//渲染窗口

Ogre::SceneManager*mSceneMgr;//场景管理器指针

Ogre::Camera*mCamera;//摄像机

bool mShutDowm;

};

第二,在define.cpp文件中定义函数,代码如下

 #include "define.h"

 MyApplication::MyApplication()//构造函数
{
mRoot = NULL;
mWindow = NULL;
mSceneMgr = NULL;
mCamera = NULL;
mWindow = NULL;
mShutDowm = false;
}
MyApplication::~MyApplication()//析构函数
{
if (mRoot)
{
delete mRoot;
}
}
bool MyApplication::setup()
{
mRoot = new Ogre::Root("plugins_d.cfg");
setupResources();
if (!configure())
{
return false;
}
chooseSceneManager();
createCamera();
createViewports();
loadResources();
createScene();
return true;
}
void MyApplication::setupResources()
{
// 加载资源,ConfigFile类是Ogre中用来读取和解析脚本使用的格式的
Ogre::ConfigFile cf;
cf.load("resources_d.cfg");
//循环遍历资源
Ogre::ConfigFile::SectionIterator seci = cf.getSectionIterator();// 获取迭代器
Ogre::String secName, typeName,archName;
while (seci.hasMoreElements())//组名
{
secName = seci.peekNextKey();
Ogre::ConfigFile::SettingsMultiMap *settings =seci.getNext();
Ogre::ConfigFile::SettingsMultiMap::iterator i;
for (i =settings->begin();i != settings->end(); ++i)
{
typeName = i->first;//键名
archName = i->second;//键值
Ogre::ResourceGroupManager::getSingleton().addResourceLocation(archName,typeName, secName);
}
}
}
bool MyApplication::configure()
{
if (!mRoot->showConfigDialog())//是否显示配置窗口
{
return false;
}
mWindow = mRoot->initialise(true,"IMedia Project");
return true;
}
void MyApplication::chooseSceneManager()
{
mSceneMgr = mRoot->createSceneManager(Ogre::ST_GENERIC);
}
void MyApplication::createCamera()
{
mCamera = mSceneMgr->createCamera("MyCamera");
mCamera->setPosition(Ogre::Vector3(,,));
mCamera->lookAt(Ogre::Vector3(,,-));
mCamera->setNearClipDistance();
}
void MyApplication::createViewports()
{
Ogre::Viewport*vp = mWindow->addViewport(mCamera);
vp->setBackgroundColour(Ogre::ColourValue(,,));
mCamera->setAspectRatio(Ogre::Real(vp->getActualWidth())/Ogre::Real(vp->getActualHeight()));
}
void MyApplication::loadResources()
{
Ogre::ResourceGroupManager::getSingleton().initialiseAllResourceGroups();
}
void MyApplication::createScene()
{
Ogre::Entity*ent = mSceneMgr->createEntity("Sinbad.mesh");
mSceneMgr->getRootSceneNode()->attachObject(ent);
}
void MyApplication::go()
{
if (!setup())
return;
mRoot->startRendering();
}

  在setup函数中完成了一系列的初始化操作,其中的setupResource()函数解释一下,ConfigFile类是Ogre中用来读取和解析脚本使用的格式的,我们用它来加载资源脚本,load函数定义如下:

   void load(const String& filename, const String& separators = "\t:=", bool trimWhitespace = true);//使用文件名加载文件

  接下来的while循环是循环,while循环负责组名的遍历,内部的for循环负责键名与键值的读取。

ogre3D学习基础17 --- 如何手动创建ogre程序

第三,我们在main.cpp文件中添加WinMain函数

 #include <windows.h>
#include "define.h" INT WINAPI WinMain( HINSTANCE hInst, HINSTANCE, LPSTR strCmdLine, INT )
{
MyApplication app;
app.go();
return ;
}

这里是我们所需要的最少的代码。如此就可以保证程序跑起来,但还需要继续改进。运行就可以看到结果。

现在我们试试把鼠标和键盘监听添加进去

第一添加新的父类,包含头文件OIS.h

class MyApplication:public Ogre::FrameListener,public OIS::KeyListener,public OIS::MouseListener

{

.......................

}

第二,添加成员函数以及成员变量

 Public:

 void createFrameListener(void);//创建帧监听器

 virtual bool frameRenderingQueued(const Ogre::FrameEvent& evt);//OGRE

 virtual bool keyPressed(const OIS::KeyEvent &arg);//ois key

 virtual bool keyReleased(const OIS::KeyEvent &arg);//key

 virtual bool mouseMoved( const OIS::MouseEvent &arg );//mouse

 virtual bool mousePressed( const OIS::MouseEvent &arg, OIS::MouseButtonID id );

 virtual bool mouseReleased( const OIS::MouseEvent &arg, OIS::MouseButtonID id );

 Private:

 OIS::InputManager *minputManager;//输入管理器

 OIS::Mouse *mMouse;//鼠标

 OIS::Keyboard *mKeyboard;//键盘

第三,函数定义,虚函数并没有添加其他代码,你可以直接添加需要的动作

 void MyApplication::createFrameListener()
{
OIS::ParamList pl;
size_t windowHnd = ;
std::ostringstream windowHndStr;
mWindow->getCustomAttribute("WINDOW", &windowHnd);//获取自己定义的属性
windowHndStr << windowHnd;
pl.insert(std::make_pair(std::string("WINDOW"), windowHndStr.str()));
minputManager = OIS::InputManager::createInputSystem( pl );//依照系统环境创建一个合适的输入系统
mKeyboard=static_cast<OIS::Keyboard*>(minputManager->createInputObject( OIS::OISKeyboard, true ));//创建输入对象
mMouse = static_cast<OIS::Mouse*>(minputManager->createInputObject( OIS::OISMouse, true )); mMouse->setEventCallback(this);
mKeyboard->setEventCallback(this);
mRoot->addFrameListener(this); }
bool MyApplication::frameRenderingQueued(const Ogre::FrameEvent& evt)
{
if (mWindow->isClosed())
{
return false;
}
if (mShutDowm)
{
return false;
}
mKeyboard->capture();
mMouse->capture();
return true;
}
bool MyApplication::keyPressed(const OIS::KeyEvent &arg)
{
if (arg.key == OIS::KC_ESCAPE)
{
mShutDowm = true;
}
return true;
}
bool MyApplication::keyReleased(const OIS::KeyEvent &arg)
{
return true;
}
bool MyApplication::mouseReleased( const OIS::MouseEvent &arg, OIS::MouseButtonID id )
{
return true;
}
bool MyApplication::mousePressed( const OIS::MouseEvent &arg, OIS::MouseButtonID id )
{
return true;
}
bool MyApplication::mouseMoved( const OIS::MouseEvent &arg )
{ return true;
}

代码解释:

这里看一下createFrameListener()函数,其中 ParamList是一个map类型,定义如下:

  typedef std::multimap<std::string, std::string> ParamList;

然后是创建输入对象,第一个参数指出了对象的类型

  Object* createInputObject( Type iType, bool bufferMode, const std::string &vendor = "");

 第四,记得在析构函数中清空对象

     if (minputManager)
{
minputManager->destroyInputObject(mKeyboard);
minputManager->destroyInputObject(mMouse);
OIS::InputManager::destroyInputSystem(minputManager);
minputManager = ;
}

  并在setup()函数中调用createFrameListener()函数

bool MyApplication::setup()
{
  .........
createFrameListener();//
return true;
}

 现在可以实现我们以前用ExampleApplication.h才能实现的功能了,ogre程序的运行过程就是这样。

 

ogre3D学习基础17 --- 如何手动创建ogre程序的更多相关文章

  1. ogre3D学习基础16 -- 手动创建实体&lpar;ManualObject&rpar;

    这一节练习一下手动创建实体,用到了对象(ManualObject) 第一,依然是模板 #include "ExampleApplication.h" class Example1 ...

  2. ogre3D学习基础18 -- 材质的使用与脚本的简单书写

    这一节以基础16为基础,练习材质的使用. 第一,看看框架 //material #include "ExampleApplication.h" class TutorialAppl ...

  3. ogre3D学习基础6---场景管理器的使用

    场景管理器的使用 最常使用的坐标系统空间(同时也是Ogre程序所能提供的)即是世界空间(World).父节点空间(Parent)以及本地空间(Local). 1.世界空间 就是物体所存在的地方,当我们 ...

  4. maven学习(二)——手动创建maven项目

    一.Maven的简单使用 1.Maven项目的目录约定 MavenProjectRoot(项目根目录)   |----src   |     |----main   |     |         | ...

  5. ogre3D学习基础15 -- 创建BSP Scene Manager

    BSP(binary-space partitioning) Scene Manager(二叉空间分割)场景管理器比较适合用于室内场景. 第一,添加框架代码如下 #include "Exam ...

  6. ogre3D学习基础5 -- 阴影与动画

    五.阴影 阴影是渲染一个真实场景的重要组成部分,它可以给场景中的物体提供更加真实的感觉,同时还可以帮助用户更好的了解对象间的空间关系. 启用阴影: 缺省情况下,阴影是关闭的,开启方式如下: 1.建立场 ...

  7. ogre3D学习基础1 -- 核心对象与脚本技术

    一.核心对象介绍1.命名空间 Ogre3d使用了C++的特性--命名空间,可以防止命名混淆.使用方法也简单,using namespace Ogre;或者直接在使用时加上“Ogre::”的前缀,如Og ...

  8. ogre3D学习基础13 -- 键盘控制网格动画mesh

    以上一节为蓝本,这里增加一点难度,添加了四个节点,增加键盘控制移动速度,使用bool变量控制是否移动. 第一,要增加键盘控制,那就使用OIS::KeyListener,在监听器里添加一个父类KeyLi ...

  9. ogre3D学习基础3 -- 粒子与表层脚本

    9.粒子脚本 粒子脚本允许你实例化地在你的脚本代码中定义粒子系统,而不必在源代码中进行设置,使得你做任何修改都能得到快速回应.脚本里定义的粒子系统被用作模板,并且多个实际的系统可以在运行时从这里被创建 ...

随机推荐

  1. Oracle TO&lowbar;DATE 日期格式

    Oracle trunc()函数的用法 --Oracle trunc()函数的用法/**************日期********************/1.select trunc(sysdat ...

  2. 应用程序框架实战三十四&colon;数据传输对象&lpar;DTO&rpar;介绍及各类型实体比较

    本文将介绍DDD分层架构中广泛使用的数据传输对象Dto,并且与领域实体Entity,查询实体QueryObject,视图实体ViewModel等几种实体进行比较. 领域实体为何不能一统江湖? 当你阅读 ...

  3. npm 初学者教程

    Node.js 让 JavaScript 编写服务器端应用程序成为可能.它建立在 JavaScript V8(C++ 编写的) 运行时之上,所以它很快.最初,它旨在为应用程序提供服务器环境,但是开发人 ...

  4. Java中引用类型变量,对象,值类型,值传递,引用传递 区别与定义

    一.Java中什么叫做引用类型变量?引用:就是按内存地址查询       比如:String s = new String();这个其实是在栈内存里分配一块内存空间为s,在堆内存里new了一个Stri ...

  5. meclipse中project facet问题

    meclipse中project facet问题 (2012-02-14 14:59:48) 转载▼ 标签: 杂谈 分类: 技术 一般出现在从别处import的项目上,只有项目文件夹上有红叉,其他地方 ...

  6. c&num; 网络是否连接

    c#  网络是否连接 方案一: using System; using System.Collections.Generic; using System.Linq; using System.Text ...

  7. CentOS6&period;6&lpar;单用户模式&rpar;重设root密码

    1.开机时手要快按任意键,因为默认时间5s 2.grub菜单,只有一个内核,没什么好上下选的,按e键.不过如果你升级了系统或安装了Xen虚拟化后,就会有多个显示了. 3.接下来显示如下,选择第二项,按 ...

  8. BZOJ 1565 植物大战僵尸

    http://www.lydsy.com/JudgeOnline/problem.php?id=1565 思路:由于植物之间有保护关系:(右边的植物保护左边的植物,植物攻击范围内的植物都被保护了),因 ...

  9. WCF服务

    一.新建windows服务       二.新建wcf服务      三.添加安装程序 四.设置安装程序 五.设置启动代码 6 7 8. 注:当使用管理员身份 安装不成功时,可以使用vs自带的命令工具 ...

  10. 什么是Bash Shell的内建&lpar;build in&rpar;命令

    1.什么是build in命令: shell内建命令是指bash(或其它版本)工具集中的命令.一般都会有一个与之同名的系统命令,比如bash中的echo命令与/bin/echo是两个不同的命令,尽管他 ...