QGIS API Documentation  2.99.0-Master (08ee180)
qgsrenderchecker.h
Go to the documentation of this file.
1 /***************************************************************************
2  qgsrenderchecker.h - check maprender output against an expected image
3  --------------------------------------
4  Date : 18 Jan 2008
5  Copyright : (C) 2008 by Tim Sutton
6  email : tim @ linfiniti.com
7  ***************************************************************************
8  * *
9  * This program is free software; you can redistribute it and/or modify *
10  * it under the terms of the GNU General Public License as published by *
11  * the Free Software Foundation; either version 2 of the License, or *
12  * (at your option) any later version. *
13  * *
14  ***************************************************************************/
15 
16 #ifndef QGSRENDERCHECKER_H
17 #define QGSRENDERCHECKER_H
18 
19 #include <qgis.h>
20 #include <QDir>
21 #include <QString>
22 #include <QRegExp>
23 #include <QList>
24 
25 #include <qgslogger.h>
26 #include <qgsmapsettings.h>
27 #include <qgsdartmeasurement.h>
28 
29 class QImage;
30 
36 class CORE_EXPORT QgsRenderChecker
37 {
38  public:
39 
41 
44 
45  QString controlImagePath() const;
46 
47  QString report() { return mReport; }
48 
49  float matchPercent()
50  {
51  return static_cast<float>( mMismatchCount ) /
52  static_cast<float>( mMatchTarget ) * 100;
53  }
54  unsigned int mismatchCount() { return mMismatchCount; }
55  unsigned int matchTarget() { return mMatchTarget; }
56  //only records time for actual render part
57  int elapsedTime() { return mElapsedTime; }
58  void setElapsedTimeTarget( int theTarget ) { mElapsedTimeTarget = theTarget; }
59 
64  void setControlName( const QString &theName );
65 
69  void setControlPathPrefix( const QString &theName ) { mControlPathPrefix = theName + '/'; }
70 
71  void setControlPathSuffix( const QString& theName );
72 
74  QString imageToHash( const QString& theImageFile );
75 
76  void setRenderedImage( const QString& theImageFileName ) { mRenderedImageFile = theImageFileName; }
77 
84  QString renderedImage() { return mRenderedImageFile; }
85 
87  void setMapSettings( const QgsMapSettings& mapSettings );
88 
95  void setColorTolerance( unsigned int theColorTolerance ) { mColorTolerance = theColorTolerance; }
96 
102  void setSizeTolerance( int xTolerance, int yTolerance ) { mMaxSizeDifferenceX = xTolerance; mMaxSizeDifferenceY = yTolerance; }
103 
114  bool runTest( const QString& theTestName, unsigned int theMismatchCount = 0 );
115 
127  bool compareImages( const QString& theTestName, unsigned int theMismatchCount = 0, const QString& theRenderedImageFile = "" );
128 
136  bool isKnownAnomaly( const QString& theDiffImageFile );
137 
141  static void drawBackground( QImage* image );
142 
148  QString expectedImageFile() const { return mExpectedImageFile; }
149 
157  void enableDashBuffering( bool enable ) { mBufferDashMessages = enable; }
158 
166  QVector<QgsDartMeasurement> dartMeasurements() const { return mDashMessages; }
167 
168  protected:
169  QString mReport;
170  unsigned int mMatchTarget;
174 
175  private:
176  void emitDashMessage( const QgsDartMeasurement& dashMessage );
177  void emitDashMessage( const QString& name, QgsDartMeasurement::Type type, const QString& value );
178 
179  QString mControlName;
180  unsigned int mMismatchCount;
181  unsigned int mColorTolerance;
182  int mMaxSizeDifferenceX;
183  int mMaxSizeDifferenceY;
184  int mElapsedTimeTarget;
185  QgsMapSettings mMapSettings;
186  QString mControlPathPrefix;
187  QString mControlPathSuffix;
188  QVector<QgsDartMeasurement> mDashMessages;
189  bool mBufferDashMessages;
190 }; // class QgsRenderChecker
191 
192 
200 inline bool compareWkt( const QString& a, const QString& b, double tolerance = 0.000001 )
201 {
202  QgsDebugMsg( QString( "a:%1 b:%2 tol:%3" ).arg( a, b ).arg( tolerance ) );
203  QRegExp re( "-?\\d+(?:\\.\\d+)?(?:[eE]\\d+)?" );
204 
205  QString a0( a ), b0( b );
206  a0.replace( re, QStringLiteral( "#" ) );
207  b0.replace( re, QStringLiteral( "#" ) );
208 
209  QgsDebugMsg( QString( "a0:%1 b0:%2" ).arg( a0, b0 ) );
210 
211  if ( a0 != b0 )
212  return false;
213 
214  QList<double> al, bl;
215 
216  int pos;
217  for ( pos = 0; ( pos = re.indexIn( a, pos ) ) != -1; pos += re.matchedLength() )
218  {
219  al << re.cap( 0 ).toDouble();
220  }
221  for ( pos = 0; ( pos = re.indexIn( b, pos ) ) != -1; pos += re.matchedLength() )
222  {
223  bl << re.cap( 0 ).toDouble();
224  }
225 
226  if ( al.size() != bl.size() )
227  return false;
228 
229  for ( int i = 0; i < al.size(); i++ )
230  {
231  if ( !qgsDoubleNear( al[i], bl[i], tolerance ) )
232  return false;
233  }
234 
235  return true;
236 }
237 
238 #endif
void setColorTolerance(unsigned int theColorTolerance)
Set tolerance for color components used by runTest() and compareImages().
QString expectedImageFile() const
Returns the path to the expected image file.
QVector< QgsDartMeasurement > dartMeasurements() const
Get access to buffered dash messages.
void enableDashBuffering(bool enable)
Call this to enable internal buffering of dash messages.
#define QgsDebugMsg(str)
Definition: qgslogger.h:33
QString renderedImage()
The path of the rendered image can be retrieved through that method.
This is a helper class for unit tests that need to write an image and compare it to an expected resul...
void setSizeTolerance(int xTolerance, int yTolerance)
Sets the largest allowable difference in size between the rendered and the expected image...
bool qgsDoubleNear(double a, double b, double epsilon=4 *DBL_EPSILON)
Compare two doubles (but allow some difference)
Definition: qgis.h:196
The QgsMapSettings class contains configuration for rendering of the map.
void setRenderedImage(const QString &theImageFileName)
~QgsRenderChecker()
Destructor.
unsigned int mMatchTarget
bool compareWkt(const QString &a, const QString &b, double tolerance=0.000001)
Compare two WKT strings with some tolerance.
unsigned int matchTarget()
void setControlPathPrefix(const QString &theName)
Prefix where the control images are kept.
unsigned int mismatchCount()
void setElapsedTimeTarget(int theTarget)