MyTetra Share
Делитесь знаниями!
Круг нержавеющий 34 40х13 в екатеринбурге apromgroup.ru/krug-nerzh.
Работа с картами в QML (перевод официальной документации Qt 5.10)
08.08.2018
16:35
Автор: Сергей Степанов AKA xintrea
Текстовые метки: qt, qml, карты, картография, документация, перевод, Map, QtPositioning, Location
Раздел: Компьютер - Программирование - Язык C++ - Библиотека Qt - Картография в Qt и QML

Карты в QML



Обзор


QML-тип Map позволяет отображать карту и размещать объекты на этой карте. Могут быть определены различные точки интереса и отображены на карте. Так же, тип Map имеет много возможностей по контролю за тем, как карта отображается на экране. С помощью элемента Map можно перемещать центр карты, увеличивать/уменьшать карту, сдвигаться и перемещаться над "поверхностью" карты.


На карту могут быть добавлены дополнительные элементы, называемые MapItems. Эти элементы позиционируются на карте через координаты, которые состоят из широты, долготы и высоты. Элемент начинает отображаться автоматически сразу после того, как он был добавлен в элемент Map.



Позиция на карте


Всё позиционирование на карте происходит с помощью API модуля QtPositioning. Основная часть информации о позиции - это координаты (coordinate). Одна единица координат включает в себя широту, долготу и высоту для одного местоположения. Высота измеряется в метрах. Имеется метод для определения дистанции до точки с другими координатами. Координаты могут храниться в элементе с типом Location, в котором так же содержится информация об ограничивающей площади для определения достаточной близости к географическому местоположению или к адресу.


Ниже приведен пример, который использует источник информации о местоположении (position source), и отображает карту так, чтобы в центре карты находилось текущее местоположение:



Rectangle {


import QtPositioning 5.2

import QtLocation 5.3

...


Map {

id: map

// initialize map

...

}


PositionSource {

onPositionChanged: {

// center the map on the current position

map.center = position.coordinate

}

}

}


Геокодирование (geocoding)


Геокодирование - это получение географических координат (широты и долготы) из другой географической информации о месте. Например, это может быть адрес. Обратное геокодирование также возможно, когда используется адрес для определения географических координат. Для выполнения геокодирования можно использовать тип GeocodeModel.


Следующий пример кода представляют собой небольшую часть компонента карты в примере Map Viewer (QML). Фрагмент демонстрирует объявление компонента GeocodeModel.


В фрагменте мы видим, что GeocodeModel содержит плагин и два обработчика сигналов. Один для отслеживания изменения статуса onStatusChanged, а другой для обновления центрирования объекта Map в слоте onLocationsChanged.



GeocodeModel {

id: geocodeModel

plugin: map.plugin

onStatusChanged: {

if ((status == GeocodeModel.Ready) || (status == GeocodeModel.Error))

map.geocodeFinished()

}

onLocationsChanged:

{

if (count == 1) {

map.center.latitude = get(0).coordinate.latitude

map.center.longitude = get(0).coordinate.longitude

}

}

}


MapItemView {

model: geocodeModel

delegate: pointDelegate

}



Функции геокодирования вызываются из кода более высокого уровня.


В следующем фрагменте показан объект Address, заполненный требуемыми параметрами:



Address {

id :fromAddress

street: "Sandakerveien 116"

city: "Oslo"

country: "Norway"

state : ""

postalCode: "0484"

}



Элемент типа Address позже используется в запросе у GeocodeModel геогерафических координат указанного места:



// send the geocode request

geocodeModel.query = fromAddress

geocodeModel.update()



Навигация


Очень важной функцией QML-типа Map является навигация из начального места в место назначения с использованием путевых точек (waypoints) для построения маршрута (route). Маршрут разбивается на серии сегментов. Конец каждого сегмента является вершиной (узлом), называемый "точкой манёвра". Сегменты содержат внутри себя информацию о времени и расстоянии до конца сегмента. Точки маневра содержат информацию о том, что делать дальше, т. е. как попасть в следующий сегмент, если таковой имеется. Таким образом, в точке маневра содержится навигационная информация, которую можно преобразовать в сообщение, например, «повернуть прямо сейчас».


Для поиска подходящего маршрута необходимо использовать тип RouteQuery, в котором задаются критерии выбора и добавляются любые необходимые путевые точки. Тип RouteModel возвращает список из элементов типа RouteSegment, которые определяют маршрут к месту назначения, с рекомендациями по навигации в соединениях между сегментами, представляемыме элементами типа RouteManeuvers (точки манёвра на построенном маршруте).


Есть много вариантов, которые можно добавить к запросу RouteQuery, чтобы сузить критерии построения маршрута. Свойства RouteQuery включают в себя:



numberAlternativeRoutes

Количество альтернативных маршрутов

travelModes

Режим перемещения

routeOptimizations

Оптимизации при построении маршрута

segmentDetail

Уровень детализации сегментов маршрута

maneuverDetail

Уровень детализации в точках манёвра между сегментами

waypoints

Список путевых точек

excludedAreas

Список исключенных областей, которые маршрут не должен пересекать

