weightpaint_clean, option to clean all vgroups
authorCampbell Barton <ideasman42@gmail.com>
Wed, 27 Dec 2006 09:31:28 +0000 (09:31 +0000)
committerCampbell Barton <ideasman42@gmail.com>
Wed, 27 Dec 2006 09:31:28 +0000 (09:31 +0000)
weightpaint_envelope_assign - can update active vgroup only
weightpaint_normalize - fixups
BKE_plugin_types - made the max length 32 ratehr then 16 so you can fill the text space in pupBlock

release/scripts/bpymodules/BPyMesh.py
release/scripts/weightpaint_clean.py
release/scripts/weightpaint_envelope_assign.py
release/scripts/weightpaint_gradient.py
release/scripts/weightpaint_normalize.py
source/blender/blenkernel/BKE_plugin_types.h

index 712b6b72f80d8efa6cea10a97f90f60df1c76c1c..3fb2d0b35a22dc79601cf635e7cfed52de1b3099 100644 (file)
@@ -78,6 +78,8 @@ def list2MeshWeight(me, groupNames, vWeightList):
        if len(vWeightList) != len(me.verts):
                raise 'Error, Lists Differ in size, do not modify your mesh.verts before updating the weights'
        
+       act_group = me.activeGroup
+       
        # Clear the vert group.
        currentGroupNames= me.getVertGroupNames()
        for group in currentGroupNames:
@@ -100,6 +102,9 @@ def list2MeshWeight(me, groupNames, vWeightList):
                                except:
                                        pass # vert group is not used anymore.
        
+       try:    me.activeGroup = act_group
+       except: pass
+       
        me.update()
 
 
@@ -134,6 +139,8 @@ def dict2MeshWeight(me, groupNames, vWeightDict):
        if len(vWeightDict) != len(me.verts):
                raise 'Error, Lists Differ in size, do not modify your mesh.verts before updating the weights'
        
+       act_group = me.activeGroup
+       
        # Clear the vert group.
        currentGroupNames= me.getVertGroupNames()
        for group in currentGroupNames:
@@ -159,6 +166,9 @@ def dict2MeshWeight(me, groupNames, vWeightDict):
                        except:
                                pass # vert group is not used anymore.
        
+       try:    me.activeGroup = act_group
+       except: pass
+       
        me.update()
 
 def dictWeightMerge(dict_weights):
@@ -290,6 +300,23 @@ def mesh2linkedFaces(me):
        return [fg for fg in face_groups if fg]
 
 
