فهرست منبع

Work on transparent rendering path
Also a few fixes:
- Issue with default shader data not being applied
- Issue with OpenGL not parsing int/uint sampled buffers
- Issue with shader flags not properly being sent to the core-thread counterpart object
- Issue with material data parameter syncing between sim and core threads
- Issue with DX11 not properly parsing non-structured buffer parameters in shaders

BearishSun 9 سال پیش
والد
کامیت
b2dd0ffa03
29فایلهای تغییر یافته به همراه445 افزوده شده و 155 حذف شده
  1. 4 3
      Data/Examples/Example.bsl
  2. BIN
      Data/Examples/Example.bsl.asset
  3. 8 4
      Data/Raw/Engine/DataList.json
  4. 23 19
      Data/Raw/Engine/Includes/BasePass.bslinc
  5. 4 13
      Data/Raw/Engine/Includes/LightingCommon.bslinc
  6. 8 6
      Data/Raw/Engine/Includes/NormalVertexInput.bslinc
  7. 8 6
      Data/Raw/Engine/Includes/SkinnedVertexInput.bslinc
  8. 8 8
      Data/Raw/Engine/Includes/Surface.bslinc
  9. 1 1
      Data/Raw/Engine/Shaders/Default.bsl
  10. 3 3
      Data/Raw/Engine/Shaders/Diffuse.bsl
  11. 3 0
      Data/Raw/Engine/Shaders/LightGridLLCreation.bsl
  12. 10 8
      Data/Raw/Engine/Shaders/LightGridLLReduction.bsl
  13. 8 0
      Data/Raw/Engine/Shaders/TiledDeferredLighting.bsl
  14. 168 0
      Data/Raw/Engine/Shaders/Transparent.bsl
  15. 5 3
      Documentation/Manuals/Native/bslfx.md
  16. 3 3
      Source/BansheeCore/Source/BsMaterialParams.cpp
  17. 24 2
      Source/BansheeCore/Source/BsShader.cpp
  18. 13 2
      Source/BansheeD3D11RenderAPI/Source/BsD3D11HLSLParamParser.cpp
  19. 3 1
      Source/BansheeEngine/Include/BsBuiltinResources.h
  20. 5 1
      Source/BansheeEngine/Source/BsBuiltinResources.cpp
  21. 2 0
      Source/BansheeGLRenderAPI/Source/BsGLSLParamParser.cpp
  22. 4 1
      Source/MBansheeEditor/Inspectors/MaterialInspector.cs
  23. 2 1
      Source/MBansheeEngine/Utility/Builtin.cs
  24. 22 5
      Source/RenderBeast/Include/BsLightRendering.h
  25. 2 0
      Source/RenderBeast/Include/BsRenderBeast.h
  26. 6 0
      Source/RenderBeast/Include/BsRendererObject.h
  27. 47 42
      Source/RenderBeast/Source/BsLightRendering.cpp
  28. 11 0
      Source/RenderBeast/Source/BsObjectRendering.cpp
  29. 40 23
      Source/RenderBeast/Source/BsRenderBeast.cpp

+ 4 - 3
Data/Examples/Example.bsl

@@ -1,4 +1,4 @@
-#include "$ENGINE$\DeferredBasePass.bslinc"
+#include "$ENGINE$\BasePass.bslinc"
 
 
 Parameters = 
 Parameters = 
 {
 {
@@ -44,8 +44,9 @@ Technique : base("Surface") =
 		Fragment =
 		Fragment =
 		{
 		{
 			layout(location = 0) in vec2 uv0;
 			layout(location = 0) in vec2 uv0;
-			layout(location = 1) in vec3 tangentToWorldZ;
-			layout(location = 2) in vec4 tangentToWorldX;			
+			layout(location = 1) in vec3 worldPosition;
+			layout(location = 2) in vec3 tangentToWorldZ;
+			layout(location = 3) in vec4 tangentToWorldX;			
 		
 		
 			layout(binding = 4) uniform sampler2D tex;
 			layout(binding = 4) uniform sampler2D tex;
 
 

BIN
Data/Examples/Example.bsl.asset


+ 8 - 4
Data/Raw/Engine/DataList.json

@@ -48,10 +48,6 @@
         }
         }
     ],
     ],
     "Includes": [
     "Includes": [
-        {
-            "Path": "DeferredBasePass.bslinc",
-            "UUID": "d4078f9c-d7e9-4d63-b506-4d270c08b01e"
-        },
         {
         {
             "Path": "GBuffer.bslinc",
             "Path": "GBuffer.bslinc",
             "UUID": "ef1a179a-4bf9-4dbd-b62a-e18524d959b6"
             "UUID": "ef1a179a-4bf9-4dbd-b62a-e18524d959b6"
@@ -111,6 +107,10 @@
         {
         {
             "Path": "SurfaceData.bslinc",
             "Path": "SurfaceData.bslinc",
             "UUID": "3364cb35-9140-4571-8fae-d5648ae7386f"
             "UUID": "3364cb35-9140-4571-8fae-d5648ae7386f"
+        },
+        {
+            "Path": "BasePass.bslinc",
+            "UUID": "ec1d3d37-5509-4bcb-9be2-93208d6ae224"
         }
         }
     ],
     ],
     "Shaders": [
     "Shaders": [
@@ -205,6 +205,10 @@
         {
         {
             "Path": "LightGridLLReduction.bsl",
             "Path": "LightGridLLReduction.bsl",
             "UUID": "d190e4e1-5ea9-4961-9ee3-b5df218cb5e6"
             "UUID": "d190e4e1-5ea9-4961-9ee3-b5df218cb5e6"
+        },
+        {
+            "Path": "Transparent.bsl",
+            "UUID": "10db2029-145c-424e-8399-2be48aa66680"
         }
         }
     ],
     ],
     "Skin": [
     "Skin": [

+ 23 - 19
Data/Raw/Engine/Includes/DeferredBasePass.bslinc → Data/Raw/Engine/Includes/BasePass.bslinc

@@ -7,8 +7,9 @@
 #define USE_BLEND_SHAPES
 #define USE_BLEND_SHAPES
 #include "$ENGINE$\SkinnedVertexInput.bslinc"
 #include "$ENGINE$\SkinnedVertexInput.bslinc"
 #include "$ENGINE$\NormalVertexInput.bslinc"
 #include "$ENGINE$\NormalVertexInput.bslinc"
+#undef USE_BLEND_SHAPES
 
 
-Technique : base("DeferredBasePassCommon") =
+Technique : base("BasePassCommon") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
 	
 	
@@ -23,6 +24,7 @@ Technique : base("DeferredBasePassCommon") =
 				VertexIntermediate intermediate = getVertexIntermediate(input);
 				VertexIntermediate intermediate = getVertexIntermediate(input);
 				float4 worldPosition = getVertexWorldPosition(input, intermediate);
 				float4 worldPosition = getVertexWorldPosition(input, intermediate);
 				
 				
+				output.worldPosition = worldPosition.xyz;
 				output.position = mul(gMatViewProj, worldPosition);
 				output.position = mul(gMatViewProj, worldPosition);
 				populateVertexOutput(input, intermediate, output);
 				populateVertexOutput(input, intermediate, output);
 							
 							
@@ -48,51 +50,51 @@ Technique : base("DeferredBasePassCommon") =
 };
 };
 
 
 Technique
 Technique
- : base("DeferredBasePass")
+ : base("BasePass")
  : inherits("GBuffer")
  : inherits("GBuffer")
  : inherits("PerCameraData")
  : inherits("PerCameraData")
  : inherits("PerObjectData")
  : inherits("PerObjectData")
  : inherits("NormalVertexInput")
  : inherits("NormalVertexInput")
- : inherits("DeferredBasePassCommon") =
+ : inherits("BasePassCommon") =
 { 
 { 
 	Language = "HLSL11";
 	Language = "HLSL11";
 };
 };
 
 
 Technique
 Technique
- : base("DeferredBasePassSkinned")
+ : base("BasePassSkinned")
  : inherits("GBuffer")
  : inherits("GBuffer")
  : inherits("PerCameraData")
  : inherits("PerCameraData")
  : inherits("PerObjectData")
  : inherits("PerObjectData")
  : inherits("SkinnedVertexInput")
  : inherits("SkinnedVertexInput")
- : inherits("DeferredBasePassCommon") =
+ : inherits("BasePassCommon") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
 };
 };
 
 
 Technique
 Technique
