[Bf-blender-cvs] [242a044bd1f] blender2.8: GPUMaterial: Add support for tangent node.

Clément Foucault noreply at git.blender.org
Thu May 18 16:05:08 CEST 2017


Commit: 242a044bd1fd015f5424318f60fd7a4604970783
Author: Clément Foucault
Date:   Thu May 18 14:29:57 2017 +0200
Branches: blender2.8
https://developer.blender.org/rB242a044bd1fd015f5424318f60fd7a4604970783

GPUMaterial: Add support for tangent node.

===================================================================

M	source/blender/draw/intern/draw_cache_impl_mesh.c
M	source/blender/gpu/intern/gpu_codegen.c
M	source/blender/gpu/shaders/gpu_shader_material.glsl
M	source/blender/nodes/shader/nodes/node_shader_geometry.c
M	source/blender/nodes/shader/nodes/node_shader_tangent.c

===================================================================

diff --git a/source/blender/draw/intern/draw_cache_impl_mesh.c b/source/blender/draw/intern/draw_cache_impl_mesh.c
index 841092f1c8d..999ce0a95e4 100644
--- a/source/blender/draw/intern/draw_cache_impl_mesh.c
+++ b/source/blender/draw/intern/draw_cache_impl_mesh.c
@@ -1754,6 +1754,8 @@ static VertexBuffer *mesh_batch_cache_get_tri_shading_data(MeshRenderData *rdata
 
 			/* Tangent */
 			attrib_name = mesh_render_data_tangent_layer_uuid_get(rdata, i);
+			/* WATCH IT : only specifying 3 component instead of 4 (4th is sign).
+			 * That may cause some problem but I could not make it to fail (fclem) */
 #ifdef USE_COMP_MESH_DATA
 #  if USE_10_10_10 && 0 /* Tangents need more precision than this */
 			tangent_id[i] = VertexFormat_add_attrib(format, attrib_name, COMP_I10, 3, NORMALIZE_INT_TO_FLOAT);
diff --git a/source/blender/gpu/intern/gpu_codegen.c b/source/blender/gpu/intern/gpu_codegen.c
index 33655396d88..734474465cd 100644
--- a/source/blender/gpu/intern/gpu_codegen.c
+++ b/source/blender/gpu/intern/gpu_codegen.c
@@ -626,6 +626,8 @@ static void codegen_call_functions(DynStr *ds, ListBase *nodes, GPUOutput *final
 					BLI_dynstr_append(ds, "viewinv");
 				else if (input->builtin == GPU_CAMERA_TEXCO_FACTORS)
 					BLI_dynstr_append(ds, "camtexfac");
+				else if (input->builtin == GPU_OBJECT_MATRIX)
+					BLI_dynstr_append(ds, "objmat");
 				else if (input->builtin == GPU_INVERSE_OBJECT_MATRIX)
 					BLI_dynstr_append(ds, "objinv");
 				else if (input->builtin == GPU_VIEW_POSITION)
@@ -697,6 +699,8 @@ static char *code_generate_fragment(ListBase *nodes, GPUOutput *output, bool use
 	if (use_new_shading) {
 		if (builtins & GPU_CAMERA_TEXCO_FACTORS)
 			BLI_dynstr_append(ds, "\tvec4 camtexfac = CameraTexCoFactors;\n");
+		if (builtins & GPU_OBJECT_MATRIX)
+			BLI_dynstr_append(ds, "\tmat4 objmat = ModelMatrix;\n");
 		if (builtins & GPU_INVERSE_OBJECT_MATRIX)
 			BLI_dynstr_append(ds, "\tmat4 objinv = ModelMatrixInverse;\n");
 		if (builtins & GPU_INVERSE_VIEW_MATRIX)
@@ -709,6 +713,8 @@ static char *code_generate_fragment(ListBase *nodes, GPUOutput *output, bool use
 	else {
 		if (builtins & GPU_CAMERA_TEXCO_FACTORS)
 			BLI_dynstr_append(ds, "\tvec4 camtexfac = unfcameratexfactors;\n");
+		if (builtins & GPU_OBJECT_MATRIX)
+			BLI_dynstr_append(ds, "\tmat4 objmat = unfobmat;\n");
 		if (builtins & GPU_INVERSE_OBJECT_MATRIX)
 			BLI_dynstr_append(ds, "\tmat4 objinv = unfinvobmat;\n");
 		if (builtins & GPU_INVERSE_VIEW_MATRIX)
diff --git a/source/blender/gpu/shaders/gpu_shader_material.glsl b/source/blender/gpu/shaders/gpu_shader_material.glsl
index 5a1f48f1f83..f179d9da7bf 100644
--- a/source/blender/gpu/shaders/gpu_shader_material.glsl
+++ b/source/blender/gpu/shaders/gpu_shader_material.glsl
@@ -3,6 +3,7 @@ uniform mat4 ModelViewMatrix;
 #ifndef EEVEE_ENGINE
 uniform mat4 ProjectionMatrix;
 #endif
+uniform mat4 ModelMatrix;
 uniform mat4 ModelMatrixInverse;
 uniform mat4 ModelViewMatrixInverse;
 uniform mat4 ViewMatrixInverse;
@@ -2922,15 +2923,43 @@ void node_uvmap(vec3 attr_uv, out vec3 outvec)
 	outvec = attr_uv;
 }
 
+void tangent_orco_x(vec3 orco_in, out vec3 orco_out)
+{
+	orco_out = vec3(0.0, (orco_in.z - 0.5) * -0.5, (orco_in.y - 0.5) * 0.5);
+}
+
+void tangent_orco_y(vec3 orco_in, out vec3 orco_out)
+{
+	orco_out = vec3((orco_in.z - 0.5) * -0.5, 0.0, (orco_in.x - 0.5) * 0.5);
+}
+
+void tangent_orco_z(vec3 orco_in, out vec3 orco_out)
+{
+	orco_out = vec3((orco_in.y - 0.5) * -0.5, (orco_in.x - 0.5) * 0.5, 0.0);
+}
+
+void node_tangentmap(vec4 attr_tangent, mat4 toworld, out vec3 tangent)
+{
+	tangent = (toworld * vec4(attr_tangent.xyz, 0.0)).xyz;
+}
+
+void node_tangent(vec3 N, vec3 orco, mat4 objmat, mat4 toworld, out vec3 T)
+{
+	N = (toworld * vec4(N, 0.0)).xyz;
+	T = (objmat * vec4(orco, 0.0)).xyz;
+	T = cross(N, normalize(cross(T, N)));
+}
+
 void node_geometry(
-        vec3 I, vec3 N, mat4 toworld,
+        vec3 I, vec3 N, vec3 orco, mat4 objmat, mat4 toworld,
         out vec3 position, out vec3 normal, out vec3 tangent,
         out vec3 true_normal, out vec3 incoming, out vec3 parametric,
         out float backfacing, out float pointiness)
 {
 	position = (toworld * vec4(I, 1.0)).xyz;
 	normal = (toworld * vec4(N, 0.0)).xyz;
-	tangent = vec3(0.0);
+	tangent_orco_z(orco, orco);
+	node_tangent(N, orco, objmat, toworld, tangent);
 	true_normal = normal;
 
 	/* handle perspective/orthographic */
diff --git a/source/blender/nodes/shader/nodes/node_shader_geometry.c b/source/blender/nodes/shader/nodes/node_shader_geometry.c
index 553ea65154f..79833034498 100644
--- a/source/blender/nodes/shader/nodes/node_shader_geometry.c
+++ b/source/blender/nodes/shader/nodes/node_shader_geometry.c
@@ -45,6 +45,7 @@ static int node_shader_gpu_geometry(GPUMaterial *mat, bNode *UNUSED(node), bNode
 {
 	return GPU_stack_link(mat, "node_geometry", in, out,
 	                      GPU_builtin(GPU_VIEW_POSITION), GPU_builtin(GPU_VIEW_NORMAL),
+	                      GPU_attribute(CD_ORCO, ""), GPU_builtin(GPU_OBJECT_MATRIX),
 	                      GPU_builtin(GPU_INVERSE_VIEW_MATRIX));
 }
 
diff --git a/source/blender/nodes/shader/nodes/node_shader_tangent.c b/source/blender/nodes/shader/nodes/node_shader_tangent.c
index 7aa7fb43221..9c853f9d86f 100644
--- a/source/blender/nodes/shader/nodes/node_shader_tangent.c
+++ b/source/blender/nodes/shader/nodes/node_shader_tangent.c
@@ -41,6 +41,28 @@ static void node_shader_init_tangent(bNodeTree *UNUSED(ntree), bNode *node)
 	node->storage = attr;
 }
 
+static int node_shader_gpu_tangent(GPUMaterial *mat, bNode *node, bNodeExecData *UNUSED(execdata), GPUNodeStack *in, GPUNodeStack *out)
+{
+	NodeShaderTangent *attr = node->storage;
+
+	if (attr->direction_type == SHD_TANGENT_UVMAP) {
+		return GPU_stack_link(mat, "node_tangentmap", in, out, GPU_attribute(CD_TANGENT, ""), GPU_builtin(GPU_INVERSE_VIEW_MATRIX));
+	}
+	else {
+		GPUNodeLink *orco = GPU_attribute(CD_ORCO, "");
+
+		if (attr->axis == SHD_TANGENT_AXIS_X)
+			GPU_link(mat, "tangent_orco_x", orco, &orco);
+		else if (attr->axis == SHD_TANGENT_AXIS_Y)
+			GPU_link(mat, "tangent_orco_y", orco, &orco);
+		else
+			GPU_link(mat, "tangent_orco_z", orco, &orco);
+
+		return GPU_stack_link(mat, "node_tangent", in, out, GPU_builtin(GPU_VIEW_NORMAL), orco,
+			GPU_builtin(GPU_OBJECT_MATRIX), GPU_builtin(GPU_INVERSE_VIEW_MATRIX));
+	}
+}
+
 /* node type definition */
 void register_node_type_sh_tangent(void)
 {
@@ -51,6 +73,7 @@ void register_node_type_sh_tangent(void)
 	node_type_socket_templates(&ntype, NULL, sh_node_tangent_out);
 	node_type_size_preset(&ntype, NODE_SIZE_MIDDLE);
 	node_type_init(&ntype, node_shader_init_tangent);
+	node_type_gpu(&ntype, node_shader_gpu_tangent);
 	node_type_storage(&ntype, "NodeShaderTangent", node_free_standard_storage, node_copy_standard_storage);
 
 	nodeRegisterType(&ntype);




More information about the Bf-blender-cvs mailing list