[Bf-blender-cvs] [e34ba9fb7a9] strand_editmode: Use a 2D texture for the hair interpolation data instead of 1D for larger number of hairs.

Lukas Tönne noreply at git.blender.org
Thu Aug 3 09:13:29 CEST 2017


Commit: e34ba9fb7a91ef9be9109eaae5242cd4b3d7a22c
Author: Lukas Tönne
Date:   Thu Aug 3 08:11:48 2017 +0100
Branches: strand_editmode
https://developer.blender.org/rBe34ba9fb7a91ef9be9109eaae5242cd4b3d7a22c

Use a 2D texture for the hair interpolation data instead of 1D for larger number of hairs.

It turns out that 1D textures have the same size limit on their 1 axis as 2D textures.
This limits the potential number of hair dramatically, even though the actual size of
the texture is very small. Using a 2D texture and wrapping the index avoids this problem.

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

M	source/blender/blenkernel/BKE_editstrands.h
M	source/blender/blenkernel/BKE_hair.h
M	source/blender/blenkernel/intern/editstrands.c
M	source/blender/blenkernel/intern/hair.c
M	source/blender/draw/CMakeLists.txt
M	source/blender/draw/engines/eevee/eevee_materials.c
M	source/blender/draw/engines/eevee/shaders/hair_lib.glsl
M	source/blender/draw/intern/draw_cache_impl_strands.c
M	source/blender/draw/intern/draw_common.h
A	source/blender/draw/intern/draw_hair.c

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

diff --git a/source/blender/blenkernel/BKE_editstrands.h b/source/blender/blenkernel/BKE_editstrands.h
index 9199668fb9e..e5858160f65 100644
--- a/source/blender/blenkernel/BKE_editstrands.h
+++ b/source/blender/blenkernel/BKE_editstrands.h
@@ -85,10 +85,11 @@ bool BKE_editstrands_hair_ensure(struct BMEditStrands *es);
 void BKE_editstrands_hair_free(struct BMEditStrands *es);
 
 int* BKE_editstrands_hair_get_fiber_lengths(struct BMEditStrands *es);
-void BKE_editstrands_hair_get_texture_buffer(struct BMEditStrands *es, void **texbuffer, int *r_size,
-                                             int *strand_map_start,
-                                             int *strand_vertex_start,
-                                             int *fiber_start);
+void BKE_editstrands_hair_get_texture_buffer_size(struct BMEditStrands *es, int *r_size,
+                                                  int *r_strand_map_start,
+                                                  int *r_strand_vertex_start,
+                                                  int *r_fiber_start);
+void BKE_editstrands_hair_get_texture_buffer(struct BMEditStrands *es, void *texbuffer);
 
 /* === Constraints === */
 
diff --git a/source/blender/blenkernel/BKE_hair.h b/source/blender/blenkernel/BKE_hair.h
index 4169a3b6f16..5eafc14e66f 100644
--- a/source/blender/blenkernel/BKE_hair.h
+++ b/source/blender/blenkernel/BKE_hair.h
@@ -68,9 +68,11 @@ struct HairFiber* BKE_hair_fibers_create(const struct StrandsView *strands,
 int* BKE_hair_get_fiber_lengths(const struct HairFiber *fibers, int totfibers,
                                  const struct StrandsView *strands);
 
+void BKE_hair_get_texture_buffer_size(const struct StrandsView *strands, int totfibers,
+                                      int *r_size, int *r_strand_map_start,
+                                      int *r_strand_vertex_start, int *r_fiber_start);
 void BKE_hair_get_texture_buffer(const struct StrandsView *strands, struct DerivedMesh *scalp,
                                  const struct HairFiber *fibers, int totfibers,
-                                 void **r_texbuffer, int *r_size, int *r_strand_map_start,
-                                 int *r_strand_vertex_start, int *r_fiber_start);
+                                 void *texbuffer);
 
 #endif
diff --git a/source/blender/blenkernel/intern/editstrands.c b/source/blender/blenkernel/intern/editstrands.c
index 16e47aabf91..0fe286a5d3a 100644
--- a/source/blender/blenkernel/intern/editstrands.c
+++ b/source/blender/blenkernel/intern/editstrands.c
@@ -239,14 +239,20 @@ int* BKE_editstrands_hair_get_fiber_lengths(BMEditStrands *es)
 	return BKE_hair_get_fiber_lengths(es->hair_fibers, es->hair_totfibers, &strands.base);
 }
 
