QGIS/tests/src/core/testqgslayoutshapes.cpp
luz.paz 0908daaa0e Misc. typos
Found via `codespell -q 3 -I ../qgis-word-whitelist.txt --skip="*.ts,*.po,./scripts/spell_check"`
2018-09-07 00:30:54 +02:00

320 lines
11 KiB
C++

/***************************************************************************
testqgslayoutshapes.cpp
----------------------
begin : October 2017
copyright : (C) 2017 by Nyall Dawson
email : nyall dot dawson at gmail.com
***************************************************************************/
/***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/
#include "qgsapplication.h"
#include "qgslayout.h"
#include "qgsmultirenderchecker.h"
#include "qgslayoutitemshape.h"
#include "qgsmapsettings.h"
#include "qgsproject.h"
#include "qgssymbol.h"
#include "qgssinglesymbolrenderer.h"
#include "qgsfillsymbollayer.h"
#include "qgsreadwritecontext.h"
#include <QObject>
#include "qgstest.h"
#include <QColor>
#include <QPainter>
class TestQgsLayoutShapes : public QObject
{
Q_OBJECT
public:
TestQgsLayoutShapes() = default;
private slots:
void initTestCase();// will be called before the first testfunction is executed.
void cleanupTestCase();// will be called after the last testfunction was executed.
void init();// will be called before each testfunction is executed.
void cleanup();// will be called after every testfunction.
void rectangle(); //test if rectangle shape is functioning
void triangle(); //test if triangle shape is functioning
void ellipse(); //test if ellipse shape is functioning
void roundedRectangle(); //test if rounded rectangle shape is functioning
void symbol(); //test if styling shapes via symbol is working
void readWriteXml();
void bounds();
void shapeRotation();
private:
QString mReport;
};
void TestQgsLayoutShapes::initTestCase()
{
QgsApplication::init();
QgsApplication::initQgis();
mReport = QStringLiteral( "<h1>Composer Shape Tests</h1>\n" );
}
void TestQgsLayoutShapes::cleanupTestCase()
{
QString myReportFile = QDir::tempPath() + "/qgistest.html";
QFile myFile( myReportFile );
if ( myFile.open( QIODevice::WriteOnly | QIODevice::Append ) )
{
QTextStream myQTextStream( &myFile );
myQTextStream << mReport;
myFile.close();
}
QgsApplication::exitQgis();
}
void TestQgsLayoutShapes::init()
{
}
void TestQgsLayoutShapes::cleanup()
{
}
void TestQgsLayoutShapes::rectangle()
{
QgsProject p;
QgsLayout l( &p );
l.initializeDefaults();
QgsLayoutItemShape *shape = new QgsLayoutItemShape( &l );
shape->attemptMove( QgsLayoutPoint( 20, 20 ) );
shape->attemptResize( QgsLayoutSize( 150, 100 ) );
QgsSimpleFillSymbolLayer *simpleFill = new QgsSimpleFillSymbolLayer();
std::unique_ptr< QgsFillSymbol > fillSymbol( new QgsFillSymbol() );
fillSymbol->changeSymbolLayer( 0, simpleFill );
simpleFill->setColor( QColor( 255, 150, 0 ) );
simpleFill->setStrokeColor( QColor( 0, 0, 0 ) );
simpleFill->setStrokeWidth( 0.3 );
simpleFill->setPenJoinStyle( Qt::MiterJoin );
shape->setSymbol( fillSymbol.get() );
l.addLayoutItem( shape );
QgsLayoutChecker checker( QStringLiteral( "composershapes_rectangle" ), &l );
checker.setControlPathPrefix( QStringLiteral( "composer_shapes" ) );
QVERIFY( checker.testLayout( mReport ) );
}
void TestQgsLayoutShapes::triangle()
{
QgsProject p;
QgsLayout l( &p );
l.initializeDefaults();
QgsLayoutItemShape *shape = new QgsLayoutItemShape( &l );
shape->setShapeType( QgsLayoutItemShape::Triangle );
shape->attemptMove( QgsLayoutPoint( 20, 20 ) );
shape->attemptResize( QgsLayoutSize( 150, 100 ) );
QgsSimpleFillSymbolLayer *simpleFill = new QgsSimpleFillSymbolLayer();
std::unique_ptr< QgsFillSymbol > fillSymbol( new QgsFillSymbol() );
fillSymbol->changeSymbolLayer( 0, simpleFill );
simpleFill->setColor( QColor( 255, 150, 0 ) );
simpleFill->setStrokeColor( QColor( 0, 0, 0 ) );
simpleFill->setStrokeWidth( 0.3 );
simpleFill->setPenJoinStyle( Qt::MiterJoin );
shape->setSymbol( fillSymbol.get() );
l.addLayoutItem( shape );
QgsLayoutChecker checker( QStringLiteral( "composershapes_triangle" ), &l );
checker.setControlPathPrefix( QStringLiteral( "composer_shapes" ) );
QVERIFY( checker.testLayout( mReport ) );
}
void TestQgsLayoutShapes::ellipse()
{
QgsProject p;
QgsLayout l( &p );
l.initializeDefaults();
QgsLayoutItemShape *shape = new QgsLayoutItemShape( &l );
shape->setShapeType( QgsLayoutItemShape::Ellipse );
shape->attemptMove( QgsLayoutPoint( 20, 20 ) );
shape->attemptResize( QgsLayoutSize( 150, 100 ) );
QgsSimpleFillSymbolLayer *simpleFill = new QgsSimpleFillSymbolLayer();
std::unique_ptr< QgsFillSymbol > fillSymbol( new QgsFillSymbol() );
fillSymbol->changeSymbolLayer( 0, simpleFill );
simpleFill->setColor( QColor( 255, 150, 0 ) );
simpleFill->setStrokeColor( QColor( 0, 0, 0 ) );
simpleFill->setStrokeWidth( 0.3 );
simpleFill->setPenJoinStyle( Qt::MiterJoin );
shape->setSymbol( fillSymbol.get() );
l.addLayoutItem( shape );
QgsLayoutChecker checker( QStringLiteral( "composershapes_ellipse" ), &l );
checker.setControlPathPrefix( QStringLiteral( "composer_shapes" ) );
QVERIFY( checker.testLayout( mReport ) );
}
void TestQgsLayoutShapes::roundedRectangle()
{
QgsProject p;
QgsLayout l( &p );
l.initializeDefaults();
QgsLayoutItemShape *shape = new QgsLayoutItemShape( &l );
shape->attemptMove( QgsLayoutPoint( 20, 20 ) );
shape->attemptResize( QgsLayoutSize( 150, 100 ) );
QgsSimpleFillSymbolLayer *simpleFill = new QgsSimpleFillSymbolLayer();
std::unique_ptr< QgsFillSymbol > fillSymbol( new QgsFillSymbol() );
fillSymbol->changeSymbolLayer( 0, simpleFill );
simpleFill->setColor( QColor( 255, 150, 0 ) );
simpleFill->setStrokeColor( QColor( 0, 0, 0 ) );
simpleFill->setStrokeWidth( 0.3 );
simpleFill->setPenJoinStyle( Qt::MiterJoin );
shape->setSymbol( fillSymbol.get() );
l.addLayoutItem( shape );
shape->setCornerRadius( QgsLayoutMeasurement( 30 ) );
QgsLayoutChecker checker( QStringLiteral( "composershapes_roundedrect" ), &l );
checker.setControlPathPrefix( QStringLiteral( "composer_shapes" ) );
QVERIFY( checker.testLayout( mReport ) );
}
void TestQgsLayoutShapes::symbol()
{
QgsProject p;
QgsLayout l( &p );
l.initializeDefaults();
QgsLayoutItemShape *shape = new QgsLayoutItemShape( &l );
shape->attemptMove( QgsLayoutPoint( 20, 20 ) );
shape->attemptResize( QgsLayoutSize( 150, 100 ) );
//setup simple fill
QgsSimpleFillSymbolLayer *simpleFill = new QgsSimpleFillSymbolLayer();
QgsFillSymbol *fillSymbol = new QgsFillSymbol();
fillSymbol->changeSymbolLayer( 0, simpleFill );
simpleFill->setColor( Qt::green );
simpleFill->setStrokeColor( Qt::yellow );
simpleFill->setStrokeWidth( 6 );
shape->setSymbol( fillSymbol );
delete fillSymbol;
l.addLayoutItem( shape );
QgsLayoutChecker checker( QStringLiteral( "composershapes_symbol" ), &l );
checker.setControlPathPrefix( QStringLiteral( "composer_shapes" ) );
QVERIFY( checker.testLayout( mReport ) );
}
void TestQgsLayoutShapes::readWriteXml()
{
QgsProject p;
QgsLayout l( &p );
std::unique_ptr< QgsLayoutItemShape > shape = qgis::make_unique< QgsLayoutItemShape >( &l );
shape->setShapeType( QgsLayoutItemShape::Triangle );
QgsSimpleFillSymbolLayer *simpleFill = new QgsSimpleFillSymbolLayer();
QgsFillSymbol *fillSymbol = new QgsFillSymbol();
fillSymbol->changeSymbolLayer( 0, simpleFill );
simpleFill->setColor( Qt::green );
simpleFill->setStrokeColor( Qt::yellow );
simpleFill->setStrokeWidth( 6 );
shape->setSymbol( fillSymbol );
delete fillSymbol;
//save original item to xml
QDomImplementation DomImplementation;
QDomDocumentType documentType =
DomImplementation.createDocumentType(
QStringLiteral( "qgis" ), QStringLiteral( "http://mrcc.com/qgis.dtd" ), QStringLiteral( "SYSTEM" ) );
QDomDocument doc( documentType );
QDomElement rootNode = doc.createElement( QStringLiteral( "qgis" ) );
shape->writeXml( rootNode, doc, QgsReadWriteContext() );
//create new item and restore settings from xml
std::unique_ptr< QgsLayoutItemShape > copy = qgis::make_unique< QgsLayoutItemShape >( &l );
QVERIFY( copy->readXml( rootNode.firstChildElement(), doc, QgsReadWriteContext() ) );
QCOMPARE( copy->shapeType(), QgsLayoutItemShape::Triangle );
QCOMPARE( copy->symbol()->symbolLayer( 0 )->color().name(), QStringLiteral( "#00ff00" ) );
QCOMPARE( copy->symbol()->symbolLayer( 0 )->strokeColor().name(), QStringLiteral( "#ffff00" ) );
}
void TestQgsLayoutShapes::bounds()
{
QgsProject p;
QgsLayout l( &p );
std::unique_ptr< QgsLayoutItemShape > shape = qgis::make_unique< QgsLayoutItemShape >( &l );
shape->attemptMove( QgsLayoutPoint( 20, 20 ) );
shape->attemptResize( QgsLayoutSize( 150, 100 ) );
QgsSimpleFillSymbolLayer *simpleFill = new QgsSimpleFillSymbolLayer();
QgsFillSymbol *fillSymbol = new QgsFillSymbol();
fillSymbol->changeSymbolLayer( 0, simpleFill );
simpleFill->setColor( Qt::green );
simpleFill->setStrokeColor( Qt::yellow );
simpleFill->setStrokeWidth( 6 );
shape->setSymbol( fillSymbol );
delete fillSymbol;
// scene bounding rect should include symbol outline
QRectF bounds = shape->sceneBoundingRect();
QCOMPARE( bounds.left(), 17.0 );
QCOMPARE( bounds.right(), 173.0 );
QCOMPARE( bounds.top(), 17.0 );
QCOMPARE( bounds.bottom(), 123.0 );
// rectWithFrame should include symbol outline too
bounds = shape->rectWithFrame();
QCOMPARE( bounds.left(), -3.0 );
QCOMPARE( bounds.right(), 153.0 );
QCOMPARE( bounds.top(), -3.0 );
QCOMPARE( bounds.bottom(), 103.0 );
}
void TestQgsLayoutShapes::shapeRotation()
{
QgsProject p;
QgsLayout l( &p );
l.initializeDefaults();
QgsLayoutItemShape *shape = new QgsLayoutItemShape( &l );
shape->attemptSetSceneRect( QRectF( 70, 70, 150, 100 ) );
shape->setItemRotation( 45 );
//setup simple fill
QgsSimpleFillSymbolLayer *simpleFill = new QgsSimpleFillSymbolLayer();
QgsFillSymbol *fillSymbol = new QgsFillSymbol();
fillSymbol->changeSymbolLayer( 0, simpleFill );
simpleFill->setColor( QColor( 255, 150, 0 ) );
simpleFill->setStrokeColor( Qt::black );
//simpleFill->setStrokeColor( Qt::yellow );
//simpleFill->setStrokeWidth( 6 );
shape->setSymbol( fillSymbol );
delete fillSymbol;
l.addLayoutItem( shape );
QgsLayoutChecker checker( QStringLiteral( "composerrotation_shape" ), &l );
checker.setControlPathPrefix( QStringLiteral( "composer_items" ) );
QVERIFY( checker.testLayout( mReport ) );
}
QGSTEST_MAIN( TestQgsLayoutShapes )
#include "testqgslayoutshapes.moc"