This section of the archives stores flipcode's complete Developer Toolbox collection, featuring a variety of mini-articles and source code contributions from our readers.

 

  mMath Lib
  Submitted by



mMath is a 3d math library intend for games or real-time 3d Viz applications. It is still in development and is still being tested. Currently it is based around a mFrame and mOCS class similar to classes from Chris Hargrove's COTC articles. Optimizations have currently been kept at a portable level. This may change in the future, but for now, please point out anything that you feel is non-optimal. The vector classes are pretty complete. If I have missed a commonly used function, please tell me. The matrix class is meant to be very simple, because the OCS is meant to be used in most places that a matrix is normally used. The volume classes are still being worked on and will be added shortly. These currently include an axis-aligned bounding box, sphere, plane, and frustum. Ellipsoids, cylinders, and possibly an oriented bounding box will be added later. mMath will continue to be in the public domain. All source will be provided each update. If anyone wishes to help, please email me fixes or additions.

* Description quoted from mMath documentation file.

Currently browsing [mmath.zip] (283,561 bytes) - [examples/mMath/VecOcs/VecOCS.cpp] - (3,966 bytes)

//****************************************************************************
//**
//**    VecOCS.cpp
//**    Source - Simple example of using the mVec3 and mOCS classes.
//**    Copyright (C)2000 Douglas H. Cox
//**
//**    DHC - 8/3/2000
//**
//****************************************************************************
//============================================================================
//    Headers
//============================================================================
#include <mMath.h>
#include <mVec3.h>
#include <mOCS.h>
#include <mMatrix.h>

#include <stdio.h> //============================================================================ // Private Defines / Enums / Typedefs //============================================================================ //============================================================================ // Private Structs / Functions / Utility Classes //============================================================================ //============================================================================ // Private Data //============================================================================ //============================================================================ // Function Implementations //============================================================================ //============================================================= // vec3Test void vec3Test() { // mVec3 functions mVec3 a, b, r;

a.set(1.5f, 0.0f, 0.0f); a.normalize();

b.set(0.0f, 2.75f, 0.0f); b.normalize();

r.cross(a, b); // should be pointing in +z direction }

//============================================================= // ocsTest void ocsTest() { mOCS parentOCS(mVec3(10.0f, 1.0f, -10.0f), mFrame(), mVec3(), mOCS::ORIGIN); mOCS childOCS(mVec3(20.0f, 5.0f, -30.0f), mFrame(), mVec3(), mOCS::ORIGIN); // ^ construct 2 ocs's with only the origin component not an identity value. mOCS r;

unsigned parentType = parentOCS.getType(); // ^ should = mOCS::ORIGIN r.xformFrom(parentOCS, childOCS);

parentOCS.setOrigin(0.0f, 0.0f, 0.0f); parentOCS.setHP(90.0f, 0.0f); // ^ Heading=Rotation about Z axis, // ^ Pitch=Rotation about the X axis, // Roll=Rotation about the Y axis. parentType = parentOCS.getType(); // ^ should = mOCS::ORIGIN | mOCS::FRAME, because the above setHP // modifies the frame component.

r.xformFrom(childOCS, parentOCS); // r can now be thought of as the world->child OCS mVec3 a(1.0f, 2.0f, 3.0f); mVec3 b; mVec3 rv1, rv2;

rv1.xformFrom(a, childOCS); // rv1 is now positioned in the parentOCS rv1.xformFrom(rv1, parentOCS); // rv1 is now positioned in the world OCS rv2.xformFrom(a, r);

// assert(rv1 == rv2); // NOTE: ^ may assert because of precision errors. // Viewing the variables in the watch window shows they should be the same. assert(rv1.approxEqual(rv2)); // ^ mVec*.approxEqual and mApproxEqual should be used when comparing // transformed points. b.xformTo(rv1, r); // go from a point in the world ocs to child ocs. // assert(b == a); // NOTE: ^ may assert because of precision errors. // Viewing the variables in the watch window shows they should be the same. assert(b.approxEqual(a)); // ^ mVec*.approxEqual and mApproxEqual should be used when comparing // transformed points. }

//============================================================= // main void main() { mInitialize(); // * Must be called 1st. // Simple mVec3 testing. vec3Test();

// Simple mOCS testing. ocsTest();

mUninitialize(); }

//**************************************************************************** //** End - VecOCS.cpp //****************************************************************************

Currently browsing [mmath.zip] (283,561 bytes) - [include/mFrame.h] - (4,866 bytes)

#ifndef __mFrame_H__
#define __mFrame_H__

/*! \file mFrame.h \brief 3D Axial Frame \author Douglas H. Cox */

//============================================================================ // REQUIRED HEADERS //============================================================================ #include "mMath.h" #include "mVec3.h"

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================ class mQuat;

//============================================================================ // FUNCTION PROTOTYPES //============================================================================ //============================================================================ // CLASS PROTOTYPES //============================================================================ //! 3D Axial Frame /*! mFrame represents a 3D Axial Frame. An axial frame consists of three normalized, orthogonal vectors. These describe a rotation value for a give coordinate system. Transformations \e from an axial frame perform a rotation from the frame's local-space into its parents. Transformations \e to an axial frame perform a rotation from the frame's parent- space into its local-space. \sa http://www.loonygames.com/content/1.29/cotc/ */ class MMATH_DLL mFrame { public: mVec3 a[3]; //!< normalized x, y, z axes. right handed. //! Default constructor /*! No initialization is done here. */ mFrame() { }

//! Copy constructor mFrame(const mFrame& src) { a[0].set(src.a[0]); a[1].set(src.a[1]); a[2].set(src.a[2]); }

//! Constructor from 3 normalized, orthogonal axes. mFrame(const mVec3& x, const mVec3& y, const mVec3& z) { a[0].set(x); a[1].set(y); a[2].set(z); }

//! Set this to cartesian axes. void makeIdentity() { a[0].set(1.0f, 0.0f, 0.0f); a[1].set(0.0f, 1.0f, 0.0f); a[2].set(0.0f, 0.0f, 1.0f); }

//! Assignment void set(const mFrame& src) { a[0].set(src.a[0]); a[1].set(src.a[1]); a[2].set(src.a[2]); }

//! Assignment from 3 normalized, orthogonal axes void set(const mVec3& x, const mVec3& y, const mVec3& z) { a[0].set(x); a[1].set(y); a[2].set(z); }

//! Assignment mFrame& operator = (const mFrame& src) { a[0].set(src.a[0]); a[1].set(src.a[1]); a[2].set(src.a[2]); return *this; }

//! Accessor void get(mVec3& x, mVec3& y, mVec3& z) const { x.set(a[0]); y.set(a[1]); z.set(a[2]); }

//! Accessor mVec3& operator [] (int i) { return a[i]; }

//! Accessor const mVec3& operator [] (int i) const { return a[i]; }

//! Returns true if this == f bool operator == (const mFrame& f) const { return( a[0] == f.a[0] && a[1] == f.a[1] && a[2] == f.a[2] ); }

//! Returns true if this != f bool operator != (const mFrame& f) const { return !(operator==(f)); } //! Returns true is this is within some tolerance value of \em f. bool approxEqual(const mFrame& f, float tol = mZeroTol) const;

//! Computes the inverse of f. void inverse(); //! Computes the inverse of f. void inverse(const mFrame& f);

//! Transforms f into 'to's axial frame. void xformTo(const mFrame& f, const mFrame& to);

//! Transforms f from 'from's axial frame. void xformFrom(const mFrame& f, const mFrame& from); //! Sets this to the rotation defined by the quaternion q. void setQuat(const mQuat& q);

//! Gets a normalized quaternion. void getQuat(mQuat& q) const;

//! Sets this to a rotation about a unit vector n. a is in degrees. void setAxisAngle(const mVec3& n, float a);

//! Gets an angle about a unit vector n. void getAxisAngle(mVec3& n, float& a) const;

//! Sets this to a rotation defined by the heading and pitch in degrees. /*! This assumes a roll of 0.0f and is faster than the full setHPR method. \todo: Test this. */ void setHP(float heading, float pitch);

//! Sets this to a rotation defined by heading, pitch, and roll in degrees. /*! \todo: Test this. */ void setHPR(float heading, float pitch, float roll);

//! Sets this to a rotation defined by heading, pitch, and roll in degrees. void setHPR(const mVec3& hpr) { setHPR(hpr.v[0], hpr.v[1], hpr.v[2]); }

};

//**************************************************************************** //** END HEADER mFrame.h //**************************************************************************** #endif // __mFrame_H__

Currently browsing [mmath.zip] (283,561 bytes) - [include/mMath.h] - (8,331 bytes)

#ifndef __mMath_H__
#define __mMath_H__

/*! \file mMath.h \brief Main mMath include file. \author Douglas Cox */

//============================================================= // DOCUMENTATION //============================================================= /*! \mainpage mMath Library \section Introduction Introduction mMath is a 3d math library intend for games or real-time 3d Viz applications. It is still in development and is still being tested. Currently it is based around a mFrame and mOCS class similar to classes from Chris Hargrove's COTC articles.

Optimizations have currently been kept at a portable level. This may change in the future, but for now, please point out anything that you feel is non-optimal.

The vector classes are pretty complete. If I have missed a commonly used function, please tell me. The matrix class is meant to be very simple, because the OCS is meant to be used in most places that a matrix is normally used.

The volume classes are still being worked on and will be added shortly. These currently include an axis-aligned bounding box, sphere, plane, and frustum. Ellipsoids, cylinders, and possibly an oriented bounding box will be added later.

mMath will continue to be in the public domain. All source will be provided each update. If anyone wishes to help, please email me fixes or additions.

<a href="http://www.doxygen.org>Doxygen</a> was used for all documentation.

\section BeforeYouBegin Before You Begin Before you begin using any classes from the library, you should note the following: mMath uses a right-handed, +Z = up, +Y = forward (into the screen), +X = right coordinate system. This is different than OpenGL (right-handed, +Y = up, -Z = forward, +X = right) and Direct3D (left-handed, +Y = up, +Z = forward, +X = right). Future examples will show how to convert to the desired API format. Also, heading is defined as a rotation about the +Z axis, pitch is a rotation about the +X axis, and roll is a rotation about the +Y axis.

Finally, make sure you call mInitialize before calling any functions in this library.

\section Compiling Compiling mMath.dsp compiles the library into a Win32 DLL. If you wish to compile the code into a large DLL or executable, #define MMATH_STATIC in your project's settings (Project / Settings / C++ / Preprocessor definitions). This code should compile on non-Windows OSs. If not, please email any corrections.

\section Examples Examples Currently there is only a single, very simple example. It briefly demonstrates how to use the mOCS class. Other examples will be added shortly. Please browse through the per-class documentation as well as the source code for further help.

*/


//============================================================================ // REQUIRED HEADERS //============================================================================

#ifdef WIN32 #include <float.h> #endif // WIN32

#include <assert.h> #include <math.h>

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================

