Ogre 1.7中的地形教程

地形创建的工作步骤:

1.创建地形全局配置

2.创建地形分组

3.创建默认的地形分块属性

4.创建地形分块


第一步

首先,在Ogre1.7中,地形是由一块一块的地形组成的,他们每快地形都有共同的属性,所以在创建地形之前我们必须指定地形块的全局配置。

代码:

 

  1. mTerrainGlobals = new Ogre::TerrainGlobalOptions();   
  2. mTerrainGlobals->setMaxPixelError(8);   
  3. mTerrainGlobals->setCompositeMapDistance(3000);   
  4. mTerrainGlobals->setLightMapDirection(l->getDerivedDirection());   
  5. mTerrainGlobals->setCompositeMapAmbient(mSceneMgr->getAmbientLight());   
  6. mTerrainGlobals->setCompositeMapDiffuse(l->getDiffuseColour());   
  7. mTerrainGlobals->setLightMapSize(TERRAINWORLDSIZE);  

 

代码说明:

首先实例化一个TerrainGlobalOptions的全局对象

然后我们看几个主要属性

mTerrainGlobals->setLightMapDirection(l->getDerivedDirection());

//设置光线的方向,所有地形块均采用同一个方向的光
mTerrainGlobals->setCompositeMapAmbient(mSceneMgr->getAmbientLight());

//设置环境光
mTerrainGlobals->setCompositeMapDiffuse(l->getDiffuseColour());

//设置漫反射光
mTerrainGlobals->setLightMapSize(TERRAINWORLDSIZE);

//设置光线图的大小,这个数字越小,地图的阴影将越粗糙

其余的几个属性可保留此默认


第二步

我们将要创建地形分组对象,该对象用于创建以及管理地形块。

代码:

 

  1. mTerrainGroup = new Ogre::TerrainGroup(mSceneMgr, Ogre::Terrain::ALIGN_X_Z, TERRAINWORLDSIZE, TERRAINWORLDSIZE);   
  2. mTerrainGroup->setOrigin(Ogre::Vector3((float)TERRAINWORLDSIZE / 2.0f,0,(float)TERRAINWORLDSIZE / 2.0f));  

 

这段代码比较简单

首先是实例化一个TerrainGroup对象

并为他指定场管理器、地形的平铺方向、地形的大小

平铺方向一般采用ALIGN_X_Z,也就是采用Y作为高度

然后第二句设置了该地形组的起始位置,在以后创建的地形块中均采用此位置作为相对位置


第三步

有了地形分组之后,我们就可以通过地形分组创建地形块了,但是每一个地形块都有很多属性,我们可以在创建地形块的同时设置那些属性,但是这样极为不方便。所以,我们可以先设置默认的地形块属性,那么创建地形块的时候就可以一个方法搞定了

代码:

 

  1. ////设置地形默认属性   
  2. Ogre::Terrain::ImportData& defaultimp = mTerrainGroup->getDefaultImportSettings();   
  3. defaultimp.terrainSize = TERRAINWORLDSIZE;   
  4. defaultimp.worldSize = TERRAINWORLDSIZE;   
  5. defaultimp.inputScale = 1;   
  6. defaultimp.minBatchSize = 33;   
  7. defaultimp.maxBatchSize = 65;   
  8. //设置纹理    
  9. defaultimp.layerList.resize(1);   
  10. defaultimp.layerList[0].worldSize = BLENDMAPWORLDSIZE;   
  11. defaultimp.layerList[0].textureNames.push_back("DefaultTexture.jpg");   
  12. defaultimp.layerList[0].textureNames.push_back(DEFAULTNORMALMAP);  

 

这些属性都比较容易理解,设置地形大小,设置每个titles大小,设置bath相关,以及设置默认的纹理。


第四步

以上三步工作做好了之后,我们就可以很方便的创建地形块了

mTerrainGroup->defineTerrain(x, y,0.0f);

加上这句代码,你将会在你的场景中看到一块地形了

defineTerrain方法首先要指定该块地形在地形分组中的索引位置,然后第三个参数必须指定高度数据,这里我设置为0.0f,那么将是出现一个平面地形。


纹理混合

地形创建好之后,接下来再来给大家讲一下纹理混合的问题

Ogre1.7的地形纹理默认支持8层纹理混合,如果想更改,可通过地形的全局配置设置,混合越多越慢。

纹理混合包括两大步骤

1.设置纹理以及法线图

2.设置纹理混合的系数


首先先获取一个Terrain对象,可通过TerrainGroup的GetTerrainAt方法获取

那么我们可以对该Terrain对象进行纹理控制

比如新增一层纹理

代码:

 

  1. Ogre::StringVector vTextures;   
  2. vTextures.push_back(textureName);   
  3. Ogre::String fName = textureName.substr(0,textureName.find_first_of("."));   
  4. vTextures.push_back(fName + _S("_normalheight.dds"));   
  5. terrain->addLayer(k,BLENDMAPWORLDSIZE,&vTextures);  

 

这段代码非常简单,知道stl估计都看得懂。vTextures的第一个元素代表纹理图本身,第二个元素代表法线图。法线可以为纹理增加凹凸不平的效果。

那么通过以上方式,增加了N层纹理之后,你可能发现“为什么只显示第一层纹理啊?其他新增的问题怎么不显示了?”,那是因为你还没有为他指定混合系数

一张纹理,贴在地形上,你必须指定他的纹理可见度。比如我的一个地形,我需要在左边显示A纹理,右边显示B纹理,那也就是说A纹理的左边设置为可见,B纹理的右边设置为可见。那如何做到这一点呢?

首先看一小段代码

 

  1. Ogre::TerrainLayerBlendMap* blendMap = terrain->getLayerBlendMap(l);   
  2. float* data = blendMap->getBlendPointer();   
  3. for (int h = 0;h<100;h++)   
  4. {   
  5.     for (int 0;w<100;w++)   
  6.     {   
  7.         data[dataIndex] = 0.0f;   
  8.     }   
  9. }   
  10. blendMap->dirty();   
  11. blendMap->update();  

 

看开始两句,获取了Terrain的第X层纹理,然后获取了纹理系数data,然后我们把高100宽100的位置的混合系数设置为0,即不可见,混合系数取值为0~1之间,系数越大纹理越清晰,故0就是一点都不可见。

改变纹理系数之后,再更新了一下纹理。

当这段代码执行以后,你会发现你的地形纹理上出现了一个100X100的白色正方形,明白了吧,纹理系数就是这么简单,多层纹理的时候必须为每层纹理设置系数。

今天的文章先简单写到这里,如果还有不明白的请QQ81786254或者Email:is-dragon@hotmail.com询问。

文章任何信息均由本博原创,转载请注明出处!

转载于:https://www.cnblogs.com/lancidie/archive/2011/06/19/2084490.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值