[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [46841] trunk/blender: Cycles: add Object Info node, with outputs object location, object/material

Brecht Van Lommel brechtvanlommel at pandora.be
Mon May 21 14:52:28 CEST 2012


Revision: 46841
          http://projects.blender.org/scm/viewvc.php?view=rev&root=bf-blender&revision=46841
Author:   blendix
Date:     2012-05-21 12:52:28 +0000 (Mon, 21 May 2012)
Log Message:
-----------
Cycles: add Object Info node, with outputs object location, object/material
pass index, and a random number unique to the instance of the object.

This can be useful to give some variation to a single material assigned to
multiple instances, either manually controlled through the object index, based
on the object location, or randomized for each instance. 

http://wiki.blender.org/index.php/Doc:2.6/Manual/Render/Cycles/Nodes/More#Object_Info	

Modified Paths:
--------------
    trunk/blender/intern/cycles/blender/blender_object.cpp
    trunk/blender/intern/cycles/blender/blender_shader.cpp
    trunk/blender/intern/cycles/kernel/kernel_object.h
    trunk/blender/intern/cycles/kernel/kernel_shader.h
    trunk/blender/intern/cycles/kernel/svm/svm.h
    trunk/blender/intern/cycles/kernel/svm/svm_geometry.h
    trunk/blender/intern/cycles/kernel/svm/svm_types.h
    trunk/blender/intern/cycles/render/nodes.cpp
    trunk/blender/intern/cycles/render/nodes.h
    trunk/blender/intern/cycles/render/object.cpp
    trunk/blender/intern/cycles/render/object.h
    trunk/blender/intern/cycles/util/util_hash.h
    trunk/blender/source/blender/blenkernel/BKE_node.h
    trunk/blender/source/blender/blenkernel/intern/node.c
    trunk/blender/source/blender/gpu/shaders/gpu_shader_material.glsl
    trunk/blender/source/blender/gpu/shaders/gpu_shader_material.glsl.c
    trunk/blender/source/blender/makesrna/intern/rna_nodetree_types.h
    trunk/blender/source/blender/nodes/CMakeLists.txt
    trunk/blender/source/blender/nodes/NOD_shader.h

Added Paths:
-----------
    trunk/blender/source/blender/nodes/shader/nodes/node_shader_object_info.c

Modified: trunk/blender/intern/cycles/blender/blender_object.cpp
===================================================================
--- trunk/blender/intern/cycles/blender/blender_object.cpp	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/blender/blender_object.cpp	2012-05-21 12:52:28 UTC (rev 46841)
@@ -245,6 +245,7 @@
 	/* object sync */
 	if(object_updated || (object->mesh && object->mesh->need_update)) {
 		object->name = b_ob.name().c_str();
+		object->instance_id = b_index;
 		object->pass_id = b_ob.pass_index();
 		object->tfm = tfm;
 		object->motion.pre = tfm;

Modified: trunk/blender/intern/cycles/blender/blender_shader.cpp
===================================================================
--- trunk/blender/intern/cycles/blender/blender_shader.cpp	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/blender/blender_shader.cpp	2012-05-21 12:52:28 UTC (rev 46841)
@@ -334,6 +334,10 @@
 			node = new LightFalloffNode();
 			break;
 		}
+		case BL::ShaderNode::type_OBJECT_INFO: {
+			node = new ObjectInfoNode();
+			break;
+		}
 		case BL::ShaderNode::type_TEX_IMAGE: {
 			BL::ShaderNodeTexImage b_image_node(b_node);
 			BL::Image b_image(b_image_node.image());

Modified: trunk/blender/intern/cycles/kernel/kernel_object.h
===================================================================
--- trunk/blender/intern/cycles/kernel/kernel_object.h	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/kernel/kernel_object.h	2012-05-21 12:52:28 UTC (rev 46841)
@@ -117,6 +117,16 @@
 #endif
 }
 
+__device_inline float3 object_location(KernelGlobals *kg, ShaderData *sd)
+{
+#ifdef __MOTION__
+	return make_float3(sd->ob_tfm.x.w, sd->ob_tfm.y.w, sd->ob_tfm.z.w);
+#else
+	Transform tfm = object_fetch_transform(kg, sd->object, 0.0f, OBJECT_TRANSFORM);
+	return make_float3(tfm.x.w, tfm.y.w, tfm.z.w);
+#endif
+}
+
 __device_inline float object_surface_area(KernelGlobals *kg, int object)
 {
 	int offset = object*OBJECT_SIZE + OBJECT_PROPERTIES;
@@ -134,5 +144,20 @@
 	return f.y;
 }
 
+__device_inline float object_random_number(KernelGlobals *kg, int object)
+{
+	if(object == ~0)
+		return 0.0f;
+
+	int offset = object*OBJECT_SIZE + OBJECT_PROPERTIES;
+	float4 f = kernel_tex_fetch(__objects, offset);
+	return f.z;
+}
+
+__device int shader_pass_id(KernelGlobals *kg, ShaderData *sd)
+{
+	return kernel_tex_fetch(__shader_flag, (sd->shader & SHADER_MASK)*2 + 1);
+}
+
 CCL_NAMESPACE_END
 

Modified: trunk/blender/intern/cycles/kernel/kernel_shader.h
===================================================================
--- trunk/blender/intern/cycles/kernel/kernel_shader.h	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/kernel/kernel_shader.h	2012-05-21 12:52:28 UTC (rev 46841)
@@ -679,11 +679,6 @@
 }
 #endif
 