// Define MMATH_DLL for proper import/export behavior. #ifndef WIN32 #define MMATH_DLL #else #ifdef MMATH_STATIC // ^ Define MMATH_STATIC to compile .cpp files statically // with another project. #define MMATH_DLL #else #ifdef MMATH_EXPORTS // ^ Should be defined by the project building the DLL. #define MMATH_DLL __declspec(dllexport) #else #define MMATH_DLL __declspec(dllimport) #ifdef _DEBUG #pragma comment(lib, "mMath-dbg") #else #pragma comment(lib, "mMath") #endif #endif #endif #endif

// Common constants

//! The smallest possible floating point value. #define mFloatMin (FLT_MIN)

//! The largest possible floating point value. #define mFloatMax (FLT_MAX)

//! PI #define mPI 3.1415926536f

//! mPI / 2 #define mHalfPI 1.5707963268f

//! A value < this is equal to zero. #define mZeroTol 0.000001f

// Square root table used for fast square root function. MMATH_DLL extern unsigned int mFastSqrtTable[0x10000];

// Macro used by fast sqrt function. (nVidia) #define mFPBits(fp) (*(unsigned *)&(fp))

//============================================================================ // FUNCTION PROTOTYPES //============================================================================

//! Initializes the math library. /*! This must be called before using any functions in this library. */ MMATH_DLL bool mInitialize();

//! Uninitializes the math library. MMATH_DLL void mUninitialize();

//! Returns the absolute value of x. inline float mAbs(float x) { return (x < 0.0f) ? -x : x; }

//! Returns the smaller value. template<class T> inline T mMin(T a, T b) { return (a < b ? a : b); }

//! Returns the larger value. template<class T> inline T mMax(T a, T b) { return (a > b ? a : b); }

//! Returns the remainder of a / b. inline float mMod(float a, float b) { int n = int(a / b); a -= n * b; return (a < 0.0f) ? (a + b) : a; }

//! Returns the floor of x. inline float mFloor(float x) { int ix = int(x); return float(ix - (x < 0.0f && x != float(ix))); }

//! Returns the ceiling of x. inline float mCeil(float x) { int ix = int(x); return float(ix + (x > 0.0f && x != float(ix))); }

//! Clamps x to a specific range [a, b]. inline float mClamp(float x, float a, float b) { return (x < a ? a : (x > b ? b : x)); }

//! Returns true if a is approximately equal to b +- tol. inline bool mApproxEqual(float a, float b, float tol = mZeroTol) { return (mAbs(a-b) <= tol); }

//! Rounds x to the closest integer. inline int mRound(float x) { return int(x + 0.5f); }

//! Returns x * x. inline float mSquare(float x) { return (x*x); }

//! Table-based square root of x. (nVidia) inline float mSqrt(float x) { if (mFPBits(x) == 0) return 0.0f;

mFPBits(x) = mFastSqrtTable[(mFPBits(x) >> 8) & 0xFFFF] | ((((mFPBits(x) - 0x3F800000) >> 1) + 0x3F800000) & 0x7F800000); return x; }

//! Slower but more accurate version of mSqrt. inline float mSlowSqrt(float x) { return float(sqrt(x)); }

//! Converts radians to degrees inline float mRadToDeg(float x) { return (x * 57.295779513f); }

//! Converts degrees to radians inline float mDegToRad(float x) { return (x * 0.017453292520f); }

//! Calculates the cosine of a in degrees. inline float mCos(float a) { return float(cos(mDegToRad(a))); }

//! Calculates the arc cosine of a in degrees. inline float mACos(float a) { return mRadToDeg(float(acos(mClamp(a, -1.0f, 1.0f)))); }

//! Calculates the sine of a in degrees. inline float mSin(float a) { return float(sin(mDegToRad(a))); }

//! Calculates the arc sine of a in degrees. inline float mASin(float a) { return mRadToDeg(float(asin(mClamp(a, -1.0f, 1.0f)))); }

//! Calculates the sine and cosine of a in degrees. inline void mSinCos(float a, float& sine, float& cosine) { a = mDegToRad(a); sine = float(sin(a)); cosine = float(cos(a));

// Don't Intel CPUs have a SINCOS op? }

//! Calculates the tangent of a in degrees. inline float mTan(float a) { return float(tan(mDegToRad(a))); }

//! Calculates the arc tangent of x in degrees. inline float mATan(float x) { return mRadToDeg(float(atan(x))); }

//! Calculates the arc tangent of y/x in degrees. inline float mATan2(float y, float x) { return mRadToDeg(float(atan2(y, x))); }

//============================================================================ // CLASS PROTOTYPES //============================================================================

//**************************************************************************** //** END HEADER mMath.h //**************************************************************************** #endif // __mMath_H__

Currently browsing [mmath.zip] (283,561 bytes) - [include/mMatrix.h] - (2,133 bytes)

#ifndef __mMatrix_H__
#define __mMatrix_H__

/*! \file mMatrix.h \brief 4x4 Column-order Matrix \author Douglas H. Cox */

//============================================================================ // REQUIRED HEADERS //============================================================================ #include "mMath.h"

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================ //============================================================================ // FUNCTION PROTOTYPES //============================================================================ //============================================================================ // CLASS PROTOTYPES //============================================================================ //! 4x4 Column-order Matrix /*! Matrices are meant to be used only when needed by the rendering API. OCSes should be used instead. \sa mOCS::getMatrix() */ class MMATH_DLL mMatrix { public: float m[16]; //!< Matrix data in column order. public: //! Default constructor /*! No initialization is done here. */ mMatrix() { }

//! Copy constructor mMatrix(const mMatrix& src) { set(src); }

//! Assignment void set(const mMatrix& src);

//! Assignment mMatrix& operator = (const mMatrix& src) { set(src); return *this; }

//! Accessor float& operator [] (int i) { return m[i]; }

//! Accessor float operator [] (int i) const { return m[i]; }

//! Creates an identity matrix. void makeIdentity();

//! Multiplies matrix a by matrix b. /*! \todo Optimize this. */ void mult(const mMatrix& a, const mMatrix& b);

};

//**************************************************************************** //** END HEADER mMatrix.h //**************************************************************************** #endif // __mMatrix_H__

Currently browsing [mmath.zip] (283,561 bytes) - [include/mOCS.h] - (7,059 bytes)

#ifndef __mOCS_H__
#define __mOCS_H__

/*! \file mOCS.h \brief 3D Orthogonal Coordinate System \author Douglas H. Cox */

//============================================================================ // REQUIRED HEADERS //============================================================================ #include "mMath.h" #include "mVec3.h" #include "mFrame.h"

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================ class mQuat; class mMatrix;

//============================================================================ // FUNCTION PROTOTYPES //============================================================================ //============================================================================ // CLASS PROTOTYPES //============================================================================ //! 3D Orthogonal Coordinate System /*! mOCS represents a 3D Orthogonal Coordinate System. \sa http://www.loonygames.com/content/1.29/cotc/ */ class MMATH_DLL mOCS { private: mVec3 o; //!< OCS origin. mFrame f; //!< OCS axial frame. mVec3 s; //!< OCS axis scale.

public: enum TYPE { IDENTITY = 0x00, ORIGIN = 0x01, FRAME = 0x02, SCALE = 0x04 }; private: unsigned type; //!< Specifies the valid components of the OCS. friend class mVec3; friend class mRay;

public: //! Default constructor /*! Initialized to origin at zero, cartesian axes, and unit scale. */ mOCS() { type = IDENTITY; makeIdentity(); }

//! Copy constructor mOCS(const mOCS& src);

//! Constructor specifying origin, axial frame, and scale. /*! Example: mOCS ocs(&origin, &rot, NULL);

would create an OCS with an \em origin and a \em frame component. Types not specified by \em type are set to an identity value. */
mOCS(const mVec3& origin, const mFrame& frame, const mVec3& scale, unsigned type = ORIGIN | FRAME | SCALE);

//! Origin at zero, cartesian axes, unit scale. void makeIdentity();

//! Creates an ocs with specified origin, unit scale, and cartesian axes. void makeOrigin(const mVec3& origin) { makeOrigin(origin[0], origin[1], origin[2]); }

//! Creates an ocs with specified origin, unit scale, and cartesian axes. void makeOrigin(float x, float y, float z);

//! Creates an ocs with specified frame, origin at zero, and unit scale. void makeFrame(const mFrame& frame);

//! Creates an ocs with specified scale, origin at zero, and cartesian axes. void makeScale(const mVec3& scale) { makeScale(scale[0], scale[1], scale[2]); }

//! Creates an ocs with specified scale, origin at zero, and cartesian axes. void makeScale(float x, float y, float z);

//! Assignment void set(const mOCS& src);

//! Assignment specifying origin, axial frame, and scale. /*! Types not specified by \em type are set to an identity value. */ void set(const mVec3& origin, const mFrame& frame, const mVec3& scale, unsigned type = ORIGIN | FRAME | SCALE); //! Assignment void setOrigin(const mVec3& origin) { o.set(origin); type |= ORIGIN; }

//! Assignment void setOrigin(float x, float y, float z) { o.set(x, y, z); type |= ORIGIN; }

//! Assignment void setFrame(const mFrame& frame) { f.set(frame); type |= FRAME; }

//! Sets the axial frame to the rotation defined by the quaternion q. /*! This call only affects the axial frame. */ void setQuat(const mQuat& q) { f.setQuat(q); type |= FRAME; }

//! Sets the axial frame to a rotation about a unit vector n. a is in degrees. /*! This call only affects the axial frame. */ void setAxisAngle(const mVec3& n, float a) { f.setAxisAngle(n, a); type |= FRAME; } //! Sets this to a rotation defined by the heading and pitch in degrees. /*! This assumes a roll of 0.0f and is faster than the full setHPR method. */ void setHP(float heading, float pitch) { f.setHP(heading, pitch); type |= FRAME; }

//! Sets this to a rotation defined by heading, pitch, and roll in degrees. void setHPR(float heading, float pitch, float roll) { f.setHPR(heading, pitch, roll); type |= FRAME; }

//! Sets this to a rotation defined by heading, pitch, and roll in degrees. void setHPR(const mVec3& hpr) { setHPR(hpr.v[0], hpr.v[1], hpr.v[2]); }

//! Assignment void setScale(const mVec3& scale) { s.set(scale); type |= SCALE; }

//! Assignment void setScale(float x, float y, float z) { s.set(x, y, z); type |= SCALE; }

//! Assignment mOCS& operator = (const mOCS& src) { set(src); return *this; }

//! Accessor void get(mVec3& origin, mFrame& frame, mVec3& scale) const; //! Accessor const mVec3* getOrigin() const { return &o; }

//! Accessor const mFrame* getFrame() const { return &f; }

//! Accessor const mVec3* getScale() const { return &s; }

//! Returns the type of valid components in the OCS. unsigned getType() const { return type; }

//! Returns true if the two OCSs are equal. bool operator == (const mOCS& ocs) const;

//! Returns true if the two OCSs are not equal. bool operator != (const mOCS& ocs) const { return !(operator==(ocs)); }

