Places Backend
Обзор
Интерфейс QPlaceManager, предоставляемый клиентам для доступа к информации о местах, напрямую зависит от реализации QPlaceManagerEngine. Движок предоставляет реализации функций бэкэнда, которые вызываются менеджером.
Реализатор бэкэнда мест должен быть производным от QPlaceManagerEngine и предоставить реализации виртуальных функций, относящихся к их бэкэнду. Большинство этих функций асинхронные, поэтому реализаторы также должны быть производными от соответствующих классов ответов. Объекты ответов отвечают за управление асинхронным запросом; они используются для уведомления о завершении запроса и хранения результатов этого запроса. QPlaceManagerEngine предоставляет реализацию по умолчанию для всех виртуальных функций. Реализации по умолчанию для асинхронных функций возвращают ответ, который будет излучать сигналы error() и finished() на следующей итерации цикла событий.
Реализация/Наследование объектов ответов
Объект ответа будет унаследован следующим образом:
class SearchReply : public QPlaceSearchReply
{
public:
explicit SearchReply(ManagerEngine *engine)
: QPlaceSearchReply(engine), m_engine(engine){}
~SearchReply();
void setResults(const QList<QPlaceSearchResult> &results);
void setRequest(const QPlaceSearchRequest &request);
...
void triggerDone(QPlaceReply::Error error = QPlaceReply::NoError,
const QString &errorString = QString());
ManagerEngine *m_engine;
}; Реализация QPlaceManagerEngine должна гарантировать, что любые сигналы, излучаемые объектами ответов, задерживаются до тех пор, пока функции запроса не вернутся, и код приложения имеет возможность подключить эти сигналы к слотам. Типичный подход заключается в использовании QMetaObject::invokeMethod() с Qt::QueuedConnection для излучения сигналов.
void SearchSuggestionReply::triggerDone(QPlaceReply::Error error,
const QString &errorString)
{
if (error != QPlaceReply::NoError) {
this->setError(error,errorString);
QMetaObject::invokeMethod(m_engine, "error", Qt::QueuedConnection,
Q_ARG(QPlaceReply *,this),
Q_ARG(QPlaceReply::Error, error),
Q_ARG(QString, errorString));
QMetaObject::invokeMethod(this, "error", Qt::QueuedConnection,
Q_ARG(QPlaceReply::Error, error),
Q_ARG(QString, errorString));
}
this->setFinished(true);
QMetaObject::invokeMethod(m_engine, "finished", Qt::QueuedConnection,
Q_ARG(QPlaceReply *,this));
QMetaObject::invokeMethod(this, "finished", Qt::QueuedConnection);
} Обратите внимание, что finished сигналы должны всегда излучаться при завершении ответа, даже если возникла ошибка. То есть, если есть ошибка, оба error и finished сигнала должны излучаться, а если ошибки нет, то излучаются только finished сигналы.
Защищенные функции QPlaceSearchReply::setResults() и QPlaceSearchReply::setRequest() сделаны общедоступными, чтобы плагин мог назначать результаты и запросы. Поскольку эти функции не экспортируются публично, вопрос доступности не столь актуален. Альтернативой было бы объявление дружественного класса в SearchReply.
Обычно экземпляр движка является parent объекта ответа. Если разработчик не удаляет ответы при завершении, движок может очистить их при уничтожении. Обычно у ответа также есть ссылка на указатель обратно на движок, который может использоваться для излучения сигналов QPlaceManagerEngine::finished() и QPlaceManagerEngine::error(). Это всего лишь один из многих способов реализации ответа.
URL-адреса значков
URL-адреса значков предоставляются через функцию QPlaceManagerEngine::constructIconUrl(). Ожидаемое поведение заключается в том, что движок будет использовать QPlaceIcon::parameters() для построения соответствующего URL-адреса. Когда объект QPlace возвращается менеджером, либо из поиска, либо из запроса для получения подробностей о месте, ожидается, что движок будет правильно заполнять параметры по мере необходимости.
Бэкенд свободен выбирать ключи и значения параметров, однако, если у бэкэнда есть только один URL-адрес на значок, рекомендуется использовать QPlaceIcon::SingleUrl в качестве ключа.
Категории
Категории движка менеджера — это относительно статические сущности; для движков, которые обращаются к удалённым хранилищам данных о местах, может быть целесообразно кешировать структуру категорий, а не запрашивать сервер каждый раз, когда вызывается QPlaceManagerEngine::initializeCategories(). В зависимости от того, насколько динамичны категории, возможно, более целесообразно всегда загружать самую свежую совокупность категорий.
Сохранение мест в менеджере
Место обычно нельзя сохранить напрямую между менеджерами, так как оно содержит данные, специфичные для менеджера, такие как значки и категории. Для облегчения сохранения в собственном менеджере реализаторы движка должны реализовать функцию QPlaceManagerEngine::compatiblePlace(). Эта функция возвращает копию входного места с обрезанными или изменёнными свойствами, так что копию можно сохранить в менеджер.
Создание совместимого места может включать игнорирование определённых свойств из исходного места, например, если контактные данные не поддерживаются, они опускаются в совместимом месте. В других случаях это может включать изменение определённых свойств, например, изменение параметров значка для облегчения копирования или загрузки значка исходного места в местоположение, к которому может получить доступ бэкенд.
Перекрёстная ссылка мест между менеджерами
Иногда может возникнуть ситуация, когда нам нужно перекрёстно ссылаться и сопоставлять места между менеджерами. Такая ситуация может возникнуть, когда один менеджер предоставляет только чтение к местам (исходный менеджер), а другой менеджер чтение/запись (менеджер назначения) используется для сохранения выбранных избранных мест из первого. При поиске в исходном менеджере мы можем захотеть узнать, какие из них были помечены как избранные в менеджер назначения, и, возможно, отобразить изменённое имя избранного, а не исходное.
Перекрёстная ссылка по альтернативному идентификатору
Для выполнения перекрёстной ссылки необходима связь между исходным местом и избранным местом, и это обычно обрабатывается через атрибут альтернативного идентификатора. Избранное место содержит атрибут альтернативного идентификатора, который имеет идентификатор исходного места.
origin R/O manager(here) destination R/W manager (places_jsondb)
Save
Place id: ae246 ---> Place id: 0001
Attribute type: x_provider Attribute type: x_id_here
Attribute value: here Attribute text value: ae246 Для реализации перекрёстной ссылки по альтернативному идентификатору существуют 3 предварительных условия. Первое — исходный менеджер должен предоставить атрибут x_provider со значением, являющимся именем QGeoServiceProvider менеджера. Метка атрибута должна оставаться пустой, указывая, что атрибут не должен отображаться пользователям.
Примечание: Обычно ожидается, что все менеджеры должны установить атрибут x_provider.
Второе — функция QPlaceManager::compatiblePlace менеджера назначения должна использовать атрибут x_provider исходного места и установить атрибут альтернативного идентификатора сохраняемого места. Ключом атрибута альтернативного идентификатора является x_id_<provider name>, а текстовым значением является идентификатор исходного места. Атрибут x_provider не должен передаваться в совместимое место. При сохранении x_provider сохранённого места считается менеджером назначения.
Третье — функция QPlaceManager::matchingPlaces менеджера назначения должна принимать QPlaceMatchRequest::AlternativeId в качестве параметра ключа и ключ атрибута альтернативного идентификатора в качестве значения, в этом случае x_id_<provider name> будет ожидаемым значением. Это указывает, что идентификаторы мест в QPlaceMatchRequest должны быть сопоставлены с атрибутами альтернативного идентификатора x_id_<provider name>.
Обратите внимание, что если менеджер назначения должен облегчить сохранение и перекрёстную ссылку из любого произвольного менеджера, он внутренне должен поддерживать сохранение произвольных пар ключ-значение, поскольку мы не можем знать имена поставщиков заранее, а также мы не можем знать, какой структурой будут идентификаторы.
Другие методы связи
Если исходный менеджер не предоставляет идентификатор места, может потребоваться предоставить какой-либо другой способ перекрёстной ссылки/сопоставления. Один подход может заключаться в использовании координат места, если координаты места в исходном менеджере идентичны или близки к координатам места в менеджере назначения, высока вероятность, что это одно и то же место. В этом случае менеджер может реализовать QPlaceManager::matchingPlaces() для принятия QPlaceMatchRequest с параметром ключа 'proximity' и значением параметра — расстоянием, на котором два места должны быть, чтобы определить совпадение. Например, если исходное место и место назначения находятся в пределах 50 м друг от друга, их можно считать одним и тем же местом.
Однако, как правило, рекомендуется реализовать перекрёстную ссылку через альтернативные идентификаторы, как описано выше.
Атрибуты, читаемые пользователем, и нечитаемые пользователем расширенные атрибуты
Если атрибут не предназначен для чтения конечными пользователями, поле метки следует оставлять пустым, как индикатор этого факта.
© The Qt Company Ltd
Licensed under the GNU Free Documentation License, Version 1.3.
https://doc.qt.io/archives/qt-5.6/location-places-backend.html