diff options
author | Paolo Angelelli <paolo.angelelli@theqtcompany.com> | 2016-07-11 14:27:34 +0200 |
---|---|---|
committer | Alex Blasche <alexander.blasche@theqtcompany.com> | 2016-07-27 05:36:25 +0000 |
commit | 04762a9eecafc80ebeb90c06258de551d451497f (patch) | |
tree | 1ac1ff2d6ea9f9fb448fee41aca0f2a30a50eea1 /src/plugins/geoservices/osm/qgeotileproviderosm.h | |
parent | 5adda3e6651f3d45838ece962a4ae656eac5af04 (diff) |
Add indirection for osm providers
To prevent furter breakage of qtlocation osm provider
in existing qt versions, this patch introduces one
level of indirection in resolving OSM providers, fetching
the tile server address from files hosted at
http://maps-redirect.qt.io/osm/5.6/
The content of the files requested for the server
address resolution must be in JSON format, containing
(currently) the following fields:
{
"Enabled" : bool, (optional)
"UrlTemplate" : "<url template>", (mandatory)
"ImageFormat" : "<image format>", (mandatory)
"MapCopyRight" : "<copyright>", (mandatory)
"DataCopyRight" : "<copyright>", (mandatory)
"MinimumZoomLevel" : <minimumZoomLevel>, (optional)
"MaximumZoomLevel" : <maximumZoomLevel>, (optional)
}
Enabled is optional, and allows us to temporarily disable
tile providers if they go offline without firing requests
to them. Default is true.
MinimumZoomLevel and MaximumZoomLevel are also optional,
and allow us to prevent tile requests to the providers,
if they do not support the specific ZL. Default is 0 and
19, respectively.
<server address template> is required, and is the tile
url template, with %x, %y and %z as placeholders for the
actual parameters.
Example:
http://localhost:8080/maps/%z/%x/%y.png
<image format> is required, and is the format of the tile.
Example:
"png" or "jpg"
<MapCopyRight> is required and is the string that will be
displayed in the "Map (c)" part of the on-screen copyright
notice.
example:
"<a href='http://www.mapquest.com/'>MapQuest</a>"
<DataCopyRight> is required and is the string that will be
displayed in the "Data (c)" part of the on-screen copyright
notice.
example:
"a href=
'http://www.openstreetmap.org/copyright'>OpenStreetMap</a>
contributors"
The patch also adds four additional OSM plugin parameters,
modifies an existing ones, and removes another existing one.
Removed:
- osm.mapping.copyright, now removed and replaced by two
other parameters (see below).
New:
- osm.mapping.providersrepository.address, allowing to change
the hardcoded http://maps-redirect.qt.io/osm/5.6/
The implication of this parameter is that it becomes possible
to use file:// urls or even qrc:, allowing to ship custom
providers with the applicarions
- osm.mapping.providersrepository.disabled, allowing to disable
the indirection and go with hardcoded URLs by default.
- osm.mapping.custom.mapcopyright replaces the old
osm.mapping.copyright, and contains the copyright notice to be
displayed next to the "Map (c)" part of the copyright, to be
consistent with the way the copyright notice coming from the
provider data is handled
- osm.mapping.custom.datacopyright replaces the old
osm.mapping.copyright, and contains the copyright notice to be
displayed next to the "Data (c)" part of the copyright, to be
consistent with the way the copyright notice coming from the
provider data is handled
Modified:
- osm.mapping.host now became osm.mapping.custom.host,
improving the naming consistency.
Task-number: QTBUG-54599
Change-Id: Iee88883572a198c00bcf54cf2bc33fbcc0498a68
Reviewed-by: Alex Blasche <alexander.blasche@theqtcompany.com>
Diffstat (limited to 'src/plugins/geoservices/osm/qgeotileproviderosm.h')
-rw-r--r-- | src/plugins/geoservices/osm/qgeotileproviderosm.h | 256 |
1 files changed, 256 insertions, 0 deletions
diff --git a/src/plugins/geoservices/osm/qgeotileproviderosm.h b/src/plugins/geoservices/osm/qgeotileproviderosm.h new file mode 100644 index 00000000..cdff7997 --- /dev/null +++ b/src/plugins/geoservices/osm/qgeotileproviderosm.h @@ -0,0 +1,256 @@ +/**************************************************************************** +** +** Copyright (C) 2016 The Qt Company Ltd. +** Contact: http://www.qt.io/licensing/ +** +** This file is part of the QtLocation module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL3$ +** Commercial License Usage +** Licensees holding valid commercial Qt licenses may use this file in +** accordance with the commercial license agreement provided with the +** Software or, alternatively, in accordance with the terms contained in +** a written agreement between you and The Qt Company. For licensing terms +** and conditions see http://www.qt.io/terms-conditions. For further +** information use the contact form at http://www.qt.io/contact-us. +** +** GNU Lesser General Public License Usage +** Alternatively, this file may be used under the terms of the GNU Lesser +** General Public License version 3 as published by the Free Software +** Foundation and appearing in the file LICENSE.LGPLv3 included in the +** packaging of this file. Please review the following information to +** ensure the GNU Lesser General Public License version 3 requirements +** will be met: https://www.gnu.org/licenses/lgpl.html. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU +** General Public License version 2.0 or later as published by the Free +** Software Foundation and appearing in the file LICENSE.GPL included in +** the packaging of this file. Please review the following information to +** ensure the GNU General Public License version 2.0 requirements will be +** met: http://www.gnu.org/licenses/gpl-2.0.html. +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#ifndef QTILEPROVIDEROSM_H +#define QTILEPROVIDEROSM_H + +#include <QtLocation/private/qgeomaptype_p.h> + +#include <QtCore/QUrl> +#include <QtNetwork/QNetworkAccessManager> +#include <QtNetwork/QNetworkReply> +#include <QtCore/QPointer> +#include <QTimer> +#include <algorithm> + +QT_BEGIN_NAMESPACE + +class QGeoTileProviderOsm: public QObject +{ + Q_OBJECT + + friend class QGeoTileFetcherOsm; + friend class QGeoMapReplyOsm; + friend class QGeoTiledMappingManagerEngineOsm; +public: + struct TileProvider { + + static inline void sort2(int &a, int &b) + { + if (a > b) { + int temp=a; + a=b; + b=temp; + } + } + + TileProvider() : m_valid(false) + { + + } + + TileProvider(const QString &urlTemplate, + const QString &format, + const QString ©RightMap, + const QString ©RightData, + int minimumZoomLevel = 0, + int maximumZoomLevel = 19) : m_valid(false) + { + if (urlTemplate.isEmpty()) + return; + m_urlTemplate = urlTemplate; + + if (format.isEmpty()) + return; + m_format = format; + + m_copyRightMap = copyRightMap; + m_copyRightData = copyRightData; + + if (minimumZoomLevel < 0 || minimumZoomLevel > 30) + return; + m_minimumZoomLevel = minimumZoomLevel; + + if (maximumZoomLevel < 0 || maximumZoomLevel > 30 || maximumZoomLevel < minimumZoomLevel) + return; + m_maximumZoomLevel = maximumZoomLevel; + + // Currently supporting only %x, %y and &z + int offset[3]; + offset[0] = m_urlTemplate.indexOf(QLatin1String("%x")); + if (offset[0] < 0) + return; + + offset[1] = m_urlTemplate.indexOf(QLatin1String("%y")); + if (offset[1] < 0) + return; + + offset[2] = m_urlTemplate.indexOf(QLatin1String("%z")); + if (offset[2] < 0) + return; + + int sortedOffsets[3]; + std::copy(offset, offset + 4, sortedOffsets); + sort2(sortedOffsets[0] ,sortedOffsets[1]); + sort2(sortedOffsets[1] ,sortedOffsets[2]); + sort2(sortedOffsets[0] ,sortedOffsets[1]); + + int min = sortedOffsets[0]; + int max = sortedOffsets[2]; + int mid = sortedOffsets[1]; + + // Initing LUT + for (int i=0; i<3; i++) { + if (offset[0] == sortedOffsets[i]) + paramsLUT[i] = 0; + else if (offset[1] == sortedOffsets[i]) + paramsLUT[i] = 1; + else + paramsLUT[i] = 2; + } + + m_urlPrefix = m_urlTemplate.mid(0 , min); + m_urlSuffix = m_urlTemplate.mid(max + 2, m_urlTemplate.size() - max - 2); + + paramsSep[0] = m_urlTemplate.mid(min + 2, mid - min - 2); + paramsSep[1] = m_urlTemplate.mid(mid + 2, max - mid - 2); + m_valid = true; + } + + ~TileProvider() + { + } + + inline bool isValid() const + { + return m_valid; + } + + inline QString mapCopyRight() const + { + return m_copyRightMap; + } + + inline QString dataCopyRight() const + { + return m_copyRightData; + } + + inline QString styleCopyRight() const + { + return m_copyRightStyle; + } + + inline QString format() const + { + return m_format; + } + + // Optional properties, not needed to construct a provider + void setStyleCopyRight(const QString ©right) + { + m_copyRightStyle = copyright; + } + + QUrl tileAddress(int x, int y, int z) const + { + if (z < m_minimumZoomLevel || z > m_maximumZoomLevel) + return QUrl(); + int params[3] = { x, y, z}; + QString url; + url += m_urlPrefix; + url += QString::number(params[paramsLUT[0]]); + url += paramsSep[0]; + url += QString::number(params[paramsLUT[1]]); + url += paramsSep[1]; + url += QString::number(params[paramsLUT[2]]); + url += m_urlSuffix; + return QUrl(url); + } + + bool m_valid; + QString m_urlTemplate; + QString m_format; + QString m_copyRightMap; + QString m_copyRightData; + QString m_copyRightStyle; + QString m_urlPrefix; + QString m_urlSuffix; + int m_minimumZoomLevel; + int m_maximumZoomLevel; + + int paramsLUT[3]; //Lookup table to handle possibly shuffled x,y,z + QString paramsSep[2]; // what goes in between %x, %y and %z + }; + + enum Status {Idle, + Resolving, + Valid, + Invalid }; + + QGeoTileProviderOsm(const QString &urlRedir, + QNetworkAccessManager *nm, + const QGeoMapType &mapType, + const TileProvider &providerFallback); + + ~QGeoTileProviderOsm(); + + + + QUrl tileAddress(int x, int y, int z) const; + QString mapCopyRight() const; + QString dataCopyRight() const; + QString styleCopyRight() const; + QString format() const; + const QGeoMapType &mapType() const; + bool isValid() const; + bool isResolved() const; + +Q_SIGNALS: + void resolutionFinished(const QGeoTileProviderOsm *provider); + void resolutionError(const QGeoTileProviderOsm *provider, QNetworkReply::NetworkError error); + +public Q_SLOTS: + void onNetworkReplyFinished(); + void onNetworkReplyError(QNetworkReply::NetworkError error); + void resolveProvider(); + +protected: + void disableRedirection(); + void handleError(QNetworkReply::NetworkError error); + + QNetworkAccessManager *m_nm; + QUrl m_urlRedirector; // The URL from where to fetch the URL template + TileProvider m_provider; + TileProvider m_providerFallback; + QGeoMapType m_mapType; + Status m_status; + QTimer m_retryTimer; +}; + +QT_END_NAMESPACE + +#endif // QTILEPROVIDEROSM_H |