3D float scalar

class S4f;

// 3D float scalar.
class RVAPI S3f
{
public:
    // X coordinate.
    float x;

    // Y coordinate.
    float y;

    // Z coordinate.
    float z;

    // Check if all coordinates are zero.
    bool operator ! () const { return !x && !y && !z; }

    // Get scalar with negated coordnates.
    S3f operator - () const { return S3f(-x, -y, -z); }

    // Get sum of scalars.
    S3f operator + (const S3f &scalar) const { return S3f(x + scalar.x, y + scalar.y, z + scalar.z); }

    // Get difference of scalars.
    S3f operator - (const S3f &scalar) const { return S3f(x - scalar.x, y - scalar.y, z - scalar.z); }

    // Get product of scalars.
    S3f operator * (const S3f &scalar) const { return S3f(x * scalar.x, y * scalar.y, z * scalar.z); }

    // Get division of scalars.
    S3f operator / (const S3f &scalar) const { return S3f(x / scalar.x, y / scalar.y, z / scalar.z); }

    // Add [scalar] to this scalar.
    S3f &operator += (const S3f &scalar) { return *this = *this + scalar; }

    // Subtract [scalar] from this scalar.
    S3f &operator -= (const S3f &scalar) { return *this = *this - scalar; }

    // Multiply [scalar] and this scalar.
    S3f &operator *= (const S3f &scalar) { return *this = *this * scalar; }

    // Divide [scalar] into this scalar.
    S3f &operator /= (const S3f &scalar) { return *this = *this / scalar; }

    // Get dot product of scalars.
    float Dot(const S3f &scalar) const { return x * scalar.x + y * scalar.y + z * scalar.z; }

    // Get cross product of scalars.
    S3f Cross(const S3f &scalar) const 
    {
        return S3f(y * scalar.z - z * scalar.y, z * scalar.x - x * scalar.z, x * scalar.y - y * scalar.x);
    }

    // Get angle between scalars.
    float Angle(const S3f &scalar) const;

    // Get angle of scalar on X/Y plane.
    float XYAngle() const;

    // Get angle of scalar on X/Z plane.
    float XZAngle() const;

    // Get angle of scalar on Y/Z plane.
    float YZAngle() const;

    // Get magnitude squared of scalar.
    float MagSqr() const;

    // Get magnitued of scalar.
    float Mag() const;

    // Get mininum of scalars.
    S3f Min(const S3f &scalar) const
    {
        return S3f(scalar.x < x ? scalar.x : x, scalar.y < y ? scalar.y : y, scalar.z < z ? scalar.z : z);
    }

    // Get maximum of scalars.
    S3f Max(const S3f &scalar) const
    {
        return S3f(scalar.x > x ? scalar.x : x, scalar.y > y ? scalar.y : y, scalar.z < z ? scalar.z : z);
    }

    // Normalized scalar.
    S3f &Normalize();

    // Construct scalar from coordinates.
    S3f(float x, float y, float z) : x(x), y(y), z(z) {}

    // Construct scalar from single value.
    S3f(float n = 0) : x(n), y(n), z(n) {}

    // Construct scalar from S4f scalar.
    S3f(const S4f &scalar);

    // Destructor.
    ~S3f() {}
};