standardMaterial.ts 77 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917
  1. import { serialize, SerializationHelper, serializeAsColor3, expandToProperty, serializeAsFresnelParameters, serializeAsTexture } from "../Misc/decorators";
  2. import { Observer } from "../Misc/observable";
  3. import { SmartArray } from "../Misc/smartArray";
  4. import { IAnimatable } from '../Animations/animatable.interface';
  5. import { Nullable } from "../types";
  6. import { Scene } from "../scene";
  7. import { Matrix } from "../Maths/math.vector";
  8. import { Color3 } from '../Maths/math.color';
  9. import { VertexBuffer } from "../Meshes/buffer";
  10. import { SubMesh } from "../Meshes/subMesh";
  11. import { AbstractMesh } from "../Meshes/abstractMesh";
  12. import { Mesh } from "../Meshes/mesh";
  13. import { ImageProcessingConfiguration, IImageProcessingConfigurationDefines } from "./imageProcessingConfiguration";
  14. import { ColorCurves } from "./colorCurves";
  15. import { FresnelParameters } from "./fresnelParameters";
  16. import { Material, ICustomShaderNameResolveOptions } from "../Materials/material";
  17. import { MaterialDefines } from "../Materials/materialDefines";
  18. import { PushMaterial } from "./pushMaterial";
  19. import { MaterialHelper } from "./materialHelper";
  20. import { BaseTexture } from "../Materials/Textures/baseTexture";
  21. import { Texture } from "../Materials/Textures/texture";
  22. import { CubeTexture } from "../Materials/Textures/cubeTexture";
  23. import { RenderTargetTexture } from "../Materials/Textures/renderTargetTexture";
  24. import { _TypeStore } from "../Misc/typeStore";
  25. import { MaterialFlags } from "./materialFlags";
  26. import "../Shaders/default.fragment";
  27. import "../Shaders/default.vertex";
  28. import { Constants } from "../Engines/constants";
  29. import { EffectFallbacks } from './effectFallbacks';
  30. import { Effect, IEffectCreationOptions } from './effect';
  31. import { IMaterialDetailMapDefines, DetailMapConfiguration } from './material.detailMapConfiguration';
  32. const onCreatedEffectParameters = { effect: null as unknown as Effect, subMesh: null as unknown as Nullable<SubMesh> };
  33. /** @hidden */
  34. export class StandardMaterialDefines extends MaterialDefines implements IImageProcessingConfigurationDefines, IMaterialDetailMapDefines {
  35. public MAINUV1 = false;
  36. public MAINUV2 = false;
  37. public DIFFUSE = false;
  38. public DIFFUSEDIRECTUV = 0;
  39. public DETAIL = false;
  40. public DETAILDIRECTUV = 0;
  41. public DETAIL_NORMALBLENDMETHOD = 0;
  42. public AMBIENT = false;
  43. public AMBIENTDIRECTUV = 0;
  44. public OPACITY = false;
  45. public OPACITYDIRECTUV = 0;
  46. public OPACITYRGB = false;
  47. public REFLECTION = false;
  48. public EMISSIVE = false;
  49. public EMISSIVEDIRECTUV = 0;
  50. public SPECULAR = false;
  51. public SPECULARDIRECTUV = 0;
  52. public BUMP = false;
  53. public BUMPDIRECTUV = 0;
  54. public PARALLAX = false;
  55. public PARALLAXOCCLUSION = false;
  56. public SPECULAROVERALPHA = false;
  57. public CLIPPLANE = false;
  58. public CLIPPLANE2 = false;
  59. public CLIPPLANE3 = false;
  60. public CLIPPLANE4 = false;
  61. public CLIPPLANE5 = false;
  62. public CLIPPLANE6 = false;
  63. public ALPHATEST = false;
  64. public DEPTHPREPASS = false;
  65. public ALPHAFROMDIFFUSE = false;
  66. public POINTSIZE = false;
  67. public FOG = false;
  68. public SPECULARTERM = false;
  69. public DIFFUSEFRESNEL = false;
  70. public OPACITYFRESNEL = false;
  71. public REFLECTIONFRESNEL = false;
  72. public REFRACTIONFRESNEL = false;
  73. public EMISSIVEFRESNEL = false;
  74. public FRESNEL = false;
  75. public NORMAL = false;
  76. public UV1 = false;
  77. public UV2 = false;
  78. public VERTEXCOLOR = false;
  79. public VERTEXALPHA = false;
  80. public NUM_BONE_INFLUENCERS = 0;
  81. public BonesPerMesh = 0;
  82. public BONETEXTURE = false;
  83. public INSTANCES = false;
  84. public THIN_INSTANCES = false;
  85. public GLOSSINESS = false;
  86. public ROUGHNESS = false;
  87. public EMISSIVEASILLUMINATION = false;
  88. public LINKEMISSIVEWITHDIFFUSE = false;
  89. public REFLECTIONFRESNELFROMSPECULAR = false;
  90. public LIGHTMAP = false;
  91. public LIGHTMAPDIRECTUV = 0;
  92. public OBJECTSPACE_NORMALMAP = false;
  93. public USELIGHTMAPASSHADOWMAP = false;
  94. public REFLECTIONMAP_3D = false;
  95. public REFLECTIONMAP_SPHERICAL = false;
  96. public REFLECTIONMAP_PLANAR = false;
  97. public REFLECTIONMAP_CUBIC = false;
  98. public USE_LOCAL_REFLECTIONMAP_CUBIC = false;
  99. public REFLECTIONMAP_PROJECTION = false;
  100. public REFLECTIONMAP_SKYBOX = false;
  101. public REFLECTIONMAP_EXPLICIT = false;
  102. public REFLECTIONMAP_EQUIRECTANGULAR = false;
  103. public REFLECTIONMAP_EQUIRECTANGULAR_FIXED = false;
  104. public REFLECTIONMAP_MIRROREDEQUIRECTANGULAR_FIXED = false;
  105. public INVERTCUBICMAP = false;
  106. public LOGARITHMICDEPTH = false;
  107. public REFRACTION = false;
  108. public REFRACTIONMAP_3D = false;
  109. public REFLECTIONOVERALPHA = false;
  110. public TWOSIDEDLIGHTING = false;
  111. public SHADOWFLOAT = false;
  112. public MORPHTARGETS = false;
  113. public MORPHTARGETS_NORMAL = false;
  114. public MORPHTARGETS_TANGENT = false;
  115. public MORPHTARGETS_UV = false;
  116. public NUM_MORPH_INFLUENCERS = 0;
  117. public NONUNIFORMSCALING = false; // https://playground.babylonjs.com#V6DWIH
  118. public PREMULTIPLYALPHA = false; // https://playground.babylonjs.com#LNVJJ7
  119. public ALPHATEST_AFTERALLALPHACOMPUTATIONS = false;
  120. public ALPHABLEND = true;
  121. public PREPASS = false;
  122. public SCENE_MRT_COUNT = 0;
  123. public RGBDLIGHTMAP = false;
  124. public RGBDREFLECTION = false;
  125. public RGBDREFRACTION = false;
  126. public IMAGEPROCESSING = false;
  127. public VIGNETTE = false;
  128. public VIGNETTEBLENDMODEMULTIPLY = false;
  129. public VIGNETTEBLENDMODEOPAQUE = false;
  130. public TONEMAPPING = false;
  131. public TONEMAPPING_ACES = false;
  132. public CONTRAST = false;
  133. public COLORCURVES = false;
  134. public COLORGRADING = false;
  135. public COLORGRADING3D = false;
  136. public SAMPLER3DGREENDEPTH = false;
  137. public SAMPLER3DBGRMAP = false;
  138. public IMAGEPROCESSINGPOSTPROCESS = false;
  139. public MULTIVIEW = false;
  140. /**
  141. * If the reflection texture on this material is in linear color space
  142. * @hidden
  143. */
  144. public IS_REFLECTION_LINEAR = false;
  145. /**
  146. * If the refraction texture on this material is in linear color space
  147. * @hidden
  148. */
  149. public IS_REFRACTION_LINEAR = false;
  150. public EXPOSURE = false;
  151. constructor() {
  152. super();
  153. this.rebuild();
  154. }
  155. public setReflectionMode(modeToEnable: string) {
  156. var modes = [
  157. "REFLECTIONMAP_CUBIC", "REFLECTIONMAP_EXPLICIT", "REFLECTIONMAP_PLANAR",
  158. "REFLECTIONMAP_PROJECTION", "REFLECTIONMAP_PROJECTION", "REFLECTIONMAP_SKYBOX",
  159. "REFLECTIONMAP_SPHERICAL", "REFLECTIONMAP_EQUIRECTANGULAR", "REFLECTIONMAP_EQUIRECTANGULAR_FIXED",
  160. "REFLECTIONMAP_MIRROREDEQUIRECTANGULAR_FIXED"
  161. ];
  162. for (var mode of modes) {
  163. (<any>this)[mode] = (mode === modeToEnable);
  164. }
  165. }
  166. }
  167. /**
  168. * This is the default material used in Babylon. It is the best trade off between quality
  169. * and performances.
  170. * @see https://doc.babylonjs.com/babylon101/materials
  171. */
  172. export class StandardMaterial extends PushMaterial {
  173. @serializeAsTexture("diffuseTexture")
  174. private _diffuseTexture: Nullable<BaseTexture> = null;
  175. /**
  176. * The basic texture of the material as viewed under a light.
  177. */
  178. @expandToProperty("_markAllSubMeshesAsTexturesAndMiscDirty")
  179. public diffuseTexture: Nullable<BaseTexture>;
  180. @serializeAsTexture("ambientTexture")
  181. private _ambientTexture: Nullable<BaseTexture> = null;
  182. /**
  183. * AKA Occlusion Texture in other nomenclature, it helps adding baked shadows into your material.
  184. */
  185. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  186. public ambientTexture: Nullable<BaseTexture>;
  187. @serializeAsTexture("opacityTexture")
  188. private _opacityTexture: Nullable<BaseTexture> = null;
  189. /**
  190. * Define the transparency of the material from a texture.
  191. * The final alpha value can be read either from the red channel (if texture.getAlphaFromRGB is false)
  192. * or from the luminance or the current texel (if texture.getAlphaFromRGB is true)
  193. */
  194. @expandToProperty("_markAllSubMeshesAsTexturesAndMiscDirty")
  195. public opacityTexture: Nullable<BaseTexture>;
  196. @serializeAsTexture("reflectionTexture")
  197. private _reflectionTexture: Nullable<BaseTexture> = null;
  198. /**
  199. * Define the texture used to display the reflection.
  200. * @see https://doc.babylonjs.com/how_to/reflect#how-to-obtain-reflections-and-refractions
  201. */
  202. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  203. public reflectionTexture: Nullable<BaseTexture>;
  204. @serializeAsTexture("emissiveTexture")
  205. private _emissiveTexture: Nullable<BaseTexture> = null;
  206. /**
  207. * Define texture of the material as if self lit.
  208. * This will be mixed in the final result even in the absence of light.
  209. */
  210. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  211. public emissiveTexture: Nullable<BaseTexture>;
  212. @serializeAsTexture("specularTexture")
  213. private _specularTexture: Nullable<BaseTexture> = null;
  214. /**
  215. * Define how the color and intensity of the highlight given by the light in the material.
  216. */
  217. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  218. public specularTexture: Nullable<BaseTexture>;
  219. @serializeAsTexture("bumpTexture")
  220. private _bumpTexture: Nullable<BaseTexture> = null;
  221. /**
  222. * Bump mapping is a technique to simulate bump and dents on a rendered surface.
  223. * These are made by creating a normal map from an image. The means to do this can be found on the web, a search for 'normal map generator' will bring up free and paid for methods of doing this.
  224. * @see https://doc.babylonjs.com/how_to/more_materials#bump-map
  225. */
  226. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  227. public bumpTexture: Nullable<BaseTexture>;
  228. @serializeAsTexture("lightmapTexture")
  229. private _lightmapTexture: Nullable<BaseTexture> = null;
  230. /**
  231. * Complex lighting can be computationally expensive to compute at runtime.
  232. * To save on computation, lightmaps may be used to store calculated lighting in a texture which will be applied to a given mesh.
  233. * @see https://doc.babylonjs.com/babylon101/lights#lightmaps
  234. */
  235. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  236. public lightmapTexture: Nullable<BaseTexture>;
  237. @serializeAsTexture("refractionTexture")
  238. private _refractionTexture: Nullable<BaseTexture> = null;
  239. /**
  240. * Define the texture used to display the refraction.
  241. * @see https://doc.babylonjs.com/how_to/reflect#how-to-obtain-reflections-and-refractions
  242. */
  243. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  244. public refractionTexture: Nullable<BaseTexture>;
  245. /**
  246. * The color of the material lit by the environmental background lighting.
  247. * @see https://doc.babylonjs.com/babylon101/materials#ambient-color-example
  248. */
  249. @serializeAsColor3("ambient")
  250. public ambientColor = new Color3(0, 0, 0);
  251. /**
  252. * The basic color of the material as viewed under a light.
  253. */
  254. @serializeAsColor3("diffuse")
  255. public diffuseColor = new Color3(1, 1, 1);
  256. /**
  257. * Define how the color and intensity of the highlight given by the light in the material.
  258. */
  259. @serializeAsColor3("specular")
  260. public specularColor = new Color3(1, 1, 1);
  261. /**
  262. * Define the color of the material as if self lit.
  263. * This will be mixed in the final result even in the absence of light.
  264. */
  265. @serializeAsColor3("emissive")
  266. public emissiveColor = new Color3(0, 0, 0);
  267. /**
  268. * Defines how sharp are the highlights in the material.
  269. * The bigger the value the sharper giving a more glossy feeling to the result.
  270. * Reversely, the smaller the value the blurrier giving a more rough feeling to the result.
  271. */
  272. @serialize()
  273. public specularPower = 64;
  274. @serialize("useAlphaFromDiffuseTexture")
  275. private _useAlphaFromDiffuseTexture = false;
  276. /**
  277. * Does the transparency come from the diffuse texture alpha channel.
  278. */
  279. @expandToProperty("_markAllSubMeshesAsTexturesAndMiscDirty")
  280. public useAlphaFromDiffuseTexture: boolean;
  281. @serialize("useEmissiveAsIllumination")
  282. private _useEmissiveAsIllumination = false;
  283. /**
  284. * If true, the emissive value is added into the end result, otherwise it is multiplied in.
  285. */
  286. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  287. public useEmissiveAsIllumination: boolean;
  288. @serialize("linkEmissiveWithDiffuse")
  289. private _linkEmissiveWithDiffuse = false;
  290. /**
  291. * If true, some kind of energy conservation will prevent the end result to be more than 1 by reducing
  292. * the emissive level when the final color is close to one.
  293. */
  294. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  295. public linkEmissiveWithDiffuse: boolean;
  296. @serialize("useSpecularOverAlpha")
  297. private _useSpecularOverAlpha = false;
  298. /**
  299. * Specifies that the material will keep the specular highlights over a transparent surface (only the most limunous ones).
  300. * A car glass is a good exemple of that. When sun reflects on it you can not see what is behind.
  301. */
  302. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  303. public useSpecularOverAlpha: boolean;
  304. @serialize("useReflectionOverAlpha")
  305. private _useReflectionOverAlpha = false;
  306. /**
  307. * Specifies that the material will keeps the reflection highlights over a transparent surface (only the most limunous ones).
  308. * A car glass is a good exemple of that. When the street lights reflects on it you can not see what is behind.
  309. */
  310. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  311. public useReflectionOverAlpha: boolean;
  312. @serialize("disableLighting")
  313. private _disableLighting = false;
  314. /**
  315. * Does lights from the scene impacts this material.
  316. * It can be a nice trick for performance to disable lighting on a fully emissive material.
  317. */
  318. @expandToProperty("_markAllSubMeshesAsLightsDirty")
  319. public disableLighting: boolean;
  320. @serialize("useObjectSpaceNormalMap")
  321. private _useObjectSpaceNormalMap = false;
  322. /**
  323. * Allows using an object space normal map (instead of tangent space).
  324. */
  325. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  326. public useObjectSpaceNormalMap: boolean;
  327. @serialize("useParallax")
  328. private _useParallax = false;
  329. /**
  330. * Is parallax enabled or not.
  331. * @see https://doc.babylonjs.com/how_to/using_parallax_mapping
  332. */
  333. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  334. public useParallax: boolean;
  335. @serialize("useParallaxOcclusion")
  336. private _useParallaxOcclusion = false;
  337. /**
  338. * Is parallax occlusion enabled or not.
  339. * If true, the outcome is way more realistic than traditional Parallax but you can expect a performance hit that worthes consideration.
  340. * @see https://doc.babylonjs.com/how_to/using_parallax_mapping
  341. */
  342. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  343. public useParallaxOcclusion: boolean;
  344. /**
  345. * Apply a scaling factor that determine which "depth" the height map should reprensent. A value between 0.05 and 0.1 is reasonnable in Parallax, you can reach 0.2 using Parallax Occlusion.
  346. */
  347. @serialize()
  348. public parallaxScaleBias = 0.05;
  349. @serialize("roughness")
  350. private _roughness = 0;
  351. /**
  352. * Helps to define how blurry the reflections should appears in the material.
  353. */
  354. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  355. public roughness: number;
  356. /**
  357. * In case of refraction, define the value of the index of refraction.
  358. * @see https://doc.babylonjs.com/how_to/reflect#how-to-obtain-reflections-and-refractions
  359. */
  360. @serialize()
  361. public indexOfRefraction = 0.98;
  362. /**
  363. * Invert the refraction texture alongside the y axis.
  364. * It can be useful with procedural textures or probe for instance.
  365. * @see https://doc.babylonjs.com/how_to/reflect#how-to-obtain-reflections-and-refractions
  366. */
  367. @serialize()
  368. public invertRefractionY = true;
  369. /**
  370. * Defines the alpha limits in alpha test mode.
  371. */
  372. @serialize()
  373. public alphaCutOff = 0.4;
  374. @serialize("useLightmapAsShadowmap")
  375. private _useLightmapAsShadowmap = false;
  376. /**
  377. * In case of light mapping, define whether the map contains light or shadow informations.
  378. */
  379. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  380. public useLightmapAsShadowmap: boolean;
  381. // Fresnel
  382. @serializeAsFresnelParameters("diffuseFresnelParameters")
  383. private _diffuseFresnelParameters: FresnelParameters;
  384. /**
  385. * Define the diffuse fresnel parameters of the material.
  386. * @see https://doc.babylonjs.com/how_to/how_to_use_fresnelparameters
  387. */
  388. @expandToProperty("_markAllSubMeshesAsFresnelDirty")
  389. public diffuseFresnelParameters: FresnelParameters;
  390. @serializeAsFresnelParameters("opacityFresnelParameters")
  391. private _opacityFresnelParameters: FresnelParameters;
  392. /**
  393. * Define the opacity fresnel parameters of the material.
  394. * @see https://doc.babylonjs.com/how_to/how_to_use_fresnelparameters
  395. */
  396. @expandToProperty("_markAllSubMeshesAsFresnelAndMiscDirty")
  397. public opacityFresnelParameters: FresnelParameters;
  398. @serializeAsFresnelParameters("reflectionFresnelParameters")
  399. private _reflectionFresnelParameters: FresnelParameters;
  400. /**
  401. * Define the reflection fresnel parameters of the material.
  402. * @see https://doc.babylonjs.com/how_to/how_to_use_fresnelparameters
  403. */
  404. @expandToProperty("_markAllSubMeshesAsFresnelDirty")
  405. public reflectionFresnelParameters: FresnelParameters;
  406. @serializeAsFresnelParameters("refractionFresnelParameters")
  407. private _refractionFresnelParameters: FresnelParameters;
  408. /**
  409. * Define the refraction fresnel parameters of the material.
  410. * @see https://doc.babylonjs.com/how_to/how_to_use_fresnelparameters
  411. */
  412. @expandToProperty("_markAllSubMeshesAsFresnelDirty")
  413. public refractionFresnelParameters: FresnelParameters;
  414. @serializeAsFresnelParameters("emissiveFresnelParameters")
  415. private _emissiveFresnelParameters: FresnelParameters;
  416. /**
  417. * Define the emissive fresnel parameters of the material.
  418. * @see https://doc.babylonjs.com/how_to/how_to_use_fresnelparameters
  419. */
  420. @expandToProperty("_markAllSubMeshesAsFresnelDirty")
  421. public emissiveFresnelParameters: FresnelParameters;
  422. @serialize("useReflectionFresnelFromSpecular")
  423. private _useReflectionFresnelFromSpecular = false;
  424. /**
  425. * If true automatically deducts the fresnels values from the material specularity.
  426. * @see https://doc.babylonjs.com/how_to/how_to_use_fresnelparameters
  427. */
  428. @expandToProperty("_markAllSubMeshesAsFresnelDirty")
  429. public useReflectionFresnelFromSpecular: boolean;
  430. @serialize("useGlossinessFromSpecularMapAlpha")
  431. private _useGlossinessFromSpecularMapAlpha = false;
  432. /**
  433. * Defines if the glossiness/roughness of the material should be read from the specular map alpha channel
  434. */
  435. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  436. public useGlossinessFromSpecularMapAlpha: boolean;
  437. @serialize("maxSimultaneousLights")
  438. private _maxSimultaneousLights = 4;
  439. /**
  440. * Defines the maximum number of lights that can be used in the material
  441. */
  442. @expandToProperty("_markAllSubMeshesAsLightsDirty")
  443. public maxSimultaneousLights: number;
  444. @serialize("invertNormalMapX")
  445. private _invertNormalMapX = false;
  446. /**
  447. * If sets to true, x component of normal map value will invert (x = 1.0 - x).
  448. */
  449. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  450. public invertNormalMapX: boolean;
  451. @serialize("invertNormalMapY")
  452. private _invertNormalMapY = false;
  453. /**
  454. * If sets to true, y component of normal map value will invert (y = 1.0 - y).
  455. */
  456. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  457. public invertNormalMapY: boolean;
  458. @serialize("twoSidedLighting")
  459. private _twoSidedLighting = false;
  460. /**
  461. * If sets to true and backfaceCulling is false, normals will be flipped on the backside.
  462. */
  463. @expandToProperty("_markAllSubMeshesAsTexturesDirty")
  464. public twoSidedLighting: boolean;
  465. /**
  466. * Default configuration related to image processing available in the standard Material.
  467. */
  468. protected _imageProcessingConfiguration: ImageProcessingConfiguration;
  469. /**
  470. * Gets the image processing configuration used either in this material.
  471. */
  472. public get imageProcessingConfiguration(): ImageProcessingConfiguration {
  473. return this._imageProcessingConfiguration;
  474. }
  475. /**
  476. * Sets the Default image processing configuration used either in the this material.
  477. *
  478. * If sets to null, the scene one is in use.
  479. */
  480. public set imageProcessingConfiguration(value: ImageProcessingConfiguration) {
  481. this._attachImageProcessingConfiguration(value);
  482. // Ensure the effect will be rebuilt.
  483. this._markAllSubMeshesAsTexturesDirty();
  484. }
  485. /**
  486. * Keep track of the image processing observer to allow dispose and replace.
  487. */
  488. private _imageProcessingObserver: Nullable<Observer<ImageProcessingConfiguration>>;
  489. /**
  490. * Attaches a new image processing configuration to the Standard Material.
  491. * @param configuration
  492. */
  493. protected _attachImageProcessingConfiguration(configuration: Nullable<ImageProcessingConfiguration>): void {
  494. if (configuration === this._imageProcessingConfiguration) {
  495. return;
  496. }
  497. // Detaches observer
  498. if (this._imageProcessingConfiguration && this._imageProcessingObserver) {
  499. this._imageProcessingConfiguration.onUpdateParameters.remove(this._imageProcessingObserver);
  500. }
  501. // Pick the scene configuration if needed
  502. if (!configuration) {
  503. this._imageProcessingConfiguration = this.getScene().imageProcessingConfiguration;
  504. }
  505. else {
  506. this._imageProcessingConfiguration = configuration;
  507. }
  508. // Attaches observer
  509. if (this._imageProcessingConfiguration) {
  510. this._imageProcessingObserver = this._imageProcessingConfiguration.onUpdateParameters.add(() => {
  511. this._markAllSubMeshesAsImageProcessingDirty();
  512. });
  513. }
  514. }
  515. /**
  516. * Gets wether the color curves effect is enabled.
  517. */
  518. public get cameraColorCurvesEnabled(): boolean {
  519. return this.imageProcessingConfiguration.colorCurvesEnabled;
  520. }
  521. /**
  522. * Sets wether the color curves effect is enabled.
  523. */
  524. public set cameraColorCurvesEnabled(value: boolean) {
  525. this.imageProcessingConfiguration.colorCurvesEnabled = value;
  526. }
  527. /**
  528. * Gets wether the color grading effect is enabled.
  529. */
  530. public get cameraColorGradingEnabled(): boolean {
  531. return this.imageProcessingConfiguration.colorGradingEnabled;
  532. }
  533. /**
  534. * Gets wether the color grading effect is enabled.
  535. */
  536. public set cameraColorGradingEnabled(value: boolean) {
  537. this.imageProcessingConfiguration.colorGradingEnabled = value;
  538. }
  539. /**
  540. * Gets wether tonemapping is enabled or not.
  541. */
  542. public get cameraToneMappingEnabled(): boolean {
  543. return this._imageProcessingConfiguration.toneMappingEnabled;
  544. }
  545. /**
  546. * Sets wether tonemapping is enabled or not
  547. */
  548. public set cameraToneMappingEnabled(value: boolean) {
  549. this._imageProcessingConfiguration.toneMappingEnabled = value;
  550. }
  551. /**
  552. * The camera exposure used on this material.
  553. * This property is here and not in the camera to allow controlling exposure without full screen post process.
  554. * This corresponds to a photographic exposure.
  555. */
  556. public get cameraExposure(): number {
  557. return this._imageProcessingConfiguration.exposure;
  558. }
  559. /**
  560. * The camera exposure used on this material.
  561. * This property is here and not in the camera to allow controlling exposure without full screen post process.
  562. * This corresponds to a photographic exposure.
  563. */
  564. public set cameraExposure(value: number) {
  565. this._imageProcessingConfiguration.exposure = value;
  566. }
  567. /**
  568. * Gets The camera contrast used on this material.
  569. */
  570. public get cameraContrast(): number {
  571. return this._imageProcessingConfiguration.contrast;
  572. }
  573. /**
  574. * Sets The camera contrast used on this material.
  575. */
  576. public set cameraContrast(value: number) {
  577. this._imageProcessingConfiguration.contrast = value;
  578. }
  579. /**
  580. * Gets the Color Grading 2D Lookup Texture.
  581. */
  582. public get cameraColorGradingTexture(): Nullable<BaseTexture> {
  583. return this._imageProcessingConfiguration.colorGradingTexture;
  584. }
  585. /**
  586. * Sets the Color Grading 2D Lookup Texture.
  587. */
  588. public set cameraColorGradingTexture(value: Nullable<BaseTexture>) {
  589. this._imageProcessingConfiguration.colorGradingTexture = value;
  590. }
  591. /**
  592. * The color grading curves provide additional color adjustmnent that is applied after any color grading transform (3D LUT).
  593. * They allow basic adjustment of saturation and small exposure adjustments, along with color filter tinting to provide white balance adjustment or more stylistic effects.
  594. * These are similar to controls found in many professional imaging or colorist software. The global controls are applied to the entire image. For advanced tuning, extra controls are provided to adjust the shadow, midtone and highlight areas of the image;
  595. * corresponding to low luminance, medium luminance, and high luminance areas respectively.
  596. */
  597. public get cameraColorCurves(): Nullable<ColorCurves> {
  598. return this._imageProcessingConfiguration.colorCurves;
  599. }
  600. /**
  601. * The color grading curves provide additional color adjustmnent that is applied after any color grading transform (3D LUT).
  602. * They allow basic adjustment of saturation and small exposure adjustments, along with color filter tinting to provide white balance adjustment or more stylistic effects.
  603. * These are similar to controls found in many professional imaging or colorist software. The global controls are applied to the entire image. For advanced tuning, extra controls are provided to adjust the shadow, midtone and highlight areas of the image;
  604. * corresponding to low luminance, medium luminance, and high luminance areas respectively.
  605. */
  606. public set cameraColorCurves(value: Nullable<ColorCurves>) {
  607. this._imageProcessingConfiguration.colorCurves = value;
  608. }
  609. /**
  610. * Can this material render to several textures at once
  611. */
  612. public get canRenderToMRT() {
  613. return true;
  614. }
  615. /**
  616. * Defines the detail map parameters for the material.
  617. */
  618. public readonly detailMap = new DetailMapConfiguration(this._markAllSubMeshesAsTexturesDirty.bind(this));
  619. protected _renderTargets = new SmartArray<RenderTargetTexture>(16);
  620. protected _worldViewProjectionMatrix = Matrix.Zero();
  621. protected _globalAmbientColor = new Color3(0, 0, 0);
  622. protected _useLogarithmicDepth: boolean;
  623. protected _rebuildInParallel = false;
  624. /**
  625. * Instantiates a new standard material.
  626. * This is the default material used in Babylon. It is the best trade off between quality
  627. * and performances.
  628. * @see https://doc.babylonjs.com/babylon101/materials
  629. * @param name Define the name of the material in the scene
  630. * @param scene Define the scene the material belong to
  631. */
  632. constructor(name: string, scene: Scene) {
  633. super(name, scene);
  634. // Setup the default processing configuration to the scene.
  635. this._attachImageProcessingConfiguration(null);
  636. this.getRenderTargetTextures = (): SmartArray<RenderTargetTexture> => {
  637. this._renderTargets.reset();
  638. if (StandardMaterial.ReflectionTextureEnabled && this._reflectionTexture && this._reflectionTexture.isRenderTarget) {
  639. this._renderTargets.push(<RenderTargetTexture>this._reflectionTexture);
  640. }
  641. if (StandardMaterial.RefractionTextureEnabled && this._refractionTexture && this._refractionTexture.isRenderTarget) {
  642. this._renderTargets.push(<RenderTargetTexture>this._refractionTexture);
  643. }
  644. return this._renderTargets;
  645. };
  646. }
  647. /**
  648. * Gets a boolean indicating that current material needs to register RTT
  649. */
  650. public get hasRenderTargetTextures(): boolean {
  651. if (StandardMaterial.ReflectionTextureEnabled && this._reflectionTexture && this._reflectionTexture.isRenderTarget) {
  652. return true;
  653. }
  654. if (StandardMaterial.RefractionTextureEnabled && this._refractionTexture && this._refractionTexture.isRenderTarget) {
  655. return true;
  656. }
  657. return false;
  658. }
  659. /**
  660. * Gets the current class name of the material e.g. "StandardMaterial"
  661. * Mainly use in serialization.
  662. * @returns the class name
  663. */
  664. public getClassName(): string {
  665. return "StandardMaterial";
  666. }
  667. /**
  668. * In case the depth buffer does not allow enough depth precision for your scene (might be the case in large scenes)
  669. * You can try switching to logarithmic depth.
  670. * @see https://doc.babylonjs.com/how_to/using_logarithmic_depth_buffer
  671. */
  672. @serialize()
  673. public get useLogarithmicDepth(): boolean {
  674. return this._useLogarithmicDepth;
  675. }
  676. public set useLogarithmicDepth(value: boolean) {
  677. this._useLogarithmicDepth = value && this.getScene().getEngine().getCaps().fragmentDepthSupported;
  678. this._markAllSubMeshesAsMiscDirty();
  679. }
  680. /**
  681. * Specifies if the material will require alpha blending
  682. * @returns a boolean specifying if alpha blending is needed
  683. */
  684. public needAlphaBlending(): boolean {
  685. if (this._disableAlphaBlending) {
  686. return false;
  687. }
  688. return (this.alpha < 1.0) || (this._opacityTexture != null) || this._shouldUseAlphaFromDiffuseTexture() || this._opacityFresnelParameters && this._opacityFresnelParameters.isEnabled;
  689. }
  690. /**
  691. * Specifies if this material should be rendered in alpha test mode
  692. * @returns a boolean specifying if an alpha test is needed.
  693. */
  694. public needAlphaTesting(): boolean {
  695. if (this._forceAlphaTest) {
  696. return true;
  697. }
  698. return this._diffuseTexture != null && this._diffuseTexture.hasAlpha && (this._transparencyMode == null || this._transparencyMode === Material.MATERIAL_ALPHATEST);
  699. }
  700. protected _shouldUseAlphaFromDiffuseTexture(): boolean {
  701. return this._diffuseTexture != null && this._diffuseTexture.hasAlpha && this._useAlphaFromDiffuseTexture && this._transparencyMode !== Material.MATERIAL_OPAQUE;
  702. }
  703. /**
  704. * Get the texture used for alpha test purpose.
  705. * @returns the diffuse texture in case of the standard material.
  706. */
  707. public getAlphaTestTexture(): Nullable<BaseTexture> {
  708. return this._diffuseTexture;
  709. }
  710. /**
  711. * Get if the submesh is ready to be used and all its information available.
  712. * Child classes can use it to update shaders
  713. * @param mesh defines the mesh to check
  714. * @param subMesh defines which submesh to check
  715. * @param useInstances specifies that instances should be used
  716. * @returns a boolean indicating that the submesh is ready or not
  717. */
  718. public isReadyForSubMesh(mesh: AbstractMesh, subMesh: SubMesh, useInstances: boolean = false): boolean {
  719. if (subMesh.effect && this.isFrozen) {
  720. if (subMesh.effect._wasPreviouslyReady) {
  721. return true;
  722. }
  723. }
  724. if (!subMesh._materialDefines) {
  725. subMesh._materialDefines = new StandardMaterialDefines();
  726. }
  727. var scene = this.getScene();
  728. var defines = <StandardMaterialDefines>subMesh._materialDefines;
  729. if (this._isReadyForSubMesh(subMesh)) {
  730. return true;
  731. }
  732. var engine = scene.getEngine();
  733. // Lights
  734. defines._needNormals = MaterialHelper.PrepareDefinesForLights(scene, mesh, defines, true, this._maxSimultaneousLights, this._disableLighting);
  735. // Multiview
  736. MaterialHelper.PrepareDefinesForMultiview(scene, defines);
  737. // PrePass
  738. MaterialHelper.PrepareDefinesForPrePass(scene, defines, this.canRenderToMRT);
  739. // Textures
  740. if (defines._areTexturesDirty) {
  741. defines._needUVs = false;
  742. defines.MAINUV1 = false;
  743. defines.MAINUV2 = false;
  744. if (scene.texturesEnabled) {
  745. if (this._diffuseTexture && StandardMaterial.DiffuseTextureEnabled) {
  746. if (!this._diffuseTexture.isReadyOrNotBlocking()) {
  747. return false;
  748. } else {
  749. MaterialHelper.PrepareDefinesForMergedUV(this._diffuseTexture, defines, "DIFFUSE");
  750. }
  751. } else {
  752. defines.DIFFUSE = false;
  753. }
  754. if (this._ambientTexture && StandardMaterial.AmbientTextureEnabled) {
  755. if (!this._ambientTexture.isReadyOrNotBlocking()) {
  756. return false;
  757. } else {
  758. MaterialHelper.PrepareDefinesForMergedUV(this._ambientTexture, defines, "AMBIENT");
  759. }
  760. } else {
  761. defines.AMBIENT = false;
  762. }
  763. if (this._opacityTexture && StandardMaterial.OpacityTextureEnabled) {
  764. if (!this._opacityTexture.isReadyOrNotBlocking()) {
  765. return false;
  766. } else {
  767. MaterialHelper.PrepareDefinesForMergedUV(this._opacityTexture, defines, "OPACITY");
  768. defines.OPACITYRGB = this._opacityTexture.getAlphaFromRGB;
  769. }
  770. } else {
  771. defines.OPACITY = false;
  772. }
  773. if (this._reflectionTexture && StandardMaterial.ReflectionTextureEnabled) {
  774. if (!this._reflectionTexture.isReadyOrNotBlocking()) {
  775. return false;
  776. } else {
  777. defines._needNormals = true;
  778. defines.REFLECTION = true;
  779. defines.ROUGHNESS = (this._roughness > 0);
  780. defines.REFLECTIONOVERALPHA = this._useReflectionOverAlpha;
  781. defines.INVERTCUBICMAP = (this._reflectionTexture.coordinatesMode === Texture.INVCUBIC_MODE);
  782. defines.REFLECTIONMAP_3D = this._reflectionTexture.isCube;
  783. defines.RGBDREFLECTION = this._reflectionTexture.isRGBD;
  784. switch (this._reflectionTexture.coordinatesMode) {
  785. case Texture.EXPLICIT_MODE:
  786. defines.setReflectionMode("REFLECTIONMAP_EXPLICIT");
  787. break;
  788. case Texture.PLANAR_MODE:
  789. defines.setReflectionMode("REFLECTIONMAP_PLANAR");
  790. break;
  791. case Texture.PROJECTION_MODE:
  792. defines.setReflectionMode("REFLECTIONMAP_PROJECTION");
  793. break;
  794. case Texture.SKYBOX_MODE:
  795. defines.setReflectionMode("REFLECTIONMAP_SKYBOX");
  796. break;
  797. case Texture.SPHERICAL_MODE:
  798. defines.setReflectionMode("REFLECTIONMAP_SPHERICAL");
  799. break;
  800. case Texture.EQUIRECTANGULAR_MODE:
  801. defines.setReflectionMode("REFLECTIONMAP_EQUIRECTANGULAR");
  802. break;
  803. case Texture.FIXED_EQUIRECTANGULAR_MODE:
  804. defines.setReflectionMode("REFLECTIONMAP_EQUIRECTANGULAR_FIXED");
  805. break;
  806. case Texture.FIXED_EQUIRECTANGULAR_MIRRORED_MODE:
  807. defines.setReflectionMode("REFLECTIONMAP_MIRROREDEQUIRECTANGULAR_FIXED");
  808. break;
  809. case Texture.CUBIC_MODE:
  810. case Texture.INVCUBIC_MODE:
  811. default:
  812. defines.setReflectionMode("REFLECTIONMAP_CUBIC");
  813. break;
  814. }
  815. defines.USE_LOCAL_REFLECTIONMAP_CUBIC = (<any>this._reflectionTexture).boundingBoxSize ? true : false;
  816. }
  817. } else {
  818. defines.REFLECTION = false;
  819. }
  820. if (this._emissiveTexture && StandardMaterial.EmissiveTextureEnabled) {
  821. if (!this._emissiveTexture.isReadyOrNotBlocking()) {
  822. return false;
  823. } else {
  824. MaterialHelper.PrepareDefinesForMergedUV(this._emissiveTexture, defines, "EMISSIVE");
  825. }
  826. } else {
  827. defines.EMISSIVE = false;
  828. }
  829. if (this._lightmapTexture && StandardMaterial.LightmapTextureEnabled) {
  830. if (!this._lightmapTexture.isReadyOrNotBlocking()) {
  831. return false;
  832. } else {
  833. MaterialHelper.PrepareDefinesForMergedUV(this._lightmapTexture, defines, "LIGHTMAP");
  834. defines.USELIGHTMAPASSHADOWMAP = this._useLightmapAsShadowmap;
  835. defines.RGBDLIGHTMAP = this._lightmapTexture.isRGBD;
  836. }
  837. } else {
  838. defines.LIGHTMAP = false;
  839. }
  840. if (this._specularTexture && StandardMaterial.SpecularTextureEnabled) {
  841. if (!this._specularTexture.isReadyOrNotBlocking()) {
  842. return false;
  843. } else {
  844. MaterialHelper.PrepareDefinesForMergedUV(this._specularTexture, defines, "SPECULAR");
  845. defines.GLOSSINESS = this._useGlossinessFromSpecularMapAlpha;
  846. }
  847. } else {
  848. defines.SPECULAR = false;
  849. }
  850. if (scene.getEngine().getCaps().standardDerivatives && this._bumpTexture && StandardMaterial.BumpTextureEnabled) {
  851. // Bump texure can not be not blocking.
  852. if (!this._bumpTexture.isReady()) {
  853. return false;
  854. } else {
  855. MaterialHelper.PrepareDefinesForMergedUV(this._bumpTexture, defines, "BUMP");
  856. defines.PARALLAX = this._useParallax;
  857. defines.PARALLAXOCCLUSION = this._useParallaxOcclusion;
  858. }
  859. defines.OBJECTSPACE_NORMALMAP = this._useObjectSpaceNormalMap;
  860. } else {
  861. defines.BUMP = false;
  862. }
  863. if (this._refractionTexture && StandardMaterial.RefractionTextureEnabled) {
  864. if (!this._refractionTexture.isReadyOrNotBlocking()) {
  865. return false;
  866. } else {
  867. defines._needUVs = true;
  868. defines.REFRACTION = true;
  869. defines.REFRACTIONMAP_3D = this._refractionTexture.isCube;
  870. defines.RGBDREFRACTION = this._refractionTexture.isRGBD;
  871. }
  872. } else {
  873. defines.REFRACTION = false;
  874. }
  875. defines.TWOSIDEDLIGHTING = !this._backFaceCulling && this._twoSidedLighting;
  876. } else {
  877. defines.DIFFUSE = false;
  878. defines.AMBIENT = false;
  879. defines.OPACITY = false;
  880. defines.REFLECTION = false;
  881. defines.EMISSIVE = false;
  882. defines.LIGHTMAP = false;
  883. defines.BUMP = false;
  884. defines.REFRACTION = false;
  885. }
  886. defines.ALPHAFROMDIFFUSE = this._shouldUseAlphaFromDiffuseTexture();
  887. defines.EMISSIVEASILLUMINATION = this._useEmissiveAsIllumination;
  888. defines.LINKEMISSIVEWITHDIFFUSE = this._linkEmissiveWithDiffuse;
  889. defines.SPECULAROVERALPHA = this._useSpecularOverAlpha;
  890. defines.PREMULTIPLYALPHA = (this.alphaMode === Constants.ALPHA_PREMULTIPLIED || this.alphaMode === Constants.ALPHA_PREMULTIPLIED_PORTERDUFF);
  891. defines.ALPHATEST_AFTERALLALPHACOMPUTATIONS = this.transparencyMode !== null;
  892. defines.ALPHABLEND = this.transparencyMode === null || this.needAlphaBlendingForMesh(mesh); // check on null for backward compatibility
  893. }
  894. if (!this.detailMap.isReadyForSubMesh(defines, scene)) {
  895. return false;
  896. }
  897. if (defines._areImageProcessingDirty && this._imageProcessingConfiguration) {
  898. if (!this._imageProcessingConfiguration.isReady()) {
  899. return false;
  900. }
  901. this._imageProcessingConfiguration.prepareDefines(defines);
  902. defines.IS_REFLECTION_LINEAR = (this.reflectionTexture != null && !this.reflectionTexture.gammaSpace);
  903. defines.IS_REFRACTION_LINEAR = (this.refractionTexture != null && !this.refractionTexture.gammaSpace);
  904. }
  905. if (defines._areFresnelDirty) {
  906. if (StandardMaterial.FresnelEnabled) {
  907. // Fresnel
  908. if (this._diffuseFresnelParameters || this._opacityFresnelParameters ||
  909. this._emissiveFresnelParameters || this._refractionFresnelParameters ||
  910. this._reflectionFresnelParameters) {
  911. defines.DIFFUSEFRESNEL = (this._diffuseFresnelParameters && this._diffuseFresnelParameters.isEnabled);
  912. defines.OPACITYFRESNEL = (this._opacityFresnelParameters && this._opacityFresnelParameters.isEnabled);
  913. defines.REFLECTIONFRESNEL = (this._reflectionFresnelParameters && this._reflectionFresnelParameters.isEnabled);
  914. defines.REFLECTIONFRESNELFROMSPECULAR = this._useReflectionFresnelFromSpecular;
  915. defines.REFRACTIONFRESNEL = (this._refractionFresnelParameters && this._refractionFresnelParameters.isEnabled);
  916. defines.EMISSIVEFRESNEL = (this._emissiveFresnelParameters && this._emissiveFresnelParameters.isEnabled);
  917. defines._needNormals = true;
  918. defines.FRESNEL = true;
  919. }
  920. } else {
  921. defines.FRESNEL = false;
  922. }
  923. }
  924. // Misc.
  925. MaterialHelper.PrepareDefinesForMisc(mesh, scene, this._useLogarithmicDepth, this.pointsCloud, this.fogEnabled, this._shouldTurnAlphaTestOn(mesh) || this._forceAlphaTest, defines);
  926. // Attribs
  927. MaterialHelper.PrepareDefinesForAttributes(mesh, defines, true, true, true);
  928. // Values that need to be evaluated on every frame
  929. MaterialHelper.PrepareDefinesForFrameBoundValues(scene, engine, defines, useInstances, null, subMesh.getRenderingMesh().hasThinInstances);
  930. // External config
  931. this.detailMap.prepareDefines(defines, scene);
  932. // Get correct effect
  933. if (defines.isDirty) {
  934. const lightDisposed = defines._areLightsDisposed;
  935. defines.markAsProcessed();
  936. // Fallbacks
  937. var fallbacks = new EffectFallbacks();
  938. if (defines.REFLECTION) {
  939. fallbacks.addFallback(0, "REFLECTION");
  940. }
  941. if (defines.SPECULAR) {
  942. fallbacks.addFallback(0, "SPECULAR");
  943. }
  944. if (defines.BUMP) {
  945. fallbacks.addFallback(0, "BUMP");
  946. }
  947. if (defines.PARALLAX) {
  948. fallbacks.addFallback(1, "PARALLAX");
  949. }
  950. if (defines.PARALLAXOCCLUSION) {
  951. fallbacks.addFallback(0, "PARALLAXOCCLUSION");
  952. }
  953. if (defines.SPECULAROVERALPHA) {
  954. fallbacks.addFallback(0, "SPECULAROVERALPHA");
  955. }
  956. if (defines.FOG) {
  957. fallbacks.addFallback(1, "FOG");
  958. }
  959. if (defines.POINTSIZE) {
  960. fallbacks.addFallback(0, "POINTSIZE");
  961. }
  962. if (defines.LOGARITHMICDEPTH) {
  963. fallbacks.addFallback(0, "LOGARITHMICDEPTH");
  964. }
  965. MaterialHelper.HandleFallbacksForShadows(defines, fallbacks, this._maxSimultaneousLights);
  966. if (defines.SPECULARTERM) {
  967. fallbacks.addFallback(0, "SPECULARTERM");
  968. }
  969. if (defines.DIFFUSEFRESNEL) {
  970. fallbacks.addFallback(1, "DIFFUSEFRESNEL");
  971. }
  972. if (defines.OPACITYFRESNEL) {
  973. fallbacks.addFallback(2, "OPACITYFRESNEL");
  974. }
  975. if (defines.REFLECTIONFRESNEL) {
  976. fallbacks.addFallback(3, "REFLECTIONFRESNEL");
  977. }
  978. if (defines.EMISSIVEFRESNEL) {
  979. fallbacks.addFallback(4, "EMISSIVEFRESNEL");
  980. }
  981. if (defines.FRESNEL) {
  982. fallbacks.addFallback(4, "FRESNEL");
  983. }
  984. if (defines.MULTIVIEW) {
  985. fallbacks.addFallback(0, "MULTIVIEW");
  986. }
  987. //Attributes
  988. var attribs = [VertexBuffer.PositionKind];
  989. if (defines.NORMAL) {
  990. attribs.push(VertexBuffer.NormalKind);
  991. }
  992. if (defines.UV1) {
  993. attribs.push(VertexBuffer.UVKind);
  994. }
  995. if (defines.UV2) {
  996. attribs.push(VertexBuffer.UV2Kind);
  997. }
  998. if (defines.VERTEXCOLOR) {
  999. attribs.push(VertexBuffer.ColorKind);
  1000. }
  1001. MaterialHelper.PrepareAttributesForBones(attribs, mesh, defines, fallbacks);
  1002. MaterialHelper.PrepareAttributesForInstances(attribs, defines);
  1003. MaterialHelper.PrepareAttributesForMorphTargets(attribs, mesh, defines);
  1004. var shaderName = "default";
  1005. var uniforms = ["world", "view", "viewProjection", "vEyePosition", "vLightsType", "vAmbientColor", "vDiffuseColor", "vSpecularColor", "vEmissiveColor", "visibility",
  1006. "vFogInfos", "vFogColor", "pointSize",
  1007. "vDiffuseInfos", "vAmbientInfos", "vOpacityInfos", "vReflectionInfos", "vEmissiveInfos", "vSpecularInfos", "vBumpInfos", "vLightmapInfos", "vRefractionInfos",
  1008. "mBones",
  1009. "vClipPlane", "vClipPlane2", "vClipPlane3", "vClipPlane4", "vClipPlane5", "vClipPlane6", "diffuseMatrix", "ambientMatrix", "opacityMatrix", "reflectionMatrix", "emissiveMatrix", "specularMatrix", "bumpMatrix", "normalMatrix", "lightmapMatrix", "refractionMatrix",
  1010. "diffuseLeftColor", "diffuseRightColor", "opacityParts", "reflectionLeftColor", "reflectionRightColor", "emissiveLeftColor", "emissiveRightColor", "refractionLeftColor", "refractionRightColor",
  1011. "vReflectionPosition", "vReflectionSize",
  1012. "logarithmicDepthConstant", "vTangentSpaceParams", "alphaCutOff", "boneTextureWidth"
  1013. ];
  1014. var samplers = ["diffuseSampler", "ambientSampler", "opacitySampler", "reflectionCubeSampler",
  1015. "reflection2DSampler", "emissiveSampler", "specularSampler", "bumpSampler", "lightmapSampler",
  1016. "refractionCubeSampler", "refraction2DSampler", "boneSampler"];
  1017. var uniformBuffers = ["Material", "Scene"];
  1018. DetailMapConfiguration.AddUniforms(uniforms);
  1019. DetailMapConfiguration.AddSamplers(samplers);
  1020. if (ImageProcessingConfiguration) {
  1021. ImageProcessingConfiguration.PrepareUniforms(uniforms, defines);
  1022. ImageProcessingConfiguration.PrepareSamplers(samplers, defines);
  1023. }
  1024. MaterialHelper.PrepareUniformsAndSamplersList(<IEffectCreationOptions>{
  1025. uniformsNames: uniforms,
  1026. uniformBuffersNames: uniformBuffers,
  1027. samplers: samplers,
  1028. defines: defines,
  1029. maxSimultaneousLights: this._maxSimultaneousLights
  1030. });
  1031. const csnrOptions: ICustomShaderNameResolveOptions = {};
  1032. if (this.customShaderNameResolve) {
  1033. shaderName = this.customShaderNameResolve(shaderName, uniforms, uniformBuffers, samplers, defines, attribs, csnrOptions);
  1034. }
  1035. var join = defines.toString();
  1036. let previousEffect = subMesh.effect;
  1037. let effect = scene.getEngine().createEffect(shaderName, <IEffectCreationOptions>{
  1038. attributes: attribs,
  1039. uniformsNames: uniforms,
  1040. uniformBuffersNames: uniformBuffers,
  1041. samplers: samplers,
  1042. defines: join,
  1043. fallbacks: fallbacks,
  1044. onCompiled: this.onCompiled,
  1045. onError: this.onError,
  1046. indexParameters: { maxSimultaneousLights: this._maxSimultaneousLights, maxSimultaneousMorphTargets: defines.NUM_MORPH_INFLUENCERS },
  1047. processFinalCode: csnrOptions.processFinalCode,
  1048. multiTarget: defines.PREPASS
  1049. }, engine);
  1050. if (effect) {
  1051. if (this._onEffectCreatedObservable) {
  1052. onCreatedEffectParameters.effect = effect;
  1053. onCreatedEffectParameters.subMesh = subMesh;
  1054. this._onEffectCreatedObservable.notifyObservers(onCreatedEffectParameters);
  1055. }
  1056. // Use previous effect while new one is compiling
  1057. if (this.allowShaderHotSwapping && previousEffect && !effect.isReady()) {
  1058. effect = previousEffect;
  1059. this._rebuildInParallel = true;
  1060. defines.markAsUnprocessed();
  1061. if (lightDisposed) {
  1062. // re register in case it takes more than one frame.
  1063. defines._areLightsDisposed = true;
  1064. return false;
  1065. }
  1066. } else {
  1067. this._rebuildInParallel = false;
  1068. scene.resetCachedMaterial();
  1069. subMesh.setEffect(effect, defines);
  1070. this.buildUniformLayout();
  1071. }
  1072. }
  1073. }
  1074. if (!subMesh.effect || !subMesh.effect.isReady()) {
  1075. return false;
  1076. }
  1077. defines._renderId = scene.getRenderId();
  1078. subMesh.effect._wasPreviouslyReady = true;
  1079. return true;
  1080. }
  1081. /**
  1082. * Builds the material UBO layouts.
  1083. * Used internally during the effect preparation.
  1084. */
  1085. public buildUniformLayout(): void {
  1086. // Order is important !
  1087. let ubo = this._uniformBuffer;
  1088. ubo.addUniform("diffuseLeftColor", 4);
  1089. ubo.addUniform("diffuseRightColor", 4);
  1090. ubo.addUniform("opacityParts", 4);
  1091. ubo.addUniform("reflectionLeftColor", 4);
  1092. ubo.addUniform("reflectionRightColor", 4);
  1093. ubo.addUniform("refractionLeftColor", 4);
  1094. ubo.addUniform("refractionRightColor", 4);
  1095. ubo.addUniform("emissiveLeftColor", 4);
  1096. ubo.addUniform("emissiveRightColor", 4);
  1097. ubo.addUniform("vDiffuseInfos", 2);
  1098. ubo.addUniform("vAmbientInfos", 2);
  1099. ubo.addUniform("vOpacityInfos", 2);
  1100. ubo.addUniform("vReflectionInfos", 2);
  1101. ubo.addUniform("vReflectionPosition", 3);
  1102. ubo.addUniform("vReflectionSize", 3);
  1103. ubo.addUniform("vEmissiveInfos", 2);
  1104. ubo.addUniform("vLightmapInfos", 2);
  1105. ubo.addUniform("vSpecularInfos", 2);
  1106. ubo.addUniform("vBumpInfos", 3);
  1107. ubo.addUniform("diffuseMatrix", 16);
  1108. ubo.addUniform("ambientMatrix", 16);
  1109. ubo.addUniform("opacityMatrix", 16);
  1110. ubo.addUniform("reflectionMatrix", 16);
  1111. ubo.addUniform("emissiveMatrix", 16);
  1112. ubo.addUniform("lightmapMatrix", 16);
  1113. ubo.addUniform("specularMatrix", 16);
  1114. ubo.addUniform("bumpMatrix", 16);
  1115. ubo.addUniform("vTangentSpaceParams", 2);
  1116. ubo.addUniform("pointSize", 1);
  1117. ubo.addUniform("refractionMatrix", 16);
  1118. ubo.addUniform("vRefractionInfos", 4);
  1119. ubo.addUniform("vSpecularColor", 4);
  1120. ubo.addUniform("vEmissiveColor", 3);
  1121. ubo.addUniform("visibility", 1);
  1122. ubo.addUniform("vDiffuseColor", 4);
  1123. DetailMapConfiguration.PrepareUniformBuffer(ubo);
  1124. ubo.create();
  1125. }
  1126. /**
  1127. * Unbinds the material from the mesh
  1128. */
  1129. public unbind(): void {
  1130. if (this._activeEffect) {
  1131. let needFlag = false;
  1132. if (this._reflectionTexture && this._reflectionTexture.isRenderTarget) {
  1133. this._activeEffect.setTexture("reflection2DSampler", null);
  1134. needFlag = true;
  1135. }
  1136. if (this._refractionTexture && this._refractionTexture.isRenderTarget) {
  1137. this._activeEffect.setTexture("refraction2DSampler", null);
  1138. needFlag = true;
  1139. }
  1140. if (needFlag) {
  1141. this._markAllSubMeshesAsTexturesDirty();
  1142. }
  1143. }
  1144. super.unbind();
  1145. }
  1146. /**
  1147. * Binds the submesh to this material by preparing the effect and shader to draw
  1148. * @param world defines the world transformation matrix
  1149. * @param mesh defines the mesh containing the submesh
  1150. * @param subMesh defines the submesh to bind the material to
  1151. */
  1152. public bindForSubMesh(world: Matrix, mesh: Mesh, subMesh: SubMesh): void {
  1153. var scene = this.getScene();
  1154. var defines = <StandardMaterialDefines>subMesh._materialDefines;
  1155. if (!defines) {
  1156. return;
  1157. }
  1158. var effect = subMesh.effect;
  1159. if (!effect) {
  1160. return;
  1161. }
  1162. this._activeEffect = effect;
  1163. // Matrices
  1164. if (!defines.INSTANCES || defines.THIN_INSTANCES) {
  1165. this.bindOnlyWorldMatrix(world);
  1166. }
  1167. // Normal Matrix
  1168. if (defines.OBJECTSPACE_NORMALMAP) {
  1169. world.toNormalMatrix(this._normalMatrix);
  1170. this.bindOnlyNormalMatrix(this._normalMatrix);
  1171. }
  1172. let mustRebind = this._mustRebind(scene, effect, mesh.visibility);
  1173. // Bones
  1174. MaterialHelper.BindBonesParameters(mesh, effect);
  1175. let ubo = this._uniformBuffer;
  1176. if (mustRebind) {
  1177. ubo.bindToEffect(effect, "Material");
  1178. this.bindViewProjection(effect);
  1179. if (!ubo.useUbo || !this.isFrozen || !ubo.isSync) {
  1180. if (StandardMaterial.FresnelEnabled && defines.FRESNEL) {
  1181. // Fresnel
  1182. if (this.diffuseFresnelParameters && this.diffuseFresnelParameters.isEnabled) {
  1183. ubo.updateColor4("diffuseLeftColor", this.diffuseFresnelParameters.leftColor, this.diffuseFresnelParameters.power);
  1184. ubo.updateColor4("diffuseRightColor", this.diffuseFresnelParameters.rightColor, this.diffuseFresnelParameters.bias);
  1185. }
  1186. if (this.opacityFresnelParameters && this.opacityFresnelParameters.isEnabled) {
  1187. ubo.updateColor4("opacityParts", new Color3(this.opacityFresnelParameters.leftColor.toLuminance(), this.opacityFresnelParameters.rightColor.toLuminance(), this.opacityFresnelParameters.bias), this.opacityFresnelParameters.power);
  1188. }
  1189. if (this.reflectionFresnelParameters && this.reflectionFresnelParameters.isEnabled) {
  1190. ubo.updateColor4("reflectionLeftColor", this.reflectionFresnelParameters.leftColor, this.reflectionFresnelParameters.power);
  1191. ubo.updateColor4("reflectionRightColor", this.reflectionFresnelParameters.rightColor, this.reflectionFresnelParameters.bias);
  1192. }
  1193. if (this.refractionFresnelParameters && this.refractionFresnelParameters.isEnabled) {
  1194. ubo.updateColor4("refractionLeftColor", this.refractionFresnelParameters.leftColor, this.refractionFresnelParameters.power);
  1195. ubo.updateColor4("refractionRightColor", this.refractionFresnelParameters.rightColor, this.refractionFresnelParameters.bias);
  1196. }
  1197. if (this.emissiveFresnelParameters && this.emissiveFresnelParameters.isEnabled) {
  1198. ubo.updateColor4("emissiveLeftColor", this.emissiveFresnelParameters.leftColor, this.emissiveFresnelParameters.power);
  1199. ubo.updateColor4("emissiveRightColor", this.emissiveFresnelParameters.rightColor, this.emissiveFresnelParameters.bias);
  1200. }
  1201. }
  1202. // Textures
  1203. if (scene.texturesEnabled) {
  1204. if (this._diffuseTexture && StandardMaterial.DiffuseTextureEnabled) {
  1205. ubo.updateFloat2("vDiffuseInfos", this._diffuseTexture.coordinatesIndex, this._diffuseTexture.level);
  1206. MaterialHelper.BindTextureMatrix(this._diffuseTexture, ubo, "diffuse");
  1207. if (this._diffuseTexture.hasAlpha) {
  1208. effect.setFloat("alphaCutOff", this.alphaCutOff);
  1209. }
  1210. }
  1211. if (this._ambientTexture && StandardMaterial.AmbientTextureEnabled) {
  1212. ubo.updateFloat2("vAmbientInfos", this._ambientTexture.coordinatesIndex, this._ambientTexture.level);
  1213. MaterialHelper.BindTextureMatrix(this._ambientTexture, ubo, "ambient");
  1214. }
  1215. if (this._opacityTexture && StandardMaterial.OpacityTextureEnabled) {
  1216. ubo.updateFloat2("vOpacityInfos", this._opacityTexture.coordinatesIndex, this._opacityTexture.level);
  1217. MaterialHelper.BindTextureMatrix(this._opacityTexture, ubo, "opacity");
  1218. }
  1219. if (this._reflectionTexture && StandardMaterial.ReflectionTextureEnabled) {
  1220. ubo.updateFloat2("vReflectionInfos", this._reflectionTexture.level, this.roughness);
  1221. ubo.updateMatrix("reflectionMatrix", this._reflectionTexture.getReflectionTextureMatrix());
  1222. if ((<any>this._reflectionTexture).boundingBoxSize) {
  1223. let cubeTexture = <CubeTexture>this._reflectionTexture;
  1224. ubo.updateVector3("vReflectionPosition", cubeTexture.boundingBoxPosition);
  1225. ubo.updateVector3("vReflectionSize", cubeTexture.boundingBoxSize);
  1226. }
  1227. }
  1228. if (this._emissiveTexture && StandardMaterial.EmissiveTextureEnabled) {
  1229. ubo.updateFloat2("vEmissiveInfos", this._emissiveTexture.coordinatesIndex, this._emissiveTexture.level);
  1230. MaterialHelper.BindTextureMatrix(this._emissiveTexture, ubo, "emissive");
  1231. }
  1232. if (this._lightmapTexture && StandardMaterial.LightmapTextureEnabled) {
  1233. ubo.updateFloat2("vLightmapInfos", this._lightmapTexture.coordinatesIndex, this._lightmapTexture.level);
  1234. MaterialHelper.BindTextureMatrix(this._lightmapTexture, ubo, "lightmap");
  1235. }
  1236. if (this._specularTexture && StandardMaterial.SpecularTextureEnabled) {
  1237. ubo.updateFloat2("vSpecularInfos", this._specularTexture.coordinatesIndex, this._specularTexture.level);
  1238. MaterialHelper.BindTextureMatrix(this._specularTexture, ubo, "specular");
  1239. }
  1240. if (this._bumpTexture && scene.getEngine().getCaps().standardDerivatives && StandardMaterial.BumpTextureEnabled) {
  1241. ubo.updateFloat3("vBumpInfos", this._bumpTexture.coordinatesIndex, 1.0 / this._bumpTexture.level, this.parallaxScaleBias);
  1242. MaterialHelper.BindTextureMatrix(this._bumpTexture, ubo, "bump");
  1243. if (scene._mirroredCameraPosition) {
  1244. ubo.updateFloat2("vTangentSpaceParams", this._invertNormalMapX ? 1.0 : -1.0, this._invertNormalMapY ? 1.0 : -1.0);
  1245. } else {
  1246. ubo.updateFloat2("vTangentSpaceParams", this._invertNormalMapX ? -1.0 : 1.0, this._invertNormalMapY ? -1.0 : 1.0);
  1247. }
  1248. }
  1249. if (this._refractionTexture && StandardMaterial.RefractionTextureEnabled) {
  1250. var depth = 1.0;
  1251. if (!this._refractionTexture.isCube) {
  1252. ubo.updateMatrix("refractionMatrix", this._refractionTexture.getReflectionTextureMatrix());
  1253. if ((<any>this._refractionTexture).depth) {
  1254. depth = (<any>this._refractionTexture).depth;
  1255. }
  1256. }
  1257. ubo.updateFloat4("vRefractionInfos", this._refractionTexture.level, this.indexOfRefraction, depth, this.invertRefractionY ? -1 : 1);
  1258. }
  1259. }
  1260. // Point size
  1261. if (this.pointsCloud) {
  1262. ubo.updateFloat("pointSize", this.pointSize);
  1263. }
  1264. if (defines.SPECULARTERM) {
  1265. ubo.updateColor4("vSpecularColor", this.specularColor, this.specularPower);
  1266. }
  1267. ubo.updateColor3("vEmissiveColor", StandardMaterial.EmissiveTextureEnabled ? this.emissiveColor : Color3.BlackReadOnly);
  1268. // Diffuse
  1269. ubo.updateColor4("vDiffuseColor", this.diffuseColor, this.alpha);
  1270. }
  1271. // Visibility
  1272. ubo.updateFloat("visibility", mesh.visibility);
  1273. // Textures
  1274. if (scene.texturesEnabled) {
  1275. if (this._diffuseTexture && StandardMaterial.DiffuseTextureEnabled) {
  1276. effect.setTexture("diffuseSampler", this._diffuseTexture);
  1277. }
  1278. if (this._ambientTexture && StandardMaterial.AmbientTextureEnabled) {
  1279. effect.setTexture("ambientSampler", this._ambientTexture);
  1280. }
  1281. if (this._opacityTexture && StandardMaterial.OpacityTextureEnabled) {
  1282. effect.setTexture("opacitySampler", this._opacityTexture);
  1283. }
  1284. if (this._reflectionTexture && StandardMaterial.ReflectionTextureEnabled) {
  1285. if (this._reflectionTexture.isCube) {
  1286. effect.setTexture("reflectionCubeSampler", this._reflectionTexture);
  1287. } else {
  1288. effect.setTexture("reflection2DSampler", this._reflectionTexture);
  1289. }
  1290. }
  1291. if (this._emissiveTexture && StandardMaterial.EmissiveTextureEnabled) {
  1292. effect.setTexture("emissiveSampler", this._emissiveTexture);
  1293. }
  1294. if (this._lightmapTexture && StandardMaterial.LightmapTextureEnabled) {
  1295. effect.setTexture("lightmapSampler", this._lightmapTexture);
  1296. }
  1297. if (this._specularTexture && StandardMaterial.SpecularTextureEnabled) {
  1298. effect.setTexture("specularSampler", this._specularTexture);
  1299. }
  1300. if (this._bumpTexture && scene.getEngine().getCaps().standardDerivatives && StandardMaterial.BumpTextureEnabled) {
  1301. effect.setTexture("bumpSampler", this._bumpTexture);
  1302. }
  1303. if (this._refractionTexture && StandardMaterial.RefractionTextureEnabled) {
  1304. var depth = 1.0;
  1305. if (this._refractionTexture.isCube) {
  1306. effect.setTexture("refractionCubeSampler", this._refractionTexture);
  1307. } else {
  1308. effect.setTexture("refraction2DSampler", this._refractionTexture);
  1309. }
  1310. }
  1311. }
  1312. this.detailMap.bindForSubMesh(ubo, scene, this.isFrozen);
  1313. // Clip plane
  1314. MaterialHelper.BindClipPlane(effect, scene);
  1315. // Colors
  1316. scene.ambientColor.multiplyToRef(this.ambientColor, this._globalAmbientColor);
  1317. MaterialHelper.BindEyePosition(effect, scene);
  1318. effect.setColor3("vAmbientColor", this._globalAmbientColor);
  1319. }
  1320. if (mustRebind || !this.isFrozen) {
  1321. // Lights
  1322. if (scene.lightsEnabled && !this._disableLighting) {
  1323. MaterialHelper.BindLights(scene, mesh, effect, defines, this._maxSimultaneousLights, this._rebuildInParallel);
  1324. }
  1325. // View
  1326. if (scene.fogEnabled && mesh.applyFog && scene.fogMode !== Scene.FOGMODE_NONE || this._reflectionTexture || this._refractionTexture) {
  1327. this.bindView(effect);
  1328. }
  1329. // Fog
  1330. MaterialHelper.BindFogParameters(scene, mesh, effect);
  1331. // Morph targets
  1332. if (defines.NUM_MORPH_INFLUENCERS) {
  1333. MaterialHelper.BindMorphTargetParameters(mesh, effect);
  1334. }
  1335. // Log. depth
  1336. if (this.useLogarithmicDepth) {
  1337. MaterialHelper.BindLogDepth(defines, effect, scene);
  1338. }
  1339. // image processing
  1340. if (this._imageProcessingConfiguration && !this._imageProcessingConfiguration.applyByPostProcess) {
  1341. this._imageProcessingConfiguration.bind(this._activeEffect);
  1342. }
  1343. }
  1344. ubo.update();
  1345. this._afterBind(mesh, this._activeEffect);
  1346. }
  1347. /**
  1348. * Get the list of animatables in the material.
  1349. * @returns the list of animatables object used in the material
  1350. */
  1351. public getAnimatables(): IAnimatable[] {
  1352. var results = [];
  1353. if (this._diffuseTexture && this._diffuseTexture.animations && this._diffuseTexture.animations.length > 0) {
  1354. results.push(this._diffuseTexture);
  1355. }
  1356. if (this._ambientTexture && this._ambientTexture.animations && this._ambientTexture.animations.length > 0) {
  1357. results.push(this._ambientTexture);
  1358. }
  1359. if (this._opacityTexture && this._opacityTexture.animations && this._opacityTexture.animations.length > 0) {
  1360. results.push(this._opacityTexture);
  1361. }
  1362. if (this._reflectionTexture && this._reflectionTexture.animations && this._reflectionTexture.animations.length > 0) {
  1363. results.push(this._reflectionTexture);
  1364. }
  1365. if (this._emissiveTexture && this._emissiveTexture.animations && this._emissiveTexture.animations.length > 0) {
  1366. results.push(this._emissiveTexture);
  1367. }
  1368. if (this._specularTexture && this._specularTexture.animations && this._specularTexture.animations.length > 0) {
  1369. results.push(this._specularTexture);
  1370. }
  1371. if (this._bumpTexture && this._bumpTexture.animations && this._bumpTexture.animations.length > 0) {
  1372. results.push(this._bumpTexture);
  1373. }
  1374. if (this._lightmapTexture && this._lightmapTexture.animations && this._lightmapTexture.animations.length > 0) {
  1375. results.push(this._lightmapTexture);
  1376. }
  1377. if (this._refractionTexture && this._refractionTexture.animations && this._refractionTexture.animations.length > 0) {
  1378. results.push(this._refractionTexture);
  1379. }
  1380. this.detailMap.getAnimatables(results);
  1381. return results;
  1382. }
  1383. /**
  1384. * Gets the active textures from the material
  1385. * @returns an array of textures
  1386. */
  1387. public getActiveTextures(): BaseTexture[] {
  1388. var activeTextures = super.getActiveTextures();
  1389. if (this._diffuseTexture) {
  1390. activeTextures.push(this._diffuseTexture);
  1391. }
  1392. if (this._ambientTexture) {
  1393. activeTextures.push(this._ambientTexture);
  1394. }
  1395. if (this._opacityTexture) {
  1396. activeTextures.push(this._opacityTexture);
  1397. }
  1398. if (this._reflectionTexture) {
  1399. activeTextures.push(this._reflectionTexture);
  1400. }
  1401. if (this._emissiveTexture) {
  1402. activeTextures.push(this._emissiveTexture);
  1403. }
  1404. if (this._specularTexture) {
  1405. activeTextures.push(this._specularTexture);
  1406. }
  1407. if (this._bumpTexture) {
  1408. activeTextures.push(this._bumpTexture);
  1409. }
  1410. if (this._lightmapTexture) {
  1411. activeTextures.push(this._lightmapTexture);
  1412. }
  1413. if (this._refractionTexture) {
  1414. activeTextures.push(this._refractionTexture);
  1415. }
  1416. this.detailMap.getActiveTextures(activeTextures);
  1417. return activeTextures;
  1418. }
  1419. /**
  1420. * Specifies if the material uses a texture
  1421. * @param texture defines the texture to check against the material
  1422. * @returns a boolean specifying if the material uses the texture
  1423. */
  1424. public hasTexture(texture: BaseTexture): boolean {
  1425. if (super.hasTexture(texture)) {
  1426. return true;
  1427. }
  1428. if (this._diffuseTexture === texture) {
  1429. return true;
  1430. }
  1431. if (this._ambientTexture === texture) {
  1432. return true;
  1433. }
  1434. if (this._opacityTexture === texture) {
  1435. return true;
  1436. }
  1437. if (this._reflectionTexture === texture) {
  1438. return true;
  1439. }
  1440. if (this._emissiveTexture === texture) {
  1441. return true;
  1442. }
  1443. if (this._specularTexture === texture) {
  1444. return true;
  1445. }
  1446. if (this._bumpTexture === texture) {
  1447. return true;
  1448. }
  1449. if (this._lightmapTexture === texture) {
  1450. return true;
  1451. }
  1452. if (this._refractionTexture === texture) {
  1453. return true;
  1454. }
  1455. return this.detailMap.hasTexture(texture);
  1456. }
  1457. /**
  1458. * Disposes the material
  1459. * @param forceDisposeEffect specifies if effects should be forcefully disposed
  1460. * @param forceDisposeTextures specifies if textures should be forcefully disposed
  1461. */
  1462. public dispose(forceDisposeEffect?: boolean, forceDisposeTextures?: boolean): void {
  1463. if (forceDisposeTextures) {
  1464. this._diffuseTexture?.dispose();
  1465. this._ambientTexture?.dispose();
  1466. this._opacityTexture?.dispose();
  1467. this._reflectionTexture?.dispose();
  1468. this._emissiveTexture?.dispose();
  1469. this._specularTexture?.dispose();
  1470. this._bumpTexture?.dispose();
  1471. this._lightmapTexture?.dispose();
  1472. this._refractionTexture?.dispose();
  1473. }
  1474. this.detailMap.dispose(forceDisposeTextures);
  1475. if (this._imageProcessingConfiguration && this._imageProcessingObserver) {
  1476. this._imageProcessingConfiguration.onUpdateParameters.remove(this._imageProcessingObserver);
  1477. }
  1478. super.dispose(forceDisposeEffect, forceDisposeTextures);
  1479. }
  1480. /**
  1481. * Makes a duplicate of the material, and gives it a new name
  1482. * @param name defines the new name for the duplicated material
  1483. * @returns the cloned material
  1484. */
  1485. public clone(name: string): StandardMaterial {
  1486. var result = SerializationHelper.Clone(() => new StandardMaterial(name, this.getScene()), this);
  1487. result.name = name;
  1488. result.id = name;
  1489. return result;
  1490. }
  1491. /**
  1492. * Serializes this material in a JSON representation
  1493. * @returns the serialized material object
  1494. */
  1495. public serialize(): any {
  1496. return SerializationHelper.Serialize(this);
  1497. }
  1498. /**
  1499. * Creates a standard material from parsed material data
  1500. * @param source defines the JSON representation of the material
  1501. * @param scene defines the hosting scene
  1502. * @param rootUrl defines the root URL to use to load textures and relative dependencies
  1503. * @returns a new standard material
  1504. */
  1505. public static Parse(source: any, scene: Scene, rootUrl: string): StandardMaterial {
  1506. return SerializationHelper.Parse(() => new StandardMaterial(source.name, scene), source, scene, rootUrl);
  1507. }
  1508. // Flags used to enable or disable a type of texture for all Standard Materials
  1509. /**
  1510. * Are diffuse textures enabled in the application.
  1511. */
  1512. public static get DiffuseTextureEnabled(): boolean {
  1513. return MaterialFlags.DiffuseTextureEnabled;
  1514. }
  1515. public static set DiffuseTextureEnabled(value: boolean) {
  1516. MaterialFlags.DiffuseTextureEnabled = value;
  1517. }
  1518. /**
  1519. * Are detail textures enabled in the application.
  1520. */
  1521. public static get DetailTextureEnabled(): boolean {
  1522. return MaterialFlags.DetailTextureEnabled;
  1523. }
  1524. public static set DetailTextureEnabled(value: boolean) {
  1525. MaterialFlags.DetailTextureEnabled = value;
  1526. }
  1527. /**
  1528. * Are ambient textures enabled in the application.
  1529. */
  1530. public static get AmbientTextureEnabled(): boolean {
  1531. return MaterialFlags.AmbientTextureEnabled;
  1532. }
  1533. public static set AmbientTextureEnabled(value: boolean) {
  1534. MaterialFlags.AmbientTextureEnabled = value;
  1535. }
  1536. /**
  1537. * Are opacity textures enabled in the application.
  1538. */
  1539. public static get OpacityTextureEnabled(): boolean {
  1540. return MaterialFlags.OpacityTextureEnabled;
  1541. }
  1542. public static set OpacityTextureEnabled(value: boolean) {
  1543. MaterialFlags.OpacityTextureEnabled = value;
  1544. }
  1545. /**
  1546. * Are reflection textures enabled in the application.
  1547. */
  1548. public static get ReflectionTextureEnabled(): boolean {
  1549. return MaterialFlags.ReflectionTextureEnabled;
  1550. }
  1551. public static set ReflectionTextureEnabled(value: boolean) {
  1552. MaterialFlags.ReflectionTextureEnabled = value;
  1553. }
  1554. /**
  1555. * Are emissive textures enabled in the application.
  1556. */
  1557. public static get EmissiveTextureEnabled(): boolean {
  1558. return MaterialFlags.EmissiveTextureEnabled;
  1559. }
  1560. public static set EmissiveTextureEnabled(value: boolean) {
  1561. MaterialFlags.EmissiveTextureEnabled = value;
  1562. }
  1563. /**
  1564. * Are specular textures enabled in the application.
  1565. */
  1566. public static get SpecularTextureEnabled(): boolean {
  1567. return MaterialFlags.SpecularTextureEnabled;
  1568. }
  1569. public static set SpecularTextureEnabled(value: boolean) {
  1570. MaterialFlags.SpecularTextureEnabled = value;
  1571. }
  1572. /**
  1573. * Are bump textures enabled in the application.
  1574. */
  1575. public static get BumpTextureEnabled(): boolean {
  1576. return MaterialFlags.BumpTextureEnabled;
  1577. }
  1578. public static set BumpTextureEnabled(value: boolean) {
  1579. MaterialFlags.BumpTextureEnabled = value;
  1580. }
  1581. /**
  1582. * Are lightmap textures enabled in the application.
  1583. */
  1584. public static get LightmapTextureEnabled(): boolean {
  1585. return MaterialFlags.LightmapTextureEnabled;
  1586. }
  1587. public static set LightmapTextureEnabled(value: boolean) {
  1588. MaterialFlags.LightmapTextureEnabled = value;
  1589. }
  1590. /**
  1591. * Are refraction textures enabled in the application.
  1592. */
  1593. public static get RefractionTextureEnabled(): boolean {
  1594. return MaterialFlags.RefractionTextureEnabled;
  1595. }
  1596. public static set RefractionTextureEnabled(value: boolean) {
  1597. MaterialFlags.RefractionTextureEnabled = value;
  1598. }
  1599. /**
  1600. * Are color grading textures enabled in the application.
  1601. */
  1602. public static get ColorGradingTextureEnabled(): boolean {
  1603. return MaterialFlags.ColorGradingTextureEnabled;
  1604. }
  1605. public static set ColorGradingTextureEnabled(value: boolean) {
  1606. MaterialFlags.ColorGradingTextureEnabled = value;
  1607. }
  1608. /**
  1609. * Are fresnels enabled in the application.
  1610. */
  1611. public static get FresnelEnabled(): boolean {
  1612. return MaterialFlags.FresnelEnabled;
  1613. }
  1614. public static set FresnelEnabled(value: boolean) {
  1615. MaterialFlags.FresnelEnabled = value;
  1616. }
  1617. }
  1618. _TypeStore.RegisteredTypes["BABYLON.StandardMaterial"] = StandardMaterial;
  1619. Scene.DefaultMaterialFactory = (scene: Scene) => {
  1620. return new StandardMaterial("default material", scene);
  1621. };