//! Returns true is this is within some tolerance value of \em ocs. bool approxEqual(const mOCS& ocs, float tol = mZeroTol) const;

//! Computes the inverse of f. void inverse(const mOCS& ocs);

//! Transforms ocs into 'to's coordinate system. /*! \param ocs OCS that will be transformed \param to OCS that ocs will be transformed to */ void xformTo(const mOCS& ocs, const mOCS& to);

//! Transforms ocs from 'from's coordinate system. /*! \param ocs OCS that will be transformed \param from OCS that ocs will be transformed from */ void xformFrom(const mOCS& ocs, const mOCS& from);

//! Builds a matrix that transforms object into this OCS. /*! This builds an OpenGL compatible matrix. That is, one that can be loaded into a modelview matrix. */ void getToMatrix(mMatrix& matrix) const; //! Builds a matrix that transforms object from this OCS. /*! This builds an OpenGL compatible matrix. That is, one that can be loaded into a modelview matrix. */ void getFromMatrix(mMatrix& matrix) const; };

//**************************************************************************** //** END HEADER mOCS.h //**************************************************************************** #endif // __mOCS_H__

Currently browsing [mmath.zip] (283,561 bytes) - [include/mQuat.h] - (3,951 bytes)

#ifndef __mQuat_H__
#define __mQuat_H__

/*! \file mQuat.h \brief Quaterion \author Douglas H. Cox */

//============================================================================ // REQUIRED HEADERS //============================================================================ #include "mMath.h" #include "mVec4.h" #include "mVec3.h" #include "mFrame.h"

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================

//============================================================================ // FUNCTION PROTOTYPES //============================================================================ //============================================================================ // CLASS PROTOTYPES //============================================================================ //! Quaternion /*! mQuat represents a quaternion. \sa http://mathworld.wolfram.com/Quaternion.html */ class MMATH_DLL mQuat : public mVec4 { public: //! Default constructor /*! No initialization is done here. */ mQuat() {}

//! Copy constructor mQuat(const mQuat& src) { v[0] = src.v[0]; v[1] = src.v[1]; v[2] = src.v[2]; v[3] = src.v[3]; }

//! Constructor from 4 float values mQuat(float x, float y, float z, float w) { v[0] = x; v[1] = y; v[2] = z; v[3] = w; }

//! Constructor from an array of 4 float values mQuat(float *src) { v[0] = src[0]; v[1] = src[1]; v[2] = src[2]; v[3] = src[3]; }

//! Sets this to its conjugate void conjugate() { v[0] = -v[0]; v[1] = -v[1]; v[2] = -v[2]; }

//! Set this to the conjugate of q void conjugate(const mQuat& q) { v[0] = -q.v[0]; v[1] = -q.v[1]; v[2] = -q.v[2]; v[3] = q.v[3]; }

//! Computes the inverse of this. this = 1 / this void inverse();

//! Computes the inverse of q. this = 1 / q void inverse(const mQuat& q);

//! Multiply: this *= q void mult(const mQuat& q) { mult(*this, q); }

//! Multiply: this = q1 * q2 void mult(const mQuat& q1, const mQuat& q2);

//! Spherical linear interpolation between q1 and q2. void slerp(const mQuat& q1, const mQuat& q2, float t);

//! Sets this to the rotation about a unit vector n. a is in degrees. void setAxisAngle(const mVec3& n, float a);

//! Gets an angle about a unit vector n defined by this quaternion. void getAxisAngle(mVec3& n, float& a) const;

//! Sets this to the rotation defined by the heading and pitch in degrees. /*! This assumes a roll of 0.0f and is faster than the full setHPR method. */ void setHP(float heading, float pitch);

//! Returns the heading and pitch defined by this quaternion. void getHP(float &heading, float &pitch) const;

//! Sets this to the rotation defined by heading, pitch, and roll in degrees. void setHPR(float heading, float pitch, float roll);

//! Sets this to the rotation defined by heading, pitch, and roll in degrees. void setHPR(const mVec3& hpr) { setHPR(hpr.v[0], hpr.v[1], hpr.v[2]); }

//! Returns the heading and pitch defined by this quaternion. /*! \todo Implement this. */ void getHPR(mVec3& hpr) const;

//! Set this to the rotation defined by frame. void setFrame(const mFrame& frame) { frame.getQuat(*this); }

//! Assigns a frame to the rotation defined by this quaternion. void getFrame(mFrame& frame) const { frame.setQuat(*this); }

};

//**************************************************************************** //** END HEADER mQuat.h //**************************************************************************** #endif // __mQuat_H__

Currently browsing [mmath.zip] (283,561 bytes) - [include/mRay.h] - (3,187 bytes)

#ifndef __mRay_H__
#define __mRay_H__

/*! \file mRay.h \brief Ray class. \author Douglas H. Cox */

//============================================================================ // REQUIRED HEADERS //============================================================================ #include "mVec3.h"

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================ class mOCS;

//============================================================================ // FUNCTION PROTOTYPES //============================================================================ //============================================================================ // CLASS PROTOTYPES //============================================================================ //! Ray class. class MMATH_DLL mRay { public: mVec3 pos; //!< position of the ray. mVec3 dir; //!< normalized direction the ray points. float len; //!< length of the ray. if = -1, ray is infinite. //! Default constructor /*! No initialization is done here. */ mRay() { }

//! Copy constructor mRay(const mRay& src) : pos(src.pos), dir(src.dir), len(src.len) { }

//! Constructor from position, direction, and length. mRay(const mVec3& position, const mVec3& direction, const float length) : pos(position), dir(direction), len(length) { }

//! Constructor from two points. mRay(const mVec3& startPoint, const mVec3& endPoint) { set(startPoint, endPoint); }

//! Assignment void set(const mRay& src) { pos.set(src.pos); dir.set(src.dir); len = src.len; } //! Assignment from position, direction, and length. void set(const mVec3& position, const mVec3& direction, const float length) { pos.set(position); dir.set(direction); len = length; }

//! Assignment from two points. void set(const mVec3& startPoint, const mVec3& endPoint);

//! Returns the starting point for this ray. void getStartPoint(mVec3& start) const { start.set(pos); }

//! Returns the ending point for this ray. /*! \todo Check the case when len == -1. */ void getEndPoint(mVec3& end) const;

//! Returns true if the two rays are the same. bool operator == (const mRay& ray) const;

//! Returns true if the two rays are not the same. bool operator != (const mRay& ray) const { return !(operator==(ray)); }

//! Transforms the ray into the OCS. void xformTo(const mRay& ray, const mOCS& ocs);

//! Transforms the ray from the OCS. void xformFrom(const mRay& ray, const mOCS& ocs);

};

//**************************************************************************** //** END HEADER mRay.h //**************************************************************************** #endif // __mRay_H__

Currently browsing [mmath.zip] (283,561 bytes) - [include/mVec2.h] - (7,641 bytes)

#ifndef __mVec2_H__
#define __mVec2_H__

/*! \file mVec2.h \brief 2D Vector \author Douglas H. Cox */

//============================================================================ // REQUIRED HEADERS //============================================================================ #include "mMath.h"

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================ //============================================================================ // FUNCTION PROTOTYPES //============================================================================ //============================================================================ // CLASS PROTOTYPES //============================================================================ //! 2D Vector / Point /*! mVec2 represents a vector consisting of an array of two float values. */ class MMATH_DLL mVec2 { public: float v[2]; //!< vector data //! Default constructor /*! No initialization is done here. */ mVec2() {}

//! Copy constructor mVec2(const mVec2& src) { v[0] = src.v[0]; v[1] = src.v[1]; }

//! Constructor from 2 float values mVec2(float x, float y) { v[0] = x; v[1] = y; }

//! Constructor from an array of 2 float values mVec2(float *src) { v[0] = src[0]; v[1] = src[1]; }

//! Assignment void set(const mVec2& src) { v[0] = src.v[0]; v[1] = src.v[1]; }

//! Assignment from 2 float values void set(float x, float y) { v[0] = x; v[1] = y; }

//! Assignment from an arry of 2 float values void set(float *src) { v[0] = src[0]; v[1] = src[1]; }

//! Assignment mVec2& operator = (const mVec2& src) { v[0] = src.v[0]; v[1] = src.v[1]; return *this; }

//! Accessor void get(float& x, float& y) const { x = v[0]; y = v[1]; }

//! Accessor float& operator [] (int i) { return v[i]; }

//! Accessor float operator [] (int i) const { return v[i]; }

//! Returns true if this == a bool operator == (const mVec2& a) const { return( v[0] == a.v[0] && v[1] == a.v[1] ); }

//! Returns true if this != a bool operator != (const mVec2& a) const { return !(operator==(a)); }

//! Returns true is this is equal to a within some tolerance value. bool approxEqual(const mVec2& a, float tol = mZeroTol) { return( mApproxEqual(v[0], a.v[0], tol) && mApproxEqual(v[1], a.v[1], tol) ); }

//! Sets each component to the min of this and a. void setMin(const mVec2& a) { if (a.v[0] < v[0]) v[0] = a.v[0]; if (a.v[1] < v[1]) v[1] = a.v[1]; }

//! Sets each component to the max of this and a. void setMax(const mVec2& a) { if (a.v[0] > v[0]) v[0] = a.v[0]; if (a.v[1] > v[1]) v[1] = a.v[1]; }

//! Clamps each component of this to [a, b] void clamp(float a, float b) { v[0] = mClamp(v[0], a, b); v[1] = mClamp(v[1], a, b); }

//! Clamps each component of vec to [a, b] void clamp(const mVec2& vec, float a, float b) { v[0] = mClamp(vec.v[0], a, b); v[1] = mClamp(vec.v[1], a, b); }

//! Addition: this += a void add(const mVec2& a) { v[0] += a.v[0]; v[1] += a.v[1]; }

//! Addition: this = a + b void add(const mVec2& a, const mVec2& b) { v[0] = a.v[0] + b.v[0]; v[1] = a.v[1] + b.v[1]; }

//! Addition: Returns this + a mVec2 operator + (const mVec2& a) const { return mVec2(v[0] + a.v[0], v[1] + a.v[1]); }

//! Addition: this += a mVec2& operator += (const mVec2& a) { v[0] += a.v[0]; v[1] += a.v[1]; return *this; }

//! this += a * s void addScaled(const mVec2& a, float s) { v[0] += a.v[0] * s; v[1] += a.v[1] * s; }

//! this = a + b * s void addScaled(const mVec2& a, const mVec2& b, float s) { v[0] = a.v[0] + b.v[0] * s; v[1] = a.v[1] + b.v[1] * s; }

//! this = a * s1 + b * s2 void addScaled(const mVec2& a, float s1, const mVec2& b, float s2) { v[0] = a.v[0] * s1 + b.v[0] * s2; v[1] = a.v[1] * s1 + b.v[1] * s2; }

//! Subtraction: this -= a void sub(const mVec2& a) { v[0] -= a.v[0]; v[1] -= a.v[1]; }

//! Subtraction: this = a - b void sub(const mVec2& a, const mVec2& b) { v[0] = a.v[0] - b.v[0]; v[1] = a.v[1] - b.v[1]; }