- : base("DeferredBasePassMorph")
+ : base("BasePassMorph")
  : inherits("GBuffer")
  : inherits("GBuffer")
  : inherits("PerCameraData")
  : inherits("PerCameraData")
  : inherits("PerObjectData")
  : inherits("PerObjectData")
  : inherits("MorphVertexInput")
  : inherits("MorphVertexInput")
- : inherits("DeferredBasePassCommon") =
+ : inherits("BasePassCommon") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
 };
 };
 
 
 Technique
 Technique
- : base("DeferredBasePassSkinnedMorph")
+ : base("BasePassSkinnedMorph")
  : inherits("GBuffer")
  : inherits("GBuffer")
  : inherits("PerCameraData")
  : inherits("PerCameraData")
  : inherits("PerObjectData")
  : inherits("PerObjectData")
  : inherits("SkinnedMorphVertexInput")
  : inherits("SkinnedMorphVertexInput")
- : inherits("DeferredBasePassCommon") =
+ : inherits("BasePassCommon") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
 };
 };
 
 
 Technique 
 Technique 
-	: base("DeferredBasePassCommon") =
+	: base("BasePassCommon") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
 	
 	
@@ -107,8 +109,10 @@ Technique
 			
 			
 				vec4 worldPos;
 				vec4 worldPos;
 				getVertexWorldPosition(intermediate, worldPos);
 				getVertexWorldPosition(intermediate, worldPos);
-			
+				
+				outWorldPosition = worldPos.xyz;
 				gl_Position = gMatViewProj * worldPos;
 				gl_Position = gMatViewProj * worldPos;
+				
 				populateVertexOutput(intermediate);
 				populateVertexOutput(intermediate);
 			}
 			}
 		};
 		};
@@ -129,45 +133,45 @@ Technique
 };
 };
 
 
 Technique
 Technique
- : base("DeferredBasePass")
+ : base("BasePass")
  : inherits("GBuffer")
  : inherits("GBuffer")
  : inherits("PerCameraData")
  : inherits("PerCameraData")
  : inherits("PerObjectData")
  : inherits("PerObjectData")
  : inherits("NormalVertexInput")
  : inherits("NormalVertexInput")
- : inherits("DeferredBasePassCommon") =
+ : inherits("BasePassCommon") =
 { 
 { 
 	Language = "GLSL";
 	Language = "GLSL";
 };
 };
 
 
 Technique
 Technique
- : base("DeferredBasePassSkinned")
+ : base("BasePassSkinned")
  : inherits("GBuffer")
  : inherits("GBuffer")
  : inherits("PerCameraData")
  : inherits("PerCameraData")
  : inherits("PerObjectData")
  : inherits("PerObjectData")
  : inherits("SkinnedVertexInput")
  : inherits("SkinnedVertexInput")
- : inherits("DeferredBasePassCommon") =
+ : inherits("BasePassCommon") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
 };
 };
 
 
 Technique
 Technique
- : base("DeferredBasePassMorph")
+ : base("BasePassMorph")
  : inherits("GBuffer")
  : inherits("GBuffer")
  : inherits("PerCameraData")
  : inherits("PerCameraData")
  : inherits("PerObjectData")
  : inherits("PerObjectData")
  : inherits("MorphVertexInput")
  : inherits("MorphVertexInput")
- : inherits("DeferredBasePassCommon") =
+ : inherits("BasePassCommon") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
 };
 };
 
 
 Technique
 Technique
- : base("DeferredBasePassSkinnedMorph")
+ : base("BasePassSkinnedMorph")
  : inherits("GBuffer")
  : inherits("GBuffer")
  : inherits("PerCameraData")
  : inherits("PerCameraData")
  : inherits("PerObjectData")
  : inherits("PerObjectData")
  : inherits("SkinnedMorphVertexInput")
  : inherits("SkinnedMorphVertexInput")
- : inherits("DeferredBasePassCommon") =
+ : inherits("BasePassCommon") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
 };
 };

+ 4 - 13
Data/Raw/Engine/Includes/LightingCommon.bslinc

@@ -1,19 +1,11 @@
-#include "$ENGINE$\PerCameraData.bslinc"
-
-Blocks =
-{
-	Block PerCamera : auto("PerCamera");
-};
-
 Technique
 Technique
- : base("LightingCommon")
- : inherits("PerCameraData") =
+ : base("LightingCommon") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
 	
 	
 	Pass =
 	Pass =
 	{
 	{
-		Compute = 
+		Common = 
 		{
 		{
 			#define PI 3.1415926
 			#define PI 3.1415926
 			#define HALF_PI 1.5707963
 			#define HALF_PI 1.5707963
@@ -88,14 +80,13 @@ Technique
 };
 };
 
 
 Technique
 Technique
- : base("LightingCommon")
- : inherits("PerCameraData") =
+ : base("LightingCommon") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
 	
 	
 	Pass =
 	Pass =
 	{
 	{
-		Compute = 
+		Common = 
 		{
 		{
 			#define PI 3.1415926
 			#define PI 3.1415926
 			#define HALF_PI 1.5707963
 			#define HALF_PI 1.5707963

+ 8 - 6
Data/Raw/Engine/Includes/NormalVertexInput.bslinc

@@ -15,6 +15,7 @@ Technique
 			{
 			{
 				float4 position : SV_Position;
 				float4 position : SV_Position;
 				float2 uv0 : TEXCOORD0;
 				float2 uv0 : TEXCOORD0;
+				float3 worldPosition : TEXCOORD1;
 				
 				
 				float3 tangentToWorldZ : NORMAL; // Note: Half-precision could be used
 				float3 tangentToWorldZ : NORMAL; // Note: Half-precision could be used
 				float4 tangentToWorldX : TANGENT; // Note: Half-precision could be used
 				float4 tangentToWorldX : TANGENT; // Note: Half-precision could be used
@@ -124,9 +125,10 @@ Technique
 				layout(location = 5) in vec4 bs_normal1;
 				layout(location = 5) in vec4 bs_normal1;
 			#endif
 			#endif
 		
 		
-			layout(location = 0) out vec2 uv0;
-			layout(location = 1) out vec3 tangentToWorldZ;
-			layout(location = 2) out vec4 tangentToWorldX;	
+			layout(location = 0) out vec2 outUV0;
+			layout(location = 1) out vec3 outWorldPosition;
+			layout(location = 2) out vec3 outTangentToWorldZ;
+			layout(location = 3) out vec4 outTangentToWorldX;	
 		
 		
 			out gl_PerVertex
 			out gl_PerVertex
 			{
 			{
@@ -182,10 +184,10 @@ Technique
 			
 			
 			void populateVertexOutput(VertexIntermediate intermediate)
 			void populateVertexOutput(VertexIntermediate intermediate)
 			{
 			{
-				uv0 = bs_texcoord0;
+				outUV0 = bs_texcoord0;
 				
 				
-				tangentToWorldZ = intermediate.worldNormal;
-				tangentToWorldX = intermediate.worldTangent;
+				outTangentToWorldZ = intermediate.worldNormal;
+				outTangentToWorldX = intermediate.worldTangent;
 			}
 			}
 		};
 		};
 	};
 	};

+ 8 - 6
Data/Raw/Engine/Includes/SkinnedVertexInput.bslinc

@@ -20,6 +20,7 @@ Technique
 			{
 			{
 				float4 position : SV_Position;
 				float4 position : SV_Position;
 				float2 uv0 : TEXCOORD0;
 				float2 uv0 : TEXCOORD0;
+				float3 worldPosition : TEXCOORD1;
 				
 				
 				float3 tangentToWorldZ : NORMAL; // Note: Half-precision could be used
 				float3 tangentToWorldZ : NORMAL; // Note: Half-precision could be used
 				float4 tangentToWorldX : TANGENT; // Note: Half-precision could be used
 				float4 tangentToWorldX : TANGENT; // Note: Half-precision could be used
@@ -162,9 +163,10 @@ Technique
 				layout(location = 7) in vec4 bs_normal1;
 				layout(location = 7) in vec4 bs_normal1;
 			#endif
 			#endif
 			
 			
-			layout(location = 0) out vec2 uv0;
-			layout(location = 1) out vec3 tangentToWorldZ;
-			layout(location = 2) out vec4 tangentToWorldX;	
+			layout(location = 0) out vec2 outUV0;
+			layout(location = 1) out vec3 outWorldPosition;
+			layout(location = 2) out vec3 outTangentToWorldZ;
+			layout(location = 3) out vec4 outTangentToWorldX;	
 			
 			
 			layout(binding = 3) uniform samplerBuffer boneMatrices;
 			layout(binding = 3) uniform samplerBuffer boneMatrices;
 		
 		
@@ -260,10 +262,10 @@ Technique
 			
 			
 			void populateVertexOutput(VertexIntermediate intermediate)
 			void populateVertexOutput(VertexIntermediate intermediate)
 			{
 			{
-				uv0 = bs_texcoord0;
+				outUV0 = bs_texcoord0;
 				
 				
-				tangentToWorldZ = intermediate.worldNormal;
-				tangentToWorldX = intermediate.worldTangent;
+				outTangentToWorldZ = intermediate.worldNormal;
+				outTangentToWorldX = intermediate.worldTangent;
 			}
 			}
 		};
 		};
 	};
 	};

+ 8 - 8
Data/Raw/Engine/Includes/Surface.bslinc

@@ -1,12 +1,12 @@
 Technique 
 Technique 
- : inherits("DeferredBasePass")
+ : inherits("BasePass")
  : inherits("Surface") =
  : inherits("Surface") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
 };
 };
 
 
 Technique 
 Technique 
- : inherits("DeferredBasePassSkinned")
+ : inherits("BasePassSkinned")
  : inherits("Surface") =
  : inherits("Surface") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
@@ -14,7 +14,7 @@ Technique
 };
 };
 
 
 Technique 
 Technique 
