summaryrefslogtreecommitdiff
path: root/platform/qt/src
diff options
context:
space:
mode:
authorThiago Marcos P. Santos <thiago@mapbox.com>2015-07-22 14:12:34 +0300
committerThiago Marcos P. Santos <thiago@mapbox.com>2016-04-20 20:55:51 +0300
commit854b3bc39b2a84656ca2c120865bf926d7a4b47d (patch)
treebe6f82db23adf0a00d3b22c2332ecc79eeb7b72b /platform/qt/src
parenta0146e372fe2a44d7eebe7bad9c1f65e18eac785 (diff)
downloadqtlocation-mapboxgl-854b3bc39b2a84656ca2c120865bf926d7a4b47d.tar.gz
[Qt] Add a Qt wrapper aroung mbgl::Map
Signed-off-by: Bruno Abinader <bruno@mapbox.com> Signed-off-by: Thiago Marcos P. Santos <thiago@mapbox.com>
Diffstat (limited to 'platform/qt/src')
-rw-r--r--platform/qt/src/qmapboxgl.cpp314
-rw-r--r--platform/qt/src/qmapboxgl_p.hpp50
2 files changed, 364 insertions, 0 deletions
diff --git a/platform/qt/src/qmapboxgl.cpp b/platform/qt/src/qmapboxgl.cpp
new file mode 100644
index 0000000000..e648354e54
--- /dev/null
+++ b/platform/qt/src/qmapboxgl.cpp
@@ -0,0 +1,314 @@
+#include "qmapboxgl_p.hpp"
+
+#include <mbgl/annotation/point_annotation.hpp>
+#include <mbgl/gl/gl.hpp>
+#include <mbgl/map/map.hpp>
+#include <mbgl/sprite/sprite_image.hpp>
+#include <mbgl/util/geo.hpp>
+#include <mbgl/util/vec.hpp>
+
+#include <QCoreApplication>
+#include <QImage>
+#include <QMapboxGL>
+#include <QString>
+
+#include <memory>
+
+QMapboxGLSettings::QMapboxGLSettings()
+ : m_cacheMaximumSize(mbgl::util::DEFAULT_MAX_CACHE_SIZE)
+ , m_cacheDatabasePath(":memory:")
+ , m_assetPath(QCoreApplication::applicationDirPath())
+{
+}
+
+unsigned QMapboxGLSettings::cacheDatabaseMaximumSize() const
+{
+ return m_cacheMaximumSize;
+}
+
+void QMapboxGLSettings::setCacheDatabaseMaximumSize(unsigned size)
+{
+ m_cacheMaximumSize = size;
+}
+
+QString QMapboxGLSettings::cacheDatabasePath() const
+{
+ return m_cacheDatabasePath;
+}
+
+void QMapboxGLSettings::setCacheDatabasePath(const QString &path)
+{
+ m_cacheDatabasePath = path;
+}
+
+QString QMapboxGLSettings::assetPath() const
+{
+ return m_assetPath;
+}
+
+void QMapboxGLSettings::setAssetPath(const QString &path)
+{
+ m_assetPath = path;
+}
+
+QString QMapboxGLSettings::accessToken() const {
+ return m_accessToken;
+}
+
+void QMapboxGLSettings::setAccessToken(const QString &token)
+{
+ m_accessToken = token;
+}
+
+QMapboxGL::QMapboxGL(QObject *parent_, const QMapboxGLSettings &settings)
+ : QObject(parent_)
+ , d_ptr(new QMapboxGLPrivate(this, settings))
+{
+ d_ptr->fileSourceObj->setAccessToken(settings.accessToken().toStdString());
+
+ d_ptr->mapObj = std::make_unique<mbgl::Map>(*d_ptr, *d_ptr->fileSourceObj,
+ mbgl::MapMode::Continuous, mbgl::GLContextMode::Shared);
+}
+
+QMapboxGL::~QMapboxGL()
+{
+ delete d_ptr;
+}
+
+void QMapboxGL::setStyleJSON(const QString &style)
+{
+ d_ptr->mapObj->setStyleJSON(style.toUtf8().constData());
+}
+
+void QMapboxGL::setStyleURL(const QString &url)
+{
+ d_ptr->mapObj->setStyleURL(url.toUtf8().constData());
+}
+
+double QMapboxGL::latitude() const
+{
+ return d_ptr->mapObj->getLatLng().latitude;
+}
+
+void QMapboxGL::setLatitude(double latitude_)
+{
+ d_ptr->mapObj->setLatLng(mbgl::LatLng { latitude_, longitude() });
+}
+
+double QMapboxGL::longitude() const
+{
+ return d_ptr->mapObj->getLatLng().longitude;
+}
+
+void QMapboxGL::setLongitude(double longitude_)
+{
+ d_ptr->mapObj->setLatLng(mbgl::LatLng { latitude(), longitude_ });
+}
+
+double QMapboxGL::zoom() const
+{
+ return d_ptr->mapObj->getZoom();
+}
+
+void QMapboxGL::setZoom(double zoom_, int milliseconds)
+{
+ d_ptr->mapObj->setZoom(zoom_, std::chrono::milliseconds(milliseconds));
+}
+
+double QMapboxGL::minimumZoom() const
+{
+ return d_ptr->mapObj->getMinZoom();
+}
+
+double QMapboxGL::maximumZoom() const
+{
+ return d_ptr->mapObj->getMaxZoom();
+}
+
+QMapboxGL::Coordinate QMapboxGL::coordinate() const
+{
+ const mbgl::LatLng& latLng = d_ptr->mapObj->getLatLng();
+ return Coordinate(latLng.latitude, latLng.longitude);
+}
+
+void QMapboxGL::setCoordinate(const Coordinate &coordinate_, int milliseconds)
+{
+ d_ptr->mapObj->setLatLng(
+ mbgl::LatLng { coordinate_.first, coordinate_.second },
+ std::chrono::milliseconds(milliseconds));
+}
+
+void QMapboxGL::setCoordinateZoom(const Coordinate &coordinate_, double zoom_, int milliseconds)
+{
+ d_ptr->mapObj->setLatLngZoom(
+ mbgl::LatLng { coordinate_.first, coordinate_.second }, zoom_,
+ std::chrono::milliseconds(milliseconds));
+}
+
+double QMapboxGL::bearing() const
+{
+ return d_ptr->mapObj->getBearing();
+}
+
+void QMapboxGL::setBearing(double degrees, int milliseconds)
+{
+ d_ptr->mapObj->setBearing(degrees, std::chrono::milliseconds(milliseconds));
+}
+
+void QMapboxGL::setBearing(double degrees, const QPointF &center)
+{
+ d_ptr->mapObj->setBearing(degrees, mbgl::ScreenCoordinate { center.x(), center.y() });
+}
+
+double QMapboxGL::pitch() const
+{
+ return d_ptr->mapObj->getPitch();
+}
+
+void QMapboxGL::setPitch(double pitch_, int milliseconds)
+{
+ d_ptr->mapObj->setPitch(pitch_, std::chrono::milliseconds(milliseconds));
+}
+
+void QMapboxGL::setGestureInProgress(bool inProgress)
+{
+ d_ptr->mapObj->setGestureInProgress(inProgress);
+}
+
+bool QMapboxGL::isRotating() const
+{
+ return d_ptr->mapObj->isRotating();
+}
+
+bool QMapboxGL::isScaling() const
+{
+ return d_ptr->mapObj->isScaling();
+}
+
+bool QMapboxGL::isPanning() const
+{
+ return d_ptr->mapObj->isPanning();
+}
+
+bool QMapboxGL::isFullyLoaded() const
+{
+ return d_ptr->mapObj->isFullyLoaded();
+}
+
+void QMapboxGL::moveBy(const QPointF &offset)
+{
+ d_ptr->mapObj->moveBy(mbgl::ScreenCoordinate { offset.x(), offset.y() });
+}
+
+void QMapboxGL::scaleBy(double scale_, const QPointF &center, int milliseconds) {
+ d_ptr->mapObj->scaleBy(
+ scale_, mbgl::ScreenCoordinate { center.x(), center.y() },
+ std::chrono::milliseconds(milliseconds));
+}
+
+void QMapboxGL::rotateBy(const QPointF &first, const QPointF &second)
+{
+ d_ptr->mapObj->rotateBy(
+ mbgl::ScreenCoordinate { first.x(), first.y() },
+ mbgl::ScreenCoordinate { second.x(), second.y() });
+}
+
+void QMapboxGL::resize(const QSize& size)
+{
+ if (d_ptr->size == size) return;
+
+ d_ptr->size = size;
+ d_ptr->mapObj->update(mbgl::Update::Dimensions);
+}
+
+void QMapboxGL::addAnnotationIcon(const QString &name, const QImage &sprite)
+{
+ if (sprite.isNull()) return;
+
+ const QImage swapped = sprite
+ .rgbSwapped()
+ .convertToFormat(QImage::Format_ARGB32_Premultiplied);
+
+ auto img = std::make_unique<uint8_t[]>(swapped.byteCount());
+ memcpy(img.get(), swapped.constBits(), swapped.byteCount());
+
+ d_ptr->mapObj->addAnnotationIcon(name.toStdString(), std::make_shared<mbgl::SpriteImage>(
+ mbgl::PremultipliedImage { size_t(swapped.width()), size_t(swapped.height()), std::move(img) }, 1.0));
+}
+
+QPointF QMapboxGL::pixelForCoordinate(const Coordinate &coordinate_) const
+{
+ const mbgl::vec2<double> pixel =
+ d_ptr->mapObj->pixelForLatLng(mbgl::LatLng { coordinate_.first, coordinate_.second });
+
+ return QPointF(pixel.x, pixel.y);
+}
+
+QMapboxGL::Coordinate QMapboxGL::coordinateForPixel(const QPointF &pixel) const
+{
+ const mbgl::LatLng latLng =
+ d_ptr->mapObj->latLngForPixel(mbgl::ScreenCoordinate { pixel.x(), pixel.y() });
+
+ return Coordinate(latLng.latitude, latLng.longitude);
+}
+
+void QMapboxGL::render()
+{
+ d_ptr->mapObj->render();
+}
+
+QMapboxGLPrivate::QMapboxGLPrivate(QMapboxGL *q, const QMapboxGLSettings &settings)
+ : QObject(q)
+ , size(0, 0)
+ , q_ptr(q)
+ , fileSourceObj(std::make_unique<mbgl::DefaultFileSource>(
+ settings.cacheDatabasePath().toStdString(),
+ settings.assetPath().toStdString(),
+ settings.cacheDatabaseMaximumSize()))
+ , mapObj(std::make_unique<mbgl::Map>(
+ *this, *fileSourceObj,
+ mbgl::MapMode::Continuous,
+ mbgl::GLContextMode::Shared))
+{
+ connect(this, SIGNAL(needsRendering()), q_ptr, SIGNAL(needsRendering()));
+ connect(this, SIGNAL(mapRegionDidChange()), q_ptr, SIGNAL(mapRegionDidChange()));
+}
+
+QMapboxGLPrivate::~QMapboxGLPrivate()
+{
+}
+
+float QMapboxGLPrivate::getPixelRatio() const
+{
+ // FIXME: Should handle pixel ratio.
+ return 1.0;
+}
+
+std::array<uint16_t, 2> QMapboxGLPrivate::getSize() const
+{
+ return {{ static_cast<uint16_t>(size.width()), static_cast<uint16_t>(size.height()) }};
+}
+
+std::array<uint16_t, 2> QMapboxGLPrivate::getFramebufferSize() const
+{
+ return getSize();
+}
+
+void QMapboxGLPrivate::invalidate()
+{
+ emit needsRendering();
+}
+
+void QMapboxGLPrivate::notifyMapChange(mbgl::MapChange change)
+{
+ // Map thread.
+ switch (change) {
+ case mbgl::MapChangeRegionDidChange:
+ case mbgl::MapChangeRegionDidChangeAnimated:
+ case mbgl::MapChangeRegionIsChanging:
+ emit mapRegionDidChange();
+ break;
+ default:
+ break;
+ }
+}
diff --git a/platform/qt/src/qmapboxgl_p.hpp b/platform/qt/src/qmapboxgl_p.hpp
new file mode 100644
index 0000000000..4b2b5b5252
--- /dev/null
+++ b/platform/qt/src/qmapboxgl_p.hpp
@@ -0,0 +1,50 @@
+#ifndef QMAPBOXGL_P_H
+#define QMAPBOXGL_P_H
+
+#include <mbgl/map/map.hpp>
+#include <mbgl/map/view.hpp>
+#include <mbgl/storage/default_file_source.hpp>
+#include <mbgl/util/run_loop.hpp>
+
+#include <QMapboxGL>
+#include <QObject>
+#include <QSize>
+
+#include <memory>
+
+class QMapboxGL;
+class QMapboxGLSettings;
+
+class QMapboxGLPrivate : public QObject, public mbgl::View
+{
+ Q_OBJECT
+
+public:
+ explicit QMapboxGLPrivate(QMapboxGL *q, const QMapboxGLSettings &);
+ virtual ~QMapboxGLPrivate();
+
+ // mbgl::View implementation.
+ float getPixelRatio() const final;
+ std::array<uint16_t, 2> getSize() const final;
+ std::array<uint16_t, 2> getFramebufferSize() const final;
+
+ void activate() final {}
+ void deactivate() final {}
+ void invalidate() final;
+ void notifyMapChange(mbgl::MapChange change) final;
+
+ QSize size;
+
+ QMapboxGL *q_ptr = nullptr;
+
+ mbgl::util::RunLoop loop;
+
+ std::unique_ptr<mbgl::DefaultFileSource> fileSourceObj;
+ std::unique_ptr<mbgl::Map> mapObj;
+
+signals:
+ void mapRegionDidChange();
+ void needsRendering();
+};
+
+#endif // QMAPBOXGL_P_H