[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [40337] branches/soc-2011-radish/source/ blender: refactor wpaint_stroke_update_step not to call expensive functions per-vertex and move args passed to do_weight_paint_vertex into WeightPaintInfo structure since there were far too many args to this function .

Campbell Barton ideasman42 at gmail.com
Mon Sep 19 06:53:12 CEST 2011


Revision: 40337
          http://projects.blender.org/scm/viewvc.php?view=rev&root=bf-blender&revision=40337
Author:   campbellbarton
Date:     2011-09-19 04:53:11 +0000 (Mon, 19 Sep 2011)
Log Message:
-----------
refactor wpaint_stroke_update_step not to call expensive functions per-vertex and move args passed to do_weight_paint_vertex into WeightPaintInfo structure since there were far too many args to this function.

Modified Paths:
--------------
    branches/soc-2011-radish/source/blender/blenkernel/intern/armature.c
    branches/soc-2011-radish/source/blender/editors/sculpt_paint/paint_vertex.c

Modified: branches/soc-2011-radish/source/blender/blenkernel/intern/armature.c
===================================================================
--- branches/soc-2011-radish/source/blender/blenkernel/intern/armature.c	2011-09-19 02:43:03 UTC (rev 40336)
+++ branches/soc-2011-radish/source/blender/blenkernel/intern/armature.c	2011-09-19 04:53:11 UTC (rev 40337)
@@ -2466,7 +2466,8 @@
 }
 
 