-void BKE_editstrands_hair_get_texture_buffer(BMEditStrands *es, void **r_texbuffer, int *r_size,
-                                             int *r_strand_map_start,
-                                             int *r_strand_vertex_start,
-                                             int *r_fiber_start)
+void BKE_editstrands_hair_get_texture_buffer_size(BMEditStrands *es, int *r_size,
+                                                  int *r_strand_map_start,
+                                                  int *r_strand_vertex_start,
+                                                  int *r_fiber_start)
 {
 	EditStrandsView strands = editstrands_get_view(es);
-	BKE_hair_get_texture_buffer(&strands.base, es->root_dm, es->hair_fibers, es->hair_totfibers,
-	                            r_texbuffer, r_size, r_strand_map_start, r_strand_vertex_start, r_fiber_start);
+	BKE_hair_get_texture_buffer_size(&strands.base, es->hair_totfibers,
+	                                 r_size, r_strand_map_start, r_strand_vertex_start, r_fiber_start);
+}
+
+void BKE_editstrands_hair_get_texture_buffer(BMEditStrands *es, void *texbuffer)
+{
+	EditStrandsView strands = editstrands_get_view(es);
+	BKE_hair_get_texture_buffer(&strands.base, es->root_dm, es->hair_fibers, es->hair_totfibers, texbuffer);
 }
 
 /* === Constraints === */
diff --git a/source/blender/blenkernel/intern/hair.c b/source/blender/blenkernel/intern/hair.c
index 838956ea843..59677a25bc1 100644
--- a/source/blender/blenkernel/intern/hair.c
+++ b/source/blender/blenkernel/intern/hair.c
@@ -374,60 +374,60 @@ static void hair_get_fiber_buffer(const HairFiber *fibers, int totfibers, Derive
 	}
 }
 
