GLES drivers adapted, but only did make compile-tests. git-svn-id: svn://svn.code.sf.net/p/irrlicht/code/branches/ogl-es@6038 dfc29bdd-3216-0410-991c-e03cc46cb475
		
			
				
	
	
		
			123 lines
		
	
	
		
			12 KiB
		
	
	
	
		
			HTML
		
	
	
	
	
	
			
		
		
	
	
			123 lines
		
	
	
		
			12 KiB
		
	
	
	
		
			HTML
		
	
	
	
	
	
| <html>
 | |
| <head>
 | |
| <title>Irrlicht Engine Tutorial</title>
 | |
| <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
 | |
| </head>
 | |
| 
 | |
| <body bgcolor="#FFFFFF" leftmargin="0" topmargin="0" marginwidth="0" marginheight="0">
 | |
| <br>
 | |
| <table width="95%" border="0" cellspacing="0" cellpadding="2" align="center">
 | |
|   <tr> 
 | |
|     <td bgcolor="#666699" width="10"><b><a href="http://irrlicht.sourceforge.net" target="_blank"><img src="../../media/irrlichtlogo.jpg" width="88" height="31" border="0"></a></b></td>
 | |
|     <td bgcolor="#666699" width="100%">
 | |
| <div align="center">
 | |
|         <div align="left"><b><font color="#FFFFFF">Tutorial 12. Terrain Rendering</font></b></div>
 | |
|       </div>
 | |
|       </td>
 | |
|   </tr>
 | |
|   <tr bgcolor="#eeeeff"> 
 | |
|     <td height="90" colspan="2"> 
 | |
|       <div align="left"> 
 | |
|         <p> This tutorial will briefly show how to use the terrain renderer of 
 | |
|           Irrlicht. It will also show the terrain renderer triangle selector to 
 | |
|           be able to do collision detection with terrain.</p>
 | |
|         <p>The program which is described here will look like this:</p>
 | |
|         <p align="center"><img src="../../media/012shot.jpg" width="258" height="202"></p>
 | |
|         <p align="left"><br>
 | |
|           Note that the terrain renderer in Irrlicht is based the terrain renderer 
 | |
|           by Soconne and the GeoMipMapSceneNode developed by Spinz, lots of thanks 
 | |
|           go to them.</p>
 | |
|       </div>
 | |
|     </td>
 | |
|   </tr>
 | |
| </table>
 | |
| <br>
 | |
| <table width="95%" border="0" cellspacing="0" cellpadding="2" align="center">
 | |
|   <tr> 
 | |
|     <td bgcolor="#666699"> <b><font color="#FFFFFF">Lets start!</font></b></td>
 | |
|   </tr>
 | |
|   <tr> 
 | |
|     <td height="90" bgcolor="#eeeeff" valign="top"> <div align="left"> 
 | |
|         <div align="left"> 
 | |
|           <p> In the beginning there is nothing special. We include the needed 
 | |
|             header files and create an event listener to listen if the user presses 
 | |
|             the 'W' key so we can switch to wireframe mode and if he presses 'D' 
 | |
|             we toggle to material between solid and detail mapped.</p>
 | |
|           <table width="95%" border="0" cellspacing="2" cellpadding="0" bgcolor="#CCCCCC" align="center">
 | |
|             <tr> 
 | |
|               <td> <pre>#include <irrlicht.h><br>#include <iostream><br>using namespace irr;<br><br>#pragma comment(lib, "Irrlicht.lib")<br><br>class MyEventReceiver : public IEventReceiver<br>{<br>public:<br>	MyEventReceiver(scene::ISceneNode* terrain)<br>	{<br><font color="#006600">		// store pointer to terrain so we can change its drawing mode<br></font>		Terrain = terrain;<br>	}<br><br>	bool OnEvent(const SEvent& event)<br>	{<br>	<font color="#006600">	// check if user presses the key 'W' or 'D'</font><br>		if (event.EventType == irr::EET_KEY_INPUT_EVENT && !event.KeyInput.PressedDown)<br>		{<br>			switch (event.KeyInput.Key)<br>			{<br>			case irr::KEY_KEY_W:<font color="#006600"> // switch wire frame mode</font><br>				Terrain->setMaterialFlag(video::EMF_WIREFRAME, !Terrain->getMaterial(0).Wireframe);<br>				return true;<br>			case irr::KEY_KEY_D:<font color="#006600"> // toggle detail map</font><br>				Terrain->setMaterialType(<br>					Terrain->getMaterial(0).MaterialType == video::EMT_SOLID ? <br>					video::EMT_DETAIL_MAP : video::EMT_SOLID);<br>				return true;<br>			}<br>		}<br>		return false;<br>	}<br><br>private:<br>	scene::ISceneNode* Terrain;<br>};<br><br></pre></td>
 | |
