1
$\begingroup$

I have a model that I want to move vertex groups or a vertex from one group to another. I almost have the code down, but I'm running into a problem.

This is the code I have so far (I'm only learning and there is probably an easier to code it, but this is code I can understand at my level of experience)

import bpy
vgname1 = 'Leg_L'
vgname2 = 'LegD3_L'
vgi1 = -1
vgi2 = -1
vvgi1 = -1
vvgi2 = -1
verts=[]
vWeight=[]

Get current mode and name for active object
mode = bpy.context.active_object.mode
obname = bpy.context.active_object.name
print(mode, obname)

Walk through Vertex Groups and determine if the New Group
already exists, if not, create the new Group Also Get the 
index numbers for the 2 Groups in question

for ob in bpy.data.objects:
    if ob.name == obname:
        for vgn in ob.vertex_groups:
            if vgn.name == vgname1:
                vgi1 = vgn.index

            if vgn.name == vgname2:
                vgi2 = vgn.index

            if vgi2 == -1:
                ob.vertex_groups.new(name=vgname2)
                for vgn2 in ob.vertex_groups:
                    if vgn2.name == vgname2:
                        vgi2 = vgn2.index
Test the results
        print( ob.name, vgname1,vgi1, vgname2, vgi2)

Put the object into Object Mode and get the 
vertexes that are currently assigned to the group to be removed
Put the vertex indexes to be moved into a list

        bpy.ops.object.mode_set(mode = 'OBJECT')
        for v in bpy.context.active_object.data.vertices:
            for vg in v.groups:
                if vg.group == vgi1:
                    print(vg.group, vg.weight)
                    verts.append(v.index)
Ignore            vWeight = vg.weight

Now add the vertexes to the other group 

                    vg2 = ob.vertex_groups
                    for vga in vg2:
                        if vga.index == vgi2:
                            print(vga.index,vga.name)
                            vga.add(verts, 0, 'ADD')

This is where I go astray. The new group is added and the vertexes are assigned, but what if the new vertex group already exists and I just want to add the missing vertexes? I don't want to create another instance of the new group. (which is what this code does if I run it twice)

I went to the Blender Python documentation and this bit on Vertex Groups doesn't tell me anything

add(index, weight, type)
Add vertices to the group

Parameters:
•index (int array of 1 items in [-inf, inf]) – Index List
•weight (float in [0, 1]) – Vertex weight
•type (enum in ['REPLACE', 'ADD', 'SUBTRACT']) – 
Vertex assign mode
◦REPLACE Replace, Replace.
◦ADD Add, Add.
◦SUBTRACT Subtract, Subtract.

I see types for add, replace and subtract, but no append...

I understand what add and subtract will do, but what the devil does Replace do?

I'm setting the weight to 0 in the vga.add(verts, 0, 'ADD') statement because using a variable seems to set it to 1 by default. I can add another routine later to reset the weights on the vertices in the new group before removing the old group.

I'm stuck right now on when the new vertex group already exists in the object and I want to add vertices to it without creating a .001 instance of the new group name.

Help???

Thanks

$\endgroup$
  • $\begingroup$ Please don't add the answer as part of the question and don't add "solved" as part of the title. Write a proper answer instead and mark your own answer as accepted. $\endgroup$ – cegaton Apr 22 at 4:46
  • $\begingroup$ Thanks cegaton, repaired the post as you suggested and removed Solved from the title. I did not see the Write Answer button when I edited the post and The Add more info selection looked like the proper way to add more to the discussion. $\endgroup$ – PteJack Apr 24 at 16:40
1
$\begingroup$

Solution:

This code is clunky and really inflated. I know that actual coders out there will tell me that there are much better and more efficient ways to write this, but as I said, I'm just learning.

After playing with this abit, I found that this new code does just what I need it to do...

import bpy
vgname1 = 'Leg_R'
vgname2 = 'LegD_R'
vgi1 = -1
vgi2 = -1
vvgi1 = -1
vvgi2 = -1
verts=[]
vWeight=[]
x = 0
y = 0
z = 0
mode = bpy.context.active_object.mode
obname = bpy.context.active_object.name

for ob in bpy.data.objects:

    if ob.name == obname:

        for vgn in ob.vertex_groups:

            if vgn.name == vgname1:
                vgi1 = vgn.index
                x=x+1

            if vgn.name == vgname2:
                vgi2 = vgn.index
                y=y+1

        for vgn in ob.vertex_groups:

            if vgi2 == -1:
                z=z+1
                ob.vertex_groups.new(name=vgname2)

                for vgn2 in ob.vertex_groups:

                    if vgn2.name == vgname2:
                        vgi2 = vgn2.index
                        print(vgi2)

        bpy.ops.object.mode_set(mode = 'OBJECT')

        for v in bpy.context.active_object.data.vertices:

            for vg in v.groups:

                if vg.group == vgi1:
                    verts.append(v.index)
                    vg2 = ob.vertex_groups

                    for vga in vg2:

                        if vga.index == vgi2:
                            vga.add(verts, 0, 'ADD')

                    for v1 in bpy.context.active_object.data.vertices:

                        for vg1 in v1.groups:

                            if vg1.group == vgi1:
                                    print(v1.index, vg1.group, vgi1)
                                    vWeight = vg1.weight

                                    for v2 in bpy.context.active_object.data.vertices:

                                        if v2.index == v1.index:

                                            for vg2 in v2.groups:

                                                if vg2.group == vgi2:
                                                    vg2.weight = vWeight

            bpy.ops.object.vertex_group_set_active(group=vgname1)
            bpy.ops.object.vertex_group_remove()

If you wish to leave comments on how this code "should" be written, please go to the posting I made on here https://blenderartists.org/t/solved-trying-to-move-weights-from-one-vgroup-to-another-in-the-same-mesh-object-using-python/1156842/2 and post there.

Thanks

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.