Merge pull request #3 from Lauchmelder23/transformable

Transformable now works
This commit is contained in:
Lauchmelder 2021-01-23 16:45:54 +01:00 committed by GitHub
commit a9f169deba
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
9 changed files with 234 additions and 246 deletions

View file

@ -28,7 +28,7 @@ add_library(openglu SHARED
${include_files} ${include_files}
${source_files} ${source_files}
"cpp.hint" "cpp.hint"
"src/transformable.cpp") )
target_compile_definitions(openglu PRIVATE OGLU_BUILD_DLL) target_compile_definitions(openglu PRIVATE OGLU_BUILD_DLL)
@ -48,7 +48,6 @@ if(${build_documentation})
COMMAND ${DOXYGEN_EXECUTABLE} "${CMAKE_BINARY_DIR}/doxyfile" COMMAND ${DOXYGEN_EXECUTABLE} "${CMAKE_BINARY_DIR}/doxyfile"
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR} WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
COMMENT "Building documentation..." COMMENT "Building documentation..."
VERBATIM
) )
endif() endif()

View file

@ -1,4 +1,4 @@
add_executable(debug "main.cpp") add_executable(debug "main.cpp" "shaders/fragmentShader.frag" "shaders/vertexShader.vert")
find_package(glfw3 REQUIRED) find_package(glfw3 REQUIRED)

View file

@ -86,13 +86,11 @@ int main(int argc, char** argv)
oglu::Texture crate = oglu::MakeTexture("assets/crate.jpg"); oglu::Texture crate = oglu::MakeTexture("assets/crate.jpg");
oglu::Texture opengl = oglu::MakeTexture("assets/opengl.png"); oglu::Texture opengl = oglu::MakeTexture("assets/opengl.png");
glm::mat4 view = glm::mat4(1.0f); oglu::Camera camera;
view = glm::translate(view, glm::vec3(0.0f, 0.0f, -5.0f)); camera.Move(0.0f, 0.0f, -5.0f);
glm::mat4 projection;
projection = glm::perspective(glm::radians(45.f), 1.0f, 0.1f, 100.0f);
// Window loop // Window loop
float t = 0.0f;
while (!glfwWindowShouldClose(window)) while (!glfwWindowShouldClose(window))
{ {
processInput(window); processInput(window);
@ -101,15 +99,14 @@ int main(int argc, char** argv)
square.Rotate(6.0f, 0.0f, 0.0f); square.Rotate(6.0f, 0.0f, 0.0f);
square2.Rotate(-6.0f, 0.0f, 0.0f); square2.Rotate(-6.0f, 0.0f, 0.0f);
camera.Rotate(0.0f, 1.0f, 0.0f);
view = glm::rotate(view, glm::radians(1.0f), glm::vec3(0.0f, 1.0f, 0.0f));
shader->Use(); shader->Use();
shader->SetUniform("texture1", crate, 0); shader->SetUniform("texture1", crate, 0);
shader->SetUniform("texture2", opengl, 1); shader->SetUniform("texture2", opengl, 1);
shader->SetUniform("model", square); shader->SetUniform("model", square);
shader->SetUniformMatrix4fv("view", 1, GL_FALSE, glm::value_ptr(view)); shader->SetUniform("view", camera);
shader->SetUniformMatrix4fv("projection", 1, GL_FALSE, glm::value_ptr(projection)); shader->SetUniformMatrix4fv("projection", 1, GL_FALSE, camera.GetProjectionMatrix());
square.Render(); square.Render();
@ -118,6 +115,8 @@ int main(int argc, char** argv)
glfwSwapBuffers(window); glfwSwapBuffers(window);
glfwPollEvents(); glfwPollEvents();
t += 0.1f;
} }
glfwTerminate(); glfwTerminate();

View file

@ -72,6 +72,8 @@ int main(int argc, char** argv)
oglu::Enable(GL_DEPTH_TEST); oglu::Enable(GL_DEPTH_TEST);
oglu::Camera camera(45.0f, 1.0f, 0.1f, 100.0f); oglu::Camera camera(45.0f, 1.0f, 0.1f, 100.0f);
camera.Move(0.0f, -5.0f, -10.0f);
camera.LookAt(glm::value_ptr(glm::make_vec3(utah.GetPosition()) + glm::vec3(0.0f, 2.0f, 0.0f)));
float t = 0.0f; float t = 0.0f;
@ -82,12 +84,11 @@ int main(int argc, char** argv)
oglu::ClearScreen(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT, oglu::Color(0.29f, 0.13f, 0.23f)); oglu::ClearScreen(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT, oglu::Color(0.29f, 0.13f, 0.23f));
camera.SetPosition(10.0f * cosf(t), -5.0f, 10.0f * sinf(t)); utah.Rotate(0.0f, 10.0f, 0.0f);
camera.LookAt(utah);
shader->Use(); shader->Use();
shader->SetUniform("model", utah); shader->SetUniform("model", utah);
shader->SetUniformMatrix4fv("view", 1, GL_FALSE, camera.GetMatrix()); shader->SetUniform("view", camera);
shader->SetUniformMatrix4fv("projection", 1, GL_FALSE, camera.GetProjectionMatrix()); shader->SetUniformMatrix4fv("projection", 1, GL_FALSE, camera.GetProjectionMatrix());
oglu::PolygonMode(GL_FRONT_AND_BACK, GL_LINE); oglu::PolygonMode(GL_FRONT_AND_BACK, GL_LINE);

View file

@ -78,6 +78,16 @@ namespace oglu
*/ */
void LookAt(const GLfloat* target); void LookAt(const GLfloat* target);
/**
* @brief Have camera face at a certain position.
*
* This will adjust the camera's rotation in order to put the
* specified coordinate at the center of the screen.
*
* @param[in] target 3D vector with the target position
*/
void LookAt(const glm::vec3& target);
/** /**
* @brief Have camera face at a certain position. * @brief Have camera face at a certain position.
* *

View file

@ -10,6 +10,8 @@
#define TRANSFORMABLE_HPP #define TRANSFORMABLE_HPP
#include <core.hpp> #include <core.hpp>
#include <glm/glm.hpp>
#include <glm/gtx/quaternion.hpp>
namespace oglu namespace oglu
{ {
@ -48,7 +50,7 @@ namespace oglu
* @param[in] y New y position * @param[in] y New y position
* @param[in] z New z position * @param[in] z New z position
*/ */
void SetPosition(float x, float y, float z); virtual void SetPosition(float x, float y, float z);
/** /**
* @brief Sets the position. * @brief Sets the position.
@ -58,7 +60,17 @@ namespace oglu
* *
* @param[in] position An array of floats containing three scalars * @param[in] position An array of floats containing three scalars
*/ */
void SetPosition(const float* position); virtual void SetPosition(const float* position);
/**
* @brief Sets the position.
*
* This sets an absolute position, means that it resets any previous
* translations.
*
* @param[in] position A 3D position vector
*/
virtual void SetPosition(const glm::vec3& position);
/** /**
* @brief Sets the rotation. * @brief Sets the rotation.
@ -70,7 +82,7 @@ namespace oglu
* @param[in] rotY New rotation around y axis * @param[in] rotY New rotation around y axis
* @param[in] rotZ New rotation around z axis * @param[in] rotZ New rotation around z axis
*/ */
void SetRotation(float rotX, float rotY, float rotZ); virtual void SetRotation(float rotX, float rotY, float rotZ);
/** /**
* @brief Sets the rotation. * @brief Sets the rotation.
@ -80,7 +92,17 @@ namespace oglu
* *
* @param[in] rotation An array of floats containing three scalars * @param[in] rotation An array of floats containing three scalars
*/ */
void SetRotation(const float* rotation); virtual void SetRotation(const float* rotation);
/**
* @brief Sets the rotation.
*
* This sets an absolute rotation, means that it resets any previous
* rotations.
*
* @param[in] rotation A glm::vec3 containing Euler angles
*/
virtual void SetRotation(const glm::vec3& rotation);
/** /**
* @brief Sets the rotation. * @brief Sets the rotation.
@ -93,7 +115,7 @@ namespace oglu
* @param[in] yAxis The y component of the rotation axis * @param[in] yAxis The y component of the rotation axis
* @param[in] zAxis The z component of the rotation axis * @param[in] zAxis The z component of the rotation axis
*/ */
void SetRotation(float angle, float xAxis, float yAxis, float zAxis); virtual void SetRotation(float angle, float xAxis, float yAxis, float zAxis);
/** /**
* @brief Sets the rotation. * @brief Sets the rotation.
@ -104,7 +126,18 @@ namespace oglu
* @param[in] angle The angle to rotate by * @param[in] angle The angle to rotate by
* @param[in] axis An array of floats containing the three rotation axis components * @param[in] axis An array of floats containing the three rotation axis components
*/ */
void SetRotation(float angle, const float* axis); virtual void SetRotation(float angle, const float* axis);
/**
* @brief Sets the rotation.
*
* This sets an absolute rotation, means that it resets any previous
* rotations.
*
* @param[in] angle The angle to rotate by
* @param[in] axis The axis to rotate around
*/
virtual void SetRotation(float angle, const glm::vec3& axis);
/** /**
* @brief Sets the scaling. * @brief Sets the scaling.
@ -116,7 +149,7 @@ namespace oglu
* @param[in] scaleY The scaling in y direction * @param[in] scaleY The scaling in y direction
* @param[in] scaleZ The scaling in z direction * @param[in] scaleZ The scaling in z direction
*/ */
void SetScale(float scaleX, float scaleY, float scaleZ); virtual void SetScale(float scaleX, float scaleY, float scaleZ);
/** /**
* @brief Sets the scaling. * @brief Sets the scaling.
@ -126,7 +159,17 @@ namespace oglu
* *
* @param[in] scale An array of floats containing three scalars * @param[in] scale An array of floats containing three scalars
*/ */
void SetScale(const float* scale); virtual void SetScale(const float* scale);
/**
* @brief Sets the scaling.
*
* This sets an absolute scaling, means that it resets any previous
* scaling.
*
* @param[in] scale A 3D scaling vector
*/
virtual void SetScale(const glm::vec3& scale);
/** /**
* @brief Performs a translation. * @brief Performs a translation.
@ -138,7 +181,7 @@ namespace oglu
* @param[in] y Offset along the y axis * @param[in] y Offset along the y axis
* @param[in] z Offset along the z axis * @param[in] z Offset along the z axis
*/ */
void Move(float x, float y, float z); virtual void Move(float x, float y, float z);
/** /**
* @brief Performs a translation. * @brief Performs a translation.
@ -148,7 +191,17 @@ namespace oglu
* *
* @param[in] position An array of floats containing the offset values * @param[in] position An array of floats containing the offset values
*/ */
void Move(const float* translation); virtual void Move(const float* translation);
/**
* @brief Performs a translation.
*
* This function applies a translation to the object, it operates
* operates on the current position.
*
* @param[in] position A 3D displacement vector
*/
virtual void Move(const glm::vec3& translation);
/** /**
* @brief Performs a rotation. * @brief Performs a rotation.
@ -160,7 +213,7 @@ namespace oglu
* @param[in] rotY Rotation around the y axis * @param[in] rotY Rotation around the y axis
* @param[in] rotZ Rotation around the z axis * @param[in] rotZ Rotation around the z axis
*/ */
void Rotate(float rotX, float rotY, float rotZ); virtual void Rotate(float rotX, float rotY, float rotZ);
/** /**
* @brief Performs a rotation. * @brief Performs a rotation.
@ -170,7 +223,17 @@ namespace oglu
* *
* @param[in] rotation An array of floats containing the rotation values * @param[in] rotation An array of floats containing the rotation values
*/ */
void Rotate(const float* rotation); virtual void Rotate(const float* rotation);
/**
* @brief Performs a rotation.
*
* This function applies a rotation to the object, it operates
* operates on the current rotation.
*
* @param[in] rotation An 3D vector containing Euler angles
*/
virtual void Rotate(const glm::vec3& rotation);
/** /**
* @brief Performs a rotation. * @brief Performs a rotation.
@ -183,7 +246,7 @@ namespace oglu
* @param[in] yAxis y component of the rotation axis * @param[in] yAxis y component of the rotation axis
* @param[in] zAxis z component of the rotation axis * @param[in] zAxis z component of the rotation axis
*/ */
void Rotate(float angle, float xAxis, float yAxis, float zAxis); virtual void Rotate(float angle, float xAxis, float yAxis, float zAxis);
/** /**
* @brief Performs a rotation. * @brief Performs a rotation.
@ -192,9 +255,20 @@ namespace oglu
* operates on the current rotation. * operates on the current rotation.
* *
* @param[in] angle The angle to rotate by * @param[in] angle The angle to rotate by
* @param[in] An array of floats containing the components of the rotation axis * @param[in] axis An array of floats containing the components of the rotation axis
*/ */
void Rotate(float angle, const float* axis); virtual void Rotate(float angle, const float* axis);
/**
* @brief Performs a rotation.
*
* This function applies a rotation to the object, it operates
* operates on the current rotation.
*
* @param[in] angle The angle to rotate by
* @param[in] axis The axis to rotate around
*/
virtual void Rotate(float angle, const glm::vec3& axis);
/** /**
* @brief Performs scaling. * @brief Performs scaling.
@ -206,7 +280,7 @@ namespace oglu
* @param[in] scaleX Scaling in y direction * @param[in] scaleX Scaling in y direction
* @param[in] scaleX Scaling in z direction * @param[in] scaleX Scaling in z direction
*/ */
void Scale(float scaleX, float scaleY, float scaleZ); virtual void Scale(float scaleX, float scaleY, float scaleZ);
/** /**
* @brief Performs scaling. * @brief Performs scaling.
@ -216,54 +290,56 @@ namespace oglu
* *
* @param[in] scale An array of floats containing three scaling values * @param[in] scale An array of floats containing three scaling values
*/ */
void Scale(const float* scale); virtual void Scale(const float* scale);
/**
* @brief Performs scaling.
*
* This function applies scaling to the object, it operates
* operates on the current scaling.
*
* @param[in] scale A 3D scaling vector
*/
virtual void Scale(const glm::vec3& scale);
/** /**
* @brief Returns a transformation matrix. * @brief Returns a transformation matrix.
* *
* Internally, this function multiplies the translation, rotation,
* and scaling matrices into one transformation matrix which is
* then returned.
*
* This multiplication is only performed when a change occured to one
* of those matrices (so when there was a translation, rotation or scaling).
* So it is okay to call this function multiple times without huge performance
* loss, as long as no transformations occur inbetween.
*
* @return An array of 16 floats representing the transformation matrix * @return An array of 16 floats representing the transformation matrix
*/ */
const float* GetMatrix(); virtual const glm::mat4& GetMatrix();
/** /**
* @brief Get position as a 3D vector. * @brief Get position as a 3D vector.
* *
* @returns A pointer to an array of floats * @returns A pointer to an array of floats
*/ */
const float* GetPosition() const; virtual const glm::vec3& GetPosition() const;
/** /**
* @brief Get rotation as a matrix. * @brief Get rotation as a matrix.
* *
* @returns A pointer to a 4x4 matrix * @returns A pointer to a 4x4 matrix
*/ */
const float* GetRotation() const; virtual const glm::quat& GetRotation() const;
/** /**
* @brief Get scaling as a 3D vector. * @brief Get scaling as a 3D vector.
* *
* @returns A pointer to an array of floats * @returns A pointer to an array of floats
*/ */
const float* GetScaling() const; virtual const glm::vec3& GetScaling() const;
protected: protected:
// TODO: Separate translation, rotation and scaling matrices. // TODO: Separate translation, rotation and scaling matrices.
// Combine them only when the user wants the transformation matrix // Combine them only when the user wants the transformation matrix
float* position; ///< Position vector glm::mat4 transformation;
float* rotation; ///< Rotation matrix
float* scaling; ///< Scaling vector
float* transformation; glm::vec3 scale;
bool calculateMatrix; ///< Wether GetMatrix() needs to re-calculate the transformation matrix glm::quat orientation;
glm::vec3 translation;
glm::vec3 skew;
glm::vec4 perspective;
}; };
} }