|             </tr>
 | |
|           </table>
 | |
|           <p>The start of the main function starts like in most other example. 
 | |
|             We ask the user for the desired renderer and start it up. </p>
 | |
|           <table width="95%" border="0" cellspacing="2" cellpadding="0" bgcolor="#CCCCCC" align="center">
 | |
|             <tr> 
 | |
|               <td> <pre>int main()<br>{<br><font color="#006600">	// let user select driver type<br></font><br>	video::E_DRIVER_TYPE driverType = video::EDT_DIRECT3D9;<br><br>	printf("Please select the driver you want for this example:\n"\<br>		" (a) Direct3D 9.0c\n (b) Direct3D 8.1\n (c) OpenGL 1.5\n"\<br>		" (d) Software Renderer\n (e) Apfelbaum Software Renderer\n"\<br>		" (f) NullDevice\n (otherKey) exit\n\n");<br><br>	char i;<br>	std::cin >> i;<br><br>	switch(i)<br>	{<br>		case 'a': driverType = video::EDT_DIRECT3D9;break;<br>		case 'b': driverType = video::EDT_DIRECT3D8;break;<br>		case 'c': driverType = video::EDT_OPENGL;   break;<br>		case 'd': driverType = video::EDT_SOFTWARE; break;<br>		case 'e': driverType = video::EDT_BURNINGSVIDEO;break;<br>		case 'f': driverType = video::EDT_NULL;     break;<br>		default: return 1;<br>	}	<br><font color="#006600"><br>	// create device<br></font>	IrrlichtDevice* device = createDevice(driverType, core::dimension2d<s32>(640, 480));<br><br>	if (device == 0)<br>		return 1; <font color="#006600">// could not create selected driver.</font><br></pre></td>
 | |
|             </tr>
 | |
|           </table>
 | |
|           <p> First, we add standard stuff to the scene: A nice irrlicht engine 
 | |
|             logo, a small help text, a user controlled camera, and we disable 
 | |
|             the mouse cursor.</p>
 | |
|           <table width="95%" border="0" cellspacing="2" cellpadding="0" bgcolor="#CCCCCC" align="center">
 | |
|             <tr> 
 | |
|               <td> <pre>video::IVideoDriver* driver = device->getVideoDriver();<br>scene::ISceneManager* smgr = device->getSceneManager();<br>gui::IGUIEnvironment* env = device->getGUIEnvironment();<br><br>driver->setTextureCreationFlag(video::ETCF_ALWAYS_32_BIT, true);<br><br><font color="#006600">// add irrlicht logo<br></font>env->addImage(driver->getTexture("../../media/irrlichtlogoalpha.tga"),<br>    core::position2d<s32>(10,10));<br>
 | |
| <font color="#006600">// add some help text<br></font>gui::IGUIStaticText* text = env->addStaticText(<br>	L"Press 'W' to change wireframe mode\nPress 'D' to toggle detail map",<br>	core::rect<s32>(10,453,200,475), true, true, 0, -1, true);<br>
 | |
| <font color="#006600">// add camera<br></font>scene::ICameraSceneNode* camera = <br>    smgr->addCameraSceneNodeFPS(0,100.0f,1200.0f);<br>camera->setPosition(core::vector3df(1900*2,255*2,3700*2));<br>camera->setTarget(core::vector3df(2397*2,343*2,2700*2));<br>camera->setFarValue(12000.0f);<br><br><font color="#006600">// disable mouse cursor<br></font>device->getCursorControl()->setVisible(false);</pre></td>
 | |
|             </tr>
 | |
|           </table>
 | |
|           <p> Here comes the terrain renderer scene node: We add it just like 
 | |
|             any other scene node to the scene using ISceneManager::addTerrainSceneNode(). 
 | |
|             The only parameter we use is a file name to the heightmap we use. 
 | |
|             A heightmap is simply a gray scale texture. The terrain renderer loads 
 | |
|             it and creates the 3D terrain from it.<br>
 | |
|             To make the terrain look more big, we change the scale factor of it 
 | |
|             to (40, 4.4, 40). Because we don't have any dynamic lights in the 
 | |
|             scene, we switch off the lighting, and we set the file terrain-texture.jpg 
 | |
|             as texture for the terrain and detailmap3.jpg as second texture, called 
 | |
|             detail map. At last, we set the scale values for the texture: The 
 | |
|             first texture will be repeated only one time over the whole terrain, 
 | |
|             and the second one (detail map) 20 times. </p>
 | |
|           <table width="95%" border="0" cellspacing="2" cellpadding="0" bgcolor="#CCCCCC" align="center">
 | |
|             <tr> 
 | |
|               <td> <pre><font color="#006600">// add terrain scene node<br></font>scene::ITerrainSceneNode* terrain = smgr->addTerrainSceneNode( <br>      "../../media/terrain-heightmap.bmp");<br><br>terrain->setScale(core::vector3df(40, 4.4f, 40));<br>terrain->setMaterialFlag(video::EMF_LIGHTING, false);<br><br>terrain->setMaterialTexture(0, driver->getTexture("../../media/terrain-texture.jpg"));<br>terrain->setMaterialTexture(1, driver->getTexture("../../media/detailmap3.jpg"));<br>	<br>terrain->setMaterialType(video::EMT_DETAIL_MAP);<br>terrain->scaleTexture(1.0f, 20.0f);<font color="#006600"><br></font></pre></td>
 | |
|             </tr>
 | |
|           </table>
 | |
|           <p> To be able to do collision with the terrain, we create a triangle 
 | |
|             selector. If you want to know what triangle selectors do, just take 
 | |
|             a look into the collision tutorial. The terrain triangle selector 
 | |
|             works together with the terrain. To demonstrate this, we create a 
 | |
|             collision response animator and attach it to the camera, so that the 
 | |
|             camera will not be able to fly through the terrain. </p>
 | |
|         </div>
 | |
|         <table width="95%" border="0" cellspacing="2" cellpadding="0" bgcolor="#CCCCCC" align="center">
 | |
|           <tr> 
 | |
|             <td> <pre><font color="#006600">// create triangle selector for the terrain	<br></font>scene::ITriangleSelector* selector =<br>    smgr->createTerrainTriangleSelector(terrain, 0);<br>terrain->setTriangleSelector(selector);<br><br><font color="#006600">// create collision response animator and attach it to the camera<br></font>scene::ISceneNodeAnimator* anim = smgr->createCollisionResponseAnimator(<br>	selector, camera, core::vector3df(60,100,60),<br>	core::vector3df(0,0,0), <br>	core::vector3df(0,50,0));<br>selector->drop();<br>camera->addAnimator(anim);<br>anim->drop();</pre></td>
 | |
|           </tr>
 | |
|         </table>
 | |
|         <p> To make the user be able to switch between normal and wireframe mode, 
 | |
|           we create an instance of the event reciever from above and let Irrlicht 
 | |
|           know about it. In addition, we add the skybox which we already used 
 | |
|           in lots of Irrlicht examples.</p>
 | |
|         <table width="95%" border="0" cellspacing="2" cellpadding="0" bgcolor="#CCCCCC" align="center">
 | |
|           <tr> 
 | |
|             <td><pre><font color="#006600">// create event receiver<br></font>MyEventReceiver receiver(terrain);<br>device->setEventReceiver(&receiver);<br><br><font color="#006600">// create skybox<br></font>driver->setTextureCreationFlag(video::ETCF_CREATE_MIP_MAPS, false);<br><br>smgr->addSkyBoxSceneNode(<br>	driver->getTexture("../../media/irrlicht2_up.jpg"),<br>	driver->getTexture("../../media/irrlicht2_dn.jpg"),<br>	driver->getTexture("../../media/irrlicht2_lf.jpg"),<br>	driver->getTexture("../../media/irrlicht2_rt.jpg"),<br>	driver->getTexture("../../media/irrlicht2_ft.jpg"),<br>	driver->getTexture("../../media/irrlicht2_bk.jpg"));<br>
 | |
| driver->setTextureCreationFlag(video::ETCF_CREATE_MIP_MAPS, true);<br></pre></td>
 | |
|           </tr>
 | |
|         </table>
 | |
|         <p> That's it, draw everything. Now you know how to use terrain in Irrlicht.</p>
 | |
|         <table width="95%" border="0" cellspacing="2" cellpadding="0" bgcolor="#CCCCCC" align="center">
 | |
|           <tr> 
 | |
|             <td><pre>	int lastFPS = -1;<br><br>	while(device->run())<br>	if (device->isWindowActive())<br>	{<br>		driver->beginScene(true, true, 0 );<br><br>		smgr->drawAll();<br>		env->drawAll();<br><br>		driver->endScene();
 | |
| <br><font color="#006600">		// display frames per second in window title
 | |
| </font>		int fps = driver->getFPS();<br><br>		if (lastFPS != fps)<br>		{<br>			core::stringw str = L"Terrain Renderer - Irrlicht Engine [";<br>			str += driver->getName();<br>			str += "] FPS:";<br>			str += fps;<br>			device->setWindowCaption(str.c_str());<br>			lastFPS = fps;<br>		}<br>	}<br><br>	device->drop();<br>	<br>	return 0;<br>}</pre></td>
 | |
|           </tr>
 | |
|         </table>
 | |
|         <p>  </p>
 | |
|       </div>
 | |
|       </td>
 | |
|   </tr>
 | |
| </table>
 | |
| <p> </p>
 | |
|       </body>
 | |
| </html>
 |