+void BKE_hair_get_texture_buffer_size(const StrandsView *strands, int totfibers,
+                                      int *r_size, int *r_strand_map_start,
+                                      int *r_strand_vertex_start, int *r_fiber_start)
+{
+	const int totstrands = strands->get_num_strands(strands);
+	const int totverts = strands->get_num_verts(strands);
+	*r_strand_map_start = 0;
+	*r_strand_vertex_start = *r_strand_map_start + totstrands * sizeof(HairStrandMapTextureBuffer);
+	*r_fiber_start = *r_strand_vertex_start + totverts * sizeof(HairStrandVertexTextureBuffer);
+	*r_size = *r_fiber_start + totfibers * sizeof(HairFiberTextureBuffer);
+}
+
 void BKE_hair_get_texture_buffer(const StrandsView *strands, DerivedMesh *scalp,
                                  const HairFiber *fibers, int totfibers,
-                                 void **r_texbuffer, int *r_size, int *r_strand_map_start,
-                                 int *r_strand_vertex_start, int *r_fiber_start)
+                                 void *buffer)
 {
 	const int totstrands = strands->get_num_strands(strands);
 	const int totverts = strands->get_num_verts(strands);
 	const int strand_map_start = 0;
 	const int strand_vertex_start = strand_map_start + totstrands * sizeof(HairStrandMapTextureBuffer);
 	const int fiber_start = strand_vertex_start + totverts * sizeof(HairStrandVertexTextureBuffer);
-	const int size = fiber_start + totfibers * sizeof(HairFiberTextureBuffer);
 	
-	void *buffer = MEM_mallocN(size, "hair texture buffer");
+	int *lengths = MEM_mallocN(sizeof(int) * totstrands, "strand lengths");
+	MeshSample *roots = MEM_mallocN(sizeof(MeshSample) * totstrands, "strand roots");
+	float (*positions)[3] = MEM_mallocN(sizeof(float[3]) * totverts, "strand vertex positions");
 	
-	{
-		int *lengths = MEM_mallocN(sizeof(int) * totstrands, "strand lengths");
-		MeshSample *roots = MEM_mallocN(sizeof(MeshSample) * totstrands, "strand roots");
-		float (*positions)[3] = MEM_mallocN(sizeof(float[3]) * totverts, "strand vertex positions");
-		
-		strands->get_strand_lengths(strands, lengths);
-		strands->get_strand_roots(strands, roots);
-		strands->get_strand_vertices(strands, positions);
+	strands->get_strand_lengths(strands, lengths);
+	strands->get_strand_roots(strands, roots);
+	strands->get_strand_vertices(strands, positions);
+	
+	HairStrandMapTextureBuffer *smap = (HairStrandMapTextureBuffer*)((char*)buffer + strand_map_start);
+	HairStrandVertexTextureBuffer *svert = (HairStrandVertexTextureBuffer*)((char*)buffer + strand_vertex_start);
+	unsigned int vertex_start = 0;
+	for (int i = 0; i < totstrands; ++i) {
+		const unsigned int len = lengths[i];
+		smap->vertex_start = vertex_start;
+		smap->vertex_count = len;
 		
-		HairStrandMapTextureBuffer *smap = (HairStrandMapTextureBuffer*)((char*)buffer + strand_map_start);
-		HairStrandVertexTextureBuffer *svert = (HairStrandVertexTextureBuffer*)((char*)buffer + strand_vertex_start);
-		unsigned int vertex_start = 0;
-		for (int i = 0; i < totstrands; ++i) {
-			const unsigned int len = lengths[i];
-			smap->vertex_start = vertex_start;
-			smap->vertex_count = len;
-			
-			{
-				float pos[3];
-				float matrix[3][3];
-				BKE_mesh_sample_eval(scalp, &roots[i], pos, matrix[2], matrix[0]);
-				cross_v3_v3v3(matrix[1], matrix[2], matrix[0]);
-				hair_strand_calc_verts(positions + vertex_start, len, matrix, svert);
-			}
-			
-			vertex_start += len;
-			++smap;
-			svert += len;
+		{
+			float pos[3];
+			float matrix[3][3];
+			BKE_mesh_sample_eval(scalp, &roots[i], pos, matrix[2], matrix[0]);
+			cross_v3_v3v3(matrix[1], matrix[2], matrix[0]);
+			hair_strand_calc_verts(positions + vertex_start, len, matrix, svert);
 		}
 		
-		MEM_freeN(lengths);
-		MEM_freeN(roots);
-		MEM_freeN(positions);
+		vertex_start += len;
+		++smap;
+		svert += len;
 	}
 	
-	hair_get_fiber_buffer(fibers, totfibers, scalp, (HairFiberTextureBuffer*)((char*)buffer + fiber_start));
+	MEM_freeN(lengths);
+	MEM_freeN(roots);
+	MEM_freeN(positions);
 	
-	*r_strand_map_start = strand_map_start;
-	*r_strand_vertex_start = strand_vertex_start;
-	*r_fiber_start = fiber_start;
-	*r_texbuffer = buffer;
-	*r_size = size;
+	hair_get_fiber_buffer(fibers, totfibers, scalp, (HairFiberTextureBuffer*)((char*)buffer + fiber_start));
 }
diff --git a/source/blender/draw/CMakeLists.txt b/source/blender/draw/CMakeLists.txt
index b4527361615..1fada0e6f93 100644
--- a/source/blender/draw/CMakeLists.txt
+++ b/source/blender/draw/CMakeLists.txt
@@ -62,6 +62,7 @@ set(SRC
 	intern/draw_cache_impl_particles.c
 	intern/draw_cache_impl_strands.c
 	intern/draw_common.c
+	intern/draw_hair.c
 	intern/draw_manager.c
 	intern/draw_manager_text.c
 	intern/draw_view.c
diff --git a/source/blender/draw/engines/eevee/eevee_materials.c b/source/blender/draw/engines/eevee/eevee_materials.c
index 1c937cac92e..a50b5b62e62 100644
--- a/source/blender/draw/engines/eevee/eevee_materials.c
+++ b/source/blender/draw/engines/eevee/eevee_materials.c
@@ -196,7 +196,7 @@ static char *eevee_get_defines(int options)
 		BLI_dynstr_appendf(ds, "#define HAIR_SHADER\n");
 	}
 	if ((options & VAR_MAT_HAIR_FIBERS) != 0) {
-		BLI_dynstr_appendf(ds, "#define HAIR_SHADER_FIBERS\n");
+		BLI_dynstr_append(ds, DRW_hair_shader_defines());
 	}
 	if ((options & VAR_MAT_PROBE) != 0) {
 		BLI_dynstr_appendf(ds, "#define PROBE_CAPTURE\n");
@@ -381,12 +381,15 @@ void EEVEE_materials_init(EEVEE_StorageList *stl)
 		        "#define CLIP_PLANES\n");
 
 		e_data.default_prepass_hair_fiber_sh = DRW_shader_create(
-		        hair_fiber_vert_str, NULL, datatoc_prepass_frag_glsl,
-		        "#define HAIR_SHADER\n#define HAIR_SHADER_FIBERS\n");
+		        hair_fiber_vert_str, NULL, datatoc_prepass_frag_glsl, DRW_hair_shader_defines());
 
-		e_data.default_prepass_hair_fiber

@@ Diff output truncated at 10240 characters. @@




More information about the Bf-blender-cvs mailing list