Example #1
0
	vec3 reorient_vector(const vec3 v, const vec3 up) {
		const vec3 new_y = normalized(up);
		const vec3 new_x = normalized(find_orthogonal_vector(new_y));
		const vec3 new_z = normalized(cross(new_x, new_y));

		const mat3 base2 = { new_x, new_y, new_z };
		const mat3 base = transpose(base2);

		return base * v;
	}
Example #2
0
LocalCS_Data::quaternion::quaternion(const float rot[9], const quaternion *pq)
{
    if (rot[0] == 1.0 && rot[4] == 1.0 && rot[8] == 1.0)
    {
        _a = 1.0;
        _b = _c = _d = 0.0;
    }
    else
    {
        float cos_theta = (rot[0] + rot[4] + rot[8] - 1.0) * 0.5;
        float stuff = (cos_theta + 1.0) * 0.5;
        float cos_theta_sur_2 = sqrt(stuff);
        float sin_theta_sur_2 = sqrt(1 - stuff);

        float x;
        float y;
        float z;

        find_invariant_vector(rot, x, y, z);

        float u;
        float v;
        float w;

        find_orthogonal_vector(x, y, z, u, v, w);

        float r;
        float s;
        float t;

        find_vector_for_BOD(x, y, z, u, v, w, r, s, t);

        float ru = rot[0] * u + rot[1] * v + rot[2] * w;
        float rv = rot[3] * u + rot[4] * v + rot[5] * w;
        float rw = rot[6] * u + rot[7] * v + rot[8] * w;

        float angle_sign_determinator = r * ru + s * rv + t * rw;
        if (angle_sign_determinator > 0.0)
        {
            _a = cos_theta_sur_2;
            _b = x * sin_theta_sur_2;
            _c = y * sin_theta_sur_2;
            _d = z * sin_theta_sur_2;
        }
        else if (angle_sign_determinator < 0.0)
        {
            _a = cos_theta_sur_2;
            _b = -x * sin_theta_sur_2;
            _c = -y * sin_theta_sur_2;
            _d = -z * sin_theta_sur_2;
        }
        else if (u * ru + v * rv + w * rw < 0.0)
        {
            _a = 0.0;
            _b = x;
            _c = y;
            _d = z;
        }
        else
        {
            _a = 1.0;
            _b = _c = _d = 0.0;
        }
    }

    if (pq && abs2(*pq, *this) > abs2(*this, *pq))
    {
        _a *= -1.0;
        _b *= -1.0;
        _c *= -1.0;
        _d *= -1.0;
    }
}