//! Subtraction: Returns this - a mVec2 operator - (const mVec2& a) const { return mVec2(v[0] - a.v[0], v[1] - a.v[1]); }

//! Subtraction: this -= a mVec2& operator -= (const mVec2& a) { v[0] -= a.v[0]; v[1] -= a.v[1]; return *this; }

//! Scales each component by s. void scale(float s) { v[0] *= s; v[1] *= s; }

//! Scales each component of a by s. void scale(const mVec2& a, float s) { v[0] = a.v[0] * s; v[1] = a.v[1] * s; }

//! Scales each component by s. mVec2& operator *= (float s) { v[0] *= s; v[1] *= s; return *this; }

//! Negate: this = -this void neg() { v[0] = -v[0]; v[1] = -v[1]; }

//! Negate: this = -a void neg(const mVec2& a) { v[0] = -a.v[0]; v[1] = -a.v[1]; }

//! Negate: Returns -this mVec2 operator - () const { return mVec2(-v[0], -v[1]); }

//! Component multiplication void compMult(const mVec2& a) { v[0] *= a[0]; v[1] *= a[1]; }

//! Component multiplication void compMult(const mVec2& a, const mVec2& b) { v[0] = a[0] * b[0]; v[1] = a[1] * b[1]; }

//! Component division void compDiv(const mVec2& a) { v[0] /= a[0]; v[1] /= a[1]; }

//! Component division void compDiv(const mVec2& a, const mVec2& b) { v[0] = a[0] * b[0]; v[1] = a[1] * b[1]; }

//! Returns the distance squared between this and a. float distance2(const mVec2& a) const { return( mSquare(v[0] - a.v[0]) + mSquare(v[1] - a.v[1]) ); }

//! Returns the distance between this and a. float distance(const mVec2& a) const { return( mSqrt(distance2(a)) ); }

//! Returns the length squared of this. float length2() const { return( mSquare(v[0]) + mSquare(v[1]) ); }

//! Returns the length of this. float length() const { return( mSqrt(length2()) ); }

//! Returns the dot product of this and a. float dot(const mVec2& a) const { return( v[0] * a.v[0] + v[1] * a.v[1] ); }

//! Normalizes this and returns the previous length. float normalize() { float l(length()); if (l != 0.0f) scale(1.0f / l); return l; }

//! Linearly interpolates between two vectors. void lerp(const mVec2& a, const mVec2& b, float t) { v[0] = a.v[0] + t * (b.v[0] - a.v[0]); v[1] = a.v[1] + t * (b.v[1] - a.v[1]); }

};

// Common constant values. const mVec3 mZero2(0.0f, 0.0f); const mVec3 mOne2(1.0f, 1.0f);

//**************************************************************************** //** END HEADER mVec2.h //**************************************************************************** #endif // __mVec2_H__

Currently browsing [mmath.zip] (283,561 bytes) - [include/mVec3.h] - (10,352 bytes)

#ifndef __mVec3_H__
#define __mVec3_H__

/*! \file mVec3.h \brief 3D Vector \author Douglas H. Cox */

//============================================================================ // REQUIRED HEADERS //============================================================================ #include "mMath.h"

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================ class mFrame; class mOCS; //============================================================================ // FUNCTION PROTOTYPES //============================================================================ //============================================================================ // CLASS PROTOTYPES //============================================================================ //! 3D Vector / Point /*! mVec3 represents a vector consisting of an array of three float values. */ class MMATH_DLL mVec3 { public: float v[3]; //!< vector data //! Default constructor /*! No initialization is done here. */ mVec3() {}

//! Copy constructor mVec3(const mVec3& src) { v[0] = src.v[0]; v[1] = src.v[1]; v[2] = src.v[2]; }

//! Constructor from 3 float values mVec3(float x, float y, float z) { v[0] = x; v[1] = y; v[2] = z; }

//! Constructor from an array of 3 float values mVec3(float *src) { v[0] = src[0]; v[1] = src[1]; v[2] = src[2]; }

//! Assignment void set(const mVec3& src) { v[0] = src.v[0]; v[1] = src.v[1]; v[2] = src.v[2]; }

//! Assignment from 3 float values void set(float x, float y, float z) { v[0] = x; v[1] = y; v[2] = z; }

//! Assignment from an arry of 3 float values void set(float *src) { v[0] = src[0]; v[1] = src[1]; v[2] = src[2]; }

//! Assignment mVec3& operator = (const mVec3& src) { v[0] = src.v[0]; v[1] = src.v[1]; v[2] = src.v[2]; return *this; }

//! Sets this to a vector pointing in the specified heading. /*! The resulting vector is normalized. */ void setH(float heading) { mSinCos(heading, v[0], v[1]); v[0] = -v[0]; v[2] = 0.0f; }

//! Sets this to a vector pointing in the specified heading and pitch. /*! The resulting vector is normalized. */ void setHP(float heading, float pitch);

//! Accessor void get(float& x, float& y, float& z) const { x = v[0]; y = v[1]; z = v[2]; }

//! Returns the heading and pitch for a normalized vector. void getHP(float& heading, float& pitch) const;

//! Accessor float& operator [] (int i) { return v[i]; }

//! Accessor float operator [] (int i) const { return v[i]; }

//! Returns true if this == a bool operator == (const mVec3& a) const { return( v[0] == a.v[0] && v[1] == a.v[1] && v[2] == a.v[2] ); }

//! Returns true if this != a bool operator != (const mVec3& a) const { return !(operator==(a)); }

//! Returns true is this is within some tolerance value of a. bool approxEqual(const mVec3& a, float tol = mZeroTol) const { return( mApproxEqual(v[0], a.v[0], tol) && mApproxEqual(v[1], a.v[1], tol) && mApproxEqual(v[2], a.v[2], tol) ); }

//! Sets each component to the min of this and a. void setMin(const mVec3& a) { if (a.v[0] < v[0]) v[0] = a.v[0]; if (a.v[1] < v[1]) v[1] = a.v[1]; if (a.v[2] < v[2]) v[2] = a.v[2]; }

//! Sets each component to the max of this and a. void setMax(const mVec3& a) { if (a.v[0] > v[0]) v[0] = a.v[0]; if (a.v[1] > v[1]) v[1] = a.v[1]; if (a.v[2] > v[2]) v[2] = a.v[2]; }

//! Clamps each component of this to [a, b] void clamp(float a, float b) { v[0] = mClamp(v[0], a, b); v[1] = mClamp(v[1], a, b); v[2] = mClamp(v[2], a, b); }

//! Clamps each component of vec to [a, b] void clamp(const mVec3& vec, float a, float b) { v[0] = mClamp(vec.v[0], a, b); v[1] = mClamp(vec.v[1], a, b); v[2] = mClamp(vec.v[2], a, b); }

//! Addition: this += a void add(const mVec3& a) { v[0] += a.v[0]; v[1] += a.v[1]; v[2] += a.v[2]; }

//! Addition: this = a + b void add(const mVec3& a, const mVec3& b) { v[0] = a.v[0] + b.v[0]; v[1] = a.v[1] + b.v[1]; v[2] = a.v[2] + b.v[2]; }

//! Addition: Returns this + a mVec3 operator + (const mVec3& a) const { return mVec3(v[0] + a.v[0], v[1] + a.v[1], v[2] + a.v[2]); }

//! Addition: this += a mVec3& operator += (const mVec3& a) { v[0] += a.v[0]; v[1] += a.v[1]; v[2] += a.v[2]; return *this; }

//! this += a * s void addScaled(const mVec3& a, float s) { v[0] += a.v[0] * s; v[1] += a.v[1] * s; v[2] += a.v[2] * s; }

//! this = a + b * s void addScaled(const mVec3& a, const mVec3& b, float s) { v[0] = a.v[0] + b.v[0] * s; v[1] = a.v[1] + b.v[1] * s; v[2] = a.v[2] + b.v[2] * s; }

//! this = a * s1 + b * s2 void addScaled(const mVec3& a, float s1, const mVec3& b, float s2) { v[0] = a.v[0] * s1 + b.v[0] * s2; v[1] = a.v[1] * s1 + b.v[1] * s2; v[2] = a.v[2] * s1 + b.v[2] * s2; }

//! Subtraction: this -= a void sub(const mVec3& a) { v[0] -= a.v[0]; v[1] -= a.v[1]; v[2] -= a.v[2]; }

//! Subtraction: this = a - b void sub(const mVec3& a, const mVec3& b) { v[0] = a.v[0] - b.v[0]; v[1] = a.v[1] - b.v[1]; v[2] = a.v[2] - b.v[2]; }

//! Subtraction: Returns this - a mVec3 operator - (const mVec3& a) const { return mVec3(v[0] - a.v[0], v[1] - a.v[1], v[2] - a.v[2]); }

//! Subtraction: this -= a mVec3& operator -= (const mVec3& a) { v[0] -= a.v[0]; v[1] -= a.v[1]; v[2] -= a.v[2]; return *this; }

//! Scales each component by s. void scale(float s) { v[0] *= s; v[1] *= s; v[2] *= s; }

//! Scales each component of a by s. void scale(const mVec3& a, float s) { v[0] = a.v[0] * s; v[1] = a.v[1] * s; v[2] = a.v[2] * s; }

//! Scales each component by s. mVec3& operator *= (float s) { v[0] *= s; v[1] *= s; v[2] *= s; return *this; }

//! Negate: this = -this void neg() { v[0] = -v[0]; v[1] = -v[1]; v[2] = -v[2]; }

//! Negate: this = -a void neg(const mVec3& a) { v[0] = -a.v[0]; v[1] = -a.v[1]; v[2] = -a.v[2]; }

//! Negate: Returns -this mVec3 operator - () const { return mVec3(-v[0], -v[1], -v[2]); }

//! Component multiplication void compMult(const mVec3& a) { v[0] *= a[0]; v[1] *= a[1]; v[2] *= a[2]; }

//! Component multiplication void compMult(const mVec3& a, const mVec3& b) { v[0] = a[0] * b[0]; v[1] = a[1] * b[1]; v[2] = a[2] * b[2]; }

//! Component division void compDiv(const mVec3& a) { v[0] /= a[0]; v[1] /= a[1]; v[2] /= a[2]; }

//! Component division void compDiv(const mVec3& a, const mVec3& b) { v[0] = a[0] / b[0]; v[1] = a[1] / b[1]; v[2] = a[2] / b[2]; }

//! Returns the distance squared between this and a. float distance2(const mVec3& a) const { return( mSquare(v[0] - a.v[0]) + mSquare(v[1] - a.v[1]) + mSquare(v[2] - a.v[2]) ); }

//! Returns the distance between this and a. float distance(const mVec3& a) const { return( mSqrt(distance2(a)) ); }

//! Returns the length squared of this. float length2() const { return( mSquare(v[0]) + mSquare(v[1]) + mSquare(v[2]) ); }

//! Returns the length of this. float length() const { return( mSqrt(length2()) ); }

