From 3213287b186fd9de237ff13c170e3bacd89dfa0e Mon Sep 17 00:00:00 2001 From: hyzboy Date: Fri, 23 Aug 2024 01:57:04 +0800 Subject: [PATCH] Added TransformBase and few Transform???? classes. --- inc/hgl/math/Matrix.h | 1 + inc/hgl/math/Transform.h | 322 +++++++++++++++++++++++++++++++++++++++ 2 files changed, 323 insertions(+) diff --git a/inc/hgl/math/Matrix.h b/inc/hgl/math/Matrix.h index a08f3e3..15cf168 100644 --- a/inc/hgl/math/Matrix.h +++ b/inc/hgl/math/Matrix.h @@ -10,6 +10,7 @@ #include #include #include +#include namespace hgl { diff --git a/inc/hgl/math/Transform.h b/inc/hgl/math/Transform.h index d1fdfec..a5a3d1f 100644 --- a/inc/hgl/math/Transform.h +++ b/inc/hgl/math/Transform.h @@ -3,6 +3,328 @@ namespace hgl { + /** + * 变换基类 + */ + class TransformBase + { + uint version; + uint cur_version; + + Matrix4f CurMatrix; + + protected: + + virtual uint UpdateVersion() + { + //版本号只是为了记录变化,让程序知道和上次不一样,所以最大值是多少其实无所谓的 + version=(version >= 1000000)?0:++version; + + return version; + } + + virtual void UpdateMatrix(Matrix4f &)=0; + + public: + + TransformBase() + { + version=0; + cur_version=0; + CurMatrix=Identity4f; + } + virtual ~TransformBase()=default; + + virtual constexpr const size_t GetTypeHash()const=0; ///<取得类型哈希值 + + const uint GetVersion()const{return version;} ///<取得当前数据版本号 + + virtual const uint GetMatrix(Matrix4f &mat) ///<取得当前矩阵,并返回当前矩阵版本号 + { + if (cur_version != version) + { + UpdateMatrix(CurMatrix); + cur_version=version; + } + + mat=CurMatrix; + return cur_version; + } + };//class TransformBase + + class TransformMatrix :public TransformBase + { + Matrix4f transform_matrix; + + public: + + virtual constexpr const size_t GetTypeHash()const override { return hgl::GetTypeHash(); } + + const Matrix4f &GetTransformMatrix()const { return transform_matrix; } + + void SetTransformMatrix(const Matrix4f &mat) + { + if (transform_matrix==mat) + return; + + transform_matrix=mat; + UpdateVersion(); + } + + virtual void UpdateMatrix(Matrix4f &mat) override + { + mat=transform_matrix; + } + };//class TransformMatrix + + class TransformTranslate3f :public TransformBase + { + Vector3f offset; + + public: + + virtual constexpr const size_t GetTypeHash()const override{return hgl::GetTypeHash();} + + const Vector3f &GetOffset()const { return offset; } + void SetOffset(const Vector3f &o) + { + if(IsNearlyEqual(offset,o)) + return; + + offset=o; + UpdateVersion(); + } + + void AddOffset(const Vector3f &o) + { + if (IsNearlyZero(o)) + return; + + offset+=o; + UpdateVersion(); + } + + virtual void UpdateMatrix(Matrix4f &mat) override + { + mat=translate(offset); + } + };//class TransformTranslate + + class TransformRotateQuat :public TransformBase + { + Quatf quat; + + public: + + virtual constexpr const size_t GetTypeHash()const override{return hgl::GetTypeHash();} + + const Quatf &GetQuat()const { return quat; } + void SetQuat(const Quatf &q) + { + if (IsNearlyEqual(quat,q)) + return; + + quat=q; + UpdateVersion(); + } + + virtual void UpdateMatrix(Matrix4f &mat) override + { + mat=ToMatrix(quat); + } + };//class TransformRotateQuat + + class TransformRotateAxis :public TransformBase + { + Vector3f axis; + float angle; + + public: + + virtual constexpr const size_t GetTypeHash()const override { return hgl::GetTypeHash(); } + + const Vector3f &GetAxis()const { return axis; } + const float GetAngle()const { return angle; } + + void SetAxisAngle(const Vector3f &a,float ang) + { + if (IsNearlyEqual(axis,a) && IsNearlyEqual(angle,ang)) + return; + + axis=a; + angle=ang; + UpdateVersion(); + } + + void SetAxis(const Vector3f &a) + { + if (IsNearlyEqual(axis,a)) + return; + + axis=a; + UpdateVersion(); + } + + void SetAngle(float a) + { + if (IsNearlyEqual(angle,a)) + return; + + angle=a; + UpdateVersion(); + } + + virtual void UpdateMatrix(Matrix4f &mat) override + { + mat=rotate(angle,axis); + } + };//class TransformRotateAxis + + class TransformRotateEuler :public TransformBase + { + float pitch; ///<绕X轴旋转弧度 + float yaw; ///<绕Y轴旋转弧度 + float roll; ///<绕Z轴旋转弧度 + + public: + + virtual constexpr const size_t GetTypeHash()const override { return hgl::GetTypeHash(); } + + const Vector3f &GetEuler()const { return Vector3f(pitch,yaw,roll); } + + const float GetPitch()const { return pitch; } + const float GetYaw()const { return yaw; } + const float GetRoll()const { return roll; } + + void SetEuler(const Vector3f &e) + { + if (IsNearlyEqual(e.x,pitch) + &&IsNearlyEqual(e.y,yaw) + &&IsNearlyEqual(e.z,roll)) + return; + + pitch=e.x; + yaw=e.y; + roll=e.z; + + UpdateVersion(); + } + + void SetPitch(float p) + { + if (IsNearlyEqual(pitch,p)) + return; + + pitch=p; + UpdateVersion(); + } + + void SetYaw(float y) + { + if (IsNearlyEqual(yaw,y)) + return; + + yaw=y; + UpdateVersion(); + } + + void SetRoll(float r) + { + if (IsNearlyEqual(roll,r)) + return; + + roll=r; + UpdateVersion(); + } + + virtual void UpdateMatrix(Matrix4f &mat) override + { + mat=glm::eulerAngleXYZ(pitch,yaw,roll); + } + };//class TransformRotateEuler + + class TransformScale3f :public TransformBase + { + Vector3f scale3f; + + public: + + virtual constexpr const size_t GetTypeHash()const override { return hgl::GetTypeHash(); } + + const Vector3f &GetScale()const { return scale3f; } + void SetScale(const Vector3f &s) + { + if (IsNearlyEqual(scale3f,s)) + return; + + scale3f=s; + UpdateVersion(); + } + + virtual void UpdateMatrix(Matrix4f &mat) override + { + mat=scale(scale3f); + } + };//class TransformScale + + class TransformLookAt :public TransformBase + { + Vector3f eye; + Vector3f center; + Vector3f up; + + public: + + virtual constexpr const size_t GetTypeHash()const override { return hgl::GetTypeHash(); } + + const Vector3f &GetEye()const { return eye; } + const Vector3f &GetCenter()const { return center; } + const Vector3f &GetUp()const { return up; } + + void SetLookAt(const Vector3f &e,const Vector3f &c,const Vector3f &u) + { + if (IsNearlyEqual(eye,e) && IsNearlyEqual(center,c) && IsNearlyEqual(up,u)) + return; + + eye=e; + center=c; + up=u; + UpdateVersion(); + } + + void SetEye(const Vector3f &pos) + { + if(IsNearlyEqual(eye,pos)) + return; + + eye=pos; + UpdateVersion(); + } + + void SetCenter(const Vector3f &pos) + { + if (IsNearlyEqual(center,pos)) + return; + + center=pos; + UpdateVersion(); + } + + void SetUp(const Vector3f &pos) + { + if (IsNearlyEqual(up,pos)) + return; + + up=pos; + UpdateVersion(); + } + + virtual void UpdateMatrix(Matrix4f &mat) override + { + mat=lookat(eye,center,up); + } + };//class TransformLookAt + /** * 变换矩阵
* 便于分散管理平移、旋转、缩放等数值