+
+def getEdgeLoopsFromFaces(faces):
+       '''
+       Takes me.faces or a list of faces and returns the edge loops
+       These edge loops are the edges that sit between quads, so they dont touch
+       1 quad, not not connected will make 2 edge loops, both only containing 2 edges.
+       '''
+       
+       edges = {}
+       
+       for f in faces:
+               for i, edkey in enumerate(f.edge_keys):
+                       try:    edges[edkey].append((f, i))
+                       except: edges[edkey] = [(f, i)]
+       
+
+
 def getMeshFromObject(ob, container_mesh=None, apply_modifiers=True, vgroups=True, scn=None):
        '''
        ob - the object that you want to get the mesh from
index d23b4ec916f96cbc917296672639d1dbf429be13..f6e42507f263ee900faf4c98d1a660416327139b 100644 (file)
@@ -41,20 +41,35 @@ It removes very low weighted verts from the current group with a weight option.
 from Blender import Scene, Draw
 import BPyMesh
 SMALL_NUM= 0.000001
-def actWeightNormalize(me, PREF_THRESH, PREF_KEEP_SINGLE):
+def weightClean(me, PREF_THRESH, PREF_KEEP_SINGLE, PREF_OTHER_GROUPS):
        
        groupNames, vWeightDict= BPyMesh.meshWeight2Dict(me)
        act_group= me.activeGroup
        
-       for wd in vWeightDict:
-               if not PREF_KEEP_SINGLE or len(wd) > 1:
-                       try:
-                               w= wd[act_group]
-                               if w <= PREF_THRESH:
-                                       # small weight, remove.
-                                       del wd[act_group]
-                       except:
-                               pass
+       if PREF_OTHER_GROUPS:
+               for wd in vWeightDict:
+                       l = len(wd)
+                       if not PREF_KEEP_SINGLE or l > 1:
+                               for group in wd.keys():
+                                       w= wd[group]
+                                       if w <= PREF_THRESH:
+                                               # small weight, remove.
+                                               del wd[group]
+                                       l-=1
+                                       
+                                       if PREF_KEEP_SINGLE and l == 1:
+                                               break
+       
+       else:
+               for wd in vWeightDict:
+                       if not PREF_KEEP_SINGLE or len(wd) > 1:
+                               try:
+                                       w= wd[act_group]
+                                       if w <= PREF_THRESH:
+                                               # small weight, remove.
+                                               del wd[act_group]
+                               except:
+                                       pass
        
        # Copy weights back to the mesh.
        BPyMesh.dict2MeshWeight(me, groupNames, vWeightDict)
@@ -62,29 +77,28 @@ def actWeightNormalize(me, PREF_THRESH, PREF_KEEP_SINGLE):
 
 def main():
        scn= Scene.GetCurrent()
-       ob= scn.getActiveObject()
+       ob= scn.objects.active
        
-       if not ob or ob.getType() != 'Mesh':
+       if not ob or ob.type != 'Mesh':
                Draw.PupMenu('Error, no active mesh object, aborting.')
                return
        
        me= ob.getData(mesh=1)
        
-       PREF_PEAKWEIGHT= Draw.Create(0.005)
+       PREF_PEAKWEIGHT= Draw.Create(0.001)
        PREF_KEEP_SINGLE= Draw.Create(1)
+       PREF_OTHER_GROUPS= Draw.Create(0)
        
        pup_block= [\
-       ('Peak Weight:', PREF_PEAKWEIGHT, 0.01, 1.0, 'Upper weight for normalizing.'),\
-       ('Keep Single User', PREF_KEEP_SINGLE, 'Dont remove verts that are in this group only.'),\
+       ('Peak Weight:', PREF_PEAKWEIGHT, 0.005, 1.0, 'Remove verts from groups below this weight.'),\
+       ('All Other Groups', PREF_OTHER_GROUPS, 'Clean all groups, not just the current one.'),\
+       ('Keep Single User', PREF_KEEP_SINGLE, 'Keep verts in at least 1 group.'),\
        ]
        
        if not Draw.PupBlock('Clean Selected Meshes...', pup_block):
                return
        
-       PREF_PEAKWEIGHT= PREF_PEAKWEIGHT.val
-       PREF_KEEP_SINGLE= PREF_KEEP_SINGLE.val
-       
-       actWeightNormalize(me, PREF_PEAKWEIGHT, PREF_KEEP_SINGLE)
+       weightClean(me, PREF_PEAKWEIGHT.val, PREF_KEEP_SINGLE.val, PREF_OTHER_GROUPS.val)
        
 if __name__=='__main__':
        main()
\ No newline at end of file
index cdd2c3ad21e52f9d7783e81c06ca99206a854c9d..33475294b2d4fe8768e5da1d5e41533546178656 100644 (file)
@@ -135,36 +135,70 @@ def point_in_data(point, mesh_data_tuple):
        return len( filter(isect, mesh_data) ) % 2
 
 import BPyMesh
-def env_from_group(ob_act, grp, PREF_OVERWRITE=True):
-       # get intersection data
-       # group_isect_data = [intersection_data(ob) for ob in group.objects]
-       group_isect_data = []
-       for ob in grp.objects:
-               if ob != ob_act: # in case we're in the group.
-                       gid = intersection_data(ob)
-                       if gid[1]: # has some triangles?
-                               group_isect_data.append( gid )
+def env_from_group(ob_act, grp, PREF_UPDATE_ACT=True):
        
-       # sort by name
-       group_isect_data.sort()
+       me = ob_act.getData(mesh=1)
+       
+       if PREF_UPDATE_ACT:
+               act_group = me.activeGroup
+               if act_group == 'None':
+                       Draw.PupMenu('Error%t|No active vertex group.')
+                       return
+               
+               try:
+                       ob = Object.Get(act_group)
+               except:
+                       Draw.PupMenu('Error%t|No object named "'+ act_group +'".')
+                       return
+               
+               group_isect = intersection_data(ob)
+               
+       else:
+               
+               # get intersection data
+               # group_isect_data = [intersection_data(ob) for ob in group.objects]
+               group_isect_data = []
+               for ob in grp.objects:
+                       if ob != ob_act: # in case we're in the group.
+                               gid = intersection_data(ob)
+                               if gid[1]: # has some triangles?
+                                       group_isect_data.append( gid )
+                                       
+                                       # we only need 1 for the active group
+                                       if PREF_UPDATE_ACT:
+                                               break
+       
+               # sort by name
+               group_isect_data.sort()
+       
+       if PREF_UPDATE_ACT:
+               group_names, vweight_list = BPyMesh.meshWeight2List(me)
+               group_index = group_names.index(act_group)
+       else:
+               group_names = [gid[0] for gid in group_isect_data]
+               vweight_list= [[0.0]* len(group_names) for i in xrange(len(me.verts))]
        
-       group_names = [gid[0] for gid in group_isect_data]
        
-       me = ob_act.getData(mesh=1)
-       len_group_names= len(group_names)
-       vweight_list= [[0.0]*len_group_names for i in xrange(len(me.verts))]
        
        ob_act_mat = ob_act.matrixWorld
        for vi, v in enumerate(me.verts):
                # Get all the groups for this vert
                co = v.co * ob_act_mat
-               for group_index, group_isect in enumerate(group_isect_data):
-                       if point_in_data(co, group_isect):
-                               vweight_list[vi][group_index] = 1.0
+               
+               if PREF_UPDATE_ACT:
+                       # only update existing
+                       if point_in_data(co, group_isect):      w = 1.0
+                       else:                                                           w = 0.0
+                       vweight_list[vi][group_index] = w
+                       
+               else:
+                       # generate new vgroup weights.
+                       for group_index, group_isect in enumerate(group_isect_data):
+                               if point_in_data(co, group_isect):
+                                       vweight_list[vi][group_index] = 1.0
        
        BPyMesh.list2MeshWeight(me, group_names, vweight_list)
 
-
 import BPyMessages
 def main():
        
@@ -175,28 +209,30 @@ def main():
                return
        
        PREF_ENV_GROUPNAME= Draw.Create('')     
-       PREF_OVERWRITE= Draw.Create(False)
+       PREF_UPDATE_ACT= Draw.Create(True)
        pup_block= [\
-       'Group Name',\
+       ('Update Active', PREF_UPDATE_ACT, 'Only apply envalope weights to the active group.'),\
+       'or initialize from group',\
        ('GR:', PREF_ENV_GROUPNAME, 0, 21, 'The name of an existing groups to '),\
-       #('Overwrite', PREF_OVERWRITE, 'Overwrite existing vertex groups.'),\
        ]
        
        if not Draw.PupBlock('Envalope From Group...', pup_block):
                return
        
-       try:
-               grp = Group.Get(PREF_ENV_GROUPNAME.val)
-       except: 
-               Draw.PupMenu('Error%t|Group "' + PREF_ENV_GROUPNAME.val + '" does not exist.')
-               return
+       PREF_UPDATE_ACT= PREF_UPDATE_ACT.val
        
-       PREF_ENV_GROUPNAME= PREF_ENV_GROUPNAME.val
-       PREF_OVERWRITE= PREF_OVERWRITE.val
+       if not PREF_UPDATE_ACT:
+               try:
+                       grp = Group.Get(PREF_ENV_GROUPNAME.val)
+               except: 
+                       Draw.PupMenu('Error%t|Group "' + PREF_ENV_GROUPNAME.val + '" does not exist.')
+                       return
+       else:
+               grp = None
        
        Window.WaitCursor(1)
        t = sys.time()
-       env_from_group(ob_act, grp, PREF_OVERWRITE)
+       env_from_group(ob_act, grp, PREF_UPDATE_ACT)
        print 'assigned envelopes in:', sys.time() - t
        Window.WaitCursor(0)
 
index 4c125ca485525ee24e54b04c83eed094ab66b4bf..604bf6ca5fec4fd1820d289d653da902b469bd88 100755 (executable)
@@ -25,9 +25,9 @@ import Blender
 
 def main():
        scn= Blender.Scene.GetCurrent()
-       ob= scn.getActiveObject()
+       ob= scn.objects.active
        
-       if not ob or ob.getType() != 'Mesh':
+       if not ob or ob.type != 'Mesh':
                Blender.Draw.PupMenu('Error, no active mesh object, aborting.')
                return
        # MODE 0 == VCOL
index e0e7ee92b5bb5751a1b376932907df0ba94aad08..204868a79fc12c0df2cba723bb80a67b3af3c422 100644 (file)
@@ -66,6 +66,7 @@ def actWeightNormalize(me, PREF_PEAKWEIGHT, PREF_KEEP_PROPORTION):
        
        if abs(max_weight-PREF_PEAKWEIGHT) < SMALL_NUM:
                Draw.PupMenu('Vert Weights are alredy normalized.')
+               return
        
        max_weight= max_weight/PREF_PEAKWEIGHT
        
@@ -90,13 +91,13 @@ def actWeightNormalize(me, PREF_PEAKWEIGHT, PREF_KEEP_PROPORTION):
                
        # Copy weights back to the mesh.
        BPyMesh.dict2MeshWeight(me, groupNames, vWeightDict)
-
+       
 
 def main():
        scn= Scene.GetCurrent()
-       ob= scn.getActiveObject()
+       ob= scn.objects.active
        
-       if not ob or ob.getType() != 'Mesh':
+       if not ob or ob.type != 'Mesh':
                Draw.PupMenu('Error, no active mesh object, aborting.')
                return
        
@@ -113,10 +114,7 @@ def main():
        if not Draw.PupBlock('Clean Selected Meshes...', pup_block):
                return
        
-       PREF_PEAKWEIGHT= PREF_PEAKWEIGHT.val
-       PREF_KEEP_PROPORTION= PREF_KEEP_PROPORTION.val
-       
-       actWeightNormalize(me, PREF_PEAKWEIGHT, PREF_KEEP_PROPORTION)
+       actWeightNormalize(me, PREF_PEAKWEIGHT.val, PREF_KEEP_PROPORTION.val)
        
 if __name__=='__main__':
        main()
\ No newline at end of file
index 2b7c6c06832a183889748b963eea777f72f22eed..dfb3ddf0eff97552181cc2e953af300c98169562 100644 (file)
@@ -46,7 +46,7 @@ typedef void (*SeqDoit)(void*, float, float, int, int,
 
 typedef struct VarStruct {
        int type;
-       char name[16];
+       char name[32];
        float def, min, max;
        char tip[80];
 } VarStruct;