1/****************************************************************************
2**
3** Copyright (C) 2016 Vlad Seryakov <vseryakov@gmail.com>
4** Copyright (C) 2016 Aaron McCarthy <mccarthy.aaron@gmail.com>
5** Contact: https://www.qt.io/licensing/
6**
7** This file is part of the QtLocation module of the Qt Toolkit.
8**
9** $QT_BEGIN_LICENSE:LGPL$
10** Commercial License Usage
11** Licensees holding valid commercial Qt licenses may use this file in
12** accordance with the commercial license agreement provided with the
13** Software or, alternatively, in accordance with the terms contained in
14** a written agreement between you and The Qt Company. For licensing terms
15** and conditions see https://www.qt.io/terms-conditions. For further
16** information use the contact form at https://www.qt.io/contact-us.
17**
18** GNU Lesser General Public License Usage
19** Alternatively, this file may be used under the terms of the GNU Lesser
20** General Public License version 3 as published by the Free Software
21** Foundation and appearing in the file LICENSE.LGPL3 included in the
22** packaging of this file. Please review the following information to
23** ensure the GNU Lesser General Public License version 3 requirements
24** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
25**
26** GNU General Public License Usage
27** Alternatively, this file may be used under the terms of the GNU
28** General Public License version 2.0 or (at your option) the GNU General
29** Public license version 3 or any later version approved by the KDE Free
30** Qt Foundation. The licenses are as published by the Free Software
31** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
32** included in the packaging of this file. Please review the following
33** information to ensure the GNU General Public License requirements will
34** be met: https://www.gnu.org/licenses/gpl-2.0.html and
35** https://www.gnu.org/licenses/gpl-3.0.html.
36**
37** $QT_END_LICENSE$
38**
39****************************************************************************/
40
41#include "qgeoroutereplymapbox.h"
42#include "qgeoroutingmanagerenginemapbox.h"
43#include <QtLocation/private/qgeorouteparser_p.h>
44#include <QtLocation/private/qgeoroute_p.h>
45#include <QtCore/QJsonDocument>
46#include <QtCore/QJsonObject>
47#include <QtCore/QJsonArray>
48#include <QtLocation/QGeoRouteSegment>
49#include <QtLocation/QGeoManeuver>
50
51namespace {
52
53class QGeoRouteMapbox : public QGeoRoute
54{
55public:
56 QGeoRouteMapbox(const QGeoRoute &other, const QVariantMap &metadata);
57};
58
59class QGeoRoutePrivateMapbox : public QGeoRoutePrivateDefault
60{
61public:
62 QGeoRoutePrivateMapbox(const QGeoRoutePrivateDefault &other, const QVariantMap &metadata);
63
64 virtual QString engineName() const override;
65 virtual QVariantMap metadata() const override;
66
67 QVariantMap m_metadata;
68};
69
70QGeoRouteMapbox::QGeoRouteMapbox(const QGeoRoute &other, const QVariantMap &metadata)
71 : QGeoRoute(QExplicitlySharedDataPointer<QGeoRoutePrivateMapbox>(new QGeoRoutePrivateMapbox(*static_cast<const QGeoRoutePrivateDefault *>(QGeoRoutePrivate::routePrivateData(route: other)), metadata)))
72{
73}
74
75QGeoRoutePrivateMapbox::QGeoRoutePrivateMapbox(const QGeoRoutePrivateDefault &other, const QVariantMap &metadata)
76 : QGeoRoutePrivateDefault(other)
77 , m_metadata(metadata)
78{
79}
80
81QString QGeoRoutePrivateMapbox::engineName() const
82{
83 return QStringLiteral("mapbox");
84}
85
86QVariantMap QGeoRoutePrivateMapbox::metadata() const
87{
88 return m_metadata;
89}
90
91} // namespace
92
93QT_BEGIN_NAMESPACE
94
95QGeoRouteReplyMapbox::QGeoRouteReplyMapbox(QNetworkReply *reply, const QGeoRouteRequest &request,
96 QObject *parent)
97: QGeoRouteReply(request, parent)
98{
99 if (!reply) {
100 setError(error: UnknownError, QStringLiteral("Null reply"));
101 return;
102 }
103 connect(sender: reply, SIGNAL(finished()), receiver: this, SLOT(networkReplyFinished()));
104 connect(sender: reply, SIGNAL(errorOccurred(QNetworkReply::NetworkError)),
105 receiver: this, SLOT(networkReplyError(QNetworkReply::NetworkError)));
106 connect(sender: this, signal: &QGeoRouteReply::aborted, receiver: reply, slot: &QNetworkReply::abort);
107 connect(sender: this, signal: &QObject::destroyed, receiver: reply, slot: &QObject::deleteLater);
108}
109
110QGeoRouteReplyMapbox::~QGeoRouteReplyMapbox()
111{
112}
113
114void QGeoRouteReplyMapbox::networkReplyFinished()
115{
116 QNetworkReply *reply = static_cast<QNetworkReply *>(sender());
117 reply->deleteLater();
118
119 if (reply->error() != QNetworkReply::NoError)
120 return;
121
122 QGeoRoutingManagerEngineMapbox *engine = qobject_cast<QGeoRoutingManagerEngineMapbox *>(object: parent());
123 const QGeoRouteParser *parser = engine->routeParser();
124
125 QList<QGeoRoute> routes;
126 QString errorString;
127
128 QByteArray routeReply = reply->readAll();
129 QGeoRouteReply::Error error = parser->parseReply(routes, errorString, reply: routeReply);
130 // Setting the request into the result
131 for (QGeoRoute &route : routes) {
132 route.setRequest(request());
133 for (QGeoRoute &leg: route.routeLegs()) {
134 leg.setRequest(request());
135 }
136 }
137
138 QVariantMap metadata;
139 metadata["osrm.reply-json"] = routeReply;
140
141 QList<QGeoRoute> mapboxRoutes;
142 for (const QGeoRoute &route : routes.mid(pos: 0, alength: request().numberAlternativeRoutes() + 1)) {
143 QGeoRouteMapbox mapboxRoute(route, metadata);
144 mapboxRoutes.append(t: mapboxRoute);
145 }
146
147 if (error == QGeoRouteReply::NoError) {
148 setRoutes(mapboxRoutes);
149 // setError(QGeoRouteReply::NoError, status); // can't do this, or NoError is emitted and does damages
150 setFinished(true);
151 } else {
152 setError(error, errorString);
153 }
154}
155
156void QGeoRouteReplyMapbox::networkReplyError(QNetworkReply::NetworkError error)
157{
158 Q_UNUSED(error);
159 QNetworkReply *reply = static_cast<QNetworkReply *>(sender());
160 reply->deleteLater();
161 setError(error: QGeoRouteReply::CommunicationError, errorString: reply->errorString());
162}
163
164QT_END_NAMESPACE
165

source code of qtlocation/src/plugins/geoservices/mapbox/qgeoroutereplymapbox.cpp