diff --git a/gpxsee.pro b/gpxsee.pro index c009bc37..b0223d19 100644 --- a/gpxsee.pro +++ b/gpxsee.pro @@ -178,7 +178,8 @@ HEADERS += src/common/config.h \ src/map/IMG/units.h \ src/map/IMG/style.h \ src/map/IMG/netfile.h \ - src/GUI/limitedcombobox.h + src/GUI/limitedcombobox.h \ + src/GUI/pathtickitem.h SOURCES += src/main.cpp \ src/common/coordinates.cpp \ src/common/rectc.cpp \ @@ -307,7 +308,8 @@ SOURCES += src/main.cpp \ src/map/IMG/lblfile.cpp \ src/map/IMG/vectortile.cpp \ src/map/IMG/style.cpp \ - src/map/IMG/netfile.cpp + src/map/IMG/netfile.cpp \ + src/GUI/pathtickitem.cpp greaterThan(QT_MAJOR_VERSION, 4) { HEADERS += src/data/geojsonparser.h diff --git a/src/GUI/pathitem.cpp b/src/GUI/pathitem.cpp index 7b20699b..d1e888b4 100644 --- a/src/GUI/pathitem.cpp +++ b/src/GUI/pathitem.cpp @@ -3,7 +3,7 @@ #include #include "common/greatcircle.h" #include "map/map.h" -#include "font.h" +#include "pathtickitem.h" #include "pathitem.h" @@ -19,18 +19,6 @@ static inline unsigned segments(qreal distance) return ceil(distance / GEOGRAPHICAL_MILE); } -static QFont font() -{ - QFont font; - font.setPixelSize(10); - font.setFamily(FONT_FAMILY); - font.setBold(true); - - return font; -} - -QFont PathItem::_font = font(); - PathItem::PathItem(const Path &path, Map *map, QGraphicsItem *parent) : QGraphicsObject(parent), _path(path), _map(map) { @@ -46,7 +34,7 @@ PathItem::PathItem(const Path &path, Map *map, QGraphicsItem *parent) updatePainterPath(); updateShape(); - updateTickRects(); + updateTicks(); _markerDistance = _path.first().first().distance(); _marker = new MarkerItem(this); @@ -126,30 +114,7 @@ void PathItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, painter->setPen(_pen); painter->drawPath(_painterPath); - if (_showTicks) { - painter->setFont(_font); - painter->setRenderHint(QPainter::Antialiasing, false); - - for (int i = 1; i < _tickCount; i++) { - QPoint pos(position(i * _tickSize * xInM()).toPoint()); - QPointF arrow[3] = {QPointF(pos.x() - 0.5, pos.y()), - QPointF(pos.x() + 2.5, pos.y() - 3), - QPointF(pos.x() - 3.5, pos.y() - 3)}; - QString val(QString::number(i * _tickSize)); - - QRectF br(_tickRect); - br.moveCenter(QPointF(pos.x() - 0.5, pos.y() - br.height()/2.0 - - 2.5)); - painter->setPen(Qt::white); - painter->setBrush(_pen.color()); - painter->drawPolygon(arrow, 3); - painter->drawRoundedRect(br, 1.5, 1.5); - painter->drawText(br, Qt::AlignCenter, val); - } - } - /* - painter->setBrush(Qt::NoBrush); painter->setPen(Qt::red); painter->drawRect(boundingRect()); */ @@ -163,7 +128,7 @@ void PathItem::setMap(Map *map) updatePainterPath(); updateShape(); - updateTickRects(); + updateTicks(); QPointF pos = position(_markerDistance); if (isValid(pos)) @@ -350,24 +315,30 @@ unsigned PathItem::tickSize() const return 1000; } -void PathItem::updateTickRects() +void PathItem::updateTicks() { - _tickSize = tickSize(); - qreal f = xInM(); - _tickCount = (int)_path.last().last().distance() / (_tickSize * f) + 1; + for (int i = 0; i < _ticks.size(); i++) + delete _ticks[i]; + _ticks.clear(); - QFontMetrics fm(_font); - _tickRect = fm.boundingRect(QRect(), Qt::AlignCenter, - QString::number(qMax(_tickSize * (_tickCount - 1), 10))) + if (!_showTicks) + return; + + int ts = tickSize(); + qreal f = xInM(); + int tc = (int)_path.last().last().distance() / (ts * f); + + QFontMetrics fm(PathTickItem::font()); + QRect tr = fm.boundingRect(QRect(), Qt::AlignCenter, + QString::number(qMax(ts * (tc - 1), 10))) .adjusted(-2, 0, 2, 0); - _tickBoundingRect = QRectF(); - for (int i = 1; i < _tickCount; i++) { - QPoint pos(position(i * _tickSize * xInM()).toPoint()); - QRectF br(_tickRect); - br.moveCenter(QPointF(pos.x() - 0.5, pos.y() - br.height()/2.0 - - 2.5)); - _tickBoundingRect |= br; + _ticks.resize(tc); + for (int i = 0; i < tc; i++) { + QPoint pos(position((i + 1) * ts * xInM()).toPoint()); + _ticks[i] = new PathTickItem(tr, (i + 1) * ts, this); + _ticks[i]->setPos(QPointF(pos.x() - 0.5, pos.y() - 0.5)); + _ticks[i]->setColor(_pen.color()); } } @@ -378,6 +349,7 @@ void PathItem::showTicks(bool show) prepareGeometryChange(); _showTicks = show; + updateTicks(); } void PathItem::setUnits(Units units) @@ -387,7 +359,7 @@ void PathItem::setUnits(Units units) prepareGeometryChange(); _units = units; - updateTickRects(); + updateTicks(); } void PathItem::hoverEnterEvent(QGraphicsSceneHoverEvent *event) @@ -411,10 +383,3 @@ void PathItem::hoverLeaveEvent(QGraphicsSceneHoverEvent *event) emit selected(false); } - -QRectF PathItem::boundingRect() const -{ - return _showTicks - ? _shape.boundingRect() | _tickBoundingRect - : _shape.boundingRect(); -} diff --git a/src/GUI/pathitem.h b/src/GUI/pathitem.h index 89eff43f..27508b13 100644 --- a/src/GUI/pathitem.h +++ b/src/GUI/pathitem.h @@ -8,6 +8,7 @@ #include "units.h" class Map; +class PathTickItem; class PathItem : public QGraphicsObject { @@ -17,7 +18,7 @@ public: PathItem(const Path &path, Map *map, QGraphicsItem *parent = 0); QPainterPath shape() const {return _shape;} - QRectF boundingRect() const; + QRectF boundingRect() const {return _shape.boundingRect();} void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget); @@ -43,10 +44,6 @@ public slots: signals: void selected(bool); -protected: - Path _path; - MarkerItem *_marker; - private: const PathSegment *segment(qreal x) const; QPointF position(qreal distance) const; @@ -56,11 +53,12 @@ private: qreal xInM() const; unsigned tickSize() const; - void updateTickRects(); + void updateTicks(); void hoverEnterEvent(QGraphicsSceneHoverEvent *event); void hoverLeaveEvent(QGraphicsSceneHoverEvent *event); + Path _path; Map *_map; qreal _markerDistance; int _digitalZoom; @@ -72,11 +70,9 @@ private: QPainterPath _painterPath; bool _showMarker; bool _showTicks; - QRect _tickRect; - QRectF _tickBoundingRect; - int _tickSize, _tickCount; - static QFont _font; + MarkerItem *_marker; + QVector _ticks; }; #endif // PATHITEM_H diff --git a/src/GUI/pathtickitem.cpp b/src/GUI/pathtickitem.cpp new file mode 100644 index 00000000..46f7c119 --- /dev/null +++ b/src/GUI/pathtickitem.cpp @@ -0,0 +1,56 @@ +#include +#include +#include "font.h" +#include "pathtickitem.h" + + +static QFont defaultFont() +{ + QFont font; + font.setPixelSize(10); + font.setFamily(FONT_FAMILY); + font.setBold(true); + + return font; +} + +QFont PathTickItem::_font = defaultFont(); + +PathTickItem::PathTickItem(const QRectF &tickRect, int value, + QGraphicsItem *parent) : QGraphicsItem(parent), _tickRect(tickRect), + _text(QString::number(value)) +{ + _tickRect.moveCenter(QPointF(0, -_tickRect.height()/2.0 - 3)); + + setCursor(Qt::ArrowCursor); + setAcceptHoverEvents(true); +} + +QRectF PathTickItem::boundingRect() const +{ + return _tickRect.adjusted(0, 0, 0, 3); +} + +void PathTickItem::paint(QPainter *painter, + const QStyleOptionGraphicsItem *option, QWidget *widget) +{ + Q_UNUSED(option); + Q_UNUSED(widget); + + QPointF arrow[3] = {QPointF(0, 0), QPointF(3, -3), QPointF(-3, -3)}; + + painter->setFont(_font); + painter->setRenderHint(QPainter::Antialiasing, false); + + painter->setPen(Qt::white); + painter->setBrush(_brush); + painter->drawPolygon(arrow, 3); + painter->drawRoundedRect(_tickRect, 1.5, 1.5); + painter->drawText(_tickRect, Qt::AlignCenter, _text); + +/* + painter->setBrush(Qt::NoBrush); + painter->setPen(Qt::red); + painter->drawRect(boundingRect()); +*/ +} diff --git a/src/GUI/pathtickitem.h b/src/GUI/pathtickitem.h new file mode 100644 index 00000000..9c428a36 --- /dev/null +++ b/src/GUI/pathtickitem.h @@ -0,0 +1,28 @@ +#ifndef PATHTICKITEM_H +#define PATHTICKITEM_H + +#include +#include + +class PathTickItem : public QGraphicsItem +{ +public: + PathTickItem(const QRectF &tickRect, int value, QGraphicsItem *parent = 0); + + QRectF boundingRect() const; + void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, + QWidget *widget); + + void setColor(const QColor &color) {_brush = QBrush(color);} + + static const QFont &font() {return _font;} + +private: + QRectF _tickRect; + QString _text; + QBrush _brush; + + static QFont _font; +}; + +#endif // PATHTICKITEM_H diff --git a/src/GUI/routeitem.cpp b/src/GUI/routeitem.cpp index 513e4838..22f502e6 100644 --- a/src/GUI/routeitem.cpp +++ b/src/GUI/routeitem.cpp @@ -15,7 +15,7 @@ QString RouteItem::toolTip(Units units) const tt.insert(tr("Name"), _name); if (!_desc.isEmpty()) tt.insert(tr("Description"), _desc); - tt.insert(tr("Distance"), Format::distance(_path.last().last().distance(), + tt.insert(tr("Distance"), Format::distance(path().last().last().distance(), units)); return tt.toString(); @@ -26,8 +26,9 @@ RouteItem::RouteItem(const Route &route, Map *map, QGraphicsItem *parent) { const QVector &waypoints = route.waypoints(); + _waypoints.resize(waypoints.size()); for (int i = 0; i < waypoints.size(); i++) - new WaypointItem(waypoints.at(i), map, this); + _waypoints[i] = new WaypointItem(waypoints.at(i), map, this); _name = route.name(); _desc = route.description(); @@ -38,13 +39,8 @@ RouteItem::RouteItem(const Route &route, Map *map, QGraphicsItem *parent) void RouteItem::setMap(Map *map) { - QList childs = childItems(); - for (int i = 0; i < childs.count(); i++) { - if (childs.at(i) != _marker) { - WaypointItem *wi = static_cast(childs.at(i)); - wi->setMap(map); - } - } + for (int i = 0; i < _waypoints.count(); i++) + _waypoints[i]->setMap(map); PathItem::setMap(map); } @@ -58,13 +54,8 @@ void RouteItem::setUnits(Units u) setToolTip(toolTip(units())); - QList childs = childItems(); - for (int i = 0; i < childs.count(); i++) { - if (childs.at(i) != _marker) { - WaypointItem *wi = static_cast(childs.at(i)); - wi->setToolTipFormat(units(), _coordinatesFormat); - } - } + for (int i = 0; i < _waypoints.count(); i++) + _waypoints[i]->setToolTipFormat(units(), _coordinatesFormat); } void RouteItem::setCoordinatesFormat(CoordinatesFormat format) @@ -74,30 +65,18 @@ void RouteItem::setCoordinatesFormat(CoordinatesFormat format) _coordinatesFormat = format; - QList childs = childItems(); - for (int i = 0; i < childs.count(); i++) { - if (childs.at(i) != _marker) { - WaypointItem *wi = static_cast(childs.at(i)); - wi->setToolTipFormat(units(), _coordinatesFormat); - } - } + for (int i = 0; i < _waypoints.count(); i++) + _waypoints[i]->setToolTipFormat(units(), _coordinatesFormat); } void RouteItem::showWaypoints(bool show) { - QList childs = childItems(); - for (int i = 0; i < childs.count(); i++) - if (childs.at(i) != _marker) - childs.at(i)->setVisible(show); + for (int i = 0; i < _waypoints.count(); i++) + _waypoints[i]->setVisible(show); } void RouteItem::showWaypointLabels(bool show) { - QList childs = childItems(); - for (int i = 0; i < childs.count(); i++) { - if (childs.at(i) != _marker) { - WaypointItem *wi = static_cast(childs.at(i)); - wi->showLabel(show); - } - } + for (int i = 0; i < _waypoints.count(); i++) + _waypoints[i]->showLabel(show); } diff --git a/src/GUI/routeitem.h b/src/GUI/routeitem.h index 8b99ab8c..882e68ae 100644 --- a/src/GUI/routeitem.h +++ b/src/GUI/routeitem.h @@ -7,6 +7,7 @@ #include "format.h" class Map; +class WaypointItem; class RouteItem : public PathItem { @@ -28,6 +29,8 @@ private: QString _name; QString _desc; CoordinatesFormat _coordinatesFormat; + + QVector _waypoints; }; #endif // ROUTEITEM_H diff --git a/src/GUI/trackitem.cpp b/src/GUI/trackitem.cpp index d24e36db..1ddb3ae8 100644 --- a/src/GUI/trackitem.cpp +++ b/src/GUI/trackitem.cpp @@ -13,7 +13,7 @@ QString TrackItem::toolTip(Units units) const tt.insert(tr("Name"), _name); if (!_desc.isEmpty()) tt.insert(tr("Description"), _desc); - tt.insert(tr("Distance"), Format::distance(_path.last().last().distance(), + tt.insert(tr("Distance"), Format::distance(path().last().last().distance(), units)); if (_time > 0) tt.insert(tr("Total time"), Format::timeSpan(_time));