diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 82d362f..19ed296 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -9,10 +9,10 @@ jobs: strategy: fail-fast: false matrix: - os: [ubuntu-22.04, windows-latest] + os: [ubuntu-24.04, windows-latest] build: [Release] arch: [x86, x64] - cxx: [g++, clang++-17, ClangCl, v143] + cxx: [g++-14, clang++-19, ClangCl, v143] feature: [ [NoSIMD, 16, ' ', '/arch:IA32'], [SSE2, 16, '-msse2', '/arch:SSE2'], @@ -26,14 +26,14 @@ jobs: ] exclude: - - os: ubuntu-22.04 + - os: ubuntu-24.04 cxx: v143 - - os: ubuntu-22.04 + - os: ubuntu-24.04 cxx: ClangCl - os: windows-latest - cxx: g++ + cxx: g++-14 - os: windows-latest - cxx: clang++-17 + cxx: clang++-19 - arch: x64 cxx: ClangCl @@ -97,14 +97,14 @@ jobs: - feature: [AVX512, 64, '-mavx512f', '/arch:AVX512'] include: - - cxx: g++ - c: gcc - - cxx: clang++-17 - c: clang-17 - - os: ubuntu-22.04 + - cxx: g++-14 + c: gcc-14 + - cxx: clang++-19 + c: clang-19 + - os: ubuntu-24.04 arch: x86 cmake_args: "-DCMAKE_CXX_FLAGS=-m32" - - os: ubuntu-22.04 + - os: ubuntu-24.04 arch: x64 cmake_args: "-DCMAKE_CXX_FLAGS=-m64" - os: windows-latest @@ -120,21 +120,28 @@ jobs: - name: Clone uses: actions/checkout@v4 - - if: matrix.os == 'ubuntu-22.04' && matrix.arch == 'x86' + - if: matrix.os == 'ubuntu-24.04' && matrix.arch == 'x86' name: Prepare Linux for cross-compilation run: | sudo apt update - sudo apt install g++-multilib + sudo apt install g++-14-multilib - - if: matrix.cxx == 'clang++-17' - name: Installing Clang 17 + - if: matrix.cxx == 'g++-14' + name: Installing G++ 14 + run: | + sudo apt update + sudo apt install gcc-14 g++-14 + + - if: matrix.cxx == 'clang++-19' + name: Installing Clang 19 run: | wget -O - https://apt.llvm.org/llvm-snapshot.gpg.key | sudo apt-key add - - sudo apt-add-repository "deb http://apt.llvm.org/jammy/ llvm-toolchain-jammy-17 main" + sudo apt-add-repository "deb http://apt.llvm.org/noble/ llvm-toolchain-noble-19 main" sudo apt update - sudo apt install clang-17 + sudo apt install gcc-14 g++-14 # clang-19 needs stdc++14.2 see https://github.com/llvm/llvm-project/issues/102336 + sudo apt install clang-19 - - if: matrix.os == 'ubuntu-22.04' + - if: matrix.os == 'ubuntu-24.04' name: Configure (Linux) run: > mkdir build && cd build && cmake .. diff --git a/CMakeLists.txt b/CMakeLists.txt index 73c6a8f..843f5b1 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -13,15 +13,15 @@ if(PROJECT_IS_TOP_LEVEL OR NOT LANGULUS) include(LangulusUtilities.cmake) # Add Langulus::Core/Logger/RTTI/SIMD/Fractalloc/Anyness/Flow libraries - fetch_langulus_module(Core GIT_TAG 393d95b6ab13fc5846bda8a3044e4ca62f02fd5a) - fetch_langulus_module(Logger GIT_TAG 69626cd4c738195df0929a1cd867317422506e61) - fetch_langulus_module(RTTI GIT_TAG 720e675b1ea114156c309fe44871e03557e0a64f) + fetch_langulus_module(Core GIT_TAG 35756f11d2f9c475f27b094b8d4c82cd453969fc) + fetch_langulus_module(Logger GIT_TAG dafbeb825071ec60d8403254143f75606151a7e6) + fetch_langulus_module(RTTI GIT_TAG fc49750884ac943dff4261ac5b8dfb2c148423d7) if(LANGULUS_FEATURE_MANAGED_MEMORY) - fetch_langulus_module(Fractalloc GIT_TAG b4917194b18c139969fb9d0a14bf993ee5f2582a) + fetch_langulus_module(Fractalloc GIT_TAG 66408e8557b1bb3c80615909129342bcebd3fb9f) endif() - fetch_langulus_module(SIMD GIT_TAG 6611cf422e3c8157b88c086f30966afbf4e7dc6c) - fetch_langulus_module(Anyness GIT_TAG 7e433990052d2cf4c1dbd73afdddb1c697d92c56) - fetch_langulus_module(Flow GIT_TAG 4a0b0f349e5a6f543114b9269f96f55adc025a60) + fetch_langulus_module(SIMD GIT_TAG ead5493049e2800b4c3c02d385c0c6314efac69c) + fetch_langulus_module(Anyness GIT_TAG 46a6513d6bcf3d532e9bf746b50d1299692eb96a) + fetch_langulus_module(Flow GIT_TAG 06000427afccf13016738140d09850f0b8cf837b) endif() file(GLOB_RECURSE @@ -31,7 +31,7 @@ file(GLOB_RECURSE ) # Build and install Math library -add_library(LangulusMath ${LANGULUS_LIBRARY_TYPE} +add_langulus_library(LangulusMath $ $ $<$:$> diff --git a/include/Math/Number.hpp b/include/Math/Number.hpp index 6d34bdb..9de389b 100644 --- a/include/Math/Number.hpp +++ b/include/Math/Number.hpp @@ -7,3 +7,4 @@ /// #pragma once #include "../../source/Numbers/TNumber.inl" +#include "../../source/Numbers/Infinity.hpp" diff --git a/source/Adaptive.hpp b/source/Adaptive.hpp index 8001806..8140bce 100644 --- a/source/Adaptive.hpp +++ b/source/Adaptive.hpp @@ -41,25 +41,6 @@ namespace Langulus concept NotAdaptive = ((not Adaptive) and ...); } - /// Custom name generator at compile-time for adaptive types - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::Adaptive; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset = 0; - - // Write prefix - for (auto i : "Adaptive") - name[offset++] = i; - --offset; - - // Write the rest - for (auto i : NameOf()) - name[offset++] = i; - return name; - } - namespace Math { @@ -69,8 +50,26 @@ namespace Langulus /// template struct Adaptive : A::Adaptive { + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset = 0; + + // Write prefix + for (auto i : "Adaptive") + name[offset++] = i; + --offset; + + // Write the rest + for (auto i : NameOf()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; - LANGULUS(NAME) CustomNameOf::Generate(); LANGULUS(TYPED) T; LANGULUS_BASES(A::Adaptive); LANGULUS_CONVERTS_TO(Flow::Code); @@ -80,6 +79,7 @@ namespace Langulus // The level in which the data is adapted to Level mLevel {}; + public: constexpr Adaptive() noexcept = default; constexpr Adaptive(const T& data, Level level = {}) noexcept : mValue {data} diff --git a/source/Colors/TColor.cpp b/source/Colors/TColor.cpp new file mode 100644 index 0000000..8f8bec0 --- /dev/null +++ b/source/Colors/TColor.cpp @@ -0,0 +1,53 @@ +/// +/// Langulus::Math +/// Copyright (c) 2014 Dimo Markov +/// Part of the Langulus framework, see https://langulus.com +/// +/// SPDX-License-Identifier: GPL-3.0-or-later +/// +#include "TColor.inl" + + +namespace Langulus::Math +{ + + /// Register all commonly used color types and constants, so they can be + /// instantiated from scripts + void RegisterColors() { + // Types + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + + (void) MetaOf(); + (void) MetaOf(); + + // Constants + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + } + +} // namespace Langulus::Math \ No newline at end of file diff --git a/source/Colors/TColor.hpp b/source/Colors/TColor.hpp index 4f4dfe5..aa7bcb9 100644 --- a/source/Colors/TColor.hpp +++ b/source/Colors/TColor.hpp @@ -13,6 +13,9 @@ namespace Langulus { namespace Math { + + LANGULUS_API(MATH) extern void RegisterColors(); + template struct TColor; @@ -81,43 +84,6 @@ namespace Langulus } // namespace Langulus::A - - /// Custom name generator at compile-time for colors - template - constexpr auto CustomName(Of>&&) noexcept { - constexpr auto defaultClassName = RTTI::LastCppNameOf>(); - ::std::array name {}; - ::std::size_t offset {}; - - // Write prefix - switch (T::MemberCount) { - case 2: - for (auto i : "Grayscale") - name[offset++] = i; - break; - case 3: - for (auto i : "RGB") - name[offset++] = i; - break; - case 4: - for (auto i : "RGBA") - name[offset++] = i; - break; - } - - // Write suffix - --offset; - if constexpr (not CT::Same, ::std::uint8_t>) { - if constexpr (CT::Same, float>) - name[offset++] = 'f'; - else if constexpr (CT::Same, double>) - name[offset++] = 'd'; - else for (auto i : SuffixOf>()) - name[offset++] = i; - } - return name; - } - namespace Math { @@ -143,22 +109,60 @@ namespace Langulus "Invalid number of channels"); static constexpr bool CTTI_ColorTrait = true; - LANGULUS(NAME) CustomNameOf::Generate(); + private: + /// Custom name generator at compile-time for colors + static constexpr auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + // Write prefix + switch (T::MemberCount) { + case 2: + for (auto i : "Grayscale") + name[offset++] = i; + break; + case 3: + for (auto i : "RGB") + name[offset++] = i; + break; + case 4: + for (auto i : "RGBA") + name[offset++] = i; + break; + } + + // Write suffix + --offset; + if constexpr (not CT::Same, ::std::uint8_t>) { + if constexpr (CT::Same, float>) + name[offset++] = 'f'; + else if constexpr (CT::Same, double>) + name[offset++] = 'd'; + else for (auto i : SuffixOf>()) + name[offset++] = i; + } + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS_BASES( A::ColorOfSize, A::ColorOfType>, T ); + public: using T::T; constexpr TColor(const CT::Vector auto&) noexcept; constexpr TColor(Logger::Color); using T::Get; - using T::operator =; + template - constexpr TColor& operator = (const TColorComponent&) noexcept; + constexpr auto operator = (const TColorComponent&) noexcept -> TColor&; operator Flow::Code() const; operator Logger::Color() const; diff --git a/source/Colors/TColor.inl b/source/Colors/TColor.inl index d3ff2f4..2699766 100644 --- a/source/Colors/TColor.inl +++ b/source/Colors/TColor.inl @@ -180,10 +180,10 @@ namespace Langulus::Math /// Copy a channel TEMPLATE() template - constexpr TColor& TColor::operator = (const TColorComponent& com) noexcept { + constexpr auto TColor::operator = (const TColorComponent& com) noexcept -> TColor& { static_assert(D::Index < MemberCount, "Index out of bounds"); Get(D::Index) = Adapt(com.mValue); - return *this; + return *this; } /// Serialize the color to flow code @@ -202,7 +202,8 @@ namespace Langulus::Math result += Code::Operator::CloseScope; return Abandon(result); } - else return T::template Serialize(); + else return T::template Serialize(); + } /// Covert to a console color @@ -264,28 +265,54 @@ namespace Langulus::Math } // namespace Langulus::Math -namespace Langulus +namespace Langulus::Colors { - namespace Colors - { - using ::Langulus::Math::RGBA; + using ::Langulus::Math::RGBA; + + constexpr RGBA White { 255, 255, 255, 255 }; + constexpr RGBA Black { 0, 0, 0, 255 }; + constexpr RGBA Grey { 127, 127, 127, 255 }; + constexpr RGBA Red { 255, 0, 0, 255 }; + constexpr RGBA Green { 0, 255, 0, 255 }; + constexpr RGBA DarkGreen { 0, 128, 0, 255 }; + constexpr RGBA Blue { 0, 0, 255, 255 }; + constexpr RGBA DarkBlue { 0, 0, 128, 255 }; + constexpr RGBA Cyan { 128, 128, 255, 255 }; + constexpr RGBA DarkCyan { 80, 80, 128, 255 }; + constexpr RGBA Orange { 128, 128, 0, 255 }; + constexpr RGBA Yellow { 255, 255, 0, 255 }; + constexpr RGBA Purple { 255, 0, 255, 255 }; + constexpr RGBA DarkPurple { 128, 0, 128, 255 }; - constexpr RGBA White { 255, 255, 255, 255 }; - constexpr RGBA Black { 0, 0, 0, 255 }; - constexpr RGBA Grey { 127, 127, 127, 255 }; - constexpr RGBA Red { 255, 0, 0, 255 }; - constexpr RGBA Green { 0, 255, 0, 255 }; - constexpr RGBA DarkGreen { 0, 128, 0, 255 }; - constexpr RGBA Blue { 0, 0, 255, 255 }; - constexpr RGBA DarkBlue { 0, 0, 128, 255 }; - constexpr RGBA Cyan { 128, 128, 255, 255 }; - constexpr RGBA DarkCyan { 80, 80, 128, 255 }; - constexpr RGBA Orange { 128, 128, 0, 255 }; - constexpr RGBA Yellow { 255, 255, 0, 255 }; - constexpr RGBA Purple { 255, 0, 255, 255 }; - constexpr RGBA DarkPurple { 128, 0, 128, 255 }; +} // namespace Langulus::Colors - } // namespace Langulus::Colors -} // namespace Langulus +LANGULUS_DEFINE_CONSTANT(ColorWhite, ::Langulus::Colors::White, + "Colors::White", "An opaque white color") +LANGULUS_DEFINE_CONSTANT(ColorBlack, ::Langulus::Colors::Black, + "Colors::Black", "An opaque black color") +LANGULUS_DEFINE_CONSTANT(ColorGrey, ::Langulus::Colors::Grey, + "Colors::Grey", "An opaque gray color") +LANGULUS_DEFINE_CONSTANT(ColorRed, ::Langulus::Colors::Red, + "Colors::Red", "An opaque red color") +LANGULUS_DEFINE_CONSTANT(ColorGreen, ::Langulus::Colors::Green, + "Colors::Green", "An opaque green color") +LANGULUS_DEFINE_CONSTANT(ColorDarkGreen, ::Langulus::Colors::DarkGreen, + "Colors::DarkGreen", "An opaque dark green color") +LANGULUS_DEFINE_CONSTANT(ColorBlue, ::Langulus::Colors::Blue, + "Colors::Blue", "An opaque blue color") +LANGULUS_DEFINE_CONSTANT(ColorDarkBlue, ::Langulus::Colors::DarkBlue, + "Colors::DarkBlue", "An opaque dark blue color") +LANGULUS_DEFINE_CONSTANT(ColorCyan, ::Langulus::Colors::Cyan, + "Colors::Cyan", "An opaque cyan color") +LANGULUS_DEFINE_CONSTANT(ColorDarkCyan, ::Langulus::Colors::DarkCyan, + "Colors::DarkCyan", "An opaque dark cyan color") +LANGULUS_DEFINE_CONSTANT(ColorOrange, ::Langulus::Colors::Orange, + "Colors::Orange", "An opaque orange color") +LANGULUS_DEFINE_CONSTANT(ColorYellow, ::Langulus::Colors::Yellow, + "Colors::Yellow", "An opaque yellow color") +LANGULUS_DEFINE_CONSTANT(ColorPurple, ::Langulus::Colors::Purple, + "Colors::Purple", "An opaque purple color") +LANGULUS_DEFINE_CONSTANT(ColorDarkPurple, ::Langulus::Colors::DarkPurple, + "Colors::DarkPurple", "An opaque dark purple color") diff --git a/source/Functions/Arithmetics.hpp b/source/Functions/Arithmetics.hpp index 5d53a7e..8555634 100644 --- a/source/Functions/Arithmetics.hpp +++ b/source/Functions/Arithmetics.hpp @@ -161,7 +161,7 @@ namespace Langulus::Math else if constexpr (CT::Signed) return a < T {0} ? -a : a; else - LANGULUS_ERROR("T must either have Abs() method, or be a number"); + static_assert(false, "T must either have Abs() method, or be a number"); } /// Signed unit @@ -179,7 +179,7 @@ namespace Langulus::Math else if constexpr (CT::Signed) return a < T {0} ? T {-1} : T {1}; else - LANGULUS_ERROR("T must either have Sign() method, or be a number"); + static_assert(false, "T must either have Sign() method, or be a number"); } /// Calculate base to the power of the exponent @@ -211,7 +211,7 @@ namespace Langulus::Math else if constexpr (CT::Real) return ::std::pow(FundamentalCast(base), FundamentalCast(exponent)); else - LANGULUS_ERROR("T must either have Pow(exponent) method, or be a number"); + static_assert(false, "T must either have Pow(exponent) method, or be a number"); } /// Get the smallest of the provided @@ -224,7 +224,7 @@ namespace Langulus::Math else if constexpr (CT::Sortable) return t1 < t2 ? Forward(t1) : Forward(t2); else - LANGULUS_ERROR("T must either have Min(t2) method, or be sortable"); + static_assert(false, "T must either have Min(t2) method, or be sortable"); } else return Min(Min(Forward(t1), Forward(t2)), Forward(tail)...); } @@ -239,7 +239,7 @@ namespace Langulus::Math else if constexpr (CT::Sortable) return t1 > t2 ? Forward(t1) : Forward(t2); else - LANGULUS_ERROR("T must either have Max(t2) method, or be sortable"); + static_assert(false, "T must either have Max(t2) method, or be sortable"); } else return Max(Max(Forward(t1), Forward(t2)), Forward(tail)...); } @@ -255,7 +255,7 @@ namespace Langulus::Math else if constexpr (CT::Real) return ::std::round(a); else - LANGULUS_ERROR("T must either have Round() method, or be a number"); + static_assert(false, "T must either have Round() method, or be a number"); } /// Round and return an integer @@ -274,7 +274,7 @@ namespace Langulus::Math const auto aa = static_cast(a) + Double {6755399441055744.0}; return int {reinterpret_cast(aa)}; } - else LANGULUS_ERROR("T must either have Round() method, or be a number"); + else static_assert(false, "T must either have Round() method, or be a number"); }*/ /// Floor @@ -289,7 +289,7 @@ namespace Langulus::Math const auto round_a = Round(a); return round_a <= a ? round_a : round_a - T {1}; } - else LANGULUS_ERROR("T must either have Floor() method, or be a number"); + else static_assert(false, "T must either have Floor() method, or be a number"); } /// Floor and return an integer @@ -311,7 +311,7 @@ namespace Langulus::Math const auto round_a = Round(a); return round_a >= a ? round_a : round_a + T(1); } - else LANGULUS_ERROR("T must either have Ceil() method, or be a number"); + else static_assert(false, "T must either have Ceil() method, or be a number"); } /// Ceil and return an integer @@ -328,7 +328,7 @@ namespace Langulus::Math if constexpr (CT::Multipliable) return n * n; else - LANGULUS_ERROR("T must be CT::Multipliable"); + static_assert(false, "T must be CT::Multipliable"); } namespace Detail @@ -379,7 +379,7 @@ namespace Langulus::Math } while (r < p); return p; } - else LANGULUS_ERROR("T must either have Sqrt() method, or be a number"); + else static_assert(false, "T must either have Sqrt() method, or be a number"); } /// Get a fractional part @@ -393,7 +393,7 @@ namespace Langulus::Math else if constexpr (CT::Integer) return T {0}; else - LANGULUS_ERROR("T must either have Frac() method, or be a number"); + static_assert(false, "T must either have Frac() method, or be a number"); } /// Modulate @@ -405,7 +405,7 @@ namespace Langulus::Math else if constexpr (CT::Number) return x - y * Floor(x / y); else - LANGULUS_ERROR("T must either have Mod(y) method, or be a number"); + static_assert(false, "T must either have Mod(y) method, or be a number"); } /// Remaps a [0; 1] range to a [-1; 1] range @@ -424,7 +424,7 @@ namespace Langulus::Math else if constexpr (CT::Number) return v < min ? min : (v > max ? max : v); else - LANGULUS_ERROR("T must either have Clamp(min, max) method, or be a number"); + static_assert(false, "T must either have Clamp(min, max) method, or be a number"); } /// Clamp a value inside the interval [0:1] @@ -447,7 +447,7 @@ namespace Langulus::Math return v - min > halfd ? max : min; return v; } - else LANGULUS_ERROR("T must either have ClampRev(min, max) method, or be a number"); + else static_assert(false, "T must either have ClampRev(min, max) method, or be a number"); } /// Dot product @@ -456,7 +456,8 @@ namespace Langulus::Math constexpr auto Dot(const T1& a, const T2& b) noexcept { if constexpr (CT::HasDot) return a.Dot(b); - else LANGULUS_ERROR("T must have Dot(b) method"); + else + static_assert(false, "T must have Dot(b) method"); } /// Self dot product @@ -472,7 +473,8 @@ namespace Langulus::Math constexpr auto Cross(const T1& a, const T2& b) noexcept { if constexpr (CT::HasCross) return a.Cross(b); - else LANGULUS_ERROR("T must have Cross(b) method"); + else + static_assert(false, "T must have Cross(b) method"); } /// Get length (as in magnitude) @@ -486,7 +488,7 @@ namespace Langulus::Math else if constexpr (CT::Character) return Abs(v); else - LANGULUS_ERROR("T must either have Length() method, or be a number"); + static_assert(false, "T must either have Length() method, or be a number"); } /// Distance @@ -503,7 +505,7 @@ namespace Langulus::Math if constexpr (CT::HasNormalize) return v.Normalize(); else - LANGULUS_ERROR("T must have Normalize() method"); + static_assert(false, "T must have Normalize() method"); } /// Step function @@ -515,7 +517,7 @@ namespace Langulus::Math else if constexpr (CT::Number) return x < edge ? T {0} : T {1}; else - LANGULUS_ERROR("T must either have Step(edge) method, or be a number"); + static_assert(false, "T must either have Step(edge) method, or be a number"); } /// Smooth step (Hermite) interpolation, analogous to the GLSL function @@ -537,7 +539,7 @@ namespace Langulus::Math else if constexpr (CT::Number) return ::std::exp(x); else - LANGULUS_ERROR("T must either have Exp() method, or be a number"); + static_assert(false, "T must either have Exp() method, or be a number"); } /// Solve 2^x @@ -557,7 +559,7 @@ namespace Langulus::Math LANGULUS_ASSUME(UserAssumes, n >= 0, "Can't get sum of non-positive integers"); return (n * (n + T {1})) / T {2}; } - else LANGULUS_ERROR("T must either have Sum() method, or be a number"); + else static_assert(false, "T must either have Sum() method, or be a number"); } /// A Kahan summation used to minimize floating-point math error diff --git a/source/Matrices/TMatrix.hpp b/source/Matrices/TMatrix.hpp index d506813..2108ce4 100644 --- a/source/Matrices/TMatrix.hpp +++ b/source/Matrices/TMatrix.hpp @@ -120,41 +120,6 @@ namespace Langulus } // namespace Langulus::A - /// Custom name generator at compile-time for matrices - TEMPLATE() - consteval auto CustomName(Of&&) noexcept { - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (COLUMNS > 4 or ROWS > 4) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - constexpr Token prefix = "Matrix"; - for (auto i : prefix) - name[offset++] = i; - - // Write columns and rows - if constexpr (COLUMNS == ROWS) { - name[offset++] = '0' + COLUMNS; - } - else { - name[offset++] = '0' + COLUMNS; - name[offset++] = 'x'; - name[offset++] = '0' + ROWS; - } - - // Write suffix - for (auto i : SuffixOf()) - name[offset++] = i; - return name; - } - - namespace Math { @@ -185,8 +150,42 @@ namespace Langulus T mArray[MemberCount]; }; + private: + /// Custom name generator at compile-time for matrices + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (COLUMNS > 4 or ROWS > 4) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + constexpr Token prefix = "Matrix"; + for (auto i : prefix) + name[offset++] = i; + + // Write columns and rows + if constexpr (COLUMNS == ROWS) { + name[offset++] = '0' + COLUMNS; + } + else { + name[offset++] = '0' + COLUMNS; + name[offset++] = 'x'; + name[offset++] = '0' + ROWS; + } + + // Write suffix + for (auto i : SuffixOf()) + name[offset++] = i; + return name; + } + public: - LANGULUS(NAME) CustomNameOf::Generate(); + LANGULUS(NAME) GenerateToken(); LANGULUS(POD) CT::POD; LANGULUS(NULLIFIABLE) false; LANGULUS(TYPED) T; diff --git a/source/Matrices/TMatrix.inl b/source/Matrices/TMatrix.inl index b1ee334..6477fd9 100644 --- a/source/Matrices/TMatrix.inl +++ b/source/Matrices/TMatrix.inl @@ -480,7 +480,7 @@ namespace Langulus::Math constexpr auto TME()::GetRight() const noexcept -> TVector { if constexpr (IsSquare and Rows > 2) return {mColumns[0][0], mColumns[1][0], mColumns[2][0]}; - else LANGULUS_ERROR("Can't get right axis of this matrix"); + else static_assert(false, "Can't get right axis of this matrix"); } /// Get up axis @@ -488,7 +488,7 @@ namespace Langulus::Math constexpr auto TME()::GetUp() const noexcept -> TVector { if constexpr (IsSquare and Rows > 2) return {mColumns[0][1], mColumns[1][1], mColumns[2][1]}; - else LANGULUS_ERROR("Can't get up axis of this matrix"); + else static_assert(false, "Can't get up axis of this matrix"); } /// Get view axis @@ -496,7 +496,7 @@ namespace Langulus::Math constexpr auto TME()::GetView() const noexcept -> TVector { if constexpr (IsSquare and Rows > 2) return {mColumns[0][2], mColumns[1][2], mColumns[2][2]}; - else LANGULUS_ERROR("Can't get view axis of this matrix"); + else static_assert(false, "Can't get view axis of this matrix"); } /// Get translation @@ -504,7 +504,7 @@ namespace Langulus::Math constexpr auto TME()::GetScale() const noexcept -> TVector { if constexpr (IsSquare and Rows > 2) return {GetRight().Length(), GetUp().Length(), GetView().Length()}; - else LANGULUS_ERROR("Can't get translation of this matrix"); + else static_assert(false, "Can't get translation of this matrix"); } /// Get translation @@ -797,7 +797,7 @@ namespace Langulus::Math (n12 * n23 * n31 - n13 * n22 * n31 + n13 * n21 * n32 - n11 * n23 * n32 - n12 * n21 * n33 + n11 * n22 * n33)* detInv, }; } - else LANGULUS_ERROR("Matrix inversion code not implemented"); + else static_assert(false, "Matrix inversion code not implemented"); } @@ -929,7 +929,10 @@ namespace Langulus::Math /// @param rhs - right matrix /// @return the product LANGULUS(INLINED) - constexpr auto operator * (const CT::MatrixBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator * ( + const CT::MatrixBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using LHS = Deref; using RHS = Deref; static_assert(LHS::Rows == RHS::Columns and LHS::Columns == RHS::Rows, @@ -969,7 +972,10 @@ namespace Langulus::Math /// @param rhs - right matrix /// @return the added matrices LANGULUS(INLINED) - constexpr auto operator + (const CT::MatrixBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator + ( + const CT::MatrixBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using Ret = LosslessMatrix; TypeOf result[Ret::Columns][Ret::Rows]; Sequence::ForEach([&]() noexcept { @@ -987,7 +993,10 @@ namespace Langulus::Math /// @param rhs - right matrix /// @return the subtracted matrices LANGULUS(INLINED) - constexpr auto operator - (const CT::MatrixBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator - ( + const CT::MatrixBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using Ret = LosslessMatrix; TypeOf result[Ret::Columns][Ret::Rows]; Sequence::ForEach([&]() noexcept { @@ -1005,7 +1014,10 @@ namespace Langulus::Math /// @param rhs - matrix /// @return the transformed vector LANGULUS(INLINED) - constexpr auto operator * (const CT::VectorBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator * ( + const CT::VectorBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using Ret = Deref; constexpr auto C = CountOf; TypeOf r[C]; @@ -1020,7 +1032,10 @@ namespace Langulus::Math /// @param rhs - matrix /// @return the modified matrix LANGULUS(INLINED) - constexpr auto operator + (const CT::VectorBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator + ( + const CT::VectorBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using Ret = Deref; TypeOf result[Ret::Columns][Ret::Rows]; Sequence::ForEach([&]() noexcept { @@ -1034,7 +1049,10 @@ namespace Langulus::Math /// @param rhs - matrix /// @return the modified matrix LANGULUS(INLINED) - constexpr auto operator - (const CT::VectorBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator - ( + const CT::VectorBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using Ret = Deref; TypeOf result[Ret::Columns][Ret::Rows]; Sequence::ForEach([&]() noexcept { @@ -1048,7 +1066,10 @@ namespace Langulus::Math /// @param rhs - vector /// @return the transformed vector LANGULUS(INLINED) - constexpr auto operator * (const CT::MatrixBased auto& lhs, const CT::VectorBased auto& rhs) noexcept { + constexpr auto operator * ( + const CT::MatrixBased auto& lhs, + const CT::VectorBased auto& rhs + ) noexcept { using Ret = Deref; constexpr auto C = CountOf; TypeOf r[C]; @@ -1063,7 +1084,10 @@ namespace Langulus::Math /// @param rhs - vector /// @return the modified matrix LANGULUS(INLINED) - constexpr auto operator + (const CT::MatrixBased auto& lhs, const CT::VectorBased auto& rhs) noexcept { + constexpr auto operator + ( + const CT::MatrixBased auto& lhs, + const CT::VectorBased auto& rhs + ) noexcept { using Ret = Deref; TypeOf result[Ret::Columns][Ret::Rows]; Sequence::ForEach([&]() noexcept { @@ -1077,7 +1101,10 @@ namespace Langulus::Math /// @param rhs - vector /// @return the modified matrix LANGULUS(INLINED) - constexpr auto operator - (const CT::MatrixBased auto& lhs, const CT::VectorBased auto& rhs) noexcept { + constexpr auto operator - ( + const CT::MatrixBased auto& lhs, + const CT::VectorBased auto& rhs + ) noexcept { using Ret = Deref; TypeOf result[Ret::Columns][Ret::Rows]; Sequence::ForEach([&]() noexcept { @@ -1091,7 +1118,10 @@ namespace Langulus::Math /// @param rhs - matrix /// @return the scaled matrix LANGULUS(INLINED) - constexpr auto operator * (const CT::ScalarBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator * ( + const CT::ScalarBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using Ret = Deref; TypeOf result[Ret::MemberCount]; SIMD::Multiply(rhs.mArray, lhs, result); @@ -1099,7 +1129,10 @@ namespace Langulus::Math } LANGULUS(INLINED) - constexpr auto operator * (const CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) noexcept { + constexpr auto operator * ( + const CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) noexcept { return rhs * lhs; } @@ -1108,7 +1141,10 @@ namespace Langulus::Math /// @param rhs - scalar /// @return the scaled matrix LANGULUS(INLINED) - constexpr auto operator / (const CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) { + constexpr auto operator / ( + const CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) { using Ret = Deref; TypeOf result[Ret::MemberCount]; SIMD::Divide(lhs.mArray, rhs, result); @@ -1120,7 +1156,10 @@ namespace Langulus::Math /// @param rhs - matrix /// @return the modified matrix LANGULUS(INLINED) - constexpr auto operator + (const CT::ScalarBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator + ( + const CT::ScalarBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using Ret = Deref; TypeOf result[Ret::MemberCount]; SIMD::Add(rhs.mArray, lhs, result); @@ -1128,7 +1167,10 @@ namespace Langulus::Math } LANGULUS(INLINED) - constexpr auto operator + (const CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) noexcept { + constexpr auto operator + ( + const CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) noexcept { return rhs + lhs; } @@ -1137,7 +1179,10 @@ namespace Langulus::Math /// @param rhs - scalar /// @return the modified matrix LANGULUS(INLINED) - constexpr auto operator - (const CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) noexcept { + constexpr auto operator - ( + const CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) noexcept { using Ret = Deref; TypeOf result[Ret::MemberCount]; SIMD::Subtract(lhs.mArray, rhs, result); @@ -1150,60 +1195,87 @@ namespace Langulus::Math /// /// Add two matrices LANGULUS(INLINED) - constexpr auto& operator += (CT::MatrixBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto& operator += ( + CT::MatrixBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { SIMD::Add(lhs.mArray, rhs.mArray, lhs.mArray); return lhs; } /// Add a scalar to a matrix LANGULUS(INLINED) - constexpr auto& operator += (CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) noexcept { + constexpr auto& operator += ( + CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) noexcept { SIMD::Add(lhs.mArray, rhs, lhs.mArray); return lhs; } /// Add a vector to each column of a matrix LANGULUS(INLINED) - constexpr auto& operator += (CT::MatrixBased auto& lhs, const CT::VectorBased auto& rhs) noexcept { + constexpr auto& operator += ( + CT::MatrixBased auto& lhs, + const CT::VectorBased auto& rhs + ) noexcept { return (lhs = lhs + rhs); } /// Subtract two matrices LANGULUS(INLINED) - constexpr auto& operator -= (CT::MatrixBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto& operator -= ( + CT::MatrixBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { SIMD::Subtract(lhs.mArray, rhs.mArray, lhs.mArray); return lhs; } /// Subtract a scalar from a matrix LANGULUS(INLINED) - constexpr auto& operator -= (CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) noexcept { + constexpr auto& operator -= ( + CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) noexcept { SIMD::Subtract(lhs.mArray, rhs, lhs.mArray); return lhs; } /// Subtract a vector from each column of a matrix LANGULUS(INLINED) - constexpr auto& operator -= (CT::MatrixBased auto& lhs, const CT::VectorBased auto& rhs) noexcept { + constexpr auto& operator -= ( + CT::MatrixBased auto& lhs, + const CT::VectorBased auto& rhs + ) noexcept { return (lhs = lhs - rhs); } /// Multiply two matrices LANGULUS(INLINED) - constexpr auto& operator *= (CT::MatrixBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto& operator *= ( + CT::MatrixBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { return (lhs = lhs * rhs); } /// Multiply matrix by a scalar LANGULUS(INLINED) - constexpr auto& operator *= (CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) noexcept { + constexpr auto& operator *= ( + CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) noexcept { SIMD::Multiply(lhs.mArray, rhs, lhs.mArray); return lhs; } /// Divide matrix by a scalar LANGULUS(INLINED) - constexpr auto& operator /= (CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) { + constexpr auto& operator /= ( + CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) { SIMD::Divide(lhs.mArray, rhs, lhs.mArray); return lhs; } @@ -1213,7 +1285,10 @@ namespace Langulus::Math /// Comparison /// LANGULUS(INLINED) - constexpr auto operator == (const CT::MatrixBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator == ( + const CT::MatrixBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { using LHS = Deref; using RHS = Deref; if constexpr (LHS::Columns != RHS::Columns or LHS::Rows != RHS::Rows) @@ -1223,12 +1298,18 @@ namespace Langulus::Math } LANGULUS(INLINED) - constexpr auto operator == (const CT::MatrixBased auto& lhs, const CT::ScalarBased auto& rhs) noexcept { + constexpr auto operator == ( + const CT::MatrixBased auto& lhs, + const CT::ScalarBased auto& rhs + ) noexcept { return SIMD::Equals(lhs.mArray, rhs); } LANGULUS(INLINED) - constexpr auto operator == (const CT::ScalarBased auto& lhs, const CT::MatrixBased auto& rhs) noexcept { + constexpr auto operator == ( + const CT::ScalarBased auto& lhs, + const CT::MatrixBased auto& rhs + ) noexcept { return SIMD::Equals(rhs.mArray, lhs); } diff --git a/source/Numbers/Infinity.hpp b/source/Numbers/Infinity.hpp new file mode 100644 index 0000000..06dbb46 --- /dev/null +++ b/source/Numbers/Infinity.hpp @@ -0,0 +1,25 @@ +/// +/// Langulus::Math +/// Copyright (c) 2014 Dimo Markov +/// Part of the Langulus framework, see https://langulus.com +/// +/// SPDX-License-Identifier: GPL-3.0-or-later +/// +#pragma once +#include "TNumber.hpp" + + +namespace Langulus::Math +{ + + /// + /// Infinity representation for use in descriptors + /// + struct Infinity { + int mOrder; + }; + +} // namespace Langulus::Math + +LANGULUS_DEFINE_CONSTANT(Infinity, ::Langulus::Math::Infinity {1}, + "Infinity", "First order of infinity") diff --git a/source/Numbers/Level.hpp b/source/Numbers/Level.hpp index 55d24f7..6ee282b 100644 --- a/source/Numbers/Level.hpp +++ b/source/Numbers/Level.hpp @@ -122,4 +122,4 @@ namespace Langulus::Math constexpr Offset GetOffsetInt() const noexcept; }; -} // namespace Langulus::Math \ No newline at end of file +} // namespace Langulus::Math diff --git a/source/Numbers/Level.inl b/source/Numbers/Level.inl index cf9d3da..742db8e 100644 --- a/source/Numbers/Level.inl +++ b/source/Numbers/Level.inl @@ -94,3 +94,84 @@ namespace Langulus::Math } } // namespace Langulus::Math + + +LANGULUS_DEFINE_CONSTANT(LevelHuman, + ::Langulus::Math::Level {::Langulus::Math::Level::Human}, + "Level::Human", "A canonical human level" +) + +LANGULUS_DEFINE_CONSTANT(LevelAsteroid, + ::Langulus::Math::Level {::Langulus::Math::Level::Asteroid}, + "Level::Asteroid", "A canonical asteroid level" +) + +LANGULUS_DEFINE_CONSTANT(LevelPlanet, + ::Langulus::Math::Level {::Langulus::Math::Level::Planet}, + "Level::Planet", "A canonical planet level" +) + +LANGULUS_DEFINE_CONSTANT(LevelSystem, + ::Langulus::Math::Level {::Langulus::Math::Level::System}, + "Level::System", "A canonical system level" +) + +LANGULUS_DEFINE_CONSTANT(LevelGalaxy, + ::Langulus::Math::Level {::Langulus::Math::Level::Galaxy}, + "Level::Galaxy", "A canonical galaxy level" +) + +LANGULUS_DEFINE_CONSTANT(LevelUniverse, + ::Langulus::Math::Level {::Langulus::Math::Level::Universe}, + "Level::Universe", "A canonical universe level" +) + +LANGULUS_DEFINE_CONSTANT(LevelCell, + ::Langulus::Math::Level {::Langulus::Math::Level::Cell}, + "Level::Cell", "A canonical cell level" +) + +LANGULUS_DEFINE_CONSTANT(LevelVirus, + ::Langulus::Math::Level {::Langulus::Math::Level::Virus}, + "Level::Virus", "A canonical virus level" +) + +LANGULUS_DEFINE_CONSTANT(LevelAtom, + ::Langulus::Math::Level {::Langulus::Math::Level::Atom}, + "Level::Atom", "A canonical atom level" +) + +LANGULUS_DEFINE_CONSTANT(LevelNeutron, + ::Langulus::Math::Level {::Langulus::Math::Level::Neutron}, + "Level::Neutron", "A canonical neutron level" +) + +LANGULUS_DEFINE_CONSTANT(LevelQuark, + ::Langulus::Math::Level {::Langulus::Math::Level::Quark}, + "Level::Quark", "A canonical quark level" +) + +LANGULUS_DEFINE_CONSTANT(LevelNeutrino, + ::Langulus::Math::Level {::Langulus::Math::Level::Neutrino}, + "Level::Neutrino", "A canonical neutrino level" +) + +LANGULUS_DEFINE_CONSTANT(LevelPlanck, + ::Langulus::Math::Level {::Langulus::Math::Level::Planck}, + "Level::Planck", "A canonical Planck level" +) + +LANGULUS_DEFINE_CONSTANT(LevelMax, + ::Langulus::Math::Level {::Langulus::Math::Level::Max}, + "Level::Max", "A canonical max level" +) + +LANGULUS_DEFINE_CONSTANT(LevelMin, + ::Langulus::Math::Level {::Langulus::Math::Level::Min}, + "Level::Min", "A canonical min level" +) + +LANGULUS_DEFINE_CONSTANT(LevelDefault, + ::Langulus::Math::Level {::Langulus::Math::Level::Default}, + "Level::Default", "The default level" +) \ No newline at end of file diff --git a/source/Numbers/TAngle.hpp b/source/Numbers/TAngle.hpp index 6c64580..da5c2a4 100644 --- a/source/Numbers/TAngle.hpp +++ b/source/Numbers/TAngle.hpp @@ -183,39 +183,6 @@ namespace Langulus } // namespace Langulus::A - /// Custom name generator at compile-time for angles - template - constexpr auto CustomName(Of>&&) noexcept { - constexpr auto defaultClassName = RTTI::LastCppNameOf>(); - ::std::array name {}; - ::std::size_t offset {}; - - // Write dimension name - if constexpr (D::Index == 0) { - for (auto i : "Pitch") - name[offset++] = i; - } - else if constexpr (D::Index == 1) { - for (auto i : "Yaw") - name[offset++] = i; - } - else if constexpr (D::Index == 2) { - for (auto i : "Roll") - name[offset++] = i; - } - else LANGULUS_ERROR("Unsupported dimension"); - - // Write angle suffix if degrees - // Radians have no suffix by default - if constexpr (CT::Degrees) - name[offset++] = 'd'; - - // Write type suffix - for (auto i : SuffixOf()) - name[offset++] = i; - return name; - } - namespace Math { @@ -224,13 +191,47 @@ namespace Langulus /// template struct TAngle : T { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static constexpr auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + // Provision a bit more in case default class name turns out + // to be too small (g++-14 complains for some reason) + ::std::array name {}; + ::std::size_t offset = 0; + + // Write dimension name + if constexpr (D::Index == 0) { + for (auto i : "Pitch") + name[offset++] = i; + } + else if constexpr (D::Index == 1) { + for (auto i : "Yaw") + name[offset++] = i; + } + else if constexpr (D::Index == 2) { + for (auto i : "Roll") + name[offset++] = i; + } + else static_assert(false, "Unsupported dimension"); + + // Write angle suffix if degrees + // Radians have no suffix by default + if constexpr (CT::Degrees) + name[offset++] = 'd'; + + // Write type suffix + for (auto i : SuffixOf()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS_BASES(T, A::AngleOfDimension, A::AngleOfType); LANGULUS_CONVERTS_TO(Anyness::Text, Flow::Code); - using Dimension = D; + using Dimension = D; using T::mValue; - using T::T; using T::operator =; TAngle(Describe&&); diff --git a/source/Numbers/TNumber.cpp b/source/Numbers/TNumber.cpp new file mode 100644 index 0000000..aac5e69 --- /dev/null +++ b/source/Numbers/TNumber.cpp @@ -0,0 +1,40 @@ +/// +/// Langulus::Math +/// Copyright (c) 2014 Dimo Markov +/// Part of the Langulus framework, see https://langulus.com +/// +/// SPDX-License-Identifier: GPL-3.0-or-later +/// +#include "TAngle.hpp" +#include "Level.inl" +#include "Infinity.hpp" + + +namespace Langulus::Math +{ + + /// Register number types + void RegisterNumbers() { + RegisterAngles(); + + (void) MetaOf(); + + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + } + +} // namespace Langulus::Math diff --git a/source/Numbers/TNumber.hpp b/source/Numbers/TNumber.hpp index 428f2ac..b3edf3f 100644 --- a/source/Numbers/TNumber.hpp +++ b/source/Numbers/TNumber.hpp @@ -12,6 +12,9 @@ namespace Langulus::Math { + LANGULUS_API(MATH) extern void RegisterNumbers(); + + /// /// Templated number /// @@ -44,7 +47,10 @@ namespace Langulus::Math , A::Real , Conditional , A::SignedInteger - , A::UnsignedInteger>>); + , A::UnsignedInteger + > + > + ); LANGULUS_CONVERTS_TO(Flow::Code); static constexpr Count MemberCount = 1; diff --git a/source/Numbers/TNumber.inl b/source/Numbers/TNumber.inl index c308332..810be9d 100644 --- a/source/Numbers/TNumber.inl +++ b/source/Numbers/TNumber.inl @@ -27,7 +27,8 @@ namespace Langulus::Math mValue = a.mValue; else if constexpr (CT::Convertible) mValue = static_cast(a); - else LANGULUS_ERROR("Bad number construction"); + else + static_assert(false, "Bad number construction"); } /// Assign any number-convertible thing @@ -42,7 +43,8 @@ namespace Langulus::Math mValue = a.mValue; else if constexpr (CT::Convertible) mValue = static_cast(a); - else LANGULUS_ERROR("Bad number assignment"); + else + static_assert(false, "Bad number assignment"); return *this; } @@ -243,7 +245,7 @@ namespace Langulus::Math * ::std::floor(FundamentalCast(lhs) / FundamentalCast(rhs))}; } } - else LANGULUS_ERROR("Incompatible custom numbers for modulation"); + else static_assert(false, "Incompatible custom numbers for modulation"); } template LANGULUS(INLINED) @@ -271,7 +273,7 @@ namespace Langulus::Math else if constexpr (CT::DerivedFrom) return RHS {FundamentalCast(lhs) << FundamentalCast(rhs)}; else - LANGULUS_ERROR("Incompatible custom numbers for left bitshift"); + static_assert(false, "Incompatible custom numbers for left bitshift"); } template @@ -295,7 +297,7 @@ namespace Langulus::Math else if constexpr (CT::DerivedFrom) return RHS {FundamentalCast(lhs) >> FundamentalCast(rhs)}; else - LANGULUS_ERROR("Incompatible custom numbers for right bitshift"); + static_assert(false, "Incompatible custom numbers for right bitshift"); } template @@ -319,7 +321,7 @@ namespace Langulus::Math else if constexpr (CT::DerivedFrom) return RHS {FundamentalCast(lhs) ^ FundamentalCast(rhs)}; else - LANGULUS_ERROR("Incompatible custom numbers for xor"); + static_assert(false, "Incompatible custom numbers for xor"); } template diff --git a/source/Primitives/TBox.hpp b/source/Primitives/TBox.hpp index 76a8068..4577675 100644 --- a/source/Primitives/TBox.hpp +++ b/source/Primitives/TBox.hpp @@ -52,62 +52,6 @@ namespace Langulus } // namespace Langulus::CT - /// Custom name generator at compile-time for boxes - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TBox; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Box") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - - /// Custom name generator at compile-time for rounded boxes - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TBoxRounded; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "BoxRounded") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - } // namespace Langulus namespace Langulus::Math @@ -129,7 +73,34 @@ namespace Langulus::Math /// | template struct TBox : A::Box { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Box") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; LANGULUS(POD) CT::POD; LANGULUS(TYPED) TypeOf; @@ -166,7 +137,34 @@ namespace Langulus::Math /// | template struct TBoxRounded : TBox { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "BoxRounded") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS_CONVERTS_TO(Anyness::Text, Flow::Code); using Base = TBox; diff --git a/source/Primitives/TLine.hpp b/source/Primitives/TLine.hpp index 0f0039d..db9a615 100644 --- a/source/Primitives/TLine.hpp +++ b/source/Primitives/TLine.hpp @@ -76,91 +76,6 @@ namespace Langulus } // namespace Langulus::CT - - /// Custom name generator at compile-time for lines - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TLine; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Line") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - - /// Custom name generator at compile-time for line loop - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TLineLoop; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "LineLoop") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - - /// Custom name generator at compile-time for line loop - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TLineStrip; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "LineStrip") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - } // namespace Langulus namespace Langulus::Math @@ -172,7 +87,34 @@ namespace Langulus::Math #pragma pack(push, 1) template struct TLine : A::Line { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Line") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; LANGULUS(POD) CT::POD; LANGULUS(NULLIFIABLE) CT::Nullifiable; @@ -219,7 +161,34 @@ namespace Langulus::Math /// template struct TLineLoop : A::LineLoop { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "LineLoop") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; LANGULUS(TYPED) TypeOf; LANGULUS_BASES(A::LineLoop); @@ -240,7 +209,34 @@ namespace Langulus::Math /// template struct TLineStrip : A::LineStrip { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "LineStrip") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; LANGULUS(TYPED) TypeOf; LANGULUS_BASES(A::LineStrip); diff --git a/source/Primitives/TSphere.hpp b/source/Primitives/TSphere.hpp index 11865de..58f252a 100644 --- a/source/Primitives/TSphere.hpp +++ b/source/Primitives/TSphere.hpp @@ -50,63 +50,6 @@ namespace Langulus } // namespace Langulus::CT - - /// Custom name generator at compile-time for boxes - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TSphere; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - else if constexpr (T::MemberCount == 3) { - for (auto i : "Sphere") - name[offset++] = i; - } - else if constexpr (T::MemberCount == 2) { - for (auto i : "Circle") - name[offset++] = i; - } - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - - /// Custom name generator at compile-time for rounded boxes - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TEllipsoid; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Ellipsoid") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - } // namespace Langulus namespace Langulus::Math @@ -117,7 +60,34 @@ namespace Langulus::Math /// template struct TSphere { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + else if constexpr (T::MemberCount == 3) { + for (auto i : "Sphere") + name[offset++] = i; + } + else if constexpr (T::MemberCount == 2) { + for (auto i : "Circle") + name[offset++] = i; + } + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; LANGULUS(POD) CT::POD; LANGULUS(TYPED) TypeOf; @@ -156,8 +126,34 @@ namespace Langulus::Math /// template struct TEllipsoid { + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Ellipsoid") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + public: - LANGULUS(NAME) CustomNameOf::Generate(); + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; LANGULUS(POD) CT::POD; LANGULUS(TYPED) TypeOf; diff --git a/source/Primitives/TTorus.hpp b/source/Primitives/TTorus.hpp index 803a559..69cb945 100644 --- a/source/Primitives/TTorus.hpp +++ b/source/Primitives/TTorus.hpp @@ -58,7 +58,7 @@ namespace Langulus::Math const auto q = TVector, 2>(point.xy().Length() - mOuterRadius, point[2]); return q.Length() - mInnerRadius; } - else LANGULUS_ERROR("Unsupported dimension"); + else static_assert(false, "Unsupported dimension"); } }; diff --git a/source/Primitives/TTriangle.hpp b/source/Primitives/TTriangle.hpp index f6ffa98..b9e415a 100644 --- a/source/Primitives/TTriangle.hpp +++ b/source/Primitives/TTriangle.hpp @@ -81,90 +81,6 @@ namespace Langulus concept TriangleFan = (DerivedFrom and ...); } // namespace Langulus::CT - - /// Custom name generator at compile-time for triangles - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TTriangle; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Tri") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - - /// Custom name generator at compile-time for triangle strips - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TTriangleStrip; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "TriStrip") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - - /// Custom name generator at compile-time for triangle fans - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TTriangleFan; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (T::MemberCount > 3) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "TriFan") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + T::MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } } // namespace Langulus @@ -177,7 +93,34 @@ namespace Langulus::Math #pragma pack(push, 1) template struct TTriangle : A::Triangle { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Tri") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; LANGULUS(POD) CT::POD; LANGULUS(NULLIFIABLE) CT::Nullifiable; @@ -329,7 +272,34 @@ namespace Langulus::Math /// template struct TTriangleStrip : A::TriangleStrip { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "TriStrip") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(TYPED) TypeOf; LANGULUS_BASES(A::TriangleStrip); @@ -360,7 +330,34 @@ namespace Langulus::Math /// template struct TTriangleFan : A::TriangleFan { - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (T::MemberCount > 3) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "TriFan") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + T::MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(TYPED) TypeOf; LANGULUS_BASES(A::TriangleFan); diff --git a/source/Quaternions/TQuaternion.hpp b/source/Quaternions/TQuaternion.hpp index d71c935..654f43d 100644 --- a/source/Quaternions/TQuaternion.hpp +++ b/source/Quaternions/TQuaternion.hpp @@ -49,29 +49,6 @@ namespace Langulus::A } // namespace Langulus::A -namespace Langulus -{ - - /// Custom name generator at compile-time for vectors - template - consteval auto CustomName(Of>&&) noexcept { - constexpr auto defaultClassName = RTTI::LastCppNameOf>(); - ::std::array name {}; - ::std::size_t offset {}; - - // Write prefix - for (auto i : "Quat") - name[offset++] = i; - - // Write suffix - --offset; - for (auto i : SuffixOf()) - name[offset++] = i; - - return name; - } -} - namespace Langulus::Math { @@ -94,8 +71,26 @@ namespace Langulus::Math using Base::all; + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + // Write prefix + for (auto i : "Quat") + name[offset++] = i; + + // Write suffix + --offset; + for (auto i : SuffixOf()) + name[offset++] = i; + + return name; + } + public: - LANGULUS(NAME) CustomNameOf::Generate(); + LANGULUS(NAME) GenerateToken(); LANGULUS(NULLIFIABLE) false; LANGULUS_BASES(Base, A::QuaternionOfType); diff --git a/source/Quaternions/TQuaternion.inl b/source/Quaternions/TQuaternion.inl index f86c832..dbdee05 100644 --- a/source/Quaternions/TQuaternion.inl +++ b/source/Quaternions/TQuaternion.inl @@ -155,7 +155,7 @@ namespace Langulus::Math else if constexpr (CT::Same) return FromAxis(TVector{0, 0, 1, 0}, angle); else - LANGULUS_ERROR("Unsupported dimension"); + static_assert(false, "Unsupported dimension"); } /// Constructor from axii and angles diff --git a/source/Randomness/Hashes.hpp b/source/Randomness/Hashes.hpp index 031c3b6..340e491 100644 --- a/source/Randomness/Hashes.hpp +++ b/source/Randomness/Hashes.hpp @@ -127,7 +127,7 @@ namespace Langulus::Math return Frac((p4.xxyz() + p4.yzzw()) * p4.zywx()); } } - else LANGULUS_ERROR("Hash function with this output doesn't exist, for input 1"); + else static_assert(false, "Hash function with this output doesn't exist, for input 1"); } else if constexpr (DIN == 2) { if constexpr (DOUT == 1) { @@ -213,7 +213,7 @@ namespace Langulus::Math return Frac((p4.xxyz() + p4.yzzw()) * p4.zywx()); } } - else LANGULUS_ERROR("Hash function with this output doesn't exist, for input 2"); + else static_assert(false, "Hash function with this output doesn't exist, for input 2"); } else if constexpr (DIN == 3) { if constexpr (DOUT == 1) { @@ -298,7 +298,7 @@ namespace Langulus::Math return Frac((p4.xxyz() + p4.yzzw()) * p4.zywx()); } } - else LANGULUS_ERROR("Hash function with this output doesn't exist, for input 3"); + else static_assert(false, "Hash function with this output doesn't exist, for input 3"); } else if constexpr (DIN == 4) { if constexpr (DOUT == 1) { @@ -383,9 +383,9 @@ namespace Langulus::Math return Frac((p.xxyz() + p.yzzw()) * p.zywx()); } } - else LANGULUS_ERROR("Hash function with this output doesn't exist, for input 4"); + else static_assert(false, "Hash function with this output doesn't exist, for input 4"); } - else LANGULUS_ERROR("Hash function with this input doesn't exist"); + else static_assert(false, "Hash function with this input doesn't exist"); } }; diff --git a/source/Randomness/MersenneTwister.hpp b/source/Randomness/MersenneTwister.hpp index 9e42d11..112d07e 100644 --- a/source/Randomness/MersenneTwister.hpp +++ b/source/Randomness/MersenneTwister.hpp @@ -39,7 +39,7 @@ namespace Langulus::Math ::std::uniform_real_distribution dist(-1, 1); return dist(mStdGenerator); } - else LANGULUS_ERROR("Unsupported number type"); + else static_assert(false, "Unsupported number type"); } /// Provide random numbers for different number types, in a range @@ -73,7 +73,7 @@ namespace Langulus::Math ::std::uniform_real_distribution dist(min, max); result = dist(mStdGenerator); } - else LANGULUS_ERROR("Unsupported number type"); + else static_assert(false, "Unsupported number type"); if constexpr (!MIN_INCLUSIVE) { // Offset from lower limit diff --git a/source/Randomness/SimplexNoise.hpp b/source/Randomness/SimplexNoise.hpp index 29d5aa4..8166d14 100644 --- a/source/Randomness/SimplexNoise.hpp +++ b/source/Randomness/SimplexNoise.hpp @@ -74,7 +74,7 @@ namespace Langulus::Math TODO(); } } - else LANGULUS_ERROR("Hash function with this output doesn't exist, for input 1"); + else static_assert(false, "Hash function with this output doesn't exist, for input 1"); } else if constexpr (DIN == 2) { if constexpr (DOUT == 1) { @@ -131,7 +131,7 @@ namespace Langulus::Math TODO(); } } - else LANGULUS_ERROR("Hash function with this output doesn't exist, for input 2"); + else static_assert(false, "Hash function with this output doesn't exist, for input 2"); } else if constexpr (DIN == 3) { if constexpr (DOUT == 1) { @@ -216,7 +216,7 @@ namespace Langulus::Math TODO(); } } - else LANGULUS_ERROR("Hash function with this output doesn't exist, for input 3"); + else static_assert(false, "Hash function with this output doesn't exist, for input 3"); } else if constexpr (DIN == 4) { if constexpr (DOUT == 1) { @@ -255,9 +255,9 @@ namespace Langulus::Math TODO(); } } - else LANGULUS_ERROR("Hash function with this output doesn't exist, for input 4"); + else static_assert(false, "Hash function with this output doesn't exist, for input 4"); } - else LANGULUS_ERROR("Hash function with this input doesn't exist"); + else static_assert(false, "Hash function with this input doesn't exist"); } }; diff --git a/source/Ranges/TRange.cpp b/source/Ranges/TRange.cpp new file mode 100644 index 0000000..b2ab8ec --- /dev/null +++ b/source/Ranges/TRange.cpp @@ -0,0 +1,55 @@ +/// +/// Langulus::Math +/// Copyright (c) 2014 Dimo Markov +/// Part of the Langulus framework, see https://langulus.com +/// +/// SPDX-License-Identifier: GPL-3.0-or-later +/// +#include "TRange.inl" + + +namespace Langulus::Math +{ + + /// Combines S and T... to form a vector type, and then a range from it + /// @tparam S - size of the vector + template + struct RangeTypeGenerator { + template + static void Register(Types&&) { + (((void) MetaOf>>()), ...); + } + }; + + /// Register all commonly used vector types and constants, so they can be + /// instantiated from scripts + void RegisterRanges() { + using AllTypes = Types< + ::std::uint8_t, ::std::uint16_t, ::std::uint32_t, ::std::uint64_t, + ::std::int8_t, ::std::int16_t, ::std::int32_t, ::std::int64_t, + Float, Double + >; + + RangeTypeGenerator<1>::Register(AllTypes {}); + RangeTypeGenerator<2>::Register(AllTypes {}); + RangeTypeGenerator<3>::Register(AllTypes {}); + RangeTypeGenerator<4>::Register(AllTypes {}); + + + // Constants + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + } + +} // namespace Langulus::Math \ No newline at end of file diff --git a/source/Ranges/TRange.hpp b/source/Ranges/TRange.hpp index 0dc4a8a..cdb535f 100644 --- a/source/Ranges/TRange.hpp +++ b/source/Ranges/TRange.hpp @@ -15,6 +15,8 @@ namespace Langulus::Math { + LANGULUS_API(MATH) extern void RegisterRanges(); + TEMPLATE() struct TRange; using Range1f = TRange; @@ -100,39 +102,6 @@ namespace Langulus::A } // namespace Langulus::A -namespace Langulus -{ - - /// Custom name generator at compile-time for ranges - TEMPLATE() - consteval auto CustomName(Of&&) noexcept { - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - constexpr auto S = CountOf; - if constexpr (S > 4) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Range") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + S; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - - return name; - } -} - namespace Langulus::Math { @@ -148,17 +117,45 @@ namespace Langulus::Math static constexpr auto Default = T::Default; union { + // Useful representation for directly feeding to SIMD + MemberType mArray[MemberCount] {}; + struct { PointType mMin; PointType mMax; }; - - // Useful representation for directly feeding to SIMD - MemberType mArray[MemberCount]; }; public: - LANGULUS(NAME) CustomNameOf::Generate(); + /// Custom name generator at compile-time for ranges + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset = 0; + + constexpr auto S = CountOf; + if constexpr (S > 4) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Range") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + S; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + + return name; + } + + LANGULUS(NAME) GenerateToken(); LANGULUS(TYPED) MemberType; LANGULUS(POD) CT::POD; LANGULUS(NULLIFIABLE) CT::Nullifiable; @@ -173,64 +170,49 @@ namespace Langulus::Math static constexpr bool CTTI_RangeTrait = true; public: - constexpr TRange() noexcept; + constexpr TRange() noexcept = default; constexpr TRange(const TRange&) noexcept; constexpr TRange(const CT::Vector auto&) noexcept; constexpr TRange(const CT::Scalar auto&) noexcept; constexpr TRange(const PointType&, const PointType&) noexcept; constexpr TRange(const MemberType&, const MemberType&) noexcept; - #if LANGULUS_SIMD(128BIT) - TRange(const simde__m128&) noexcept; - TRange(const simde__m128d&) noexcept; - TRange(const simde__m128i&) noexcept; - #endif - - #if LANGULUS_SIMD(256BIT) - TRange(const simde__m256&) noexcept; - TRange(const simde__m256d&) noexcept; - TRange(const simde__m256i&) noexcept; - #endif - - #if LANGULUS_SIMD(512BIT) - TRange(const simde__m512&) noexcept; - TRange(const simde__m512d&) noexcept; - TRange(const simde__m512i&) noexcept; - #endif - + TRange(const CT::SIMD auto&) noexcept; TRange(Describe&&); /// /// Assignment /// - constexpr TRange& operator = (const TRange&) noexcept = default; - constexpr TRange& operator = (const CT::RangeBased auto&) noexcept; - constexpr TRange& operator = (const CT::VectorBased auto&) noexcept; - constexpr TRange& operator = (const CT::ScalarBased auto&) noexcept; + constexpr auto operator = (const TRange&) noexcept -> TRange& = default; + constexpr auto operator = (const CT::RangeBased auto&) noexcept -> TRange&; + constexpr auto operator = (const CT::VectorBased auto&) noexcept -> TRange&; + constexpr auto operator = (const CT::ScalarBased auto&) noexcept -> TRange&; template constexpr auto& operator = (const TVectorComponent&) noexcept; + NOD() explicit operator Anyness::Text() const; NOD() explicit operator Flow::Code() const; - constexpr TRange& Embrace(const auto&) noexcept; - constexpr TRange& ConstrainBy(const auto&) noexcept; + constexpr auto Embrace(const auto&) noexcept -> TRange&; + constexpr auto ConstrainBy(const auto&) noexcept -> TRange&; + + NOD() auto GetMin() const noexcept -> const PointType&; + NOD() auto GetMax() const noexcept -> const PointType&; + NOD() auto Length() const noexcept -> PointType; + NOD() auto Center() const noexcept -> PointType; - NOD() const PointType& GetMin() const noexcept; - NOD() const PointType& GetMax() const noexcept; - NOD() PointType Length() const noexcept; - NOD() PointType Center() const noexcept; NOD() constexpr bool IsDegenerate() const noexcept; NOD() constexpr bool Inside(const PointType&) const noexcept; NOD() constexpr bool IsInsideHalfClosed(const PointType&) const noexcept; - NOD() constexpr PointType ClampRev(const PointType&) const noexcept; - NOD() constexpr PointType Clamp(const PointType&) const noexcept; + NOD() constexpr auto ClampRev(const PointType&) const noexcept -> PointType; + NOD() constexpr auto Clamp(const PointType&) const noexcept -> PointType; - NOD() constexpr TRange operator | (const TRange&) const noexcept; - constexpr TRange& operator |= (const TRange&) noexcept; + NOD() constexpr auto operator | (const TRange&) const noexcept -> TRange ; + constexpr auto operator |= (const TRange&) noexcept -> TRange&; - NOD() constexpr MemberType& operator [] (Offset) noexcept; - NOD() constexpr const MemberType& operator [] (Offset) const noexcept; + NOD() constexpr auto operator [] (Offset) noexcept -> MemberType&; + NOD() constexpr auto operator [] (Offset) const noexcept -> const MemberType&; }; #pragma pack(pop) diff --git a/source/Ranges/TRange.inl b/source/Ranges/TRange.inl index 2255f8a..8610309 100644 --- a/source/Ranges/TRange.inl +++ b/source/Ranges/TRange.inl @@ -16,17 +16,11 @@ namespace Langulus::Math { - /// Default constructor - TEMPLATE() LANGULUS(INLINED) - constexpr TME()::TRange() noexcept - : mMin {} - , mMax {} {} - /// Copy constructor TEMPLATE() LANGULUS(INLINED) - constexpr TME()::TRange(const TRange& a) noexcept - : mMin {a.mMin} - , mMax {a.mMax} {} + constexpr TME()::TRange(const TRange& a) noexcept { + SIMD::Convert<0>(a.mArray, mArray); + } /// Construct the range sequentially, like so: /// minX, minY, minZ..., maxX, maxY, maxZ... @@ -43,66 +37,27 @@ namespace Langulus::Math /// Create range from a min and a max vectors TEMPLATE() LANGULUS(INLINED) - constexpr TME()::TRange(const PointType& min, const PointType& max) noexcept - : mMin {min} - , mMax {max} {} - - /// Create range from a min and a max scalars - TEMPLATE() LANGULUS(INLINED) - constexpr TME()::TRange(const MemberType& min, const MemberType& max) noexcept - : mMin {min} - , mMax {max} {} - -#if LANGULUS_SIMD(128BIT) - TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m128& source) noexcept { - SIMD::Store(source, mArray); - } - - TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m128d& source) noexcept { - SIMD::Store(source, mArray); - } - - TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m128i& source) noexcept { - SIMD::Store(source, mArray); - } -#endif - -#if LANGULUS_SIMD(256BIT) - TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m256& source) noexcept { - SIMD::Store(source, mArray); - } - - TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m256d& source) noexcept { - SIMD::Store(source, mArray); - } - - TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m256i& source) noexcept { - SIMD::Store(source, mArray); - } -#endif - -#if LANGULUS_SIMD(512BIT) - TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m512& source) noexcept { - SIMD::Store(source, mArray); + constexpr TME()::TRange(const PointType& min, const PointType& max) noexcept { + for (Count i = 0; i < CountOf; ++i) { + mArray[i] = min.all[i]; + mArray[i + CountOf] = max.all[i]; + } } + /// Create range from a min and a max scalars TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m512d& source) noexcept { - SIMD::Store(source, mArray); + constexpr TME()::TRange(const MemberType& min, const MemberType& max) noexcept { + for (Count i = 0; i < CountOf; ++i) { + mArray[i] = min; + mArray[i + CountOf] = max; + } } - + + /// Create from registers TEMPLATE() LANGULUS(INLINED) - TME()::TRange(const simde__m512i& source) noexcept { + TME()::TRange(const CT::SIMD auto& source) noexcept { SIMD::Store(source, mArray); } -#endif /// Construct from a descriptor /// @param describe - the descriptor to scan @@ -145,7 +100,7 @@ namespace Langulus::Math /// @param r - the range to copy /// @return a reference to this range TEMPLATE() LANGULUS(INLINED) - constexpr TME()& TME()::operator = (const CT::RangeBased auto& r) noexcept { + constexpr auto TME()::operator = (const CT::RangeBased auto& r) noexcept -> TRange& { return *new (this) TRange {DeintCast(r)}; } @@ -153,7 +108,7 @@ namespace Langulus::Math /// @param v - the vector to copy /// @return a reference to this range TEMPLATE() LANGULUS(INLINED) - constexpr TME()& TME()::operator = (const CT::VectorBased auto& v) noexcept { + constexpr auto TME()::operator = (const CT::VectorBased auto& v) noexcept -> TRange& { return *new (this) TRange {DeintCast(v)}; } @@ -161,16 +116,14 @@ namespace Langulus::Math /// @param s - the scalar value /// @return a reference to this range TEMPLATE() LANGULUS(INLINED) - constexpr TME()& TME()::operator = (const CT::ScalarBased auto& s) noexcept { + constexpr auto TME()::operator = (const CT::ScalarBased auto& s) noexcept -> TRange& { return *new (this) TRange {DeintCast(s)}; } /// Set only a specific component /// @param c - the component to overwrite /// @return a reference to this vector - TEMPLATE() - template - LANGULUS(INLINED) + TEMPLATE() template LANGULUS(INLINED) constexpr auto& TME()::operator = (const TVectorComponent& c) noexcept { return *new (this) TRange {PointType {c}}; } @@ -195,36 +148,36 @@ namespace Langulus::Math } TEMPLATE() LANGULUS(INLINED) - constexpr TME()& TME()::Embrace(const auto& other) noexcept { + constexpr auto TME()::Embrace(const auto& other) noexcept -> TRange& { mMin = Min(mMin, other); mMax = Max(mMax, other); return *this; } TEMPLATE() LANGULUS(INLINED) - constexpr TME()& TME()::ConstrainBy(const auto& limits) noexcept { + constexpr auto TME()::ConstrainBy(const auto& limits) noexcept -> TRange& { mMin = Clamp(mMin, limits.mMin, limits.mMax); mMax = Clamp(mMax, limits.mMin, limits.mMax); return *this; } TEMPLATE() LANGULUS(INLINED) - const typename TME()::PointType& TME()::GetMin() const noexcept { + auto TME()::GetMin() const noexcept -> const PointType& { return mMin; } TEMPLATE() LANGULUS(INLINED) - const typename TME()::PointType& TME()::GetMax() const noexcept { + auto TME()::GetMax() const noexcept -> const PointType& { return mMax; } TEMPLATE() LANGULUS(INLINED) - typename TME()::PointType TME()::Length() const noexcept { + auto TME()::Length() const noexcept -> PointType { return mMax - mMin; } TEMPLATE() LANGULUS(INLINED) - typename TME()::PointType TME()::Center() const noexcept { + auto TME()::Center() const noexcept -> PointType { return mMin + Length() * 0.5f; } @@ -244,17 +197,17 @@ namespace Langulus::Math } TEMPLATE() LANGULUS(INLINED) - constexpr typename TME()::PointType TME()::ClampRev(const PointType& pos) const noexcept { + constexpr auto TME()::ClampRev(const PointType& pos) const noexcept -> PointType { return pos.ClampRev(mMin, mMax); } TEMPLATE() LANGULUS(INLINED) - constexpr typename TME()::PointType TME()::Clamp(const PointType& pos) const noexcept { + constexpr auto TME()::Clamp(const PointType& pos) const noexcept -> PointType { return pos.Clamp(mMin, mMax); } TEMPLATE() LANGULUS(INLINED) - constexpr TME() TME()::operator | (const TME()& a) const noexcept { + constexpr auto TME()::operator | (const TME()& a) const noexcept -> TRange { return { mMin.Clamp(a.mMin, a.mMax), mMax.Clamp(a.mMin, a.mMax) @@ -262,7 +215,7 @@ namespace Langulus::Math } TEMPLATE() LANGULUS(INLINED) - constexpr TME()& TME()::operator |= (const TME()& a) noexcept { + constexpr auto TME()::operator |= (const TME()& a) noexcept -> TRange& { *this = *this | a; } @@ -273,12 +226,12 @@ namespace Langulus::Math /// minX minY minZ ... maxX maxY maxZ ... /// @returns a reference to the component TEMPLATE() LANGULUS(INLINED) - constexpr TypeOf& TME()::operator [] (const Offset a) noexcept { + constexpr auto TME()::operator [] (const Offset a) noexcept -> MemberType& { return mArray[a]; } TEMPLATE() LANGULUS(INLINED) - constexpr const TypeOf& TME()::operator [] (const Offset a) const noexcept { + constexpr auto TME()::operator [] (const Offset a) const noexcept -> const MemberType& { return mArray[a]; } @@ -434,8 +387,7 @@ namespace Langulus::Math /// /// Add - template - LANGULUS(INLINED) + template LANGULUS(INLINED) auto& operator += (TRange& me, const TRange& other) noexcept { me.mMin += other.mMin; me.mMax += other.mMax; @@ -443,8 +395,7 @@ namespace Langulus::Math } /// Subtract - template - LANGULUS(INLINED) + template LANGULUS(INLINED) auto& operator -= (TRange& me, const TRange& other) noexcept { me.mMin -= other.mMin; me.mMax -= other.mMax; @@ -452,8 +403,7 @@ namespace Langulus::Math } /// Multiply - template - LANGULUS(INLINED) + template LANGULUS(INLINED) auto& operator *= (TRange& me, const TRange& other) noexcept { me.mMin *= other.mMin; me.mMax *= other.mMax; @@ -461,8 +411,7 @@ namespace Langulus::Math } /// Divide - template - LANGULUS(INLINED) + template LANGULUS(INLINED) auto& operator /= (TRange& me, const TRange& other) { me.mMin /= other.mMin; me.mMax /= other.mMax; @@ -472,4 +421,55 @@ namespace Langulus::Math } // namespace Langulus::Math #undef TEMPLATE -#undef TME \ No newline at end of file +#undef TME + + +namespace Langulus::Ranges +{ + + using Math::Range3; + using Math::Vec3; + + //TODO use infinities instead of big numbers + constexpr Range3 In { -1, +1 }; + constexpr Range3 On { +1, +1 }; + constexpr Range3 Under { {-1, -1, -1}, {+1, -1, +1} }; + constexpr Range3 Above { {-1, +1, -1}, {+1, +1000, +1} }; + constexpr Range3 Below { {-1, -1000, -1}, {+1, -1, +1} }; + constexpr Range3 Center { 0, 0 }; + constexpr Range3 Middle { -0.5, +0.5 }; + constexpr Range3 Rear { {-1, -1, -1}, {+1, +1, -1} }; + constexpr Range3 Behind { {-1, -1, -1000}, {+1, +1, -1} }; + constexpr Range3 Front { {-1, -1, 1}, {+1, +1, 1} }; + constexpr Range3 Ahead { {-1, -1, 1}, {+1, +1, 1000} }; + constexpr Range3 Left { {-1000, -1, -1}, {-1, +1, +1} }; + constexpr Range3 Right { {1, -1, -1}, {1000, +1, +1} }; + +} // namespace Langulus::Ranges + +LANGULUS_DEFINE_CONSTANT(RangeIn, ::Langulus::Ranges::In, + "Ranges::In", "A canonical 'in' range") +LANGULUS_DEFINE_CONSTANT(RangeOn, ::Langulus::Ranges::On, + "Ranges::On", "A canonical 'on the surface' range") +LANGULUS_DEFINE_CONSTANT(RangeUnder, ::Langulus::Ranges::Under, + "Ranges::Under", "A canonical 'on the underside' range") +LANGULUS_DEFINE_CONSTANT(RangeAbove, ::Langulus::Ranges::Above, + "Ranges::Above", "A canonical 'above and beyond' range") +LANGULUS_DEFINE_CONSTANT(RangeBelow, ::Langulus::Ranges::Below, + "Ranges::Below", "A canonical 'below and beyond' range") +LANGULUS_DEFINE_CONSTANT(RangeCenter, ::Langulus::Ranges::Center, + "Ranges::Center", "A canonical center range (not really a range)") +LANGULUS_DEFINE_CONSTANT(RangeMiddle, ::Langulus::Ranges::Middle, + "Ranges::Middle", "A canonical 'middle' range") +LANGULUS_DEFINE_CONSTANT(RangeRear, ::Langulus::Ranges::Rear, + "Ranges::Rear", "A canonical 'on the rear surface' range") +LANGULUS_DEFINE_CONSTANT(RangeBehind, ::Langulus::Ranges::Behind, + "Ranges::Behind", "A canonical 'behind and beyond' range") +LANGULUS_DEFINE_CONSTANT(RangeFront, ::Langulus::Ranges::Front, + "Ranges::Front", "A canonical 'on the front surface' range") +LANGULUS_DEFINE_CONSTANT(RangeAhead, ::Langulus::Ranges::Ahead, + "Ranges::Ahead", "A canonical 'ahead and beyond' range") +LANGULUS_DEFINE_CONSTANT(RangeLeft, ::Langulus::Ranges::Left, + "Ranges::Left", "A canonical 'on the left and beyond' range") +LANGULUS_DEFINE_CONSTANT(RangeRight, ::Langulus::Ranges::Right, + "Ranges::Right", "A canonical 'on the right and beyond' range") diff --git a/source/SignedDistance/TBox.inl b/source/SignedDistance/TBox.inl index a9817b9..0903489 100644 --- a/source/SignedDistance/TBox.inl +++ b/source/SignedDistance/TBox.inl @@ -24,7 +24,7 @@ namespace Langulus::Math else if constexpr (C == 2) return Length(Max(d, T {0})) + Min(Max(d.x(), d.y()), T {0}); else - LANGULUS_ERROR("Unsupported box dimensions"); + static_assert(false, "Unsupported box dimensions"); }; } // namespace Langulus::Math diff --git a/source/SignedDistance/TBoxRounded.inl b/source/SignedDistance/TBoxRounded.inl index 93b5f00..fe9d8e7 100644 --- a/source/SignedDistance/TBoxRounded.inl +++ b/source/SignedDistance/TBoxRounded.inl @@ -24,7 +24,7 @@ namespace Langulus::Math else if constexpr (C == 2) return Length(Max(d, T {0})) + Min(Max(d.x(), d.y()), T {0}) - box.mRadius; else - LANGULUS_ERROR("Unsupported box dimensions"); + static_assert(false, "Unsupported box dimensions"); }; } // namespace Langulus::Math \ No newline at end of file diff --git a/source/SignedDistance/TCylinder.inl b/source/SignedDistance/TCylinder.inl index f34b33b..0e9650b 100644 --- a/source/SignedDistance/TCylinder.inl +++ b/source/SignedDistance/TCylinder.inl @@ -25,7 +25,7 @@ namespace Langulus::Math else if constexpr (CT::Same) return Length(point.xy()) - cylinder.mRadius; else - LANGULUS_ERROR("Unsupported dimension"); + static_assert(false, "Unsupported dimension"); }; } // namespace Langulus::Math diff --git a/source/TInstance.inl b/source/TInstance.inl index 0cf394f..016a6ae 100644 --- a/source/TInstance.inl +++ b/source/TInstance.inl @@ -303,7 +303,7 @@ namespace Langulus::Math else if constexpr (CT::Same) mAim *= QuatType::FromAxis(GetForward(), angle * sign); else - LANGULUS_ERROR("Unsupported dimension"); + static_assert(false, "Unsupported dimension"); } } diff --git a/source/Vectors/TNormal.hpp b/source/Vectors/TNormal.hpp index 85bf175..9ad4472 100644 --- a/source/Vectors/TNormal.hpp +++ b/source/Vectors/TNormal.hpp @@ -73,35 +73,6 @@ namespace Langulus } // namespace Langulus::A - /// Custom name generator at compile-time for normals - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TNormal; - constexpr auto MemberCount = CLASS::MemberCount; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (MemberCount > 4) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Normal") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - namespace Math { @@ -121,7 +92,34 @@ namespace Langulus static_assert(CT::Real>, "Normal can be only made of real numbers"); - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (MemberCount > 4) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Normal") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(TYPED) TypeOf; LANGULUS_BASES( A::NormalOfSize, diff --git a/source/Vectors/TSampler.hpp b/source/Vectors/TSampler.hpp index 3fb4317..5fbd10f 100644 --- a/source/Vectors/TSampler.hpp +++ b/source/Vectors/TSampler.hpp @@ -120,35 +120,6 @@ namespace Langulus } // namespace Langulus::A - /// Custom name generator at compile-time for samplers - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TSampler; - constexpr auto MemberCount = CLASS::MemberCount; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (MemberCount > 4) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Sampler") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - namespace Math { @@ -162,7 +133,34 @@ namespace Langulus using T::MemberCount; using T::T; - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (MemberCount > 4) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Sampler") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(TYPED) TypeOf; LANGULUS_BASES( A::SamplerOfSize, diff --git a/source/Vectors/TScale.hpp b/source/Vectors/TScale.hpp index 95b771e..1ed86d8 100644 --- a/source/Vectors/TScale.hpp +++ b/source/Vectors/TScale.hpp @@ -119,35 +119,6 @@ namespace Langulus } // namespace Langulus::A - /// Custom name generator at compile-time for scales - template - consteval auto CustomName(Of>&&) noexcept { - using CLASS = Math::TScale; - constexpr auto MemberCount = CLASS::MemberCount; - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (MemberCount > 4) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Scale") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + MemberCount; - - // Write suffix - for (auto i : SuffixOf>()) - name[offset++] = i; - return name; - } - namespace Math { @@ -160,7 +131,34 @@ namespace Langulus using T::MemberCount; using T::T; - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (MemberCount > 4) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Scale") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + MemberCount; + + // Write suffix + for (auto i : SuffixOf>()) + name[offset++] = i; + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(TYPED) TypeOf; LANGULUS_BASES( A::ScaleOfSize, diff --git a/source/Vectors/TVector.cpp b/source/Vectors/TVector.cpp index 010b9cb..1e091b0 100644 --- a/source/Vectors/TVector.cpp +++ b/source/Vectors/TVector.cpp @@ -21,7 +21,6 @@ namespace Langulus::Math } }; - /// Register all commonly used vector types and constants, so they can be /// instantiated from scripts void RegisterVectors() { @@ -36,19 +35,19 @@ namespace Langulus::Math VectorTypeGenerator<3>::Register(AllTypes {}); VectorTypeGenerator<4>::Register(AllTypes {}); - (void) MetaOf(); - (void) MetaOf(); - (void) MetaOf(); - (void) MetaOf(); - (void) MetaOf(); - (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); - (void) MetaOf(); - (void) MetaOf(); - (void) MetaOf(); - (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); + (void) MetaOf(); - (void) MetaOf(); + (void) MetaOf(); } } // namespace Langulus::Math \ No newline at end of file diff --git a/source/Vectors/TVector.hpp b/source/Vectors/TVector.hpp index 0222b7c..a0678a4 100644 --- a/source/Vectors/TVector.hpp +++ b/source/Vectors/TVector.hpp @@ -140,35 +140,6 @@ namespace Langulus } // namespace Langulus::A - - /// Custom name generator at compile-time for vectors - TEMPLATE() - consteval auto CustomName(Of&&) noexcept { - constexpr auto defaultClassName = RTTI::LastCppNameOf(); - ::std::array name {}; - ::std::size_t offset {}; - - if constexpr (S > 4) { - for (auto i : defaultClassName) - name[offset++] = i; - return name; - } - - // Write prefix - for (auto i : "Vec") - name[offset++] = i; - - // Write size - --offset; - name[offset++] = '0' + S; - - // Write suffix - for (auto i : SuffixOf()) - name[offset++] = i; - - return name; - } - } // namespace Langulus namespace Langulus::Math @@ -192,25 +163,25 @@ namespace Langulus::Math // This is necessary to work around the dependent names in TVector // This will also error out, when missing (), but if you happen to // call them by accident, you will get a proper compile error - void y() { LANGULUS_ERROR("1D vector doesn't have 'y' component"); } - void second() { LANGULUS_ERROR("1D vector doesn't have 'second' component"); } - void g() { LANGULUS_ERROR("1D vector doesn't have 'g' component"); } - void green() { LANGULUS_ERROR("1D vector doesn't have 'green' component"); } - void v() { LANGULUS_ERROR("1D vector doesn't have 'v' component"); } - - void z() { LANGULUS_ERROR("1D vector doesn't have 'z' component"); } - void third() { LANGULUS_ERROR("1D vector doesn't have 'third' component"); } - void b() { LANGULUS_ERROR("1D vector doesn't have 'b' component"); } - void blue() { LANGULUS_ERROR("1D vector doesn't have 'blue' component"); } - void s() { LANGULUS_ERROR("1D vector doesn't have 's' component"); } - - void w() { LANGULUS_ERROR("1D vector doesn't have 'w' component"); } - void fourth() { LANGULUS_ERROR("1D vector doesn't have 'fourth' component"); } - void a() { LANGULUS_ERROR("1D vector doesn't have 'a' component"); } - void alpha() { LANGULUS_ERROR("1D vector doesn't have 'alpha' component"); } - void t() { LANGULUS_ERROR("1D vector doesn't have 't' component"); } - - void tail() { LANGULUS_ERROR("1D vector doesn't have a tail"); } + void y() { static_assert(false, "1D vector doesn't have 'y' component"); } + void second() { static_assert(false, "1D vector doesn't have 'second' component"); } + void g() { static_assert(false, "1D vector doesn't have 'g' component"); } + void green() { static_assert(false, "1D vector doesn't have 'green' component"); } + void v() { static_assert(false, "1D vector doesn't have 'v' component"); } + + void z() { static_assert(false, "1D vector doesn't have 'z' component"); } + void third() { static_assert(false, "1D vector doesn't have 'third' component"); } + void b() { static_assert(false, "1D vector doesn't have 'b' component"); } + void blue() { static_assert(false, "1D vector doesn't have 'blue' component"); } + void s() { static_assert(false, "1D vector doesn't have 's' component"); } + + void w() { static_assert(false, "1D vector doesn't have 'w' component"); } + void fourth() { static_assert(false, "1D vector doesn't have 'fourth' component"); } + void a() { static_assert(false, "1D vector doesn't have 'a' component"); } + void alpha() { static_assert(false, "1D vector doesn't have 'alpha' component"); } + void t() { static_assert(false, "1D vector doesn't have 't' component"); } + + void tail() { static_assert(false, "1D vector doesn't have a tail"); } LANGULUS_MEMBERS(&TVectorBase::x); @@ -250,19 +221,19 @@ namespace Langulus::Math // This is necessary to work around the dependent names in TVector // This will also error out, when missing (), but if you happen to // call them by accident, you will get a proper compile error - void z() { LANGULUS_ERROR("2D vector doesn't have 'z' component"); } - void third() { LANGULUS_ERROR("2D vector doesn't have 'third' component"); } - void b() { LANGULUS_ERROR("2D vector doesn't have 'b' component"); } - void blue() { LANGULUS_ERROR("2D vector doesn't have 'blue' component"); } - void s() { LANGULUS_ERROR("2D vector doesn't have 's' component"); } + void z() { static_assert(false, "2D vector doesn't have 'z' component"); } + void third() { static_assert(false, "2D vector doesn't have 'third' component"); } + void b() { static_assert(false, "2D vector doesn't have 'b' component"); } + void blue() { static_assert(false, "2D vector doesn't have 'blue' component"); } + void s() { static_assert(false, "2D vector doesn't have 's' component"); } - void w() { LANGULUS_ERROR("2D vector doesn't have 'w' component"); } - void fourth() { LANGULUS_ERROR("2D vector doesn't have 'fourth' component"); } - void a() { LANGULUS_ERROR("2D vector doesn't have 'a' component"); } - void alpha() { LANGULUS_ERROR("2D vector doesn't have 'alpha' component"); } - void t() { LANGULUS_ERROR("2D vector doesn't have 't' component"); } + void w() { static_assert(false, "2D vector doesn't have 'w' component"); } + void fourth() { static_assert(false, "2D vector doesn't have 'fourth' component"); } + void a() { static_assert(false, "2D vector doesn't have 'a' component"); } + void alpha() { static_assert(false, "2D vector doesn't have 'alpha' component"); } + void t() { static_assert(false, "2D vector doesn't have 't' component"); } - void tail() { LANGULUS_ERROR("2D vector doesn't have a tail"); } + void tail() { static_assert(false, "2D vector doesn't have a tail"); } LANGULUS_MEMBERS(&TVectorBase::x, &TVectorBase::y); @@ -305,13 +276,13 @@ namespace Langulus::Math // This is necessary to work around the dependent names in TVector // This will also error out, when missing (), but if you happen to // call them by accident, you will get a proper compile error - void w() { LANGULUS_ERROR("3D vector doesn't have 'w' component"); } - void fourth() { LANGULUS_ERROR("3D vector doesn't have 'fourth' component"); } - void a() { LANGULUS_ERROR("3D vector doesn't have 'a' component"); } - void alpha() { LANGULUS_ERROR("3D vector doesn't have 'alpha' component"); } - void t() { LANGULUS_ERROR("3D vector doesn't have 't' component"); } + void w() { static_assert(false, "3D vector doesn't have 'w' component"); } + void fourth() { static_assert(false, "3D vector doesn't have 'fourth' component"); } + void a() { static_assert(false, "3D vector doesn't have 'a' component"); } + void alpha() { static_assert(false, "3D vector doesn't have 'alpha' component"); } + void t() { static_assert(false, "3D vector doesn't have 't' component"); } - void tail() { LANGULUS_ERROR("3D vector doesn't have a tail"); } + void tail() { static_assert(false, "3D vector doesn't have a tail"); } LANGULUS_MEMBERS(&TVectorBase::x, &TVectorBase::y, &TVectorBase::z); @@ -351,7 +322,7 @@ namespace Langulus::Math }; }; - void tail() { LANGULUS_ERROR("4D vector doesn't have a tail"); } + void tail() { static_assert(false, "4D vector doesn't have a tail"); } LANGULUS_MEMBERS(&TVectorBase::x, &TVectorBase::y, &TVectorBase::z, &TVectorBase::w); @@ -436,7 +407,35 @@ namespace Langulus::Math using ArrayType = T[S]; using Base = TVectorBase; - LANGULUS(NAME) CustomNameOf::Generate(); + private: + static consteval auto GenerateToken() { + constexpr auto defaultClassName = RTTI::LastCppNameOf(); + ::std::array name {}; + ::std::size_t offset {}; + + if constexpr (S > 4) { + for (auto i : defaultClassName) + name[offset++] = i; + return name; + } + + // Write prefix + for (auto i : "Vec") + name[offset++] = i; + + // Write size + --offset; + name[offset++] = '0' + S; + + // Write suffix + for (auto i : SuffixOf()) + name[offset++] = i; + + return name; + } + + public: + LANGULUS(NAME) GenerateToken(); LANGULUS(ABSTRACT) false; LANGULUS(POD) CT::POD; LANGULUS(NULLIFIABLE) DEFAULT == 0; @@ -669,8 +668,7 @@ namespace Langulus::Math /// template struct TProxyArray : TVector { - LANGULUS(UNINSERTABLE) true; - LANGULUS(REFLECTABLE) false; + LANGULUS(ACT_AS) void; static_assert(sizeof...(I) > 1, "Invalid proxy array size"); static constexpr bool CTTI_VectorTrait = false; static constexpr bool CTTI_ProxyArray = true; diff --git a/source/Vectors/TVector.inl b/source/Vectors/TVector.inl index c4e6e28..93ab584 100644 --- a/source/Vectors/TVector.inl +++ b/source/Vectors/TVector.inl @@ -107,7 +107,9 @@ namespace Langulus::Math static_assert(D::Index < S, "LHS doesn't have such dimension"); all[D::Index] = Adapt(source.mValue); } - + + /// Construct from a SIMD register + /// @param source - register TEMPLATE() LANGULUS(INLINED) TME()::TVector(const CT::SIMD auto& source) noexcept { SIMD::Store(source, all); @@ -1667,27 +1669,27 @@ namespace Langulus::Axes } // Langulus::Axes -LANGULUS_DEFINE_CONSTANT(Forward, ::Langulus::Axes::Forward<>, +LANGULUS_DEFINE_CONSTANT(AxisForward, ::Langulus::Axes::Forward<>, "Axes::Forward", "A canonical forward vector") -LANGULUS_DEFINE_CONSTANT(Backward, ::Langulus::Axes::Backward<>, +LANGULUS_DEFINE_CONSTANT(AxisBackward, ::Langulus::Axes::Backward<>, "Axes::Backward", "A canonical backward vector") -LANGULUS_DEFINE_CONSTANT(Up, ::Langulus::Axes::Up<>, +LANGULUS_DEFINE_CONSTANT(AxisUp, ::Langulus::Axes::Up<>, "Axes::Up", "A canonical up vector") -LANGULUS_DEFINE_CONSTANT(Down, ::Langulus::Axes::Down<>, +LANGULUS_DEFINE_CONSTANT(AxisDown, ::Langulus::Axes::Down<>, "Axes::Down", "A canonical down vector") -LANGULUS_DEFINE_CONSTANT(Right, ::Langulus::Axes::Right<>, +LANGULUS_DEFINE_CONSTANT(AxisRight, ::Langulus::Axes::Right<>, "Axes::Right", "A canonical right vector") -LANGULUS_DEFINE_CONSTANT(Left, ::Langulus::Axes::Left<>, +LANGULUS_DEFINE_CONSTANT(AxisLeft, ::Langulus::Axes::Left<>, "Axes::Left", "A canonical left vector") -LANGULUS_DEFINE_CONSTANT(X, ::Langulus::Axes::X<>, +LANGULUS_DEFINE_CONSTANT(AxisX, ::Langulus::Axes::X<>, "Axes::X", "A canonical X axis") -LANGULUS_DEFINE_CONSTANT(Y, ::Langulus::Axes::Y<>, +LANGULUS_DEFINE_CONSTANT(AxisY, ::Langulus::Axes::Y<>, "Axes::Y", "A canonical Y axis") -LANGULUS_DEFINE_CONSTANT(Z, ::Langulus::Axes::Z<>, +LANGULUS_DEFINE_CONSTANT(AxisZ, ::Langulus::Axes::Z<>, "Axes::Z", "A canonical Z axis") -LANGULUS_DEFINE_CONSTANT(W, ::Langulus::Axes::W<>, +LANGULUS_DEFINE_CONSTANT(AxisW, ::Langulus::Axes::W<>, "Axes::W", "A canonical W axis") -LANGULUS_DEFINE_CONSTANT(Origin, ::Langulus::Axes::Origin<>, +LANGULUS_DEFINE_CONSTANT(AxisOrigin, ::Langulus::Axes::Origin<>, "Origin", "A canonical zero vector") diff --git a/source/Verbs/Add.inl b/source/Verbs/Add.inl index f6a4ce0..8bfa16a 100644 --- a/source/Verbs/Add.inl +++ b/source/Verbs/Add.inl @@ -8,6 +8,7 @@ #pragma once #include "Add.hpp" #include "Arithmetic.inl" +#include "../Numbers/Infinity.hpp" #if 0 #define VERBOSE_ADD(...) Logger::Verbose(__VA_ARGS__) @@ -180,6 +181,19 @@ namespace Langulus::Verbs return true; } } + else if (verb.CastsTo()) { + if (verb.GetMass() < 0) { + // Negate infinity + verb.ForEach([&](Math::Infinity i) { + verb << Math::Infinity {-i.mOrder}; + }); + } + else { + // Don't do anything + verb << verb.GetArgument(); + return true; + } + } return false; } diff --git a/source/Verbs/Arithmetic.inl b/source/Verbs/Arithmetic.inl index a2a8aa3..bc2f334 100644 --- a/source/Verbs/Arithmetic.inl +++ b/source/Verbs/Arithmetic.inl @@ -81,7 +81,7 @@ namespace Langulus::Flow // MVulkan to incorporate compute shader for even batcher batching!!1 //TODO detect underflows and overflows TMany result; - result.Reserve(lhs.GetCount()); + result.template Reserve(lhs.GetCount()); const T* ilhs = lhs.GetRaw(); const T* const ilhsEnd = ilhs + lhs.GetCount(); const T& irhs = *rhs.GetRaw(); diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index 9cae60f..e5e945e 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -4,14 +4,7 @@ file(GLOB_RECURSE *.cpp ) -add_executable(LangulusMathTest ${LANGULUS_MATH_TEST_SOURCES}) - -target_link_libraries(LangulusMathTest - PRIVATE LangulusMath - Catch2 -) - -add_test( - NAME LangulusMathTest - COMMAND LangulusMathTest +add_langulus_test(LangulusMathTest + SOURCES ${LANGULUS_MATH_TEST_SOURCES} + LIBRARIES LangulusMath ) \ No newline at end of file diff --git a/test/Main.cpp b/test/Main.cpp index 85cc047..9a49738 100644 --- a/test/Main.cpp +++ b/test/Main.cpp @@ -16,6 +16,7 @@ #include #include +#include #include #define CATCH_CONFIG_RUNNER @@ -28,6 +29,7 @@ int main(int argc, char* argv[]) { Math::RegisterTraits(); Math::RegisterVerbs(); Math::RegisterVectors(); + Math::RegisterRanges(); Catch::Session session; return session.run(argc, argv); diff --git a/test/Main.hpp b/test/Main.hpp index ec2720d..0985337 100644 --- a/test/Main.hpp +++ b/test/Main.hpp @@ -26,7 +26,6 @@ using namespace ::Langulus::Math; /// A mockup of a fraction struct Fraction : public Flow::Resolvable { LANGULUS(ABSTRACT) false; - LANGULUS(UNINSERTABLE) false; LANGULUS_BASES(Resolvable); Fraction() : Resolvable {this} {} }; diff --git a/test/TestFlow.cpp b/test/TestFlow.cpp index 79e6b45..ce4284e 100644 --- a/test/TestFlow.cpp +++ b/test/TestFlow.cpp @@ -24,11 +24,9 @@ SCENARIO("Parsing scripts", "[code]") { const auto code = "- 4 ^ 2"_code; WHEN("Parsed without optimization") { - Many required = Verbs::Add { - Many {Verbs::Exponent {Real(2)} - .SetSource(Real(4)) - } - }.SetMass(-1); + Many required = Verbs::Add {Many { + Verbs::Exponent {Real(2)}.SetSource(Real(4)) + }}.SetMass(-1); const auto parsed = code.Parse(false); DumpResults(code, parsed, required); @@ -44,17 +42,17 @@ SCENARIO("Parsing scripts", "[code]") { } } - GIVEN("The script: - .Sampler.y ^ 2") { - const auto code = "- .Sampler.y ^ 2"_code; + GIVEN("The script: - .sampler.y ^ 2") { + const auto code = "- .sampler.y ^ 2"_code; WHEN("Parsed without optimization") { - Many required = Verbs::Add { - Many {Verbs::Exponent {Real(2)} - .SetSource(Verbs::Select {MetaOf()} - .SetSource(Verbs::Select {MetaOf()}) + Many required = Verbs::Add {Many { + Verbs::Exponent {Real(2)}.SetSource( + Verbs::Select {MetaOf()}.SetSource( + Verbs::Select {MetaOf()} ) - } - }.SetMass(-1); + ) + }}.SetMass(-1); const auto parsed = code.Parse(); DumpResults(code, parsed, required); @@ -62,30 +60,28 @@ SCENARIO("Parsing scripts", "[code]") { } } - GIVEN("The script: Vec2(.Sampler.x, -(.Time * 8.75 - .Sampler.y ^ 2))") { - const auto code = "Vec2(.Sampler.x, -(.Time * 8.75 - .Sampler.y ^ 2))"_code; + GIVEN("The script: Vec2(.sampler.x, -(.time * 8.75 - .sampler.y ^ 2))") { + const auto code = "Vec2(.sampler.x, -(.time * 8.75 - .sampler.y ^ 2))"_code; WHEN("Parsed without optimization") { - Many required = Construct::From( - Verbs::Select {MetaOf()} - .SetSource( - Verbs::Select {MetaOf()} - ), - Verbs::Add { - Many {Verbs::Add { - Many {Verbs::Exponent {Real(2)} - .SetSource( - Verbs::Select {MetaOf()} - .SetSource(Verbs::Select {MetaOf()}) - )} - }.SetSource( - Verbs::Multiply {Real(8.75)} - .SetSource( - Verbs::Select {MetaOf()} + Many required = Construct::From(Many::Wrap( + Verbs::Select {MetaOf()}.SetSource( + Verbs::Select {MetaOf()} + ), + Verbs::Add {Many { + Verbs::Add {Many { + Verbs::Exponent {Real(2)}.SetSource( + Verbs::Select {MetaOf()}.SetSource( + Verbs::Select {MetaOf()} ) - ).SetMass(-1)} - }.SetMass(-1) - ); + ) + }}.SetSource( + Verbs::Multiply {Real(8.75)}.SetSource( + Verbs::Select {MetaOf()} + ) + ).SetMass(-1) + }}.SetMass(-1) + )); const auto parsed = code.Parse(); DumpResults(code, parsed, required); @@ -95,11 +91,9 @@ SCENARIO("Parsing scripts", "[code]") { GIVEN("The script: Create^1(Count(1)) Add^3 2") { const Code code = "Create^1(Count(1)) Add^3 2"; - const Many required = Verbs::Add {Real(2)} - .SetSource( - Verbs::Create {Traits::Count {Real(1)}} - .SetRate(1)) - .SetRate(3); + const Many required = Verbs::Add {Real(2)}.SetSource( + Verbs::Create {Traits::Count {Real(1)}}.SetRate(1) + ).SetRate(3); WHEN("Parsed") { const auto parsed = code.Parse(); @@ -110,11 +104,9 @@ SCENARIO("Parsing scripts", "[code]") { GIVEN("The script: Create^1(Count(1)) Add^3(2)") { const Code code = "Create^1(Count(1)) Add^3(2)"; - const Many required = Verbs::Add {Real(2)} - .SetSource( - Verbs::Create {Traits::Count {Real(1)}} - .SetRate(1)) - .SetRate(3); + const Many required = Verbs::Add {Real(2)}.SetSource( + Verbs::Create {Traits::Count {Real(1)}}.SetRate(1) + ).SetRate(3); WHEN("Parsed") { const auto parsed = code.Parse(); @@ -126,13 +118,10 @@ SCENARIO("Parsing scripts", "[code]") { GIVEN("The script: Create^1(Count(1)) Add^2(2) Multiply^3(4)") { const Code code = "Create^1(Count(1)) Add^2(2) Multiply^3(4)"; const Many multiply = Verbs::Multiply {Real(4)} - .SetSource(Real(2)) - .SetRate(3); + .SetSource(Real(2)).SetRate(3); const Many required = Verbs::Add {multiply} - .SetRate(2) - .SetSource( - Verbs::Create {Traits::Count {Real(1)}} - .SetRate(1) + .SetRate(2).SetSource( + Verbs::Create {Traits::Count {Real(1)}}.SetRate(1) ); WHEN("Parsed") { @@ -144,10 +133,8 @@ SCENARIO("Parsing scripts", "[code]") { GIVEN("The script: Create^1(Count(1)) + 2 * 4") { const Code code = "Create^1(Count(1)) + 2 * 4"; - const Many required = Verbs::Add {Real(8)} - .SetSource( - Verbs::Create {Traits::Count {Real(1)}} - .SetRate(1) + const Many required = Verbs::Add {Real(8)}.SetSource( + Verbs::Create {Traits::Count {Real(1)}}.SetRate(1) ); WHEN("Parsed") { @@ -162,10 +149,8 @@ SCENARIO("Parsing scripts", "[code]") { const Many exponent = Verbs::Exponent {Real(2)} .SetSource(Real(14)); const Many addition = Verbs::Add {exponent} - .SetMass(-1) - .SetSource( - Verbs::Multiply {Real(8.75)} - .SetSource(Real(2)) + .SetMass(-1).SetSource( + Verbs::Multiply {Real(8.75)}.SetSource(Real(2)) ); const Many required = Verbs::Add {addition} .SetMass(-1); diff --git a/test/TestVectors.cpp b/test/TestVectors.cpp index 694d7bf..ad0da26 100644 --- a/test/TestVectors.cpp +++ b/test/TestVectors.cpp @@ -69,7 +69,7 @@ TEMPLATE_TEST_CASE("Vectors", "[vec]", else if constexpr (C == 4) REQUIRE(x.HSum() == (1 + 5 + 12 + 1)); else - LANGULUS_ERROR("TODO"); + static_assert(false, "TODO"); } WHEN("Horizontally multiplying a vector") { @@ -84,7 +84,7 @@ TEMPLATE_TEST_CASE("Vectors", "[vec]", else if constexpr (C == 4) REQUIRE(x.HMul() == (1 * 5 * 12 * 1)); else - LANGULUS_ERROR("TODO"); + static_assert(false, "TODO"); } WHEN("Testing swizzling (const)") { @@ -115,7 +115,7 @@ TEMPLATE_TEST_CASE("Vectors", "[vec]", REQUIRE(cx.zyxw() == TVector {12, 5, 1, 1}); REQUIRE(cx.wyzx() == TVector { 1, 5, 12, 1}); } - else LANGULUS_ERROR("TODO"); + else static_assert(false, "TODO"); } WHEN("Testing swizzling (mutable, using proxy arrays)") { @@ -145,7 +145,7 @@ TEMPLATE_TEST_CASE("Vectors", "[vec]", REQUIRE(x.zyxw() == TVector {12, 5, 1, 1}); REQUIRE(x.wyzx() == TVector { 1, 5, 12, 1}); } - else LANGULUS_ERROR("TODO"); + else static_assert(false, "TODO"); } } @@ -224,17 +224,17 @@ TEMPLATE_TEST_CASE("Vectors", "[vec]", } else if constexpr (CountOf == 2) { const auto serialized = static_cast(x); - const Anyness::Text required = MetaDataOf()->mToken + "(0, 5)"_text; + const Anyness::Text required = MetaDataOf() + "(0, 5)"_text; REQUIRE(serialized == required); } else if constexpr (CountOf == 3) { const auto serialized = static_cast(x); - const Anyness::Text required = MetaDataOf()->mToken + "(0, 5, 12)"_text; + const Anyness::Text required = MetaDataOf() + "(0, 5, 12)"_text; REQUIRE(serialized == required); } else if constexpr (CountOf == 4) { const auto serialized = static_cast(x); - const Anyness::Text required = MetaDataOf()->mToken + "(0, 5, 12, 1)"_text; + const Anyness::Text required = MetaDataOf() + "(0, 5, 12, 1)"_text; REQUIRE(serialized == required); } } @@ -246,17 +246,17 @@ TEMPLATE_TEST_CASE("Vectors", "[vec]", } else if constexpr (CountOf == 2) { const auto serialized = static_cast(x); - const Flow::Code required = MetaDataOf()->mToken + "(0, 5)"_text; + const Flow::Code required = MetaDataOf() + "(0, 5)"_text; REQUIRE(serialized == required); } else if constexpr (CountOf == 3) { const auto serialized = static_cast(x); - const Flow::Code required = MetaDataOf()->mToken + "(0, 5, 12)"_text; + const Flow::Code required = MetaDataOf() + "(0, 5, 12)"_text; REQUIRE(serialized == required); } else if constexpr (CountOf == 4) { const auto serialized = static_cast(x); - const Flow::Code required = MetaDataOf()->mToken + "(0, 5, 12, 1)"_text; + const Flow::Code required = MetaDataOf() + "(0, 5, 12, 1)"_text; REQUIRE(serialized == required); } } @@ -279,17 +279,17 @@ TEMPLATE_TEST_CASE("Vectors", "[vec]", } else if constexpr (CountOf == 2) { const auto serialized = static_cast(x); - const Anyness::Text required = MetaDataOf()->mToken + "(0, ~5)"_text; + const Anyness::Text required = MetaDataOf() + "(0, ~5)"_text; REQUIRE(serialized == required); } else if constexpr (CountOf == 3) { const auto serialized = static_cast(x); - const Anyness::Text required = MetaDataOf()->mToken + "(0, ~5, ~-12.53)"_text; + const Anyness::Text required = MetaDataOf() + "(0, ~5, ~-12.53)"_text; REQUIRE(serialized == required); } else if constexpr (CountOf == 4) { const auto serialized = static_cast(x); - const Anyness::Text required = MetaDataOf()->mToken + "(0, ~5, ~-12.53, 6666.1)"_text; + const Anyness::Text required = MetaDataOf() + "(0, ~5, ~-12.53, 6666.1)"_text; REQUIRE(serialized == required); } } @@ -301,17 +301,17 @@ TEMPLATE_TEST_CASE("Vectors", "[vec]", } else if constexpr (CountOf == 2) { const auto serialized = static_cast(x); - const Flow::Code required = MetaDataOf()->mToken + "(0, 5.00001)"_text; + const Flow::Code required = MetaDataOf() + "(0, 5.00001)"_text; REQUIRE(serialized == required); } else if constexpr (CountOf == 3) { const auto serialized = static_cast(x); - const Flow::Code required = MetaDataOf()->mToken + "(0, 5.00001, -12.532)"_text; + const Flow::Code required = MetaDataOf() + "(0, 5.00001, -12.532)"_text; REQUIRE(serialized == required); } else if constexpr (CountOf == 4) { const auto serialized = static_cast(x); - const Flow::Code required = MetaDataOf()->mToken + "(0, 5.00001, -12.532, 6666.1)"_text; + const Flow::Code required = MetaDataOf() + "(0, 5.00001, -12.532, 6666.1)"_text; REQUIRE(serialized == required); } }