I am trying to make and auto-aligner for the particle system. Each particle has a previous location and current location. So I want to use those two values to determine a rotation for an object placed at the current current location. This way the object would align to the path the particle was traveling.
@CoDEManX: At this link you mention “you can turn any two points into a direction”.
Do you or anyone know how to take two points and return a rotation_euler(x,y,z) angles or radians?
import bpy
ob_emitter = bpy.data.objects.get("Cube")
psys = ob_emitter.particle_systems[0]
if psys != None:
print("
particle_list")
c = 0
for p in psys.particles:
print("Particle #%i" %c)
print(p.location)
print(p.prev_location)
print(p.location-p.prev_location)
# Need a line here to calculate the ROT (X,Y,Z) from locations.
print("")
c = c + 1
I am digging around and wonder if atan2 might be part of the solution.
I think I have a solution for you. First you need two vectors instead of just the one you generate from those two particle locations, I’ll call them vector A and B.
Vector A is the (normalized) ‘forward’ axis of the object you want to place at the particle.
Vector B is “p.location-p.prev_location”
Then do something like this:
# make sure this stuff is imported
from mathutils import Vector, Quaternion
# normalize B (A and B should both be normalized)
B.normalize()
# cross and dot products of A and B
C = A.cross(B)
D = A.dot(B)
# create and normalize a quaternion
Q = Quaternion((D+1, C[0], C[1], C[2]))
Q.normalize()
# now you can apply the quaternion to your Object
bpy.data.objects['myObject'].rotation_quaternion = Q
# or convert it to euler rotation
Rot = Q.to_euler()
import bpy
from mathutils import Vector, Quaternion
#empty Plain Axes
A = bpy.data.objects['A']
B = bpy.data.objects['B']
#empty Single Arrow - align its z-axis with the direction from b to a
C = bpy.data.objects['C']
a = A.location
b = B.location
direction = (a - b).normalized()
axis_align = Vector((0.0, 0.0, 1.0))
angle = axis_align.angle(direction)
axis = axis_align.cross(direction)
q = Quaternion(axis, angle)
C.location = b
C.rotation_euler = q.to_euler('XYZ')
#if rotation_mode == "QUATERNION":
#C.rotation_quaternion = q
You can turn two points into a direction vector and assume it to be e.g. the Z-vector of a 3x3 matrix, but you actually need a third point to find out the different in rotation…