1 /* Copyright (C) 2017 Wildfire Games. 2 * This file is part of 0 A.D. 3 * 4 * 0 A.D. is free software: you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License as published by 6 * the Free Software Foundation, either version 2 of the License, or 7 * (at your option) any later version. 8 * 9 * 0 A.D. is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with 0 A.D. If not, see <http://www.gnu.org/licenses/>. 16 */ 17 18 /* 19 * higher level interface on top of OpenGL to render basic objects: 20 * terrain, models, sprites, particles etc. 21 */ 22 23 #ifndef INCLUDED_RENDERER 24 #define INCLUDED_RENDERER 25 26 #include "graphics/Camera.h" 27 #include "graphics/SColor.h" 28 #include "graphics/ShaderProgramPtr.h" 29 #include "lib/file/vfs/vfs_path.h" 30 #include "lib/res/handle.h" 31 #include "ps/Singleton.h" 32 33 #include "graphics/ShaderDefines.h" 34 #include "renderer/Scene.h" 35 36 // necessary declarations 37 class CFontManager; 38 class CLightEnv; 39 class CMaterial; 40 class CMaterialManager; 41 class CModel; 42 class CParticleManager; 43 class CPatch; 44 class CPostprocManager; 45 class CShaderManager; 46 class CSimulation2; 47 class CTextureManager; 48 class CTimeManager; 49 class RenderPathVertexShader; 50 class ShadowMap; 51 class SkyManager; 52 class TerrainRenderer; 53 class WaterManager; 54 55 // rendering modes 56 enum ERenderMode { WIREFRAME, SOLID, EDGED_FACES }; 57 58 // transparency modes 59 enum ETransparentMode { TRANSPARENT, TRANSPARENT_OPAQUE, TRANSPARENT_BLEND }; 60 61 // access to sole renderer object 62 #define g_Renderer CRenderer::GetSingleton() 63 64 /////////////////////////////////////////////////////////////////////////////////////////// 65 // CRenderer: base renderer class - primary interface to the rendering engine 66 struct CRendererInternals; 67 68 class CRenderer : 69 public Singleton<CRenderer>, 70 private SceneCollector 71 { 72 public: 73 // various enumerations and renderer related constants 74 enum { NumAlphaMaps=14 }; 75 enum Option { 76 OPT_NOVBO, 77 OPT_SHADOWS, 78 OPT_WATEREFFECTS, 79 OPT_WATERFANCYEFFECTS, 80 OPT_WATERREALDEPTH, 81 OPT_WATERREFLECTION, 82 OPT_WATERREFRACTION, 83 OPT_SHADOWSONWATER, 84 OPT_SHADOWPCF, 85 OPT_PARTICLES, 86 OPT_PREFERGLSL, 87 OPT_FOG, 88 OPT_SILHOUETTES, 89 OPT_SHOWSKY, 90 OPT_SMOOTHLOS, 91 OPT_POSTPROC, 92 OPT_DISPLAYFRUSTUM, 93 }; 94 95 enum CullGroup { 96 CULL_DEFAULT, 97 CULL_SHADOWS, 98 CULL_REFLECTIONS, 99 CULL_REFRACTIONS, 100 CULL_SILHOUETTE_OCCLUDER, 101 CULL_SILHOUETTE_CASTER, 102 CULL_MAX 103 }; 104 105 enum RenderPath { 106 // If no rendering path is configured explicitly, the renderer 107 // will choose the path when Open() is called. 108 RP_DEFAULT, 109 110 // Classic fixed function. 111 RP_FIXED, 112 113 // Use new ARB/GLSL system 114 RP_SHADER 115 }; 116 117 // stats class - per frame counts of number of draw calls, poly counts etc 118 struct Stats { 119 // set all stats to zero ResetStats120 void Reset() { memset(this, 0, sizeof(*this)); } 121 // number of draw calls per frame - total DrawElements + Begin/End immediate mode loops 122 size_t m_DrawCalls; 123 // number of terrain triangles drawn 124 size_t m_TerrainTris; 125 // number of water triangles drawn 126 size_t m_WaterTris; 127 // number of (non-transparent) model triangles drawn 128 size_t m_ModelTris; 129 // number of overlay triangles drawn 130 size_t m_OverlayTris; 131 // number of splat passes for alphamapping 132 size_t m_BlendSplats; 133 // number of particles 134 size_t m_Particles; 135 }; 136 137 // renderer options 138 struct Options { 139 bool m_NoVBO; 140 bool m_Shadows; 141 142 bool m_WaterEffects; 143 bool m_WaterFancyEffects; 144 bool m_WaterRealDepth; 145 bool m_WaterRefraction; 146 bool m_WaterReflection; 147 bool m_WaterShadows; 148 149 RenderPath m_RenderPath; 150 bool m_ShadowAlphaFix; 151 bool m_ARBProgramShadow; 152 bool m_ShadowPCF; 153 bool m_Particles; 154 bool m_PreferGLSL; 155 bool m_ForceAlphaTest; 156 bool m_GPUSkinning; 157 bool m_Fog; 158 bool m_Silhouettes; 159 bool m_SmoothLOS; 160 bool m_ShowSky; 161 bool m_Postproc; 162 bool m_DisplayFrustum; 163 } m_Options; 164 165 struct Caps { 166 bool m_VBO; 167 bool m_ARBProgram; 168 bool m_ARBProgramShadow; 169 bool m_VertexShader; 170 bool m_FragmentShader; 171 bool m_Shadows; 172 bool m_PrettyWater; 173 }; 174 175 public: 176 // constructor, destructor 177 CRenderer(); 178 ~CRenderer(); 179 180 // open up the renderer: performs any necessary initialisation 181 bool Open(int width,int height); 182 183 // resize renderer view 184 void Resize(int width,int height); 185 186 // set/get boolean renderer option 187 void SetOptionBool(enum Option opt, bool value); 188 bool GetOptionBool(enum Option opt) const; 189 void SetRenderPath(RenderPath rp); GetRenderPath()190 RenderPath GetRenderPath() const { return m_Options.m_RenderPath; } 191 static CStr GetRenderPathName(RenderPath rp); 192 static RenderPath GetRenderPathByName(const CStr& name); 193 194 // return view width GetWidth()195 int GetWidth() const { return m_Width; } 196 // return view height GetHeight()197 int GetHeight() const { return m_Height; } 198 // return view aspect ratio GetAspect()199 float GetAspect() const { return float(m_Width)/float(m_Height); } 200 201 // signal frame start 202 void BeginFrame(); 203 // signal frame end 204 void EndFrame(); 205 206 /** 207 * Set simulation context for rendering purposes. 208 * Must be called at least once when the game has started and before 209 * frames are rendered. 210 */ 211 void SetSimulation(CSimulation2* simulation); 212 213 // set color used to clear screen in BeginFrame() 214 void SetClearColor(SColor4ub color); 215 216 // trigger a reload of shaders (when parameters they depend on have changed) 217 void MakeShadersDirty(); 218 219 /** 220 * Set up the camera used for rendering the next scene; this includes 221 * setting OpenGL state like viewport, projection and modelview matrices. 222 * 223 * @param viewCamera this camera determines the eye position for rendering 224 * @param cullCamera this camera determines the frustum for culling in the renderer and 225 * for shadow calculations 226 */ 227 void SetSceneCamera(const CCamera& viewCamera, const CCamera& cullCamera); 228 229 // set the viewport 230 void SetViewport(const SViewPort &); 231 232 // get the last viewport 233 SViewPort GetViewport(); 234 235 /** 236 * Render the given scene immediately. 237 * @param scene a Scene object describing what should be rendered. 238 */ 239 void RenderScene(Scene& scene); 240 241 /** 242 * Return the scene that is currently being rendered. 243 * Only valid when the renderer is in a RenderScene call. 244 */ 245 Scene& GetScene(); 246 247 /** 248 * Render text overlays on top of the scene. 249 * Assumes the caller has set up the GL environment for orthographic rendering 250 * with texturing and blending. 251 */ 252 void RenderTextOverlays(); 253 254 // set the current lighting environment; (note: the passed pointer is just copied to a variable within the renderer, 255 // so the lightenv passed must be scoped such that it is not destructed until after the renderer is no longer rendering) SetLightEnv(CLightEnv * lightenv)256 void SetLightEnv(CLightEnv* lightenv) { 257 m_LightEnv=lightenv; 258 } 259 260 // set the mode to render subsequent terrain patches SetTerrainRenderMode(ERenderMode mode)261 void SetTerrainRenderMode(ERenderMode mode) { m_TerrainRenderMode = mode; } 262 // get the mode to render subsequent terrain patches GetTerrainRenderMode()263 ERenderMode GetTerrainRenderMode() const { return m_TerrainRenderMode; } 264 265 // set the mode to render subsequent water patches SetWaterRenderMode(ERenderMode mode)266 void SetWaterRenderMode(ERenderMode mode) { m_WaterRenderMode = mode; } 267 // get the mode to render subsequent water patches GetWaterRenderMode()268 ERenderMode GetWaterRenderMode() const { return m_WaterRenderMode; } 269 270 // set the mode to render subsequent models SetModelRenderMode(ERenderMode mode)271 void SetModelRenderMode(ERenderMode mode) { m_ModelRenderMode = mode; } 272 // get the mode to render subsequent models GetModelRenderMode()273 ERenderMode GetModelRenderMode() const { return m_ModelRenderMode; } 274 275 // debugging SetDisplayTerrainPriorities(bool enabled)276 void SetDisplayTerrainPriorities(bool enabled) { m_DisplayTerrainPriorities = enabled; } 277 278 // bind a GL texture object to active unit 279 void BindTexture(int unit, unsigned int tex); 280 281 // load the default set of alphamaps. 282 // return a negative error code if anything along the way fails. 283 // called via delay-load mechanism. 284 int LoadAlphaMaps(); 285 void UnloadAlphaMaps(); 286 287 // return stats accumulated for current frame GetStats()288 Stats& GetStats() { return m_Stats; } 289 290 // return the current light environment GetLightEnv()291 const CLightEnv &GetLightEnv() { return *m_LightEnv; } 292 293 // return the current view camera GetViewCamera()294 const CCamera& GetViewCamera() const { return m_ViewCamera; } 295 // replace the current view camera SetViewCamera(const CCamera & camera)296 void SetViewCamera(const CCamera& camera) { m_ViewCamera = camera; } 297 298 // return the current cull camera GetCullCamera()299 const CCamera& GetCullCamera() const { return m_CullCamera; } 300 301 /** 302 * GetWaterManager: Return the renderer's water manager. 303 * 304 * @return the WaterManager object used by the renderer 305 */ GetWaterManager()306 WaterManager* GetWaterManager() { return m_WaterManager; } 307 308 /** 309 * GetSkyManager: Return the renderer's sky manager. 310 * 311 * @return the SkyManager object used by the renderer 312 */ GetSkyManager()313 SkyManager* GetSkyManager() { return m_SkyManager; } 314 315 CTextureManager& GetTextureManager(); 316 317 CShaderManager& GetShaderManager(); 318 319 CParticleManager& GetParticleManager(); 320 321 TerrainRenderer& GetTerrainRenderer(); 322 323 CMaterialManager& GetMaterialManager(); 324 325 CFontManager& GetFontManager(); 326 GetSystemShaderDefines()327 CShaderDefines GetSystemShaderDefines() { return m_SystemShaderDefines; } 328 329 CTimeManager& GetTimeManager(); 330 331 CPostprocManager& GetPostprocManager(); 332 333 /** 334 * GetCapabilities: Return which OpenGL capabilities are available and enabled. 335 * 336 * @return capabilities structure 337 */ GetCapabilities()338 const Caps& GetCapabilities() const { return m_Caps; } 339 340 ShadowMap& GetShadowMap(); 341 342 /** 343 * Resets the render state to default, that was before a game started 344 */ 345 void ResetState(); 346 347 protected: 348 friend struct CRendererInternals; 349 friend class CVertexBuffer; 350 friend class CPatchRData; 351 friend class CDecalRData; 352 friend class FixedFunctionModelRenderer; 353 friend class ModelRenderer; 354 friend class PolygonSortModelRenderer; 355 friend class SortModelRenderer; 356 friend class RenderPathVertexShader; 357 friend class HWLightingModelRenderer; 358 friend class ShaderModelVertexRenderer; 359 friend class InstancingModelRenderer; 360 friend class ShaderInstancingModelRenderer; 361 friend class TerrainRenderer; 362 friend class WaterRenderer; 363 364 //BEGIN: Implementation of SceneCollector 365 void Submit(CPatch* patch); 366 void Submit(SOverlayLine* overlay); 367 void Submit(SOverlayTexturedLine* overlay); 368 void Submit(SOverlaySprite* overlay); 369 void Submit(SOverlayQuad* overlay); 370 void Submit(CModelDecal* decal); 371 void Submit(CParticleEmitter* emitter); 372 void Submit(SOverlaySphere* overlay); 373 void SubmitNonRecursive(CModel* model); 374 //END: Implementation of SceneCollector 375 376 // render any batched objects 377 void RenderSubmissions(const CBoundingBoxAligned& waterScissor); 378 379 // patch rendering stuff 380 void RenderPatches(const CShaderDefines& context, int cullGroup); 381 382 // model rendering stuff 383 void RenderModels(const CShaderDefines& context, int cullGroup); 384 void RenderTransparentModels(const CShaderDefines& context, int cullGroup, ETransparentMode transparentMode, bool disableFaceCulling); 385 386 void RenderSilhouettes(const CShaderDefines& context); 387 388 void RenderParticles(int cullGroup); 389 390 // shadow rendering stuff 391 void RenderShadowMap(const CShaderDefines& context); 392 393 // render water reflection and refraction textures 394 void RenderReflections(const CShaderDefines& context, const CBoundingBoxAligned& scissor); 395 void RenderRefractions(const CShaderDefines& context, const CBoundingBoxAligned& scissor); 396 397 void ComputeReflectionCamera(CCamera& camera, const CBoundingBoxAligned& scissor) const; 398 void ComputeRefractionCamera(CCamera& camera, const CBoundingBoxAligned& scissor) const; 399 400 // debugging 401 void DisplayFrustum(); 402 403 // enable oblique frustum clipping with the given clip plane 404 void SetObliqueFrustumClipping(CCamera& camera, const CVector4D& clipPlane) const; 405 406 void ReloadShaders(); 407 void RecomputeSystemShaderDefines(); 408 409 // hotloading 410 static Status ReloadChangedFileCB(void* param, const VfsPath& path); 411 412 // RENDERER DATA: 413 /// Private data that is not needed by inline functions 414 CRendererInternals* m; 415 // view width 416 int m_Width; 417 // view height 418 int m_Height; 419 // current terrain rendering mode 420 ERenderMode m_TerrainRenderMode; 421 // current water rendering mode 422 ERenderMode m_WaterRenderMode; 423 // current model rendering mode 424 ERenderMode m_ModelRenderMode; 425 426 CShaderDefines m_SystemShaderDefines; 427 428 SViewPort m_Viewport; 429 430 /** 431 * m_ViewCamera: determines the eye position for rendering 432 * 433 * @see CGameView::m_ViewCamera 434 */ 435 CCamera m_ViewCamera; 436 437 /** 438 * m_CullCamera: determines the frustum for culling and shadowmap calculations 439 * 440 * @see CGameView::m_ViewCamera 441 */ 442 CCamera m_CullCamera; 443 444 // only valid inside a call to RenderScene 445 Scene* m_CurrentScene; 446 int m_CurrentCullGroup; 447 448 // color used to clear screen in BeginFrame 449 float m_ClearColor[4]; 450 // current lighting setup 451 CLightEnv* m_LightEnv; 452 // ogl_tex handle of composite alpha map (all the alpha maps packed into one texture) 453 Handle m_hCompositeAlphaMap; 454 // coordinates of each (untransformed) alpha map within the packed texture 455 struct { 456 float u0,u1,v0,v1; 457 } m_AlphaMapCoords[NumAlphaMaps]; 458 // card capabilities 459 Caps m_Caps; 460 // build card cap bits 461 void EnumCaps(); 462 // per-frame renderer stats 463 Stats m_Stats; 464 465 /** 466 * m_WaterManager: the WaterManager object used for water textures and settings 467 * (e.g. water color, water height) 468 */ 469 WaterManager* m_WaterManager; 470 471 /** 472 * m_SkyManager: the SkyManager object used for sky textures and settings 473 */ 474 SkyManager* m_SkyManager; 475 476 /** 477 * Enable rendering of terrain tile priority text overlay, for debugging. 478 */ 479 bool m_DisplayTerrainPriorities; 480 481 public: 482 /** 483 * m_ShadowZBias: Z bias used when rendering shadows into a depth texture. 484 * This can be used to control shadowing artifacts. 485 * 486 * Can be accessed via JS as renderer.shadowZBias 487 * ShadowMap uses this for matrix calculation. 488 */ 489 float m_ShadowZBias; 490 491 /** 492 * m_ShadowMapSize: Size of shadow map, or 0 for default. Typically slow but useful 493 * for high-quality rendering. Changes don't take effect until the shadow map 494 * is regenerated. 495 * 496 * Can be accessed via JS as renderer.shadowMapSize 497 */ 498 int m_ShadowMapSize; 499 500 /** 501 * m_SkipSubmit: Disable the actual submission of rendering commands to OpenGL. 502 * All state setup is still performed as usual. 503 * 504 * Can be accessed via JS as renderer.skipSubmit 505 */ 506 bool m_SkipSubmit; 507 }; 508 509 510 #endif 511