#pragma once #include #include #include namespace gz { /** * @brief Class containing 2 numbers */ template class vec2 { public: // Constructors /// Default constructor vec2() : x(0), y(0) {}; /// Create a vec2 from n n template vec2(N0 n0, N1 n1) : x(static_cast(n0)), y(static_cast(n1)) {}; /// Create a vec2 from vec2 template vec2(const vec2& v0) : x(static_cast(v0.x)), y(static_cast(v0.y)) {}; // Values T x; T y; // Assignment /// component-wise assignment template void operator=(const vec2& other) { x = static_cast(other.x); y = static_cast(other.y); }; template void operator=(const N& other) { x = static_cast(other); y = static_cast(other); }; // Arithmetic // Vectorial /// component-wise + template vec2 operator+(const vec2& other) const { return vec2(x + static_cast(other.x), y + static_cast(other.y)); }; /// component-wise - template vec2 operator-(const vec2& other) const { return vec2(x - static_cast(other.x), y - static_cast(other.y)); }; /// component-wise * template vec2 operator*(const vec2& other) const { return vec2(x * static_cast(other.x), y * static_cast(other.y)); }; /// component-wise / template vec2 operator/(const vec2& other) const { return vec2(x / static_cast(other.x), y / static_cast(other.y)); }; /// component-wise % template vec2 operator%(const vec2& other) const { return vec2(x % static_cast(other.x), y % static_cast(other.y)); }; /// component-wise assignment+= template void operator+=(const vec2& other) { x += static_cast(other.x); y += static_cast(other.y); }; /// component-wise assignment-= template void operator-=(const vec2& other) { x -= static_cast(other.x); y -= static_cast(other.y); }; /// component-wise assignment*= template void operator*=(const vec2& other) { x *= static_cast(other.x); y *= static_cast(other.y); }; /// component-wise assignment/= template void operator/=(const vec2& other) { x /= static_cast(other.x); y /= static_cast(other.y); }; /// component-wise assignment%= template void operator%=(const vec2& other) { x %= static_cast(other.x); y %= static_cast(other.y); }; // Scalar /// component-wise + template vec2 operator+(const N& other) const { return vec2(x + static_cast(other.x), y + static_cast(other.y)); }; /// component-wise - template vec2 operator-(const N& other) const { return vec2(x - static_cast(other.x), y - static_cast(other.y)); }; /// component-wise * template vec2 operator*(const N& other) const { return vec2(x * static_cast(other.x), y * static_cast(other.y)); }; /// component-wise / template vec2 operator/(const N& other) const { return vec2(x / static_cast(other.x), y / static_cast(other.y)); }; /// component-wise % template vec2 operator%(const N& other) const { return vec2(x % static_cast(other.x), y % static_cast(other.y)); }; /// component-wise assignment+= template void operator+=(const N& other) { x += static_cast(other.x); y += static_cast(other.y); }; /// component-wise assignment-= template void operator-=(const N& other) { x -= static_cast(other.x); y -= static_cast(other.y); }; /// component-wise assignment*= template void operator*=(const N& other) { x *= static_cast(other.x); y *= static_cast(other.y); }; /// component-wise assignment/= template void operator/=(const N& other) { x /= static_cast(other.x); y /= static_cast(other.y); }; /// component-wise assignment%= template void operator%=(const N& other) { x %= static_cast(other.x); y %= static_cast(other.y); }; // Comparison // Vectorial /// component-wise comparison == (and) template bool operator==(const vec2& other) const { return x == other.x and y == other.y; }; /// component-wise comparison < (and) template bool operator<(const vec2& other) const { return x < other.x and y < other.y; }; /// component-wise comparison > (and) template bool operator>(const vec2& other) const { return x > other.x and y > other.y; }; /// component-wise comparison != (and) template bool operator!=(const vec2& other) const { return x == other.x and y == other.y; }; /// component-wise comparison <= (and) template bool operator<=(const vec2& other) const { return x > other.x and y > other.y; }; /// component-wise comparison >= (and) template bool operator>=(const vec2& other) const { return x < other.x and y < other.y; }; // Scalar /// component-wise comparison == (and) template bool operator==(const N& other) const { return x == other.x and y == other.y; }; /// component-wise comparison < (and) template bool operator<(const N& other) const { return x < other.x and y < other.y; }; /// component-wise comparison > (and) template bool operator>(const N& other) const { return x > other.x and y > other.y; }; /// component-wise comparison != (and) template bool operator!=(const N& other) const { return x == other.x and y == other.y; }; /// component-wise comparison <= (and) template bool operator<=(const N& other) const { return x > other.x and y > other.y; }; /// component-wise comparison >= (and) template bool operator>=(const N& other) const { return x < other.x and y < other.y; }; // Functional /// Returns the absolute value of the vector inline float abs() const { return std::sqrt(static_cast(x * x) + static_cast(y * y)); };/// Returns x/y inline float ratio() const { return static_cast(x) / y; };/// Returns y/x inline float inverseRatio() const { return static_cast(y) / x; };/// Returns the min of the components inline T min() const { return std::min_element(cbegin(), cend()); }; /// Returns the max of the components inline T max() const { return std::max_element(cbegin(), cend()); }; /// Scalar product template inline vec2 dot(const vec2& other) { return vec2(x * static_cast(other.x) + y * static_cast(other.y)); }; // Utility std::string to_string() const { return "(" + std::to_string(x) + ", " + std::to_string(y) + ")"; }; struct Iterator { public: using value_type = T; Iterator() : ptr(nullptr) {}; Iterator(T* ptr) : ptr(ptr) {}; T& operator*() { return *ptr; }; Iterator& operator=(const Iterator& other) { ptr = other.ptr; return *this; }; Iterator& operator++() { ptr += sizeof(T); return *this; }; Iterator operator++(int) { auto copy = *this; ptr += sizeof(T); return copy; }; friend int operator-(Iterator lhs, Iterator rhs) { return lhs.ptr - rhs.ptr; }; bool operator==(const Iterator& other) const { return ptr == other.ptr; }; // bool operator!=(const Iterator& other) const { return ptr != other.ptr; }; private: T* ptr; }; const Iterator cbegin() const { return Iterator(&x); }; const Iterator cend() const { return Iterator(&y); }; const Iterator begin() const { return Iterator(&x); }; const Iterator end() const { return Iterator(&y); }; }; // vec2 /** * @brief Class containing 3 numbers */ template class vec3 { public: // Constructors /// Default constructor vec3() : x(0), y(0), z(0) {}; /// Create a vec3 from n n n template vec3(N0 n0, N1 n1, N2 n2) : x(static_cast(n0)), y(static_cast(n1)), z(static_cast(n2)) {}; /// Create a vec3 from n vec2 template vec3(N0 n0, const vec2& v0) : x(static_cast(n0)), y(static_cast(v0.x)), z(static_cast(v0.y)) {}; /// Create a vec3 from vec2 n template vec3(const vec2& v0, N0 n0) : x(static_cast(v0.x)), y(static_cast(v0.y)), z(static_cast(n0)) {}; /// Create a vec3 from vec3 template vec3(const vec3& v0) : x(static_cast(v0.x)), y(static_cast(v0.y)), z(static_cast(v0.z)) {}; // Values T x; T y; T z; // Assignment /// component-wise assignment template void operator=(const vec3& other) { x = static_cast(other.x); y = static_cast(other.y); z = static_cast(other.z); }; template void operator=(const N& other) { x = static_cast(other); y = static_cast(other); z = static_cast(other); }; // Arithmetic // Vectorial /// component-wise + template vec3 operator+(const vec3& other) const { return vec3(x + static_cast(other.x), y + static_cast(other.y), z + static_cast(other.z)); }; /// component-wise - template vec3 operator-(const vec3& other) const { return vec3(x - static_cast(other.x), y - static_cast(other.y), z - static_cast(other.z)); }; /// component-wise * template vec3 operator*(const vec3& other) const { return vec3(x * static_cast(other.x), y * static_cast(other.y), z * static_cast(other.z)); }; /// component-wise / template vec3 operator/(const vec3& other) const { return vec3(x / static_cast(other.x), y / static_cast(other.y), z / static_cast(other.z)); }; /// component-wise % template vec3 operator%(const vec3& other) const { return vec3(x % static_cast(other.x), y % static_cast(other.y), z % static_cast(other.z)); }; /// component-wise assignment+= template void operator+=(const vec3& other) { x += static_cast(other.x); y += static_cast(other.y); z += static_cast(other.z); }; /// component-wise assignment-= template void operator-=(const vec3& other) { x -= static_cast(other.x); y -= static_cast(other.y); z -= static_cast(other.z); }; /// component-wise assignment*= template void operator*=(const vec3& other) { x *= static_cast(other.x); y *= static_cast(other.y); z *= static_cast(other.z); }; /// component-wise assignment/= template void operator/=(const vec3& other) { x /= static_cast(other.x); y /= static_cast(other.y); z /= static_cast(other.z); }; /// component-wise assignment%= template void operator%=(const vec3& other) { x %= static_cast(other.x); y %= static_cast(other.y); z %= static_cast(other.z); }; // Scalar /// component-wise + template vec3 operator+(const N& other) const { return vec3(x + static_cast(other.x), y + static_cast(other.y), z + static_cast(other.z)); }; /// component-wise - template vec3 operator-(const N& other) const { return vec3(x - static_cast(other.x), y - static_cast(other.y), z - static_cast(other.z)); }; /// component-wise * template vec3 operator*(const N& other) const { return vec3(x * static_cast(other.x), y * static_cast(other.y), z * static_cast(other.z)); }; /// component-wise / template vec3 operator/(const N& other) const { return vec3(x / static_cast(other.x), y / static_cast(other.y), z / static_cast(other.z)); }; /// component-wise % template vec3 operator%(const N& other) const { return vec3(x % static_cast(other.x), y % static_cast(other.y), z % static_cast(other.z)); }; /// component-wise assignment+= template void operator+=(const N& other) { x += static_cast(other.x); y += static_cast(other.y); z += static_cast(other.z); }; /// component-wise assignment-= template void operator-=(const N& other) { x -= static_cast(other.x); y -= static_cast(other.y); z -= static_cast(other.z); }; /// component-wise assignment*= template void operator*=(const N& other) { x *= static_cast(other.x); y *= static_cast(other.y); z *= static_cast(other.z); }; /// component-wise assignment/= template void operator/=(const N& other) { x /= static_cast(other.x); y /= static_cast(other.y); z /= static_cast(other.z); }; /// component-wise assignment%= template void operator%=(const N& other) { x %= static_cast(other.x); y %= static_cast(other.y); z %= static_cast(other.z); }; // Comparison // Vectorial /// component-wise comparison == (and) template bool operator==(const vec3& other) const { return x == other.x and y == other.y and z == other.z; }; /// component-wise comparison < (and) template bool operator<(const vec3& other) const { return x < other.x and y < other.y and z < other.z; }; /// component-wise comparison > (and) template bool operator>(const vec3& other) const { return x > other.x and y > other.y and z > other.z; }; /// component-wise comparison != (and) template bool operator!=(const vec3& other) const { return x == other.x and y == other.y and z == other.z; }; /// component-wise comparison <= (and) template bool operator<=(const vec3& other) const { return x > other.x and y > other.y and z > other.z; }; /// component-wise comparison >= (and) template bool operator>=(const vec3& other) const { return x < other.x and y < other.y and z < other.z; }; // Scalar /// component-wise comparison == (and) template bool operator==(const N& other) const { return x == other.x and y == other.y and z == other.z; }; /// component-wise comparison < (and) template bool operator<(const N& other) const { return x < other.x and y < other.y and z < other.z; }; /// component-wise comparison > (and) template bool operator>(const N& other) const { return x > other.x and y > other.y and z > other.z; }; /// component-wise comparison != (and) template bool operator!=(const N& other) const { return x == other.x and y == other.y and z == other.z; }; /// component-wise comparison <= (and) template bool operator<=(const N& other) const { return x > other.x and y > other.y and z > other.z; }; /// component-wise comparison >= (and) template bool operator>=(const N& other) const { return x < other.x and y < other.y and z < other.z; }; // Functional /// Returns the absolute value of the vector inline float abs() const { return std::sqrt(static_cast(x * x) + static_cast(y * y) + static_cast(z * z)); };/// Returns the min of the components inline T min() const { return std::min_element(cbegin(), cend()); }; /// Returns the max of the components inline T max() const { return std::max_element(cbegin(), cend()); }; /// Scalar product template inline vec3 dot(const vec3& other) { return vec3(x * static_cast(other.x) + y * static_cast(other.y) + z * static_cast(other.z)); }; // Utility std::string to_string() const { return "(" + std::to_string(x) + ", " + std::to_string(y) + ", " + std::to_string(z) + ")"; }; struct Iterator { public: using value_type = T; Iterator() : ptr(nullptr) {}; Iterator(T* ptr) : ptr(ptr) {}; T& operator*() { return *ptr; }; Iterator& operator=(const Iterator& other) { ptr = other.ptr; return *this; }; Iterator& operator++() { ptr += sizeof(T); return *this; }; Iterator operator++(int) { auto copy = *this; ptr += sizeof(T); return copy; }; friend int operator-(Iterator lhs, Iterator rhs) { return lhs.ptr - rhs.ptr; }; bool operator==(const Iterator& other) const { return ptr == other.ptr; }; // bool operator!=(const Iterator& other) const { return ptr != other.ptr; }; private: T* ptr; }; const Iterator cbegin() const { return Iterator(&x); }; const Iterator cend() const { return Iterator(&z); }; const Iterator begin() const { return Iterator(&x); }; const Iterator end() const { return Iterator(&z); }; }; // vec3 /** * @brief Class containing 4 numbers */ template class vec4 { public: // Constructors /// Default constructor vec4() : x(0), y(0), z(0), w(0) {}; /// Create a vec4 from n n n n template vec4(N0 n0, N1 n1, N2 n2, N3 n3) : x(static_cast(n0)), y(static_cast(n1)), z(static_cast(n2)), w(static_cast(n3)) {}; /// Create a vec4 from n n vec2 template vec4(N0 n0, N1 n1, const vec2& v0) : x(static_cast(n0)), y(static_cast(n1)), z(static_cast(v0.x)), w(static_cast(v0.y)) {}; /// Create a vec4 from n vec2 n template vec4(N0 n0, const vec2& v0, N1 n1) : x(static_cast(n0)), y(static_cast(v0.x)), z(static_cast(v0.y)), w(static_cast(n1)) {}; /// Create a vec4 from n vec3 template vec4(N0 n0, const vec3& v0) : x(static_cast(n0)), y(static_cast(v0.x)), z(static_cast(v0.y)), w(static_cast(v0.z)) {}; /// Create a vec4 from vec2 n n template vec4(const vec2& v0, N0 n0, N1 n1) : x(static_cast(v0.x)), y(static_cast(v0.y)), z(static_cast(n0)), w(static_cast(n1)) {}; /// Create a vec4 from vec2 vec2 template vec4(const vec2& v0, const vec2& v1) : x(static_cast(v0.x)), y(static_cast(v0.y)), z(static_cast(v1.x)), w(static_cast(v1.y)) {}; /// Create a vec4 from vec3 n template vec4(const vec3& v0, N0 n0) : x(static_cast(v0.x)), y(static_cast(v0.y)), z(static_cast(v0.z)), w(static_cast(n0)) {}; /// Create a vec4 from vec4 template vec4(const vec4& v0) : x(static_cast(v0.x)), y(static_cast(v0.y)), z(static_cast(v0.z)), w(static_cast(v0.w)) {}; // Values T x; T y; T z; T w; // Assignment /// component-wise assignment template void operator=(const vec4& other) { x = static_cast(other.x); y = static_cast(other.y); z = static_cast(other.z); w = static_cast(other.w); }; template void operator=(const N& other) { x = static_cast(other); y = static_cast(other); z = static_cast(other); w = static_cast(other); }; // Arithmetic // Vectorial /// component-wise + template vec4 operator+(const vec4& other) const { return vec4(x + static_cast(other.x), y + static_cast(other.y), z + static_cast(other.z), w + static_cast(other.w)); }; /// component-wise - template vec4 operator-(const vec4& other) const { return vec4(x - static_cast(other.x), y - static_cast(other.y), z - static_cast(other.z), w - static_cast(other.w)); }; /// component-wise * template vec4 operator*(const vec4& other) const { return vec4(x * static_cast(other.x), y * static_cast(other.y), z * static_cast(other.z), w * static_cast(other.w)); }; /// component-wise / template vec4 operator/(const vec4& other) const { return vec4(x / static_cast(other.x), y / static_cast(other.y), z / static_cast(other.z), w / static_cast(other.w)); }; /// component-wise % template vec4 operator%(const vec4& other) const { return vec4(x % static_cast(other.x), y % static_cast(other.y), z % static_cast(other.z), w % static_cast(other.w)); }; /// component-wise assignment+= template void operator+=(const vec4& other) { x += static_cast(other.x); y += static_cast(other.y); z += static_cast(other.z); w += static_cast(other.w); }; /// component-wise assignment-= template void operator-=(const vec4& other) { x -= static_cast(other.x); y -= static_cast(other.y); z -= static_cast(other.z); w -= static_cast(other.w); }; /// component-wise assignment*= template void operator*=(const vec4& other) { x *= static_cast(other.x); y *= static_cast(other.y); z *= static_cast(other.z); w *= static_cast(other.w); }; /// component-wise assignment/= template void operator/=(const vec4& other) { x /= static_cast(other.x); y /= static_cast(other.y); z /= static_cast(other.z); w /= static_cast(other.w); }; /// component-wise assignment%= template void operator%=(const vec4& other) { x %= static_cast(other.x); y %= static_cast(other.y); z %= static_cast(other.z); w %= static_cast(other.w); }; // Scalar /// component-wise + template vec4 operator+(const N& other) const { return vec4(x + static_cast(other.x), y + static_cast(other.y), z + static_cast(other.z), w + static_cast(other.w)); }; /// component-wise - template vec4 operator-(const N& other) const { return vec4(x - static_cast(other.x), y - static_cast(other.y), z - static_cast(other.z), w - static_cast(other.w)); }; /// component-wise * template vec4 operator*(const N& other) const { return vec4(x * static_cast(other.x), y * static_cast(other.y), z * static_cast(other.z), w * static_cast(other.w)); }; /// component-wise / template vec4 operator/(const N& other) const { return vec4(x / static_cast(other.x), y / static_cast(other.y), z / static_cast(other.z), w / static_cast(other.w)); }; /// component-wise % template vec4 operator%(const N& other) const { return vec4(x % static_cast(other.x), y % static_cast(other.y), z % static_cast(other.z), w % static_cast(other.w)); }; /// component-wise assignment+= template void operator+=(const N& other) { x += static_cast(other.x); y += static_cast(other.y); z += static_cast(other.z); w += static_cast(other.w); }; /// component-wise assignment-= template void operator-=(const N& other) { x -= static_cast(other.x); y -= static_cast(other.y); z -= static_cast(other.z); w -= static_cast(other.w); }; /// component-wise assignment*= template void operator*=(const N& other) { x *= static_cast(other.x); y *= static_cast(other.y); z *= static_cast(other.z); w *= static_cast(other.w); }; /// component-wise assignment/= template void operator/=(const N& other) { x /= static_cast(other.x); y /= static_cast(other.y); z /= static_cast(other.z); w /= static_cast(other.w); }; /// component-wise assignment%= template void operator%=(const N& other) { x %= static_cast(other.x); y %= static_cast(other.y); z %= static_cast(other.z); w %= static_cast(other.w); }; // Comparison // Vectorial /// component-wise comparison == (and) template bool operator==(const vec4& other) const { return x == other.x and y == other.y and z == other.z and w == other.w; }; /// component-wise comparison < (and) template bool operator<(const vec4& other) const { return x < other.x and y < other.y and z < other.z and w < other.w; }; /// component-wise comparison > (and) template bool operator>(const vec4& other) const { return x > other.x and y > other.y and z > other.z and w > other.w; }; /// component-wise comparison != (and) template bool operator!=(const vec4& other) const { return x == other.x and y == other.y and z == other.z and w == other.w; }; /// component-wise comparison <= (and) template bool operator<=(const vec4& other) const { return x > other.x and y > other.y and z > other.z and w > other.w; }; /// component-wise comparison >= (and) template bool operator>=(const vec4& other) const { return x < other.x and y < other.y and z < other.z and w < other.w; }; // Scalar /// component-wise comparison == (and) template bool operator==(const N& other) const { return x == other.x and y == other.y and z == other.z and w == other.w; }; /// component-wise comparison < (and) template bool operator<(const N& other) const { return x < other.x and y < other.y and z < other.z and w < other.w; }; /// component-wise comparison > (and) template bool operator>(const N& other) const { return x > other.x and y > other.y and z > other.z and w > other.w; }; /// component-wise comparison != (and) template bool operator!=(const N& other) const { return x == other.x and y == other.y and z == other.z and w == other.w; }; /// component-wise comparison <= (and) template bool operator<=(const N& other) const { return x > other.x and y > other.y and z > other.z and w > other.w; }; /// component-wise comparison >= (and) template bool operator>=(const N& other) const { return x < other.x and y < other.y and z < other.z and w < other.w; }; // Functional /// Returns the absolute value of the vector inline float abs() const { return std::sqrt(static_cast(x * x) + static_cast(y * y) + static_cast(z * z) + static_cast(w * w)); };/// Returns the min of the components inline T min() const { return std::min_element(cbegin(), cend()); }; /// Returns the max of the components inline T max() const { return std::max_element(cbegin(), cend()); }; /// Scalar product template inline vec4 dot(const vec4& other) { return vec4(x * static_cast(other.x) + y * static_cast(other.y) + z * static_cast(other.z) + w * static_cast(other.w)); }; // Utility std::string to_string() const { return "(" + std::to_string(x) + ", " + std::to_string(y) + ", " + std::to_string(z) + ", " + std::to_string(w) + ")"; }; struct Iterator { public: using value_type = T; Iterator() : ptr(nullptr) {}; Iterator(T* ptr) : ptr(ptr) {}; T& operator*() { return *ptr; }; Iterator& operator=(const Iterator& other) { ptr = other.ptr; return *this; }; Iterator& operator++() { ptr += sizeof(T); return *this; }; Iterator operator++(int) { auto copy = *this; ptr += sizeof(T); return copy; }; friend int operator-(Iterator lhs, Iterator rhs) { return lhs.ptr - rhs.ptr; }; bool operator==(const Iterator& other) const { return ptr == other.ptr; }; // bool operator!=(const Iterator& other) const { return ptr != other.ptr; }; private: T* ptr; }; const Iterator cbegin() const { return Iterator(&x); }; const Iterator cend() const { return Iterator(&w); }; const Iterator begin() const { return Iterator(&x); }; const Iterator end() const { return Iterator(&w); }; }; // vec4 using vec2f = vec2; using vec2d = vec2; using vec2i = vec2; using vec2u = vec2; using vec3f = vec3; using vec3d = vec3; using vec3i = vec3; using vec3u = vec3; using vec4f = vec4; using vec4d = vec4; using vec4i = vec4; using vec4u = vec4; } // namespace gz