//! Returns the dot product of this and a. float dot(const mVec3& a) const { return( v[0] * a.v[0] + v[1] * a.v[1] + v[2] * a.v[2] ); }

//! Calculates the cross product of a and b void cross(const mVec3& a, const mVec3& b) { mVec3 cp; cp.v[0] = a.v[1]*b.v[2] - a.v[2]*b.v[1]; cp.v[1] = a.v[2]*b.v[0] - a.v[0]*b.v[2]; cp.v[2] = a.v[0]*b.v[1] - a.v[1]*b.v[0]; set(cp); }

//! Normalizes this and returns the previous length. float normalize() { float l(length()); if (l != 0.0f) scale(1.0f / l); return l; }

//! Linearly interpolates between two vectors. void lerp(const mVec3& a, const mVec3& b, float t) { v[0] = a.v[0] + t * (b.v[0] - a.v[0]); v[1] = a.v[1] + t * (b.v[1] - a.v[1]); v[2] = a.v[2] + t * (b.v[2] - a.v[2]); }

//! Creates a normal from three points. void makeNormal(const mVec3& a, const mVec3& b, const mVec3& c);

//! Transforms the point p into f's axial frame. void xformTo(const mVec3& p, const mFrame& f);

//! Transforms the point p into the OCS. void xformTo(const mVec3& p, const mOCS& ocs);

//! Transforms the vector into the OCS. /*! Assumes \e vec is a vector. The ocs's origin is not used. */ void xformVecTo(const mVec3& vec, const mOCS& ocs);

//! Transforms the point p from f's axial frame. void xformFrom(const mVec3& p, const mFrame& f);

//! Transforms the point p from the OCS. void xformFrom(const mVec3& p, const mOCS& ocs);

//! Transforms the vector from the OCS. /*! Assumes \e vec is a vector. The ocs's origin is not used. */ void xformVecFrom(const mVec3& vec, const mOCS& ocs);

};

// Common constant values. const mVec3 mZero3(0.0f, 0.0f, 0.0f); const mVec3 mOne3(1.0f, 1.0f, 1.0f);

//**************************************************************************** //** END HEADER mVec3.h //**************************************************************************** #endif // __mVec3_H__

Currently browsing [mmath.zip] (283,561 bytes) - [include/mVec4.h] - (9,742 bytes)

#ifndef __mVec4_H__
#define __mVec4_H__

/*! \file mVec4.h \brief 4D Vector \author Douglas H. Cox */

//============================================================================ // REQUIRED HEADERS //============================================================================ #include "mMath.h"

//============================================================================ // DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS / CLASS FORWARDS //============================================================================ //============================================================================ // FUNCTION PROTOTYPES //============================================================================ //============================================================================ // CLASS PROTOTYPES //============================================================================ //! 4D Vector /*! mVec4 represents a vector consisting of an array of four float values. */ class MMATH_DLL mVec4 { public: float v[4]; //!< vector data //! Default constructor /*! No initialization is done here. */ mVec4() {}

//! Copy constructor mVec4(const mVec4& src) { v[0] = src.v[0]; v[1] = src.v[1]; v[2] = src.v[2]; v[3] = src.v[3]; }

//! Constructor from 4 float values mVec4(float x, float y, float z, float w) { v[0] = x; v[1] = y; v[2] = z; v[3] = w; }

//! Constructor from an array of 4 float values mVec4(float *src) { v[0] = src[0]; v[1] = src[1]; v[2] = src[2]; v[3] = src[3]; }

//! Assignment void set(const mVec4& src) { v[0] = src.v[0]; v[1] = src.v[1]; v[2] = src.v[2]; v[3] = src.v[3]; }

//! Assignment from 4 float values void set(float x, float y, float z, float w) { v[0] = x; v[1] = y; v[2] = z; v[3] = w; }

//! Assignment from an arry of 4 float values void set(float *src) { v[0] = src[0]; v[1] = src[1]; v[2] = src[2]; v[3] = src[3]; }

//! Assignment mVec4& operator = (const mVec4& src) { v[0] = src.v[0]; v[1] = src.v[1]; v[2] = src.v[2]; v[3] = src.v[3]; return *this; }

//! Accessor void get(float& x, float& y, float& z, float& w) const { x = v[0]; y = v[1]; z = v[2]; w = v[3]; }

//! Accessor float& operator [] (int i) { return v[i]; }

//! Accessor float operator [] (int i) const { return v[i]; }

//! Returns true if this == a bool operator == (const mVec4& a) const { return( v[0] == a.v[0] && v[1] == a.v[1] && v[2] == a.v[2] && v[3] == a.v[3] ); }

//! Returns true if this != a bool operator != (const mVec4& a) const { return !(operator==(a)); }

//! Returns true is this is equal to a within some tolerance value. bool approxEqual(const mVec4& a, float tol = mZeroTol) { return( mApproxEqual(v[0], a.v[0], tol) && mApproxEqual(v[1], a.v[1], tol) && mApproxEqual(v[2], a.v[2], tol) && mApproxEqual(v[3], a.v[3], tol) ); }

//! Sets each component to the min of this and a. void setMin(const mVec4& a) { if (a.v[0] < v[0]) v[0] = a.v[0]; if (a.v[1] < v[1]) v[1] = a.v[1]; if (a.v[2] < v[2]) v[2] = a.v[2]; if (a.v[3] < v[3]) v[3] = a.v[3]; }

//! Sets each component to the max of this and a. void setMax(const mVec4& a) { if (a.v[0] > v[0]) v[0] = a.v[0]; if (a.v[1] > v[1]) v[1] = a.v[1]; if (a.v[2] > v[2]) v[2] = a.v[2]; if (a.v[3] > v[3]) v[3] = a.v[3]; }

//! Clamps each component of this to [a, b] void clamp(float a, float b) { v[0] = mClamp(v[0], a, b); v[1] = mClamp(v[1], a, b); v[2] = mClamp(v[2], a, b); v[3] = mClamp(v[3], a, b); }

//! Clamps each component of vec to [a, b] void clamp(const mVec4& vec, float a, float b) { v[0] = mClamp(vec.v[0], a, b); v[1] = mClamp(vec.v[1], a, b); v[2] = mClamp(vec.v[2], a, b); v[3] = mClamp(vec.v[3], a, b); }

//! Addition: this += a void add(const mVec4& a) { v[0] += a.v[0]; v[1] += a.v[1]; v[2] += a.v[2]; v[3] += a.v[3]; }

//! Addition: this = a + b void add(const mVec4& a, const mVec4& b) { v[0] = a.v[0] + b.v[0]; v[1] = a.v[1] + b.v[1]; v[2] = a.v[2] + b.v[2]; v[3] = a.v[3] + b.v[3]; }

//! Addition: Returns this + a mVec4 operator + (const mVec4& a) const { return mVec4(v[0] + a.v[0], v[1] + a.v[1], v[2] + a.v[2], v[3] + a.v[3]); }

//! Addition: this += a mVec4& operator += (const mVec4& a) { v[0] += a.v[0]; v[1] += a.v[1]; v[2] += a.v[2]; v[3] += a.v[3]; return *this; }

//! this += a * s void addScaled(const mVec4& a, float s) { v[0] += a.v[0] * s; v[1] += a.v[1] * s; v[2] += a.v[2] * s; v[3] += a.v[3] * s; }

//! this = a + b * s void addScaled(const mVec4& a, const mVec4& b, float s) { v[0] = a.v[0] + b.v[0] * s; v[1] = a.v[1] + b.v[1] * s; v[2] = a.v[2] + b.v[2] * s; v[3] = a.v[3] + b.v[3] * s; }

//! this = a * s1 + b * s2 void addScaled(const mVec4& a, float s1, const mVec4& b, float s2) { v[0] = a.v[0] * s1 + b.v[0] * s2; v[1] = a.v[1] * s1 + b.v[1] * s2; v[2] = a.v[2] * s1 + b.v[2] * s2; v[3] = a.v[3] * s1 + b.v[3] * s2; }

//! Subtraction: this -= a void sub(const mVec4& a) { v[0] -= a.v[0]; v[1] -= a.v[1]; v[2] -= a.v[2]; v[3] -= a.v[3]; }

//! Subtraction: this = a - b void sub(const mVec4& a, const mVec4& b) { v[0] = a.v[0] - b.v[0]; v[1] = a.v[1] - b.v[1]; v[2] = a.v[2] - b.v[2]; v[3] = a.v[3] - b.v[3]; }

//! Subtraction: Returns this - a mVec4 operator - (const mVec4& a) const { return mVec4(v[0] - a.v[0], v[1] - a.v[1], v[2] - a.v[2], v[3] - a.v[3]); }

//! Subtraction: this -= a mVec4& operator -= (const mVec4& a) { v[0] -= a.v[0]; v[1] -= a.v[1]; v[2] -= a.v[2]; v[3] -= a.v[3]; return *this; }

//! Scales each component by s. void scale(float s) { v[0] *= s; v[1] *= s; v[2] *= s; v[3] *= s; }

//! Scales each component of a by s. void scale(const mVec4& a, float s) { v[0] = a.v[0] * s; v[1] = a.v[1] * s; v[2] = a.v[2] * s; v[3] = a.v[3] * s; }

//! Scales each component by s. mVec4& operator *= (float s) { v[0] *= s; v[1] *= s; v[2] *= s; v[3] *= s; return *this; }

//! Negate: this = -this void neg() { v[0] = -v[0]; v[1] = -v[1]; v[2] = -v[2]; v[3] = -v[3]; }

//! Negate: this = -a void neg(const mVec4& a) { v[0] = -a.v[0]; v[1] = -a.v[1]; v[2] = -a.v[2]; v[3] = -a.v[3]; }

//! Negate: Returns -this mVec4 operator - () const { return mVec4(-v[0], -v[1], -v[2], -v[3]); } //! Component multiplication void compMult(const mVec4& a) { v[0] *= a[0]; v[1] *= a[1]; v[2] *= a[2]; v[3] *= a[3]; }

//! Component multiplication void compMult(const mVec4& a, const mVec4& b) { v[0] = a[0] * b[0]; v[1] = a[1] * b[1]; v[2] = a[2] * b[2]; v[3] = a[3] * b[3]; }

//! Component division void compDiv(const mVec4& a) { v[0] /= a[0]; v[1] /= a[1]; v[2] /= a[2]; v[3] /= a[3]; }

//! Component division void compDiv(const mVec4& a, const mVec4& b) { v[0] = a[0] * b[0]; v[1] = a[1] * b[1]; v[2] = a[2] * b[2]; v[3] = a[3] * b[3]; }

//! Returns the distance squared between this and a. float distance2(const mVec4& a) const { return( mSquare(v[0] - a.v[0]) + mSquare(v[1] - a.v[1]) + mSquare(v[2] - a.v[2]) + mSquare(v[3] - a.v[3]) ); }

//! Returns the distance between this and a. float distance(const mVec4& a) const { return( mSqrt(distance2(a)) ); }

//! Returns the length squared of this. float length2() const { return( mSquare(v[0]) + mSquare(v[1]) + mSquare(v[2]) + mSquare(v[3]) ); }

