diff --git a/src/KChart/Polar/KChartRadarDiagram.cpp b/src/KChart/Polar/KChartRadarDiagram.cpp
index d03dc24..19ed72d 100644
--- a/src/KChart/Polar/KChartRadarDiagram.cpp
+++ b/src/KChart/Polar/KChartRadarDiagram.cpp
@@ -1,332 +1,331 @@
/*
* Copyright (C) 2001-2015 Klaralvdalens Datakonsult AB. All rights reserved.
*
* This file is part of the KD Chart library.
*
* 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.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
#include "KChartRadarDiagram.h"
#include "KChartRadarDiagram_p.h"
#include "KChartPaintContext.h"
#include "KChartPainterSaver_p.h"
#include "KChartMath_p.h"
#include
using namespace KChart;
RadarDiagram::Private::Private() :
closeDatasets( false ),
reverseData( false ),
fillAlpha( 0.0 )
{
}
RadarDiagram::Private::~Private() {}
#define d d_func()
RadarDiagram::RadarDiagram( QWidget* parent, RadarCoordinatePlane* plane ) :
AbstractPolarDiagram( new Private( ), parent, plane )
{
//init();
}
RadarDiagram::~RadarDiagram()
{
}
void RadarDiagram::init()
{
}
RadarDiagram * RadarDiagram::clone() const
{
RadarDiagram* newDiagram = new RadarDiagram( new Private( *d ) );
// This needs to be copied after the fact
newDiagram->d->closeDatasets = d->closeDatasets;
return newDiagram;
}
const QPair RadarDiagram::calculateDataBoundaries () const
{
if ( !checkInvariants(true) ) return QPair( QPointF( 0, 0 ), QPointF( 0, 0 ) );
const int rowCount = model()->rowCount(rootIndex());
const int colCount = model()->columnCount(rootIndex());
qreal xMin = 0.0;
qreal xMax = colCount;
qreal yMin = 0, yMax = 0;
for ( int iCol=0; iColdata( model()->index( iRow, iCol, rootIndex() ) ).toReal(); // checked
yMax = qMax( yMax, value );
yMin = qMin( yMin, value );
}
}
QPointF bottomLeft ( QPointF( xMin, yMin ) );
QPointF topRight ( QPointF( xMax, yMax ) );
return QPair ( bottomLeft, topRight );
}
void RadarDiagram::paintEvent ( QPaintEvent*)
{
QPainter painter ( viewport() );
PaintContext ctx;
ctx.setPainter ( &painter );
ctx.setRectangle( QRectF ( 0, 0, width(), height() ) );
paint ( &ctx );
}
void RadarDiagram::paint( PaintContext* ctx )
{
qreal dummy1, dummy2;
paint( ctx, true, dummy1, dummy2 );
paint( ctx, false, dummy1, dummy2 );
}
static qreal fitFontSizeToGeometry( const QString& text, const QFont& font, const QRectF& geometry, const TextAttributes& ta )
{
QFont f = font;
const qreal origResult = f.pointSizeF();
qreal result = origResult;
const QSizeF mySize = geometry.size();
if ( mySize.isNull() )
return result;
const QString t = text;
QFontMetrics fm( f );
while ( true )
{
const QSizeF textSize = rotatedRect( fm.boundingRect( t ), ta.rotation() ).normalized().size();
if ( textSize.height() <= mySize.height() && textSize.width() <= mySize.width() )
return result;
result -= 0.5;
if ( result <= 0.0 )
return origResult;
f.setPointSizeF( result );
fm = QFontMetrics( f );
}
}
static QPointF scaleToRealPosition( const QPointF& origin, const QRectF& sourceRect, const QRectF& destRect, const AbstractCoordinatePlane& plane )
{
QPointF result = plane.translate( origin );
result -= sourceRect.topLeft();
result.setX( result.x() / sourceRect.width() * destRect.width() );
result.setY( result.y() / sourceRect.height() * destRect.height() );
result += destRect.topLeft();
return result;
}
void RadarDiagram::setReverseData( bool val )
{
d->reverseData = val;
}
bool RadarDiagram::reverseData()
{
return d->reverseData;
}
// local structure to remember the settings of a polygon inclusive the used color and pen.
struct Polygon {
QPolygonF polygon;
QBrush brush;
QPen pen;
Polygon(const QPolygonF &polygon, const QBrush &brush, const QPen &pen) : polygon(polygon), brush(brush), pen(pen) {}
};
void RadarDiagram::paint( PaintContext* ctx,
bool calculateListAndReturnScale,
qreal& newZoomX, qreal& newZoomY )
{
// note: Not having any data model assigned is no bug
// but we can not draw a diagram then either.
if ( !checkInvariants(true) )
return;
d->reverseMapper.clear();
const int rowCount = model()->rowCount( rootIndex() );
const int colCount = model()->columnCount( rootIndex() );
int iRow, iCol;
const qreal min = dataBoundaries().first.y();
const qreal r = qAbs( min ) + dataBoundaries().second.y();
const qreal step = ( r - qAbs( min ) ) / ( numberOfGridRings() );
RadarCoordinatePlane* plane = dynamic_cast(ctx->coordinatePlane());
TextAttributes ta = plane->textAttributes();
QRectF fontRect = ctx->rectangle();
fontRect.setSize( QSizeF( fontRect.width(), step / 2.0 ) );
const qreal labelFontSize = fitFontSizeToGeometry( QString::fromLatin1( "TestXYWQgqy" ), ta.font(), fontRect, ta );
QFont labelFont = ta.font();
ctx->painter()->setPen( ta.pen() );
labelFont.setPointSizeF( labelFontSize );
const QFontMetricsF metric( labelFont );
const qreal labelHeight = metric.height();
- QPointF offset;
QRectF destRect = ctx->rectangle();
if ( ta.isVisible() )
{
destRect.setY( destRect.y() + 2 * labelHeight );
destRect.setHeight( destRect.height() - 4 * labelHeight );
}
if ( calculateListAndReturnScale ) {
ctx->painter()->save();
// Check if all of the data value texts / data comments will fit
// into the available space:
d->labelPaintCache.clear();
ctx->painter()->save();
for ( iCol=0; iCol < colCount; ++iCol ) {
for ( iRow=0; iRow < rowCount; ++iRow ) {
QModelIndex index = model()->index( iRow, iCol, rootIndex() ); // checked
const qreal value = model()->data( index ).toReal();
QPointF point = scaleToRealPosition( QPointF( value, iRow ), ctx->rectangle(), destRect, *ctx->coordinatePlane() );
d->addLabel( &d->labelPaintCache, index, nullptr, PositionPoints( point ),
Position::Center, Position::Center, value );
}
}
ctx->painter()->restore();
const qreal oldZoomX = coordinatePlane()->zoomFactorX();
const qreal oldZoomY = coordinatePlane()->zoomFactorY();
newZoomX = oldZoomX;
newZoomY = oldZoomY;
if ( d->labelPaintCache.paintReplay.count() ) {
QRectF txtRectF;
d->paintDataValueTextsAndMarkers( ctx, d->labelPaintCache, true, true, &txtRectF );
const QRect txtRect = txtRectF.toRect();
const QRect curRect = coordinatePlane()->geometry();
const qreal gapX = qMin( txtRect.left() - curRect.left(), curRect.right() - txtRect.right() );
const qreal gapY = qMin( txtRect.top() - curRect.top(), curRect.bottom() - txtRect.bottom() );
newZoomX = oldZoomX;
newZoomY = oldZoomY;
if ( gapX < 0.0 )
newZoomX *= 1.0 + (gapX-1.0) / curRect.width();
if ( gapY < 0.0 )
newZoomY *= 1.0 + (gapY-1.0) / curRect.height();
}
ctx->painter()->restore();
} else {
// Iterate through data sets and create a list of polygons out of them.
QList polygons;
for ( iCol=0; iCol < colCount; ++iCol ) {
//TODO(khz): As of yet RadarDiagram can not show per-segment line attributes
// but it draws every polyline in one go - using one color.
// This needs to be enhanced to allow for cell-specific settings
// in the same way as LineDiagram does it.
QPolygonF polygon;
QPointF point0;
for ( iRow=0; iRow < rowCount; ++iRow ) {
QModelIndex index = model()->index( iRow, iCol, rootIndex() ); // checked
const qreal value = model()->data( index ).toReal();
QPointF point = scaleToRealPosition( QPointF( value, d->reverseData ? ( rowCount - iRow ) : iRow ), ctx->rectangle(), destRect, *ctx->coordinatePlane() );
polygon.append( point );
if ( ! iRow )
point0= point;
}
if ( closeDatasets() && rowCount )
polygon.append( point0 );
QBrush brush = d->datasetAttrs( iCol, KChart::DatasetBrushRole ).value();
QPen p = d->datasetAttrs( iCol, KChart::DatasetPenRole ).value< QPen >();
if ( p.style() != Qt::NoPen )
{
polygons.append( Polygon( polygon, brush, PrintingParameters::scalePen( p ) ) );
}
}
// first fill the areas with the brush-color and the defined alpha-value.
if (d->fillAlpha > 0.0) {
Q_FOREACH(const Polygon& p, polygons) {
PainterSaver painterSaver( ctx->painter() );
ctx->painter()->setRenderHint ( QPainter::Antialiasing );
QBrush br = p.brush;
QColor c = br.color();
c.setAlphaF(d->fillAlpha);
br.setColor(c);
ctx->painter()->setBrush( br );
ctx->painter()->setPen( p.pen );
ctx->painter()->drawPolygon( p.polygon );
}
}
// then draw the poly-lines.
Q_FOREACH(const Polygon& p, polygons) {
PainterSaver painterSaver( ctx->painter() );
ctx->painter()->setRenderHint ( QPainter::Antialiasing );
ctx->painter()->setBrush( p.brush );
ctx->painter()->setPen( p.pen );
ctx->painter()->drawPolyline( p.polygon );
}
d->paintDataValueTextsAndMarkers( ctx, d->labelPaintCache, true );
}
}
void RadarDiagram::resize ( const QSizeF& size )
{
AbstractPolarDiagram::resize( size );
}
/*virtual*/
qreal RadarDiagram::valueTotals () const
{
return model()->rowCount(rootIndex());
}
/*virtual*/
qreal RadarDiagram::numberOfValuesPerDataset() const
{
return model() ? model()->rowCount(rootIndex()) : 0.0;
}
/*virtual*/
qreal RadarDiagram::numberOfGridRings() const
{
return 5; // FIXME
}
void RadarDiagram::setCloseDatasets( bool closeDatasets )
{
d->closeDatasets = closeDatasets;
}
bool RadarDiagram::closeDatasets() const
{
return d->closeDatasets;
}
qreal RadarDiagram::fillAlpha() const
{
return d->fillAlpha;
}
void RadarDiagram::setFillAlpha(qreal alphaF)
{
d->fillAlpha = alphaF;
}
void RadarDiagram::resizeEvent ( QResizeEvent*)
{
}
diff --git a/src/KChart/ReverseMapper.cpp b/src/KChart/ReverseMapper.cpp
index 7e7596c..c058870 100644
--- a/src/KChart/ReverseMapper.cpp
+++ b/src/KChart/ReverseMapper.cpp
@@ -1,178 +1,177 @@
/*
* Copyright (C) 2001-2015 Klaralvdalens Datakonsult AB. All rights reserved.
*
* This file is part of the KD Chart library.
*
* 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.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
#include "ReverseMapper.h"
#include
#include
#include
#include
#include
#include
#include "KChartAbstractDiagram.h"
#include "ChartGraphicsItem.h"
using namespace KChart;
ReverseMapper::ReverseMapper()
: m_scene( nullptr )
, m_diagram( nullptr )
{
}
ReverseMapper::ReverseMapper( AbstractDiagram* diagram )
: m_scene( nullptr )
, m_diagram( diagram )
{
}
ReverseMapper::~ReverseMapper()
{
delete m_scene; m_scene = nullptr;
}
void ReverseMapper::setDiagram( AbstractDiagram* diagram )
{
m_diagram = diagram;
}
void ReverseMapper::clear()
{
m_itemMap.clear();
delete m_scene;
m_scene = new QGraphicsScene();
}
QModelIndexList ReverseMapper::indexesIn( const QRect& rect ) const
{
Q_ASSERT( m_diagram );
if ( m_scene && m_scene->sceneRect().intersects( rect ) ) {
QList items = m_scene->items( rect );
QModelIndexList indexes;
Q_FOREACH( QGraphicsItem* item, items ) {
ChartGraphicsItem* i = qgraphicsitem_cast( item );
if ( i ) {
QModelIndex index ( m_diagram->model()->index( i->row(), i->column(), m_diagram->rootIndex() ) ); // checked
indexes << index;
}
}
return indexes;
} else {
return QModelIndexList();
}
}
QModelIndexList ReverseMapper::indexesAt( const QPointF& point ) const
{
Q_ASSERT( m_diagram );
if ( m_scene && m_scene->sceneRect().contains( point ) ) {
QList items = m_scene->items( point );
QModelIndexList indexes;
Q_FOREACH( QGraphicsItem* item, items ) {
ChartGraphicsItem* i = qgraphicsitem_cast( item );
if ( i ) {
QModelIndex index ( m_diagram->model()->index( i->row(), i->column(), m_diagram->rootIndex() ) ); // checked
if ( !indexes.contains(index) )
indexes << index;
}
}
return indexes;
} else {
return QModelIndexList();
}
}
QPolygonF ReverseMapper::polygon( int row, int column ) const
{
if ( !m_diagram->model()->hasIndex( row, column, m_diagram->rootIndex() ) )
return QPolygon();
const QModelIndex index = m_diagram->model()->index( row, column, m_diagram->rootIndex() ); // checked
return m_itemMap.contains( index ) ? m_itemMap[ index ]->polygon() : QPolygon();
}
QRectF ReverseMapper::boundingRect( int row, int column ) const
{
if ( !m_diagram->model()->hasIndex( row, column, m_diagram->rootIndex() ) )
return QRectF();
const QModelIndex index = m_diagram->model()->index( row, column, m_diagram->rootIndex() ); // checked
return m_itemMap.contains( index ) ? m_itemMap[ index ]->polygon().boundingRect() : QRectF();
}
void ReverseMapper::addItem( ChartGraphicsItem* item )
{
Q_ASSERT( m_scene );
m_scene->addItem( item );
m_itemMap.insert( m_diagram->model()->index( item->row(), item->column(), m_diagram->rootIndex() ), item ); // checked
}
void ReverseMapper::addRect( int row, int column, const QRectF& rect )
{
addPolygon( row, column, QPolygonF( rect ) );
}
void ReverseMapper::addPolygon( int row, int column, const QPolygonF& polygon )
{
ChartGraphicsItem* item = new ChartGraphicsItem( row, column );
item->setPolygon( polygon );
addItem( item );
}
void ReverseMapper::addCircle( int row, int column, const QPointF& location, const QSizeF& diameter )
{
QPainterPath path;
QPointF ossfet( -0.5*diameter.width(), -0.5*diameter.height() );
path.addEllipse( QRectF( location + ossfet, diameter ) );
addPolygon( row, column, QPolygonF( path.toFillPolygon() ) );
}
void ReverseMapper::addLine( int row, int column, const QPointF& from, const QPointF& to )
{
// that's no line, dude... make a small circle around that point, instead
if ( from == to )
{
addCircle( row, column, from, QSizeF( 1.5, 1.5 ) );
return;
}
// lines do not make good polygons to click on. we calculate a 2
// pixel wide rectangle, where the original line is excatly
// centered in.
// make a 3 pixel wide polygon from the line:
- static const QPointF pixel( 1.0, 1.0 );
QPointF left, right;
if ( from.x() < to.x() ) {
left = from;
right = to;
} else {
right = from;
left = to;
}
const QPointF lineVector( right - left );
const qreal lineVectorLength = sqrt( lineVector.x() * lineVector.x() + lineVector.y() * lineVector.y() );
const QPointF lineVectorUnit( lineVector / lineVectorLength );
const QPointF normOfLineVectorUnit( -lineVectorUnit.y(), lineVectorUnit.x() );
// now the four polygon end points:
const QPointF one( left - lineVectorUnit + normOfLineVectorUnit );
const QPointF two( left - lineVectorUnit - normOfLineVectorUnit );
const QPointF three( right + lineVectorUnit - normOfLineVectorUnit );
const QPointF four( right + lineVectorUnit + normOfLineVectorUnit );
addPolygon( row, column, QPolygonF() << one << two << three << four );
}
diff --git a/src/KChart/Ternary/KChartTernaryAxis.cpp b/src/KChart/Ternary/KChartTernaryAxis.cpp
index 5b1713f..13bd363 100644
--- a/src/KChart/Ternary/KChartTernaryAxis.cpp
+++ b/src/KChart/Ternary/KChartTernaryAxis.cpp
@@ -1,280 +1,279 @@
/*
* Copyright (C) 2001-2015 Klaralvdalens Datakonsult AB. All rights reserved.
*
* This file is part of the KD Chart library.
*
* 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.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
#include "KChartTernaryAxis.h"
#include
#include
#include
#include "TernaryConstants.h"
#include "KChartTernaryCoordinatePlane.h"
#include "KChartAbstractTernaryDiagram.h"
#include "KChartLayoutItems.h"
#include "KChartTextLabelCache.h"
using namespace KChart;
// m_label and m_fifty do not have to be pointers, once the class is
// pimpled (PrerenderedLabel is not published API)
TernaryAxis::TernaryAxis ( AbstractTernaryDiagram* diagram)
: AbstractAxis( diagram )
, m_position( KChartEnums::PositionUnknown )
, m_label( new PrerenderedLabel )
, m_fifty( new PrerenderedLabel )
{
resetTitleTextAttributes();
setPosition( KChartEnums::PositionSouth ); // arbitrary
m_fifty->setText( QObject::tr( "50%" ) ); // const
// FIXME is this consistent with other diagram/axis/plane implementations?
diagram->addAxis( this );
}
TernaryAxis::~TernaryAxis()
{
delete m_label; m_label = nullptr;
delete m_fifty; m_fifty = nullptr;
}
void TernaryAxis::paintAll (QPainter &)
{
// not used
}
void TernaryAxis::paint (QPainter *)
{
// not used
}
void TernaryAxis::paintCtx (PaintContext * paintContext)
{
QPainter* p = paintContext->painter();
TernaryCoordinatePlane* plane =
(TernaryCoordinatePlane*) paintContext->coordinatePlane();
// QObject* refArea = plane->parent();
- QRectF titleArea;
// paint the axis label (across the triangle, that one):
QList labels;
labels << m_label << m_fifty;
Q_FOREACH( PrerenderedLabel* label, labels ) {
const QPixmap& pixmap = label->pixmap();
QPointF point = plane->translate( label->position() )
- label->referencePointLocation();
p->drawPixmap( point, pixmap );
}
}
bool TernaryAxis::isEmpty() const
{
// todo: what's this method for?
return false;
}
QRect TernaryAxis::geometry () const
{
return m_geometry;
}
void TernaryAxis::setGeometry (const QRect &rect)
{
m_geometry = rect;
}
QSize TernaryAxis::minimumSize () const
{
// todo: return realistic sizes
return QSize( 100, 100 );
}
QSize TernaryAxis::maximumSize () const
{
return QSize( 300, 200 );
}
QSize TernaryAxis::sizeHint () const
{
return QSize( 150, 100 );
}
Qt::Orientations TernaryAxis::expandingDirections () const
{
return Qt::Vertical | Qt::Horizontal;
}
const Position TernaryAxis::position () const
{
return m_position;
}
void TernaryAxis::setPosition (Position p)
{
if ( p == position() ) return;
if ( p != KChartEnums::PositionWest
&& p != KChartEnums::PositionEast
&& p != KChartEnums::PositionSouth )
{
qDebug() << "TernaryAxis::setPosition: only south, east and west are supported "
"positions for ternary axes.";
return;
}
if ( m_title.isEmpty() )
switch ( p.value() ) {
case KChartEnums::PositionSouth:
m_label->setText( tr( "A" ) );
break;
case KChartEnums::PositionWest:
m_label->setText( tr( "C" ) );
break;
case KChartEnums::PositionEast:
m_label->setText( tr( "B" ) );
break;
default:
break;
}
m_position = p;
updatePrerenderedLabels(); // position has changed
}
void TernaryAxis::setTitleText( const QString& text )
{
m_title = text; // do not remove
m_label->setText( text );
}
QString TernaryAxis::titleText() const
{
return m_label->text();
}
void TernaryAxis::setTitleTextAttributes( const TextAttributes &a )
{
m_titleAttributes = a;
updatePrerenderedLabels();
}
TextAttributes TernaryAxis::titleTextAttributes() const
{
return m_titleAttributes;
}
void TernaryAxis::resetTitleTextAttributes()
{
TextAttributes a;
m_titleAttributes = a;
updatePrerenderedLabels();
}
bool TernaryAxis::hasDefaultTitleTextAttributes() const
{
TextAttributes a;
return m_titleAttributes == a;
}
void TernaryAxis::updatePrerenderedLabels()
{
TextAttributes attributes = titleTextAttributes();
qreal axisLabelAngle = 0.0;
qreal fiftyMarkAngle = 0.0;
QPointF axisLabelPosition;
QPointF fiftyMarkPosition;
KChartEnums::PositionValue fiftyMarkReferencePoint = KChartEnums::PositionUnknown;
switch ( position().value() ) {
case KChartEnums::PositionSouth:
// this is the axis on the other side of A
axisLabelAngle = 0.0;
fiftyMarkAngle = 0.0;
axisLabelPosition = TriangleTop;
fiftyMarkPosition = 0.5 * AxisVector_B_C - RelMarkerLength * Norm_B_C;
fiftyMarkReferencePoint = KChartEnums::PositionNorth;
break;
case KChartEnums::PositionEast:
// this is the axis on the other side of B
axisLabelAngle = 240.0;
fiftyMarkAngle = 60;
axisLabelPosition = TriangleBottomLeft;
fiftyMarkPosition = AxisVector_B_C + 0.5 * AxisVector_C_A - RelMarkerLength * Norm_C_A;
fiftyMarkReferencePoint = KChartEnums::PositionSouth;
break;
case KChartEnums::PositionWest:
// this is the axis on the other side of C
axisLabelAngle = 120.0;
fiftyMarkAngle = 300.0;
axisLabelPosition = TriangleBottomRight;
fiftyMarkPosition = 0.5 * AxisVector_B_A + RelMarkerLength * Norm_B_A;
fiftyMarkReferencePoint = KChartEnums::PositionSouth;
break;
case KChartEnums::PositionUnknown:
break; // initial value
default:
qDebug() << "TernaryAxis::updatePrerenderedLabel: unknown location";
};
m_label->setFont( attributes.font() );
// m_label->setText( titleText() ); // done by setTitleText()
m_label->setAngle( axisLabelAngle );
m_label->setPosition( axisLabelPosition );
m_label->setReferencePoint( KChartEnums::PositionSouth );
QFont font = attributes.font();
font.setPointSizeF( 0.85 * font.pointSizeF() );
m_fifty->setFont( font );
m_fifty->setAngle( fiftyMarkAngle );
m_fifty->setPosition( fiftyMarkPosition );
m_fifty->setReferencePoint( fiftyMarkReferencePoint );
}
QPair TernaryAxis::requiredMargins() const
{
QSizeF topleft( 0.0, 0.0 );
QSizeF bottomRight( 0.0, 0.0 );
switch ( position().value() ) {
case KChartEnums::PositionSouth:
// the label of the south axis is, in fact, up north.
topleft.setHeight( m_label->pixmap().height() );
bottomRight.setHeight( m_fifty->pixmap().height() );
break;
case KChartEnums::PositionWest:
bottomRight.setWidth( m_label->pixmap().width()
- m_label->referencePointLocation().x() );
bottomRight.setHeight( m_label->pixmap().height()
- m_label->referencePointLocation().y() );
break;
case KChartEnums::PositionEast:
topleft.setWidth( m_label->pixmap().width()
- ( m_label->pixmap().width()
- m_label->referencePointLocation().x() ) );
bottomRight.setHeight( m_label->pixmap().height()
- ( m_label->pixmap().height()
- m_label->referencePointLocation().y() ) );
break;
default:
qDebug() << "TernaryAxis::requiredMargins: unknown location";
}
// qDebug() << "TernaryAxis::requiredMargins:" << topleft << bottomRight;
return QPair( topleft, bottomRight );
}
diff --git a/src/KGantt/test/TestKGanttConstraintModel.cpp b/src/KGantt/test/TestKGanttConstraintModel.cpp
index 4a5eba9..1f8d707 100644
--- a/src/KGantt/test/TestKGanttConstraintModel.cpp
+++ b/src/KGantt/test/TestKGanttConstraintModel.cpp
@@ -1,86 +1,84 @@
/*
* Copyright (C) 2018 Dag Andersen
*
* This file is part of the KGantt library.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public License
* along with this library; see the file COPYING.LIB. If not, write to
* the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
* Boston, MA 02110-1301, USA.
*/
#include "TestKGanttConstraintModel.h"
#include "kganttglobal.h"
#include
using namespace KGantt;
void TestKGanttConstraintModel::initTestCase()
{
itemModel = new QStandardItemModel(100, 100);
}
void TestKGanttConstraintModel::cleanupTestCase()
{
delete itemModel;
}
void TestKGanttConstraintModel::testModel()
{
ConstraintModel model;
- QModelIndex invalidIndex;
-
QCOMPARE(model.constraints().count(), 0);
model.addConstraint(Constraint(QModelIndex(), QModelIndex()));
QCOMPARE(model.constraints().count(), 1);
model.addConstraint(Constraint(QModelIndex(), QModelIndex()));
QCOMPARE(model.constraints().count(), 1);
QPersistentModelIndex idx1 = itemModel->index(7, 17, QModelIndex());
QPersistentModelIndex idx2 = itemModel->index(42, 17, QModelIndex());
model.addConstraint(Constraint(idx1, idx2));
QCOMPARE(model.constraints().count(), 2);
QVERIFY(model.hasConstraint(Constraint(idx1, idx2)));
QCOMPARE(model.constraintsForIndex(QModelIndex()).count(), 1);
QCOMPARE(model.constraints().count(), 2);
model.removeConstraint(Constraint(QModelIndex(), QModelIndex()));
QCOMPARE(model.constraints().count(), 1);
QVERIFY(!model.hasConstraint(Constraint(QModelIndex(), QModelIndex())));
model.removeConstraint(Constraint(QModelIndex(), QModelIndex()));
QCOMPARE(model.constraints().count(), 1);
model.removeConstraint(Constraint(idx1, idx2));
QCOMPARE(model.constraints().count(), 0);
QVERIFY(!model.hasConstraint(Constraint(idx1, idx2)));
model.addConstraint(Constraint(idx1, idx2));
QVERIFY(model.hasConstraint(Constraint(idx1, idx2)));
itemModel->removeRow(8);
QVERIFY(idx2 == itemModel->index(41, 17, QModelIndex()));
QVERIFY(model.hasConstraint(Constraint(idx1, idx2)));
itemModel->removeRow(7);
QVERIFY(!idx1.isValid());
QVERIFY(idx2 == itemModel->index(40, 17, QModelIndex()));
QVERIFY(model.hasConstraint(Constraint(idx1, idx2)));
}
QTEST_GUILESS_MAIN(TestKGanttConstraintModel)