diff --git a/gpxsee.nsi b/gpxsee.nsi
index 94080a3f..8fe322cc 100644
--- a/gpxsee.nsi
+++ b/gpxsee.nsi
@@ -63,7 +63,7 @@ Section "GPXSee (required)" SEC_APP
; Write the uninstall keys for Windows
WriteRegStr HKCU "${REGENTRY}" "DisplayName" "GPXSee"
WriteRegStr HKCU "${REGENTRY}" "Publisher" "Martin Tuma"
- WriteRegStr HKCU "${REGENTRY}" "DisplayVersion" "2.4"
+ WriteRegStr HKCU "${REGENTRY}" "DisplayVersion" "2.5"
WriteRegStr HKCU "${REGENTRY}" "UninstallString" '"$INSTDIR\uninstall.exe"'
WriteRegDWORD HKCU "${REGENTRY}" "NoModify" 1
WriteRegDWORD HKCU "${REGENTRY}" "NoRepair" 1
diff --git a/gpxsee.pro b/gpxsee.pro
index 043e755e..122d5ff5 100644
--- a/gpxsee.pro
+++ b/gpxsee.pro
@@ -27,7 +27,8 @@ HEADERS += src/config.h \
src/filebrowser.h \
src/map.h \
src/maplist.h \
- src/downloader.h
+ src/downloader.h \
+ src/units.h
SOURCES += src/main.cpp \
src/gui.cpp \
src/gpx.cpp \
diff --git a/lang/gpxsee_cs.ts b/lang/gpxsee_cs.ts
index d2c5f07e..691ec3c6 100644
--- a/lang/gpxsee_cs.ts
+++ b/lang/gpxsee_cs.ts
@@ -15,31 +15,43 @@
+
km
km
+
m
m
-
+
Ascent
Stoupání
-
+
Descent
Klesání
-
+
Minimum
Minimum
-
+
+ mi
+ mi
+
+
+
+ ft
+ ft
+
+
+
Maximum
Maximum
@@ -52,12 +64,12 @@
O Qt
-
+
GPXSee is distributed under the terms of the GNU General Public License version 3. For more info about GPXSee visit the project homepage at
Program GPXSee je distribuován pod podmínkami licence GNU General Public License verze 3. Pro více informací navštivte stránky programu na adrese
-
+
Open file
Otevřít soubor
@@ -67,7 +79,7 @@
Uložit jako
-
+
Open POI file
Otevřít POI soubor
@@ -83,8 +95,8 @@
-
-
+
+
Keyboard controls
Ovládací klávesy
@@ -104,20 +116,20 @@
Znovu načíst
-
+
Show
Zobrazit
-
-
+
+
File
Soubor
-
-
+
+
Data sources
Zdroje dat
@@ -148,190 +160,205 @@
+ Metric
+ Metrické
+
+
+
+ Imperial
+ Imperiální
+
+
+
Next
Následující
-
+
Previous
Předchozí
-
+
Last
Poslední
-
+
First
První
-
+
Map
Mapa
-
+
POI
POI
-
+
Settings
Nastavení
-
+
+ Units
+ Jednotky
+
+
+
Help
Nápověda
-
+
Elevation
Výška
-
+
Speed
Rychlost
-
+
Next file
Následující soubor
-
+
Previous file
Předchozí soubor
-
+
First file
První soubor
-
+
Last file
Poslední soubor
-
+
Append modifier
Modifikátor nahradit/přidat
-
+
Map (tiles) source URLs are read on program startup from the following file:
URL mapových zdrojů (dlaždic) jsou načteny při startu programu z následujícího souboru:
-
+
The file format is one map entry per line, consisting of the map name and tiles URL delimited by a TAB character. The tile X and Y coordinates are replaced with $x and $y in the URL and the zoom level is replaced with $z. An example map file could look like:
Formát souboru je jeden mapový záznam na řádku, kde mapový záznam sestává ze jména mapy a URL dlaždic navzájem oddělených tabulátorem. Souřadnice dlaždice jsou v URL nahrazeny řetězci $x a $y, úroven přiblížení (zoom) pak řetězcem $z. Příklad:
-
+
To make GPXSee load a POI file automatically on startup, add the file to the following directory:
POI soubory, které se mají automaticky nahrát při startu programu jsou načítány z následujícího adresáře:
-
-
+
+
Line: %1
Řádka: %1
-
+
Maximum
Maximum
-
+
Minimum
Minimum
-
+
About GPXSee
O aplikaci GPXSee
-
+
Navigation
Navigace
-
+
GPX viewer and analyzer
Prohlížeč a analyzátor GPX
-
+
Map sources
Mapové zdroje
-
+
POIs
POI body
-
+
Distance
Vzdálenost
-
+
Time
Čas
-
+
Ascent
Stoupání
-
-
-
-
+
+
+
+
m
m
-
+
Descent
Klesání
-
+
%1 tracks
Počet tras: %1
-
-
+
+
km
km
-
-
+
+
Error
Chyba
-
+
Error loading GPX file:
%1
Soubor GPX nelze otevřít:
%1
-
+
Error loading POI file:
%1
Soubor POI nelze otevřít:
@@ -352,11 +379,13 @@
+
km
+
km/h
km/h
@@ -370,5 +399,15 @@
Maximum
Maximum
+
+
+ mi
+ mi
+
+
+
+ mi/h
+ mi/h
+
diff --git a/src/config.h b/src/config.h
index a91ed59a..2ea923bd 100644
--- a/src/config.h
+++ b/src/config.h
@@ -3,7 +3,7 @@
#define APP_NAME "GPXSee"
#define APP_HOMEPAGE "http://tumic.wz.cz/gpxsee"
-#define APP_VERSION "2.4"
+#define APP_VERSION "2.5"
#define FONT_FAMILY "Arial"
#define FONT_SIZE 12
diff --git a/src/elevationgraph.cpp b/src/elevationgraph.cpp
index 136ee379..cfee6301 100644
--- a/src/elevationgraph.cpp
+++ b/src/elevationgraph.cpp
@@ -14,7 +14,19 @@ ElevationGraph::ElevationGraph(QWidget *parent) : Graph(parent)
Graph::setYLabel(tr("Elevation"));
Graph::setXUnits(tr("km"));
Graph::setYUnits(tr("m"));
- Graph::setXScale(0.001);
+ Graph::setXScale(M2KM);
+}
+
+void ElevationGraph::addInfo()
+{
+ Graph::addInfo(tr("Ascent"), QString::number(_ascent * _yScale, 'f', 0)
+ + THIN_SPACE + _yUnits);
+ Graph::addInfo(tr("Descent"), QString::number(_descent * _yScale, 'f', 0)
+ + THIN_SPACE + _yUnits);
+ Graph::addInfo(tr("Maximum"), QString::number(_max * _yScale, 'f', 0)
+ + THIN_SPACE + _yUnits);
+ Graph::addInfo(tr("Minimum"), QString::number(_min * _yScale, 'f', 0)
+ + THIN_SPACE + _yUnits);
}
void ElevationGraph::loadGPX(const GPX &gpx)
@@ -49,16 +61,8 @@ void ElevationGraph::loadGPX(const GPX &gpx)
_max = qMax(_max, max);
_min = qMin(_min, min);
- addInfo(tr("Ascent"), QString::number(_ascent, 'f', 0)
- + THIN_SPACE + _yUnits);
- addInfo(tr("Descent"), QString::number(_descent, 'f', 0)
- + THIN_SPACE + _yUnits);
- addInfo(tr("Maximum"), QString::number(_max, 'f', 0)
- + THIN_SPACE + _yUnits);
- addInfo(tr("Minimum"), QString::number(_min, 'f', 0)
- + THIN_SPACE + _yUnits);
-
- Graph::loadData(data);
+ addInfo();
+ loadData(data);
}
void ElevationGraph::clear()
@@ -70,3 +74,23 @@ void ElevationGraph::clear()
Graph::clear();
}
+
+void ElevationGraph::setUnits(enum Units units)
+{
+ if (units == Metric) {
+ Graph::setXUnits(tr("km"));
+ Graph::setYUnits(tr("m"));
+ Graph::setXScale(M2KM);
+ Graph::setYScale(1);
+ } else {
+ Graph::setXUnits(tr("mi"));
+ Graph::setYUnits(tr("ft"));
+ Graph::setXScale(M2MI);
+ Graph::setYScale(M2FT);
+ }
+
+ clearInfo();
+ addInfo();
+
+ redraw();
+}
diff --git a/src/elevationgraph.h b/src/elevationgraph.h
index 66fbce78..5e8ad24b 100644
--- a/src/elevationgraph.h
+++ b/src/elevationgraph.h
@@ -3,6 +3,7 @@
#include "graph.h"
#include "gpx.h"
+#include "units.h"
class ElevationGraph : public Graph
{
@@ -13,6 +14,7 @@ public:
void loadGPX(const GPX &gpx);
void clear();
+ void setUnits(enum Units units);
qreal ascent() const {return _ascent;}
qreal descent() const {return _descent;}
@@ -20,6 +22,8 @@ public:
qreal min() const {return _min;}
private:
+ void addInfo();
+
qreal _ascent, _descent;
qreal _max, _min;
};
diff --git a/src/graph.cpp b/src/graph.cpp
index 83cf6ab8..c1755e4e 100644
--- a/src/graph.cpp
+++ b/src/graph.cpp
@@ -116,6 +116,16 @@ void Graph::setYUnits(const QString &units)
createYLabel();
}
+void Graph::setXScale(qreal scale)
+{
+ _xScale = scale;
+}
+
+void Graph::setYScale(qreal scale)
+{
+ _yScale = scale;
+}
+
void Graph::loadData(const QVector &data)
{
QPainterPath path;
@@ -143,7 +153,13 @@ void Graph::loadData(const QVector &data)
if (_graphs.size() > 1)
_sliderInfo->hide();
- resize(viewport()->size() - QSizeF(MARGIN, MARGIN));
+ redraw();
+}
+
+void Graph::redraw()
+{
+ if (!_graphs.isEmpty())
+ resize(viewport()->size() - QSizeF(MARGIN, MARGIN));
}
void Graph::resize(const QSizeF &size)
@@ -187,8 +203,11 @@ void Graph::resize(const QSizeF &size)
_scene->addItem(_xAxis);
_scene->addItem(_yAxis);
+ qreal sp = (_slider->pos().x() == _slider->area().left())
+ ? 0 : (_slider->pos().x() - _slider->area().left())
+ / _slider->area().width();
_slider->setArea(r);
- _slider->setPos(r.bottomLeft());
+ _slider->setPos(QPointF(sp * r.width(), r.bottom()));
_scene->addItem(_slider);
r = _scene->itemsBoundingRect();
@@ -202,7 +221,7 @@ void Graph::resize(const QSizeF &size)
void Graph::resizeEvent(QResizeEvent *)
{
if (!_graphs.empty())
- resize(viewport()->size() - QSizeF(MARGIN, MARGIN));
+ redraw();
}
void Graph::plot(QPainter *painter, const QRectF &target)
@@ -234,6 +253,7 @@ void Graph::clear()
_scene->removeItem(_info);
_sliderInfo->show();
+ _slider->clear();
_info->clear();
_scene->clear();
_graphs.clear();
@@ -285,3 +305,8 @@ void Graph::addInfo(const QString &key, const QString &value)
{
_info->insert(key, value);
}
+
+void Graph::clearInfo()
+{
+ _info->clear();
+}
diff --git a/src/graph.h b/src/graph.h
index c351b06d..62a10af1 100644
--- a/src/graph.h
+++ b/src/graph.h
@@ -41,10 +41,12 @@ public:
void setYLabel(const QString &label);
void setXUnits(const QString &units);
void setYUnits(const QString &units);
- void setXScale(qreal scale) {_xScale = scale;}
- void setYScale(qreal scale) {_yScale = scale;}
+ void setXScale(qreal scale);
+ void setYScale(qreal scale);
void setPrecision(int p) {_precision = p;}
+ void redraw();
+
void plot(QPainter *painter, const QRectF &target);
void clear();
@@ -52,6 +54,7 @@ public:
void setSliderPosition(qreal pos);
void addInfo(const QString &key, const QString &value);
+ void clearInfo();
signals:
void sliderPositionChanged(qreal);
diff --git a/src/gui.cpp b/src/gui.cpp
index 379a607b..c522749c 100644
--- a/src/gui.cpp
+++ b/src/gui.cpp
@@ -31,7 +31,7 @@ static QString timeSpan(qreal time)
s = time - (h * 3600) - (m * 60);
return QString("%1:%2:%3").arg(h).arg(m, 2, 10, QChar('0'))
- .arg(s,2, 10, QChar('0'));
+ .arg(s, 2, 10, QChar('0'));
}
@@ -193,6 +193,19 @@ void GUI::createActions()
_showToolbarsAction->setChecked(true);
connect(_showToolbarsAction, SIGNAL(triggered(bool)), this,
SLOT(showToolbars(bool)));
+ QActionGroup *ag = new QActionGroup(this);
+ ag->setExclusive(true);
+ _metricUnitsAction = new QAction(tr("Metric"), this);
+ _metricUnitsAction->setCheckable(true);
+ _metricUnitsAction->setActionGroup(ag);
+ _metricUnitsAction->setChecked(true);
+ connect(_metricUnitsAction, SIGNAL(triggered()), this,
+ SLOT(setMetricUnits()));
+ _imperialUnitsAction = new QAction(tr("Imperial"), this);
+ _imperialUnitsAction->setCheckable(true);
+ _imperialUnitsAction->setActionGroup(ag);
+ connect(_imperialUnitsAction, SIGNAL(triggered()), this,
+ SLOT(setImperialUnits()));
// Navigation actions
_nextAction = new QAction(QIcon(QPixmap(NEXT_FILE_ICON)), tr("Next"), this);
@@ -237,6 +250,10 @@ void GUI::createMenus()
_poiMenu->addAction(_showPOIAction);
_settingsMenu = menuBar()->addMenu(tr("Settings"));
+ _unitsMenu = _settingsMenu->addMenu(tr("Units"));
+ _unitsMenu->addAction(_metricUnitsAction);
+ _unitsMenu->addAction(_imperialUnitsAction);
+ _settingsMenu->addSeparator();
_settingsMenu->addAction(_showToolbarsAction);
_settingsMenu->addAction(_showGraphsAction);
@@ -487,17 +504,31 @@ void GUI::saveFile(const QString &fileName)
QGraphicsScene scene;
InfoItem info;
- info.insert(tr("Distance"), QString::number(_distance / 1000, 'f', 1)
- + THIN_SPACE + tr("km"));
- info.insert(tr("Time"), timeSpan(_time));
- info.insert(tr("Ascent"), QString::number(_elevationGraph->ascent(), 'f', 0)
- + THIN_SPACE + tr("m"));
- info.insert(tr("Descent"), QString::number(_elevationGraph->descent(), 'f',
- 0) + THIN_SPACE + tr("m"));
- info.insert(tr("Maximum"), QString::number(_elevationGraph->max(), 'f', 0)
- + THIN_SPACE + tr("m"));
- info.insert(tr("Minimum"), QString::number(_elevationGraph->min(), 'f', 0)
- + THIN_SPACE + tr("m"));
+ if (_imperialUnitsAction->isChecked()) {
+ info.insert(tr("Distance"), QString::number(_distance * M2MI, 'f', 1)
+ + THIN_SPACE + tr("mi"));
+ info.insert(tr("Time"), timeSpan(_time));
+ info.insert(tr("Ascent"), QString::number(_elevationGraph->ascent()
+ * M2FT, 'f', 0) + THIN_SPACE + tr("ft"));
+ info.insert(tr("Descent"), QString::number(_elevationGraph->descent()
+ * M2FT, 'f', 0) + THIN_SPACE + tr("ft"));
+ info.insert(tr("Maximum"), QString::number(_elevationGraph->max()
+ * M2FT, 'f', 0) + THIN_SPACE + tr("ft"));
+ info.insert(tr("Minimum"), QString::number(_elevationGraph->min()
+ * M2FT, 'f', 0) + THIN_SPACE + tr("ft"));
+ } else {
+ info.insert(tr("Distance"), QString::number(_distance * M2KM, 'f', 1)
+ + THIN_SPACE + tr("km"));
+ info.insert(tr("Time"), timeSpan(_time));
+ info.insert(tr("Ascent"), QString::number(_elevationGraph->ascent(),
+ 'f', 0) + THIN_SPACE + tr("m"));
+ info.insert(tr("Descent"), QString::number(_elevationGraph->descent(),
+ 'f', 0) + THIN_SPACE + tr("m"));
+ info.insert(tr("Maximum"), QString::number(_elevationGraph->max(), 'f',
+ 0) + THIN_SPACE + tr("m"));
+ info.insert(tr("Minimum"), QString::number(_elevationGraph->min(), 'f',
+ 0) + THIN_SPACE + tr("m"));
+ }
scene.addItem(&info);
scene.render(&p, QRectF(0, 0, printer.width(), 200));
@@ -593,8 +624,12 @@ void GUI::updateStatusBarInfo()
else
_fileNameLabel->setText(tr("%1 tracks").arg(_files.size()));
- _distanceLabel->setText(QString::number(_distance / 1000, 'f', 1)
- + " " + tr("km"));
+ if (_imperialUnitsAction->isChecked())
+ _distanceLabel->setText(QString::number(_distance * M2MI, 'f', 1)
+ + " " + tr("mi"));
+ else
+ _distanceLabel->setText(QString::number(_distance * M2KM, 'f', 1)
+ + " " + tr("km"));
_timeLabel->setText(timeSpan(_time));
}
@@ -633,6 +668,20 @@ void GUI::updateNavigationActions()
}
}
+void GUI::setMetricUnits()
+{
+ _elevationGraph->setUnits(Metric);
+ _speedGraph->setUnits(Metric);
+ updateStatusBarInfo();
+}
+
+void GUI::setImperialUnits()
+{
+ _elevationGraph->setUnits(Imperial);
+ _speedGraph->setUnits(Imperial);
+ updateStatusBarInfo();
+}
+
void GUI::next()
{
QString file = _browser->next();
diff --git a/src/gui.h b/src/gui.h
index 049bb5c4..ec98b094 100644
--- a/src/gui.h
+++ b/src/gui.h
@@ -50,6 +50,9 @@ private slots:
void last();
void first();
+ void setMetricUnits();
+ void setImperialUnits();
+
private:
void loadFiles();
@@ -73,6 +76,7 @@ private:
QMenu *_poiMenu;
QMenu *_mapMenu;
QMenu *_settingsMenu;
+ QMenu *_unitsMenu;
QToolBar *_fileToolBar;
QToolBar *_showToolBar;
@@ -100,6 +104,8 @@ private:
QAction *_prevAction;
QAction *_lastAction;
QAction *_firstAction;
+ QAction *_metricUnitsAction;
+ QAction *_imperialUnitsAction;
QList _mapActions;
QLabel *_fileNameLabel;
diff --git a/src/slideritem.cpp b/src/slideritem.cpp
index 104066ec..5d2192fe 100644
--- a/src/slideritem.cpp
+++ b/src/slideritem.cpp
@@ -46,3 +46,9 @@ QVariant SliderItem::itemChange(GraphicsItemChange change, const QVariant &value
return QGraphicsItem::itemChange(change, value);
}
+
+void SliderItem::clear()
+{
+ _area = QRectF();
+ setPos(QPointF());
+}
diff --git a/src/slideritem.h b/src/slideritem.h
index be8c6921..047f46e0 100644
--- a/src/slideritem.h
+++ b/src/slideritem.h
@@ -17,6 +17,8 @@ public:
QRectF area() {return _area;}
void setArea(const QRectF &area) {_area = area;}
+ void clear();
+
signals:
void positionChanged(const QPointF&);
diff --git a/src/speedgraph.cpp b/src/speedgraph.cpp
index b2488108..22d50280 100644
--- a/src/speedgraph.cpp
+++ b/src/speedgraph.cpp
@@ -10,11 +10,19 @@ SpeedGraph::SpeedGraph(QWidget *parent) : Graph(parent)
Graph::setYLabel(tr("Speed"));
Graph::setXUnits(tr("km"));
Graph::setYUnits(tr("km/h"));
- Graph::setXScale(0.001);
- Graph::setYScale(3.6);
+ Graph::setXScale(M2KM);
+ Graph::setYScale(MS2KMH);
Graph::setPrecision(1);
}
+void SpeedGraph::addInfo()
+{
+ Graph::addInfo(tr("Average"), QString::number(avg() * _yScale, 'f', 1)
+ + THIN_SPACE + _yUnits);
+ Graph::addInfo(tr("Maximum"), QString::number(_max * _yScale, 'f', 1)
+ + THIN_SPACE + _yUnits);
+}
+
void SpeedGraph::loadGPX(const GPX &gpx)
{
QVector data;
@@ -31,13 +39,8 @@ void SpeedGraph::loadGPX(const GPX &gpx)
max = qMax(max, data.at(i).y());
_max = qMax(_max, max);
-
- addInfo(tr("Average"), QString::number(avg() * _yScale, 'f', 1)
- + THIN_SPACE + _yUnits);
- addInfo(tr("Maximum"), QString::number(_max * _yScale, 'f', 1)
- + THIN_SPACE + _yUnits);
-
- Graph::loadData(data);
+ addInfo();
+ loadData(data);
}
qreal SpeedGraph::avg() const
@@ -60,3 +63,23 @@ void SpeedGraph::clear()
Graph::clear();
}
+
+void SpeedGraph::setUnits(enum Units units)
+{
+ if (units == Metric) {
+ Graph::setXUnits(tr("km"));
+ Graph::setYUnits(tr("km/h"));
+ Graph::setXScale(M2KM);
+ Graph::setYScale(MS2KMH);
+ } else {
+ Graph::setXUnits(tr("mi"));
+ Graph::setYUnits(tr("mi/h"));
+ Graph::setXScale(M2MI);
+ Graph::setYScale(MS2MIH);
+ }
+
+ clearInfo();
+ addInfo();
+
+ redraw();
+}
diff --git a/src/speedgraph.h b/src/speedgraph.h
index c9dc6e8c..9acf0087 100644
--- a/src/speedgraph.h
+++ b/src/speedgraph.h
@@ -4,6 +4,7 @@
#include
#include "graph.h"
#include "gpx.h"
+#include "units.h"
class SpeedGraph : public Graph
{
@@ -14,11 +15,14 @@ public:
void loadGPX(const GPX &gpx);
void clear();
+ void setUnits(enum Units units);
qreal avg() const;
qreal max() const {return _max;}
private:
+ void addInfo();
+
qreal _max;
QList _avg;
};
diff --git a/src/units.h b/src/units.h
new file mode 100644
index 00000000..59f68dd4
--- /dev/null
+++ b/src/units.h
@@ -0,0 +1,15 @@
+#ifndef UNITS_H
+#define UNITS_H
+
+enum Units {
+ Metric,
+ Imperial
+};
+
+#define M2KM 0.001000000000 // m -> km
+#define M2MI 0.000621371192 // m -> mi
+#define M2FT 3.280839900000 // m -> ft
+#define MS2KMH 3.600000000000 // m/s -> km/h
+#define MS2MIH 2.236936290000 // m/s -> mi/h
+
+#endif // UNITS_H