View file

@ -13,6 +13,10 @@ namespace oglu
Camera::Camera() : Camera::Camera() :
fov(45.0f), aspectRatio(0.0f), zNear(0.1f), zFar(100.0f), projection(new float[16]{ 0.0f }) fov(45.0f), aspectRatio(0.0f), zNear(0.1f), zFar(100.0f), projection(new float[16]{ 0.0f })
{ {
GLint viewport[4];
glGetIntegerv(GL_VIEWPORT, viewport);
aspectRatio = (float)viewport[2] / (float)viewport[3];
memcpy( memcpy(
projection, projection,
glm::value_ptr(glm::perspective(glm::radians(fov), aspectRatio, zNear, zFar)), glm::value_ptr(glm::perspective(glm::radians(fov), aspectRatio, zNear, zFar)),
@ -53,37 +57,18 @@ namespace oglu
void Camera::LookAt(GLfloat x, GLfloat y, GLfloat z) void Camera::LookAt(GLfloat x, GLfloat y, GLfloat z)
{ {
glm::mat4 newTransform = glm::lookAt(glm::make_vec3(position), glm::vec3(x, y, z), glm::vec3(0.0f, 1.0f, 0.0f)); LookAt(glm::vec3(x, y, z));
glm::vec3 scale;
glm::vec3 pos;
glm::quat rot;
glm::vec3 skew;
glm::vec4 pers;
glm::decompose(newTransform, scale, rot, pos, skew, pers);
memcpy(
position,
glm::value_ptr(pos),
3 * sizeof(float)
);
memcpy(
rotation,
glm::value_ptr(glm::toMat4(rot)),
16 * sizeof(float)
);
memcpy(
scaling,
glm::value_ptr(scale),
3 * sizeof(float)
);
calculateMatrix = true;
} }
void Camera::LookAt(const GLfloat* target) void Camera::LookAt(const GLfloat* target)
{ {
LookAt(target[0], target[1], target[2]); LookAt(glm::make_vec3(target));
}
void Camera::LookAt(const glm::vec3& target)
{
transformation = glm::lookAt(translation, target, glm::vec3(0.0f, 1.0f, 0.0f));
glm::decompose(transformation, scale, orientation, translation, skew, perspective);
} }
void Camera::LookAt(const Transformable& target) void Camera::LookAt(const Transformable& target)

View file

@ -9,6 +9,8 @@
#include <texture.hpp> #include <texture.hpp>
#include <transformable.hpp> #include <transformable.hpp>
#include <glm/gtc/type_ptr.hpp>
namespace oglu namespace oglu
{ {
AbstractShader::AbstractShader(const AbstractShader& other) : AbstractShader::AbstractShader(const AbstractShader& other) :
@ -254,7 +256,7 @@ namespace oglu
void AbstractShader::SetUniform(GLint location, Transformable& v0, GLboolean transpose) void AbstractShader::SetUniform(GLint location, Transformable& v0, GLboolean transpose)
{ {
glUniformMatrix4fv(location, 1, transpose, v0.GetMatrix()); glUniformMatrix4fv(location, 1, transpose, glm::value_ptr(v0.GetMatrix()));
} }
void AbstractShader::SetUniform1fv(const GLchar* name, GLsizei count, const GLfloat* value) void AbstractShader::SetUniform1fv(const GLchar* name, GLsizei count, const GLfloat* value)

View file

@ -2,266 +2,182 @@
#include <algorithm> #include <algorithm>
#include <glm/glm.hpp>
#include <glm/gtc/matrix_transform.hpp> #include <glm/gtc/matrix_transform.hpp>
#include <glm/gtx/matrix_decompose.hpp>
#include <glm/gtx/quaternion.hpp>
#include <glm/gtc/type_ptr.hpp> #include <glm/gtc/type_ptr.hpp>
namespace oglu namespace oglu
{ {
oglu::Transformable::Transformable() : oglu::Transformable::Transformable() :
position(new float[3]{ 0.f }), rotation(new float[16]), scaling(new float[3]{ 1.f, 1.f, 1.f }), transformation(new float[16]), calculateMatrix(false) transformation(glm::mat4(1.0f))
{ {
glm::mat4 identity(1.0f); glm::decompose(transformation, scale, orientation, translation, skew, perspective);
memcpy(
rotation,
glm::value_ptr(identity),
16 * sizeof(float)
);
memcpy(
transformation,
glm::value_ptr(identity),
16 * sizeof(float)
);
} }
Transformable::Transformable(const Transformable& other) : Transformable::Transformable(const Transformable& other) :
position(new float[3]), rotation(new float[16]), scaling(new float[3]), transformation(new float[16]), calculateMatrix(true) transformation(other.transformation)
{ {
memcpy( glm::decompose(transformation, scale, orientation, translation, skew, perspective);
this->position,
other.position,
3 * sizeof(float)
);
memcpy(
this->rotation,
other.rotation,
16 * sizeof(float)
);
memcpy(
this->scaling,
other.scaling,
3 * sizeof(float)
);
} }
Transformable::~Transformable() Transformable::~Transformable()
{ {
delete[] scaling;
delete[] rotation;
delete[] position;
} }
void Transformable::SetPosition(float x, float y, float z) void Transformable::SetPosition(float x, float y, float z)
{ {
this->position[0] = x; SetPosition(glm::vec3(x, y, z));
this->position[1] = y;
this->position[2] = z;
calculateMatrix = true;
} }
void Transformable::SetPosition(const float* translation) void Transformable::SetPosition(const float* translation)
{ {
memcpy( SetPosition(glm::make_vec3(translation));
this->position, }
translation,
3 * sizeof(float) void Transformable::SetPosition(const glm::vec3& position)
); {
calculateMatrix = true; glm::decompose(transformation, scale, orientation, this->translation, skew, perspective);
this->translation = translation - this->translation;
transformation = glm::translate(transformation, this->translation);
} }
void Transformable::SetRotation(float rotX, float rotY, float rotZ) void Transformable::SetRotation(float rotX, float rotY, float rotZ)
{ {
// TODO: Using rotation matrices is stupid. Eventually this could (should) be done with quaternions SetRotation(glm::vec3(rotX, rotY, rotZ));
// For now we'll just risk gimbal locking the model
memcpy(
this->rotation,
glm::value_ptr(
glm::rotate(
glm::rotate(
glm::rotate(
glm::mat4(1.0f), glm::radians(rotX), glm::vec3(1.0f, 0.0f, 0.0f)
), glm::radians(rotY), glm::vec3(0.0f, 1.0f, 0.0f)
), glm::radians(rotZ), glm::vec3(0.0f, 0.0f, 1.0f)
)
),
16 * sizeof(float)
);
calculateMatrix = true;
} }
void Transformable::SetRotation(const float* rotation) void Transformable::SetRotation(const float* rotation)
{ {
memcpy( SetRotation(glm::make_vec3(rotation));
this->rotation, }
glm::value_ptr(
glm::rotate( void Transformable::SetRotation(const glm::vec3& rotation)
glm::rotate( {
glm::rotate( glm::decompose(transformation, scale, orientation, translation, skew, perspective);
glm::mat4(1.0f), glm::radians(rotation[0]), glm::vec3(1.0f, 0.0f, 0.0f) orientation = glm::quat(glm::radians(rotation)) * (-orientation);
), glm::radians(rotation[1]), glm::vec3(0.0f, 1.0f, 0.0f) transformation = glm::rotate(transformation, glm::angle(orientation), glm::axis(orientation));
), glm::radians(rotation[2]), glm::vec3(0.0f, 0.0f, 1.0f)
)
),
16 * sizeof(float)
);
calculateMatrix = true;
} }
void Transformable::SetRotation(float angle, float xAxis, float yAxis, float zAxis) void Transformable::SetRotation(float angle, float xAxis, float yAxis, float zAxis)
{ {
memcpy( SetRotation(angle, glm::vec3(xAxis, yAxis, zAxis));
this->rotation,
glm::value_ptr(glm::rotate(glm::mat4(1.0f), glm::radians(angle), glm::vec3(xAxis, yAxis, zAxis))),
16 * sizeof(float)
);
calculateMatrix = true;
} }
void Transformable::SetRotation(float angle, const float* axis) void Transformable::SetRotation(float angle, const float* axis)
{ {
memcpy( SetRotation(angle, glm::make_vec3(axis));
this->rotation, }
glm::value_ptr(glm::rotate(glm::mat4(1.0f), glm::radians(angle), glm::make_vec3(axis))),
16 * sizeof(float) void Transformable::SetRotation(float angle, const glm::vec3& axis)
); {
calculateMatrix = true; glm::decompose(transformation, scale, orientation, translation, skew, perspective);
orientation = glm::angleAxis(glm::radians(angle), axis) * (-orientation);
transformation = glm::rotate(transformation, glm::angle(orientation), glm::axis(orientation));
} }
void Transformable::SetScale(float scaleX, float scaleY, float scaleZ) void Transformable::SetScale(float scaleX, float scaleY, float scaleZ)
{ {
this->scaling[0] = scaleX; SetScale(glm::vec3(scaleX, scaleY, scaleZ));
this->scaling[1] = scaleY;
this->scaling[2] = scaleZ;
calculateMatrix = true;
} }
void Transformable::SetScale(const float* scale) void Transformable::SetScale(const float* scale)
{ {
memcpy( SetScale(glm::make_vec3(scale));
this->scaling, }
scale,
3 * sizeof(float) void Transformable::SetScale(const glm::vec3& scale)
); {
calculateMatrix = true; glm::decompose(transformation, this->scale, orientation, translation, skew, perspective);
this->scale = scale / this->scale;
if (this->scale.x == INFINITY) this->scale.x = scale.x;
if (this->scale.y == INFINITY) this->scale.y = scale.y;
if (this->scale.z == INFINITY) this->scale.z = scale.z;
transformation = glm::scale(transformation, this->scale);
} }
void Transformable::Move(float x, float y, float z) void Transformable::Move(float x, float y, float z)
{ {
this->position[0] += x; Move(glm::vec3(x, y, z));
this->position[1] += y;
this->position[2] += z;
calculateMatrix = true;
} }
void Transformable::Move(const float* translation) void Transformable::Move(const float* translation)
{ {
this->position[0] += translation[0]; Move(glm::make_vec3(translation));
this->position[1] += translation[1]; }
this->position[2] += translation[2];
calculateMatrix = true; void Transformable::Move(const glm::vec3& translation)
{
transformation = glm::translate(transformation, translation);
glm::decompose(transformation, scale, orientation, this->translation, skew, perspective);
} }
void Transformable::Rotate(float rotX, float rotY, float rotZ) void Transformable::Rotate(float rotX, float rotY, float rotZ)
{ {
memcpy( Rotate(glm::vec3(rotX, rotY, rotZ));
this->rotation,
glm::value_ptr(
glm::rotate(
glm::rotate(
glm::rotate(
glm::make_mat4(this->rotation), glm::radians(rotX), glm::vec3(1.0f, 0.0f, 0.0f)
), glm::radians(rotY), glm::vec3(0.0f, 1.0f, 0.0f)
), glm::radians(rotZ), glm::vec3(0.0f, 0.0f, 1.0f)
)
),
16 * sizeof(float)
);
calculateMatrix = true;
} }
void Transformable::Rotate(const float* rotation) void Transformable::Rotate(const float* rotation)
{ {
memcpy( Rotate(glm::make_vec3(rotation));
this->rotation, }
glm::value_ptr(
glm::rotate( void Transformable::Rotate(const glm::vec3& rotation)
glm::rotate( {
glm::rotate( glm::quat rot = glm::quat(glm::radians(rotation));
glm::make_mat4(this->rotation), glm::radians(rotation[0]), glm::vec3(1.0f, 0.0f, 0.0f) transformation = glm::rotate(transformation, glm::angle(rot), glm::axis(rot));
), glm::radians(rotation[1]), glm::vec3(0.0f, 1.0f, 0.0f) glm::decompose(transformation, scale, orientation, translation, skew, perspective);
), glm::radians(rotation[2]), glm::vec3(0.0f, 0.0f, 1.0f)
)
),
16 * sizeof(float)
);
calculateMatrix = true;
} }
void Transformable::Rotate(float angle, float xAxis, float yAxis, float zAxis) void Transformable::Rotate(float angle, float xAxis, float yAxis, float zAxis)
{ {
memcpy( Rotate(angle, glm::vec3(xAxis, yAxis, zAxis));
this->rotation,
glm::value_ptr(glm::rotate(glm::make_mat4(this->rotation), glm::radians(angle), glm::vec3(xAxis, yAxis, zAxis))),
16 * sizeof(float)
);
calculateMatrix = true;
} }
void Transformable::Rotate(float angle, const float* axis) void Transformable::Rotate(float angle, const float* axis)
{ {
memcpy( Rotate(angle, glm::make_vec3(axis));
this->rotation, }
glm::value_ptr(glm::rotate(glm::make_mat4(this->rotation), glm::radians(angle), glm::make_vec3(axis))),
16 * sizeof(float) void Transformable::Rotate(float angle, const glm::vec3& axis)
); {
calculateMatrix = true; transformation = glm::rotate(transformation, glm::radians(angle), axis);
glm::decompose(transformation, scale, orientation, translation, skew, perspective);
} }
void Transformable::Scale(float scaleX, float scaleY, float scaleZ) void Transformable::Scale(float scaleX, float scaleY, float scaleZ)
{ {
this->scaling[0] += scaleX; Scale(glm::vec3(scaleX, scaleY, scaleZ));
this->scaling[1] += scaleY;
this->scaling[2] += scaleZ;
calculateMatrix = true;
} }
void Transformable::Scale(const float* scale) void Transformable::Scale(const float* scale)
{ {
this->scaling[0] += scale[0]; Scale(glm::make_vec3(scale));
this->scaling[1] += scale[1];
this->scaling[2] += scale[2];
calculateMatrix = true;
} }
const float* Transformable::GetMatrix() void Transformable::Scale(const glm::vec3& scale)
{ {
if (calculateMatrix) transformation = glm::scale(transformation, scale);
{ glm::decompose(transformation, this->scale, orientation, translation, skew, perspective);
memcpy( }
transformation,
glm::value_ptr(glm::translate(glm::mat4(1.0f), glm::make_vec3(position)) * glm::make_mat4(rotation) * glm::scale(glm::mat4(1.0f), glm::make_vec3(scaling))),
16 * sizeof(float)
);
calculateMatrix = false;
}
const glm::mat4& Transformable::GetMatrix()
{
return transformation; return transformation;
} }
const float* Transformable::GetPosition() const const glm::vec3& Transformable::GetPosition() const
{ {
return position; return translation;
} }
const float* Transformable::GetRotation() const const glm::quat& Transformable::GetRotation() const
{ {
return rotation; return orientation;
} }
const float* Transformable::GetScaling() const const glm::vec3& Transformable::GetScaling() const
{ {
return scaling; return scale;
} }
} }