//! Returns the length of this. float length() const { return( mSqrt(length2()) ); }

//! Returns the dot product of this and a. float dot(const mVec4& a) const { return( v[0] * a.v[0] + v[1] * a.v[1] + v[2] * a.v[2] + v[3] * a.v[3] ); }

//! Normalizes this and returns the previous length. float normalize() { float l(length()); if (l != 0.0f) scale(1.0f / l); return l; }

//! Linearly interpolates between two vectors. void lerp(const mVec4& a, const mVec4& b, float t) { v[0] = a.v[0] + t * (b.v[0] - a.v[0]); v[1] = a.v[1] + t * (b.v[1] - a.v[1]); v[2] = a.v[2] + t * (b.v[2] - a.v[2]); v[3] = a.v[3] + t * (b.v[3] - a.v[3]); }

};

// Common constant values. const mVec4 mZero4(0.0f, 0.0f, 0.0f, 0.0f); const mVec4 mOne4(1.0f, 1.0f, 1.0f, 1.0f);

//**************************************************************************** //** END HEADER mVec4.h //**************************************************************************** #endif // __mVec4_H__

Currently browsing [mmath.zip] (283,561 bytes) - [src/mMath/mFrame.cpp] - (6,246 bytes)

//****************************************************************************
//**
//**    mFrame.cpp
//**    Implementation for mFrame.
//**    (C) 2000 - Douglas H. Cox
//**
//****************************************************************************
//============================================================================
//    HEADERS
//============================================================================
#include "mFrame.h"

#include "mQuat.h"

//============================================================================ // PRIVATE DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS //============================================================================ //============================================================================ // PRIVATE STRUCTURES / UTILITY CLASSES //============================================================================ //============================================================================ // PRIVATE DATA //============================================================================ //============================================================================ // PRIVATE FUNCTIONS //============================================================================ //============================================================================ // FUNCTIONS //============================================================================ //============================================================================ // CLASS METHODS //============================================================================ //============================================================= // mFrame::approxEqual bool mFrame::approxEqual(const mFrame& f, float tol) const { return (a[0].approxEqual(f.a[0], tol) && a[1].approxEqual(f.a[1], tol) && a[2].approxEqual(f.a[2], tol)); }

//============================================================= // mFrame::inverse void mFrame::inverse() { float tmp; tmp = a[0].v[1]; a[0].v[1] = a[1].v[0]; a[1].v[0] = tmp;

tmp = a[0].v[2]; a[0].v[2] = a[2].v[0]; a[2].v[0] = tmp;

tmp = a[1].v[2]; a[1].v[2] = a[2].v[1]; a[2].v[1] = tmp; }

//============================================================= // mFrame::inverse void mFrame::inverse(const mFrame& f) { float tmp; tmp = f.a[0].v[1]; a[0].v[1] = f.a[1].v[0]; a[1].v[0] = tmp;

tmp = f.a[0].v[2]; a[0].v[2] = f.a[2].v[0]; a[2].v[0] = tmp;

tmp = f.a[1].v[2]; a[1].v[2] = f.a[2].v[1]; a[2].v[1] = tmp; // diagonal a[0].v[0] = f.a[0].v[0]; a[1].v[1] = f.a[1].v[1]; a[2].v[2] = f.a[2].v[2]; }

//============================================================= // mFrame::xformTo void mFrame::xformTo(const mFrame& f, const mFrame& to) { mFrame nf;

nf.a[0].xformTo(f.a[0], to); nf.a[1].xformTo(f.a[1], to); nf.a[2].xformTo(f.a[2], to);

set(nf); }

//============================================================= // mFrame::xformFrom void mFrame::xformFrom(const mFrame& f, const mFrame& from) { mFrame nf;

nf.a[0].xformFrom(f.a[0], from); nf.a[1].xformFrom(f.a[1], from); nf.a[2].xformFrom(f.a[2], from);

set(nf); } //============================================================= // mFrame::setQuat void mFrame::setQuat(const mQuat& q) { // standard quaternion to matrix operations float x(q.v[0]), y(q.v[1]), z(q.v[2]), w(q.v[3]); float x2(x*2.0f), y2(y*2.0f), z2(z*2.0f), w2(w*2.0f); float xx2(x*x2), yy2(y*y2), zz2(z*z2), ww2(w*w2); float xy2(x*y2), xz2(x*z2), xw2(x*w2), yz2(y*z2), yw2(y*w2), zw2(z*w2);

a[0].set(1.0f - (yy2 + zz2), xy2 - zw2, xz2 + yw2); a[1].set(xy2 + zw2, 1.0f - (xx2 + zz2), yz2 - xw2); a[2].set(xz2 - yw2, yz2 + xw2, 1.0f - (xx2 + yy2)); }

//============================================================= // mFrame::getQuat void mFrame::getQuat(mQuat& q) const { float tr, s; tr = a[0].v[0] + a[1].v[1] + a[2].v[2];

if (tr > 0.0f) { s = mSqrt(tr + 1.0f); q.v[3] = s*0.5f; s = 0.5f / s;

q.v[0] = s * (a[2].v[1] - a[1].v[2]); q.v[1] = s * (a[0].v[2] - a[2].v[0]); q.v[2] = s * (a[1].v[0] - a[0].v[1]); } else { const int n[3] = {1, 2, 0}; int i, j, k;

i = 0; if (a[1].v[1] > a[0].v[0]) i = 1; if (a[2].v[2] > a[i].v[i]) i = 2; j = n[i]; k = n[j];

s = mSqrt((a[i].v[i] - (a[j].v[j] + a[k].v[k])) + 1.0f);

q.v[i] = s * 0.5f; assert(s != 0.0f);

s = 0.5f / s;

q.v[3] = (a[k].v[j] - a[j].v[k]) * s; q.v[j] = (a[j].v[i] + a[i].v[j]) * s; q.v[k] = (a[k].v[i] + a[i].v[k]) * s; // TODO: Test this. bool bNotYetTested = false; assert(bNotYetTested); } }

//============================================================= // mFrame::setAxisAngle void mFrame::setAxisAngle(const mVec3& n, float a) { mQuat q; q.setAxisAngle(n, a); setQuat(q); }

//============================================================= // mFrame::getAxisAngle void mFrame::getAxisAngle(mVec3& n, float& a) const { mQuat q; getQuat(q); q.getAxisAngle(n, a); }

// ============================================================ // mFrame::setHP void mFrame::setHP(float heading, float pitch) { float sh, ch, sp, cp; mSinCos(heading, sh, ch); mSinCos(pitch, sp, cp);

a[0].set(ch, sh, 0.0f); a[1].set(-cp*sh, ch*cp, sp); a[2].set(sp*sh, sp*ch, cp); }

// ============================================================ // mFrame::setHPR void mFrame::setHPR(float heading, float pitch, float roll) { float sh, ch, sp, cp, sr, cr; mSinCos(heading, sh, ch); mSinCos(pitch, sp, cp); mSinCos(roll, sr, cr);

float srsp = sr*sp; float crsp = cr*sp;

a[0].set(cr*ch - srsp*sh, cr*sh + srsp*ch, -sr * cp); a[1].set(-cp*sh, ch*cp, sp); a[2].set(sr*ch + crsp*sh, sr*sh - crsp*ch, cr * cp); }

//**************************************************************************** //** END MODULE mFrame.cpp //****************************************************************************

Currently browsing [mmath.zip] (283,561 bytes) - [src/mMath/mMath.cpp] - (3,478 bytes)

//****************************************************************************
//**
//**    mMath.cpp
//**    Common math functions.
//**    (C) 2000 - Douglas H. Cox
//**
//****************************************************************************
//============================================================================
//    HEADERS
//============================================================================
#include "mMath.h"

// The following results in a ~10k drop in size for a release build. #ifdef NDEBUG #if _MSC_VER >= 1000 #pragma comment(linker,"/OPT:nowin98") #endif // _MSC_VER >= 1000 #endif // NDEBUG //============================================================================ // PRIVATE DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS //============================================================================ //============================================================================ // PRIVATE STRUCTURES / UTILITY CLASSES //============================================================================ //============================================================================ // PRIVATE DATA //============================================================================ // Square root table used for fast square root function. unsigned int mFastSqrtTable[0x10000];

// Keep track of initialized ref count static int s_initRefCount = 0;

//============================================================================ // PRIVATE FUNCTIONS //============================================================================ // ============================================================ // buildSqrtTable - from nVidia's fastmath.cpp void buildFastSqrtTable() { union uFloatUInt { float f; unsigned int i; } s;

unsigned int i;

for (i = 0; i <= 0x7FFF; i++) { // Build a float with the bit pattern i as mantissa // and an exponent of 0, stored as 127 s.i = (i << 8) | (0x7F << 23); s.f = (float)sqrt(s.f); // Take the square root then strip the first 7 bits of // the mantissa into the table mFastSqrtTable[i + 0x8000] = (s.i & 0x7FFFFF); // Repeat the process, this time with an exponent of 1, // stored as 128 s.i = (i << 8) | (0x80 << 23); s.f = (float)sqrt(s.f); mFastSqrtTable[i] = (s.i & 0x7FFFFF); } }

//============================================================================ // FUNCTIONS //============================================================================ // ============================================================ // mInitialize bool mInitialize() { s_initRefCount++; if (s_initRefCount > 1) return true;

// Initialize fast square root table. buildFastSqrtTable();

return true; }

// ============================================================ // mUninitialize void mUninitialize() { s_initRefCount--; if (s_initRefCount > 0) return; // Free up any allocated memory here. }

//============================================================================ // CLASS METHODS //============================================================================ //**************************************************************************** //** END MODULE mMath.cpp //****************************************************************************

Currently browsing [mmath.zip] (283,561 bytes) - [src/mMath/mMatrix.cpp] - (3,575 bytes)

//****************************************************************************
//**
//**    mMatrix.cpp
//**    Implementation for mMatrix.
//**    (C) 2000 - Douglas H. Cox
//**
//****************************************************************************
//============================================================================
//    HEADERS
//============================================================================
#include "mMatrix.h"

//============================================================================ // PRIVATE DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS //============================================================================ //============================================================================ // PRIVATE STRUCTURES / UTILITY CLASSES //============================================================================ //============================================================================ // PRIVATE DATA //============================================================================ //============================================================================ // PRIVATE FUNCTIONS //============================================================================ //============================================================================ // FUNCTIONS //============================================================================ //============================================================================ // CLASS METHODS //============================================================================ //============================================================= // mMatrix::set void mMatrix::set(const mMatrix& src) { for (int i = 0; i < 15;) { m[i] = src.m[i]; i++; m[i] = src.m[i]; i++; m[i] = src.m[i]; i++; m[i] = src.m[i]; i++; } }

