📄 quaternion.java
字号:
/**
*
* <code>toAxes</code> takes in an array of three vectors. Each vector
* corresponds to an axis of the coordinate system defined by the quaternion
* rotation.
*
* @param axis
* the array of vectors to be filled.
*/
public void toAxes(Vector3f axis[]) {
Matrix3f tempMat = toRotationMatrix();
axis[0] = tempMat.getColumn(0, axis[0]);
axis[1] = tempMat.getColumn(1, axis[1]);
axis[2] = tempMat.getColumn(2, axis[2]);
}
/**
* <code>mult</code> multiplies this quaternion by a parameter vector. The
* result is returned as a new vector.
*
* @param v
* the vector to multiply this quaternion by.
* @return the new vector.
*/
public Vector3f mult(Vector3f v) {
return mult(v, null);
}
/**
* <code>mult</code> multiplies this quaternion by a parameter vector. The
* result is stored in the supplied vector
*
* @param v
* the vector to multiply this quaternion by.
* @return v
*/
public Vector3f multLocal(Vector3f v) {
float tempX, tempY;
tempX = w * w * v.x + 2 * y * w * v.z - 2 * z * w * v.y + x * x * v.x
+ 2 * y * x * v.y + 2 * z * x * v.z - z * z * v.x - y * y * v.x;
tempY = 2 * x * y * v.x + y * y * v.y + 2 * z * y * v.z + 2 * w * z
* v.x - z * z * v.y + w * w * v.y - 2 * x * w * v.z - x * x
* v.y;
v.z = 2 * x * z * v.x + 2 * y * z * v.y + z * z * v.z - 2 * w * y * v.x
- y * y * v.z + 2 * w * x * v.y - x * x * v.z + w * w * v.z;
v.x = tempX;
v.y = tempY;
return v;
}
/**
* Multiplies this Quaternion by the supplied quaternion. The result is
* stored in this Quaternion, which is also returned for chaining. Similar
* to this *= q.
*
* @param q
* The Quaternion to multiply this one by.
* @return This Quaternion, after multiplication.
*/
public Quaternion multLocal(Quaternion q) {
float x1 = x * q.w + y * q.z - z * q.y + w * q.x;
float y1 = -x * q.z + y * q.w + z * q.x + w * q.y;
float z1 = x * q.y - y * q.x + z * q.w + w * q.z;
w = -x * q.x - y * q.y - z * q.z + w * q.w;
x = x1;
y = y1;
z = z1;
return this;
}
/**
* Multiplies this Quaternion by the supplied quaternion. The result is
* stored in this Quaternion, which is also returned for chaining. Similar
* to this *= q.
*
* @param qx -
* quat x value
* @param qy -
* quat y value
* @param qz -
* quat z value
* @param qw -
* quat w value
*
* @return This Quaternion, after multiplication.
*/
public Quaternion multLocal(float qx, float qy, float qz, float qw) {
float x1 = x * qw + y * qz - z * qy + w * qx;
float y1 = -x * qz + y * qw + z * qx + w * qy;
float z1 = x * qy - y * qx + z * qw + w * qz;
w = -x * qx - y * qy - z * qz + w * qw;
x = x1;
y = y1;
z = z1;
return this;
}
/**
* <code>mult</code> multiplies this quaternion by a parameter vector. The
* result is returned as a new vector.
*
* @param v
* the vector to multiply this quaternion by.
* @param store
* the vector to store the result in. It IS safe for v and store
* to be the same object.
* @return the result vector.
*/
public Vector3f mult(Vector3f v, Vector3f store) {
if (store == null)
store = new Vector3f();
if (v.x == 0 && v.y == 0 && v.z == 0) {
store.set(0, 0, 0);
} else {
float vx = v.x, vy = v.y, vz = v.z;
store.x = w * w * vx + 2 * y * w * vz - 2 * z * w * vy + x * x
* vx + 2 * y * x * vy + 2 * z * x * vz - z * z * vx - y
* y * vx;
store.y = 2 * x * y * vx + y * y * vy + 2 * z * y * vz + 2 * w
* z * vx - z * z * vy + w * w * vy - 2 * x * w * vz - x
* x * vy;
store.z = 2 * x * z * vx + 2 * y * z * vy + z * z * vz - 2 * w
* y * vx - y * y * vz + 2 * w * x * vy - x * x * vz + w
* w * vz;
}
return store;
}
/**
* <code>mult</code> multiplies this quaternion by a parameter scalar. The
* result is returned as a new quaternion.
*
* @param scalar
* the quaternion to multiply this quaternion by.
* @return the new quaternion.
*/
public Quaternion mult(float scalar) {
return new Quaternion(scalar * x, scalar * y, scalar * z, scalar * w);
}
/**
* <code>mult</code> multiplies this quaternion by a parameter scalar. The
* result is stored locally.
*
* @param scalar
* the quaternion to multiply this quaternion by.
* @return this.
*/
public Quaternion multLocal(float scalar) {
w *= scalar;
x *= scalar;
y *= scalar;
z *= scalar;
return this;
}
/**
* <code>dot</code> calculates and returns the dot product of this
* quaternion with that of the parameter quaternion.
*
* @param q
* the quaternion to calculate the dot product of.
* @return the dot product of this and the parameter quaternion.
*/
public float dot(Quaternion q) {
return w * q.w + x * q.x + y * q.y + z * q.z;
}
/**
* <code>norm</code> returns the norm of this quaternion. This is the dot
* product of this quaternion with itself.
*
* @return the norm of the quaternion.
*/
public float norm() {
return w * w + x * x + y * y + z * z;
}
/**
* <code>normalize</code> normalizes the current <code>Quaternion</code>
*/
public void normalize() {
float n = FastMath.invSqrt(norm());
x *= n;
y *= n;
z *= n;
w *= n;
}
/**
* <code>inverse</code> returns the inverse of this quaternion as a new
* quaternion. If this quaternion does not have an inverse (if its normal is
* 0 or less), then null is returned.
*
* @return the inverse of this quaternion or null if the inverse does not
* exist.
*/
public Quaternion inverse() {
float norm = norm();
if (norm > 0.0) {
float invNorm = 1.0f / norm;
return new Quaternion(-x * invNorm, -y * invNorm, -z * invNorm, w
* invNorm);
}
// return an invalid result to flag the error
return null;
}
/**
* <code>inverse</code> calculates the inverse of this quaternion and
* returns this quaternion after it is calculated. If this quaternion does
* not have an inverse (if it's norma is 0 or less), nothing happens
*
* @return the inverse of this quaternion
*/
public Quaternion inverseLocal() {
float norm = norm();
if (norm > 0.0) {
float invNorm = 1.0f / norm;
x *= -invNorm;
y *= -invNorm;
z *= -invNorm;
w *= invNorm;
}
return this;
}
/**
* <code>negate</code> inverts the values of the quaternion.
*
*/
public void negate() {
x *= -1;
y *= -1;
z *= -1;
w *= -1;
}
/**
*
* <code>toString</code> creates the string representation of this
* <code>Quaternion</code>. The values of the quaternion are displace (x,
* y, z, w), in the following manner: <br>
* com.jme.math.Quaternion: [x=1" y=2 z=3 w=1]
*
* @return the string representation of this object.
* @see java.lang.Object#toString()
*/
public String toString() {
return "com.jme.math.Quaternion: [x=" + x + " y=" + y + " z=" + z
+ " w=" + w + "]";
}
/**
* <code>equals</code> determines if two quaternions are logically equal,
* that is, if the values of (x, y, z, w) are the same for both quaternions.
*
* @param o
* the object to compare for equality
* @return true if they are equal, false otherwise.
*/
public boolean equals(Object o) {
if (!(o instanceof Quaternion) ) {
return false;
}
if (this == o) {
return true;
}
Quaternion comp = (Quaternion) o;
if (Float.compare(x,comp.x) != 0) return false;
if (Float.compare(y,comp.y) != 0) return false;
if (Float.compare(z,comp.z) != 0) return false;
if (Float.compare(w,comp.w) != 0) return false;
return true;
}
/**
*
* <code>hashCode</code> returns the hash code value as an integer and is
* supported for the benefit of hashing based collection classes such as
* Hashtable, HashMap, HashSet etc.
*
* @return the hashcode for this instance of Quaternion.
* @see java.lang.Object#hashCode()
*/
public int hashCode() {
int hash = 37;
hash = 37 * hash + Float.floatToIntBits(x);
hash = 37 * hash + Float.floatToIntBits(y);
hash = 37 * hash + Float.floatToIntBits(z);
hash = 37 * hash + Float.floatToIntBits(w);
return hash;
}
/**
* <code>readExternal</code> builds a quaternion from an
* <code>ObjectInput</code> object. <br>
* NOTE: Used with serialization. Not to be called manually.
*
* @param in
* the ObjectInput value to read from.
* @throws IOException
* if the ObjectInput value has problems reading a float.
* @see java.io.Externalizable
*/
public void readExternal(ObjectInput in) throws IOException {
x = in.readFloat();
y = in.readFloat();
z = in.readFloat();
w = in.readFloat();
}
/**
* <code>writeExternal</code> writes this quaternion out to a
* <code>ObjectOutput</code> object. NOTE: Used with serialization. Not to
* be called manually.
*
* @param out
* the object to write to.
* @throws IOException
* if writing to the ObjectOutput fails.
* @see java.io.Externalizable
*/
public void writeExternal(ObjectOutput out) throws IOException {
out.writeFloat(x);
out.writeFloat(y);
out.writeFloat(z);
out.writeFloat(w);
}
private static final Vector3f tmpYaxis = new Vector3f();
private static final Vector3f tmpZaxis = new Vector3f();
private static final Vector3f tmpXaxis = new Vector3f();
/**
* <code>lookAt</code> is a convienence method for auto-setting the
* quaternion based on a direction and an up vector. It computes
* the rotation to transform the z-axis to point into 'direction'
* and the y-axis to 'up'.
*
* @param direction
* where to look at in terms of local coordinates
* @param up
* a vector indicating the local up direction.
* (typically {0, 1, 0} in jME.)
*/
public void lookAt(Vector3f direction, Vector3f up ) {
tmpZaxis.set( direction ).normalizeLocal();
tmpXaxis.set( up ).crossLocal( direction ).normalizeLocal();
tmpYaxis.set( direction ).crossLocal( tmpXaxis ).normalizeLocal();
fromAxes( tmpXaxis, tmpYaxis, tmpZaxis );
}
public void write(JMEExporter e) throws IOException {
OutputCapsule cap = e.getCapsule(this);
cap.write(x, "x", 0);
cap.write(y, "y", 0);
cap.write(z, "z", 0);
cap.write(w, "w", 1);
}
public void read(JMEImporter e) throws IOException {
InputCapsule cap = e.getCapsule(this);
x = cap.readFloat("x", 0);
y = cap.readFloat("y", 0);
z = cap.readFloat("z", 0);
w = cap.readFloat("w", 1);
}
public Class<? extends Quaternion> getClassTag() {
return this.getClass();
}
/**
* @return A new quaternion that describes a rotation that would point you
* in the exact opposite direction of this Quaternion.
*/
public Quaternion opposite() {
return opposite(null);
}
/**
* FIXME: This seems to have singularity type issues with angle == 0, possibly others such as PI.
* @param store
* A Quaternion to store our result in. If null, a new one is
* created.
* @return The store quaternion (or a new Quaterion, if store is null) that
* describes a rotation that would point you in the exact opposite
* direction of this Quaternion.
*/
public Quaternion opposite(Quaternion store) {
if (store == null)
store = new Quaternion();
Vector3f axis = new Vector3f();
float angle = toAngleAxis(axis);
store.fromAngleAxis(FastMath.PI + angle, axis);
return store;
}
/**
* @return This Quaternion, altered to describe a rotation that would point
* you in the exact opposite direction of where it is pointing
* currently.
*/
public Quaternion oppositeLocal() {
return opposite(this);
}
@Override
public Quaternion clone() {
try {
return (Quaternion) super.clone();
} catch (CloneNotSupportedException e) {
throw new AssertionError(); // can not happen
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -