diff options
author | Thiago Marcos P. Santos <thiago@mapbox.com> | 2017-03-04 09:06:04 -0800 |
---|---|---|
committer | Thiago Marcos P. Santos <tmpsantos@gmail.com> | 2017-03-06 11:40:05 -0800 |
commit | 2b7319d529e2335b355eacf602dda12c9e01dd9b (patch) | |
tree | dfcb568d4b588fd749b33680c609af9869e541fe /platform/qt | |
parent | b5d0a661c520716c6345aca6ea0207f5d49b6d54 (diff) | |
download | qtlocation-mapboxgl-2b7319d529e2335b355eacf602dda12c9e01dd9b.tar.gz |
[Qt] Remove the QML app
We are now on Qt 5.9 and this is where the plugin will be developed
from now on.
Diffstat (limited to 'platform/qt')
-rw-r--r-- | platform/qt/README.md | 46 | ||||
-rw-r--r-- | platform/qt/bitrise-qt5.yml | 1 | ||||
-rw-r--r-- | platform/qt/include/qquickmapboxgl.hpp | 176 | ||||
-rw-r--r-- | platform/qt/include/qquickmapboxglmapparameter.hpp | 34 | ||||
-rw-r--r-- | platform/qt/qmlapp/main.cpp | 24 | ||||
-rw-r--r-- | platform/qt/qmlapp/main.qml | 347 | ||||
-rw-r--r-- | platform/qt/qmlapp/qml.qrc | 5 | ||||
-rw-r--r-- | platform/qt/qt5.cmake | 24 | ||||
-rw-r--r-- | platform/qt/src/qquickmapboxgl.cpp | 469 | ||||
-rw-r--r-- | platform/qt/src/qquickmapboxglmapparameter.cpp | 35 | ||||
-rw-r--r-- | platform/qt/src/qquickmapboxglrenderer.cpp | 120 | ||||
-rw-r--r-- | platform/qt/src/qquickmapboxglrenderer.hpp | 34 |
12 files changed, 3 insertions, 1312 deletions
diff --git a/platform/qt/README.md b/platform/qt/README.md index dc17d69903..22c06310c3 100644 --- a/platform/qt/README.md +++ b/platform/qt/README.md @@ -3,43 +3,10 @@ [![Travis](https://travis-ci.org/mapbox/mapbox-gl-native.svg?branch=master)](https://travis-ci.org/mapbox/mapbox-gl-native/builds) [![Bitrise](https://www.bitrise.io/app/96cfbc97e0245c22.svg?token=GxsqIOGPXhn0F23sSVSsYA&branch=master)](https://www.bitrise.io/app/96cfbc97e0245c22) -Provides [Qt](http://www.qt.io/) example applications and APIs via `QMapboxGL` -and `QQuickMapboxGL`: - -**QMapboxGL** - implements a C++03x-conformant API that has been tested from Qt -4.7 onwards (Travis CI currently builds it using both Qt 4 and Qt 5). - -**QQuickMapboxGL** - implements a Qt Quick (QML) item that can be added to a -scene. Because `QQuickFramebufferObject` has been added in Qt version 5.2, we -support this API from this version onwards. - -![Mapbox Qt QML -example](https://c2.staticflickr.com/8/7689/26247088394_01541b34de_o.png) - ### Developing -[Qt supports many platforms](https://www.qt.io/qt-framework/#section-4) - so far -we have been testing our code on Linux and macOS desktops, as well as embedded -devices such as Raspberry Pi 3. - -If you need to maintain backwards compatibility with prior releases of -Qt, chose `QMapboxGL`. Otherwise, go for `QQuickMapboxGL`. - -Both `QMapboxGL` and `QQuickMapboxGL` requires a [Mapbox access -token](https://www.mapbox.com/help/define-access-token/) at runtime - you need -to provide it by setting the environment variable `MAPBOX_ACCESS_TOKEN`: - - export MAPBOX_ACCESS_TOKEN=MYTOKEN - -Optionally, you can specify a custom style to the QMapboxGL example application: - - export MAPBOX_STYLE_URL=MYSTYLEURL - -#### Using QMapboxGL - -`QMapboxGL` is a [QObject](http://doc.qt.io/qt-5/qobject.html) - [MapWindow](https://github.com/mapbox/mapbox-gl-native/blob/master/platform/qt/app/mapwindow.hpp) provides an example [QGLWidget](http://doc.qt.io/qt-5/qglwidget.html) that contains a `QMapboxGL` object. If you use `QMapboxGL` in non-standard Qt widgets, make sure to initialize the GL extensions required by Mapbox whenever possible: - - QMapbox::initializeGLExtensions(); +This is the foundation for the Mapbox GL plugin available since Qt 5.9. Use the Qt bugtracker +for bugs related to the plugin and this GitHub repository for bugs related to Mapbox GL Native. #### Linux @@ -47,9 +14,7 @@ For Linux (Ubuntu) desktop, together with these [build instructions](https://github.com/mapbox/mapbox-gl-native/tree/master/platform/linux#build), you also need: - sudo apt-get install qt5-default qtlocation5-dev qtpositioning5-dev \ - qml-module-qtquick2 qml-module-qtpositioning qml-module-qtgraphicaleffects \ - qml-module-qtquick-layouts qml-module-qtquick-controls + sudo apt-get install qt5-default #### macOS @@ -74,8 +39,3 @@ can be found in [platform/qt/include](https://github.com/mapbox/mapbox-gl-native ```make qt-app``` or ```make run-qt-app``` to run the application at the end of build. - -#### QQuickMapboxGL example application: - -```make qt-qml-app``` or ```make run-qt-qml-app``` to run the application at the -end of build. diff --git a/platform/qt/bitrise-qt5.yml b/platform/qt/bitrise-qt5.yml index e0627f03e5..036ec044c5 100644 --- a/platform/qt/bitrise-qt5.yml +++ b/platform/qt/bitrise-qt5.yml @@ -39,7 +39,6 @@ workflows: ln -s /usr/local/Cellar/qt5/$HOMEBREW_QT5_VERSION/plugins /usr/local/plugins export BUILDTYPE=Debug make qt-app - make qt-qml-app make run-qt-test - is_debug: 'yes' - deploy-to-bitrise-io: diff --git a/platform/qt/include/qquickmapboxgl.hpp b/platform/qt/include/qquickmapboxgl.hpp deleted file mode 100644 index 39b4395bd6..0000000000 --- a/platform/qt/include/qquickmapboxgl.hpp +++ /dev/null @@ -1,176 +0,0 @@ -#pragma once - -#include "qmapbox.hpp" -#include "qmapboxgl.hpp" -#include "qquickmapboxglmapparameter.hpp" - -#include <QColor> -#include <QGeoCoordinate> -#include <QGeoServiceProvider> -#include <QGeoShape> -#include <QImage> -#include <QPointF> -#include <QQmlListProperty> -#include <QQuickFramebufferObject> -#include <QQuickItem> - -class QDeclarativeGeoServiceProvider; -class QQuickMapboxGLRenderer; - -class Q_DECL_EXPORT QQuickMapboxGL : public QQuickFramebufferObject -{ - Q_OBJECT - - // Map QML Type interface. - Q_ENUMS(QGeoServiceProvider::Error) - Q_PROPERTY(QDeclarativeGeoServiceProvider *plugin READ plugin WRITE setPlugin NOTIFY pluginChanged) - Q_PROPERTY(qreal minimumZoomLevel READ minimumZoomLevel WRITE setMinimumZoomLevel NOTIFY minimumZoomLevelChanged) - Q_PROPERTY(qreal maximumZoomLevel READ maximumZoomLevel WRITE setMaximumZoomLevel NOTIFY maximumZoomLevelChanged) - Q_PROPERTY(qreal zoomLevel READ zoomLevel WRITE setZoomLevel NOTIFY zoomLevelChanged) - Q_PROPERTY(QGeoCoordinate center READ center WRITE setCenter NOTIFY centerChanged) - Q_PROPERTY(QGeoServiceProvider::Error error READ error NOTIFY errorChanged) - Q_PROPERTY(QString errorString READ errorString NOTIFY errorChanged) - Q_PROPERTY(QGeoShape visibleRegion READ visibleRegion WRITE setVisibleRegion) - Q_PROPERTY(bool copyrightsVisible READ copyrightsVisible WRITE setCopyrightsVisible NOTIFY copyrightsVisibleChanged) - Q_PROPERTY(QColor color READ color WRITE setColor NOTIFY colorChanged) - - // Proposed Qt interface - based on the example documentation below: - // http://doc.qt.io/qt-5/qtqml-referenceexamples-properties-example.html - Q_PROPERTY(QQmlListProperty<QQuickMapboxGLMapParameter> parameters READ parameters) - -public: - QQuickMapboxGL(QQuickItem *parent = 0); - virtual ~QQuickMapboxGL(); - - // QQuickFramebufferObject implementation. - virtual Renderer *createRenderer() const Q_DECL_FINAL; - - // Map QML Type interface implementation. - void setPlugin(QDeclarativeGeoServiceProvider *plugin); - QDeclarativeGeoServiceProvider *plugin() const; - - void setMinimumZoomLevel(qreal minimumZoomLevel); - qreal minimumZoomLevel() const; - - void setMaximumZoomLevel(qreal maximumZoomLevel); - qreal maximumZoomLevel() const; - - void setZoomLevel(qreal zoomLevel); - qreal zoomLevel() const; - - QGeoCoordinate center() const; - - QGeoServiceProvider::Error error() const; - QString errorString() const; - - void setVisibleRegion(const QGeoShape &shape); - QGeoShape visibleRegion() const; - - void setCopyrightsVisible(bool visible); - bool copyrightsVisible() const; - - void setColor(const QColor &color); - QColor color() const; - - Q_INVOKABLE void pan(int dx, int dy); - - // Proposed Qt interface implementation. - QQmlListProperty<QQuickMapboxGLMapParameter> parameters(); - -protected: - // QQmlParserStatus implementation - void componentComplete() override; - -signals: - // Map QML Type signals. - void minimumZoomLevelChanged(); - void maximumZoomLevelChanged(); - void zoomLevelChanged(qreal zoomLevel); - void centerChanged(const QGeoCoordinate &coordinate); - void colorChanged(const QColor &color); - void errorChanged(); - - // Compatibility with Map QML Type, but no-op. - void pluginChanged(QDeclarativeGeoServiceProvider *plugin); - void copyrightLinkActivated(const QString &link); - void copyrightsVisibleChanged(bool visible); - -public slots: - void setCenter(const QGeoCoordinate ¢er); - -private slots: - void onMapChanged(QMapboxGL::MapChange); - void onParameterPropertyUpdated(const QString &name); - -private: - static void appendParameter(QQmlListProperty<QQuickMapboxGLMapParameter> *prop, QQuickMapboxGLMapParameter *mapObject); - static int countParameters(QQmlListProperty<QQuickMapboxGLMapParameter> *prop); - static QQuickMapboxGLMapParameter *parameterAt(QQmlListProperty<QQuickMapboxGLMapParameter> *prop, int index); - static void clearParameter(QQmlListProperty<QQuickMapboxGLMapParameter> *prop); - - enum SyncState { - NothingNeedsSync = 0, - ZoomNeedsSync = 1 << 0, - CenterNeedsSync = 1 << 1, - StyleNeedsSync = 1 << 2, - PanNeedsSync = 1 << 3, - BearingNeedsSync = 1 << 4, - PitchNeedsSync = 1 << 5, - }; - - struct Image { - QString name; - QImage sprite; - }; - - struct StyleProperty { - enum Type { - Paint = 0, - Layout - }; - - Type type; - QString layer; - QString property; - QVariant value; - QString klass; - }; - - void processMapParameter(QQuickMapboxGLMapParameter *); - bool parseImage(QQuickMapboxGLMapParameter *); - bool parseStyle(QQuickMapboxGLMapParameter *); - bool parseStyleProperty(QQuickMapboxGLMapParameter *, const QString &name); - bool parseStyleLayer(QQuickMapboxGLMapParameter *); - bool parseStyleSource(QQuickMapboxGLMapParameter *); - bool parseStyleFilter(QQuickMapboxGLMapParameter *); - bool parseBearing(QQuickMapboxGLMapParameter *); - bool parsePitch(QQuickMapboxGLMapParameter *); - - qreal m_minimumZoomLevel = 0; - qreal m_maximumZoomLevel = 20; - qreal m_zoomLevel = 20; - - QPointF m_pan; - - QGeoCoordinate m_center; - QGeoShape m_visibleRegion; - QColor m_color; - QString m_styleUrl; - QList<Image> m_imageChanges; - QList<StyleProperty> m_stylePropertyChanges; - QList<QVariantMap> m_layerChanges; - QList<QVariantMap> m_sourceChanges; - QList<QVariantMap> m_filterChanges; - QList<QQuickMapboxGLMapParameter*> m_parameters; - - QGeoServiceProvider::Error m_error = QGeoServiceProvider::NoError; - QString m_errorString; - - qreal m_bearing = 0; - qreal m_pitch = 0; - - int m_syncState = NothingNeedsSync; - bool m_styleLoaded = false; - - friend class QQuickMapboxGLRenderer; -}; diff --git a/platform/qt/include/qquickmapboxglmapparameter.hpp b/platform/qt/include/qquickmapboxglmapparameter.hpp deleted file mode 100644 index 1dca0cf55d..0000000000 --- a/platform/qt/include/qquickmapboxglmapparameter.hpp +++ /dev/null @@ -1,34 +0,0 @@ -#pragma once - -#include <QObject> -#include <QQmlParserStatus> -#include <QString> -#include <qqml.h> - -class Q_DECL_EXPORT QQuickMapboxGLMapParameter : public QObject, public QQmlParserStatus -{ - Q_OBJECT - Q_INTERFACES(QQmlParserStatus) - -public: - QQuickMapboxGLMapParameter(QObject *parent = 0); - virtual ~QQuickMapboxGLMapParameter() {}; - - int propertyOffset() const { return m_metaPropertyOffset; } - -signals: - void propertyUpdated(const QString &name); - -protected: - // QQmlParserStatus implementation - void classBegin() override {} - void componentComplete() override; - -private slots: - void onPropertyUpdated(int index); - -private: - int m_metaPropertyOffset; -}; - -QML_DECLARE_TYPE(QQuickMapboxGLMapParameter) diff --git a/platform/qt/qmlapp/main.cpp b/platform/qt/qmlapp/main.cpp deleted file mode 100644 index 8606704002..0000000000 --- a/platform/qt/qmlapp/main.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include <QQuickMapboxGL> -#include <QQuickMapboxGLMapParameter> - -#include <QGuiApplication> -#include <QIcon> -#include <QQmlApplicationEngine> -#include <qqml.h> - -int main(int argc, char *argv[]) -{ - QGuiApplication app(argc, argv); - -#if QT_VERSION >= 0x050300 - app.setWindowIcon(QIcon(":icon.png")); -#endif - - qmlRegisterType<QQuickMapboxGL>("QQuickMapboxGL", 1, 0, "MapboxMap"); - qmlRegisterType<QQuickMapboxGLMapParameter>("QQuickMapboxGL", 1, 0, "MapParameter"); - - QQmlApplicationEngine engine; - engine.load(QUrl(QStringLiteral("qrc:/main.qml"))); - - return app.exec(); -} diff --git a/platform/qt/qmlapp/main.qml b/platform/qt/qmlapp/main.qml deleted file mode 100644 index fd62193b42..0000000000 --- a/platform/qt/qmlapp/main.qml +++ /dev/null @@ -1,347 +0,0 @@ -import QtGraphicalEffects 1.0 -import QtPositioning 5.0 -import QtQuick 2.0 -import QtQuick.Controls 1.0 -import QtQuick.Dialogs 1.0 -import QtQuick.Layouts 1.0 - -import QQuickMapboxGL 1.0 - -ApplicationWindow { - title: "Mapbox GL QML example" - width: 1024 - height: 768 - visible: true - - MapboxMap { - id: map - anchors.fill: parent - - parameters: [ - MapParameter { - id: style - property var type: "style" - property var url: "mapbox://styles/mapbox/streets-v9" - }, - MapParameter { - id: waterPaint - property var type: "paint" - property var layer: "water" - property var fillColor: waterColorDialog.color - }, - MapParameter { - id: source - property var type: "source" - property var name: "routeSource" - property var sourceType: "geojson" - property var data: ":source1.geojson" - }, - MapParameter { - property var type: "layer" - property var name: "routeCase" - property var layerType: "line" - property var source: "routeSource" - }, - MapParameter { - property var type: "paint" - property var layer: "routeCase" - property var lineColor: "white" - property var lineWidth: 20.0 - }, - MapParameter { - property var type: "layout" - property var layer: "routeCase" - property var lineJoin: "round" - property var lineCap: lineJoin - property var visibility: toggleRoute.checked ? "visible" : "none" - }, - MapParameter { - property var type: "layer" - property var name: "route" - property var layerType: "line" - property var source: "routeSource" - }, - MapParameter { - id: linePaint - property var type: "paint" - property var layer: "route" - property var lineColor: "blue" - property var lineWidth: 8.0 - }, - MapParameter { - property var type: "layout" - property var layer: "route" - property var lineJoin: "round" - property var lineCap: "round" - property var visibility: toggleRoute.checked ? "visible" : "none" - }, - MapParameter { - property var type: "image" - property var name: "label-arrow" - property var sprite: ":label-arrow.svg" - }, - MapParameter { - property var type: "image" - property var name: "label-background" - property var sprite: ":label-background.svg" - }, - MapParameter { - property var type: "layer" - property var name: "markerArrow" - property var layerType: "symbol" - property var source: "routeSource" - }, - MapParameter { - property var type: "layout" - property var layer: "markerArrow" - property var iconImage: "label-arrow" - property var iconSize: 0.5 - property var iconIgnorePlacement: true - property var iconOffset: [ 0.0, -15.0 ] - property var visibility: toggleRoute.checked ? "visible" : "none" - }, - MapParameter { - property var type: "layer" - property var name: "markerBackground" - property var layerType: "symbol" - property var source: "routeSource" - }, - MapParameter { - property var type: "layout" - property var layer: "markerBackground" - property var iconImage: "label-background" - property var textField: "{name}" - property var iconTextFit: "both" - property var iconIgnorePlacement: true - property var textIgnorePlacement: true - property var textAnchor: "left" - property var textSize: 16.0 - property var textPadding: 0.0 - property var textLineHeight: 1.0 - property var textMaxWidth: 8.0 - property var iconTextFitPadding: [ 15.0, 10.0, 15.0, 10.0 ] - property var textOffset: [ -0.5, -1.5 ] - property var visibility: toggleRoute.checked ? "visible" : "none" - }, - MapParameter { - property var type: "paint" - property var layer: "markerBackground" - property var textColor: "white" - }, - MapParameter { - property var type: "filter" - property var layer: "markerArrow" - property var filter: [ "==", "$type", "Point" ] - }, - MapParameter { - property var type: "filter" - property var layer: "markerBackground" - property var filter: [ "==", "$type", "Point" ] - }, - MapParameter { - property var type: "bearing" - property var angle: bearingSlider.value - }, - MapParameter { - property var type: "pitch" - property var angle: pitchSlider.value - } - ] - - center: QtPositioning.coordinate(60.170448, 24.942046) // Helsinki - zoomLevel: 12.25 - minimumZoomLevel: 0 - maximumZoomLevel: 20 - - color: landColorDialog.color - copyrightsVisible: true - - states: State { - name: "moved"; when: mouseArea.pressed - PropertyChanges { target: linePaint; lineColor: "red"; } - } - - transitions: Transition { - ColorAnimation { properties: "lineColor"; easing.type: Easing.InOutQuad; duration: 500 } - } - - Image { - anchors.right: parent.right - anchors.bottom: parent.bottom - anchors.margins: 20 - - opacity: .75 - - sourceSize.width: 80 - sourceSize.height: 80 - - source: "icon.png" - } - - MouseArea { - id: mouseArea - anchors.fill: parent - - property var lastX: 0 - property var lastY: 0 - - onWheel: map.zoomLevel += 0.2 * wheel.angleDelta.y / 120 - - onPressed: { - lastX = mouse.x - lastY = mouse.y - } - - onPositionChanged: { - map.pan(mouse.x - lastX, mouse.y - lastY) - - lastX = mouse.x - lastY = mouse.y - } - } - } - - ColorDialog { - id: landColorDialog - title: "Land color" - color: "#e0ded8" - } - - ColorDialog { - id: waterColorDialog - title: "Water color" - color: "#63c5ee" - } - - Rectangle { - anchors.fill: menu - anchors.margins: -20 - radius: 30 - clip: true - } - - ColumnLayout { - id: menu - - anchors.right: parent.right - anchors.top: parent.top - anchors.margins: 30 - - Label { - text: "Bearing:" - } - - Slider { - id: bearingSlider - - anchors.left: parent.left - anchors.right: parent.right - maximumValue: 180 - } - - Label { - text: "Pitch:" - } - - Slider { - id: pitchSlider - - anchors.left: parent.left - anchors.right: parent.right - maximumValue: 60 - } - - GroupBox { - anchors.left: parent.left - anchors.right: parent.right - title: "Style:" - - ColumnLayout { - ExclusiveGroup { id: styleGroup } - RadioButton { - text: "Streets" - checked: true - exclusiveGroup: styleGroup - onClicked: { - style.url = "mapbox://styles/mapbox/streets-v9" - landColorDialog.color = "#e0ded8" - waterColorDialog.color = "#63c5ee" - } - } - RadioButton { - text: "Dark" - exclusiveGroup: styleGroup - onClicked: { - style.url = "mapbox://styles/mapbox/dark-v9" - landColorDialog.color = "#343332" - waterColorDialog.color = "#191a1a" - } - } - RadioButton { - text: "Satellite" - exclusiveGroup: styleGroup - onClicked: { - style.url = "mapbox://styles/mapbox/satellite-v9" - } - } - } - } - - Button { - anchors.left: parent.left - anchors.right: parent.right - text: "Select land color" - onClicked: landColorDialog.open() - } - - Button { - anchors.left: parent.left - anchors.right: parent.right - text: "Select water color" - onClicked: waterColorDialog.open() - } - - GroupBox { - anchors.left: parent.left - anchors.right: parent.right - title: "Route:" - - ColumnLayout { - ExclusiveGroup { id: sourceGroup } - RadioButton { - text: "Route 1" - checked: true - exclusiveGroup: sourceGroup - onClicked: { - source.data = ":source1.geojson" - } - } - RadioButton { - text: "Route 2" - exclusiveGroup: sourceGroup - onClicked: { - source.data = ":source2.geojson" - } - } - RadioButton { - text: "Route 3" - exclusiveGroup: sourceGroup - onClicked: { - source.data = '{ "type": "FeatureCollection", "features": \ - [{ "type": "Feature", "properties": {}, "geometry": { \ - "type": "LineString", "coordinates": [[ 24.934938848018646, \ - 60.16830257086771 ], [ 24.943315386772156, 60.16227776476442 ]]}}]}' - } - } - } - } - - CheckBox { - id: toggleRoute - anchors.left: parent.left - anchors.right: parent.right - text: "Toggle route" - checked: true - } - } -} diff --git a/platform/qt/qmlapp/qml.qrc b/platform/qt/qmlapp/qml.qrc deleted file mode 100644 index 5f6483ac33..0000000000 --- a/platform/qt/qmlapp/qml.qrc +++ /dev/null @@ -1,5 +0,0 @@ -<RCC> - <qresource prefix="/"> - <file>main.qml</file> - </qresource> -</RCC> diff --git a/platform/qt/qt5.cmake b/platform/qt/qt5.cmake index 9a482f6d30..ed51051311 100644 --- a/platform/qt/qt5.cmake +++ b/platform/qt/qt5.cmake @@ -3,7 +3,6 @@ find_package(Qt5Gui REQUIRED) find_package(Qt5Location REQUIRED) find_package(Qt5Network REQUIRED) find_package(Qt5OpenGL REQUIRED) -find_package(Qt5Quick REQUIRED) find_package(Qt5Widgets REQUIRED) find_package(Qt5Sql REQUIRED) @@ -21,21 +20,11 @@ set(MBGL_QT_TEST_LIBRARIES PRIVATE Qt5::OpenGL ) -target_sources(qmapboxgl - PRIVATE platform/qt/include/qquickmapboxgl.hpp - PRIVATE platform/qt/include/qquickmapboxglmapparameter.hpp - PRIVATE platform/qt/src/qquickmapboxgl.cpp - PRIVATE platform/qt/src/qquickmapboxglmapparameter.cpp - PRIVATE platform/qt/src/qquickmapboxglrenderer.cpp - PRIVATE platform/qt/src/qquickmapboxglrenderer.hpp -) - target_link_libraries(qmapboxgl PRIVATE mbgl-core PRIVATE Qt5::Core PRIVATE Qt5::Gui PRIVATE Qt5::Location - PRIVATE Qt5::Quick PRIVATE Qt5::Sql ) @@ -44,16 +33,3 @@ target_link_libraries(mbgl-qt PRIVATE Qt5::OpenGL PRIVATE Qt5::Widgets ) - -# QtQuick app -add_executable(mbgl-qt-qml - platform/qt/qmlapp/main.cpp - platform/qt/qmlapp/qml.qrc - platform/qt/resources/common.qrc -) - -target_link_libraries(mbgl-qt-qml - PRIVATE qmapboxgl - PRIVATE Qt5::Location - PRIVATE Qt5::Quick -) diff --git a/platform/qt/src/qquickmapboxgl.cpp b/platform/qt/src/qquickmapboxgl.cpp deleted file mode 100644 index 7325bfe3c2..0000000000 --- a/platform/qt/src/qquickmapboxgl.cpp +++ /dev/null @@ -1,469 +0,0 @@ -#include "qquickmapboxgl.hpp" - -#include "qquickmapboxglmapparameter.hpp" -#include "qquickmapboxglrenderer.hpp" - -#include <mbgl/util/constants.hpp> - -#include <QDebug> -#include <QQuickItem> -#include <QRegularExpression> -#include <QString> -#include <QtGlobal> -#include <QQmlListProperty> -#include <QJSValue> - -namespace { - -static const QRegularExpression s_camelCase {"([a-z0-9])([A-Z])"}; -static const QStringList s_parameterTypes = QStringList() - << "style" << "paint" << "layout" << "layer" << "source" << "filter" << "image" - << "bearing" << "pitch"; - -} // namespace - -QQuickMapboxGL::QQuickMapboxGL(QQuickItem *parent_) - : QQuickFramebufferObject(parent_) -{ -} - -QQuickMapboxGL::~QQuickMapboxGL() -{ -} - -QQuickFramebufferObject::Renderer *QQuickMapboxGL::createRenderer() const -{ - return new QQuickMapboxGLRenderer; -} - -void QQuickMapboxGL::setPlugin(QDeclarativeGeoServiceProvider *) -{ - m_error = QGeoServiceProvider::NotSupportedError; - m_errorString = "QQuickMapboxGL does not support plugins."; - emit errorChanged(); -} - -QDeclarativeGeoServiceProvider *QQuickMapboxGL::plugin() const -{ - return nullptr; -} - -void QQuickMapboxGL::componentComplete() -{ - QQuickFramebufferObject::componentComplete(); - - for (const auto& param : m_parameters) { - processMapParameter(param); - } -} - -void QQuickMapboxGL::setMinimumZoomLevel(qreal zoom) -{ - zoom = qMax(mbgl::util::MIN_ZOOM, zoom); - zoom = qMin(m_maximumZoomLevel, zoom); - - if (m_minimumZoomLevel == zoom) { - return; - } - - m_minimumZoomLevel = zoom; - setZoomLevel(m_zoomLevel); // Constrain. - - emit minimumZoomLevelChanged(); -} - -qreal QQuickMapboxGL::minimumZoomLevel() const -{ - return m_minimumZoomLevel; -} - -void QQuickMapboxGL::setMaximumZoomLevel(qreal zoom) -{ - zoom = qMin(mbgl::util::MAX_ZOOM, zoom); - zoom = qMax(m_minimumZoomLevel, zoom); - - if (m_maximumZoomLevel == zoom) { - return; - } - - m_maximumZoomLevel = zoom; - setZoomLevel(m_zoomLevel); // Constrain. - - emit maximumZoomLevelChanged(); -} - -qreal QQuickMapboxGL::maximumZoomLevel() const -{ - return m_maximumZoomLevel; -} - -void QQuickMapboxGL::setZoomLevel(qreal zoom) -{ - zoom = qMin(m_maximumZoomLevel, zoom); - zoom = qMax(m_minimumZoomLevel, zoom); - - if (m_zoomLevel == zoom) { - return; - } - - m_zoomLevel = zoom; - - m_syncState |= ZoomNeedsSync; - update(); - - emit zoomLevelChanged(m_zoomLevel); -} - -qreal QQuickMapboxGL::zoomLevel() const -{ - return m_zoomLevel; -} - -void QQuickMapboxGL::setCenter(const QGeoCoordinate &coordinate) -{ - if (m_center == coordinate) { - return; - } - - m_center = coordinate; - - m_syncState |= CenterNeedsSync; - update(); - - emit centerChanged(m_center); -} - -QGeoCoordinate QQuickMapboxGL::center() const -{ - return m_center; -} - -QGeoServiceProvider::Error QQuickMapboxGL::error() const -{ - return m_error; -} - -QString QQuickMapboxGL::errorString() const -{ - return m_errorString; -} - -void QQuickMapboxGL::setVisibleRegion(const QGeoShape &shape) -{ - m_visibleRegion = shape; -} - -QGeoShape QQuickMapboxGL::visibleRegion() const -{ - return m_visibleRegion; -} - -void QQuickMapboxGL::setCopyrightsVisible(bool) -{ - qWarning() << Q_FUNC_INFO << "Not implemented."; -} - -bool QQuickMapboxGL::copyrightsVisible() const -{ - return false; -} - -void QQuickMapboxGL::setColor(const QColor &color) -{ - if (m_color == color) { - return; - } - - m_color = color; - - StyleProperty change; - change.type = StyleProperty::Paint; - change.layer = "background"; - change.property = "background-color"; - change.value = color; - m_stylePropertyChanges << change; - - update(); - - emit colorChanged(m_color); -} - -QColor QQuickMapboxGL::color() const -{ - return m_color; -} - -void QQuickMapboxGL::pan(int dx, int dy) -{ - m_pan += QPointF(dx, -dy); - - m_syncState |= PanNeedsSync; - update(); -} - -void QQuickMapboxGL::onMapChanged(QMapboxGL::MapChange change) -{ - if (change == QMapboxGL::MapChangeDidFinishLoadingStyle) { - m_styleLoaded = true; - update(); - } -} - -bool QQuickMapboxGL::parseImage(QQuickMapboxGLMapParameter *param) -{ - m_imageChanges << Image { - param->property("name").toString(), - QImage(param->property("sprite").toString()) - }; - return true; -} - -bool QQuickMapboxGL::parseStyle(QQuickMapboxGLMapParameter *param) -{ - QString url = param->property("url").toString(); - if (m_styleUrl == url) { - return false; - } - - // Reload parameters if switching style URLs. - if (!m_styleUrl.isEmpty()) { - for (const auto& param_ : m_parameters) { - if (param_->property("type").toString() == "style") continue; - processMapParameter(param_); - } - } - - m_styleUrl = url; - m_styleLoaded = false; - m_syncState |= StyleNeedsSync; - - return true; -} - -bool QQuickMapboxGL::parseStyleProperty(QQuickMapboxGLMapParameter *param, const QString &name) -{ - // Ignore meta-properties "type", "layer" and "class". - if (name == "type" || name == "layer" || name == "class") { - return false; - } - - QString formattedName(name); - formattedName = formattedName.replace(s_camelCase, "\\1-\\2").toLower(); - - QVariant value = param->property(name.toLatin1()); - if (value.canConvert<QJSValue>()) { - value = value.value<QJSValue>().toVariant(); - } - - m_stylePropertyChanges << QQuickMapboxGL::StyleProperty { - param->property("type").toString().at(0) == 'p' ? StyleProperty::Paint : StyleProperty::Layout, - param->property("layer").toString(), - formattedName, - value, - param->property("class").toString() - }; - return true; -} - -bool QQuickMapboxGL::parseStyleLayer(QQuickMapboxGLMapParameter *param) -{ - QVariantMap layer; - layer["id"] = param->property("name"); - layer["source"] = param->property("source"); - layer["type"] = param->property("layerType"); - if (param->property("sourceLayer").isValid()) { - layer["source-layer"] = param->property("sourceLayer"); - } - m_layerChanges << layer; - return true; -} - -bool QQuickMapboxGL::parseStyleSource(QQuickMapboxGLMapParameter *param) -{ - QString sourceType = param->property("sourceType").toString(); - - QVariantMap source; - source["id"] = param->property("name"); - source["type"] = sourceType; - if (sourceType == "vector" || sourceType == "raster") { - source["url"] = param->property("url"); - m_sourceChanges << source; - } else if (sourceType == "geojson") { - auto data = param->property("data").toString(); - if (data.startsWith(':')) { - QFile geojson(data); - geojson.open(QIODevice::ReadOnly); - source["data"] = geojson.readAll(); - } else { - source["data"] = data.toUtf8(); - } - m_sourceChanges << source; - } else { - m_error = QGeoServiceProvider::UnknownParameterError; - m_errorString = "Invalid source type: " + sourceType; - emit errorChanged(); - return false; - } - return true; -} - -bool QQuickMapboxGL::parseStyleFilter(QQuickMapboxGLMapParameter *param) -{ - QVariantMap filter; - filter["layer"] = param->property("layer"); - filter["filter"] = param->property("filter"); - m_filterChanges << filter; - return true; -} - -bool QQuickMapboxGL::parseBearing(QQuickMapboxGLMapParameter *param) -{ - qreal angle = param->property("angle").toReal(); - if (m_bearing == angle) return false; - m_bearing = angle; - m_syncState |= BearingNeedsSync; - update(); - return true; -} - -bool QQuickMapboxGL::parsePitch(QQuickMapboxGLMapParameter *param) -{ - qreal angle = param->property("angle").toReal(); - angle = qMin(qMax(0., angle), mbgl::util::PITCH_MAX * mbgl::util::RAD2DEG); - if (m_pitch == angle) return false; - m_pitch = angle; - m_syncState |= PitchNeedsSync; - update(); - return true; -} - -void QQuickMapboxGL::processMapParameter(QQuickMapboxGLMapParameter *param) -{ - bool needsUpdate = false; - switch (s_parameterTypes.indexOf(param->property("type").toString())) { - case -1: - m_error = QGeoServiceProvider::UnknownParameterError; - m_errorString = "Invalid value for property 'type': " + param->property("type").toString(); - emit errorChanged(); - break; - case 0: // style - needsUpdate |= parseStyle(param); - break; - case 1: // paint - case 2: // layout - for (int i = param->propertyOffset(); i < param->metaObject()->propertyCount(); ++i) { - needsUpdate |= parseStyleProperty(param, QString(param->metaObject()->property(i).name())); - } - break; - case 3: // layer - needsUpdate |= parseStyleLayer(param); - break; - case 4: // source - needsUpdate |= parseStyleSource(param); - break; - case 5: // filter - needsUpdate |= parseStyleFilter(param); - break; - case 6: // image - needsUpdate |= parseImage(param); - break; - case 7: // bearing - needsUpdate |= parseBearing(param); - break; - case 8: // pitch - needsUpdate |= parsePitch(param); - break; - } - if (needsUpdate) update(); -} - -void QQuickMapboxGL::onParameterPropertyUpdated(const QString &propertyName) -{ - QQuickMapboxGLMapParameter *param = qobject_cast<QQuickMapboxGLMapParameter *>(sender()); - if (!param) { - m_error = QGeoServiceProvider::NotSupportedError; - m_errorString = "QQuickMapboxGL::onParameterPropertyUpdated should be called from a QQuickMapboxGLMapParameter."; - emit errorChanged(); - return; - } - - if (propertyName == "type") { - m_error = QGeoServiceProvider::NotSupportedError; - m_errorString = "Property 'type' is a write-once."; - emit errorChanged(); - return; - } - - bool needsUpdate = false; - switch (s_parameterTypes.indexOf(param->property("type").toString())) { - case -1: - m_error = QGeoServiceProvider::UnknownParameterError; - m_errorString = "Invalid value for property 'type': " + param->property("type").toString(); - emit errorChanged(); - break; - case 0: // style - needsUpdate |= parseStyle(param); - break; - case 1: // paint - case 2: // layout - needsUpdate |= parseStyleProperty(param, propertyName); - break; - case 3: // layer - needsUpdate |= parseStyleLayer(param); - break; - case 4: // source - needsUpdate |= parseStyleSource(param); - break; - case 5: // filter - needsUpdate |= parseStyleFilter(param); - break; - case 6: // image - needsUpdate |= parseImage(param); - break; - case 7: // bearing - needsUpdate |= parseBearing(param); - break; - case 8: // pitch - needsUpdate |= parsePitch(param); - break; - } - if (needsUpdate) update(); -} - -void QQuickMapboxGL::appendParameter(QQmlListProperty<QQuickMapboxGLMapParameter> *prop, QQuickMapboxGLMapParameter *param) -{ - QQuickMapboxGL *map = static_cast<QQuickMapboxGL *>(prop->object); - map->m_parameters.append(param); - QObject::connect(param, SIGNAL(propertyUpdated(QString)), map, SLOT(onParameterPropertyUpdated(QString))); -} - -int QQuickMapboxGL::countParameters(QQmlListProperty<QQuickMapboxGLMapParameter> *prop) -{ - QQuickMapboxGL *map = static_cast<QQuickMapboxGL *>(prop->object); - return map->m_parameters.count(); -} - -QQuickMapboxGLMapParameter *QQuickMapboxGL::parameterAt(QQmlListProperty<QQuickMapboxGLMapParameter> *prop, int index) -{ - QQuickMapboxGL *map = static_cast<QQuickMapboxGL *>(prop->object); - return map->m_parameters[index]; -} - -void QQuickMapboxGL::clearParameter(QQmlListProperty<QQuickMapboxGLMapParameter> *prop) -{ - QQuickMapboxGL *map = static_cast<QQuickMapboxGL *>(prop->object); - for (auto param : map->m_parameters) { - QObject::disconnect(param, SIGNAL(propertyUpdated(QString)), map, SLOT(onParameterPropertyUpdated(QString))); - } - map->m_parameters.clear(); -} - -QQmlListProperty<QQuickMapboxGLMapParameter> QQuickMapboxGL::parameters() -{ - return QQmlListProperty<QQuickMapboxGLMapParameter>(this, - nullptr, - appendParameter, - countParameters, - parameterAt, - clearParameter); -} diff --git a/platform/qt/src/qquickmapboxglmapparameter.cpp b/platform/qt/src/qquickmapboxglmapparameter.cpp deleted file mode 100644 index abf6e5ff1c..0000000000 --- a/platform/qt/src/qquickmapboxglmapparameter.cpp +++ /dev/null @@ -1,35 +0,0 @@ -#include "qquickmapboxglmapparameter.hpp" - -#include <QByteArray> -#include <QMetaObject> -#include <QMetaProperty> -#include <QSignalMapper> - -QQuickMapboxGLMapParameter::QQuickMapboxGLMapParameter(QObject *parent) - : QObject(parent) - , m_metaPropertyOffset(metaObject()->propertyCount()) -{ -} - -void QQuickMapboxGLMapParameter::componentComplete() -{ - for (int i = m_metaPropertyOffset; i < metaObject()->propertyCount(); ++i) { - QMetaProperty property = metaObject()->property(i); - - if (!property.hasNotifySignal()) { - return; - } - - auto mapper = new QSignalMapper(this); - mapper->setMapping(this, i); - - const QByteArray signalName = '2' + property.notifySignal().methodSignature(); - QObject::connect(this, signalName, mapper, SLOT(map())); - QObject::connect(mapper, SIGNAL(mapped(int)), this, SLOT(onPropertyUpdated(int))); - } -} - -void QQuickMapboxGLMapParameter::onPropertyUpdated(int index) -{ - emit propertyUpdated(metaObject()->property(index).name()); -} diff --git a/platform/qt/src/qquickmapboxglrenderer.cpp b/platform/qt/src/qquickmapboxglrenderer.cpp deleted file mode 100644 index 133bed40e2..0000000000 --- a/platform/qt/src/qquickmapboxglrenderer.cpp +++ /dev/null @@ -1,120 +0,0 @@ -#include "qquickmapboxglrenderer.hpp" - -#include "qmapboxgl.hpp" -#include "qquickmapboxgl.hpp" - -#include <QSize> -#include <QOpenGLFramebufferObject> -#include <QOpenGLFramebufferObjectFormat> -#include <QQuickWindow> -#include <QThread> - -QQuickMapboxGLRenderer::QQuickMapboxGLRenderer() -{ - QMapbox::initializeGLExtensions(); - - QMapboxGLSettings settings; - settings.setAccessToken(qgetenv("MAPBOX_ACCESS_TOKEN")); - settings.setCacheDatabasePath("/tmp/mbgl-cache.db"); - settings.setCacheDatabaseMaximumSize(20 * 1024 * 1024); - settings.setViewportMode(QMapboxGLSettings::FlippedYViewport); - - m_map.reset(new QMapboxGL(nullptr, settings, QSize(256, 256), 1)); -} - -QQuickMapboxGLRenderer::~QQuickMapboxGLRenderer() -{ -} - -QOpenGLFramebufferObject* QQuickMapboxGLRenderer::createFramebufferObject(const QSize &size) -{ - m_map->resize(size / m_pixelRatio, size); - - QOpenGLFramebufferObjectFormat format; - format.setAttachment(QOpenGLFramebufferObject::CombinedDepthStencil); - - return new QOpenGLFramebufferObject(size, format); -} - -void QQuickMapboxGLRenderer::render() -{ - framebufferObject()->bind(); - m_map->render(); - framebufferObject()->release(); -} - -void QQuickMapboxGLRenderer::synchronize(QQuickFramebufferObject *item) -{ - auto quickMap = qobject_cast<QQuickMapboxGL*>(item); - if (!m_initialized) { - QObject::connect(m_map.data(), &QMapboxGL::needsRendering, quickMap, &QQuickMapboxGL::update); - QObject::connect(m_map.data(), SIGNAL(mapChanged(QMapboxGL::MapChange)), quickMap, SLOT(onMapChanged(QMapboxGL::MapChange))); - QObject::connect(this, &QQuickMapboxGLRenderer::centerChanged, quickMap, &QQuickMapboxGL::setCenter); - m_initialized = true; - } - - if (auto window = quickMap->window()) { - m_pixelRatio = window->devicePixelRatio(); - } else { - m_pixelRatio = 1; - } - - auto syncStatus = quickMap->m_syncState; - quickMap->m_syncState = QQuickMapboxGL::NothingNeedsSync; - - if (syncStatus & QQuickMapboxGL::CenterNeedsSync || syncStatus & QQuickMapboxGL::ZoomNeedsSync) { - const auto& center = quickMap->center(); - m_map->setCoordinateZoom({ center.latitude(), center.longitude() }, quickMap->zoomLevel()); - } - - if (syncStatus & QQuickMapboxGL::StyleNeedsSync && !quickMap->m_styleUrl.isEmpty()) { - m_map->setStyleUrl(quickMap->m_styleUrl); - } - - if (syncStatus & QQuickMapboxGL::PanNeedsSync) { - m_map->moveBy(quickMap->m_pan); - quickMap->m_pan = QPointF(); - emit centerChanged(QGeoCoordinate(m_map->latitude(), m_map->longitude())); - } - - if (syncStatus & QQuickMapboxGL::BearingNeedsSync) { - m_map->setBearing(quickMap->m_bearing); - } - - if (syncStatus & QQuickMapboxGL::PitchNeedsSync) { - m_map->setPitch(quickMap->m_pitch); - } - - if (!quickMap->m_styleLoaded) { - return; - } - - for (const auto& change : quickMap->m_sourceChanges) { - m_map->updateSource(change.value("id").toString(), change); - } - quickMap->m_sourceChanges.clear(); - - for (const auto& change : quickMap->m_layerChanges) { - m_map->addLayer(change); - } - quickMap->m_layerChanges.clear(); - - for (const auto& change : quickMap->m_filterChanges) { - m_map->setFilter(change.value("layer").toString(), change.value("filter")); - } - quickMap->m_filterChanges.clear(); - - for (const auto& change : quickMap->m_imageChanges) { - m_map->addImage(change.name, change.sprite); - } - quickMap->m_imageChanges.clear(); - - for (const auto& change : quickMap->m_stylePropertyChanges) { - if (change.type == QQuickMapboxGL::StyleProperty::Paint) { - m_map->setPaintProperty(change.layer, change.property, change.value, change.klass); - } else { - m_map->setLayoutProperty(change.layer, change.property, change.value); - } - } - quickMap->m_stylePropertyChanges.clear(); -} diff --git a/platform/qt/src/qquickmapboxglrenderer.hpp b/platform/qt/src/qquickmapboxglrenderer.hpp deleted file mode 100644 index 1fb7a50f4a..0000000000 --- a/platform/qt/src/qquickmapboxglrenderer.hpp +++ /dev/null @@ -1,34 +0,0 @@ -#pragma once - -#include "qmapbox.hpp" -#include "qmapboxgl.hpp" - -#include <QGeoCoordinate> -#include <QObject> -#include <QOpenGLFramebufferObject> -#include <QQuickFramebufferObject> -#include <QScopedPointer> -#include <QSize> - -class QQuickMapboxGLRenderer : public QObject, public QQuickFramebufferObject::Renderer -{ - Q_OBJECT - -public: - QQuickMapboxGLRenderer(); - virtual ~QQuickMapboxGLRenderer(); - - virtual QOpenGLFramebufferObject * createFramebufferObject(const QSize &); - - virtual void render(); - virtual void synchronize(QQuickFramebufferObject *); - -signals: - void centerChanged(const QGeoCoordinate &); - -private: - bool m_initialized = false; - qreal m_pixelRatio = 1; - - QScopedPointer<QMapboxGL> m_map; -}; |