- : inherits("DeferredBasePassMorph")
+ : inherits("BasePassMorph")
  : inherits("Surface") =
  : inherits("Surface") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
@@ -22,7 +22,7 @@ Technique
 };
 };
 
 
 Technique 
 Technique 
- : inherits("DeferredBasePassSkinnedMorph")
+ : inherits("BasePassSkinnedMorph")
  : inherits("Surface") =
  : inherits("Surface") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
@@ -30,14 +30,14 @@ Technique
 };
 };
 
 
 Technique 
 Technique 
- : inherits("DeferredBasePass")
+ : inherits("BasePass")
  : inherits("Surface") =
  : inherits("Surface") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
 };
 };
 
 
 Technique 
 Technique 
- : inherits("DeferredBasePassSkinned")
+ : inherits("BasePassSkinned")
  : inherits("Surface") =
  : inherits("Surface") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
@@ -45,7 +45,7 @@ Technique
 };
 };
 
 
 Technique 
 Technique 
- : inherits("DeferredBasePassMorph")
+ : inherits("BasePassMorph")
  : inherits("Surface") =
  : inherits("Surface") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
@@ -53,7 +53,7 @@ Technique
 };
 };
 
 
 Technique 
 Technique 
- : inherits("DeferredBasePassSkinnedMorph")
+ : inherits("BasePassSkinnedMorph")
  : inherits("Surface") =
  : inherits("Surface") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";

+ 1 - 1
Data/Raw/Engine/Shaders/Default.bsl

@@ -1,4 +1,4 @@
-#include "$ENGINE$\DeferredBasePass.bslinc"
+#include "$ENGINE$\BasePass.bslinc"
 
 
 Technique : base("Surface") =
 Technique : base("Surface") =
 {
 {

+ 3 - 3
Data/Raw/Engine/Shaders/Diffuse.bsl

@@ -1,4 +1,4 @@
-#include "$ENGINE$\DeferredBasePass.bslinc"
+#include "$ENGINE$\BasePass.bslinc"
 
 
 Parameters =
 Parameters =
 {
 {
@@ -53,8 +53,8 @@ Technique : base("Surface") =
 		Fragment =
 		Fragment =
 		{
 		{
 			layout(location = 0) in vec2 uv0;
 			layout(location = 0) in vec2 uv0;
-			layout(location = 1) in vec3 tangentToWorldZ;
-			layout(location = 2) in vec4 tangentToWorldX;			
+			layout(location = 2) in vec3 tangentToWorldZ;
+			layout(location = 3) in vec4 tangentToWorldX;			
 		
 		
 			layout(binding = 4) uniform sampler2D gAlbedoTex;
 			layout(binding = 4) uniform sampler2D gAlbedoTex;
 			layout(binding = 5) uniform sampler2D gNormalTex;
 			layout(binding = 5) uniform sampler2D gNormalTex;

+ 3 - 0
Data/Raw/Engine/Shaders/LightGridLLCreation.bsl

@@ -1,4 +1,5 @@
 #include "$ENGINE$\GBuffer.bslinc"
 #include "$ENGINE$\GBuffer.bslinc"
+#include "$ENGINE$\PerCameraData.bslinc"
 #include "$ENGINE$\LightingCommon.bslinc"
 #include "$ENGINE$\LightingCommon.bslinc"
 
 
 Blocks =
 Blocks =
@@ -8,6 +9,7 @@ Blocks =
 
 
 Technique
 Technique
  : inherits("GBuffer")
  : inherits("GBuffer")
+ : inherits("PerCameraData")
  : inherits("LightingCommon") =
  : inherits("LightingCommon") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
@@ -133,6 +135,7 @@ Technique
 
 
 Technique
 Technique
  : inherits("GBuffer")
  : inherits("GBuffer")
+ : inherits("PerCameraData")
  : inherits("LightingCommon") =
  : inherits("LightingCommon") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";

+ 10 - 8
Data/Raw/Engine/Shaders/LightGridLLReduction.bsl

@@ -1,4 +1,6 @@
-Technique
+#include "$ENGINE$\PerCameraData.bslinc"
+
+Technique : inherits("PerCameraData") = 
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
 	
 	
@@ -71,7 +73,7 @@ Technique
 	};
 	};
 };
 };
 
 
-Technique
+Technique : inherits("PerCameraData") = 
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";
 	
 	
@@ -108,15 +110,15 @@ Technique
 					return;
 					return;
 					
 					
 				uint maxNumLinks = gNumCells * gMaxNumLightsPerCell;	
 				uint maxNumLinks = gNumCells * gMaxNumLightsPerCell;	
-				uint cellIdx = (gl_GlobalInvocationID.z * gGridSize.y + gl_GlobalInvocationID.y) * gGridSize.x + gl_GlobalInvocationID.x;
+				int cellIdx = int((gl_GlobalInvocationID.z * gGridSize.y + gl_GlobalInvocationID.y) * gGridSize.x + gl_GlobalInvocationID.x);
 				
 				
 				// First count total number of lights affecting the tile
 				// First count total number of lights affecting the tile
-				uint currentIdx = texelFetch(gLinkedListHeads, cellIdx).x;
+				int currentIdx = int(texelFetch(gLinkedListHeads, cellIdx).x);
 				uint numLights = 0;
 				uint numLights = 0;
 				while(currentIdx != 0xFFFFFFFF)
 				while(currentIdx != 0xFFFFFFFF)
 				{
 				{
 					numLights++;
 					numLights++;
-					currentIdx = texelFetch(gLinkedList, currentIdx).y;
+					currentIdx = int(texelFetch(gLinkedList, currentIdx).y);
 				}
 				}
 				
 				
 				// Allocate enough room and remember the offset to indices
 				// Allocate enough room and remember the offset to indices
@@ -125,15 +127,15 @@ Technique
 
 
 				// Actually write light indices
 				// Actually write light indices
 				// Note: Values are written in the reverse order than they were found in
 				// Note: Values are written in the reverse order than they were found in
-				currentIdx = texelFetch(gLinkedListHeads, cellIdx).x;
+				currentIdx = int(texelFetch(gLinkedListHeads, cellIdx).x);
 				uint lightIdx = 0;
 				uint lightIdx = 0;
 				while(currentIdx != 0xFFFFFFFF)
 				while(currentIdx != 0xFFFFFFFF)
 				{
 				{
 					uvec2 entry = texelFetch(gLinkedList, currentIdx).xy;
 					uvec2 entry = texelFetch(gLinkedList, currentIdx).xy;
 				
 				
-					imageStore(gGridLightIndices, indicesStart + lightIdx, uvec4(entry.x, 0, 0, 0));
+					imageStore(gGridLightIndices, int(indicesStart + lightIdx), uvec4(entry.x, 0, 0, 0));
 					
 					
-					currentIdx = entry.y;
+					currentIdx = int(entry.y);
 					lightIdx++;
 					lightIdx++;
 				}
 				}
 			}
 			}

+ 8 - 0
Data/Raw/Engine/Shaders/TiledDeferredLighting.bsl

@@ -1,4 +1,5 @@
 #include "$ENGINE$\GBuffer.bslinc"
 #include "$ENGINE$\GBuffer.bslinc"
+#include "$ENGINE$\PerCameraData.bslinc"
 #include "$ENGINE$\LightingCommon.bslinc"
 #include "$ENGINE$\LightingCommon.bslinc"
 
 
 Parameters =
 Parameters =
