summaryrefslogtreecommitdiff
path: root/examples/location/geojson_viewer/doc/src/geojson_viewer.qdoc
diff options
context:
space:
mode:
Diffstat (limited to 'examples/location/geojson_viewer/doc/src/geojson_viewer.qdoc')
-rw-r--r--examples/location/geojson_viewer/doc/src/geojson_viewer.qdoc190
1 files changed, 190 insertions, 0 deletions
diff --git a/examples/location/geojson_viewer/doc/src/geojson_viewer.qdoc b/examples/location/geojson_viewer/doc/src/geojson_viewer.qdoc
new file mode 100644
index 00000000..b90c02b8
--- /dev/null
+++ b/examples/location/geojson_viewer/doc/src/geojson_viewer.qdoc
@@ -0,0 +1,190 @@
+// Copyright (C) 2017 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GFDL-1.3-no-invariants-only
+
+/*!
+ \example geojson_viewer
+ \title GeoJson Viewer (C++/QML)
+ \ingroup qtlocation-examples
+
+ \brief The GeoJson viewer example demonstrates how to manipulate MapItems, handle user input
+ and I/O to and from a GeoJson file.
+
+ \image geojson_viewer.png
+
+ The example displays a map with various MapItems. The MapItems are either imported from a
+ GeoJson file, using the \l {QGeoJson} API of \l {QtLocation} or drawn by the user using
+ \l {TapHandler}{TapHandlers}.
+
+ Examples for GeoJson files can be found in the directory data within the example directory.
+ They are read and written using the \l {QGeoJson::importGeoJson}{importGeoJson} and
+ \l {QGeoJson::exportGeoJson}{exportGeoJson} functions.
+
+ To draw a MapItem, right click on an empty part of the map and select an item type of your
+ choice in the appearing menu. The next clicks will define the chosen item. The example allows
+ to draw \l {MapCircle}{MapCircles}, \l {MapRectangle}{MapRectangles}, \l {MapPolygon}{MapPolygons}
+ and \l {MapPolyline}{MapPolylines}. Items that are fully defined by two points, i.e. circles
+ and rectangles, are drawn with two clicks of the left mouse button. Items that are defined by
+ multiple points, i.e. polygons and polylines, are created by an arbitrary amount of left button
+ clicks and completed with the right mouse button. Items drawn this way are saved as points,
+ polygons and polylines to fit the GeoJson specification, see \l {https://geojson.org/}.
+
+
+ \include examples-run.qdocinc
+
+
+ \section1 Creating a MapView
+
+ First we create a base map on which all items can be placed on. We take advantage of a
+ \l {MapView} element that combines a basic \l Map with input handling (mouse wheel, drag,
+ etc.). The underlying \l Map can be accessed with \l {MapView::map}{map} property. If you miss
+ a property in \l {MapView} it can be most likely accessed with \l {MapView::map}{MapView.map}.
+
+ \snippet geojson_viewer/main.qml MapView Creation
+
+
+ \section1 Setting up the GeoJson Model / Display MapItems
+
+ In order to display file contents on the map we will use a design pattern known as
+ \l {model-view-programming}{Model/View Programming}. First we need to set up a suitable view,
+ in this example a \l {MapItemView} element. Its parent must be set to the underlying map of the
+ \l {MapView} to correctly display all items placed in it.
+
+ \snippet geojson_viewer/main.qml MapItemView
+
+ Next we need a suitable model, representing a GeoJson file. The GeoJson file is converted into
+ a tree of \l {QVariantMap}{QVariantMaps} and \l{QVariantList}{QVariantLists} within a C++ class
+ in this example.
+
+ \snippet geojson_viewer/main.cpp GeoJsoner
+
+ The class contains a member \c{model} which will be set after reading a GeoJson file.
+
+ \snippet geojson_viewer/main.cpp Conversion QVariantList
+
+ The class is made available to the QML Engine to further process the model in QML.
+
+ \snippet geojson_viewer/main.cpp QMLEngine
+
+ The \l {MapItemView::model}{model} property of the \l{MapItemView} element can then be set to
+ the \l{QVariant} representation of the model:
+
+ \snippet geojson_viewer/main.qml MapItemView Model
+
+ Finally we need a delegate, translating the model data into a representation of items, filling
+ the \l {MapItemView}. It is set to the \l {MapItemView::delegate}{delegate} property of the
+ \l{MapItemView}:
+
+ \snippet geojson_viewer/main.qml MapItemView Delegate
+
+ We use a \l {DelegateChooser} element defined the file \c{GeoJsonDelegate.qml} to take into
+ account the varying representation of different geometry types of GeoJson objects.
+
+ \snippet geojson_viewer/GeoJsonDelegate.qml DelegateChooser
+
+ Various \l {DelegateChoice}{DelegateChoices} are included, each representing a different
+ geometry type to be found in a GeoJson file. The property \l {DelegateChooser::role}{role}
+ will be matched with \l {DelegateChoice::roleValue}{DelegateChoice.roleValue} to determine the
+ correct delegate.
+
+ As an example, a point, described with \c {"type":"Point"} in GeoJson, is represented by a
+ \l {MapCircle} on the \l {MapItemView}:
+
+ \snippet geojson_viewer/GeoJsonDelegate.qml DelegateChoice Point
+
+ Properties of the \l {MapCircle}, such as \l {MapCircle::color}{color} or
+ \l{MapCircle::radius}{radius} are attempted to be read from the GeoJson file that is
+ available in form of the modelData property. However, this is not a strict standard of GeoJson
+ and fallback values are set for all properties.
+
+
+ \section1 Writing MapItems to GeoJson
+
+ To write MapItems to a GeoJson file we first will convert the Mapitems into a representation
+ of \l {QVariantMap}{QVariantMaps} and \l{QVariantList}{QVariantLists}. This is conducted in C++
+ in this example, as part of the \c {GeoJsoner} class used before:
+
+ \snippet geojson_viewer/main.cpp Conversion QVariantList From Items
+
+ \c {extractor} is a helper class that converts Mapitems into \l {QVariant} representations, for
+ example the \l{MapCircle}:
+
+ \snippet geojson_viewer/main.cpp Extractor Example Circle
+
+ In a second step the \l {QVariant} representation can be dumped into a file using
+ \l {QJsonDocument}.
+
+ \snippet geojson_viewer/main.cpp Write QVariantList to Json
+
+ The two C++ functions that are required for writing files can be called from QML, thanks to the
+ definition as \l {Q_INVOKABLE}:
+
+ \snippet geojson_viewer/main.qml Write File
+
+ Note that we could use \c {geoJsoner.model} instead of rebuilding the \l {QVariant}
+ representation. However, the latter is done for demonstration purposes here.
+
+ \section1 User Interaction with MapItems
+
+ To handle user interactions we will use \l {PointHandler}{PointHandlers}. They are especially
+ well suited for the task as they conform to the exact shape of the underlying item, in contrast
+ to \l{MouseArea}{MouseArea}, which always covers a square shape. MapItems that are imported
+ from a GeoJson file get their own \l {HoverHandler} and \l {TapHandler} directly in the delegate:
+
+ \snippet geojson_viewer/GeoJsonDelegate.qml Handler Point
+
+ The \l {TapHandler} is used to write some information about the item on the console when the
+ item is tapped. The \l {HoverHandler} is used to highlight items that lie beneath the mouse
+ pointer. This is implemented by describing the property
+ \l {MapCircle::border::color}{border.color} depending on the property / state
+ \l {HoverHandler::hovered}{hovered} of the \l{HoverHandler}.
+
+
+ \section1 Adding new Items
+
+ A combination of \l {HoverHandler} and \l {TapHandler} for the \l {MapView} allows us to
+ react to mouse movements and clicks by the user.
+
+ If the \l{TapHandler} emits a \l{TapHandler::singleTapped}{singleTapped} signal, we will
+ create or modify a new MapItem on \l{Qt::LeftButton}{LeftButton} and finish the MapItem on
+ \l{Qt::RightButton}{RightButton}. If there is no item to finish then the
+ \l{Qt::RightButton}{RightButton} will open a menu.
+
+ \snippet geojson_viewer/main.qml Taphandler Map
+
+ The \l {HoverHandler::pointChanged}{pointChanged} signal is used to temporarily update a
+ MapItem, giving the user a preview.
+
+ \snippet geojson_viewer/main.qml Hoverhandler Map
+
+ Mapitems are generated from prototypes that are defined in separate qml files. They are created
+ using the \l{Qt::createComponent}{createComponent} function and added to the map with
+ \l {Map::addMapItem}{addMapItem}. A reference to the new item is stored for further manipulation
+ by the user.
+
+ \snippet geojson_viewer/main.qml add item
+
+
+ Adding the item to the \l {Map} is sufficient to display the item. However, in order to
+ further use the item (e.g. saving it to a file), it has has to be registered with the model.
+ This is done after editing is finished:
+
+ \snippet geojson_viewer/main.qml finish item
+
+ The class GeoJsoner converts the new item into a \l {QVariant} representation and inserts the
+ respective result into the existing \l {QVariant} representation of all items:
+
+ \snippet geojson_viewer/main.cpp add item
+
+
+ \section1 Removing Items
+
+ To remove all items from the map, we simply reset the model to an empty \l {QVariantList}.
+ This is possible because we registered all new items with the model and items not added to the
+ mode will not be affected. This is implemented in C++,
+
+ \snippet geojson_viewer/main.cpp clear
+
+ and executed from QML
+
+ \snippet geojson_viewer/main.qml clearAllItems
+*/