[Bf-blender-cvs] [a102d33] master: Sculpting:

Antony Riakiotakis noreply at git.blender.org
Thu Dec 19 13:40:27 CET 2013


Commit: a102d3397f69e84b11d57ac15a5206a60cf41614
Author: Antony Riakiotakis
Date:   Thu Dec 19 14:39:54 2013 +0200
http://developer.blender.org/rBa102d3397f69e84b11d57ac15a5206a60cf41614

Sculpting:

* Support for symmetry in lasso masking
* Optimize away symmetry multiplication of gravity vector if no gravity
active
* Move flip_v3_v3 to paint_utils (used in masking as well)
* Use OpenMP for mask flood fill too.

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

M	source/blender/editors/sculpt_paint/paint_intern.h
M	source/blender/editors/sculpt_paint/paint_mask.c
M	source/blender/editors/sculpt_paint/paint_utils.c
M	source/blender/editors/sculpt_paint/sculpt.c

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

diff --git a/source/blender/editors/sculpt_paint/paint_intern.h b/source/blender/editors/sculpt_paint/paint_intern.h
index 01f5d53..57eaa45 100644
--- a/source/blender/editors/sculpt_paint/paint_intern.h
+++ b/source/blender/editors/sculpt_paint/paint_intern.h
@@ -219,6 +219,7 @@ int vert_paint_poll(struct bContext *C);
 int mask_paint_poll(struct bContext *C);
 
 int facemask_paint_poll(struct bContext *C);
