lldrawpoolmaterials.cpp 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573
  1. /**
  2. * @file lldrawpoolmaterials.cpp
  3. * @brief LLDrawPoolMaterials and LLDrawPoolMatPBR class implementations
  4. *
  5. * $LicenseInfo:firstyear=2012&license=viewergpl$
  6. *
  7. * Copyright (c) 2012-2022, Linden Research, Inc.
  8. *
  9. * Second Life Viewer Source Code
  10. * The source code in this file ("Source Code") is provided by Linden Lab
  11. * to you under the terms of the GNU General Public License, version 2.0
  12. * ("GPL"), unless you have obtained a separate licensing agreement
  13. * ("Other License"), formally executed by you and Linden Lab. Terms of
  14. * the GPL can be found in doc/GPL-license.txt in this distribution, or
  15. * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
  16. *
  17. * There are special exceptions to the terms and conditions of the GPL as
  18. * it is applied to this Source Code. View the full text of the exception
  19. * in the file doc/FLOSS-exception.txt in this software distribution, or
  20. * online at
  21. * http://secondlifegrid.net/programs/open_source/licensing/flossexception
  22. *
  23. * By copying, modifying or distributing this software, you acknowledge
  24. * that you have read and understood your obligations described above,
  25. * and agree to abide by those obligations.
  26. *
  27. * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
  28. * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
  29. * COMPLETENESS OR PERFORMANCE.
  30. * $/LicenseInfo$
  31. */
  32. #include "llviewerprecompiledheaders.h"
  33. #include "lldrawpoolmaterials.h"
  34. #include "llfasttimer.h"
  35. #include "llmodel.h"
  36. #include "llgltfscenemanager.h"
  37. #include "llpipeline.h"
  38. #include "llviewershadermgr.h"
  39. #include "llvoavatar.h"
  40. // Only used by the EE renderer.
  41. static S32 sDiffuseChannel = -1;
  42. static const U32 sTypeList[] =
  43. {
  44. LLRenderPass::PASS_MATERIAL,
  45. //LLRenderPass::PASS_MATERIAL_ALPHA,
  46. LLRenderPass::PASS_MATERIAL_ALPHA_MASK,
  47. LLRenderPass::PASS_MATERIAL_ALPHA_EMISSIVE,
  48. LLRenderPass::PASS_SPECMAP,
  49. //LLRenderPass::PASS_SPECMAP_BLEND,
  50. LLRenderPass::PASS_SPECMAP_MASK,
  51. LLRenderPass::PASS_SPECMAP_EMISSIVE,
  52. LLRenderPass::PASS_NORMMAP,
  53. //LLRenderPass::PASS_NORMMAP_BLEND,
  54. LLRenderPass::PASS_NORMMAP_MASK,
  55. LLRenderPass::PASS_NORMMAP_EMISSIVE,
  56. LLRenderPass::PASS_NORMSPEC,
  57. //LLRenderPass::PASS_NORMSPEC_BLEND,
  58. LLRenderPass::PASS_NORMSPEC_MASK,
  59. LLRenderPass::PASS_NORMSPEC_EMISSIVE,
  60. };
  61. ///////////////////////////////////////////////////////////////////////////////
  62. // LLDrawPoolMaterials class
  63. ///////////////////////////////////////////////////////////////////////////////
  64. LLDrawPoolMaterials::LLDrawPoolMaterials()
  65. : LLRenderPass(LLDrawPool::POOL_MATERIALS)
  66. {
  67. }
  68. //virtual
  69. void LLDrawPoolMaterials::prerender()
  70. {
  71. mShaderLevel =
  72. gViewerShaderMgrp->getShaderLevel(LLViewerShaderMgr::SHADER_OBJECT);
  73. }
  74. //virtual
  75. void LLDrawPoolMaterials::beginDeferredPass(S32 pass)
  76. {
  77. LL_FAST_TIMER(FTM_RENDER_MATERIALS);
  78. bool rigged = pass >= 12;
  79. if (rigged)
  80. {
  81. pass -= 12;
  82. }
  83. U32 shader_idx[] =
  84. {
  85. 0, // PASS_MATERIAL,
  86. //1, // PASS_MATERIAL_ALPHA,
  87. 2, // PASS_MATERIAL_ALPHA_MASK,
  88. 3, // PASS_MATERIAL_ALPHA_EMISSIVE,
  89. 4, // PASS_SPECMAP,
  90. //5, // PASS_SPECMAP_BLEND,
  91. 6, // PASS_SPECMAP_MASK,
  92. 7, // PASS_SPECMAP_EMISSIVE,
  93. 8, // PASS_NORMMAP,
  94. //9, // PASS_NORMMAP_BLEND,
  95. 10, // PASS_NORMMAP_MASK,
  96. 11, // PASS_NORMMAP_EMISSIVE,
  97. 12, // PASS_NORMSPEC,
  98. //13, // PASS_NORMSPEC_BLEND,
  99. 14, // PASS_NORMSPEC_MASK,
  100. 15, // PASS_NORMSPEC_EMISSIVE,
  101. };
  102. if (LLPipeline::sUnderWaterRender && !gUsePBRShaders)
  103. {
  104. mShader = &gDeferredMaterialWaterProgram[shader_idx[pass]];
  105. }
  106. else
  107. {
  108. mShader = &gDeferredMaterialProgram[shader_idx[pass]];
  109. }
  110. if (rigged)
  111. {
  112. if (mShader->mRiggedVariant)
  113. {
  114. mShader = mShader->mRiggedVariant;
  115. }
  116. else
  117. {
  118. llwarns_once << "Missing rigged variant shader !" << llendl;
  119. }
  120. }
  121. if (gUsePBRShaders)
  122. {
  123. gPipeline.bindDeferredShader(*mShader);
  124. }
  125. else
  126. {
  127. mShader->bind();
  128. S32 no_atmo = LLPipeline::sRenderingHUDs ? 1 : 0;
  129. mShader->uniform1i(LLShaderMgr::NO_ATMO, no_atmo);
  130. sDiffuseChannel = mShader->enableTexture(LLShaderMgr::DIFFUSE_MAP);
  131. }
  132. }
  133. //virtual
  134. void LLDrawPoolMaterials::endDeferredPass(S32 pass)
  135. {
  136. LL_FAST_TIMER(FTM_RENDER_MATERIALS);
  137. if (gUsePBRShaders)
  138. {
  139. gPipeline.unbindDeferredShader(*mShader);
  140. }
  141. else
  142. {
  143. mShader->unbind();
  144. }
  145. LLRenderPass::endRenderPass(pass);
  146. }
  147. //virtual
  148. void LLDrawPoolMaterials::renderDeferred(S32 pass)
  149. {
  150. if (!gPipeline.sCull)
  151. {
  152. // Paranoia (sCull != NULL needed for getRenderMap())
  153. return;
  154. }
  155. if (gUsePBRShaders)
  156. {
  157. renderDeferredPBR(pass);
  158. return;
  159. }
  160. bool rigged = pass >= 12;
  161. if (rigged)
  162. {
  163. pass -= 12;
  164. }
  165. llassert(pass < (S32)LL_ARRAY_SIZE(sTypeList));
  166. U32 type = sTypeList[pass];
  167. if (rigged)
  168. {
  169. ++type;
  170. }
  171. U32 mask = mShader->mAttributeMask;
  172. LLVOAvatar* last_avatarp = NULL;
  173. U64 last_hash = 0;
  174. LLCullResult::drawinfo_list_t& draw_list = gPipeline.getRenderMap(type);
  175. for (U32 i = 0, count = draw_list.size(); i < count; )
  176. {
  177. LLDrawInfo* paramsp = draw_list[i++];
  178. // Draw info cache prefetching optimization.
  179. if (i != count)
  180. {
  181. LLVertexBuffer* vb = draw_list[i]->mVertexBuffer.get();
  182. if (vb) // Paranoia
  183. {
  184. _mm_prefetch((char*)vb, _MM_HINT_NTA);
  185. }
  186. if (i + 1 < count)
  187. {
  188. _mm_prefetch((char*)draw_list[i + 1], _MM_HINT_NTA);
  189. }
  190. }
  191. if (!paramsp->mVertexBuffer) continue; // Paranoia
  192. if (rigged && paramsp->mAvatar && paramsp->mSkinInfo &&
  193. (paramsp->mAvatar != last_avatarp ||
  194. paramsp->mSkinInfo->mHash != last_hash))
  195. {
  196. #if 0 // Better seeing part of the avatar rather than nothing at all. HB
  197. if (!uploadMatrixPalette(*paramsp))
  198. {
  199. continue;
  200. }
  201. #else
  202. uploadMatrixPalette(*paramsp);
  203. #endif
  204. last_avatarp = paramsp->mAvatar;
  205. last_hash = paramsp->mSkinInfo->mHash;
  206. }
  207. mShader->uniform4f(LLShaderMgr::SPECULAR_COLOR,
  208. paramsp->mSpecColor.mV[0], paramsp->mSpecColor.mV[1],
  209. paramsp->mSpecColor.mV[2], paramsp->mSpecColor.mV[3]);
  210. mShader->uniform1f(LLShaderMgr::ENVIRONMENT_INTENSITY,
  211. paramsp->mEnvIntensity);
  212. if (paramsp->mNormalMap)
  213. {
  214. paramsp->mNormalMap->addTextureStats(paramsp->mVSize);
  215. bindNormalMap(paramsp->mNormalMap);
  216. }
  217. if (paramsp->mSpecularMap)
  218. {
  219. paramsp->mSpecularMap->addTextureStats(paramsp->mVSize);
  220. bindSpecularMap(paramsp->mSpecularMap);
  221. }
  222. mShader->setMinimumAlpha(paramsp->mAlphaMaskCutoff);
  223. F32 brightness = paramsp->mFullbright ? 1.f : 0.f;
  224. mShader->uniform1f(LLShaderMgr::EMISSIVE_BRIGHTNESS, brightness);
  225. pushMaterialsBatch(*paramsp, mask);
  226. }
  227. }
  228. void LLDrawPoolMaterials::renderDeferredPBR(S32 pass)
  229. {
  230. bool rigged = pass >= 12;
  231. if (rigged)
  232. {
  233. pass -= 12;
  234. }
  235. llassert(pass < (S32)LL_ARRAY_SIZE(sTypeList));
  236. U32 type = sTypeList[pass];
  237. if (rigged)
  238. {
  239. ++type;
  240. }
  241. S32 intensity_loc =
  242. mShader->getUniformLocation(LLShaderMgr::ENVIRONMENT_INTENSITY);
  243. S32 brightness_loc =
  244. mShader->getUniformLocation(LLShaderMgr::EMISSIVE_BRIGHTNESS);
  245. S32 min_alpha_loc =
  246. mShader->getUniformLocation(LLShaderMgr::MINIMUM_ALPHA);
  247. S32 specular_loc =
  248. mShader->getUniformLocation(LLShaderMgr::SPECULAR_COLOR);
  249. LLTexUnit* diffunitp =
  250. gGL.getTexUnit(mShader->enableTexture(LLShaderMgr::DIFFUSE_MAP));
  251. S32 channel = mShader->enableTexture(LLShaderMgr::SPECULAR_MAP);
  252. LLTexUnit* specunitp = channel > -1 ? gGL.getTexUnit(channel) : NULL;
  253. channel = mShader->enableTexture(LLShaderMgr::BUMP_MAP);
  254. LLTexUnit* normunitp = channel > -1 ? gGL.getTexUnit(channel) : NULL;
  255. diffunitp->unbindFast(LLTexUnit::TT_TEXTURE);
  256. F32 last_intensity = 0.f;
  257. if (intensity_loc > -1)
  258. {
  259. glUniform1f(intensity_loc, last_intensity);
  260. }
  261. F32 last_fullbrigh = 0.f;
  262. if (brightness_loc > -1)
  263. {
  264. glUniform1f(brightness_loc, last_fullbrigh);
  265. }
  266. F32 last_min_alpha = 0.f;
  267. if (min_alpha_loc > -1)
  268. {
  269. glUniform1f(min_alpha_loc, last_min_alpha);
  270. }
  271. LLVector4 last_specular(0.f, 0.f, 0.f, 0.f);
  272. if (specular_loc > -1)
  273. {
  274. glUniform4fv(specular_loc, 1, last_specular.mV);
  275. }
  276. LLViewerTexture* last_diffp = NULL;
  277. LLViewerTexture* last_normp = NULL;
  278. LLViewerTexture* last_specp = NULL;
  279. LLTexUnit* unit0 = gGL.getTexUnit(0);
  280. LLVOAvatar* last_avatarp = NULL;
  281. U64 last_hash = 0;
  282. LLCullResult::drawinfo_list_t& draw_list = gPipeline.getRenderMap(type);
  283. for (U32 i = 0, count = draw_list.size(); i < count; )
  284. {
  285. LLDrawInfo* paramsp = draw_list[i++];
  286. // Draw info cache prefetching optimization.
  287. if (i != count)
  288. {
  289. LLVertexBuffer* vb = draw_list[i]->mVertexBuffer.get();
  290. if (vb) // Paranoia
  291. {
  292. _mm_prefetch((char*)vb, _MM_HINT_NTA);
  293. }
  294. if (i + 1 < count)
  295. {
  296. _mm_prefetch((char*)draw_list[i + 1], _MM_HINT_NTA);
  297. }
  298. }
  299. if (!paramsp->mVertexBuffer) continue; // Paranoia
  300. if (specular_loc > -1 && paramsp->mSpecColor != last_specular)
  301. {
  302. last_specular = paramsp->mSpecColor;
  303. glUniform4fv(specular_loc, 1, last_specular.mV);
  304. }
  305. if (intensity_loc > -1 && paramsp->mEnvIntensity != last_intensity)
  306. {
  307. last_intensity = paramsp->mEnvIntensity;
  308. glUniform1f(intensity_loc, last_intensity);
  309. }
  310. if (min_alpha_loc > -1 && paramsp->mAlphaMaskCutoff != last_min_alpha)
  311. {
  312. last_min_alpha = paramsp->mAlphaMaskCutoff;
  313. glUniform1f(min_alpha_loc, last_min_alpha);
  314. }
  315. F32 fullbright = paramsp->mFullbright ? 1.f : 0.f;
  316. if (brightness_loc > -1 && fullbright != last_fullbrigh)
  317. {
  318. last_fullbrigh = fullbright;
  319. glUniform1f(brightness_loc, last_fullbrigh);
  320. }
  321. if (normunitp && paramsp->mNormalMap.get() != last_normp)
  322. {
  323. last_normp = paramsp->mNormalMap.get();
  324. if (last_normp)
  325. {
  326. normunitp->bindFast(last_normp);
  327. last_normp->addTextureStats(paramsp->mVSize);
  328. }
  329. }
  330. if (specunitp && paramsp->mSpecularMap.get() != last_specp)
  331. {
  332. last_specp = paramsp->mSpecularMap.get();
  333. if (last_specp)
  334. {
  335. specunitp->bindFast(last_specp);
  336. last_specp->addTextureStats(paramsp->mVSize);
  337. }
  338. }
  339. if (paramsp->mTexture.get() != last_diffp)
  340. {
  341. last_diffp = paramsp->mTexture.get();
  342. if (last_diffp)
  343. {
  344. diffunitp->bindFast(last_diffp);
  345. last_diffp->addTextureStats(paramsp->mVSize);
  346. }
  347. else
  348. {
  349. diffunitp->unbindFast(LLTexUnit::TT_TEXTURE);
  350. }
  351. }
  352. if (rigged && paramsp->mAvatar && paramsp->mSkinInfo &&
  353. (paramsp->mAvatar != last_avatarp ||
  354. paramsp->mSkinInfo->mHash != last_hash))
  355. {
  356. #if 0 // Better seeing part of the avatar rather than nothing at all. HB
  357. if (!uploadMatrixPalette(*paramsp))
  358. {
  359. continue;
  360. }
  361. #else
  362. uploadMatrixPalette(*paramsp);
  363. #endif
  364. last_avatarp = paramsp->mAvatar;
  365. last_hash = paramsp->mSkinInfo->mHash;
  366. }
  367. applyModelMatrix(*paramsp);
  368. bool tex_setup = false;
  369. if (paramsp->mTextureMatrix)
  370. {
  371. tex_setup = true;
  372. unit0->activate();
  373. gGL.matrixMode(LLRender::MM_TEXTURE);
  374. gGL.loadMatrix(paramsp->mTextureMatrix->getF32ptr());
  375. ++gPipeline.mTextureMatrixOps;
  376. }
  377. paramsp->mVertexBuffer->setBuffer();
  378. paramsp->mVertexBuffer->drawRange(LLRender::TRIANGLES,
  379. paramsp->mStart, paramsp->mEnd,
  380. paramsp->mCount, paramsp->mOffset);
  381. if (tex_setup)
  382. {
  383. unit0->activate();
  384. gGL.loadIdentity();
  385. gGL.matrixMode(LLRender::MM_MODELVIEW);
  386. }
  387. }
  388. }
  389. // For EE rendering only
  390. void LLDrawPoolMaterials::bindSpecularMap(LLViewerTexture* texp)
  391. {
  392. mShader->bindTexture(LLShaderMgr::SPECULAR_MAP, texp);
  393. }
  394. void LLDrawPoolMaterials::bindNormalMap(LLViewerTexture* texp)
  395. {
  396. mShader->bindTexture(LLShaderMgr::BUMP_MAP, texp);
  397. }
  398. // For EE rendering only
  399. void LLDrawPoolMaterials::pushMaterialsBatch(LLDrawInfo& params, U32 mask)
  400. {
  401. applyModelMatrix(params);
  402. bool tex_setup = false;
  403. if (params.mTextureMatrix)
  404. {
  405. #if 0
  406. if (mShiny)
  407. #endif
  408. {
  409. gGL.getTexUnit(0)->activate();
  410. gGL.matrixMode(LLRender::MM_TEXTURE);
  411. }
  412. gGL.loadMatrix(params.mTextureMatrix->getF32ptr());
  413. ++gPipeline.mTextureMatrixOps;
  414. tex_setup = true;
  415. }
  416. if (mShaderLevel > 1)
  417. {
  418. if (params.mTexture.notNull())
  419. {
  420. gGL.getTexUnit(sDiffuseChannel)->bindFast(params.mTexture);
  421. }
  422. else
  423. {
  424. gGL.getTexUnit(sDiffuseChannel)->unbindFast(LLTexUnit::TT_TEXTURE);
  425. }
  426. }
  427. params.mVertexBuffer->setBufferFast(mask);
  428. params.mVertexBuffer->drawRangeFast(params.mStart, params.mEnd,
  429. params.mCount, params.mOffset);
  430. if (tex_setup)
  431. {
  432. gGL.getTexUnit(0)->activate();
  433. gGL.loadIdentity();
  434. gGL.matrixMode(LLRender::MM_MODELVIEW);
  435. }
  436. }
  437. ///////////////////////////////////////////////////////////////////////////////
  438. // LLDrawPoolMatPBR class
  439. ///////////////////////////////////////////////////////////////////////////////
  440. LLDrawPoolMatPBR::LLDrawPoolMatPBR(U32 type)
  441. : LLRenderPass(type)
  442. {
  443. if (type == POOL_MAT_PBR_ALPHA_MASK)
  444. {
  445. mRenderType = LLPipeline::RENDER_TYPE_PASS_MAT_ALPHA_MASK_PBR;
  446. }
  447. else
  448. {
  449. mRenderType = LLPipeline::RENDER_TYPE_PASS_MAT_PBR;
  450. }
  451. }
  452. //virtual
  453. S32 LLDrawPoolMatPBR::getNumDeferredPasses()
  454. {
  455. return gUsePBRShaders ? 1 : 0;
  456. }
  457. //virtual
  458. void LLDrawPoolMatPBR::renderDeferred(S32 pass)
  459. {
  460. if (LLPipeline::sRenderingHUDs)
  461. {
  462. return;
  463. }
  464. gDeferredPBROpaqueProgram.bind();
  465. if (gUsePBRShaders)
  466. {
  467. LLGLTFSceneManager::renderOpaque();
  468. }
  469. pushGLTFBatches(mRenderType);
  470. gDeferredPBROpaqueProgram.bind(true);
  471. pushRiggedGLTFBatches(mRenderType + 1);
  472. }
  473. //virtual
  474. void LLDrawPoolMatPBR::renderPostDeferred(S32 pass)
  475. {
  476. if (LLPipeline::sRenderingHUDs)
  477. {
  478. gHUDPBROpaqueProgram.bind();
  479. pushGLTFBatches(mRenderType);
  480. return;
  481. }
  482. // *HACK: do not render glow except for the non-alpha masked implementation
  483. if (mRenderType == LLPipeline::RENDER_TYPE_PASS_MAT_PBR)
  484. {
  485. gGL.setColorMask(false, true);
  486. gPBRGlowProgram.bind();
  487. pushGLTFBatches(PASS_PBR_GLOW);
  488. gPBRGlowProgram.bind(true);
  489. pushRiggedGLTFBatches(PASS_PBR_GLOW_RIGGED);
  490. gGL.setColorMask(true, false);
  491. }
  492. }