//============================================================= // mMatrix::makeIdentity void mMatrix::makeIdentity() { m[0] = 1.0f; m[4] = 0.0f; m[8] = 0.0f; m[12] = 0.0f; m[1] = 0.0f; m[5] = 1.0f; m[9] = 0.0f; m[13] = 0.0f; m[2] = 0.0f; m[6] = 0.0f; m[10] = 1.0f; m[14] = 0.0f; m[3] = 0.0f; m[7] = 0.0f; m[11] = 0.0f; m[15] = 1.0f; }

//============================================================= // mMatrix::mult void mMatrix::mult(const mMatrix& a, const mMatrix& b) { mMatrix m;

m[0]=a[0]*b[0] + a[4]*b[1] + a[8 ]*b[2] + a[12]*b[3]; m[1]=a[1]*b[0] + a[5]*b[1] + a[9 ]*b[2] + a[13]*b[3]; m[2]=a[2]*b[0] + a[6]*b[1] + a[10]*b[2] + a[14]*b[3]; m[3]=a[3]*b[0] + a[7]*b[1] + a[11]*b[2] + a[15]*b[3];

m[4]=a[0]*b[4] + a[4]*b[5] + a[8 ]*b[6] + a[12]*b[7]; m[5]=a[1]*b[4] + a[5]*b[5] + a[9 ]*b[6] + a[13]*b[7]; m[6]=a[2]*b[4] + a[6]*b[5] + a[10]*b[6] + a[14]*b[7]; m[7]=a[3]*b[4] + a[7]*b[5] + a[11]*b[6] + a[15]*b[7];

m[8 ]=a[0]*b[8] + a[4]*b[9] + a[8 ]*b[10] + a[12]*b[11]; m[9 ]=a[1]*b[8] + a[5]*b[9] + a[9 ]*b[10] + a[13]*b[11]; m[10]=a[2]*b[8] + a[6]*b[9] + a[10]*b[10] + a[14]*b[11]; m[11]=a[3]*b[8] + a[7]*b[9] + a[11]*b[10] + a[15]*b[11];

m[12]=a[0]*b[12] + a[4]*b[13] + a[8 ]*b[14] + a[12]*b[15]; m[13]=a[1]*b[12] + a[5]*b[13] + a[9 ]*b[14] + a[13]*b[15]; m[14]=a[2]*b[12] + a[6]*b[13] + a[10]*b[14] + a[14]*b[15]; m[15]=a[3]*b[12] + a[7]*b[13] + a[11]*b[14] + a[15]*b[15];

set(m); }

//**************************************************************************** //** END MODULE mMatrix.cpp //****************************************************************************

Currently browsing [mmath.zip] (283,561 bytes) - [src/mMath/mOCS.cpp] - (8,480 bytes)

//****************************************************************************
//**
//**    mOCS.cpp
//**    Implementation for mOCS.
//**    (C) 2000 - Douglas H. Cox
//**
//****************************************************************************
//============================================================================
//    HEADERS
//============================================================================
#include "mOCS.h"

#include "mMatrix.h"

//============================================================================ // PRIVATE DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS //============================================================================ //============================================================================ // PRIVATE STRUCTURES / UTILITY CLASSES //============================================================================ //============================================================================ // PRIVATE DATA //============================================================================ //============================================================================ // PRIVATE FUNCTIONS //============================================================================ //============================================================================ // FUNCTIONS //============================================================================ //============================================================================ // CLASS METHODS //============================================================================

//============================================================= // mOCS::mOCS mOCS::mOCS(const mOCS& src) : o(src.o), f(src.f), s(src.s), type(src.type) { }

//============================================================= // mOCS::mOCS mOCS::mOCS(const mVec3& origin, const mFrame& frame, const mVec3& scale, unsigned type) { (type & ORIGIN) ? o.set(origin) : o.set(0.0f, 0.0f, 0.0f); (type & FRAME) ? f.set(frame) : f.makeIdentity(); (type & SCALE) ? s.set(scale) : s.set(1.0f, 1.0f, 1.0f);

this->type = type; }

//============================================================= // mOCS::makeIdentity void mOCS::makeIdentity() { if (type == IDENTITY) return;

o.set(0.0f, 0.0f, 0.0f); if (type & FRAME) f.makeIdentity(); s.set(1.0f, 1.0f, 1.0f); type = IDENTITY; }

//============================================================= // mOCS::makeOrigin void mOCS::makeOrigin(float x, float y, float z) { o.set(x, y, z); if (type & FRAME) f.makeIdentity(); s.set(1.0f, 1.0f, 1.0f); type = ORIGIN; }

//============================================================= // mOCS::makeFrame void mOCS::makeFrame(const mFrame& frame) { o.set(0.0f, 0.0f, 0.0f); f.set(frame); s.set(1.0f, 1.0f, 1.0f); type = FRAME; }

//============================================================= // mOCS::makeScale void mOCS::makeScale(float x, float y, float z) { o.set(0.0f, 0.0f, 0.0f); if (type & FRAME) f.makeIdentity(); s.set(x, y, z); type = SCALE; }

//============================================================= // mOCS::set void mOCS::set(const mOCS& src) { o.set(src.o); f.set(src.f); s.set(src.s); type = src.type; }

//============================================================= // mOCS::set void mOCS::set(const mVec3& origin, const mFrame& frame, const mVec3& scale, unsigned type) { (type & ORIGIN) ? o.set(origin) : o.set(0.0f, 0.0f, 0.0f); (type & FRAME) ? f.set(frame) : f.makeIdentity(); (type & SCALE) ? s.set(scale) : s.set(1.0f, 1.0f, 1.0f);

this->type = type; }

//============================================================= // mOCS::get void mOCS::get(mVec3& origin, mFrame& frame, mVec3& scale) const { origin.set(o); frame.set(f); scale.set(s); }

// ============================================================ // mOCS::operator == bool mOCS::operator == (const mOCS& ocs) const { return ( o == ocs.o && s == ocs.s && f == ocs.f ); }

//============================================================= // mOCS::approxEqual bool mOCS::approxEqual(const mOCS& ocs, float tol) const { return ( o.approxEqual(ocs.o, mZeroTol) && s.approxEqual(ocs.s, mZeroTol) && f.approxEqual(ocs.f, mZeroTol) ); }

//============================================================= // mOCS::inverse void mOCS::inverse(const mOCS &ocs) { if (ocs.type & ORIGIN) o.xformTo(mVec3(0.0f, 0.0f, 0.0f), ocs); else o.set(0.0f, 0.0f, 0.0f);

if (ocs.type & FRAME) f.inverse(ocs.f); else if (type & FRAME) f.makeIdentity();

if (ocs.type & SCALE) s.compDiv(mVec3(1.0f, 1.0f, 1.0f), ocs.s); else s.set(1.0f, 1.0f, 1.0f); type = ocs.type; }

//============================================================= // mOCS::xformTo void mOCS::xformTo(const mOCS& ocs, const mOCS& to) { mVec3 no; no.xformTo(ocs.o, to);

mFrame nf; if (to.type & FRAME) nf.xformTo(ocs.f, to.f); else nf.set(ocs.f);

mVec3 ns; if (to.type & SCALE) ns.compDiv(ocs.s, to.s); else ns.set(ocs.s); set(no, nf, ns, ocs.type | to.type); }

//============================================================= // mOCS::xformFrom void mOCS::xformFrom(const mOCS& ocs, const mOCS& from) { mVec3 no; no.xformFrom(ocs.o, from);

mFrame nf; if (from.type & FRAME) nf.xformFrom(ocs.f, from.f); else nf.set(ocs.f);

mVec3 ns; if (from.type & SCALE) ns.compMult(ocs.s, from.s); else ns.set(ocs.s); set(no, nf, ns, ocs.type | from.type); }

//============================================================= // mOCS::getToMatrix void mOCS::getToMatrix(mMatrix& matrix) const { float *m = matrix.m;

m[3] = 0.0f; m[7] = 0.0f; m[11] = 0.0f; m[15] = 1.0f;

if (type & FRAME) { m[0] = f.a[0].v[0]; m[4] = f.a[0].v[1]; m[8 ] = f.a[0].v[2]; m[1] = f.a[1].v[0]; m[5] = f.a[1].v[1]; m[9 ] = f.a[1].v[2]; m[2] = f.a[2].v[0]; m[6] = f.a[2].v[1]; m[10] = f.a[2].v[2]; if (type & SCALE) { mVec3 ns(1.0f, 1.0f, 1.0f); ns.compDiv(s); m[0] *= ns.v[0]; m[4] *= ns.v[1]; m[8 ] *= ns.v[2]; m[1] *= ns.v[0]; m[5] *= ns.v[1]; m[9 ] *= ns.v[2]; m[2] *= ns.v[0]; m[6] *= ns.v[1]; m[10] *= ns.v[2]; } } else { if (type & SCALE) { m[0] = 1.0f / s.v[0]; m[5] = 1.0f / s.v[1]; m[10] = 1.0f /s.v[2]; } else { m[0] = m[5] = m[10] = 1.0f; } m[4] = 0.0f; m[8 ] = 0.0f; m[1] = 0.0f; m[9 ] = 0.0f; m[2] = 0.0f; m[6] = 0.0f; }

if (type & ORIGIN) { mVec3 no; no.xformTo(o, *this); m[12] = o.v[0]; m[13] = o.v[1]; m[14] = o.v[2]; } else { m[12] = o.v[0]; m[13] = o.v[1]; m[14] = o.v[2]; } }

//============================================================= // mOCS::getFromMatrix void mOCS::getFromMatrix(mMatrix& matrix) const { float *m = matrix.m;

m[3] = 0.0f; m[7] = 0.0f; m[11] = 0.0f; m[15] = 1.0f;

if (type & FRAME) { m[0] = f.a[0].v[0]; m[4] = f.a[1].v[0]; m[8 ] = f.a[2].v[0]; m[1] = f.a[0].v[1]; m[5] = f.a[1].v[1]; m[9 ] = f.a[2].v[1]; m[2] = f.a[0].v[2]; m[6] = f.a[1].v[2]; m[10] = f.a[2].v[2]; if (type & SCALE) { m[0] *= s.v[0]; m[4] *= s.v[1]; m[8 ] *= s.v[2]; m[1] *= s.v[0]; m[5] *= s.v[1]; m[9 ] *= s.v[2]; m[2] *= s.v[0]; m[6] *= s.v[1]; m[10] *= s.v[2]; } } else { if (type & SCALE) { m[0] = s.v[0]; m[5] = s.v[1]; m[10] = s.v[2]; } else { m[0] = m[5] = m[10] = 1.0f; } m[4] = 0.0f; m[8 ] = 0.0f; m[1] = 0.0f; m[9 ] = 0.0f; m[2] = 0.0f; m[6] = 0.0f; }

m[12] = o.v[0]; m[13] = o.v[1]; m[14] = o.v[2]; }

//**************************************************************************** //** END MODULE mOCS.cpp //****************************************************************************

Currently browsing [mmath.zip] (283,561 bytes) - [src/mMath/mQuat.cpp] - (5,462 bytes)

//****************************************************************************
//**
//**    mQuat.cpp
//**    Implementation for mQuat.
//**    (C) 2000 - Douglas H. Cox
//**
//****************************************************************************
//============================================================================
//    HEADERS
//============================================================================
#include "mQuat.h"
#include "mVec3.h"

