00001 00002 #ifndef __ImageProcessorUtilityClasses_h_ 00003 #define __ImageProcessorUtilityClasses_h_ 00004 00005 00006 #include "Tools/Math/Vector2.h" 00007 #include "Tools/Math/Matrix2x2.h" 00008 00009 /** 00010 * @class ImageInfo 00011 * 00012 * Useful information about the current image, computed by the ImageProcessor. The 00013 * Specialists may use this information without the need to recompute it. 00014 */ 00015 class ImageInfo 00016 { 00017 00018 public: 00019 /** The horizon (normalized) */ 00020 Geometry::Line horizon; 00021 /** A line perpendicular to the horizon (normalized) */ 00022 Geometry::Line vertLine; 00023 /** Flag, indicates whether the horizon is in the image or not*/ 00024 bool horizonInImage; 00025 /** The starting point of the horizon*/ 00026 Vector2<int> horizonStart; 00027 /** The end point of the horizon*/ 00028 Vector2<int> horizonEnd; 00029 /** The bottom right corner of the image*/ 00030 Vector2<int> maxImageCoordinates; 00031 00032 /** The cameraMatrix of the previous image (more precisely, the last image processed by the 00033 ImageProcessor. */ 00034 CameraMatrix previousCameraMatrix; 00035 00036 /** 00037 * The rotation from a horizon-aligned coordinate system to the image coordinate 00038 * system. The horizon-aligned coordinate system is defined as follows: 00039 * - the x-coordinate points parallel to the horizon to the right 00040 * - the y-coordinate points perpendicular to the horizon downwards 00041 * - the origin is the top left corner of the image, i.e. the same as the the origin 00042 * of the image coordinate system. Thus the transformation from horizon-aligned to 00043 * image coordinates only requires the rotation matrix. 00044 * @author <a href="oberlies@sim.tu-darmstadt.de">Tobias Oberlies</a> 00045 */ 00046 Matrix2x2<double> rotation; 00047 00048 /** 00049 * The rotation from the image coordinates to the horizon-aligned coordinates. 00050 */ 00051 Matrix2x2<double> invRotation; 00052 00053 /** 00054 * The distance of the top left corner to the horizon. This value is the same as the 00055 * y-coordinate of the horizon in the horizon-aligned coordinate system. 00056 */ 00057 double distanceTopLeftCorner; 00058 00059 /** 00060 * Converts image coordintates into coordinates in the horizon-aligned coordinate system. 00061 * @param point The point in image coordinates. 00062 * @return The point in horizon-aligned coordinates. 00063 */ 00064 inline Vector2<double> toHorizonAligned(const Vector2<int>& imageCoord) const 00065 { 00066 return invRotation * Vector2<double>(static_cast<double>(imageCoord.x), static_cast<double>(imageCoord.y)); 00067 } 00068 00069 /** 00070 * Calculates the x-coordinate in the horizon-aligned coordinate system of a point in 00071 * image coordinates. 00072 * @param point The point in image coordinates. 00073 * @return The x-coordinate of the point in horizon-aligned coordinates. 00074 */ 00075 inline double horizonAlignedXOf(const Vector2<int>& imageCoord) const 00076 { 00077 return invRotation.c[0].x * static_cast<double>(imageCoord.x) 00078 + invRotation.c[1].x * static_cast<double>(imageCoord.y); 00079 } 00080 00081 /** 00082 * Calculates the y-coordinate in the horizon-aligned coordinate system of a point in 00083 * image coordinates. 00084 * @param point The point in image coordinates. 00085 * @return The y-coordinate of the point in horizon-aligned coordinates. 00086 */ 00087 inline double horizonAlignedYOf(const Vector2<int>& imageCoord) const 00088 { 00089 return invRotation.c[0].y * static_cast<double>(imageCoord.x) 00090 + invRotation.c[1].y * static_cast<double>(imageCoord.y); 00091 } 00092 00093 /** 00094 * Converts coordintates in the horizon-aligned coordinate system into image coordinates. 00095 * No clipping is done. 00096 * @param point The point in horizon-aligned coordinates. 00097 * @return The point in image coordinates. 00098 */ 00099 inline Vector2<int> toImageCoordinates(const Vector2<double>& horizonAlignedCoord) const 00100 { 00101 Vector2<double> result = rotation * horizonAlignedCoord; 00102 return Vector2<int>(static_cast<int>(result.x), static_cast<int>(result.y)); 00103 } 00104 00105 /** 00106 * Converts coordintates in the horizon-aligned coordinate system into image coordinates. 00107 * No clipping is done. 00108 * @param x The x-coordinate in the horizon-aligned coordinate system. 00109 * @param y The y-coordinate in the horizon-aligned coordinate system. 00110 * @return The point in image coordinates. 00111 */ 00112 inline Vector2<int> toImageCoordinates(double x, double y) const 00113 { 00114 return Vector2<int>(static_cast<int>(rotation.c[0].x*x + rotation.c[1].x*y), 00115 static_cast<int>(rotation.c[0].y*x + rotation.c[1].y*y)); 00116 } 00117 00118 /** 00119 * Clip the point to the image boundary. 00120 * @param point Point that is moved so that it is within the image boundary. 00121 */ 00122 inline void clipToImageBoundary(Vector2<int>& point) const 00123 { 00124 if (point.x < 0) 00125 point.x = 0; 00126 if (point.x > maxImageCoordinates.x) 00127 point.x = maxImageCoordinates.x; 00128 if (point.y < 0) 00129 point.y = 0; 00130 if (point.y > maxImageCoordinates.y) 00131 point.y = maxImageCoordinates.y; 00132 } 00133 }; 00134 00135 00136 /** 00137 * @class Run 00138 * 00139 * Describes a sequence of pixels of the same colour 00140 */ 00141 class Run 00142 { 00143 public: 00144 /** Constructor*/ 00145 Run():length(0) {} 00146 00147 /** The first point*/ 00148 Vector2<int> start; 00149 /** The last point*/ 00150 Vector2<int> end; 00151 /** The first point of the corresponding scan line*/ 00152 Vector2<int> scanLineStart; 00153 /** The length of the run*/ 00154 int length; 00155 /** The color*/ 00156 colorClass color; 00157 }; 00158 00159 00160 /** 00161 * @class TransformedRun 00162 * 00163 * Special class for comparing and clustering runs 00164 */ 00165 class TransformedRun 00166 { 00167 public: 00168 /** Computes values 00169 * @param run An original run 00170 * @param rotMat The rotation matrix 00171 * @param numOfRun The number of the transformed run 00172 */ 00173 void transform(const Run& run, const Matrix2x2<double>& rotMat, int numOfRun) 00174 { 00175 start.x = (double)(run.start.x - run.scanLineStart.x); 00176 start.y = (double)(run.start.y - run.scanLineStart.y); 00177 end.x = (double)(run.end.x - run.scanLineStart.x); 00178 end.y = (double)(run.end.y - run.scanLineStart.y); 00179 start = (rotMat*start); 00180 end = (rotMat*end); 00181 start.x += (double)run.scanLineStart.x; 00182 start.y += (double)run.scanLineStart.y; 00183 end.x += (double)run.scanLineStart.x; 00184 end.y += (double)run.scanLineStart.y; 00185 this->numOfRun = numOfRun; 00186 } 00187 00188 /** The first point*/ 00189 Vector2<double> start; 00190 /** The last point*/ 00191 Vector2<double> end; 00192 /** Number of corresponding real run*/ 00193 int numOfRun; 00194 }; 00195 00196 00197 #endif
1.3.6