__author__ = 'thoth'
import bpy
from mathutils import *
import random
from math import *
def random_in_circle():
while True:
x = random.random()*2-1
y = random.random()*2-1
l2 = x * x + y * y
if (l2<=0):
continue
if (l2 <=1):
return x,y
def random_quaternion():
"""
http://mathworld.wolfram.com/HyperspherePointPicking.html
"""
x,y = random_in_circle()
z_,w_ = random_in_circle()
r5 =sqrt( ( 1-x*x - y*y) / (z_*z_+w_*w_))
z = z_ * r5
w = w_ * r5
return [x,y,z,w]
kludge=0
def make_test_cube(loc, scn):
global kludge
q = Quaternion( random_quaternion() )
#q = Quaternion( [cos(kludge), sin(kludge), 0, 0 ] )
kludge = kludge+0.05
#creating the cube with a bear picture on a single face is an exercise left to the reader
mesh = bpy.data.meshes['bear cube']
obj = bpy.data.objects.new("cube", mesh)
obj.location = loc
obj.rotation_mode = 'QUATERNION'
obj.rotation_quaternion = q
# the cube is now rotated.
scn.objects.link(obj)
# create a vertex group for the armature
vg = obj.vertex_groups.new('bone')
vg.add(range(len(obj.data.vertices)), 1.0, 'REPLACE')
#
#let's see what happens when we need to put the bone at != [0,0,0]
translate = Vector([0,0,1])
arm = bpy.data.armatures.new('armature')
ao = bpy.data.objects.new('armature', arm)
ao.location = Vector(loc) - translate
scn.objects.link(ao)
scn.objects.active = ao
bpy.ops.object.mode_set(mode='EDIT') # I hate this shortcoming of armatures
bone = arm.edit_bones.new('bone')
bone.head = [0,0,0]
bone.tail = [0,1,0] # Using the Y axis is pretty important, otherwise we can't use the inverse of Q to pose the cube to an unrotated state
bone.transform(q.to_matrix())
bone.translate(translate)
# the bone is now aligned with the cube at its random orientation
bpy.ops.object.mode_set(mode='OBJECT')
# let's rig the cube to be posed by the armature
mod = obj.modifiers.new("armature", 'ARMATURE')
mod.object = ao
#
# two different ways to pose the bone into an "unrotated" orientation
if True:
q_inverse = [-q[0], q[1], q[2], q[3]]
ao.pose.bones[0].rotation_quaternion = q_inverse
else:
#boring: set the world orientation of the bone to the identity.
# This sort of ignores the rest orientation of the bone, but is useful in some situations.
ao.pose.bones[0].matrix = Matrix()
# the above works because our bone is aligned with the cube's Y axis.
# If the bone is aligned with some other axis, the cube will be aligned with that other axis.
#
def purge(scn):
doomed = []
for obj in scn.objects:
if obj.name[:4] == "cube" or obj.name[:8]=="armature":
doomed.append(obj)
for obj in doomed:
scn.objects.unlink(obj)
def mission1(scn):
for u in range(5):
for v in range(5):
make_test_cube([u*3, v*3, 0], scn)
#
#
scn = bpy.context.scene
purge(scn)
mission1(scn)
|
Blender python API quick-start
Syntax highlighting by Pygments.