-__device int shader_pass_id(KernelGlobals *kg, ShaderData *sd)
-{
-	return kernel_tex_fetch(__shader_flag, (sd->shader & SHADER_MASK)*2 + 1);
-}
-
 /* Free ShaderData */
 
 __device void shader_release(KernelGlobals *kg, ShaderData *sd)

Modified: trunk/blender/intern/cycles/kernel/svm/svm.h
===================================================================
--- trunk/blender/intern/cycles/kernel/svm/svm.h	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/kernel/svm/svm.h	2012-05-21 12:52:28 UTC (rev 46841)
@@ -266,6 +266,9 @@
 			case NODE_LIGHT_PATH:
 				svm_node_light_path(sd, stack, node.y, node.z, path_flag);
 				break;
+			case NODE_OBJECT_INFO:
+				svm_node_object_info(kg, sd, stack, node.y, node.z);
+				break;
 #endif
 			case NODE_CONVERT:
 				svm_node_convert(sd, stack, node.y, node.z, node.w);

Modified: trunk/blender/intern/cycles/kernel/svm/svm_geometry.h
===================================================================
--- trunk/blender/intern/cycles/kernel/svm/svm_geometry.h	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/kernel/svm/svm_geometry.h	2012-05-21 12:52:28 UTC (rev 46841)
@@ -74,5 +74,25 @@
 #endif
 }
 
+/* Object Info */
+
+__device void svm_node_object_info(KernelGlobals *kg, ShaderData *sd, float *stack, uint type, uint out_offset)
+{
+	float data;
+
+	switch(type) {
+		case NODE_INFO_OB_LOCATION: {
+			stack_store_float3(stack, out_offset, object_location(kg, sd));
+			return;
+		}
+		case NODE_INFO_OB_INDEX: data = object_pass_id(kg, sd->object); break;
+		case NODE_INFO_MAT_INDEX: data = shader_pass_id(kg, sd); break;
+		case NODE_INFO_OB_RANDOM: data = object_random_number(kg, sd->object); break;
+		default: data = 0.0f; break;
+	}
+
+	stack_store_float(stack, out_offset, data);
+}
+
 CCL_NAMESPACE_END
 

Modified: trunk/blender/intern/cycles/kernel/svm/svm_types.h
===================================================================
--- trunk/blender/intern/cycles/kernel/svm/svm_types.h	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/kernel/svm/svm_types.h	2012-05-21 12:52:28 UTC (rev 46841)
@@ -92,7 +92,8 @@
 	NODE_RGB_RAMP = 5900,
 	NODE_RGB_CURVES = 6000,
 	NODE_MIN_MAX = 6100,
-	NODE_LIGHT_FALLOFF = 6200
+	NODE_LIGHT_FALLOFF = 6200,
+	NODE_OBJECT_INFO = 6300
 } NodeType;
 
 typedef enum NodeAttributeType {
@@ -109,6 +110,13 @@
 	NODE_GEOM_uv
 } NodeGeometry;
 
+typedef enum NodeObjectInfo {
+	NODE_INFO_OB_LOCATION,
+	NODE_INFO_OB_INDEX,
+	NODE_INFO_MAT_INDEX,
+	NODE_INFO_OB_RANDOM
+} NodeObjectInfo;
+
 typedef enum NodeLightPath {
 	NODE_LP_camera = 0,
 	NODE_LP_shadow,

Modified: trunk/blender/intern/cycles/render/nodes.cpp
===================================================================
--- trunk/blender/intern/cycles/render/nodes.cpp	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/render/nodes.cpp	2012-05-21 12:52:28 UTC (rev 46841)
@@ -1699,7 +1699,7 @@
 	compiler.add(this, "node_light_path");
 }
 
-/* Light Path */
+/* Light Falloff */
 
 LightFalloffNode::LightFalloffNode()
 : ShaderNode("light_path")
@@ -1746,6 +1746,49 @@
 	compiler.add(this, "node_light_falloff");
 }
 