//============================================================================ // PRIVATE DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS //============================================================================ //============================================================================ // PRIVATE STRUCTURES / UTILITY CLASSES //============================================================================ //============================================================================ // PRIVATE DATA //============================================================================ //============================================================================ // PRIVATE FUNCTIONS //============================================================================ //============================================================================ // FUNCTIONS //============================================================================ //============================================================================ // CLASS METHODS //============================================================================ //============================================================= // mQuat::inverse void mQuat::inverse() { // q.scale(1.0f/length2()) // q.conjugate() scale(-1.0f / length2()); v[3] = -v[3]; }

//============================================================= // mQuat::inverse void mQuat::inverse(const mQuat& q) { // q.scale(1.0f/length2()) // q.conjugate() scale(q, -1.0f / q.length2()); v[3] = -v[3]; }

// ============================================================ // mQuat::mult void mQuat::mult(const mQuat& q1, const mQuat& q2) { mQuat tmp; tmp[0] = q1[3] * q2[0] + q1[0] * q2[3] + q1[1] * q2[2] - q1[2] * q2[1]; tmp[1] = q1[3] * q2[1] + q1[1] * q2[3] + q1[2] * q2[0] - q1[0] * q2[2]; tmp[2] = q1[3] * q2[2] + q1[2] * q2[3] + q1[0] * q2[1] - q1[1] * q2[0]; tmp[3] = q1[3] * q2[3] - q1[0] * q2[0] - q1[1] * q2[1] - q1[2] * q2[2]; set(tmp); }

//============================================================= // mQuat::setAxisAngle void mQuat::setAxisAngle(const mVec3& n, float a) { float s, c; mSinCos(a * 0.5f, s, c);

v[0] = n[0] * s; v[1] = n[1] * s; v[2] = n[2] * s; v[3] = c; }

//============================================================= // mQuat::getAxisAngle void mQuat::getAxisAngle(mVec3& n, float& a) const { float s = 1.0f / mSqrt( 1.0f - v[3]*v[3] );

a = mACos(v[3]) * 2.0f; n[0] = v[0] * s; n[1] = v[1] * s; n[2] = v[2] * s; }

// ============================================================ // mQuat::setHP void mQuat::setHP(float h, float p) { // TODO: check h/p > 180.0f etc. h *= 0.5f; p *= 0.5f;

float cH, sH; float cP, sP;

mSinCos(h, sH, cH); mSinCos(p, sP, cP);

v[0] = -(sP * cH); v[1] = -(sP * sH); v[2] = -(cP * sH); v[3] = (cP * cH); }

//============================================================= // mQuat::getHP void mQuat::getHP(float &h, float &p) const { h = 2.0f * mATan2(-v[2], v[3]); p = 2.0f * mATan2(-v[0], v[3]); }

// ============================================================ // mQuat::setHPR void mQuat::setHPR(float h, float p, float r) { h *= 0.5f; p *= 0.5f; r *= 0.5f;

float cH, sH; float cP, sP; float cR, sR;

mSinCos(h, sH, cH); mSinCos(p, sP, cP); mSinCos(r, sR, cR);

float cPcH = cP * cH; float cPsH = cP * sH; float sPcH = sP * cH; float sPsH = sP * sH;

v[0] = -(sPcH * cR) + (cPsH * sR); v[1] = -(cPcH * sR) - (sPsH * cR); v[2] = -(cPsH * cR) - (sPcH * sR); v[3] = (cPcH * cR) - (sPsH * sR); }

//============================================================= // mQuat::getHPR void mQuat::getHPR(mVec3& hpr) const { assert(false); // TODO: implement }

//============================================================= // mQuat::slerp void mQuat::slerp(const mQuat& q1, const mQuat& q2, float t) { float cosom = q1.dot(q2); float s1, s2;

if ( (1.0f + cosom) > mZeroTol) { if ( (1.0f - cosom) > mZeroTol) { double omega, isinom; omega = acos(cosom); isinom = 1.0f / sin(omega); s1 = float(sin((1.0f - t) * omega) * isinom); s2 = float(sin(t * omega) * isinom); } else { s1 = 1.0f - t; s2 = t; } addScaled(q1, s1, q2, s2); } else { mQuat pq; pq.v[0] = -q2.v[1]; pq.v[1] = q2.v[0]; pq.v[2] = -q2.v[3]; pq.v[3] = q2.v[2];

s1 = float(sin((1.0f - t) * mHalfPI)); s2 = float(sin(t * mHalfPI)); addScaled(q1, s1, pq, s2); } }

//**************************************************************************** //** END MODULE mQuat.cpp //****************************************************************************

Currently browsing [mmath.zip] (283,561 bytes) - [src/mMath/mRay.cpp] - (3,311 bytes)

//****************************************************************************
//**
//**    mRay.cpp
//**    Ray class.
//**    (C) 2000 - Douglas H. Cox
//**
//****************************************************************************
//============================================================================
//    HEADERS
//============================================================================
#include "mRay.h"

#include "mOCS.h"

//============================================================================ // PRIVATE DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS //============================================================================ //============================================================================ // PRIVATE STRUCTURES / UTILITY CLASSES //============================================================================ //============================================================================ // PRIVATE DATA //============================================================================ //============================================================================ // PRIVATE FUNCTIONS //============================================================================ //============================================================================ // FUNCTIONS //============================================================================ //============================================================================ // CLASS METHODS //============================================================================ // ============================================================ // mRay::set void mRay::set(const mVec3& startPoint, const mVec3& endPoint) { pos.set(startPoint); dir.sub(endPoint, startPoint); len = dir.normalize(); }

// ============================================================ // mRay::operator == bool mRay::operator == (const mRay& ray) const { return (len == ray.len && pos == ray.pos && dir == ray.dir); }

// ============================================================ // mRay::getEndPoint void mRay::getEndPoint(mVec3& end) const { (len >= 0.0f) ? end.addScaled(pos, dir, len) : end.addScaled(pos, dir, mFloatMax); }

// ============================================================ // mRay::xformTo void mRay::xformTo(const mRay& ray, const mOCS& ocs) { pos.xformTo(ray.pos, ocs); dir.xformVecTo(ray.dir, ocs);

if (len < 0.0f) { if (ocs.type & mOCS::SCALE) dir.normalize(); } else { if (ocs.type & mOCS::SCALE) { len *= dir.normalize(); } } }

// ============================================================ // mRay::xformFrom void mRay::xformFrom(const mRay& ray, const mOCS& ocs) { pos.xformFrom(ray.pos, ocs); dir.xformVecFrom(ray.dir, ocs);

if (len < 0.0f) { if (ocs.type & mOCS::SCALE) dir.normalize(); } else { if (ocs.type & mOCS::SCALE) { len *= dir.normalize(); } } }

//**************************************************************************** //** END MODULE mRay.cpp //****************************************************************************

Currently browsing [mmath.zip] (283,561 bytes) - [src/mMath/mVec.cpp] - (4,647 bytes)

//****************************************************************************
//**
//**    mVec.cpp
//**    Implementation for various mVec* functions.
//**    (C) 2000 - Douglas H. Cox
//**
//****************************************************************************
//============================================================================
//    HEADERS
//============================================================================
#include "mVec3.h"
#include "mFrame.h"
#include "mOCS.h"

//============================================================================ // PRIVATE DEFINITIONS / ENUMERATIONS / SIMPLE TYPEDEFS //============================================================================ //============================================================================ // PRIVATE STRUCTURES / UTILITY CLASSES //============================================================================ //============================================================================ // PRIVATE DATA //============================================================================ //============================================================================ // PRIVATE FUNCTIONS //============================================================================ //============================================================================ // FUNCTIONS //============================================================================ //============================================================================ // CLASS METHODS //============================================================================ //============================================================= // mVec3::setHP void mVec3::setHP(float heading, float pitch) { mSinCos(heading, v[0], v[1]); v[0] = -v[0]; v[2] = mSin(pitch); normalize(); }

//============================================================= // mVec3::getHP void mVec3::getHP(float& heading, float& pitch) const { heading = mATan2(-v[0], v[1]); pitch = mASin(v[2] / mSqrt(v[0]*v[0] + v[1]*v[1])); }

// ============================================================ // mVec3::makeNormal void mVec3::makeNormal(const mVec3& a, const mVec3& b, const mVec3& c) { cross(b - a, c - b); normalize(); }

//============================================================= // mVec3::xformTo void mVec3::xformTo(const mVec3& vec, const mFrame& f) { mVec3 nv(vec.dot(f.a[0]), vec.dot(f.a[1]), vec.dot(f.a[2])); set(nv); }

//============================================================= // mVec3::xformFrom void mVec3::xformFrom(const mVec3& vec, const mFrame& f) { mVec3 nv(vec.v[0] * f.a[0].v[0] + vec.v[1] * f.a[1].v[0] + vec.v[2] * f.a[2].v[0], vec.v[0] * f.a[0].v[1] + vec.v[1] * f.a[1].v[1] + vec.v[2] * f.a[2].v[1], vec.v[0] * f.a[0].v[2] + vec.v[1] * f.a[1].v[2] + vec.v[2] * f.a[2].v[2]); set(nv); }

//============================================================= // mVec3::xformTo void mVec3::xformTo(const mVec3& vec, const mOCS& ocs) { assert(&vec != &ocs.o); set(vec);

if (ocs.type & mOCS::ORIGIN) sub(ocs.o);

if (ocs.type & mOCS::FRAME) xformTo(*this, ocs.f);

if (ocs.type & mOCS::SCALE) compDiv(ocs.s); }

//============================================================= // mVec3::xformVecTo void mVec3::xformVecTo(const mVec3& vec, const mOCS& ocs) { assert(&vec != &ocs.o); set(vec);

if (ocs.type & mOCS::FRAME) xformTo(*this, ocs.f);

if (ocs.type & mOCS::SCALE) compDiv(ocs.s); }

//============================================================= // mVec3::xformFrom void mVec3::xformFrom(const mVec3& vec, const mOCS& ocs) { assert(&vec != &ocs.o); set(vec);

if (ocs.type & mOCS::SCALE) compMult(ocs.s); if (ocs.type & mOCS::FRAME) xformFrom(*this, ocs.f); if (ocs.type & mOCS::ORIGIN) add(ocs.o); }

//============================================================= // mVec3::xformVecFrom void mVec3::xformVecFrom(const mVec3& vec, const mOCS& ocs) { assert(&vec != &ocs.o); set(vec);

if (ocs.type & mOCS::SCALE) compMult(ocs.s); if (ocs.type & mOCS::FRAME) xformFrom(*this, ocs.f); }

//**************************************************************************** //** END MODULE mVec.cpp //****************************************************************************

The zip file viewer built into the Developer Toolbox made use of the zlib library, as well as the zlibdll source additions.

 

Copyright 1999-2008 (C) FLIPCODE.COM and/or the original content author(s). All rights reserved.
Please read our Terms, Conditions, and Privacy information.