@@ -12,8 +13,14 @@ Parameters =
 	Texture2D 	gDepthBufferTex : auto("GBufferDepth");
 	Texture2D 	gDepthBufferTex : auto("GBufferDepth");
 };
 };
 
 
+Blocks =
+{
+	Block PerCamera : auto("PerCamera");
+};
+
 Technique 
 Technique 
   : inherits("GBuffer")
   : inherits("GBuffer")
+  : inherits("PerCameraData")
   : inherits("LightingCommon") =
   : inherits("LightingCommon") =
 {
 {
 	Language = "HLSL11";
 	Language = "HLSL11";
@@ -273,6 +280,7 @@ Technique
 
 
 Technique 
 Technique 
   : inherits("GBuffer")
   : inherits("GBuffer")
+  : inherits("PerCameraData")
   : inherits("LightingCommon") =
   : inherits("LightingCommon") =
 {
 {
 	Language = "GLSL";
 	Language = "GLSL";

+ 168 - 0
Data/Raw/Engine/Shaders/Transparent.bsl

@@ -0,0 +1,168 @@
+#include "$ENGINE$\BasePass.bslinc"
+#include "$ENGINE$\LightingCommon.bslinc"
+
+Parameters =
+{
+	Sampler2D 	gAlbedoSamp : alias("gAlbedoTex");
+	Sampler2D 	gNormalSamp : alias("gNormalTex");
+	
+	Texture2D 	gAlbedoTex;
+	Texture2D	gNormalTex = "normal";
+	
+	float		gOpacity   = 1.0f;
+};
+
+Blocks =
+{
+	Block MaterialParams;
+};
+
+Transparent = true;
+
+Technique 
+ : inherits("LightingCommon")
+ : base("Surface") =
+{
+	Language = "HLSL11";
+	
+	Pass =
+	{
+		DepthWrite = false;
+	
+		Target = 
+		{
+			Blend = true;
+			Color = { SRCA, SRCIA, ADD };
+		};	
+	
+		Fragment =
+		{
+			SamplerState gAlbedoSamp : register(s0);
+			SamplerState gNormalSamp : register(s1);
+			
+			Texture2D gAlbedoTex : register(t0);
+			Texture2D gNormalTex : register(t1);
+			
+			StructuredBuffer<LightData> gLights : register(t2);
+		
+			cbuffer LightParams : register(b4)
+			{
+				// Offsets at which specific light types begin in gLights buffer
+				// Assumed directional lights start at 0
+				// x - offset to point lights, y - offset to spot lights, z - total number of lights
+				uint3 gLightOffsets;
+			}
+			
+			cbuffer MaterialParams : register(b5)
+			{
+				float gOpacity;
+			}
+			
+			float4 main(in VStoFS input) : SV_Target0
+			{
+				float3 normal = normalize(gNormalTex.Sample(gNormalSamp, input.uv0) * 2.0f - float3(1, 1, 1));
+				float3 worldNormal = calcWorldNormal(input, normal);
+			
+				SurfaceData surfaceData;
+				surfaceData.albedo = gAlbedoTex.Sample(gAlbedoSamp, input.uv0);
+				surfaceData.worldNormal.xyz = worldNormal;
+				
+				float3 lightAccumulator = 0;
+				for(uint i = 0; i < gLightOffsets[0]; ++i)
+					lightAccumulator += getDirLightContibution(surfaceData, gLights[i]);
+				
+				for (uint i = gLightOffsets[0]; i < gLightOffsets[1]; ++i)
+					lightAccumulator += getPointLightContribution(input.worldPosition, surfaceData, gLights[i]);
+
+				for(uint i = gLightOffsets[1]; i < gLightOffsets[2]; ++i)
+					lightAccumulator += getSpotLightContribution(input.worldPosition, surfaceData, gLights[i]);
+				
+				float3 diffuse = surfaceData.albedo.xyz / PI;
+				return float4(diffuse * lightAccumulator, gOpacity); // TODO - Add better lighting model later
+			}	
+		};
+	};
+};
+
+Technique 
+ : inherits("LightingCommon")
+ : base("Surface") =
+{
+	Language = "GLSL";
+	
+	Pass =
+	{
+		DepthWrite = false;
+		
+		Target = 
+		{
+			Blend = true;
+			Color = { SRCA, SRCIA, ADD };
+		};
+	
+		Fragment =
+		{
+			layout(location = 0) in vec2 uv0;
+			layout(location = 1) in vec3 worldPosition;
+			layout(location = 2) in vec3 tangentToWorldZ;
+			layout(location = 3) in vec4 tangentToWorldX;			
+		
+			layout(binding = 4) uniform sampler2D gAlbedoTex;
+			layout(binding = 5) uniform sampler2D gNormalTex;
+
+			layout(std430, binding = 6) buffer gLights
+			{
+				LightData[] gLightsData;
+			};
+						
+			layout(binding = 7, std140) uniform LightParams
+			{
+				// Offsets at which specific light types begin in gLights buffer
+				// Assumed directional lights start at 0
+				// x - offset to point lights, y - offset to spot lights, z - total number of lights
+				uvec3 gLightOffsets;
+			};
+			
+			layout(binding = 8, std140) uniform MaterialParams
+			{
+				float gOpacity;
+			};
+			
+			layout(location = 0) out vec4 fragColor;
+			
+			void main()
+			{
+				vec3 normal = normalize(texture(gNormalTex, uv0).xyz * 2.0f - vec3(1, 1, 1));
+				vec3 worldNormal = calcWorldNormal(tangentToWorldZ, tangentToWorldX, normal);
+			
+				SurfaceData surfaceData;
+				surfaceData.albedo = texture(gAlbedoTex, uv0);
+				surfaceData.worldNormal.xyz = worldNormal;
+				
+				vec3 lightAccumulator = vec3(0, 0, 0);
+				for(uint i = 0; i < gLightOffsets[0]; ++i)
+				{
+					LightData lightData = gLightsData[i];
+					lightAccumulator += getDirLightContibution(surfaceData, lightData);
+				}
+				
+				for (uint i = gLightOffsets[0]; i < gLightOffsets[1]; ++i)
+				{
+					LightData lightData = gLightsData[i];
+					lightAccumulator += getPointLightContribution(worldPosition, surfaceData, lightData);
+				}
+
+				for(uint i = gLightOffsets[1]; i < gLightOffsets[2]; ++i)
+				{
+					LightData lightData = gLightsData[i];
+					lightAccumulator += getSpotLightContribution(worldPosition, surfaceData, lightData);
+				}
+				
+				vec3 diffuse = surfaceData.albedo.xyz / PI; // TODO - Add better lighting model later
+				fragColor = vec4(diffuse * lightAccumulator, gOpacity); 
+			}	
+		};
+	};
+};
+
+#include "$ENGINE$\Surface.bslinc"

+ 5 - 3
Documentation/Manuals/Native/bslfx.md

@@ -186,7 +186,7 @@ Technique block should therefore always contain a "Language" property. This will
 	Language = "HLSL"
 	Language = "HLSL"
 ~~~~~~~~~~~~~~
 ~~~~~~~~~~~~~~
 
 
-Supported values are "HLSL" (DirectX 11 HLSL), "HLSL9" (DirectX 9 HLSL), and "GLSL".
+Supported values are "HLSL" and "GLSL".
 
 
 In case you are using a non-standard render, you can also specify a renderer using the "Renderer" property. This will ensure the propert technique is used as you switch between renderers.
 In case you are using a non-standard render, you can also specify a renderer using the "Renderer" property. This will ensure the propert technique is used as you switch between renderers.
 ~~~~~~~~~~~~~~
 ~~~~~~~~~~~~~~
@@ -201,9 +201,11 @@ And finally you may specify an optional set of tags that serve as hints to the r
 ~~~~~~~~~~~~~~
 ~~~~~~~~~~~~~~
 
 
 Currently recognized tags by the default renderer are:
 Currently recognized tags by the default renderer are:
- - Animated - When renderer detects it is rendering a mesh that supports skeletal or blend shape animation, it will prefer to pick a technique with this tag, rather than one without it.
+ - Skinned - Technique capable of rendering a skin animated mesh
+ - Morph -  Technique capable of rendering a blend shape animated mesh
+ - SkinnedMorph -  Technique capable of rendering a skin and blend shape animated mesh
 
 
-Unrecognized tags will just be ignored. Renderer can be extended so it supports custom tags.
+When renderer detects an object is using skinned or morph animation (or both), it will prefer to pick a technique with the relevant tag. Unrecognized tags will just be ignored. Renderer can be extended so it supports custom tags.
  
  
 Once the base properties are defined you can start defining code blocks and states.
 Once the base properties are defined you can start defining code blocks and states.
 
 

+ 3 - 3
Source/BansheeCore/Source/BsMaterialParams.cpp

@@ -575,7 +575,7 @@ namespace bs
 				numDirtyDataParams++;
 				numDirtyDataParams++;
 
 
 				UINT32 arraySize = param.arraySize > 1 ? param.arraySize : 1;
 				UINT32 arraySize = param.arraySize > 1 ? param.arraySize : 1;
-				const GpuParamDataTypeInfo& typeInfo = GpuParams::PARAM_SIZES.lookup[(int)param.type];
+				const GpuParamDataTypeInfo& typeInfo = GpuParams::PARAM_SIZES.lookup[(int)param.dataType];
 				UINT32 paramSize = typeInfo.numColumns * typeInfo.numRows * typeInfo.baseTypeSize;
 				UINT32 paramSize = typeInfo.numColumns * typeInfo.numRows * typeInfo.baseTypeSize;
 
 
 				dataParamSize += arraySize * paramSize;
 				dataParamSize += arraySize * paramSize;
@@ -638,7 +638,7 @@ namespace bs
 			case ParamType::Data:
 			case ParamType::Data:
 			{
 			{
 				UINT32 arraySize = param.arraySize > 1 ? param.arraySize : 1;
 				UINT32 arraySize = param.arraySize > 1 ? param.arraySize : 1;
-				const GpuParamDataTypeInfo& typeInfo = GpuParams::PARAM_SIZES.lookup[(int)param.type];
+				const GpuParamDataTypeInfo& typeInfo = GpuParams::PARAM_SIZES.lookup[(int)param.dataType];
 				UINT32 paramSize = typeInfo.numColumns * typeInfo.numRows * typeInfo.baseTypeSize;
 				UINT32 paramSize = typeInfo.numColumns * typeInfo.numRows * typeInfo.baseTypeSize;
 
 
 				UINT32 dataSize = arraySize * paramSize;
 				UINT32 dataSize = arraySize * paramSize;
@@ -791,7 +791,7 @@ namespace bs
 			param.version = mParamVersion;
 			param.version = mParamVersion;
 
 
 			UINT32 arraySize = param.arraySize > 1 ? param.arraySize : 1;
 			UINT32 arraySize = param.arraySize > 1 ? param.arraySize : 1;
-			const GpuParamDataTypeInfo& typeInfo = bs::GpuParams::PARAM_SIZES.lookup[(int)param.type];
+			const GpuParamDataTypeInfo& typeInfo = bs::GpuParams::PARAM_SIZES.lookup[(int)param.dataType];
 			UINT32 paramSize = typeInfo.numColumns * typeInfo.numRows * typeInfo.baseTypeSize;
 			UINT32 paramSize = typeInfo.numColumns * typeInfo.numRows * typeInfo.baseTypeSize;
 
 
 			UINT32 dataParamSize = arraySize * paramSize;
 			UINT32 dataParamSize = arraySize * paramSize;

+ 24 - 2
Source/BansheeCore/Source/BsShader.cpp

@@ -10,6 +10,7 @@
 #include "BsFrameAlloc.h"
 #include "BsFrameAlloc.h"
 #include "BsPass.h"
 #include "BsPass.h"
 #include "BsSamplerState.h"
 #include "BsSamplerState.h"
+#include "BsTexture.h"
 
 
 namespace bs
 namespace bs
 {
 {
@@ -35,8 +36,6 @@ namespace bs
 		desc.rendererSemantic = rendererSemantic;
 		desc.rendererSemantic = rendererSemantic;
 		desc.elementSize = elementSize;
 		desc.elementSize = elementSize;
 
 
-		dataParams[name] = desc;
-
 		if (defaultValue != nullptr)
 		if (defaultValue != nullptr)
 		{
 		{
 			desc.defaultValueIdx = (UINT32)dataDefaultValues.size();
 			desc.defaultValueIdx = (UINT32)dataDefaultValues.size();
@@ -47,6 +46,8 @@ namespace bs
 		}
 		}
 		else
 		else
 			desc.defaultValueIdx = (UINT32)-1;
 			desc.defaultValueIdx = (UINT32)-1;
+
+		dataParams[name] = desc;
 	}
 	}
 
 
 	template<bool Core>
 	template<bool Core>
@@ -358,9 +359,30 @@ namespace bs
 		output.bufferParams = desc.bufferParams;
 		output.bufferParams = desc.bufferParams;
 		output.paramBlocks = desc.paramBlocks;
 		output.paramBlocks = desc.paramBlocks;
 
 
+		output.dataDefaultValues = desc.dataDefaultValues;
+
+		output.samplerDefaultValues.resize(desc.samplerDefaultValues.size());
+		for (UINT32 i = 0; i < (UINT32)desc.samplerDefaultValues.size(); i++)
+		{
+			if (desc.samplerDefaultValues[i] != nullptr)
+				output.samplerDefaultValues.push_back(desc.samplerDefaultValues[i]->getCore());
+			else
+				output.samplerDefaultValues.push_back(nullptr);
+		}
+
+		output.textureDefaultValues.resize(desc.textureDefaultValues.size());
+		for (UINT32 i = 0; i < (UINT32)desc.textureDefaultValues.size(); i++)
+		{
+			if (desc.textureDefaultValues[i].isLoaded())
+				output.textureDefaultValues.push_back(desc.textureDefaultValues[i]->getCore());
+			else
+				output.textureDefaultValues.push_back(nullptr);
+		}
+
 		output.queuePriority = desc.queuePriority;
 		output.queuePriority = desc.queuePriority;
 		output.queueSortType = desc.queueSortType;
 		output.queueSortType = desc.queueSortType;
 		output.separablePasses = desc.separablePasses;
 		output.separablePasses = desc.separablePasses;
+		output.flags = desc.flags;
 		
 		
 		// Ignoring default values as they are not needed for syncing since
 		// Ignoring default values as they are not needed for syncing since
 		// they're initialized through the material.
 		// they're initialized through the material.

+ 13 - 2
Source/BansheeD3D11RenderAPI/Source/BsD3D11HLSLParamParser.cpp

@@ -113,7 +113,9 @@ namespace bs { namespace ct
 					desc.samplers.insert(std::make_pair(memberDesc.name, memberDesc));
 					desc.samplers.insert(std::make_pair(memberDesc.name, memberDesc));
 					break;
 					break;
 				case D3D_SIT_TEXTURE:
 				case D3D_SIT_TEXTURE:
-					switch(resourceDesc.Dimension)
+				{
+					bool isTexture = true;
+					switch (resourceDesc.Dimension)
 					{
 					{
 					case D3D_SRV_DIMENSION_TEXTURE1D:
 					case D3D_SRV_DIMENSION_TEXTURE1D:
 					case D3D_SRV_DIMENSION_TEXTURE1DARRAY:
 					case D3D_SRV_DIMENSION_TEXTURE1DARRAY:
@@ -134,6 +136,10 @@ namespace bs { namespace ct
 					case D3D_SRV_DIMENSION_TEXTURE2DMSARRAY:
 					case D3D_SRV_DIMENSION_TEXTURE2DMSARRAY:
 						memberDesc.type = GPOT_TEXTURE2DMS;
 						memberDesc.type = GPOT_TEXTURE2DMS;
 						break;
 						break;
+					case D3D_SRV_DIMENSION_BUFFER:
+						memberDesc.type = GPOT_BYTE_BUFFER;
+						isTexture = false;
+						break;
 					default:
 					default:
 						LOGWRN("Skipping texture because it has unsupported dimension: " + toString(resourceDesc.Dimension));
 						LOGWRN("Skipping texture because it has unsupported dimension: " + toString(resourceDesc.Dimension));
 					}
 					}
@@ -141,8 +147,13 @@ namespace bs { namespace ct
 					if (memberDesc.type != GPOT_UNKNOWN)
 					if (memberDesc.type != GPOT_UNKNOWN)
 					{
 					{
 						memberDesc.set = mapParameterToSet(type, ParamType::Texture);
 						memberDesc.set = mapParameterToSet(type, ParamType::Texture);
-						desc.textures.insert(std::make_pair(memberDesc.name, memberDesc));
+
+						if (isTexture)
+							desc.textures.insert(std::make_pair(memberDesc.name, memberDesc));
+						else
+							desc.buffers.insert(std::make_pair(memberDesc.name, memberDesc));
 					}
 					}
+				}
 					break;
 					break;
 				case D3D_SIT_STRUCTURED:
 				case D3D_SIT_STRUCTURED:
 					memberDesc.type = GPOT_STRUCTURED_BUFFER;
 					memberDesc.type = GPOT_STRUCTURED_BUFFER;

+ 3 - 1
Source/BansheeEngine/Include/BsBuiltinResources.h

@@ -29,7 +29,7 @@ namespace bs
 	/** Types of builtin shaders that are always available. */
 	/** Types of builtin shaders that are always available. */
 	enum class BuiltinShader
 	enum class BuiltinShader
 	{
 	{
-		Standard, Custom
+		Custom, Standard, Transparent
 	};
 	};
 
 
 	/**	Holds references to built-in resources used by the core engine. */
 	/**	Holds references to built-in resources used by the core engine. */
@@ -180,6 +180,7 @@ namespace bs
 		HShader mShaderSpriteNonAlphaImage;
 		HShader mShaderSpriteNonAlphaImage;
 		HShader mShaderSpriteLine;
 		HShader mShaderSpriteLine;
 		HShader mShaderDiffuse;
 		HShader mShaderDiffuse;
+		HShader mShaderTransparent;
 
 
 		SPtr<ResourceManifest> mResourceManifest;
 		SPtr<ResourceManifest> mResourceManifest;
 
 
@@ -322,6 +323,7 @@ namespace bs
 		static const WString ShaderSpriteImageNoAlphaFile;
 		static const WString ShaderSpriteImageNoAlphaFile;
 		static const WString ShaderSpriteLineFile;
 		static const WString ShaderSpriteLineFile;
 		static const WString ShaderDiffuseFile;
 		static const WString ShaderDiffuseFile;
+		static const WString ShaderTransparentFile;
 
 
 		static const WString MeshSphereFile;
 		static const WString MeshSphereFile;
 		static const WString MeshBoxFile;
 		static const WString MeshBoxFile;

+ 5 - 1
Source/BansheeEngine/Source/BsBuiltinResources.cpp

@@ -185,6 +185,7 @@ namespace bs
 	const WString BuiltinResources::ShaderSpriteImageNoAlphaFile = L"SpriteImageNoAlpha.bsl";
 	const WString BuiltinResources::ShaderSpriteImageNoAlphaFile = L"SpriteImageNoAlpha.bsl";
 	const WString BuiltinResources::ShaderSpriteLineFile = L"SpriteLine.bsl";
 	const WString BuiltinResources::ShaderSpriteLineFile = L"SpriteLine.bsl";
 	const WString BuiltinResources::ShaderDiffuseFile = L"Diffuse.bsl";
 	const WString BuiltinResources::ShaderDiffuseFile = L"Diffuse.bsl";
+	const WString BuiltinResources::ShaderTransparentFile = L"Transparent.bsl";
 
 
 	/************************************************************************/
 	/************************************************************************/
 	/* 								MESHES							  		*/
 	/* 								MESHES							  		*/
@@ -278,6 +279,7 @@ namespace bs
 		mShaderSpriteNonAlphaImage = getShader(ShaderSpriteImageNoAlphaFile);
 		mShaderSpriteNonAlphaImage = getShader(ShaderSpriteImageNoAlphaFile);
 		mShaderSpriteLine = getShader(ShaderSpriteLineFile);
 		mShaderSpriteLine = getShader(ShaderSpriteLineFile);
 		mShaderDiffuse = getShader(ShaderDiffuseFile);
 		mShaderDiffuse = getShader(ShaderDiffuseFile);
+		mShaderTransparent = getShader(ShaderTransparentFile);
 
 
 		SPtr<PixelData> dummyPixelData = PixelData::create(2, 2, 1, PF_R8G8B8A8);
 		SPtr<PixelData> dummyPixelData = PixelData::create(2, 2, 1, PF_R8G8B8A8);
 
 
@@ -1311,7 +1313,9 @@ namespace bs
 		switch(type)
 		switch(type)
 		{
 		{
 		case BuiltinShader::Standard:
 		case BuiltinShader::Standard:
-				return mShaderDiffuse;
+			return mShaderDiffuse;
+		case BuiltinShader::Transparent:
+			return mShaderTransparent;
 		}
 		}
 
 
 		return HShader();
 		return HShader();

+ 2 - 0
Source/BansheeGLRenderAPI/Source/BsGLSLParamParser.cpp

@@ -397,6 +397,8 @@ namespace bs { namespace ct
 				isImage = true;
 				isImage = true;
 				break;
 				break;
 			case GL_SAMPLER_BUFFER:
 			case GL_SAMPLER_BUFFER:
+			case GL_UNSIGNED_INT_SAMPLER_BUFFER:
+			case GL_INT_SAMPLER_BUFFER:
 			case GL_IMAGE_BUFFER:
 			case GL_IMAGE_BUFFER:
 			case GL_UNSIGNED_INT_IMAGE_BUFFER:
 			case GL_UNSIGNED_INT_IMAGE_BUFFER:
 			case GL_INT_IMAGE_BUFFER:
 			case GL_INT_IMAGE_BUFFER:

+ 4 - 1
Source/MBansheeEditor/Inspectors/MaterialInspector.cs

@@ -112,8 +112,11 @@ namespace BansheeEditor
         {
         {
             // Note: Need a better way to detect the builtin shader perhaps (store it in Material?)
             // Note: Need a better way to detect the builtin shader perhaps (store it in Material?)
             Shader standardShader = Builtin.GetShader(BuiltinShader.Standard);
             Shader standardShader = Builtin.GetShader(BuiltinShader.Standard);
-            if(standardShader == shader)
+            Shader transparentShader = Builtin.GetShader(BuiltinShader.Transparent);
+;            if(standardShader == shader)
                 return BuiltinShader.Standard;
                 return BuiltinShader.Standard;
+            else if(transparentShader == shader)
+                return BuiltinShader.Transparent;
             
             
             return BuiltinShader.Custom;
             return BuiltinShader.Custom;
         }
         }

+ 2 - 1
Source/MBansheeEngine/Utility/Builtin.cs

@@ -14,8 +14,9 @@ namespace BansheeEngine
     /// </summary>
     /// </summary>
     public enum BuiltinShader // Note: Must match C++ BuiltinShader enum
     public enum BuiltinShader // Note: Must match C++ BuiltinShader enum
     {
     {
+        Custom,
         Standard,
         Standard,
-        Custom
+        Transparent
     }
     }
 
 
     /// <summary>
     /// <summary>

+ 22 - 5
Source/RenderBeast/Include/BsLightRendering.h

@@ -40,6 +40,27 @@ namespace bs { namespace ct
 		Light* mInternal;
 		Light* mInternal;
 	};
 	};
 
 
+	/** Contains GPU buffers used by the renderer to manipulate lights. */
+	class GPULightData
+	{
+	public:
+		GPULightData();
+
+		/** Updates the internal buffers with a new set of lights. */
+		void setLights(const Vector<LightData>& lightData, UINT32 numDirLights, UINT32 numRadialLights,
+					   UINT32 numSpotLights);
+
+		/** Returns a GPU bindable buffer containing information about every light. */
+		SPtr<GpuBuffer> getLightBuffer() const { return mLightBuffer; }
+
+		/** Returns a GPU bindable param buffer containing meta-data about light in the ligth buffer. */
+		SPtr<GpuParamBlockBuffer> getParamBuffer() const { return mParamBuffer; }
+
+	private:
+		SPtr<GpuParamBlockBuffer> mParamBuffer;
+		SPtr<GpuBuffer> mLightBuffer;
+	};
+
 	BS_PARAM_BLOCK_BEGIN(TiledLightingParamDef)
 	BS_PARAM_BLOCK_BEGIN(TiledLightingParamDef)
 		BS_PARAM_BLOCK_ENTRY(Vector3I, gLightOffsets)
 		BS_PARAM_BLOCK_ENTRY(Vector3I, gLightOffsets)
 	BS_PARAM_BLOCK_END
 	BS_PARAM_BLOCK_END
@@ -58,8 +79,7 @@ namespace bs { namespace ct
 		void execute(const SPtr<RenderTargets>& gbuffer, const SPtr<GpuParamBlockBuffer>& perCamera);
 		void execute(const SPtr<RenderTargets>& gbuffer, const SPtr<GpuParamBlockBuffer>& perCamera);
 
 
 		/** Binds all the active lights. */
 		/** Binds all the active lights. */
-		void setLights(const Vector<LightData>& lightData, UINT32 numDirLights, UINT32 numRadialLights, 
-					   UINT32 numSpotLights);
+		void setLights(const GPULightData& lightData);
 	private:
 	private:
 		GpuParamTexture mGBufferA;
 		GpuParamTexture mGBufferA;
 		GpuParamTexture mGBufferB;
 		GpuParamTexture mGBufferB;
@@ -68,9 +88,6 @@ namespace bs { namespace ct
 		GpuParamBuffer mLightBufferParam;
 		GpuParamBuffer mLightBufferParam;
 		GpuParamLoadStoreTexture mOutputParam;
 		GpuParamLoadStoreTexture mOutputParam;
 
 
-		SPtr<GpuParamBlockBuffer> mParamBuffer;
-		SPtr<GpuBuffer> mLightBuffer;
-
 		static const UINT32 TILE_SIZE;
 		static const UINT32 TILE_SIZE;
 	};
 	};
 
 

+ 2 - 0
Source/RenderBeast/Include/BsRenderBeast.h

@@ -219,6 +219,8 @@ namespace bs
 		TiledDeferredLightingMat* mTiledDeferredLightingMat;
 		TiledDeferredLightingMat* mTiledDeferredLightingMat;
 		SkyboxMat* mSkyboxMat;
 		SkyboxMat* mSkyboxMat;
 
 
+		GPULightData* mGPULightData;
+
 		ObjectRenderer* mObjectRenderer;
 		ObjectRenderer* mObjectRenderer;
 
 
 		// Sim thread only fields
 		// Sim thread only fields

+ 6 - 0
Source/RenderBeast/Include/BsRendererObject.h

@@ -64,6 +64,12 @@ namespace bs { namespace ct
 		/** Index to which should the per-camera param block buffer be bound to. */
 		/** Index to which should the per-camera param block buffer be bound to. */
 		UINT32 perCameraBindingIdx;
 		UINT32 perCameraBindingIdx;
 
 
+		/** Index to which should the lights param block buffer be bound to. */
+		UINT32 lightParamsBindingIdx;
+
+		/** Parameter to which to bind light buffer used for forward rendering. */
+		GpuParamBuffer lightsBufferParam;
+
 		/** GPU buffer containing element's bone matrices, if it requires any. */
 		/** GPU buffer containing element's bone matrices, if it requires any. */
 		SPtr<GpuBuffer> boneMatrixBuffer;
 		SPtr<GpuBuffer> boneMatrixBuffer;
 
 

+ 47 - 42
Source/RenderBeast/Source/BsLightRendering.cpp

@@ -38,6 +38,50 @@ namespace bs { namespace ct
 		output.color = Vector3(color.r, color.g, color.b);
 		output.color = Vector3(color.r, color.g, color.b);
 	}
 	}
 
 
+	GPULightData::GPULightData()
+	{
+		mParamBuffer = gTiledLightingParamDef.createBuffer();
+	}
+
+	void GPULightData::setLights(const Vector<LightData>& lightData, UINT32 numDirLights, UINT32 numRadialLights,
+				   UINT32 numSpotLights)
+	{
+		Vector3I lightOffsets;
+		lightOffsets[0] = numDirLights;
+		lightOffsets[1] = lightOffsets[0] + numRadialLights;
+		lightOffsets[2] = lightOffsets[1] + numSpotLights;
+
+		UINT32 totalNumLights = (UINT32)lightOffsets[2];
+
+		UINT32 size = totalNumLights * sizeof(LightData);
+		UINT32 curBufferSize;
+
+		if (mLightBuffer != nullptr)
+			curBufferSize = mLightBuffer->getSize();
+		else
+			curBufferSize = 0;
+
+		if (size > curBufferSize || curBufferSize == 0)
+		{
+			// Allocate at least one block even if no lights, to avoid issues with null buffers
+			UINT32 bufferSize = std::max(1, Math::ceilToInt(size / (float)BUFFER_INCREMENT)) * BUFFER_INCREMENT;
+
+			GPU_BUFFER_DESC bufferDesc;
+			bufferDesc.type = GBT_STRUCTURED;
+			bufferDesc.elementCount = bufferSize / sizeof(LightData);
+			bufferDesc.elementSize = sizeof(LightData);
+			bufferDesc.format = BF_UNKNOWN;
+
+			mLightBuffer = GpuBuffer::create(bufferDesc);
+		}
+
+		if (size > 0)
+			mLightBuffer->writeData(0, size, lightData.data(), BWT_DISCARD);
+
+		gTiledLightingParamDef.gLightOffsets.set(mParamBuffer, lightOffsets);
+		mParamBuffer->flushToGPU();
+	}
+
 	const UINT32 TiledDeferredLightingMat::TILE_SIZE = 16;
 	const UINT32 TiledDeferredLightingMat::TILE_SIZE = 16;
 
 
 	TiledDeferredLightingMat::TiledDeferredLightingMat()
 	TiledDeferredLightingMat::TiledDeferredLightingMat()
@@ -57,9 +101,6 @@ namespace bs { namespace ct
 
 
 		params->getBufferParam(GPT_COMPUTE_PROGRAM, "gLights", mLightBufferParam);
 		params->getBufferParam(GPT_COMPUTE_PROGRAM, "gLights", mLightBufferParam);
 		params->getLoadStoreTextureParam(GPT_COMPUTE_PROGRAM, "gOutput", mOutputParam);
 		params->getLoadStoreTextureParam(GPT_COMPUTE_PROGRAM, "gOutput", mOutputParam);
-
-		mParamBuffer = gTiledLightingParamDef.createBuffer();
-		mParamsSet->setParamBlockBuffer("Params", mParamBuffer, true);
 	}
 	}
 
 
 	void TiledDeferredLightingMat::_initDefines(ShaderDefines& defines)
 	void TiledDeferredLightingMat::_initDefines(ShaderDefines& defines)
@@ -90,45 +131,9 @@ namespace bs { namespace ct
 		RenderAPI::instance().dispatchCompute(numTilesX, numTilesY);
 		RenderAPI::instance().dispatchCompute(numTilesX, numTilesY);
 	}
 	}
 
 
-	void TiledDeferredLightingMat::setLights(const Vector<LightData>& lightData, UINT32 numDirLights, 
-											 UINT32 numRadialLights, UINT32 numSpotLights)
+	void TiledDeferredLightingMat::setLights(const GPULightData& lightData)
 	{
 	{
-		Vector3I lightOffsets;
-		lightOffsets[0] = numDirLights;
-		lightOffsets[1] = lightOffsets[0] + numRadialLights;
-		lightOffsets[2] = lightOffsets[1] + numSpotLights;
-
-		UINT32 totalNumLights = (UINT32)lightOffsets[2];
-
-		UINT32 size = totalNumLights * sizeof(LightData);
-		UINT32 curBufferSize;
-
-		if (mLightBuffer != nullptr)
-			curBufferSize = mLightBuffer->getSize();
-		else
-			curBufferSize = 0;
-
-		if (size > curBufferSize || curBufferSize == 0)
-		{
-			// Allocate at least one block even if no lights, to avoid issues with null buffers
-			UINT32 bufferSize = std::max(1, Math::ceilToInt(size / (float)BUFFER_INCREMENT)) * BUFFER_INCREMENT;
-
-			GPU_BUFFER_DESC bufferDesc;
-			bufferDesc.type = GBT_STRUCTURED;
-			bufferDesc.elementCount = bufferSize / sizeof(LightData);
-			bufferDesc.elementSize = sizeof(LightData);
-			bufferDesc.format = BF_UNKNOWN;
-
-			mLightBuffer = GpuBuffer::create(bufferDesc);
-		}
-
-		if (size > 0)
-			mLightBuffer->writeData(0, size, lightData.data(), BWT_DISCARD);
-
-		mLightBufferParam.set(mLightBuffer);
-
-		gTiledLightingParamDef.gLightOffsets.set(mParamBuffer, lightOffsets);
-
-		mParamBuffer->flushToGPU();
+		mLightBufferParam.set(lightData.getLightBuffer());
+		mParamsSet->setParamBlockBuffer("Params", lightData.getParamBuffer(), true);
 	}
 	}
 }}
 }}

+ 11 - 0
Source/RenderBeast/Source/BsObjectRendering.cpp

@@ -27,6 +27,7 @@ namespace bs { namespace ct
 		if (shader == nullptr)
 		if (shader == nullptr)
 		{
 		{
 			element.perCameraBindingIdx = -1;
 			element.perCameraBindingIdx = -1;
+			element.lightParamsBindingIdx = -1;
 
 
 			LOGWRN("Missing shader on material.");
 			LOGWRN("Missing shader on material.");
 			return;
 			return;
@@ -50,8 +51,18 @@ namespace bs { namespace ct
 				element.params->setParamBlockBuffer(paramBlockDesc.second.name,
 				element.params->setParamBlockBuffer(paramBlockDesc.second.name,
 													owner.perCallParamBuffer, true);
 													owner.perCallParamBuffer, true);
 			}
 			}
+			else if(paramBlockDesc.second.rendererSemantic == RBS_PerCamera)
+			{
+				element.perCameraBindingIdx = element.params->getParamBlockBufferIndex(paramBlockDesc.second.name);
+			}
 		}
 		}
 
 
+		element.lightParamsBindingIdx = element.params->getParamBlockBufferIndex("LightParams");
+
+		SPtr<GpuParams> gpuParams = element.params->getGpuParams();
+		if(gpuParams->hasBuffer(GPT_FRAGMENT_PROGRAM, "gLights"))
+			gpuParams->getBufferParam(GPT_FRAGMENT_PROGRAM, "gLights", element.lightsBufferParam);
+
 		const Map<String, SHADER_OBJECT_PARAM_DESC>& bufferDescs = shader->getBufferParams();
 		const Map<String, SHADER_OBJECT_PARAM_DESC>& bufferDescs = shader->getBufferParams();
 		String boneMatricesParamName;
 		String boneMatricesParamName;
 
 

+ 40 - 23
Source/RenderBeast/Source/BsRenderBeast.cpp

@@ -39,9 +39,8 @@ using namespace std::placeholders;
 namespace bs { namespace ct
 namespace bs { namespace ct
 {
 {
 	RenderBeast::RenderBeast()
 	RenderBeast::RenderBeast()
-		: mDefaultMaterial(nullptr), mTiledDeferredLightingMat(nullptr)
-		, mSkyboxMat(nullptr), mObjectRenderer(nullptr), mOptions(bs_shared_ptr_new<RenderBeastOptions>())
-		, mOptionsDirty(true)
+		: mDefaultMaterial(nullptr), mTiledDeferredLightingMat(nullptr), mSkyboxMat(nullptr), mGPULightData(nullptr)
+		, mObjectRenderer(nullptr), mOptions(bs_shared_ptr_new<RenderBeastOptions>()), mOptionsDirty(true)
 	{ }
 	{ }
 
 
 	const StringID& RenderBeast::getName() const
 	const StringID& RenderBeast::getName() const
@@ -76,6 +75,8 @@ namespace bs { namespace ct
 		mTiledDeferredLightingMat = bs_new<TiledDeferredLightingMat>();
 		mTiledDeferredLightingMat = bs_new<TiledDeferredLightingMat>();
 		mSkyboxMat = bs_new<SkyboxMat>();
 		mSkyboxMat = bs_new<SkyboxMat>();
 
 
+		mGPULightData = bs_new<GPULightData>();
+
 		RenderTexturePool::startUp();
 		RenderTexturePool::startUp();
 		PostProcessing::startUp();
 		PostProcessing::startUp();
 	}
 	}
@@ -102,6 +103,7 @@ namespace bs { namespace ct
 		bs_delete(mDefaultMaterial);
 		bs_delete(mDefaultMaterial);
 		bs_delete(mTiledDeferredLightingMat);
 		bs_delete(mTiledDeferredLightingMat);
 		bs_delete(mSkyboxMat);
 		bs_delete(mSkyboxMat);
+		bs_delete(mGPULightData);
 
 
 		RendererUtility::shutDown();
 		RendererUtility::shutDown();
 
 
@@ -698,24 +700,6 @@ namespace bs { namespace ct
 		for(UINT32 i = 0; i < numViews; i++)
 		for(UINT32 i = 0; i < numViews; i++)
 			views[i]->determineVisible(mRenderables, mRenderableCullInfos, &mRenderableVisibility);
 			views[i]->determineVisible(mRenderables, mRenderableCullInfos, &mRenderableVisibility);
 
 
-		// Update per-object, bone matrix and morph shape GPU buffers
-		UINT32 numRenderables = (UINT32)mRenderables.size();
-		for (UINT32 i = 0; i < numRenderables; i++)
-		{
-			if (!mRenderableVisibility[i])
-				continue;
-
-			// Note: Before uploading bone matrices perhaps check if they has actually been changed since last frame
-			mRenderables[i]->renderable->updateAnimationBuffers(frameInfo.animData);
-
-			// Note: Could this step be moved in notifyRenderableUpdated, so it only triggers when material actually gets
-			// changed? Although it shouldn't matter much because if the internal versions keeping track of dirty params.
-			for (auto& element : mRenderables[i]->elements)
-				element.material->updateParamsSet(element.params);
-
-			mRenderables[i]->perObjectParamBuffer->flushToGPU();
-		}
-
 		// Generate a list of lights and their GPU buffers
 		// Generate a list of lights and their GPU buffers
 		UINT32 numDirLights = (UINT32)mDirectionalLights.size();
 		UINT32 numDirLights = (UINT32)mDirectionalLights.size();
 		for (UINT32 i = 0; i < numDirLights; i++)
 		for (UINT32 i = 0; i < numDirLights; i++)
@@ -752,11 +736,39 @@ namespace bs { namespace ct
 			mSpotLights[i].getParameters(mLightDataTemp.back());
 			mSpotLights[i].getParameters(mLightDataTemp.back());
 		}
 		}
 
 
-		mTiledDeferredLightingMat->setLights(mLightDataTemp, numDirLights, numRadialLights, numSpotLights);
+		mGPULightData->setLights(mLightDataTemp, numDirLights, numRadialLights, numSpotLights);
 
 
 		mLightDataTemp.clear();
 		mLightDataTemp.clear();
 		mLightVisibilityTemp.clear();
 		mLightVisibilityTemp.clear();
 
 
+		mTiledDeferredLightingMat->setLights(*mGPULightData);
+
+		// Update various buffers required by each renderable
+		UINT32 numRenderables = (UINT32)mRenderables.size();
+		for (UINT32 i = 0; i < numRenderables; i++)
+		{
+			if (!mRenderableVisibility[i])
+				continue;
+
+			// Note: Before uploading bone matrices perhaps check if they has actually been changed since last frame
+			mRenderables[i]->renderable->updateAnimationBuffers(frameInfo.animData);
+
+			// Note: Could this step be moved in notifyRenderableUpdated, so it only triggers when material actually gets
+			// changed? Although it shouldn't matter much because if the internal versions keeping track of dirty params.
+			for (auto& element : mRenderables[i]->elements)
+			{
+				bool isTransparent = (element.material->getShader()->getFlags() & (UINT32)ShaderFlags::Transparent) != 0;
+				if(isTransparent)
+				{
+					
+				}
+
+				element.material->updateParamsSet(element.params);
+			}
+
+			mRenderables[i]->perObjectParamBuffer->flushToGPU();
+		}
+
 		for (UINT32 i = 0; i < numViews; i++)
 		for (UINT32 i = 0; i < numViews; i++)
 		{
 		{
 			if (views[i]->isOverlay())
 			if (views[i]->isOverlay())
@@ -792,6 +804,11 @@ namespace bs { namespace ct
 			{
 			{
 				if (element.perCameraBindingIdx != -1)
 				if (element.perCameraBindingIdx != -1)
 					element.params->setParamBlockBuffer(element.perCameraBindingIdx, perCameraBuffer, true);
 					element.params->setParamBlockBuffer(element.perCameraBindingIdx, perCameraBuffer, true);
+
+				if (element.lightParamsBindingIdx != -1)
+					element.params->setParamBlockBuffer(element.lightParamsBindingIdx, mGPULightData->getParamBuffer(), true);
+
+				element.lightsBufferParam.set(mGPULightData->getLightBuffer());
 			}
 			}
 		}
 		}
 
 
@@ -861,7 +878,7 @@ namespace bs { namespace ct
 
 
 		renderTargets->bindSceneColor(false);
 		renderTargets->bindSceneColor(false);
 
 
-		// Render transparent objects (TODO - No lighting yet)
+		// Render transparent objects
 		const Vector<RenderQueueElement>& transparentElements = viewInfo->getTransparentQueue()->getSortedElements();
 		const Vector<RenderQueueElement>& transparentElements = viewInfo->getTransparentQueue()->getSortedElements();
 		for (auto iter = transparentElements.begin(); iter != transparentElements.end(); ++iter)
 		for (auto iter = transparentElements.begin(); iter != transparentElements.end(); ++iter)
 		{
 		{