- 1
- 2
- 3
- 4
- 5
- . . .
- последняя (29) »
программа создаёт арматуру.
#--------------------------------------------------- # File armature.py #--------------------------------------------------- import bpy, math from mathutils import Vector, Matrix
def createRig(name, origin, boneTable): # Создание арматуры и объекта bpy.ops.object.add( type='ARMATURE', enter_editmode=True, location=origin) ob = bpy.context.object ob.show_x_ray = True ob.name = name amt = ob.data amt.name = name+'Amt' amt.show_axes = True
# Создание костей bpy.ops.object.mode_set(mode='EDIT') for (bname, pname, vector) in boneTable: bone = amt.edit_bones.new(bname) if pname: parent = amt.edit_bones[pname] bone.parent = parent bone.head = parent.tail bone.use_connect = False (trans, rot, scale) = parent.matrix.decompose() else: bone.head = (0,0,0) rot = Matrix.Translation((0,0,0)) # Матрица идентичности bone.tail = Vector(vector) * rot + bone.head bpy.ops.object.mode_set(mode='OBJECT') return ob
def poseRig(ob, poseTable): bpy.context.scene.objects.active = ob bpy.ops.object.mode_set(mode='POSE') deg2rad = 2*math.pi/360
for (bname, axis, angle) in poseTable: pbone = ob.pose.bones[bname] # Установка режима вращения в Euler XYZ (Эйлерово), # легче для понимания, чем кватернионы по-умолчанию pbone.rotation_mode = 'XYZ' # Косяк в документации: Euler.rotate(angle,axis): # оси в ['x','y','z'] а не ['X','Y','Z'] pbone.rotation_euler.rotate_axis(axis, angle*deg2rad) bpy.ops.object.mode_set(mode='OBJECT') return
def run(origo): origin = Vector(origo) # Таблица костей в форме (кость, родитель, вектор) # Вектор дан в локальных координатах boneTable1 = [ ('Base', None, (1,0,0)), ('Mid', 'Base', (1,0,0)), ('Tip', 'Mid', (0,0,1)) ] bent = createRig('Bent', origin, boneTable1)
# Вторая оснастка является прямой линией, то есть кости проходят вдоль локальной оси Y boneTable2 = [ ('Base', None, (1,0,0)), ('Mid', 'Base', (0,0.5,0)), ('Mid2', 'Mid', (0,0.5,0)), ('Tip', 'Mid2', (0,1,0)) ] straight = createRig('Straight', origin+Vector((0,2,0)), boneTable2)
# Поза второй остнастки poseTable2 = [ ('Base', 'X', 90), ('Mid2', 'Z', 45), ('Tip', 'Y', -45) ] poseRig(straight, poseTable2)
# Поза первой остнастки poseTable1 = [ ('Tip', 'Y', 45), ('Mid', 'Y', 45), ('Base', 'Y', 45) ] poseRig(bent, poseTable1) return
if __name__ == "__main__": run((0,5,0))
#---------------------------------------------------------- # File rigged_mesh.py #---------------------------------------------------------- import bpy, mathutils
def createArmature(origin): # Создание арматуры и объекта amt = bpy.data.armatures.new('MyRigData') rig = bpy.data.objects.new('MyRig', amt) rig.location = origin rig.show_x_ray = True amt.show_names = True # Привязка объекта к сцене scn = bpy.context.scene scn.objects.link(rig) scn.objects.active = rig scn.update()
# Создание костей #next two lines by PKHG SVN 36504 W32 bpy.ops.object.editmode_toggle() # bpy.ops.object.mode_set(mode='EDIT') #original does not work??!! bpy.ops.object.mode_set(mode='EDIT') base = amt.edit_bones.new('Base') base.head = (0,0,0) base.tail = (0,0,1)
mid = amt.edit_bones.new('Mid') mid.head = (0,0,1) mid.tail = (0,0,2) mid.parent = base mid.use_connect = True
tip = amt.edit_bones.new('Tip') tip.head = (0,0,2) tip.tail = (0,0,3)
# Ограничения костей. Арматура должна быть в режиме позы. bpy.ops.object.mode_set(mode='POSE')
# Ограничение IK Mid -> Tip pMid = rig.pose.bones['Mid'] cns1 = pMid.constraints.new('IK') cns1.name = 'Ik' cns1.target = rig cns1.subtarget = 'Tip' cns1.chain_count = 1
# Ограничение StretchTo Mid -> Tip с влиянием 0.5 cns2 = pMid.constraints.new('STRETCH_TO') cns2.name = 'Stretchy' cns2.target = rig cns2.subtarget = 'Tip' cns2.influence = 0.5 cns2.keep_axis = 'PLANE_X' cns2.volume = 'VOLUME_XZX'
# Ограничение Copy rotation Base -> Tip pBase = rig.pose.bones['Base'] cns3 = pBase.constraints.new('COPY_ROTATION') cns3.name = 'Copy_Rotation' cns3.target = rig cns3.subtarget = 'Tip' cns3.owner_space = 'WORLD' cns3.target_space = 'WORLD'
bpy.ops.object.mode_set(mode='OBJECT') return rig
def createMesh(origin): # Создание меша и объекта me = bpy.data.meshes.new('Mesh') ob = bpy.data.objects.new('MeshObject', me) ob.location = origin # Привязка объекта к сцене scn = bpy.context.scene scn.objects.link(ob) scn.objects.active = ob scn.update()
# Список координат вершин. verts = [ (0.5, 0.5,0), (0.5,-0.5,0), (-0.5,-0.5,0), (-0.5,0.5,0), (0.5,0.5,1), (0.5,-0.5,1), (-0.5,-0.5,1), (-0.5,0.5,1), (-0.5,0.5,2), (-0.5,-0.5,2), (0.5,-0.5,2), (0.5,0.5,2), (0.5,0.5,3), (0.5,-0.5,3), (-0.5,-0.5,3), (-0.5, 0.5,3) ] # Список граней. faces = [ (0, 1, 2, 3), (0, 4, 5, 1), (1, 5, 6, 2), (2, 6, 7, 3), (4, 0, 3, 7), (4, 7, 8, 11), (7, 6, 9, 8), (6, 5, 10, 9), (5, 4, 11, 10), (10, 11, 12, 13), (9, 10, 13, 14), (8, 9, 14, 15), (11, 8, 15, 12), (12, 15, 14, 13) ]
# Создание меша из передаваемых списков вершин, рёбер, граней. # Или рёбра или грани должны быть [], иначе Вам нужны проблемы me.from_pydata(verts, [], faces)
# Обновление меша с новыми данными me.update(calc_edges=True) return ob
def skinMesh(ob, rig): # Списки вершин в группах, в форме (вершина, вес) vgroups = {} vgroups['Base'] = [ (0, 1.0), (1, 1.0), (2, 1.0), (3, 1.0), (4, 0.5), (5, 0.5), (6, 0.5), (7, 0.5)] vgroups['Mid'] = [ (4, 0.5), (5, 0.5), (6, 0.5), (7, 0.5), (8, 1.0), (9, 1.0), (10, 1.0), (11, 1.0)] vgroups['Tip'] = [(12, 1.0), (13, 1.0), (14, 1.0), (15, 1.0)]
# Создание групп вершин и добавление вершин и весов # Первый аргумент в назначении — список, чтобы можно # было назначать несколько вершин сразу for name in vgroups.keys(): grp = ob.vertex_groups.new(name) for (v, w) in vgroups[name]: grp.add([v], w, 'REPLACE')
# Добавление меш-объекту модификатора арматуры, с использованием # групп вершин, а не envelopes mod = ob.modifiers.new('MyRigModif', 'ARMATURE') mod.object = rig mod.use_bone_envelopes = False mod.use_vertex_groups = True
return
def run(origin): rig = createArmature(origin) ob = createMesh(origin) skinMesh(ob, rig)
# Перемещение и вращение кости Tip в режиме позы bpy.context.scene.objects.active = rig bpy.ops.object.mode_set(mode='POSE') ptip = rig.pose.bones['Tip'] ptip.location = (0.2,-0.5,0) rotMatrix = mathutils.Matrix.Rotation(0.6, 3, 'X') ptip.rotation_quaternion = rotMatrix.to_quaternion()
return
if
#--------------------------------------------------- # File armature.py #--------------------------------------------------- import bpy, math from mathutils import Vector, Matrix
def createRig(name, origin, boneTable): # Создание арматуры и объекта bpy.ops.object.add( type='ARMATURE', enter_editmode=True, location=origin) ob = bpy.context.object ob.show_x_ray = True ob.name = name amt = ob.data amt.name = name+'Amt' amt.show_axes = True
# Создание костей bpy.ops.object.mode_set(mode='EDIT') for (bname, pname, vector) in boneTable: bone = amt.edit_bones.new(bname) if pname: parent = amt.edit_bones[pname] bone.parent = parent bone.head = parent.tail bone.use_connect = False (trans, rot, scale) = parent.matrix.decompose() else: bone.head = (0,0,0) rot = Matrix.Translation((0,0,0)) # Матрица идентичности bone.tail = Vector(vector) * rot + bone.head bpy.ops.object.mode_set(mode='OBJECT') return ob
def poseRig(ob, poseTable): bpy.context.scene.objects.active = ob bpy.ops.object.mode_set(mode='POSE') deg2rad = 2*math.pi/360
for (bname, axis, angle) in poseTable: pbone = ob.pose.bones[bname] # Установка режима вращения в Euler XYZ (Эйлерово), # легче для понимания, чем кватернионы по-умолчанию pbone.rotation_mode = 'XYZ' # Косяк в документации: Euler.rotate(angle,axis): # оси в ['x','y','z'] а не ['X','Y','Z'] pbone.rotation_euler.rotate_axis(axis, angle*deg2rad) bpy.ops.object.mode_set(mode='OBJECT') return
def run(origo): origin = Vector(origo) # Таблица костей в форме (кость, родитель, вектор) # Вектор дан в локальных координатах boneTable1 = [ ('Base', None, (1,0,0)), ('Mid', 'Base', (1,0,0)), ('Tip', 'Mid', (0,0,1)) ] bent = createRig('Bent', origin, boneTable1)
# Вторая оснастка является прямой линией, то есть кости проходят вдоль локальной оси Y boneTable2 = [ ('Base', None, (1,0,0)), ('Mid', 'Base', (0,0.5,0)), ('Mid2', 'Mid', (0,0.5,0)), ('Tip', 'Mid2', (0,1,0)) ] straight = createRig('Straight', origin+Vector((0,2,0)), boneTable2)
# Поза второй остнастки poseTable2 = [ ('Base', 'X', 90), ('Mid2', 'Z', 45), ('Tip', 'Y', -45) ] poseRig(straight, poseTable2)
# Поза первой остнастки poseTable1 = [ ('Tip', 'Y', 45), ('Mid', 'Y', 45), ('Base', 'Y', 45) ] poseRig(bent, poseTable1) return
if __name__ == "__main__": run((0,5,0))
Меш с оснасткой
Эта программа добавляет арматуру и меш. Арматура имеет три кости (Base (базовая), Mid (средняя), Tip (конечная)) и ограничения: 1. Ограничение IK Mid -> Tip. 2. Ограничение Stretch To Mid -> Tip. 3. Ограничение Copy Rotation Base -> Tip. Меш деформируется арматурой. Следовательно, создаются модификатор арматуры и соответствующие группы вершин.#---------------------------------------------------------- # File rigged_mesh.py #---------------------------------------------------------- import bpy, mathutils
def createArmature(origin): # Создание арматуры и объекта amt = bpy.data.armatures.new('MyRigData') rig = bpy.data.objects.new('MyRig', amt) rig.location = origin rig.show_x_ray = True amt.show_names = True # Привязка объекта к сцене scn = bpy.context.scene scn.objects.link(rig) scn.objects.active = rig scn.update()
# Создание костей #next two lines by PKHG SVN 36504 W32 bpy.ops.object.editmode_toggle() # bpy.ops.object.mode_set(mode='EDIT') #original does not work??!! bpy.ops.object.mode_set(mode='EDIT') base = amt.edit_bones.new('Base') base.head = (0,0,0) base.tail = (0,0,1)
mid = amt.edit_bones.new('Mid') mid.head = (0,0,1) mid.tail = (0,0,2) mid.parent = base mid.use_connect = True
tip = amt.edit_bones.new('Tip') tip.head = (0,0,2) tip.tail = (0,0,3)
# Ограничения костей. Арматура должна быть в режиме позы. bpy.ops.object.mode_set(mode='POSE')
# Ограничение IK Mid -> Tip pMid = rig.pose.bones['Mid'] cns1 = pMid.constraints.new('IK') cns1.name = 'Ik' cns1.target = rig cns1.subtarget = 'Tip' cns1.chain_count = 1
# Ограничение StretchTo Mid -> Tip с влиянием 0.5 cns2 = pMid.constraints.new('STRETCH_TO') cns2.name = 'Stretchy' cns2.target = rig cns2.subtarget = 'Tip' cns2.influence = 0.5 cns2.keep_axis = 'PLANE_X' cns2.volume = 'VOLUME_XZX'
# Ограничение Copy rotation Base -> Tip pBase = rig.pose.bones['Base'] cns3 = pBase.constraints.new('COPY_ROTATION') cns3.name = 'Copy_Rotation' cns3.target = rig cns3.subtarget = 'Tip' cns3.owner_space = 'WORLD' cns3.target_space = 'WORLD'
bpy.ops.object.mode_set(mode='OBJECT') return rig
def createMesh(origin): # Создание меша и объекта me = bpy.data.meshes.new('Mesh') ob = bpy.data.objects.new('MeshObject', me) ob.location = origin # Привязка объекта к сцене scn = bpy.context.scene scn.objects.link(ob) scn.objects.active = ob scn.update()
# Список координат вершин. verts = [ (0.5, 0.5,0), (0.5,-0.5,0), (-0.5,-0.5,0), (-0.5,0.5,0), (0.5,0.5,1), (0.5,-0.5,1), (-0.5,-0.5,1), (-0.5,0.5,1), (-0.5,0.5,2), (-0.5,-0.5,2), (0.5,-0.5,2), (0.5,0.5,2), (0.5,0.5,3), (0.5,-0.5,3), (-0.5,-0.5,3), (-0.5, 0.5,3) ] # Список граней. faces = [ (0, 1, 2, 3), (0, 4, 5, 1), (1, 5, 6, 2), (2, 6, 7, 3), (4, 0, 3, 7), (4, 7, 8, 11), (7, 6, 9, 8), (6, 5, 10, 9), (5, 4, 11, 10), (10, 11, 12, 13), (9, 10, 13, 14), (8, 9, 14, 15), (11, 8, 15, 12), (12, 15, 14, 13) ]
# Создание меша из передаваемых списков вершин, рёбер, граней. # Или рёбра или грани должны быть [], иначе Вам нужны проблемы me.from_pydata(verts, [], faces)
# Обновление меша с новыми данными me.update(calc_edges=True) return ob
def skinMesh(ob, rig): # Списки вершин в группах, в форме (вершина, вес) vgroups = {} vgroups['Base'] = [ (0, 1.0), (1, 1.0), (2, 1.0), (3, 1.0), (4, 0.5), (5, 0.5), (6, 0.5), (7, 0.5)] vgroups['Mid'] = [ (4, 0.5), (5, 0.5), (6, 0.5), (7, 0.5), (8, 1.0), (9, 1.0), (10, 1.0), (11, 1.0)] vgroups['Tip'] = [(12, 1.0), (13, 1.0), (14, 1.0), (15, 1.0)]
# Создание групп вершин и добавление вершин и весов # Первый аргумент в назначении — список, чтобы можно # было назначать несколько вершин сразу for name in vgroups.keys(): grp = ob.vertex_groups.new(name) for (v, w) in vgroups[name]: grp.add([v], w, 'REPLACE')
# Добавление меш-объекту модификатора арматуры, с использованием # групп вершин, а не envelopes mod = ob.modifiers.new('MyRigModif', 'ARMATURE') mod.object = rig mod.use_bone_envelopes = False mod.use_vertex_groups = True
return
def run(origin): rig = createArmature(origin) ob = createMesh(origin) skinMesh(ob, rig)
# Перемещение и вращение кости Tip в режиме позы bpy.context.scene.objects.active = rig bpy.ops.object.mode_set(mode='POSE') ptip = rig.pose.bones['Tip'] ptip.location = (0.2,-0.5,0) rotMatrix = mathutils.Matrix.Rotation(0.6, 3, 'X') ptip.rotation_quaternion = rotMatrix.to_quaternion()
return
if
- 1
- 2
- 3
- 4
- 5
- . . .
- последняя (29) »