-/* Returns total selected vgroups */
+/* Returns total selected vgroups,
+ * wpi.defbase_sel is assumed malloc'd, all values are set */
 int get_selected_defgroups(Object *ob, char *dg_selection, int defbase_len)
 {
 	bDeformGroup *defgroup;

Modified: branches/soc-2011-radish/source/blender/editors/sculpt_paint/paint_vertex.c
===================================================================
--- branches/soc-2011-radish/source/blender/editors/sculpt_paint/paint_vertex.c	2011-09-19 02:43:03 UTC (rev 40336)
+++ branches/soc-2011-radish/source/blender/editors/sculpt_paint/paint_vertex.c	2011-09-19 04:53:11 UTC (rev 40337)
@@ -1161,15 +1161,15 @@
  * gen_lck_flags gets the status of "flag" for each bDeformGroup
  *in ob->defbase and returns an array containing them
  */
-static char *gen_lck_flags(Object* ob, int defbase_len)
+static char *gen_lock_flags(Object* ob, int defbase_tot)
 {
 	char is_locked = FALSE;
 	int i;
-	//int defbase_len = BLI_countlist(&ob->defbase);
-	char *lock_flags = MEM_mallocN(defbase_len*sizeof(char), "defflags");
+	//int defbase_tot = BLI_countlist(&ob->defbase);
+	char *lock_flags = MEM_mallocN(defbase_tot*sizeof(char), "defflags");
 	bDeformGroup *defgroup;
 
-	for(i = 0, defgroup = ob->defbase.first; i < defbase_len && defgroup; defgroup = defgroup->next, i++) {
+	for(i = 0, defgroup = ob->defbase.first; i < defbase_tot && defgroup; defgroup = defgroup->next, i++) {
 		lock_flags[i] = ((defgroup->flag & DG_LOCK_WEIGHT) != 0);
 		is_locked |= lock_flags[i];
 	}
@@ -1181,9 +1181,9 @@
 	return NULL;
 }
 
-static int has_locked_group_selected(int defbase_len, char *defbase_sel, char *lock_flags) {
+static int has_locked_group_selected(int defbase_tot, char *defbase_sel, char *lock_flags) {
 	int i;
-	for(i = 0; i < defbase_len; i++) {
+	for(i = 0; i < defbase_tot; i++) {
 		if(defbase_sel[i] && lock_flags[i]) {
 			return TRUE;
 		}
@@ -1193,12 +1193,12 @@
 
 
 #if 0 /* UNUSED */
-static int has_unselected_unlocked_bone_group(int defbase_len, char *defbase_sel, int selected, char *lock_flags, char *bone_groups) {
+static int has_unselected_unlocked_bone_group(int defbase_tot, char *defbase_sel, int selected, char *lock_flags, char *bone_groups) {
 	int i;
-	if(defbase_len == selected) {
+	if(defbase_tot == selected) {
 		return FALSE;
 	}
-	for(i = 0; i < defbase_len; i++) {
+	for(i = 0; i < defbase_tot; i++) {
 		if(bone_groups[i] && !defbase_sel[i] && !lock_flags[i]) {
 			return TRUE;
 		}
@@ -1208,12 +1208,12 @@
 #endif
 
 
-static void multipaint_selection(MDeformVert *dvert, float change, char *defbase_sel, int defbase_len) {
+static void multipaint_selection(MDeformVert *dvert, float change, char *defbase_sel, int defbase_tot) {
 	int i;
 	MDeformWeight *dw;
 	float val;
 	// make sure they are all at most 1 after the change
-	for(i = 0; i < defbase_len; i++) {
+	for(i = 0; i < defbase_tot; i++) {
 		if(defbase_sel[i]) {
 			dw = defvert_find_index(dvert, i);
 			if(dw && dw->weight) {
@@ -1230,7 +1230,7 @@
 		}
 	}
 	// apply the valid change
-	for(i = 0; i < defbase_len; i++) {
+	for(i = 0; i < defbase_tot; i++) {
 		if(defbase_sel[i]) {
 			dw = defvert_find_index(dvert, i);
 			if(dw && dw->weight) {
@@ -1289,7 +1289,7 @@
 // observe the changes made to the weights of groups.
 // make sure all locked groups on the vertex have the same deformation
 // by moving the changes made to groups onto other unlocked groups
-static void enforce_locks(MDeformVert *odv, MDeformVert *ndv, int defbase_len, char *lock_flags, char *bone_groups, char *validmap) {
+static void enforce_locks(MDeformVert *odv, MDeformVert *ndv, int defbase_tot, char *lock_flags, char *bone_groups, char *validmap) {
 	float totchange = 0.0f;
 	float totchange_allowed = 0.0f;
 	float left_over;
@@ -1311,9 +1311,9 @@
 		return;
 	}
 	// record if a group was changed, unlocked and not changed, or locked
-	change_status = MEM_callocN(sizeof(char)*defbase_len, "unlocked_unchanged");
+	change_status = MEM_callocN(sizeof(char)*defbase_tot, "unlocked_unchanged");
 
-	for(i = 0; i < defbase_len; i++) {
+	for(i = 0; i < defbase_tot; i++) {
 		ndw = defvert_find_index(ndv, i);
 		odw = defvert_find_index(odv, i);
 		// the weights are zero, so we can assume a lot
@@ -1452,51 +1452,87 @@
 	}
 }
 
+/* struct to avoid passing many args each call to do_weight_paint_vertex() */
+typedef struct WeightPaintInfo {
+
+	int defbase_tot;
+
+	/* both must add up to 'defbase_tot' */
+	int defbase_tot_sel;
+	int defbase_tot_unsel;
+
+	int vgroup_mirror; /* mirror group or -1 */
+
+	char *lock_flags;  /* boolean array for locked bones,
+						* length of defbase_tot */
+	char *defbase_sel; /* boolean array for selected bones,
+						* length of defbase_tot */
+
+
+	/* TODO, both are the result of wpaint_make_validmap() buy I'm not
+	 * convinced they must be separated like this, nevertheless there are
+	 * possible side-effects with merging them which need to be looked into
+	 * carefully, for now keep both since theres not too much harm in it
+	 * but review at some point if bone_group's var can use validmap instead.
+	 * - campbell */
+	char *vgroup_validmap;
+	char *bone_groups;
+
+
+	char do_flip;
+	char do_multipaint;
+} WeightPaintInfo;
+
 /* fresh start to make multi-paint and locking modular */
-/* returns TRUE if it thinks you need to reset the weights due to normalizing while multi-painting */
-static int apply_mp_lcks_normalize(Mesh *me, int index, MDeformWeight *dw, MDeformWeight *tdw, int defbase_len, float change, float oldChange, float oldw, float neww, char *defbase_sel, int selected, char *bone_groups, char *validmap, char *lock_flags, int multipaint)
+/* returns TRUE if it thinks you need to reset the weights due to
+ * normalizing while multi-painting */
+static int apply_mp_locks_normalize(Mesh *me, WeightPaintInfo *wpi,
+                                    const int index,
+                                    MDeformWeight *dw, MDeformWeight *tdw,
+                                    float change, float oldChange,
+                                    float oldw, float neww)
 {
-	MDeformVert *dvert = me->dvert+index;
-	MDeformVert dv= {NULL};
+	MDeformVert *dv= me->dvert+index;
+	MDeformVert dv_test= {NULL};
 
-	dv.dw= MEM_dupallocN(dvert->dw);
-	dv.flag = dvert->flag;
-	dv.totweight = dvert->totweight;
+	dv_test.dw= MEM_dupallocN(dv->dw);
+	dv_test.flag = dv->flag;
+	dv_test.totweight = dv->totweight;
 	/* do not multi-paint if a locked group is selected or the active group is locked
 	 * !lock_flags[dw->def_nr] helps if nothing is selected, but active group is locked */
-	if((lock_flags == NULL) || (lock_flags[dw->def_nr] == FALSE && has_locked_group_selected(defbase_len, defbase_sel, lock_flags) == FALSE)) {
-		if(multipaint && selected > 1) {
+	if((wpi->lock_flags == NULL) || (wpi->lock_flags[dw->def_nr] == FALSE && has_locked_group_selected(wpi->defbase_tot, wpi->defbase_sel, wpi->lock_flags) == FALSE)) {
+		if(wpi->do_multipaint && wpi->defbase_tot_sel > 1) {
 			if(change && change!=1) {
-				multipaint_selection(dvert, change, defbase_sel, defbase_len);
+				multipaint_selection(dv, change, wpi->defbase_sel, wpi->defbase_tot);
 			}
 		}
 		else { /* this lets users paint normally, but don't let them paint locked groups */
 			dw->weight = neww;
 		}
 	}
-	clamp_weights(dvert);
+	clamp_weights(dv);
 
-	enforce_locks(&dv, dvert, defbase_len, lock_flags, bone_groups, validmap);
+	enforce_locks(&dv_test, dv, wpi->defbase_tot, wpi->lock_flags, wpi->vgroup_validmap, wpi->vgroup_validmap);
 
-	do_weight_paint_auto_normalize_all_groups(dvert, validmap);
+	do_weight_paint_auto_normalize_all_groups(dv, wpi->vgroup_validmap);
 
-	if(oldChange && multipaint && selected > 1) {
+	if(oldChange && wpi->do_multipaint && wpi->defbase_tot_sel > 1) {
 		if(tdw->weight != oldw) {
 			if(neww > oldw) {
 				if(tdw->weight <= oldw) {
-					MEM_freeN(dv.dw);
+					MEM_freeN(dv_test.dw);
 					return TRUE;
 				}
 			}
 			else {
 				if(tdw->weight >= oldw) {
-					MEM_freeN(dv.dw);
+					MEM_freeN(dv_test.dw);
 					return TRUE;
 				}
 			}
 		}
 	}
-	MEM_freeN(dv.dw);
+	MEM_freeN(dv_test.dw);
 	return FALSE;
 }
 
@@ -1514,24 +1550,22 @@
 	return -1;
 }
 
+
 static char *wpaint_make_validmap(Object *ob);
 
-static void do_weight_paint_vertex(VPaint *wp, Object *ob, int index, 
-				   float alpha, float paintweight, int flip, 
-				   int vgroup_mirror, char *validmap, int multipaint)
+
+// int flip,  int vgroup_mirror, char *validmap, int multipaint
+static void do_weight_paint_vertex( /* vars which remain the same for every vert */
+                                   VPaint *wp, Object *ob, WeightPaintInfo *wpi,
+                                    /* vars which change on each stroke */
+                                   int index, float alpha, float paintweight
+                                   )
 {
 	Mesh *me= ob->data;
 	
 	MDeformWeight *dw, *uw;
 	int vgroup= ob->actdef-1;
-	
-	char *lock_flags;
-	
-	char *defbase_sel;
-	int selected;
-	int defbase_len;
 
-
 	if(wp->flag & VP_ONLYVGROUP) {
 		dw= defvert_find_index(me->dvert+index, vgroup);
 		uw= defvert_find_index(wp->wpaint_prev+index, vgroup);
@@ -1543,38 +1577,29 @@
 	if(dw==NULL || uw==NULL)
 		return;
 
-	lock_flags = gen_lck_flags(ob, defbase_len = BLI_countlist(&ob->defbase));
-	defbase_sel = MEM_mallocN(defbase_len * sizeof(char), "dg_selected_flags");
-	selected = get_selected_defgroups(ob, defbase_sel, defbase_len);
-	if(!selected && ob->actdef) {
-		selected = 1;
-	}
+	/* TODO: De-duplicate the simple weight paint - jason */
+	/* ... or not, since its <10 SLOC - campbell */
 
-	/* TODO: De-duplicate the simple weight paint */
-
 	/* If there are no locks or multipaint,
 	 * then there is no need to run the more complicated checks */
-	if((multipaint == FALSE || selected <= 1) && (lock_flags == NULL || has_locked_group(&me->dvert[index], lock_flags) == FALSE)) {
-		wpaint_blend(wp, dw, uw, alpha, paintweight, flip, FALSE);
-		do_weight_paint_auto_normalize_all_groups(me->dvert+index, validmap);

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list