llfetchedgltfmaterial.cpp 9.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382
  1. /**
  2. * @file llfetchedgltfmaterial.cpp
  3. *
  4. * $LicenseInfo:firstyear=2022&license=viewergpl$
  5. *
  6. * Copyright (c) 2022, Linden Research, Inc.
  7. *
  8. * Second Life Viewer Source Code
  9. * The source code in this file ("Source Code") is provided by Linden Lab
  10. * to you under the terms of the GNU General Public License, version 2.0
  11. * ("GPL"), unless you have obtained a separate licensing agreement
  12. * ("Other License"), formally executed by you and Linden Lab. Terms of
  13. * the GPL can be found in doc/GPL-license.txt in this distribution, or
  14. * online at http://secondlifegrid.net/programs/open_source/licensing/gplv2
  15. *
  16. * There are special exceptions to the terms and conditions of the GPL as
  17. * it is applied to this Source Code. View the full text of the exception
  18. * in the file doc/FLOSS-exception.txt in this software distribution, or
  19. * online at
  20. * http://secondlifegrid.net/programs/open_source/licensing/flossexception
  21. *
  22. * By copying, modifying or distributing this software, you acknowledge
  23. * that you have read and understood your obligations described above,
  24. * and agree to abide by those obligations.
  25. *
  26. * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
  27. * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
  28. * COMPLETENESS OR PERFORMANCE.
  29. * $/LicenseInfo$
  30. */
  31. #include "llviewerprecompiledheaders.h"
  32. #include "llfetchedgltfmaterial.h"
  33. #include "llshadermgr.h"
  34. #include "llgltfmaterialpreview.h"
  35. #include "lllocalbitmaps.h"
  36. #include "llpipeline.h"
  37. #include "llviewertexturelist.h"
  38. LLFetchedGLTFMaterial& LLFetchedGLTFMaterial::operator=(const LLFetchedGLTFMaterial& rhs)
  39. {
  40. LLGLTFMaterial::operator=(rhs);
  41. mBaseColorTexture = rhs.mBaseColorTexture;
  42. mNormalTexture = rhs.mNormalTexture;
  43. mMetallicRoughnessTexture = rhs.mMetallicRoughnessTexture;
  44. mEmissiveTexture = rhs.mEmissiveTexture;
  45. return *this;
  46. }
  47. void LLFetchedGLTFMaterial::bind(LLViewerTexture* media_texp, F32 vsize)
  48. {
  49. if (!gUsePBRShaders)
  50. {
  51. return;
  52. }
  53. LLGLSLShader* shaderp = LLGLSLShader::sCurBoundShaderPtr;
  54. if (!shaderp) // Paranoia
  55. {
  56. llwarns << "No bound shader !" << llendl;
  57. return;
  58. }
  59. // Override emissive and base color textures with media texture if present
  60. LLViewerTexture* basecolorp;
  61. LLViewerTexture* emissivep;
  62. if (media_texp)
  63. {
  64. basecolorp = emissivep = media_texp;
  65. }
  66. else
  67. {
  68. basecolorp = mBaseColorTexture;
  69. emissivep = mEmissiveTexture;
  70. }
  71. // glTF 2.0 Specification 3.9.4. Alpha Coverage: mAlphaCutoff is only valid
  72. // for LLGLTFMaterial::ALPHA_MODE_MASK.
  73. F32 min_alpha = -1.f;
  74. bool is_alpha_mask = mAlphaMode == ALPHA_MODE_MASK;
  75. if (is_alpha_mask || !LLPipeline::sShadowRender)
  76. {
  77. if (mAlphaMode == LLGLTFMaterial::ALPHA_MODE_MASK)
  78. {
  79. min_alpha = mAlphaCutoff;
  80. }
  81. shaderp->uniform1f(LLShaderMgr::MINIMUM_ALPHA, min_alpha);
  82. }
  83. if (basecolorp)
  84. {
  85. shaderp->bindTexture(LLShaderMgr::DIFFUSE_MAP, basecolorp);
  86. basecolorp->addTextureStats(vsize);
  87. }
  88. else
  89. {
  90. shaderp->bindTexture(LLShaderMgr::DIFFUSE_MAP,
  91. LLViewerFetchedTexture::sWhiteImagep);
  92. }
  93. static F32 p_basecol[8], p_normal[8], p_roughness[8], p_emissive[8];
  94. mTextureTransform[BASECOLIDX].getPacked(p_basecol);
  95. shaderp->uniform4fv(LLShaderMgr::TEXTURE_BASE_COLOR_TRANSFORM, 2,
  96. p_basecol);
  97. if (LLPipeline::sShadowRender)
  98. {
  99. return; // Nothing else to do.
  100. }
  101. if (mNormalTexture.notNull() && mNormalTexture->getDiscardLevel() <= 4)
  102. {
  103. shaderp->bindTexture(LLShaderMgr::BUMP_MAP, mNormalTexture);
  104. mNormalTexture->addTextureStats(vsize);
  105. }
  106. else
  107. {
  108. shaderp->bindTexture(LLShaderMgr::BUMP_MAP,
  109. LLViewerFetchedTexture::sFlatNormalImagep);
  110. }
  111. if (mMetallicRoughnessTexture.notNull())
  112. {
  113. // PBR linear packed Occlusion, Roughness, Metal.
  114. shaderp->bindTexture(LLShaderMgr::SPECULAR_MAP,
  115. mMetallicRoughnessTexture);
  116. mMetallicRoughnessTexture->addTextureStats(vsize);
  117. }
  118. else
  119. {
  120. shaderp->bindTexture(LLShaderMgr::SPECULAR_MAP,
  121. LLViewerFetchedTexture::sWhiteImagep);
  122. }
  123. if (emissivep)
  124. {
  125. // PBR sRGB Emissive
  126. shaderp->bindTexture(LLShaderMgr::EMISSIVE_MAP, emissivep);
  127. emissivep->addTextureStats(vsize);
  128. }
  129. else
  130. {
  131. shaderp->bindTexture(LLShaderMgr::EMISSIVE_MAP,
  132. LLViewerFetchedTexture::sWhiteImagep);
  133. }
  134. // Note: base color factor is baked into vertex stream.
  135. shaderp->uniform1f(LLShaderMgr::ROUGHNESS_FACTOR, mRoughnessFactor);
  136. shaderp->uniform1f(LLShaderMgr::METALLIC_FACTOR, mMetallicFactor);
  137. shaderp->uniform3fv(LLShaderMgr::EMISSIVE_COLOR, 1, mEmissiveColor.mV);
  138. mTextureTransform[NORMALIDX].getPacked(p_normal);
  139. shaderp->uniform4fv(LLShaderMgr::TEXTURE_NORMAL_TRANSFORM, 2, p_normal);
  140. mTextureTransform[MROUGHIDX].getPacked(p_roughness);
  141. shaderp->uniform4fv(LLShaderMgr::TEXTURE_ROUGHNESS_TRANSFORM, 2,
  142. p_roughness);
  143. mTextureTransform[EMISSIVEIDX].getPacked(p_emissive);
  144. shaderp->uniform4fv(LLShaderMgr::TEXTURE_EMISSIVE_TRANSFORM, 2,
  145. p_emissive);
  146. }
  147. void LLFetchedGLTFMaterial::onMaterialComplete(std::function<void()> cb)
  148. {
  149. if (cb)
  150. {
  151. if (!mFetching)
  152. {
  153. cb();
  154. return;
  155. }
  156. mCompleteCallbacks.emplace_back(cb);
  157. }
  158. }
  159. void LLFetchedGLTFMaterial::materialComplete(bool success)
  160. {
  161. mFetching = false;
  162. mFetchSuccess = success;
  163. for (U32 i = 0, count = mCompleteCallbacks.size(); i < count; ++i)
  164. {
  165. mCompleteCallbacks[i]();
  166. }
  167. mCompleteCallbacks.clear();
  168. }
  169. static LLViewerFetchedTexture* fetch_texture(const LLUUID& id)
  170. {
  171. if (id.isNull())
  172. {
  173. return NULL;
  174. }
  175. LLViewerFetchedTexture* texp =
  176. LLViewerTextureManager::getFetchedTexture(id, FTT_DEFAULT, true,
  177. LLGLTexture::BOOST_NONE,
  178. LLViewerTexture::LOD_TEXTURE);
  179. if (texp) // Paranoia
  180. {
  181. texp->addTextureStats(64.f * 64.f);
  182. }
  183. return texp;
  184. }
  185. //virtual
  186. bool LLFetchedGLTFMaterial::replaceLocalTexture(const LLUUID& tracking_id,
  187. const LLUUID& old_id,
  188. const LLUUID& new_id)
  189. {
  190. bool seen = false;
  191. if (mTextureId[BASECOLIDX] == old_id)
  192. {
  193. mTextureId[BASECOLIDX] = new_id;
  194. mBaseColorTexture = fetch_texture(new_id);
  195. seen = true;
  196. }
  197. if (mTextureId[NORMALIDX] == old_id)
  198. {
  199. mTextureId[NORMALIDX] = new_id;
  200. mNormalTexture = fetch_texture(new_id);
  201. seen = true;
  202. }
  203. if (mTextureId[MROUGHIDX] == old_id)
  204. {
  205. mTextureId[MROUGHIDX] = new_id;
  206. mMetallicRoughnessTexture = fetch_texture(new_id);
  207. seen = true;
  208. }
  209. if (mTextureId[EMISSIVEIDX] == old_id)
  210. {
  211. mTextureId[EMISSIVEIDX] = new_id;
  212. mEmissiveTexture = fetch_texture(new_id);
  213. seen = true;
  214. }
  215. for (U32 i = 0; i < GLTF_TEXTURE_INFO_COUNT; ++i)
  216. {
  217. if (mTextureId[i] == new_id)
  218. {
  219. seen = true;
  220. }
  221. }
  222. if (seen)
  223. {
  224. mTrackingIdToLocalTexture[tracking_id] = new_id;
  225. }
  226. else
  227. {
  228. mTrackingIdToLocalTexture.erase(tracking_id);
  229. }
  230. return seen;
  231. }
  232. //virtual
  233. void LLFetchedGLTFMaterial::addTextureEntry(LLTextureEntry* tep)
  234. {
  235. mTextureEntries.insert(tep);
  236. }
  237. //virtual
  238. void LLFetchedGLTFMaterial::removeTextureEntry(LLTextureEntry* tep)
  239. {
  240. mTextureEntries.erase(tep);
  241. }
  242. //virtual
  243. void LLFetchedGLTFMaterial::updateTextureTracking()
  244. {
  245. if (!mTrackingIdToLocalTexture.empty())
  246. {
  247. for (local_tex_map_t::const_iterator
  248. it = mTrackingIdToLocalTexture.begin(),
  249. end = mTrackingIdToLocalTexture.end();
  250. it != end; ++it)
  251. {
  252. LLLocalBitmap::associateGLTFMaterial(it->first, this);
  253. }
  254. }
  255. }
  256. LLViewerTexture* LLFetchedGLTFMaterial::getPreview()
  257. {
  258. if (mPreview.isNull())
  259. {
  260. mPreview = LLGLTFPreviewTexture::getPreview(this);
  261. }
  262. return mPreview.get();
  263. }
  264. // ----------------------------------------------------------------------------
  265. // These are functions used in the llgltf library to deal with fetched
  266. // materials without knowing anything about them excepted that they derive from
  267. // the parent LLGLTFMaterial class... HB
  268. LLGLTFMaterial* create_fetch_material()
  269. {
  270. return new LLFetchedGLTFMaterial();
  271. }
  272. void bind_fetched_material(LLGLTFMaterial* matp)
  273. {
  274. LLFetchedGLTFMaterial* fmatp = NULL;
  275. if (matp)
  276. {
  277. fmatp = dynamic_cast<LLFetchedGLTFMaterial*>(matp);
  278. }
  279. if (!fmatp)
  280. {
  281. static LLFetchedGLTFMaterial sDefault;
  282. fmatp = &sDefault;
  283. }
  284. constexpr F32 VSIZE_DEFAULT = 256.f * 256.f;
  285. fmatp->bind(NULL, VSIZE_DEFAULT);
  286. }
  287. // For the new implementation of the llgltf library (WIP).
  288. // Merely implemented here because two of them reuse fetch_texture() which we
  289. // need in this module anyway, and also because this module uses LLLocalBitmap
  290. // already. *TODO: move to llgltfscenemanager.h/cpp ? HB
  291. LLGLTexture* gl_texture_from_fetched(const LLUUID& id)
  292. {
  293. return fetch_texture(id);
  294. }
  295. LLGLTexture* gl_texture_from_local_file(const std::string& filename)
  296. {
  297. if (!LLFile::exists(filename))
  298. {
  299. return NULL;
  300. }
  301. LLLocalBitmap* bitmapp = LLLocalBitmap::addUnit(filename);
  302. if (!bitmapp)
  303. {
  304. return NULL;
  305. }
  306. return fetch_texture(bitmapp->getWorldID());
  307. }
  308. LLGLTexture* gl_texture_from_memory(U8* datap, S32 size,
  309. const std::string& mime_type)
  310. {
  311. if (!datap || size <= 0)
  312. {
  313. return NULL;
  314. }
  315. LLPointer<LLImageFormatted> imagep =
  316. LLImageFormatted::createFromMimeType(mime_type);
  317. if (!imagep)
  318. {
  319. return NULL;
  320. }
  321. U8* image_datap = imagep->allocateData(size);
  322. memcpy((void*)image_datap, (void*)datap, (size_t)size);
  323. if (!imagep->updateData())
  324. {
  325. return NULL;
  326. }
  327. LLPointer<LLImageRaw> raw_imagep = new LLImageRaw();
  328. imagep->decode(raw_imagep);
  329. if (raw_imagep.isNull())
  330. {
  331. return NULL;
  332. }
  333. LLViewerFetchedTexture* texp = new LLViewerFetchedTexture(raw_imagep,
  334. FTT_LOCAL_FILE,
  335. true);
  336. texp->setBoostLevel(LLGLTexture::BOOST_PREVIEW);
  337. texp->dontDiscard();
  338. #if !LL_IMPLICIT_SETNODELETE
  339. texp->setNoDelete();
  340. #endif
  341. return texp;
  342. }