/// <summary> /// copy constructor /// </summary> public hquat(hquat q) { this.x = q.x; this.y = q.y; this.z = q.z; this.w = q.w; }
/// <summary> /// Create a quaternion from two normalized axis (http://lolengine.net/blog/2013/09/18/beautiful-maths-quaternion-from-vectors) /// </summary> public hquat(hvec3 u, hvec3 v) { var localW = hvec3.Cross(u, v); var dot = hvec3.Dot(u, v); var q = new hquat(localW.x, localW.y, localW.z, Half.One + dot).Normalized; this.x = q.x; this.y = q.y; this.z = q.z; this.w = q.w; }
/// <summary> /// Calculates a proper spherical interpolation between two quaternions (only works for normalized quaternions). /// </summary> public static hquat Mix(hquat x, hquat y, Half a) { var cosTheta = (double)Dot(x, y); if (cosTheta > 1 - float.Epsilon) { return(Lerp(x, y, a)); } else { var angle = Math.Acos((double)cosTheta); return((hquat)((Math.Sin((1 - (double)a) * angle) * (dquat)x + Math.Sin((double)a * angle) * (dquat)y) / Math.Sin(angle))); } }
/// <summary> /// Tries to convert the string representation of the quaternion into a quaternion representation (using a designated separator), returns false if string was invalid. /// </summary> public static bool TryParse(string s, string sep, out hquat result) { result = Zero; if (string.IsNullOrEmpty(s)) { return(false); } var kvp = s.Split(new[] { sep }, StringSplitOptions.None); if (kvp.Length != 4) { return(false); } Half x = Half.Zero, y = Half.Zero, z = Half.Zero, w = Half.Zero; var ok = ((Half.TryParse(kvp[0].Trim(), out x) && Half.TryParse(kvp[1].Trim(), out y)) && (Half.TryParse(kvp[2].Trim(), out z) && Half.TryParse(kvp[3].Trim(), out w))); result = ok ? new hquat(x, y, z, w) : Zero; return(ok); }
/// <summary> /// Calculates a proper spherical interpolation between two quaternions (only works for normalized quaternions). /// </summary> public static hquat SLerp(hquat x, hquat y, Half a) { var z = y; var cosTheta = (double)Dot(x, y); if (cosTheta < 0) { z = -y; cosTheta = -cosTheta; } if (cosTheta > 1 - float.Epsilon) { return(Lerp(x, z, a)); } else { var angle = Math.Acos((double)cosTheta); return((hquat)((Math.Sin((1 - (double)a) * angle) * (dquat)x + Math.Sin((double)a * angle) * (dquat)z) / Math.Sin(angle))); } }
/// <summary> /// Returns a bvec4 from component-wise application of IsPositiveInfinity (Half.IsPositiveInfinity(v)). /// </summary> public static bvec4 IsPositiveInfinity(hquat v) => hquat.IsPositiveInfinity(v);
/// <summary> /// Returns a bvec4 from component-wise application of IsFinite (!Half.IsNaN(v) && !Half.IsInfinity(v)). /// </summary> public static bvec4 IsFinite(hquat v) => hquat.IsFinite(v);
/// <summary> /// Returns a hash code for this instance. /// </summary> public static int GetHashCode(hquat q) => q.GetHashCode();
/// <summary> /// Returns true iff this equals rhs component-wise. /// </summary> public static bool Equals(hquat q, hquat rhs) => q.Equals(rhs);
/// <summary> /// Returns a string representation of this quaternion using a provided seperator and a format and format provider for each component. /// </summary> public static string ToString(hquat q, string sep, string format, IFormatProvider provider) => q.ToString(sep, format, provider);
/// <summary> /// Returns a string representation of this quaternion using a provided seperator. /// </summary> public static string ToString(hquat q, string sep) => q.ToString(sep);
/// <summary> /// Returns an array with all values /// </summary> public static Half[] Values(hquat q) => q.Values;
/// <summary> /// Creates a hmat4 that realizes the rotation of this quaternion /// </summary> public static hmat4 ToMat4(hquat q) => q.ToMat4;
/// <summary> /// Creates a hmat3 that realizes the rotation of this quaternion /// </summary> public static hmat3 ToMat3(hquat q) => q.ToMat3;
/// <summary> /// Rotates this quaternion from an axis and an angle (in radians). /// </summary> public static hquat Rotated(hquat q, Half angle, hvec3 v) => q.Rotated(angle, v);
/// <summary> /// Returns an enumerator that iterates through all components. /// </summary> public static IEnumerator <Half> GetEnumerator(hquat q) => q.GetEnumerator();
/// <summary> /// Returns a string representation of this quaternion using ', ' as a seperator. /// </summary> public static string ToString(hquat q) => q.ToString();
/// <summary> /// Returns the conjugated quaternion /// </summary> public static hquat Conjugate(hquat q) => q.Conjugate;
/// <summary> /// Returns a string representation of this quaternion using a provided seperator and a format for each component. /// </summary> public static string ToString(hquat q, string sep, string format) => q.ToString(sep, format);
/// <summary> /// Returns the inverse quaternion /// </summary> public static hquat Inverse(hquat q) => q.Inverse;
/// <summary> /// Returns the number of components (4). /// </summary> public static int Count(hquat q) => q.Count;
/// <summary> /// Returns the cross product between two quaternions. /// </summary> public static hquat Cross(hquat q1, hquat q2) => hquat.Cross(q1, q2);
/// <summary> /// Returns true iff this equals rhs type- and component-wise. /// </summary> public static bool Equals(hquat q, object obj) => q.Equals(obj);
/// <summary> /// Calculates a proper spherical interpolation between two quaternions (only works for normalized quaternions). /// </summary> public static hquat Mix(hquat x, hquat y, Half a) => hquat.Mix(x, y, a);
/// <summary> /// Returns a bvec4 from component-wise application of IsInfinity (Half.IsInfinity(v)). /// </summary> public static bvec4 IsInfinity(hquat v) => hquat.IsInfinity(v);
/// <summary> /// Calculates a proper spherical interpolation between two quaternions (only works for normalized quaternions). /// </summary> public static hquat SLerp(hquat x, hquat y, Half a) => hquat.SLerp(x, y, a);
/// <summary> /// Returns a bvec4 from component-wise application of IsNaN (Half.IsNaN(v)). /// </summary> public static bvec4 IsNaN(hquat v) => hquat.IsNaN(v);
/// <summary> /// Applies squad interpolation of these quaternions /// </summary> public static hquat Squad(hquat q1, hquat q2, hquat s1, hquat s2, Half h) => hquat.Squad(q1, q2, s1, s2, h);
/// <summary> /// Creates a rotation matrix from a hquat. /// </summary> public hmat3(hquat q) : this(q.ToMat3) { }
/// <summary> /// Returns a hquat from component-wise application of Lerp (min * (1-a) + max * a). /// </summary> public static hquat Lerp(hquat min, hquat max, hquat a) => hquat.Lerp(min, max, a);