InTerra_Functions.hlsl 35 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914
  1. #if defined(INTERRA_OBJECT) || defined(INTERRA_MESH_TERRAIN)
  2. #if defined (_OBJECT_TRIPLANAR) || defined (_TERRAIN_TRIPLANAR_ONE) || defined (_TERRAIN_TRIPLANAR_ALL)
  3. #define TRIPLANAR
  4. #endif
  5. #endif
  6. #ifdef _LAYERS_ONE
  7. #define _LAYER_COUNT 1
  8. #else
  9. #ifdef _LAYERS_TWO
  10. #define _LAYER_COUNT 2
  11. #else
  12. #if defined(_LAYERS_EIGHT)
  13. #define _TERRAIN_8_LAYERS
  14. #define _LAYER_COUNT 8
  15. #else
  16. #define _LAYER_COUNT 4
  17. #endif
  18. #endif
  19. #endif
  20. #if defined(INTERRA_OBJECT) || defined(INTERRA_MESH_TERRAIN)
  21. #include "InTerra_LayersProperties.hlsl"
  22. #endif
  23. //----- Global Properties -----
  24. float _InTerra_TrackArea;
  25. float3 _InTerra_TrackPosition;
  26. TEXTURE2D(_InTerra_TrackTexture);
  27. float4 _InTerra_TrackTexture_TexelSize;
  28. float _InTerra_TracksLayer;
  29. float _InTerra_TracksFading;
  30. float _InTerra_TracksFadingTime;
  31. float _InTerra_TrackTextureSize;
  32. float _InTerra_TrackLayer;
  33. float _InTerra_GlobalWetness;
  34. float3 _InTerra_GlobalPuddles;
  35. float3 _InTerra_GlobalRaindropRipples;
  36. float4 _InTerra_GlobalRaindropsDistance;
  37. //==========================================================================================
  38. //====================================== FUNCTIONS =====================================
  39. //==========================================================================================
  40. float2 ObjectFrontUV(float posOffset, half4 splatUV, float offsetZ)
  41. {
  42. return float2((posOffset + splatUV.z) / splatUV.x, (offsetZ + splatUV.w) / splatUV.y);
  43. }
  44. float2 ObjectSideUV(float posOffset, half4 splatUV, float offsetX)
  45. {
  46. return float2((offsetX + splatUV.z) / splatUV.x, (posOffset + splatUV.w) / splatUV.y);
  47. }
  48. half3 WorldTangent(float3 wTangent, float3 wBTangent, half3 mixedNormal)
  49. {
  50. mixedNormal.xy = mul(float2x2(wTangent.xz, wBTangent.xz), mixedNormal.xy);
  51. return half3(mixedNormal);
  52. }
  53. half2 HeightBlendTwoTextures(float2 splat, float2 heights, half sharpness)
  54. {
  55. splat *= (1 / (1 * pow(2, heights * (-(sharpness)))) + 1) * 0.5;
  56. splat /= (splat.r + splat.g);
  57. return splat;
  58. }
  59. half3 UnpackNormalGAWithScale(half4 packednormal, float scale)
  60. {
  61. half3 normal;
  62. normal.xy = (packednormal.wy * 2 - 1) * scale;
  63. normal.z = sqrt(1 - saturate(dot(normal.xy, normal.xy)));
  64. return normal;
  65. }
  66. #ifndef INTERRA_OBJECT
  67. void uvArray(in out float2 uv[_LAYER_COUNT], float4 inUv[_LAYER_COUNT/2])
  68. {
  69. uv[0] = inUv[0].xy;
  70. uv[1] = inUv[0].zw;
  71. #ifndef _LAYERS_TWO
  72. uv[2] = inUv[1].xy;
  73. uv[3] = inUv[1].zw;
  74. #ifdef _LAYERS_EIGHT
  75. uv[4] = inUv[2].xy;
  76. uv[5] = inUv[2].zw;
  77. uv[6] = inUv[3].xy;
  78. uv[7] = inUv[3].zw;
  79. #endif
  80. #endif
  81. }
  82. #endif
  83. #if defined(INTERRA_MESH_TERRAIN)
  84. float2 TerrainFrontUV(float3 wPos, half4 splatUV, float2 tc, float3 flip)
  85. {
  86. return float2(tc.x * -flip.z, (wPos.y - _TerrainSizeXZPosY.z) * (splatUV.y / _TerrainSizeXZPosY.y) + splatUV.w);
  87. }
  88. float2 TerrainSideUV(float3 wPos, half4 splatUV, float2 tc, float3 flip)
  89. {
  90. return float2(tc.y * flip.x, (wPos.y - _TerrainSizeXZPosY.z) * (splatUV.x / _TerrainSizeXZPosY.x) + splatUV.z);
  91. }
  92. #endif
  93. void TriplanarOneToAllSteep(in out half4 blendMask[2], float weightY, in out half splatWeight)
  94. {
  95. if (_TriplanarOneToAllSteep == 1)
  96. {
  97. #if !defined(TERRAIN_SPLAT_ADDPASS)
  98. blendMask[0] = float4(saturate(blendMask[0].r + weightY), saturate((blendMask[0].gba) - weightY));
  99. blendMask[1] = float4(saturate((blendMask[1].rgba) - weightY));
  100. splatWeight = saturate(splatWeight + weightY);
  101. blendMask[0] = float4(saturate(blendMask[0].r + weightY), saturate(blendMask[0].gba - weightY));
  102. splatWeight = saturate(splatWeight + weightY);
  103. #else
  104. blendMask[0] = float4(saturate(blendMask[0].rgba - weightY));
  105. splatWeight = saturate(splatWeight - weightY);
  106. #endif
  107. }
  108. }
  109. half3 TriplanarNormal(half3 normal, half3 tangent, half3 bTangent, half3 normal_front, half3 normal_side, float3 weights, half3 flipUV)
  110. {
  111. #ifdef INTERRA_OBJECT
  112. normal_front.y *= -flipUV.z;
  113. normal_front.xy = mul(float2x2(tangent.xy, bTangent.xy), normal_front.xy);
  114. normal_side.x *= -flipUV.x;
  115. normal_side.xy = mul(float2x2(tangent.yz, bTangent.yz), normal_side.xy);
  116. #else
  117. normal_side.xy = normal_side.yx; //this is needed because the uv was rotated
  118. normal_front.xy *= -flipUV.z;
  119. normal_side.x *= -flipUV.x;
  120. normal_side.y *= flipUV.x;
  121. #endif
  122. return half3 (normal+ normal_front + normal_side);
  123. }
  124. #if defined(INTERRA_OBJECT) || defined(INTERRA_MESH_TERRAIN)
  125. #define DiffuseRemap(i) float4(_DiffuseRemapScale##i.xyzw)
  126. #else
  127. #define DiffuseRemap(i) float4(_DiffuseRemapScale##i.xyzw + _DiffuseRemapOffset##i.xyzw)
  128. #endif
  129. #if defined (PARALLAX)
  130. #define MipMapLod(i, lod) float(_MipMapLevel + (lod * log2(max(_Mask##i##_TexelSize.z, _Mask##i##_TexelSize.w)) + 1))
  131. float GetParallaxHeight(texture2D maskT, sampler maskS, float2 uv, float lod, float2 offset, int invert)
  132. {
  133. return abs(SAMPLE_TEXTURE2D_LOD(maskT, maskS, float2(uv + offset), lod).b -invert);
  134. }
  135. //this function is based on Parallax Occlusion Mapping from Shader Graph URP
  136. float2 ParallaxOffset(texture2D maskT, sampler maskS, int numSteps, float amplitude, float2 uv, float3 tangentViewDir, float affineSteps, float lod, int invert)
  137. {
  138. float2 offset = 0;
  139. if (numSteps > 0)
  140. {
  141. float3 viewDir = float3(tangentViewDir.xy * amplitude * -0.01, tangentViewDir.z);
  142. float stepSize = (1.0 / numSteps);
  143. float2 texOffsetPerStep = stepSize * viewDir.xy;
  144. // Do a first step before the loop to init all value correctly
  145. float2 texOffsetCurrent = float2(0.0, 0.0);
  146. float prevHeight = GetParallaxHeight(maskT, maskS, uv, lod, texOffsetCurrent, invert);
  147. texOffsetCurrent += texOffsetPerStep;
  148. float currHeight = GetParallaxHeight(maskT, maskS, uv, lod, texOffsetCurrent, invert);
  149. float rayHeight = 1.0 - stepSize; // Start at top less one sample
  150. for (int stepIndex = 0; stepIndex < numSteps; ++stepIndex)
  151. {
  152. // Have we found a height below our ray height ? then we have an intersection
  153. if (currHeight > rayHeight)
  154. break; // end the loop
  155. prevHeight = currHeight;
  156. rayHeight -= stepSize;
  157. texOffsetCurrent += texOffsetPerStep;
  158. currHeight = GetParallaxHeight(maskT, maskS, uv, lod, texOffsetCurrent, invert);
  159. }
  160. if (affineSteps <= 1)
  161. {
  162. float delta0 = currHeight - rayHeight;
  163. float delta1 = (rayHeight + stepSize) - prevHeight;
  164. float ratio = delta0 / (delta0 + delta1);
  165. offset = texOffsetCurrent - ratio * texOffsetPerStep;
  166. currHeight = GetParallaxHeight(maskT, maskS, uv, lod, texOffsetCurrent, invert);
  167. }
  168. else
  169. {
  170. float pt0 = rayHeight + stepSize;
  171. float pt1 = rayHeight;
  172. float delta0 = pt0 - prevHeight;
  173. float delta1 = pt1 - currHeight;
  174. float delta;
  175. // Secant method to affine the search
  176. // Ref: Faster Relief Mapping Using the Secant Method - Eric Risser
  177. for (int i = 0; i < affineSteps; ++i)
  178. {
  179. // intersectionHeight is the height [0..1] for the intersection between view ray and heightfield line
  180. float intersectionHeight = (pt0 * delta1 - pt1 * delta0) / (delta1 - delta0);
  181. // Retrieve offset require to find this intersectionHeight
  182. offset = (1 - intersectionHeight) * texOffsetPerStep * numSteps;
  183. currHeight = GetParallaxHeight(maskT, maskS, uv, lod, offset, invert);
  184. delta = intersectionHeight - currHeight;
  185. if (abs(delta) <= 0.01)
  186. break;
  187. // intersectionHeight < currHeight => new lower bounds
  188. if (delta < 0.0)
  189. {
  190. delta1 = delta;
  191. pt1 = intersectionHeight;
  192. }
  193. else
  194. {
  195. delta0 = delta;
  196. pt0 = intersectionHeight;
  197. }
  198. }
  199. }
  200. }
  201. return offset;
  202. }
  203. void ParallaxUV(inout float2 uv[_LAYER_COUNT], float3 tangentViewDir, half4 blendMask[2],float weight, float lod)
  204. {
  205. #define uvParallax(i, blendMask) \
  206. UNITY_BRANCH if (blendMask * weight > 0.01f) \
  207. { \
  208. uv[i] += ParallaxOffset(_Mask##i, SamplerState_Linear_Repeat, _DiffuseRemapOffset##i.w, DiffuseRemap(i).w, uv[i], tangentViewDir, _ParallaxAffineStepsTerrain, MipMapLod(i, lod), 0);\
  209. } \
  210. UNITY_BRANCH if (_Terrain_Parallax == 1)
  211. {
  212. uvParallax(0, blendMask[0].r);
  213. #ifndef _LAYERS_ONE
  214. uvParallax(1, blendMask[0].g);
  215. #ifndef _LAYERS_TWO
  216. uvParallax(2, blendMask[0].b);
  217. uvParallax(3, blendMask[0].a);
  218. #ifdef _LAYERS_EIGHT
  219. uvParallax(4, blendMask[1].r);
  220. uvParallax(5, blendMask[1].g);
  221. uvParallax(6, blendMask[1].b);
  222. uvParallax(7, blendMask[1].a);
  223. #endif
  224. #endif
  225. #endif
  226. }
  227. }
  228. #endif
  229. float3 UnpackNormals(float4 packednormal, float normalScale)
  230. {
  231. #ifdef UNITY_NO_DXT5nm
  232. return UnpackNormalRGB(packednormal, normalScale);
  233. #else
  234. return UnpackNormalAG(packednormal, normalScale);
  235. #endif
  236. }
  237. float3 UnpackNormalGAWithScale(float4 packednormal, float scale, half hasMask)
  238. {
  239. UNITY_BRANCH if (hasMask > 0)
  240. {
  241. return UnpackNormalAG(packednormal, scale);
  242. }
  243. else
  244. {
  245. return float3(0, 0, 1);
  246. }
  247. }
  248. float3 BlendNormals(float3 n1, float3 n2)
  249. {
  250. #ifdef INTERRA_OBJECT
  251. float3 t = n1.xyz + float3(0.0, 0.0, 1.0);
  252. float3 u = n2.xyz * float3(-1.0, -1.0, 1.0);
  253. float3 r = (t / t.z) * dot(t, u) - u;
  254. return r;
  255. #else
  256. return (float3(n1.xy + n2.xy, n1.z));
  257. #endif
  258. }
  259. #if defined(_NORMALMAPS) && !defined(_TERRAIN_NORMAL_IN_MASK)
  260. #define SampleNormals(i) (UnpackNormals(SAMPLE_TEXTURE2D(_Normal##i, SamplerState_Linear_Repeat, uv[i]), _NormalScale##i).xyz)
  261. #elif defined(_TERRAIN_NORMAL_IN_MASK)
  262. #define SampleNormals(i) float3(UnpackNormalGAWithScale(mask[i], _NormalScale##i, _LayerHasMask##i).xyz)
  263. #else
  264. #define SampleNormals(i) float3(0, 0, 1)
  265. #endif
  266. float3 SmoothMaskOrAlbedo(half mask, half albedo, float hasMask, float smoothness)
  267. {
  268. UNITY_BRANCH if (hasMask > 0)
  269. {
  270. albedo = mask;
  271. }
  272. else
  273. {
  274. albedo *= smoothness;
  275. }
  276. return albedo;
  277. }
  278. #ifdef _TERRAIN_MASK_MAPS
  279. #define Smoothness(i) SmoothMaskOrAlbedo(mask[i].a, albedo[i].a, _LayerHasMask##i, _Smoothness##i)
  280. #else
  281. #define Smoothness(i) albedo[i].a *= _Smoothness##i
  282. #endif
  283. #if defined(INTERRA_OBJECT) || defined(INTERRA_MESH_TERRAIN)
  284. #ifdef INTERRA_OBJECT
  285. #define UV(i) (posOffset.xz + _SplatUV##i.zw + _SteepDistortion) / _SplatUV##i.xy;
  286. #else
  287. #define UV(i) (posOffset.xz + _SplatUV##i.zw) / _SplatUV##i.xy;
  288. #endif
  289. #ifdef PARALLAX
  290. #define fUV(i) ObjectFrontUV(posOffset.x, _SplatUV##i, offsetZ + (_DiffuseRemapScale##i.w * 0.004 * _SplatUV##i.x) * -flip.z);
  291. #define sUV(i) ObjectSideUV(posOffset.z, _SplatUV##i, offsetX + (_DiffuseRemapScale##i.w * 0.004 * _SplatUV##i.y) * -flip.x);
  292. #else
  293. #if defined(TESSELLATION_ON)
  294. #define fUV(i) ObjectFrontUV(posOffset.x, _SplatUV##i, offsetZ + (-_DiffuseRemapOffset##i.y * 0.005 - _TerrainTessOffset) * -flip.z);
  295. #define sUV(i) ObjectSideUV(posOffset.z, _SplatUV##i, offsetX + (-_DiffuseRemapOffset##i.y * 0.005 - _TerrainTessOffset) * -flip.x);
  296. #else
  297. #define fUV(i) ObjectFrontUV(posOffset.x, _SplatUV##i, offsetZ);
  298. #define sUV(i) ObjectSideUV(posOffset.z, _SplatUV##i, offsetX);
  299. #endif
  300. #endif
  301. #else
  302. #define UV(i) uv[i];
  303. #define fUV(i) TerrainFrontUV(worldPos, _Splat##i##_ST, uvSplat[i], flip);
  304. #define sUV(i) TerrainSideUV(worldPos, _Splat##i##_ST, uvSplat[i], flip);
  305. #endif
  306. float4 RemapMasks(half4 mask, float4 remapScale, float4 remapOffset)
  307. {
  308. #ifdef _TERRAIN_NORMAL_IN_MASK
  309. mask.rb * remapScale.gb + remapOffset.gb;
  310. return mask;
  311. #else
  312. return mask * remapScale + remapOffset;
  313. #endif
  314. }
  315. #ifdef TERRAIN_MASK
  316. #define Mask(i) SAMPLE_TEXTURE2D(_Mask##i, SamplerState_Linear_Repeat, uv[i]);
  317. #ifdef _TERRAIN_NORMAL_IN_MASK
  318. #define RemapMask(i) mask[i] * float4(_MaskMapRemapScale##i.g, 1, _MaskMapRemapScale##i.b, 1) \
  319. + float4(_MaskMapRemapOffset##i.g, 0, _MaskMapRemapOffset##i.b, 0);
  320. #else
  321. #define RemapMask(i) mask[i] * _MaskMapRemapScale##i + _MaskMapRemapOffset##i;
  322. #endif
  323. #else
  324. #define Mask(i) float4(_Metallic##i, 1, 0.5, 0);
  325. #define RemapMask(i) mask[i];
  326. #endif
  327. void SampleMask(out half4 mask[_LAYER_COUNT], float2 uv[_LAYER_COUNT], half4 blendMask[2], float weight)
  328. {
  329. #define SampleMasks(i, blendMask) \
  330. UNITY_BRANCH if (blendMask * weight > 1e-5f ) \
  331. { \
  332. mask[i] = Mask(i); \
  333. mask[i] = RemapMask(i); \
  334. } \
  335. else \
  336. { \
  337. mask[i] = float4(_Metallic##i, 1, 0.5, 0); \
  338. } \
  339. SampleMasks(0, blendMask[0].r);
  340. #ifndef _LAYERS_ONE
  341. SampleMasks(1, blendMask[0].g);
  342. #ifndef _LAYERS_TWO
  343. SampleMasks(2, blendMask[0].b);
  344. SampleMasks(3, blendMask[0].a);
  345. #ifdef _TERRAIN_8_LAYERS
  346. SampleMasks(4, blendMask[1].r);
  347. SampleMasks(5, blendMask[1].g);
  348. SampleMasks(6, blendMask[1].b);
  349. SampleMasks(7, blendMask[1].a);
  350. #endif
  351. #endif
  352. #endif
  353. #undef SampleMasks
  354. }
  355. void SampleSplat(float2 uv[_LAYER_COUNT], half4 blendMask[2], float weight, inout half4 mask[_LAYER_COUNT], out float4 mixAlbedo, out float3 mixNormal)
  356. {
  357. float4 albedo[_LAYER_COUNT];
  358. float3 normal[_LAYER_COUNT];
  359. mixAlbedo = 0;
  360. mixNormal = 0;
  361. #define Samples(i, blendMask) blendMask *= weight; \
  362. UNITY_BRANCH if (blendMask > 1e-5f) \
  363. { \
  364. albedo[i] = SAMPLE_TEXTURE2D(_Splat##i, sampler_Splat0, uv[i]); \
  365. albedo[i].rgb *= DiffuseRemap(i).xyz; \
  366. albedo[i].a = Smoothness(i).x; \
  367. normal[i] = SampleNormals(i).xyz; \
  368. mixAlbedo += albedo[i].xyzw * blendMask.x; \
  369. mixNormal += normal[i].xyz * blendMask.x; \
  370. } \
  371. else \
  372. { \
  373. albedo[i] = float4(0, 0, 0, 0); \
  374. normal[i] = float3(0, 0, 1); \
  375. } \
  376. Samples(0, blendMask[0].r);
  377. #ifndef _LAYERS_ONE
  378. Samples(1, blendMask[0].g);
  379. #ifndef _LAYERS_TWO
  380. Samples(2, blendMask[0].b);
  381. Samples(3, blendMask[0].a);
  382. #ifdef _TERRAIN_8_LAYERS
  383. Samples(4, blendMask[1].r);
  384. Samples(5, blendMask[1].g);
  385. Samples(6, blendMask[1].b);
  386. Samples(7, blendMask[1].a);
  387. #endif
  388. #endif
  389. #endif
  390. #undef Samples
  391. }
  392. #if defined(INTERRA_OBJECT) || defined(INTERRA_MESH_TERRAIN)
  393. #ifndef TRIPLANAR
  394. void UvSplat(out float2 uvSplat[_LAYER_COUNT], float3 posOffset)
  395. #else
  396. void UvSplat(out float2 uvSplat[_LAYER_COUNT], out float2 uvFront[_LAYER_COUNT], out float2 uvSide[_LAYER_COUNT], float3 posOffset, float offsetZ, float offsetX, float3 flip)
  397. #endif
  398. #else
  399. #ifndef TRIPLANAR
  400. void UvSplat(out float2 uvSplat[_LAYER_COUNT], float2 uv[_LAYER_COUNT], float2 splatBaseUV)
  401. #else
  402. void UvSplat(out float2 uvSplat[_LAYER_COUNT], out float2 uvFront[_LAYER_COUNT], out float2 uvSide[_LAYER_COUNT], float3 worldPos, float2 uv[_LAYER_COUNT], float2 splatBaseUV, float3 flip)
  403. #endif
  404. #endif
  405. {
  406. #ifndef TRIPLANAR
  407. #define SplatUV(i); \
  408. uvSplat[i] = UV(i);
  409. #else
  410. #define SplatUV(i) \
  411. uvSplat[i] = UV(i); \
  412. uvFront[i] = fUV(i); \
  413. uvSide[i] = sUV(i); \
  414. #endif
  415. SplatUV(0);
  416. #ifndef _LAYERS_ONE
  417. SplatUV(1);
  418. #ifndef _LAYERS_TWO
  419. SplatUV(2);
  420. SplatUV(3);
  421. #ifdef _TERRAIN_8_LAYERS
  422. SplatUV(4);
  423. SplatUV(5);
  424. SplatUV(6);
  425. SplatUV(7);
  426. #endif
  427. #endif
  428. #endif
  429. }
  430. void DistantUV(out float2 distantUV[_LAYER_COUNT], float2 uvSplat[_LAYER_COUNT])
  431. {
  432. #define uvDistant(i) \
  433. distantUV[i] = uvSplat[i] * (_DiffuseRemapOffset##i.r + 1) * _HT_distance_scale; \
  434. uvDistant(0);
  435. #ifndef _LAYERS_ONE
  436. uvDistant(1);
  437. #ifndef _LAYERS_TWO
  438. uvDistant(2);
  439. uvDistant(3);
  440. #ifdef _TERRAIN_8_LAYERS
  441. uvDistant(4);
  442. uvDistant(5);
  443. uvDistant(6);
  444. uvDistant(7);
  445. #endif
  446. #endif
  447. #endif
  448. }
  449. void MaskWeight(inout half4 mask[_LAYER_COUNT], half4 mask_front[_LAYER_COUNT], half4 mask_side[_LAYER_COUNT], half4 blendMask[2], inout float3 triplanarWeights, float heightBlendingSharpness)
  450. {
  451. float splatWeight[_LAYER_COUNT];
  452. float3 heights = 0;
  453. splatWeight[0] = blendMask[0].x;
  454. #ifndef _LAYERS_ONE
  455. splatWeight[1] = blendMask[0].y;
  456. #ifndef _LAYERS_TWO
  457. splatWeight[2] = blendMask[0].z;
  458. splatWeight[3] = blendMask[0].w;
  459. #ifdef _TERRAIN_8_LAYERS
  460. splatWeight[4] = blendMask[1].x;
  461. splatWeight[5] = blendMask[1].y;
  462. splatWeight[6] = blendMask[1].z;
  463. splatWeight[7] = blendMask[1].w;
  464. #endif
  465. #endif
  466. #endif
  467. for (int i = 0; i < _LAYER_COUNT; ++i)
  468. {
  469. mask[i] = (mask[i] * triplanarWeights.y) + (mask_front[i] * triplanarWeights.z) + (mask_side[i] * triplanarWeights.x);
  470. }
  471. }
  472. half4 MaskSplatWeight(half4 mask[_LAYER_COUNT], half4 blendMask[2], out half4 mixedMask)
  473. {
  474. float splatWeight[_LAYER_COUNT];
  475. mixedMask = 0;
  476. #ifdef _TERRAIN_NORMAL_IN_MASK
  477. #define MixdMask(i, blendMask) float4(_Metallic##i, mask[i].r, mask[i].b, 0.0f) * blendMask
  478. #elif defined(_TERRAIN_MASK_HEIGHTMAP_ONLY)
  479. #define MixdMask(i, blendMask) float4(_Metallic##i, 1.0f, mask[i].b, 0.0f) * blendMask
  480. #else
  481. #define MixdMask(i, blendMask) mask[i] * blendMask
  482. #endif
  483. #define MixdMasks(i, blendMask) \
  484. UNITY_BRANCH if (blendMask > 0) \
  485. { \
  486. mixedMask += MixdMask(i, blendMask); \
  487. }
  488. MixdMasks(0, blendMask[0].r);
  489. #ifndef _LAYERS_ONE
  490. MixdMasks(1, blendMask[0].g);
  491. #ifndef _LAYERS_TWO
  492. MixdMasks(2, blendMask[0].b);
  493. MixdMasks(3, blendMask[0].a);
  494. #ifdef _TERRAIN_8_LAYERS
  495. MixdMasks(4, blendMask[1].r);
  496. MixdMasks(5, blendMask[1].g);
  497. MixdMasks(6, blendMask[1].b);
  498. MixdMasks(7, blendMask[1].a);
  499. #endif
  500. #endif
  501. #endif
  502. return mixedMask;
  503. }
  504. #ifdef TERRAIN_MASK
  505. float AmbientOcclusion(half4 mask[_LAYER_COUNT], half4 blendMask[2])
  506. {
  507. float occlusion[_LAYER_COUNT];
  508. #ifdef _TERRAIN_NORMAL_IN_MASK
  509. UNITY_UNROLL for (int i = 0; i < _LAYER_COUNT; ++i)
  510. {
  511. occlusion[i] = mask[i].r;
  512. }
  513. #else
  514. UNITY_UNROLL for (int i = 0; i < _LAYER_COUNT; ++i)
  515. {
  516. occlusion[i] = mask[i].g;
  517. }
  518. #endif
  519. float ao = 0;
  520. ao = occlusion[0] * blendMask[0].r;
  521. #ifndef _LAYERS_ONE
  522. ao += occlusion[1] * blendMask[0].g;
  523. #ifndef _LAYERS_TWO
  524. ao += occlusion[2] * blendMask[0].b
  525. + occlusion[3] * blendMask[0].a;
  526. #ifdef _TERRAIN_8_LAYERS
  527. ao += occlusion[4] * blendMask[1].r
  528. + occlusion[5] * blendMask[1].g
  529. + occlusion[6] * blendMask[1].b
  530. + occlusion[7] * blendMask[1].a;
  531. #endif
  532. #endif
  533. #endif
  534. return ao;
  535. }
  536. #endif
  537. #ifndef _TERRAIN_MASK_MAPS
  538. #define Metallic(i, blendMask) _Metallic##i * blendMask;
  539. #else
  540. #define Metallic(i, blendMask) mask[i].r * blendMask;
  541. #endif
  542. float MetallicMask(half4 mask[_LAYER_COUNT], half4 blendMask[2])
  543. {
  544. float metallic = 0;
  545. #define Metallics(i, blendMask) \
  546. UNITY_BRANCH if (blendMask > 0) \
  547. { \
  548. metallic += Metallic(i, blendMask); \
  549. }
  550. Metallics(0, blendMask[0].r);
  551. #ifndef _LAYERS_ONE
  552. Metallics(1, blendMask[0].g);
  553. #ifndef _LAYERS_TWO
  554. Metallics(2, blendMask[0].b);
  555. Metallics(3, blendMask[0].a);
  556. #ifdef _TERRAIN_8_LAYERS
  557. Metallics(4, blendMask[1].r);
  558. Metallics(5, blendMask[1].g);
  559. Metallics(6, blendMask[1].b);
  560. Metallics(7, blendMask[1].a);
  561. #endif
  562. #endif
  563. #endif
  564. return metallic;
  565. }
  566. float HeightSum(half4 mask[_LAYER_COUNT], half4 blendMask[2])
  567. {
  568. #ifdef _LAYERS_ONE
  569. return float(mask[0].b);
  570. #else
  571. float heightSum = dot(blendMask[0].rg, float2(mask[0].b, mask[1].b));
  572. #ifndef _LAYERS_TWO
  573. heightSum += dot(blendMask[0].ba, float2(mask[2].b, mask[3].b));
  574. #ifdef _TERRAIN_8_LAYERS
  575. heightSum += dot(blendMask[1], float4(mask[4].b, mask[5].b, mask[6].b, mask[7].b));
  576. #endif
  577. #endif
  578. return heightSum;
  579. #endif
  580. }
  581. float4 TrackSplatValues(half4 blendMask[2], float4 trackSplats[_LAYER_COUNT])
  582. {
  583. #ifdef _LAYERS_ONE
  584. return trackSplats[0];
  585. #else
  586. float4 color = (blendMask[0].r * trackSplats[0])
  587. + (blendMask[0].g * trackSplats[1]);
  588. #ifndef _LAYERS_TWO
  589. color += (blendMask[0].b * trackSplats[2])
  590. + (blendMask[0].a * trackSplats[3]);
  591. #ifdef _TERRAIN_8_LAYERS
  592. color += (blendMask[1].r * trackSplats[4])
  593. + (blendMask[1].g * trackSplats[5])
  594. + (blendMask[1].b * trackSplats[6])
  595. + (blendMask[1].a * trackSplats[7]);
  596. #endif
  597. #endif
  598. return color;
  599. #endif
  600. }
  601. #if defined(INTERRA_OBJECT) || defined(INTERRA_MESH_TERRAIN)
  602. #define SpecularValueR(i) _Specular##i.r;
  603. #define SpecularValueG(i) _Specular##i.g;
  604. #define SpecularValueB(i) _Specular##i.b;
  605. #else
  606. #define SpecularValueR(i) _Gamma ? _Specular##i.r : pow(abs(_Specular##i.r),1/2.2f);
  607. #define SpecularValueG(i) _Gamma ? _Specular##i.g : pow(abs(_Specular##i.g),1/2.2f);
  608. #define SpecularValueB(i) _Gamma ? _Specular##i.b : pow(abs(_Specular##i.b),1/2.2f);
  609. #endif
  610. void UnpackTrackSplatValues(out float4 trackSplats[_LAYER_COUNT])
  611. {
  612. float value;
  613. int precision = 1024;
  614. #define trackSplat(i) value = SpecularValueR(i); \
  615. trackSplats[i].z = value % precision; \
  616. value = floor(value / precision); \
  617. trackSplats[i].x = value; \
  618. trackSplats[i] /= (precision - 1); \
  619. \
  620. trackSplats[i].y = (_DiffuseRemapOffset##i.w * 10.0f) % 1 ; \
  621. trackSplats[i].w = floor((_DiffuseRemapOffset##i.w % 1 ) * 10.0f); \
  622. trackSplat(0);
  623. #ifndef _LAYERS_ONE
  624. trackSplat(1);
  625. #ifndef _LAYERS_TWO
  626. trackSplat(2);
  627. trackSplat(3);
  628. #ifdef _TERRAIN_8_LAYERS
  629. trackSplat(4);
  630. trackSplat(5);
  631. trackSplat(6);
  632. trackSplat(7);
  633. #endif
  634. #endif
  635. #endif
  636. }
  637. void UnpackTrackSplatColor(out float4 trackSplatsColor[_LAYER_COUNT])
  638. {
  639. float color;
  640. float value;
  641. int precision = 1024;
  642. #define trackSplatColor(i) color = SpecularValueG(i) \
  643. \
  644. trackSplatsColor[i].y = color % precision; \
  645. color = floor(color / precision); \
  646. trackSplatsColor[i].x = color; \
  647. value = SpecularValueB(i); \
  648. trackSplatsColor[i].w = value % precision; \
  649. value = floor(value / precision); \
  650. trackSplatsColor[i].z = value % precision; \
  651. trackSplatsColor[i] /= (precision - 1); \
  652. trackSplatColor(0);
  653. #ifndef _LAYERS_ONE
  654. trackSplatColor(1);
  655. #ifndef _LAYERS_TWO
  656. trackSplatColor(2);
  657. trackSplatColor(3);
  658. #ifdef _TERRAIN_8_LAYERS
  659. trackSplatColor(4);
  660. trackSplatColor(5);
  661. trackSplatColor(6);
  662. trackSplatColor(7);
  663. #endif
  664. #endif
  665. #endif
  666. }
  667. #ifdef _TERRAIN_BLEND_HEIGHT
  668. void HeightBlend(half4 mask[_LAYER_COUNT], inout half4 blendMask[2], float sharpness)
  669. {
  670. #ifdef _LAYERS_TWO
  671. float2 height = float2(mask[0].b, mask[1].b);
  672. blendMask[0].rg *= (1 / (pow(2, (height + blendMask[0].rg) * (-(sharpness)))) + 1) * 0.5;
  673. blendMask[0].rg /= (blendMask[0].r + blendMask[0].g);
  674. #else
  675. float4 height = float4 (mask[0].b, mask[1].b, mask[2].b, mask[3].b);
  676. blendMask[0].rgba *= (1 / (pow(2, (height + blendMask[0].rgba) * (-(sharpness)))) + 1) * 0.5;
  677. float heightSum = blendMask[0].r + blendMask[0].g + blendMask[0].b + blendMask[0].a;
  678. #ifdef _TERRAIN_8_LAYERS
  679. float4 height1 = float4 (mask[4].b, mask[5].b, mask[6].b, mask[7].b);
  680. blendMask[1].rgba *= (1 / (pow(2, (height1 + blendMask[1].rgba) * (-(sharpness)))) + 1) * 0.5;
  681. heightSum += blendMask[1].r + blendMask[1].g + blendMask[1].b + blendMask[1].a;
  682. blendMask[1].rgba /= heightSum;
  683. #endif
  684. blendMask[0].rgba /= heightSum;
  685. #endif
  686. }
  687. #endif
  688. #ifndef _TERRAIN_BASEMAP_GEN
  689. void SampleSplatTOL(in out half4 mixedAlbedo, in out half3 mixedNormal, float2 uv[_LAYER_COUNT], half4 blendMask[2], float weight, half4 mask[_LAYER_COUNT])
  690. {
  691. float4 albedo[1];
  692. float3 normal[1];
  693. albedo[0] = float4(0, 0, 0, 0);
  694. normal[0] = float3(0, 0, 1);
  695. blendMask[0].r *= weight;
  696. #ifndef TERRAIN_SPLAT_ADDPASS
  697. UNITY_BRANCH if (blendMask[0].r > 1e-5f)
  698. {
  699. albedo[0] = SAMPLE_TEXTURE2D(_Splat0, sampler_Splat0, uv[0]);
  700. albedo[0].rgb *= DiffuseRemap(0).rgb;
  701. albedo[0].a = Smoothness(0).x;
  702. normal[0] = SampleNormals(0);
  703. }
  704. mixedAlbedo = (albedo[0] * blendMask[0].r);
  705. mixedNormal = (normal[0] * blendMask[0].r);
  706. #else
  707. mixedAlbedo = 0.0f;
  708. mixedNormal = 0.0f;
  709. #endif
  710. }
  711. void SampleMaskTOL(out half4 mask[_LAYER_COUNT], half4 noTriplanarMask[_LAYER_COUNT], float2 uv[_LAYER_COUNT], float weight)
  712. {
  713. #ifndef TERRAIN_SPLAT_ADDPASS
  714. UNITY_BRANCH if (weight > 1e-5f)
  715. {
  716. mask[0] = Mask(0);
  717. mask[0] = RemapMask(0);
  718. }
  719. else
  720. {
  721. mask[0] = float4(0, 0, 0.5, 0);
  722. }
  723. #else
  724. mask[0] = noTriplanarMask[0];
  725. #endif
  726. mask[1] = noTriplanarMask[1];
  727. #ifndef _LAYERS_TWO
  728. mask[2] = noTriplanarMask[2];
  729. mask[3] = noTriplanarMask[3];
  730. #ifdef _TERRAIN_8_LAYERS
  731. mask[4] = noTriplanarMask[4];
  732. mask[5] = noTriplanarMask[5];
  733. mask[6] = noTriplanarMask[6];
  734. mask[7] = noTriplanarMask[7];
  735. #endif
  736. #endif
  737. }
  738. #define TAU 6.283185307
  739. float random(in float2 st)
  740. {
  741. return frac(sin(dot(st.xy, float2(12.9898, 78.233))) * 43758.5453123);
  742. }
  743. float2 rotate_2d(float2 p_input, float p_theta)
  744. {
  745. float2x2 l_rot_matrix = float2x2(cos(p_theta), -sin(p_theta),
  746. sin(p_theta), cos(p_theta));
  747. return mul(l_rot_matrix, p_input);
  748. }
  749. float3 RainRipples(float2 uv, float scale, float rotation)
  750. {
  751. float3 normal = float3(0, 0, 1);
  752. uv.xy = rotate_2d(uv.xy, rotation);
  753. float2 sUV = (uv.xy * scale + scale * 0.1f);
  754. sUV.x += step(1.0f, (sUV.y % 2.0)) * 0.5f;
  755. float2 center = float2(0.5f, 0.5f);
  756. float size = 0.25f;
  757. float2 tile = floor(sUV);
  758. float2 fract = frac(sUV);
  759. float2 offset = (center - fract.xy) * size;
  760. float2 cUV = (fract - 0.5) / size + offset;
  761. float2 polarUV = float2(length(cUV), atan2(cUV.y, cUV.x));
  762. float time = _Time.x * scale * 3.0f;
  763. float radius = frac(time * 0.9f + (random(floor(sUV) + 5000.0).x)) * 1.25f;
  764. if (radius < 0.8f)
  765. {
  766. float thickness = min((size * 0.5f + 0.25f) * 0.4f, radius);
  767. float start = radius + thickness;
  768. float end = max(0., radius - thickness);
  769. if (radius > 0.15)
  770. {
  771. thickness *= (0.9 - (radius * 0.9f));
  772. }
  773. float radius2 = radius - thickness * 1.25f;
  774. float cAngle = smoothstep(start, end, polarUV.x) * PI;
  775. float start2 = radius2 + thickness;
  776. float end2 = max(0., radius2 - thickness);
  777. float cAngle2 = smoothstep(start2, end2, polarUV.x) * PI;
  778. float rippleMask = smoothstep(thickness, -0.1f, abs(polarUV.x - radius));
  779. float rippleMask2 = smoothstep(thickness, -0.1f, abs(polarUV.x - radius2));
  780. float decayMask = min(1., max(0., 1. - polarUV.x));
  781. cAngle = lerp(cAngle, PI * 0.5f, (1.0f - rippleMask * decayMask));
  782. cAngle2 = lerp(cAngle2, PI * 0.5f, (1.0f - rippleMask2 * decayMask));
  783. float c = lerp(cos(cAngle), cos(cAngle2), 0.5f);
  784. normal = float3(c * sin(polarUV.y), c * cos(polarUV.y), sin(cAngle));
  785. float opacity = _InTerra_GlobalRaindropRipples.y;
  786. normal.xy = rotate_2d(normal.xy, rotation) * (opacity - (radius * opacity));
  787. }
  788. return normal;
  789. }
  790. #endif