+/* Object Info */
+
+ObjectInfoNode::ObjectInfoNode()
+: ShaderNode("object_info")
+{
+	add_output("Location", SHADER_SOCKET_VECTOR);
+	add_output("Object Index", SHADER_SOCKET_FLOAT);
+	add_output("Material Index", SHADER_SOCKET_FLOAT);
+	add_output("Random", SHADER_SOCKET_FLOAT);
+}
+
+void ObjectInfoNode::compile(SVMCompiler& compiler)
+{
+	ShaderOutput *out = output("Location");
+	if(!out->links.empty()) {
+		compiler.stack_assign(out);
+		compiler.add_node(NODE_OBJECT_INFO, NODE_INFO_OB_LOCATION, out->stack_offset);
+	}
+
+	out = output("Object Index");
+	if(!out->links.empty()) {
+		compiler.stack_assign(out);
+		compiler.add_node(NODE_OBJECT_INFO, NODE_INFO_OB_INDEX, out->stack_offset);
+	}
+
+	out = output("Material Index");
+	if(!out->links.empty()) {
+		compiler.stack_assign(out);
+		compiler.add_node(NODE_OBJECT_INFO, NODE_INFO_MAT_INDEX, out->stack_offset);
+	}
+
+	out = output("Random");
+	if(!out->links.empty()) {
+		compiler.stack_assign(out);
+		compiler.add_node(NODE_OBJECT_INFO, NODE_INFO_OB_RANDOM, out->stack_offset);
+	}
+}
+
+void ObjectInfoNode::compile(OSLCompiler& compiler)
+{
+	compiler.add(this, "node_object_info");
+}
+
 /* Value */
 
 ValueNode::ValueNode()

Modified: trunk/blender/intern/cycles/render/nodes.h
===================================================================
--- trunk/blender/intern/cycles/render/nodes.h	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/render/nodes.h	2012-05-21 12:52:28 UTC (rev 46841)
@@ -285,6 +285,11 @@
 	SHADER_NODE_CLASS(LightFalloffNode)
 };
 
+class ObjectInfoNode : public ShaderNode {
+public:
+	SHADER_NODE_CLASS(ObjectInfoNode)
+};
+
 class ValueNode : public ShaderNode {
 public:
 	SHADER_NODE_CLASS(ValueNode)

Modified: trunk/blender/intern/cycles/render/object.cpp
===================================================================
--- trunk/blender/intern/cycles/render/object.cpp	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/render/object.cpp	2012-05-21 12:52:28 UTC (rev 46841)
@@ -23,6 +23,7 @@
 #include "scene.h"
 
 #include "util_foreach.h"
+#include "util_hash.h"
 #include "util_map.h"
 #include "util_progress.h"
 
@@ -36,6 +37,7 @@
 	mesh = NULL;
 	tfm = transform_identity();
 	visibility = ~0;
+	instance_id = 0;
 	pass_id = 0;
 	bounds = BoundBox::empty;
 	motion.pre = transform_identity();
@@ -164,6 +166,9 @@
 		float surface_area = 0.0f;
 		float pass_id = ob->pass_id;
 		
+		uint ob_hash = hash_int_2d(hash_string(ob->name.c_str()), ob->instance_id);
+		float random_number = (float)ob_hash * (1.0f/(float)0xFFFFFFFF);
+		
 		if(transform_uniform_scale(tfm, uniform_scale)) {
 			map<Mesh*, float>::iterator it = surface_area_map.find(mesh);
 
@@ -198,7 +203,7 @@
 
 		memcpy(&objects[offset], &tfm, sizeof(float4)*3);
 		memcpy(&objects[offset+3], &itfm, sizeof(float4)*3);
-		objects[offset+6] = make_float4(surface_area, pass_id, 0.0f, 0.0f);
+		objects[offset+6] = make_float4(surface_area, pass_id, random_number, 0.0f);
 
 		if(need_motion == Scene::MOTION_PASS) {
 			/* motion transformations, is world/object space depending if mesh

Modified: trunk/blender/intern/cycles/render/object.h
===================================================================
--- trunk/blender/intern/cycles/render/object.h	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/render/object.h	2012-05-21 12:52:28 UTC (rev 46841)
@@ -41,6 +41,7 @@
 	Transform tfm;
 	BoundBox bounds;
 	ustring name;
+	int instance_id;
 	int pass_id;
 	vector<ParamValue> attributes;
 	uint visibility;

Modified: trunk/blender/intern/cycles/util/util_hash.h
===================================================================
--- trunk/blender/intern/cycles/util/util_hash.h	2012-05-21 12:30:06 UTC (rev 46840)
+++ trunk/blender/intern/cycles/util/util_hash.h	2012-05-21 12:52:28 UTC (rev 46841)
@@ -19,13 +19,15 @@
 #ifndef __UTIL_HASH_H__
 #define __UTIL_HASH_H__
 
+#include "util_types.h"
+
 CCL_NAMESPACE_BEGIN
 
-static inline unsigned int hash_int_2d(unsigned int kx, unsigned int ky)
+static inline uint hash_int_2d(uint kx, uint ky)
 {
 	#define rot(x,k) (((x)<<(k)) | ((x)>>(32-(k))))
 
-	unsigned int a, b, c;
+	uint a, b, c;
 
 	a = b = c = 0xdeadbeef + (2 << 2) + 13;
 	a += kx;
@@ -44,11 +46,21 @@
 	#undef rot
 }
 
-static inline unsigned int hash_int(unsigned int k)
+static inline uint hash_int(uint k)
 {
 	return hash_int_2d(k, 0);
 }
 
+static inline uint hash_string(const char *str)
+{
+	uint i = 0, c;
+
+	while ((c = *str++))
+		i = i * 37 + c;
+
+	return i;
+}
+
 CCL_NAMESPACE_END
 
 #endif /* __UTIL_HASH_H__ */


@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list