fTerrainC.cpp 9.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307
  1. //---------------------------------------------------------------------------
  2. #include <vcl.h>
  3. #include <GLS.Keyboard.hpp>
  4. #include <stdlib.h>
  5. #pragma hdrstop
  6. #include "fTerrainC.h"
  7. //---------------------------------------------------------------------------
  8. #pragma package(smart_init)
  9. #pragma link "GLS.LensFlare"
  10. #pragma link "GLS.VectorGeometry"
  11. #pragma link "Sounds.BASS"
  12. #pragma link "GLS.Sound"
  13. #pragma link "GLS.SceneViewer"
  14. #pragma link "GLS.SkyDome"
  15. #pragma link "GLS.BitmapFont"
  16. #pragma link "GLS.HUDObjects"
  17. #pragma link "GLS.Texture"
  18. #pragma link "GLS.Cadencer"
  19. #pragma link "GLS.HeightData"
  20. #pragma link "GLS.Objects"
  21. #pragma link "GLS.TerrainRenderer"
  22. #pragma link "GLS.Scene"
  23. #pragma link "GLS.Keyboard"
  24. #pragma link "GLS.BaseClasses"
  25. #pragma link "GLS.Coordinates"
  26. #pragma link "GLS.Material"
  27. #pragma link "GLS.FileMP3"
  28. #pragma resource "*.dfm"
  29. TForm1 *Form1;
  30. float random(void)
  31. {
  32. return (float)(rand() & 0x1FFF) / (float)0x1FFF;
  33. }
  34. //---------------------------------------------------------------------------
  35. __fastcall TForm1::TForm1(TComponent * Owner):TForm(Owner)
  36. {
  37. SetGLSceneMediaDir();
  38. // 8 MB height data cache
  39. // Note this is the data size in terms of elevation samples, it does not
  40. // take into account all the data required/allocated by the renderer
  41. GLBitmapHDS1->MaxPoolSize = 8 * 1024 * 1024;
  42. // specify height map data
  43. GLBitmapHDS1->Picture->LoadFromFile("terrain.bmp");
  44. // load the texture maps
  45. GLMaterialLibrary1->Materials->Items[0]->Material->Texture->Image->
  46. LoadFromFile("snow512.jpg");
  47. GLMaterialLibrary1->Materials->Items[1]->Material->Texture->Image->
  48. LoadFromFile("detailmap.jpg");
  49. SPMoon->Material->Texture->Image->LoadFromFile("moon.bmp");
  50. SPSun->Material->Texture->Image->LoadFromFile("flare1.bmp");
  51. // apply texture map scale (our heightmap size is 256)
  52. TerrainRenderer1->TilesPerTexture = 256.0 / TerrainRenderer1->TileSize;
  53. // load Bitmap Font
  54. BitmapFont1->Glyphs->LoadFromFile("darkgold_font.bmp");
  55. // load and setup sound samples
  56. GLSoundLibrary->Samples->Add()->LoadFromFile("ChillyWind.mp3");
  57. GLSoundLibrary->Samples->Add()->LoadFromFile("howl.mp3");
  58. // Could've been done at design time, but then it hurts the eyes ;)
  59. GLSceneViewer1->Buffer->BackgroundColor = clWhite;
  60. // Move camera starting point to an interesting hand-picked location
  61. DummyCube1->Position->X = 570;
  62. DummyCube1->Position->Z = -385;
  63. DummyCube1->Turn(90);
  64. // Initial camera height offset (controled with pageUp/pageDown)
  65. FCamHeight = 10;
  66. randomize();
  67. }
  68. //---------------------------------------------------------------------------
  69. void __fastcall TForm1::GLCadencer1Progress(TObject * Sender,
  70. const double deltaTime,
  71. const double newTime)
  72. {
  73. float speed;
  74. // handle keypresses
  75. if(IsKeyDown(VK_SHIFT))
  76. speed = 5 * deltaTime;
  77. else
  78. speed = deltaTime;
  79. TGLCoordinates *c = GLCamera1->Position;
  80. if(IsKeyDown(VK_UP))
  81. DummyCube1->Translate(c->Z * speed, 0, -c->X * speed);
  82. if(IsKeyDown(VK_DOWN))
  83. DummyCube1->Translate(-c->Z * speed, 0, c->X * speed);
  84. if(IsKeyDown(VK_LEFT))
  85. DummyCube1->Translate(-c->X * speed, 0, -c->Z * speed);
  86. if(IsKeyDown(VK_RIGHT))
  87. DummyCube1->Translate(c->X * speed, 0, c->Z * speed);
  88. if(IsKeyDown(VK_PRIOR))
  89. FCamHeight = FCamHeight + 10 * speed;
  90. if(IsKeyDown(VK_NEXT))
  91. FCamHeight = FCamHeight - 10 * speed;
  92. if(IsKeyDown(VK_ESCAPE))
  93. Close();
  94. // don't drop through terrain!
  95. DummyCube1->Position->Y =
  96. TerrainRenderer1->InterpolatedHeight(DummyCube1->Position->AsVector) +
  97. FCamHeight;
  98. }
  99. //---------------------------------------------------------------------------
  100. void __fastcall TForm1::GLSceneViewer1MouseDown(TObject * Sender,
  101. TMouseButton Button,
  102. TShiftState Shift, int X, int Y)
  103. {
  104. my = Y;
  105. mx = X;
  106. }
  107. //---------------------------------------------------------------------------
  108. void __fastcall TForm1::GLSceneViewer1MouseMove(TObject * Sender,
  109. TShiftState Shift, int X, int Y)
  110. {
  111. if(Shift.Contains(ssLeft))
  112. {
  113. GLCamera1->MoveAroundTarget((my - Y) * 0.5, (mx - X) * 0.5);
  114. mx = X;
  115. my = Y;
  116. }
  117. }
  118. //---------------------------------------------------------------------------
  119. void __fastcall TForm1::Timer1Timer(TObject * Sender)
  120. {
  121. String s;
  122. // s.printf("%.1f FPS - %d", GLSceneViewer1->FramesPerSecond(),
  123. // TerrainRenderer1->LastTriangleCount());
  124. HUDText1->Text = s;
  125. GLSceneViewer1->ResetPerformanceMonitor();
  126. }
  127. //---------------------------------------------------------------------------
  128. void __fastcall TForm1::FormKeyPress(TObject * Sender, char &Key)
  129. {
  130. TGLMaterial *fp;
  131. TGLFogEnvironment *fe;
  132. TGIFColor Color;
  133. switch (Key)
  134. {
  135. case 'w':
  136. case 'W':
  137. fp = GLMaterialLibrary1->Materials->Items[0]->Material;
  138. if(fp->PolygonMode == pmLines)
  139. fp->PolygonMode = pmFill;
  140. else
  141. fp->PolygonMode = pmLines;
  142. break;
  143. case '+':
  144. if(GLCamera1->DepthOfView < 2000)
  145. {
  146. GLCamera1->DepthOfView = GLCamera1->DepthOfView * 1.2;
  147. fe = GLSceneViewer1->Buffer->FogEnvironment;
  148. fe->FogEnd = fe->FogEnd * 1.2;
  149. fe->FogStart = fe->FogStart * 1.2;
  150. }
  151. break;
  152. case '-':
  153. if(GLCamera1->DepthOfView > 300)
  154. {
  155. GLCamera1->DepthOfView = GLCamera1->DepthOfView / 1.2;
  156. fe = GLSceneViewer1->Buffer->FogEnvironment;
  157. fe->FogEnd = fe->FogEnd / 1.2;
  158. fe->FogStart = fe->FogStart / 1.2;
  159. }
  160. break;
  161. case '*':
  162. if(TerrainRenderer1->CLODPrecision > 20)
  163. TerrainRenderer1->CLODPrecision =
  164. RoundInt(TerrainRenderer1->CLODPrecision * 0.8);
  165. break;
  166. case '/':
  167. if(TerrainRenderer1->CLODPrecision < 1000)
  168. TerrainRenderer1->CLODPrecision =
  169. RoundInt(TerrainRenderer1->CLODPrecision * 1.2);
  170. break;
  171. case '8':
  172. if(TerrainRenderer1->QualityDistance > 40)
  173. TerrainRenderer1->QualityDistance =
  174. RoundInt(TerrainRenderer1->QualityDistance * 0.8);
  175. break;
  176. case '9':
  177. if(TerrainRenderer1->QualityDistance < 1000)
  178. TerrainRenderer1->QualityDistance =
  179. RoundInt(TerrainRenderer1->QualityDistance * 1.2);
  180. break;
  181. case 'n':
  182. case 'N':
  183. if(SkyDome1->Stars->Count == 0)
  184. {
  185. // turn on 'night' mode
  186. Color.Red = 0; Color.Green = 0; Color.Blue = 8;
  187. SkyDome1->Bands->Items[0]->StopColor->AsWinColor = TGIFColorMap::RGB2Color(Color);
  188. Color.Red = 0; Color.Green = 0; Color.Blue = 0;
  189. SkyDome1->Bands->Items[0]->StartColor->AsWinColor = TGIFColorMap::RGB2Color(Color);
  190. Color.Red = 0; Color.Green = 0; Color.Blue = 16;
  191. SkyDome1->Bands->Items[1]->StopColor->AsWinColor = TGIFColorMap::RGB2Color(Color);
  192. Color.Red = 0; Color.Green = 0; Color.Blue = 8;
  193. SkyDome1->Bands->Items[1]->StartColor->AsWinColor = TGIFColorMap::RGB2Color(Color);
  194. SkyDome1->Stars->AddRandomStars(700, clWhite, True); // many white stars
  195. Color.Red = 255; Color.Green = 100; Color.Blue = 100;
  196. SkyDome1->Stars->AddRandomStars(100, TGIFColorMap::RGB2Color(Color), True); // some redish ones
  197. Color.Red = 100; Color.Green = 100; Color.Blue = 255;
  198. SkyDome1->Stars->AddRandomStars(100, TGIFColorMap::RGB2Color(Color), True); // some blueish ones
  199. Color.Red = 255; Color.Green = 255; Color.Blue = 100;
  200. SkyDome1->Stars->AddRandomStars(100, TGIFColorMap::RGB2Color(Color), True); // some yellowish ones
  201. GLSceneViewer1->Buffer->BackgroundColor = clBlack;
  202. fe = GLSceneViewer1->Buffer->FogEnvironment;
  203. fe->FogColor->AsWinColor = clBlack;
  204. fe->FogStart = -fe->FogStart; // Fog is used to make things darker
  205. SPMoon->Visible = True;
  206. SPSun->Visible = False;
  207. GLLensFlare->Visible = False;
  208. }
  209. break;
  210. case 'd':
  211. case 'D':
  212. if(SkyDome1->Stars->Count > 0)
  213. {
  214. // turn on 'day' mode
  215. SkyDome1->Bands->Items[1]->StopColor->Color = clrNavy;
  216. SkyDome1->Bands->Items[1]->StartColor->Color = clrBlue;
  217. SkyDome1->Bands->Items[0]->StopColor->Color = clrBlue;
  218. SkyDome1->Bands->Items[0]->StartColor->Color = clrWhite;
  219. SkyDome1->Stars->Clear();
  220. GLSceneViewer1->Buffer->BackgroundColor = clWhite;
  221. fe = GLSceneViewer1->Buffer->FogEnvironment;
  222. fe->FogColor->AsWinColor = clWhite;
  223. fe->FogStart = -fe->FogStart;
  224. GLSceneViewer1->Buffer->FogEnvironment->FogStart = 0;
  225. SPMoon->Visible = False;
  226. SPSun->Visible = True;
  227. }
  228. break;
  229. case 't':
  230. if(SkyDome1->Options.Contains(sdoTwinkle))
  231. SkyDome1->Options = SkyDome1->Options << sdoTwinkle;
  232. else
  233. SkyDome1->Options = SkyDome1->Options >> sdoTwinkle;
  234. break;
  235. case 'l':
  236. GLLensFlare->Visible = (!GLLensFlare->Visible) && SPSun->Visible;
  237. }
  238. Key = '\0';
  239. }
  240. //---------------------------------------------------------------------------
  241. void __fastcall TForm1::TISoundTimer(TObject * Sender)
  242. {
  243. TGLVector wolfPos;
  244. float c, s;
  245. TGLBSoundEmitter *be;
  246. if(!GLSMBASS1->Active)
  247. return;
  248. if(SkyDome1->Stars->Count == 0)
  249. {
  250. // wind blows around camera
  251. be = GetOrCreateSoundEmitter(GLCamera1);
  252. be->Source->SoundLibrary = GLSoundLibrary;
  253. be->Source->SoundName = GLSoundLibrary->Samples->Items[0]->Name;
  254. be->Source->Volume = random() * 0.5 + 0.5;
  255. be->Playing = True;
  256. }
  257. else
  258. {
  259. // wolf howl at some distance, at ground level
  260. wolfPos = GLCamera1->AbsolutePosition;
  261. SinCosine(random() * Gls::Vectorgeometry::c2PI, 100 + random(1000), s, c);
  262. wolfPos.X = wolfPos.X + c;
  263. wolfPos.Z = wolfPos.Z + s;
  264. wolfPos.Y = TerrainRenderer1->InterpolatedHeight(wolfPos);
  265. DCSound->Position->AsVector = wolfPos;
  266. be = GetOrCreateSoundEmitter(DCSound);
  267. be->Source->SoundLibrary = GLSoundLibrary;
  268. be->Source->SoundName = GLSoundLibrary->Samples->Items[1]->Name;
  269. be->Source->MinDistance = 100;
  270. be->Source->MaxDistance = 4000;
  271. be->Playing = True;
  272. }
  273. TISound->Enabled = False;
  274. TISound->Interval = 10000 + random(10000);
  275. TISound->Enabled = True;
  276. }
  277. //---------------------------------------------------------------------------