mirror of
https://github.com/tumic0/GPXSee.git
synced 2024-11-28 05:34:47 +01:00
Added support for REST WMTS maps
This commit is contained in:
parent
55e967673c
commit
5e5ff6d96f
@ -126,21 +126,20 @@ Map *MapSource::map(QXmlStreamReader &reader)
|
||||
{
|
||||
QString name, url, layer, style, set;
|
||||
QString format("image/png");
|
||||
bool invert = false;
|
||||
bool wmts, rest = false, invertAxis = false;
|
||||
Range z(ZOOM_MIN, ZOOM_MAX);
|
||||
RectC b(Coordinates(BOUNDS_LEFT, BOUNDS_TOP),
|
||||
Coordinates(BOUNDS_RIGHT, BOUNDS_BOTTOM));
|
||||
|
||||
const QXmlStreamAttributes &attr = reader.attributes();
|
||||
bool wmts = (attr.hasAttribute("type") && attr.value("type") == "WMTS")
|
||||
? true : false;
|
||||
wmts = (reader.attributes().value("type") == "WMTS") ? true : false;
|
||||
|
||||
while (reader.readNextStartElement()) {
|
||||
if (reader.name() == "name")
|
||||
name = reader.readElementText();
|
||||
else if (reader.name() == "url")
|
||||
else if (reader.name() == "url") {
|
||||
rest = (reader.attributes().value("type") == "REST") ? true : false;
|
||||
url = reader.readElementText();
|
||||
else if (reader.name() == "zoom") {
|
||||
} else if (reader.name() == "zoom") {
|
||||
z = zooms(reader);
|
||||
reader.skipCurrentElement();
|
||||
} else if (reader.name() == "bounds") {
|
||||
@ -155,7 +154,7 @@ Map *MapSource::map(QXmlStreamReader &reader)
|
||||
else if (reader.name() == "set")
|
||||
set = reader.readElementText();
|
||||
else if (reader.name() == "axis")
|
||||
invert = (reader.readElementText() == "yx") ? true : false;
|
||||
invertAxis = (reader.readElementText() == "yx") ? true : false;
|
||||
else
|
||||
reader.skipCurrentElement();
|
||||
}
|
||||
@ -163,7 +162,8 @@ Map *MapSource::map(QXmlStreamReader &reader)
|
||||
if (reader.error())
|
||||
return 0;
|
||||
else if (wmts)
|
||||
return new WMTSMap(name, url, format, layer, style, set, invert);
|
||||
return new WMTSMap(name, WMTS::Setup(url, layer, set, style, format,
|
||||
rest), invertAxis);
|
||||
else
|
||||
return new OnlineMap(name, url, z, b);
|
||||
}
|
||||
|
@ -41,12 +41,21 @@ static int scale2zoom(qreal scale)
|
||||
|
||||
|
||||
OnlineMap::OnlineMap(const QString &name, const QString &url,
|
||||
const Range &zooms, const RectC &bounds, QObject *parent)
|
||||
: Map(parent), _name(name), _zooms(zooms), _bounds(bounds)
|
||||
const Range &zooms, const RectC &bounds, QObject *parent) :
|
||||
Map(parent), _name(name), _zooms(zooms), _bounds(bounds),
|
||||
_block(false), _valid(false)
|
||||
{
|
||||
_block = false;
|
||||
QString dir(TILES_DIR + "/" + _name);
|
||||
|
||||
_zoom = _zooms.max();
|
||||
_tileLoader = TileLoader(url, TILES_DIR + "/" + name);
|
||||
_tileLoader = TileLoader(url, dir);
|
||||
|
||||
if (!QDir().mkpath(dir)) {
|
||||
_errorString = "Error creating tiles dir";
|
||||
return;
|
||||
}
|
||||
|
||||
_valid = true;
|
||||
}
|
||||
|
||||
void OnlineMap::load()
|
||||
|
@ -39,6 +39,9 @@ public:
|
||||
void load();
|
||||
void unload();
|
||||
|
||||
bool isValid() const {return _valid;}
|
||||
QString errorString() const {return _errorString;}
|
||||
|
||||
private slots:
|
||||
void emitLoaded();
|
||||
|
||||
@ -53,6 +56,9 @@ private:
|
||||
RectC _bounds;
|
||||
int _zoom;
|
||||
bool _block;
|
||||
|
||||
bool _valid;
|
||||
QString _errorString;
|
||||
};
|
||||
|
||||
#endif // ONLINEMAP_H
|
||||
|
@ -17,13 +17,6 @@ static bool loadTileFile(Tile &tile, const QString &file)
|
||||
|
||||
Downloader *TileLoader::_downloader = 0;
|
||||
|
||||
TileLoader::TileLoader(const QString &url, const QString &dir)
|
||||
: _url(url), _dir(dir)
|
||||
{
|
||||
if (!QDir().mkpath(_dir))
|
||||
qWarning("Error creating tiles dir: %s\n", qPrintable(_dir));
|
||||
}
|
||||
|
||||
void TileLoader::loadTilesAsync(QList<Tile> &list)
|
||||
{
|
||||
QList<Download> dl;
|
||||
|
@ -9,7 +9,8 @@ class TileLoader
|
||||
{
|
||||
public:
|
||||
TileLoader() {}
|
||||
TileLoader(const QString &url, const QString &dir);
|
||||
TileLoader(const QString &url, const QString &dir)
|
||||
: _url(url), _dir(dir) {}
|
||||
|
||||
void loadTilesAsync(QList<Tile> &list);
|
||||
void loadTilesSync(QList<Tile> &list);
|
||||
|
@ -194,6 +194,7 @@ void WMTS::layer(QXmlStreamReader &reader, const QString &layer,
|
||||
{
|
||||
QString id;
|
||||
RectC bounds;
|
||||
QString tpl;
|
||||
|
||||
while (reader.readNextStartElement()) {
|
||||
if (reader.name() == "Identifier")
|
||||
@ -202,12 +203,19 @@ void WMTS::layer(QXmlStreamReader &reader, const QString &layer,
|
||||
tileMatrixSetLink(reader, set);
|
||||
else if (reader.name() == "WGS84BoundingBox")
|
||||
bounds = wgs84BoundingBox(reader);
|
||||
else
|
||||
else if (reader.name() == "ResourceURL") {
|
||||
const QXmlStreamAttributes &attr = reader.attributes();
|
||||
if (attr.value("resourceType") == "tile")
|
||||
tpl = attr.value("template").toString();
|
||||
reader.skipCurrentElement();
|
||||
} else
|
||||
reader.skipCurrentElement();
|
||||
}
|
||||
|
||||
if (id == layer)
|
||||
if (id == layer) {
|
||||
_bounds = bounds;
|
||||
_tileUrl = tpl;
|
||||
}
|
||||
}
|
||||
|
||||
void WMTS::contents(QXmlStreamReader &reader, const QString &layer,
|
||||
@ -264,9 +272,7 @@ bool WMTS::getCapabilities(const QString &url, const QString &file)
|
||||
{
|
||||
QList<Download> dl;
|
||||
|
||||
QString capabilitiesUrl = QString("%1?service=WMTS&Version=1.0.0"
|
||||
"&request=GetCapabilities").arg(url);
|
||||
dl.append(Download(capabilitiesUrl, file));
|
||||
dl.append(Download(url, file));
|
||||
|
||||
QEventLoop wait;
|
||||
QObject::connect(_downloader, SIGNAL(finished()), &wait, SLOT(quit()));
|
||||
@ -281,17 +287,31 @@ bool WMTS::getCapabilities(const QString &url, const QString &file)
|
||||
}
|
||||
}
|
||||
|
||||
bool WMTS::load(const QString &file, const QString &url, const QString &layer,
|
||||
const QString &set)
|
||||
bool WMTS::load(const QString &file, const WMTS::Setup &setup)
|
||||
{
|
||||
QMap<QString, Zoom>::const_iterator it;
|
||||
QString capaUrl = setup.rest ? setup.url :
|
||||
QString("%1?service=WMTS&Version=1.0.0&request=GetCapabilities")
|
||||
.arg(setup.url);
|
||||
|
||||
if (!QFileInfo(file).exists())
|
||||
if (!getCapabilities(url, file))
|
||||
if (!getCapabilities(capaUrl, file))
|
||||
return false;
|
||||
if (!parseCapabilities(file, layer, set))
|
||||
if (!parseCapabilities(file, setup.layer, setup.set))
|
||||
return false;
|
||||
|
||||
if (!setup.rest)
|
||||
_tileUrl = QString("%1?service=WMTS&Version=1.0.0&request=GetTile"
|
||||
"&Format=%2&Layer=%3&Style=%4&TileMatrixSet=%5&TileMatrix=$z"
|
||||
"&TileRow=$y&TileCol=$x").arg(setup.url).arg(setup.format)
|
||||
.arg(setup.layer).arg(setup.style).arg(setup.set);
|
||||
else {
|
||||
_tileUrl.replace("{Style}", setup.style);
|
||||
_tileUrl.replace("{TileMatrixSet}", setup.set);
|
||||
_tileUrl.replace("{TileMatrix}", "$z");
|
||||
_tileUrl.replace("{TileRow}", "$y");
|
||||
_tileUrl.replace("{TileCol}", "$x");
|
||||
}
|
||||
|
||||
if (_matrixes.isEmpty()) {
|
||||
_errorString = "No usable tile matrix found";
|
||||
return false;
|
||||
@ -300,6 +320,10 @@ bool WMTS::load(const QString &file, const QString &url, const QString &layer,
|
||||
_errorString = "Missing CRS definition";
|
||||
return false;
|
||||
}
|
||||
if (_tileUrl.isNull()) {
|
||||
_errorString = "Missing tile URL";
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
@ -325,6 +349,14 @@ QList<WMTS::Zoom> WMTS::zooms() const
|
||||
}
|
||||
|
||||
#ifndef QT_NO_DEBUG
|
||||
QDebug operator<<(QDebug dbg, const WMTS::Setup &setup)
|
||||
{
|
||||
dbg.nospace() << "Setup(" << setup.url << ", " << setup.layer << ", "
|
||||
<< setup.set << ", " << setup.style << ", " << setup.format << ", "
|
||||
<< setup.rest << ")";
|
||||
return dbg.space();
|
||||
}
|
||||
|
||||
QDebug operator<<(QDebug dbg, const WMTS::Zoom &zoom)
|
||||
{
|
||||
dbg.nospace() << "Zoom(" << zoom.id << ", " << zoom.scaleDenominator << ", "
|
||||
|
@ -15,6 +15,20 @@ class Downloader;
|
||||
class WMTS
|
||||
{
|
||||
public:
|
||||
struct Setup {
|
||||
QString url;
|
||||
QString layer;
|
||||
QString set;
|
||||
QString style;
|
||||
QString format;
|
||||
bool rest;
|
||||
|
||||
Setup(const QString &url, const QString &layer, const QString &set,
|
||||
const QString &style, const QString &format, bool rest) :
|
||||
url(url), layer(layer), set(set), style(style), format(format),
|
||||
rest(rest) {}
|
||||
};
|
||||
|
||||
struct Zoom {
|
||||
QString id;
|
||||
qreal scaleDenominator;
|
||||
@ -32,13 +46,13 @@ public:
|
||||
{return scaleDenominator > other.scaleDenominator;}
|
||||
};
|
||||
|
||||
bool load(const QString &path, const QString &url, const QString &layer,
|
||||
const QString &set);
|
||||
bool load(const QString &path, const Setup &setup);
|
||||
const QString &errorString() const {return _errorString;}
|
||||
|
||||
const RectC &bounds() const {return _bounds;}
|
||||
QList<Zoom> zooms() const;
|
||||
const Projection &projection() const {return _projection;}
|
||||
QString tileUrl() const {return _tileUrl;}
|
||||
|
||||
static Downloader *downloader() {return _downloader;}
|
||||
static void setDownloader(Downloader *downloader)
|
||||
@ -94,6 +108,7 @@ private:
|
||||
QSet<MatrixLimits> _limits;
|
||||
RectC _bounds;
|
||||
Projection _projection;
|
||||
QString _tileUrl;
|
||||
|
||||
QString _errorString;
|
||||
|
||||
@ -114,6 +129,7 @@ inline uint qHash(const WMTS::MatrixLimits &key)
|
||||
}
|
||||
|
||||
#ifndef QT_NO_DEBUG
|
||||
QDebug operator<<(QDebug dbg, const WMTS::Setup &setup);
|
||||
QDebug operator<<(QDebug dbg, const WMTS::Zoom &zoom);
|
||||
#endif // QT_NO_DEBUG
|
||||
|
||||
|
@ -9,30 +9,27 @@
|
||||
|
||||
#define CAPABILITIES_FILE "capabilities.xml"
|
||||
|
||||
WMTSMap::WMTSMap(const QString &name, const QString &url, const QString &format,
|
||||
const QString &layer, const QString &style, const QString &set,
|
||||
bool invertAxis, QObject *parent) :
|
||||
Map(parent), _name(name), _url(url), _layer(layer), _set(set),
|
||||
_invertAxis(invertAxis), _zoom(0), _valid(false)
|
||||
WMTSMap::WMTSMap(const QString &name, const WMTS::Setup &setup, bool invertAxis,
|
||||
QObject *parent) : Map(parent), _name(name), _setup(setup),
|
||||
_invertAxis(invertAxis), _zoom(0), _valid(false)
|
||||
{
|
||||
QString dir(TILES_DIR + "/" + _name);
|
||||
QString file = dir + "/" + CAPABILITIES_FILE;
|
||||
|
||||
QString tileUrl = QString("%1?service=WMTS&Version=1.0.0&request=GetTile"
|
||||
"&Format=%2&Layer=%3&Style=%4&TileMatrixSet=%5&TileMatrix=$z&TileRow=$y"
|
||||
"&TileCol=$x").arg(_url).arg(format).arg(layer).arg(style)
|
||||
.arg(_set);
|
||||
_tileLoader = TileLoader(tileUrl, dir);
|
||||
if (!QDir().mkpath(dir)) {
|
||||
_errorString = "Error creating tiles dir";
|
||||
return;
|
||||
}
|
||||
|
||||
WMTS wmts;
|
||||
if (!wmts.load(file, _url, _layer, _set)) {
|
||||
if (!wmts.load(file, _setup)) {
|
||||
_errorString = wmts.errorString();
|
||||
return;
|
||||
}
|
||||
_bounds = wmts.bounds();
|
||||
_zooms = wmts.zooms();
|
||||
_projection = wmts.projection();
|
||||
|
||||
_tileLoader = TileLoader(wmts.tileUrl(), dir);
|
||||
updateTransform();
|
||||
|
||||
_block = false;
|
||||
@ -91,10 +88,12 @@ void WMTSMap::clearCache()
|
||||
_tileLoader.clearCache();
|
||||
|
||||
WMTS wmts;
|
||||
if (!wmts.load(file, _url, _layer, _set))
|
||||
if (!wmts.load(file, _setup))
|
||||
return;
|
||||
_bounds = wmts.bounds();
|
||||
_zooms = wmts.zooms();
|
||||
_projection = wmts.projection();
|
||||
_tileLoader = TileLoader(wmts.tileUrl(), dir);
|
||||
|
||||
if (_zoom >= _zooms.size())
|
||||
_zoom = _zooms.size() - 1;
|
||||
|
@ -13,9 +13,8 @@ class WMTSMap : public Map
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
WMTSMap(const QString &name, const QString &url, const QString &format,
|
||||
const QString &layer, const QString &style, const QString &set,
|
||||
bool invertAxis, QObject *parent = 0);
|
||||
WMTSMap(const QString &name, const WMTS::Setup &setup, bool invertAxis,
|
||||
QObject *parent = 0);
|
||||
|
||||
const QString &name() const {return _name;}
|
||||
|
||||
@ -54,7 +53,8 @@ private:
|
||||
QPointF ll2xy(const Coordinates &c) const;
|
||||
Coordinates xy2ll(const QPointF &p) const;
|
||||
|
||||
QString _name, _url, _layer, _set;
|
||||
QString _name;
|
||||
WMTS::Setup _setup;
|
||||
TileLoader _tileLoader;
|
||||
RectC _bounds;
|
||||
QList<WMTS::Zoom> _zooms;
|
||||
|
Loading…
Reference in New Issue
Block a user