From 5662355571e37e43261e0a1284f3ac5beaef8983 Mon Sep 17 00:00:00 2001 From: Wayne Venables Date: Sun, 5 Mar 2023 12:52:48 -0800 Subject: [PATCH] Matrix documentation --- doxygen.cfg | 2 +- src/util/mat2d.h | 181 ++++++++++++++++++++++++++++++++--------------- 2 files changed, 124 insertions(+), 59 deletions(-) diff --git a/doxygen.cfg b/doxygen.cfg index 2d4f8f1..1dff000 100644 --- a/doxygen.cfg +++ b/doxygen.cfg @@ -151,7 +151,7 @@ ALWAYS_DETAILED_SEC = NO # operators of the base classes will not be shown. # The default value is: NO. -INLINE_INHERITED_MEMB = NO +INLINE_INHERITED_MEMB = YES # If the FULL_PATH_NAMES tag is set to YES, doxygen will prepend the full path # before files name in the file list and in the header files. If set to NO the diff --git a/src/util/mat2d.h b/src/util/mat2d.h index c241743..76e7e68 100644 --- a/src/util/mat2d.h +++ b/src/util/mat2d.h @@ -11,7 +11,7 @@ #include "pico/double.h" #include "define.h" -// transformation matrix +/// Transformation matrix template class cMat2D { public: @@ -20,54 +20,69 @@ public: m2type m11, m12, m13; m2type m21, m22, m23; - // trasform X + /// Transform X inline m2type GetX(m2type x, m2type y) const { return x*m11 + y*m12 + m13; } - // trasform Y + /// Transform Y inline m2type GetY(m2type x, m2type y) const { return x*m21 + y*m22 + m23; } - // set unit matrix + /// Set unit matrix inline void Unit() { m11 = 1; m12 = 0; m13 = 0; m21 = 0; m22 = 1; m23 = 0; } - // copy matrix + /// Copy matrix inline void Copy(const cMat2D* m) { m11 = m->m11; m12 = m->m12; m13 = m->m13; m21 = m->m21; m22 = m->m22; m23 = m->m23; } - // translate in X direction - // 1 0 tx m11 m12 m13 m11 m12 m13+tx - // 0 1 0 * m21 m22 m23 = m21 m22 m23 - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Translate in X direction + * @details + *
+	 *  1  0 tx   m11 m12 m13   m11 m12 m13+tx
+	 *  0  1  0 * m21 m22 m23 = m21 m22 m23
+	 *  0  0  1     0   0   1    0   0   1
+	 * 
+ */ inline void TransX(m2type tx) { m13 += tx; } - // translate in Y direction - // 1 0 0 m11 m12 m13 m11 m12 m13 - // 0 1 ty * m21 m22 m23 = m21 m22 m23+ty - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Translate in Y direction + * @details + *
+	 *  1  0  0   m11 m12 m13   m11 m12 m13
+	 *  0  1 ty * m21 m22 m23 = m21 m22 m23+ty
+	 *  0  0  1     0   0   1    0   0   1
+	 * 
+ */ inline void TransY(m2type ty) { m23 += ty; } - // scale in X direction - // sx 0 0 m11 m12 m13 m11*sx m12*sx m13*sx - // 0 1 0 * m21 m22 m23 = m21 m22 m23 - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Scale in X direction + * @details + *
+	 *  sx 0  0   m11 m12 m13    m11*sx m12*sx m13*sx
+	 *  0  1  0 * m21 m22 m23  = m21    m22    m23
+	 *  0  0  1     0   0   1      0      0      1
+	 * 
+ */ inline void ScaleX(m2type sx) { m11 *= sx; @@ -75,10 +90,15 @@ public: m13 *= sx; } - // scale in Y direction - // 1 0 0 m11 m12 m13 m11 m12 m13 - // 0 sy 0 * m21 m22 m23 = m21*sy m22*sy m23*sy - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Scale in Y direction + * @details + *
+	 *  1  0  0   m11 m12 m13    m11    m12    m13
+	 *  0  sy 0 * m21 m22 m23  = m21*sy m22*sy m23*sy
+	 *  0  0  1     0   0   1      0      0      1
+	 * 
+ */ inline void ScaleY(m2type sy) { m21 *= sy; @@ -86,10 +106,15 @@ public: m23 *= sy; } - // rotate, using sin and cos - // cosa -sina 0 m11 m12 m13 m11*cosa-m21*sina m12*cosa-m22*sina m13*cosa-m23*sina - // sina cosa 0 * m21 m22 m23 = m11*sina+m21*cosa m12*sina+m22*cosa m13*sina+m23*cosa - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Rotate, using sin and cos + * @details + *
+	 *  cosa -sina  0   m11 m12 m13   m11*cosa-m21*sina  m12*cosa-m22*sina  m13*cosa-m23*sina
+	 *  sina  cosa  0 * m21 m22 m23 = m11*sina+m21*cosa  m12*sina+m22*cosa  m13*sina+m23*cosa
+	 *   0      0   1     0   0   1           0                    0                 1
+	 * 
+ */ inline void RotSC(m2type sina, m2type cosa) { m2type t1 = m11; @@ -108,13 +133,13 @@ public: m23 = t1*sina + t2*cosa; } - // rotate, using angle + /// Rotate, using angle inline void Rot(m2type a) { this->RotSC(sin(a), cos(a)); } - // rotate by 90 deg (sina=1, cosa=0) + /// Rotate by 90 deg (sina=1, cosa=0) inline void Rot90() { m2type t = m11; @@ -130,7 +155,7 @@ public: m23 = t; } - // rotate by 180 deg (=flipX and flipY) (sina=0, cosa=-1) + /// Rotate by 180 deg (=flipX and flipY) (sina=0, cosa=-1) inline void Rot180() { m11 = -m11; @@ -141,7 +166,7 @@ public: m23 = -m23; } - // rotate by 270 deg (sina=-1, cosa=0) + /// Rotate by 270 deg (sina=-1, cosa=0) inline void Rot270() { m2type t = m11; @@ -157,10 +182,15 @@ public: m23 = -t; } - // Shear in X direction - // 1 dx 0 m11 m12 m13 m11+m21*dx m12+m22*dx m13+m23*dx - // 0 1 0 * m21 m22 m23 = m21 m22 m23 - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Shear in X direction + * @details + *
+	 *  1  dx 0   m11 m12 m13   m11+m21*dx m12+m22*dx m13+m23*dx
+	 *  0  1  0 * m21 m22 m23 = m21        m22        m23
+	 *  0  0  1     0   0   1     0          0          1
+	 * 
+ */ inline void ShearX(m2type dx) { m11 += m21*dx; @@ -168,10 +198,15 @@ public: m13 += m23*dx; } - // Shear in Y direction - // 1 0 0 m11 m12 m13 m11 m12 m13 - // dy 1 0 * m21 m22 m23 = m21+m11*dy m22+m12*dy m23+m13*dy - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Shear in Y direction + * @details + *
+	 *  1  0  0   m11 m12 m13   m11        m12        m13
+	 *  dy 1  0 * m21 m22 m23 = m21+m11*dy m22+m12*dy m23+m13*dy
+	 *  0  0  1     0   0   1     0          0          1
+	 * 
+ */ inline void ShearY(m2type dy) { m21 += m11*dy; @@ -179,10 +214,15 @@ public: m23 += m13*dy; } - // flip in Y direction - // 1 0 0 m11 m12 m13 m11 m12 m13 - // 0 -1 0 * m21 m22 m23 = -m21 -m22 -m23 - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Flip in Y direction + * @details + *
+	 *  1  0  0   m11 m12 m13     m11   m12    m13
+	 *  0 -1  0 * m21 m22 m23  = -m21  -m22   -m23
+	 *  0  0  1     0   0   1      0     0      1
+	 * 
+ */ inline void FlipY() { m21 = -m21; @@ -190,10 +230,15 @@ public: m23 = -m23; } - // flip in X direction - // -1 0 0 m11 m12 m13 -m11 -m12 -m13 - // 0 1 0 * m21 m22 m23 = m21 m22 m23 - // 0 0 1 0 0 1 0 0 1 + /** + * @brief Flip in X direction + * @details + *
+	 *  -1 0  0   m11 m12 m13    -m11  -m12   -m13
+	 *  0  1  0 * m21 m22 m23  = m21    m22    m23
+	 *  0  0  1     0   0   1      0      0      1
+	 * 
+ */ inline void FlipX() { m11 = -m11; @@ -204,26 +249,46 @@ public: #define TOFRACT(f) ((int)((f)*FRACTMUL + (((f) < 0) ? -0.5f : 0.5f))) +/// @addtogroup Canvas +/// @{ + +/** + * @brief 2D Transformation Matrix + * @details Some rendering functions use the cMat2Df transformation matrix to define image transformation. The matrix has + * 6 numeric elements of float type. The transformation is prepared by setting the initial state with the Unit function and + * then entering the transformations one by one. Using the matrix, operations are performed on the image as if the + * operations were entered sequentially. +*/ class cMat2Df : public cMat2D { public: - // prepare transformation matrix (for DrawImgMat function) - // ws ... source image width - // hs ... source image height - // x0 ... reference point X on source image - // y0 ... reference point Y on source image - // wd ... destination image width (negative = flip image in X direction) - // hd ... destination image height (negative = flip image in Y direction) - // shearx ... shear image in X direction - // sheary ... shear image in Y direction - // r ... rotate image (angle in radians) - // tx ... shift in X direction (ws = whole image width) - // ty ... shift in Y direction (hs = whole image height) + /** + * @brief Prepare transformation matrix (for DrawImgMat() function) + * @details The order of operations is chosen as if the image is first moved to the point tx and ty, scaled, skewed, then + * rotated and finally moved to the target coordinates. + * @param ws Source image width + * @param hs Source image height + * @param x0 Reference point X on source image + * @param y0 Reference point Y on source image + * @param wd Destination image width (negative = flip image in X direction) + * @param hd Destination image height (negative = flip image in Y direction) + * @param shearx Shear image in X direction + * @param sheary Shear image in Y direction + * @param r Rotate image (angle in radians) + * @param tx Shift in X direction (ws = whole image width) + * @param ty Shift in Y direction (hs = whole image height) + */ void PrepDrawImg(int ws, int hs, int x0, int y0, int wd, int hd, float shearx, float sheary, float r, float tx, float ty); - // export matrix to int array[6] + /** + * @brief Export matrix to int array[6] + * @details After transformation, the lower 12 bits of the number contain the decimal part of the number, the upper 20 bits + * contain the integer part of the number. Rendering functions require this integer form of the transformation matrix. + */ void ExportInt(int* mat) const; }; +/// @} + #endif // _MAT2D_H