private double meterDistanceBetweenPoints(float lat_a, float lng_a, float lat_b, float lng_b) { float pk = (float) (180.f/Math.PI); float a1 = lat_a / pk; float a2 = lng_a / pk; float b1 = lat_b / pk; float b2 = lng_b / pk; float t1 = FloatMath.cos(a1)*FloatMath.cos(a2)*FloatMath.cos(b1)*FloatMath.cos(b2); float t2 = FloatMath.cos(a1)*FloatMath.sin(a2)*FloatMath.cos(b1)*FloatMath.sin(b2); float t3 = FloatMath.sin(a1)*FloatMath.sin(b1); double tt = Math.acos(t1 + t2 + t3); return 6366000*tt; }
/** Get the angle in radians of the rotation this quaternion represents. Does not normalize the quaternion. Use * {@link #getAxisAngleRad(Vector3)} to get both the axis and the angle of this rotation. Use * {@link #getAngleAroundRad(Vector3)} to get the angle around a specific axis. * @return the angle in radians of the rotation */ public float getAngleRad () { return (float)(2.0 * Math.acos((this.w > 1) ? (this.w / len()) : this.w)); }
/** Get the angle in radians of the rotation this quaternion represents. Does not normalize the quaternion. Use * {@link #getAxisAngleRad(Vector3)} to get both the axis and the angle of this rotation. Use * {@link #getAngleAroundRad(Vector3)} to get the angle around a specific axis. * @return the angle in radians of the rotation */ public float getAngleRad () { return (float)(2.0 * Math.acos((this.w > 1) ? (this.w / len()) : this.w)); }
@Override protected ExprEval eval(double param) { return ExprEval.of(Math.acos(param)); } }
/** Get the axis-angle representation of the rotation in radians. The supplied vector will receive the axis (x, y and z values) * of the rotation and the value returned is the angle in radians around that axis. Note that this method will alter the * supplied vector, the existing value of the vector is ignored. </p> This will normalize this quaternion if needed. The * received axis is a unit vector. However, if this is an identity quaternion (no rotation), then the length of the axis may be * zero. * * @param axis vector which will receive the axis * @return the angle in radians * @see <a href="http://en.wikipedia.org/wiki/Axis%E2%80%93angle_representation">wikipedia</a> * @see <a href="http://www.euclideanspace.com/maths/geometry/rotations/conversions/quaternionToAngle">calculation</a> */ public float getAxisAngleRad (Vector3 axis) { if (this.w > 1) this.nor(); // if w>1 acos and sqrt will produce errors, this cant happen if quaternion is normalised float angle = (float)(2.0 * Math.acos(this.w)); double s = Math.sqrt(1 - this.w * this.w); // assuming quaternion normalised then w is less than 1, so term always positive. if (s < MathUtils.FLOAT_ROUNDING_ERROR) { // test to avoid divide by zero, s is always positive due to sqrt // if s close to zero then direction of axis not important axis.x = this.x; // if it is important that axis is normalised then replace with x=1; y=z=0; axis.y = this.y; axis.z = this.z; } else { axis.x = (float)(this.x / s); // normalise axis axis.y = (float)(this.y / s); axis.z = (float)(this.z / s); } return angle; }
/** Get the axis-angle representation of the rotation in radians. The supplied vector will receive the axis (x, y and z values) * of the rotation and the value returned is the angle in radians around that axis. Note that this method will alter the * supplied vector, the existing value of the vector is ignored. </p> This will normalize this quaternion if needed. The * received axis is a unit vector. However, if this is an identity quaternion (no rotation), then the length of the axis may be * zero. * * @param axis vector which will receive the axis * @return the angle in radians * @see <a href="http://en.wikipedia.org/wiki/Axis%E2%80%93angle_representation">wikipedia</a> * @see <a href="http://www.euclideanspace.com/maths/geometry/rotations/conversions/quaternionToAngle">calculation</a> */ public float getAxisAngleRad (Vector3 axis) { if (this.w > 1) this.nor(); // if w>1 acos and sqrt will produce errors, this cant happen if quaternion is normalised float angle = (float)(2.0 * Math.acos(this.w)); double s = Math.sqrt(1 - this.w * this.w); // assuming quaternion normalised then w is less than 1, so term always positive. if (s < MathUtils.FLOAT_ROUNDING_ERROR) { // test to avoid divide by zero, s is always positive due to sqrt // if s close to zero then direction of axis not important axis.x = this.x; // if it is important that axis is normalised then replace with x=1; y=z=0; axis.y = this.y; axis.z = this.z; } else { axis.x = (float)(this.x / s); // normalise axis axis.y = (float)(this.y / s); axis.z = (float)(this.z / s); } return angle; }
float theta = (float)Math.acos(w / norm);
/** Get the angle in radians of the rotation around the specified axis. The axis must be normalized. * @param axisX the x component of the normalized axis for which to get the angle * @param axisY the y component of the normalized axis for which to get the angle * @param axisZ the z component of the normalized axis for which to get the angle * @return the angle in radians of the rotation around the specified axis */ public float getAngleAroundRad (final float axisX, final float axisY, final float axisZ) { final float d = Vector3.dot(this.x, this.y, this.z, axisX, axisY, axisZ); final float l2 = Quaternion.len2(axisX * d, axisY * d, axisZ * d, this.w); return MathUtils.isZero(l2) ? 0f : (float)(2.0 * Math.acos(MathUtils.clamp( (float)((d < 0 ? -this.w : this.w) / Math.sqrt(l2)), -1f, 1f))); }
@Override public Vector3 setToRandomDirection () { float u = MathUtils.random(); float v = MathUtils.random(); float theta = MathUtils.PI2 * u; // azimuthal angle float phi = (float)Math.acos(2f * v - 1f); // polar angle return this.setFromSpherical(theta, phi); }
/** Set this quaternion to the rotation between two vectors. * @param v1 The base vector, which should be normalized. * @param v2 The target vector, which should be normalized. * @return This quaternion for chaining */ public Quaternion setFromCross (final Vector3 v1, final Vector3 v2) { final float dot = MathUtils.clamp(v1.dot(v2), -1f, 1f); final float angle = (float)Math.acos(dot); return setFromAxisRad(v1.y * v2.z - v1.z * v2.y, v1.z * v2.x - v1.x * v2.z, v1.x * v2.y - v1.y * v2.x, angle); }
/** Get the angle in radians of the rotation around the specified axis. The axis must be normalized. * @param axisX the x component of the normalized axis for which to get the angle * @param axisY the y component of the normalized axis for which to get the angle * @param axisZ the z component of the normalized axis for which to get the angle * @return the angle in radians of the rotation around the specified axis */ public float getAngleAroundRad (final float axisX, final float axisY, final float axisZ) { final float d = Vector3.dot(this.x, this.y, this.z, axisX, axisY, axisZ); final float l2 = Quaternion.len2(axisX * d, axisY * d, axisZ * d, this.w); return MathUtils.isZero(l2) ? 0f : (float)(2.0 * Math.acos(MathUtils.clamp( (float)((d < 0 ? -this.w : this.w) / Math.sqrt(l2)), -1f, 1f))); }
@Override public Vector3 setToRandomDirection () { float u = MathUtils.random(); float v = MathUtils.random(); float theta = MathUtils.PI2 * u; // azimuthal angle float phi = (float)Math.acos(2f * v - 1f); // polar angle return this.setFromSpherical(theta, phi); }
/** Set this quaternion to the rotation between two vectors. * @param v1 The base vector, which should be normalized. * @param v2 The target vector, which should be normalized. * @return This quaternion for chaining */ public Quaternion setFromCross (final Vector3 v1, final Vector3 v2) { final float dot = MathUtils.clamp(v1.dot(v2), -1f, 1f); final float angle = (float)Math.acos(dot); return setFromAxisRad(v1.y * v2.z - v1.z * v2.y, v1.z * v2.x - v1.x * v2.z, v1.x * v2.y - v1.y * v2.x, angle); }
/** Set this quaternion to the rotation between two vectors. * @param x1 The base vectors x value, which should be normalized. * @param y1 The base vectors y value, which should be normalized. * @param z1 The base vectors z value, which should be normalized. * @param x2 The target vector x value, which should be normalized. * @param y2 The target vector y value, which should be normalized. * @param z2 The target vector z value, which should be normalized. * @return This quaternion for chaining */ public Quaternion setFromCross (final float x1, final float y1, final float z1, final float x2, final float y2, final float z2) { final float dot = MathUtils.clamp(Vector3.dot(x1, y1, z1, x2, y2, z2), -1f, 1f); final float angle = (float)Math.acos(dot); return setFromAxisRad(y1 * z2 - z1 * y2, z1 * x2 - x1 * z2, x1 * y2 - y1 * x2, angle); }
/** Set this quaternion to the rotation between two vectors. * @param x1 The base vectors x value, which should be normalized. * @param y1 The base vectors y value, which should be normalized. * @param z1 The base vectors z value, which should be normalized. * @param x2 The target vector x value, which should be normalized. * @param y2 The target vector y value, which should be normalized. * @param z2 The target vector z value, which should be normalized. * @return This quaternion for chaining */ public Quaternion setFromCross (final float x1, final float y1, final float z1, final float x2, final float y2, final float z2) { final float dot = MathUtils.clamp(Vector3.dot(x1, y1, z1, x2, y2, z2), -1f, 1f); final float angle = (float)Math.acos(dot); return setFromAxisRad(y1 * z2 - z1 * y2, z1 * x2 - x1 * z2, x1 * y2 - y1 * x2, angle); }
/** Spherically interpolates between this vector and the target vector by alpha which is in the range [0,1]. The result is * stored in this vector. * * @param target The target vector * @param alpha The interpolation coefficient * @return This vector for chaining. */ public Vector3 slerp (final Vector3 target, float alpha) { final float dot = dot(target); // If the inputs are too close for comfort, simply linearly interpolate. if (dot > 0.9995 || dot < -0.9995) return lerp(target, alpha); // theta0 = angle between input vectors final float theta0 = (float)Math.acos(dot); // theta = angle between this vector and result final float theta = theta0 * alpha; final float st = (float)Math.sin(theta); final float tx = target.x - x * dot; final float ty = target.y - y * dot; final float tz = target.z - z * dot; final float l2 = tx * tx + ty * ty + tz * tz; final float dl = st * ((l2 < 0.0001f) ? 1f : 1f / (float)Math.sqrt(l2)); return scl((float)Math.cos(theta)).add(tx * dl, ty * dl, tz * dl).nor(); }
/** Spherically interpolates between this vector and the target vector by alpha which is in the range [0,1]. The result is * stored in this vector. * * @param target The target vector * @param alpha The interpolation coefficient * @return This vector for chaining. */ public Vector3 slerp (final Vector3 target, float alpha) { final float dot = dot(target); // If the inputs are too close for comfort, simply linearly interpolate. if (dot > 0.9995 || dot < -0.9995) return lerp(target, alpha); // theta0 = angle between input vectors final float theta0 = (float)Math.acos(dot); // theta = angle between this vector and result final float theta = theta0 * alpha; final float st = (float)Math.sin(theta); final float tx = target.x - x * dot; final float ty = target.y - y * dot; final float tz = target.z - z * dot; final float l2 = tx * tx + ty * ty + tz * tz; final float dl = st * ((l2 < 0.0001f) ? 1f : 1f / (float)Math.sqrt(l2)); return scl((float)Math.cos(theta)).add(tx * dl, ty * dl, tz * dl).nor(); }
public static DoubleValue acos( AnyValue in ) { if ( in instanceof NumberValue ) { return doubleValue( Math.acos( ((NumberValue) in).doubleValue() ) ); } else { throw needsNumbers( "acos()" ); } }
@Description("arc cosine") @ScalarFunction @SqlType(StandardTypes.DOUBLE) public static double acos(@SqlType(StandardTypes.DOUBLE) double num) { return Math.acos(num); }