From 62ac07815ceb01a941b2d10944d7f1b64fb99ca2 Mon Sep 17 00:00:00 2001 From: Joshua Moerman Date: Sat, 20 Sep 2014 16:56:24 +0200 Subject: [PATCH] Adds scalar multiplication for all types --- glm/gtx/scalar_multiplication.hpp | 91 ++++++++++++++++++++++++++ test/gtx/CMakeLists.txt | 1 + test/gtx/gtx_scalar_multiplication.cpp | 32 +++++++++ 3 files changed, 124 insertions(+) create mode 100644 glm/gtx/scalar_multiplication.hpp create mode 100644 test/gtx/gtx_scalar_multiplication.cpp diff --git a/glm/gtx/scalar_multiplication.hpp b/glm/gtx/scalar_multiplication.hpp new file mode 100644 index 00000000..0baa2c13 --- /dev/null +++ b/glm/gtx/scalar_multiplication.hpp @@ -0,0 +1,91 @@ +/////////////////////////////////////////////////////////////////////////////////// +/// OpenGL Mathematics (glm.g-truc.net) +/// +/// Copyright (c) 2005 - 2014 G-Truc Creation (www.g-truc.net) +/// Permission is hereby granted, free of charge, to any person obtaining a copy +/// of this software and associated documentation files (the "Software"), to deal +/// in the Software without restriction, including without limitation the rights +/// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +/// copies of the Software, and to permit persons to whom the Software is +/// furnished to do so, subject to the following conditions: +/// +/// The above copyright notice and this permission notice shall be included in +/// all copies or substantial portions of the Software. +/// +/// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +/// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +/// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +/// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +/// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +/// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +/// THE SOFTWARE. +/// +/// @ref gtx +/// @file glm/gtx/scalar_multiplication.hpp +/// @date 2014-09-22 / 2014-09-22 +/// @author Joshua Moerman +/// +/// @brief Enables scalar multiplication for all types +/// +/// Since GLSL is very strict about types, the following (often used) combinations do not work: +/// double * vec4 +/// int * vec4 +/// vec4 / int +/// So we'll fix that! Of course "float * vec4" should remain the same (hence the enable_if magic) +/// +/////////////////////////////////////////////////////////////////////////////////// + +#pragma once + +#include "../vec2.hpp" +#include "../vec3.hpp" +#include "../vec4.hpp" +#include "../mat2x2.hpp" +#include + +namespace glm{ +namespace detail +{ + template + using return_type_scalar_multiplication = typename std::enable_if< + !std::is_same::value // T may not be a float + && std::is_arithmetic::value, Vec // But it may be an int or double (no vec3 or mat3, ...) + >::type; + +#define GLM_IMPLEMENT_SCAL_MULT(Vec) \ + template \ + return_type_scalar_multiplication \ + operator*(T const & s, Vec rh){ \ + return rh *= static_cast(s); \ + } \ + \ + template \ + return_type_scalar_multiplication \ + operator*(Vec lh, T const & s){ \ + return lh *= static_cast(s); \ + } \ + \ + template \ + return_type_scalar_multiplication \ + operator/(Vec lh, T const & s){ \ + return lh *= 1.0f / s; \ + } + +GLM_IMPLEMENT_SCAL_MULT(vec2) +GLM_IMPLEMENT_SCAL_MULT(vec3) +GLM_IMPLEMENT_SCAL_MULT(vec4) + +GLM_IMPLEMENT_SCAL_MULT(mat2) +GLM_IMPLEMENT_SCAL_MULT(mat2x3) +GLM_IMPLEMENT_SCAL_MULT(mat2x4) +GLM_IMPLEMENT_SCAL_MULT(mat3x2) +GLM_IMPLEMENT_SCAL_MULT(mat3) +GLM_IMPLEMENT_SCAL_MULT(mat3x4) +GLM_IMPLEMENT_SCAL_MULT(mat4x2) +GLM_IMPLEMENT_SCAL_MULT(mat4x3) +GLM_IMPLEMENT_SCAL_MULT(mat4) + +#undef GLM_IMPLEMENT_SCAL_MULT + +} // namespace detail +} // namespace glm diff --git a/test/gtx/CMakeLists.txt b/test/gtx/CMakeLists.txt index e93fa17c..7ac579f2 100644 --- a/test/gtx/CMakeLists.txt +++ b/test/gtx/CMakeLists.txt @@ -40,6 +40,7 @@ glmCreateTestGTC(gtx_quaternion) glmCreateTestGTC(gtx_dual_quaternion) glmCreateTestGTC(gtx_rotate_normalized_axis) glmCreateTestGTC(gtx_rotate_vector) +glmCreateTestGTC(gtx_scalar_multiplication) glmCreateTestGTC(gtx_scalar_relational) glmCreateTestGTC(gtx_simd_vec4) glmCreateTestGTC(gtx_simd_mat4) diff --git a/test/gtx/gtx_scalar_multiplication.cpp b/test/gtx/gtx_scalar_multiplication.cpp new file mode 100644 index 00000000..29b6bb3f --- /dev/null +++ b/test/gtx/gtx_scalar_multiplication.cpp @@ -0,0 +1,32 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// OpenGL Mathematics Copyright (c) 2005 - 2014 G-Truc Creation (www.g-truc.net) +/////////////////////////////////////////////////////////////////////////////////////////////////// +// Created : 2014-09-22 +// Updated : 2014-09-22 +// Licence : This source is under MIT licence +// File : test/gtx/gtx_scalar_multiplication.cpp +/////////////////////////////////////////////////////////////////////////////////////////////////// + +#include +#include + +int main() +{ + int Error(0); + glm::vec3 v(0.5, 3.1, -9.1); + + Error += glm::all(glm::equal(v, 1.0 * v)) ? 0 : 1; + Error += glm::all(glm::equal(v, 1 * v)) ? 0 : 1; + Error += glm::all(glm::equal(v, 1u * v)) ? 0 : 1; + + glm::mat3 m(1, 2, 3, 4, 5, 6, 7, 8, 9); + glm::vec3 w = 0.5f * m * v; + + Error += glm::all(glm::equal((m*v)/2, w)) ? 0 : 1; + Error += glm::all(glm::equal(m*(v/2), w)) ? 0 : 1; + Error += glm::all(glm::equal((m/2)*v, w)) ? 0 : 1; + Error += glm::all(glm::equal((0.5*m)*v, w)) ? 0 : 1; + Error += glm::all(glm::equal(0.5*(m*v), w)) ? 0 : 1; + + return Error; +}