+void flip_v3_v3(float out[3], const float in[3], const char symm);
 
 /* stroke operator */
 typedef enum BrushStrokeMode {
diff --git a/source/blender/editors/sculpt_paint/paint_mask.c b/source/blender/editors/sculpt_paint/paint_mask.c
index 320bf4f..acc138a 100644
--- a/source/blender/editors/sculpt_paint/paint_mask.c
+++ b/source/blender/editors/sculpt_paint/paint_mask.c
@@ -94,6 +94,9 @@ static int mask_flood_fill_exec(bContext *C, wmOperator *op)
 	PBVH *pbvh;
 	PBVHNode **nodes;
 	int totnode, i;
+#ifdef _OPENMP
+	Sculpt *sd = CTX_data_tool_settings(C)->sculpt;
+#endif
 
 	mode = RNA_enum_get(op->ptr, "mode");
 	value = RNA_float_get(op->ptr, "value");
@@ -108,6 +111,7 @@ static int mask_flood_fill_exec(bContext *C, wmOperator *op)
 
 	sculpt_undo_push_begin("Mask flood fill");
 
+	#pragma omp parallel for schedule(guided) if (sd->flags & SCULPT_USE_OPENMP)
 	for (i = 0; i < totnode; i++) {
 		PBVHVertexIter vi;
 
@@ -231,7 +235,7 @@ int do_sculpt_mask_box_select(ViewContext *vc, rcti *rect, bool select, bool UNU
 
 			BKE_pbvh_search_gather(pbvh, BKE_pbvh_node_planes_contain_AABB, clip_planes_final, &nodes, &totnode);
 
-#pragma omp parallel for schedule(guided) if (sd->flags & SCULPT_USE_OPENMP)
+			#pragma omp parallel for schedule(guided) if (sd->flags & SCULPT_USE_OPENMP)
 			for (i = 0; i < totnode; i++) {
 				PBVHVertexIter vi;
 				bool any_masked = false;
@@ -270,6 +274,7 @@ typedef struct LassoMaskData {
 	bool *px;
 	int width;
 	rcti rect; /* bounding box for scanfilling */
+	int symmpass;
 } LassoMaskData;
 
 
@@ -280,9 +285,11 @@ static bool is_effected_lasso(LassoMaskData *data, float co[3])
 {
 	float scr_co_f[2];
 	short scr_co_s[2];
+	float co_final[3];
 
+	flip_v3_v3(co_final, co, data->symmpass);
 	/* first project point to 2d space */
-	ED_view3d_project_float_v2_m4(data->vc->ar, co, scr_co_f, data->projviewobjmat);
+	ED_view3d_project_float_v2_m4(data->vc->ar, co_final, scr_co_f, data->projviewobjmat);
 
 	scr_co_s[0] = scr_co_f[0];
 	scr_co_s[1] = scr_co_f[1];
@@ -309,20 +316,19 @@ static int paint_mask_gesture_lasso_exec(bContext *C, wmOperator *op)
 	int (*mcords)[2] = (int (*)[2])WM_gesture_lasso_path_to_array(C, op, &mcords_tot);
 
 	if (mcords) {
-		float clip_planes[4][4];
+		float clip_planes[4][4], clip_planes_final[4][4];
 		BoundBox bb;
 		bglMats mats = {{0}};
 		Object *ob;
 		ViewContext vc;
 		LassoMaskData data;
-#ifdef _OPENMP
 		Sculpt *sd = CTX_data_tool_settings(C)->sculpt;
-#endif
+		int symm = sd->paint.symmetry_flags & PAINT_SYMM_AXIS_ALL;
 		struct MultiresModifierData *mmd;
 		DerivedMesh *dm;
 		PBVH *pbvh;
 		PBVHNode **nodes;
-		int totnode, i;
+		int totnode, i, symmpass;
 		PaintMaskFloodMode mode = PAINT_MASK_FLOOD_VALUE;
 		bool select = true; /* TODO: see how to implement deselection */
 		float value = select ? 1.0 : 0.0;
@@ -356,38 +362,55 @@ static int paint_mask_gesture_lasso_exec(bContext *C, wmOperator *op)
 		pbvh = dm->getPBVH(ob, dm);
 		ob->sculpt->pbvh = pbvh;
 
-		/* gather nodes inside lasso's enclosing rectangle (should greatly help with bigger meshes) */
-		BKE_pbvh_search_gather(pbvh, BKE_pbvh_node_planes_contain_AABB, clip_planes, &nodes, &totnode);
-
 		sculpt_undo_push_begin("Mask lasso fill");
 
-#pragma omp parallel for schedule(guided) if (sd->flags & SCULPT_USE_OPENMP)
-		for (i = 0; i < totnode; i++) {
-			PBVHVertexIter vi;
-			bool any_masked = false;
+		for (symmpass = 0; symmpass <= symm; ++symmpass) {
+			if (symmpass == 0 ||
+					(symm & symmpass &&
+					 (symm != 5 || symmpass != 3) &&
+					 (symm != 6 || (symmpass != 3 && symmpass != 5))))
+			{
+				int j = 0;
+
+				/* flip the planes symmetrically as needed */
+				for (; j < 4; j++) {
+					flip_plane(clip_planes_final[j], clip_planes[j], symmpass);
+				}
 
-			BKE_pbvh_vertex_iter_begin(pbvh, nodes[i], vi, PBVH_ITER_UNIQUE) {
-				if (is_effected_lasso(&data, vi.co)) {
-					if (!any_masked) {
-						any_masked = true;
+				data.symmpass = symmpass;
 
-						sculpt_undo_push_node(ob, nodes[i], SCULPT_UNDO_MASK);
+				/* gather nodes inside lasso's enclosing rectangle (should greatly help with bigger meshes) */
+				BKE_pbvh_search_gather(pbvh, BKE_pbvh_node_planes_contain_AABB, clip_planes_final, &nodes, &totnode);
 
-						BKE_pbvh_node_mark_redraw(nodes[i]);
-						if (BKE_pbvh_type(pbvh) == PBVH_GRIDS)
-							multires_mark_as_modified(ob, MULTIRES_COORDS_MODIFIED);
-					}
+				#pragma omp parallel for schedule(guided) if (sd->flags & SCULPT_USE_OPENMP)
+				for (i = 0; i < totnode; i++) {
+					PBVHVertexIter vi;
+					bool any_masked = false;
 
-					mask_flood_fill_set_elem(vi.mask, mode, value);
+					BKE_pbvh_vertex_iter_begin(pbvh, nodes[i], vi, PBVH_ITER_UNIQUE) {
+						if (is_effected_lasso(&data, vi.co)) {
+							if (!any_masked) {
+								any_masked = true;
+
+								sculpt_undo_push_node(ob, nodes[i], SCULPT_UNDO_MASK);
+
+								BKE_pbvh_node_mark_redraw(nodes[i]);
+								if (BKE_pbvh_type(pbvh) == PBVH_GRIDS)
+									multires_mark_as_modified(ob, MULTIRES_COORDS_MODIFIED);
+							}
+
+							mask_flood_fill_set_elem(vi.mask, mode, value);
+						}
+					} BKE_pbvh_vertex_iter_end;
 				}
-			} BKE_pbvh_vertex_iter_end;
+
+				if (nodes)
+					MEM_freeN(nodes);
+			}
 		}
 
 		sculpt_undo_push_end();
 
-		if (nodes)
-			MEM_freeN(nodes);
-
 		ED_region_tag_redraw(vc.ar);
 		MEM_freeN((void *)mcords);
 		MEM_freeN(data.px);
diff --git a/source/blender/editors/sculpt_paint/paint_utils.c b/source/blender/editors/sculpt_paint/paint_utils.c
index bfc431b..dd414a7 100644
--- a/source/blender/editors/sculpt_paint/paint_utils.c
+++ b/source/blender/editors/sculpt_paint/paint_utils.c
@@ -342,6 +342,23 @@ int imapaint_pick_face(ViewContext *vc, const int mval[2], unsigned int *index,
 	return 1;
 }
 
+/* Uses symm to selectively flip any axis of a coordinate. */
+void flip_v3_v3(float out[3], const float in[3], const char symm)
+{
+	if (symm & PAINT_SYMM_X)
+		out[0] = -in[0];
+	else
+		out[0] = in[0];
+	if (symm & PAINT_SYMM_Y)
+		out[1] = -in[1];
+	else
+		out[1] = in[1];
+	if (symm & PAINT_SYMM_Z)
+		out[2] = -in[2];
+	else
+		out[2] = in[2];
+}
+
 /* used for both 3d view and image window */
 void paint_sample_color(const bContext *C, ARegion *ar, int x, int y)    /* frontbuf */
 {
diff --git a/source/blender/editors/sculpt_paint/sculpt.c b/source/blender/editors/sculpt_paint/sculpt.c
index 4a1859c..975aa28 100644
--- a/source/blender/editors/sculpt_paint/sculpt.c
+++ b/source/blender/editors/sculpt_paint/sculpt.c
@@ -759,23 +759,6 @@ static float integrate_overlap(Brush *br)
 	return max;
 }
 
-/* Uses symm to selectively flip any axis of a coordinate. */
-static void flip_v3_v3(float out[3], const float in[3], const char symm)
-{
-	if (symm & PAINT_SYMM_X)
-		out[0] = -in[0];
-	else
-		out[0] = in[0];
-	if (symm & PAINT_SYMM_Y)
-		out[1] = -in[1];
-	else
-		out[1] = in[1];
-	if (symm & PAINT_SYMM_Z)
-		out[2] = -in[2];
-	else
-		out[2] = in[2];
-}
-
 static void flip_v3(float v[3], const char symm)
 {
 	flip_v3_v3(v, v, symm);
@@ -3478,9 +3461,10 @@ static void calc_brushdata_symm(Sculpt *sd, StrokeCache *cache, const char symm,
 	mul_m4_v3(cache->symm_rot_mat, cache->location);
 	mul_m4_v3(cache->symm_rot_mat, cache->grab_delta_symmetry);
 
-	if (cache->supports_gravity)
+	if (cache->supports_gravity) {
 		flip_v3_v3(cache->gravity_direction, cache->true_gravity_direction, symm);
 		mul_m4_v3(cache->symm_rot_mat, cache->gravity_direction);
+	}
 }
 
 typedef void (*BrushActionFunc)(Sculpt *sd, Object *ob, Brush *brush);




More information about the Bf-blender-cvs mailing list