featureTypes

Различные типы дорог на карте, которые нужно учитывать. Например, скоростное шоссе, паром



В следующем примере для стандартного запроса RouteQuery описывается элемент RouteModel:



RouteModel {

id: routeModel

plugin : map.plugin

query: RouteQuery {

id: routeQuery

}

onStatusChanged: {

if (status == RouteModel.Ready) {

switch (count) {

case 0:

// technically not an error

map.routeError()

break

case 1:

map.showRouteList()

break

}

} else if (status == RouteModel.Error) {

map.routeError()

}

}

}



Пользовательский код сообщает элементу RouteQuery некоторую информацию, такую как стартовую точку маршрута, несколько путевых точек и место назначения. Все эти местоположения являются путевыми точками, поэтому маршрут от начала до конца будут введен в виде последовательности путевых точек. После чего задаются другие свойства запроса, которые могут быть специфичными для поездки:



// clear away any old data in the query

routeQuery.clearWaypoints();


// add the start and end coords as waypoints on the route

routeQuery.addWaypoint(startCoordinate)

routeQuery.addWaypoint(endCoordinate)

routeQuery.travelModes = RouteQuery.CarTravel

routeQuery.routeOptimizations = RouteQuery.FastestRoute


routeModel.update();



Элемент routeInfoModel с QML-типом ListModel используется для получения результата запроса и создания подходящего списка для отображения маршрута:



ListView {

interactive: true

model: ListModel { id: routeInfoModel }

header: RouteListHeader {}

delegate: RouteListDelegate{

routeIndex.text: index + 1

routeInstruction.text: instruction

routeDistance.text: distance

}

}



Элемент routeInfoModel с QML-типом ListModel будет заполнен значения, которые можно обработать с помощью кода, который будет в цикле перебирать сегменты, получая длину сегмента, текст инструкции и расстояние до следующей инструкции. Полученные данные будут отображаться на экране по мере их получения:



routeInfoModel.clear()

if (routeModel.count > 0) {

for (var i = 0; i < routeModel.get(0).segments.length; i++) {

routeInfoModel.append({

"instruction": routeModel.get(0).segments[i].maneuver.instructionText,

"distance": Helper.formatDistance(routeModel.get(0).segments[i].maneuver.distanceToNextInstruction)

});

}

}



Для более подробной инфомции можно обратиться к примеру Map Viewer (QML).




Масштабирование (zoom), щепок (pinch) и панорамирование (flickable)


Элемент Map поддерживает стандартный пользовательский интерфейс в плане жестов пальцами и жестов мышкой. Это такие возможности как: прокрутка для панорамирования, щепок для уменьшения/увеличения, и т. д.


Включение/выключение щипков и прокрутки делается в типе Map достаточно просто:



Map {

id: map

// Enable pan, flick, and pinch gestures to zoom in and out

gesture.acceptedGestures: MapGestureArea.PanGesture | MapGestureArea.FlickGesture | MapGestureArea.PinchGesture | MapGestureArea.RotationGesture | MapGestureArea.TiltGesture

gesture.flickDeceleration: 3000

gesture.enabled: true

}



Масштаб может контролироваться и с помощью других объектов, таких как слайдер, который связывается с полем zoomLevel объекта типа Map.



Перечень QML-типов, используемых при работе с картами



Картография



MapCircle

Тип для отображения кругов на карте

Map

Тип, отображающий карту

MapCopyrightNotice

Тип для элемента, отображающего информацию о правообладателе на поверхности элемента типа Map

MapItemGroup

Тип для контейнера с элементами, размещаемыми на карте

MapItemView

Тип, используемый для отображения элементов, размещаемых на карте, получаемых через модель

MapParameter

Тип, представляющий из себя параметр для элемента Map. Значение параметров этого типа зависит от типа плагина, используемого для отображения карты

MapQuickItem

Тип для отображения произвольного Qt Quick объекта на карте

CameraCapabilities

Тип, содержащий информацию о возможностях виртуальной камеры, которая используется для отображения определенного типа карты

MapType

Тип, содержащий информацию о типе карты

MapPolygon

Тип для отрисовки произвольного, залитого цветом, многоугольника (polygon) на поверхности карты

MapPolyline

Тип для отрисовки произвольной ломанной линии (polyline) на поверхности карты

MapRectangle

Тип для отрисовки прямоугольника на поверхности карты

MapRoute

Тип для отрисовки маршрута на поверхности карты

MapGestureArea

Тип для определения области, которая отлавливает управляющие жесты для карты

MapPinchEvent

Тип, представляющий базовую информацию о событии "щипка"


Геокодирование


GeocodeModel

Тип обеспечивает поддержку поиска операций, применяемых относительно географической информации


Построение маршрута


RouteManeuver

Тип представляет информацию о точке, которая находится между двумя сегментами RouteSegments

Route

Тип для представления географического маршрута

RouteModel

Тип модели данных о маршруте

RouteQuery

Тип, использующийся для предоставления параметров запроса в RouteModel

RouteSegment

Тип, представляющий собой сегмент маршрута




 
MyTetra Share v.0.52
Яндекс индекс цитирования