Blender and Python molecules visualization

2012-04-11
#blender #python

Blender is free software for 3D graphics. In old versions many operations were bound to hotkeys, so it was believed that Blender is very hard to master. Now it has a more user-friendly interface with buttons in addition to hotkeys.

One of the most useful features of Blender is scripting. Below I provide a Python script for drawing molecules with cylinders and spheres.

Command to draw a sphere:

1bpy.ops.mesh.primitive_uv_sphere_add()

To draw a cylinder, you need to specify the cylinder center and rotation. Rotation is described via a rotation axis and rotation angle.

A trivial cylinder after creation is aligned with the Z axis: z = (0,0,1). If you need to connect two points r1 and r2 with a cylinder, its center coordinate is r3 = (r1+r2)/2. The cylinder must be aligned with z_desired = (r1-r2).normalized(), so the rotation axis is rot_axis = z.cross(z_desired) and the angle is angle = acos(z.dot(z_desired)).

Wrapping up, code:

 1from math import degrees, acos
 2from mathutils import Vector
 3
 4spheres = (Vector((2,3,3)),Vector((1,1,2)),Vector((2,3,4)),Vector((4,5,3)))
 5edges = ((0,1),(1,2),(2,3))
 6
 7for i in range(0, len(spheres)):
 8  r1 = spheres[i]
 9  bpy.ops.mesh.primitive_uv_sphere_add(location=(r1.x, r1.y, r1.z))
10
11for i in range(0,len(edges)):
12  r1 = spheres[edges[i][0]]
13  r2 = spheres[edges[i][1]]
14  r3 = (r1+r2)/2
15  z = Vector((0,0,1))
16  z_desired = (r1-r2).normalized()
17  rot_axis = z.cross(z_desired)
18  angle = acos(z.dot(z_desired))
19  bpy.ops.mesh.primitive_cylinder_add(radius=0.3, depth=(r2-r1).length,location=(r3.x,r3.y,r3.z))
20  bpy.ops.transform.rotate(value=(angle,), axis=rot_axis)

After copy-pasting to the Blender console you will see a similar image:

blender_python