summaryrefslogtreecommitdiffstats
path: root/src/piechart/piesliceitem.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/piechart/piesliceitem.cpp')
-rw-r--r--src/piechart/piesliceitem.cpp319
1 files changed, 0 insertions, 319 deletions
diff --git a/src/piechart/piesliceitem.cpp b/src/piechart/piesliceitem.cpp
deleted file mode 100644
index 2f3728a8..00000000
--- a/src/piechart/piesliceitem.cpp
+++ /dev/null
@@ -1,319 +0,0 @@
-/****************************************************************************
-**
-** Copyright (C) 2014 Digia Plc
-** All rights reserved.
-** For any questions to Digia, please use contact form at http://qt.digia.com
-**
-** This file is part of the Qt Enterprise Charts Add-on.
-**
-** $QT_BEGIN_LICENSE$
-** Licensees holding valid Qt Enterprise licenses may use this file in
-** accordance with the Qt Enterprise License Agreement provided with the
-** Software or, alternatively, in accordance with the terms contained in
-** a written agreement between you and Digia.
-**
-** If you have questions regarding the use of this file, please use
-** contact form at http://qt.digia.com
-** $QT_END_LICENSE$
-**
-****************************************************************************/
-
-#include "piesliceitem_p.h"
-#include "piechartitem_p.h"
-#include "qpieseries.h"
-#include "qpieslice.h"
-#include "chartpresenter_p.h"
-#include <QPainter>
-#include <qmath.h>
-#include <QGraphicsSceneEvent>
-#include <QTime>
-#include <QTextDocument>
-#include <QDebug>
-
-QTCOMMERCIALCHART_BEGIN_NAMESPACE
-
-QPointF offset(qreal angle, qreal length)
-{
- qreal dx = qSin(angle * (M_PI / 180)) * length;
- qreal dy = qCos(angle * (M_PI / 180)) * length;
- return QPointF(dx, -dy);
-}
-
-PieSliceItem::PieSliceItem(QGraphicsItem *parent)
- : QGraphicsObject(parent),
- m_hovered(false)
-{
- setAcceptHoverEvents(true);
- setAcceptedMouseButtons(Qt::MouseButtonMask);
- setZValue(ChartPresenter::PieSeriesZValue);
- m_labelItem = new QGraphicsTextItem(this);
- m_labelItem->document()->setDocumentMargin(1.0);
-}
-
-PieSliceItem::~PieSliceItem()
-{
- // If user is hovering over the slice and it gets destroyed we do
- // not get a hover leave event. So we must emit the signal here.
- if (m_hovered)
- emit hovered(false);
-}
-
-QRectF PieSliceItem::boundingRect() const
-{
- return m_boundingRect;
-}
-
-QPainterPath PieSliceItem::shape() const
-{
- // Don't include the label and label arm.
- // This is used to detect a mouse clicks. We do not want clicks from label.
- return m_slicePath;
-}
-
-void PieSliceItem::paint(QPainter *painter, const QStyleOptionGraphicsItem * /*option*/, QWidget * /*widget*/)
-{
- painter->save();
- painter->setClipRect(parentItem()->boundingRect());
- painter->setPen(m_data.m_slicePen);
- painter->setBrush(m_data.m_sliceBrush);
- painter->drawPath(m_slicePath);
- painter->restore();
-
- if (m_data.m_isLabelVisible) {
- painter->save();
-
- // Pen for label arm not defined in the QPieSeries api, let's use brush's color instead
- painter->setBrush(m_data.m_labelBrush);
-
- if (m_data.m_labelPosition == QPieSlice::LabelOutside) {
- painter->setClipRect(parentItem()->boundingRect());
- painter->strokePath(m_labelArmPath, m_data.m_labelBrush.color());
- }
-
- painter->restore();
- }
-}
-
-void PieSliceItem::hoverEnterEvent(QGraphicsSceneHoverEvent * /*event*/)
-{
- m_hovered = true;
- emit hovered(true);
-}
-
-void PieSliceItem::hoverLeaveEvent(QGraphicsSceneHoverEvent * /*event*/)
-{
- m_hovered = false;
- emit hovered(false);
-}
-
-void PieSliceItem::mousePressEvent(QGraphicsSceneMouseEvent *event)
-{
- emit clicked(event->buttons());
-}
-
-void PieSliceItem::setLayout(const PieSliceData &sliceData)
-{
- m_data = sliceData;
- updateGeometry();
- update();
-}
-
-void PieSliceItem::updateGeometry()
-{
- if (m_data.m_radius <= 0)
- return;
-
- prepareGeometryChange();
-
- // slice path
- qreal centerAngle;
- QPointF armStart;
- m_slicePath = slicePath(m_data.m_center, m_data.m_radius, m_data.m_startAngle, m_data.m_angleSpan, &centerAngle, &armStart);
-
- m_labelItem->setVisible(m_data.m_isLabelVisible);
-
- if (m_data.m_isLabelVisible) {
- // text rect
- m_labelTextRect = ChartPresenter::textBoundingRect(m_data.m_labelFont,
- m_data.m_labelText,
- 0);
-
- QString label(m_data.m_labelText);
- m_labelItem->setDefaultTextColor(m_data.m_labelBrush.color());
- m_labelItem->setFont(m_data.m_labelFont);
-
- // text position
- if (m_data.m_labelPosition == QPieSlice::LabelOutside) {
- setFlag(QGraphicsItem::ItemClipsChildrenToShape, false);
-
- // label arm path
- QPointF labelTextStart;
- m_labelArmPath = labelArmPath(armStart, centerAngle,
- m_data.m_radius * m_data.m_labelArmLengthFactor,
- m_labelTextRect.width(), &labelTextStart);
-
- m_labelTextRect.moveBottomLeft(labelTextStart);
- if (m_labelTextRect.left() < 0)
- m_labelTextRect.setLeft(0);
- else if (m_labelTextRect.left() < parentItem()->boundingRect().left())
- m_labelTextRect.setLeft(parentItem()->boundingRect().left());
- if (m_labelTextRect.right() > parentItem()->boundingRect().right())
- m_labelTextRect.setRight(parentItem()->boundingRect().right());
-
- label = ChartPresenter::truncatedText(m_data.m_labelFont, m_data.m_labelText,
- qreal(0.0), m_labelTextRect.width(),
- m_labelTextRect.height(), m_labelTextRect);
- m_labelArmPath = labelArmPath(armStart, centerAngle,
- m_data.m_radius * m_data.m_labelArmLengthFactor,
- m_labelTextRect.width(), &labelTextStart);
- m_labelTextRect.moveBottomLeft(labelTextStart);
-
- m_labelItem->setTextWidth(m_labelTextRect.width()
- + m_labelItem->document()->documentMargin());
- m_labelItem->setHtml(label);
- m_labelItem->setRotation(0);
- m_labelItem->setPos(m_labelTextRect.x(), m_labelTextRect.y() + 1.0);
- } else {
- // label inside
- setFlag(QGraphicsItem::ItemClipsChildrenToShape);
- m_labelItem->setTextWidth(m_labelTextRect.width()
- + m_labelItem->document()->documentMargin());
- m_labelItem->setHtml(label);
-
- QPointF textCenter;
- if (m_data.m_holeRadius > 0) {
- textCenter = m_data.m_center + offset(centerAngle, m_data.m_holeRadius
- + (m_data.m_radius
- - m_data.m_holeRadius) / 2);
- } else {
- textCenter = m_data.m_center + offset(centerAngle, m_data.m_radius / 2);
- }
- m_labelItem->setPos(textCenter.x() - m_labelItem->boundingRect().width() / 2,
- textCenter.y() - m_labelTextRect.height() / 2);
-
- QPointF labelCenter = m_labelItem->boundingRect().center();
- m_labelItem->setTransformOriginPoint(labelCenter);
-
- if (m_data.m_labelPosition == QPieSlice::LabelInsideTangential) {
- m_labelItem->setRotation(m_data.m_startAngle + m_data.m_angleSpan / 2);
- } else if (m_data.m_labelPosition == QPieSlice::LabelInsideNormal) {
- if (m_data.m_startAngle + m_data.m_angleSpan / 2 < 180)
- m_labelItem->setRotation(m_data.m_startAngle + m_data.m_angleSpan / 2 - 90);
- else
- m_labelItem->setRotation(m_data.m_startAngle + m_data.m_angleSpan / 2 + 90);
- } else {
- m_labelItem->setRotation(0);
- }
- }
- // Hide label if it's outside the bounding rect of parent item
- QRectF labelRect(m_labelItem->boundingRect());
- labelRect.moveTopLeft(m_labelItem->pos());
- if ((parentItem()->boundingRect().left()
- < (labelRect.left() + m_labelItem->document()->documentMargin() + 1.0))
- && (parentItem()->boundingRect().right()
- > (labelRect.right() - m_labelItem->document()->documentMargin() - 1.0))
- && (parentItem()->boundingRect().top()
- < (labelRect.top() + m_labelItem->document()->documentMargin() + 1.0))
- && (parentItem()->boundingRect().bottom()
- > (labelRect.bottom() - m_labelItem->document()->documentMargin() - 1.0)))
- m_labelItem->show();
- else
- m_labelItem->hide();
- }
-
- // bounding rect
- if (m_data.m_isLabelVisible)
- m_boundingRect = m_slicePath.boundingRect().united(m_labelArmPath.boundingRect()).united(m_labelTextRect);
- else
- m_boundingRect = m_slicePath.boundingRect();
-
- // Inflate bounding rect by 2/3 pen width to make sure it encompasses whole slice also for thick pens
- // and miter joins.
- int penWidth = (m_data.m_slicePen.width() * 2) / 3;
- m_boundingRect = m_boundingRect.adjusted(-penWidth, -penWidth, penWidth, penWidth);
-}
-
-QPointF PieSliceItem::sliceCenter(QPointF point, qreal radius, QPieSlice *slice)
-{
- if (slice->isExploded()) {
- qreal centerAngle = slice->startAngle() + (slice->angleSpan() / 2);
- qreal len = radius * slice->explodeDistanceFactor();
- point += offset(centerAngle, len);
- }
- return point;
-}
-
-QPainterPath PieSliceItem::slicePath(QPointF center, qreal radius, qreal startAngle, qreal angleSpan, qreal *centerAngle, QPointF *armStart)
-{
- // calculate center angle
- *centerAngle = startAngle + (angleSpan / 2);
-
- // calculate slice rectangle
- QRectF rect(center.x() - radius, center.y() - radius, radius * 2, radius * 2);
-
- // slice path
- QPainterPath path;
- if (m_data.m_holeRadius > 0) {
- QRectF insideRect(center.x() - m_data.m_holeRadius, center.y() - m_data.m_holeRadius, m_data.m_holeRadius * 2, m_data.m_holeRadius * 2);
- path.arcMoveTo(rect, -startAngle + 90);
- path.arcTo(rect, -startAngle + 90, -angleSpan);
- path.arcTo(insideRect, -startAngle + 90 - angleSpan, angleSpan);
- path.closeSubpath();
- } else {
- path.moveTo(rect.center());
- path.arcTo(rect, -startAngle + 90, -angleSpan);
- path.closeSubpath();
- }
-
- // calculate label arm start point
- *armStart = center;
- *armStart += offset(*centerAngle, radius + PIESLICE_LABEL_GAP);
-
- return path;
-}
-
-QPainterPath PieSliceItem::labelArmPath(QPointF start, qreal angle, qreal length, qreal textWidth, QPointF *textStart)
-{
- // Normalize the angle to 0-360 range
- // NOTE: We are using int here on purpose. Depenging on platform and hardware
- // qreal can be a double, float or something the user gives to the Qt configure
- // (QT_COORD_TYPE). Compilers do not seem to support modulo for double or float
- // but there are fmod() and fmodf() functions for that. So instead of some #ifdef
- // that might break we just use int. Precision for this is just fine for our needs.
- int normalized = angle * 10.0;
- normalized = normalized % 3600;
- if (normalized < 0)
- normalized += 3600;
- angle = (qreal) normalized / 10.0;
-
- // prevent label arm pointing straight down because it will look bad
- if (angle < 180 && angle > 170)
- angle = 170;
- if (angle > 180 && angle < 190)
- angle = 190;
-
- // line from slice to label
- QPointF parm1 = start + offset(angle, length);
-
- // line to underline the label
- QPointF parm2 = parm1;
- if (angle < 180) { // arm swings the other way on the left side
- parm2 += QPointF(textWidth, 0);
- *textStart = parm1;
- } else {
- parm2 += QPointF(-textWidth, 0);
- *textStart = parm2;
- }
-
- QPainterPath path;
- path.moveTo(start);
- path.lineTo(parm1);
- path.lineTo(parm2);
-
- return path;
-}
-
-#include "moc_piesliceitem_p.cpp"
-
-QTCOMMERCIALCHART_END_NAMESPACE
-