Show predefined popups from a web map.

Use case
Many web maps contain predefined popups which are used to display the attributes associated with each feature layer in the map, such as hiking trails, land values, or unemployment rates. You can display text, attachments, images, charts, and web links. Rather than creating new popups to display information, you can easily access and display the predefined popups.
How to use the sample
Tap on the features to prompt a popup that displays information about the feature.
How it works
- Create and load a
Mapusing a URL. - Set the map to a
MapViewand connect to theMapQuickView::mouseClickedsignal. - Use
GeoView::identifyLayer(layer, x, y, tolerance, allowPopupsOnly, maximumResults)to identify features. - Create a
PopupManagerfor each of the result’sPopups and append them to a list. - Assign the list of popup managers to the
PopupStackView.popupManagersproperty. - Display the popup stack view.
Relevant API
- IdentifyLayerResult
- Map
- PopupManager
- PopupStackView
About the data
This sample uses a feature layer that displays reported incidents in San Francisco.
Additional information
In order to use the PopupManager with a QML UI, the PopupManager, PopupAttachmentManager, PopupAttachmentListModel, and PopupAttributeListModel classes must be registered as QML Types. For more information visit our developer site.
Tags
feature, feature layer, popup, web map
Sample Code
// [WriteFile Name=ShowPopup, Category=DisplayInformation]// [Legal]// Copyright 2020 Esri.//// Licensed under the Apache License, Version 2.0 (the "License");// you may not use this file except in compliance with the License.// You may obtain a copy of the License at// http://www.apache.org/licenses/LICENSE-2.0//// Unless required by applicable law or agreed to in writing, software// distributed under the License is distributed on an "AS IS" BASIS,// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.// See the License for the specific language governing permissions and// limitations under the License.// [Legal]
#ifdef PCH_BUILD#include "pch.hpp"#endif // PCH_BUILD
// sample headers#include "ShowPopup.h"
// ArcGIS Maps SDK headers#include "Error.h"#include "Feature.h"#include "FeatureLayer.h"#include "IdentifyLayerResult.h"#include "LayerListModel.h"#include "Map.h"#include "MapQuickView.h"#include "MapTypes.h"#include "Popup.h"
// Qt headers#include <QUuid>
using namespace Esri::ArcGISRuntime;
ShowPopup::ShowPopup(QObject* parent /* = nullptr */): QObject(parent), m_map(new Map(QUrl("https://runtime.maps.arcgis.com/home/webmap/viewer.html?webmap=e4c6eb667e6c43b896691f10cc2f1580"), this)){}
ShowPopup::~ShowPopup() = default;
void ShowPopup::init(){ // Register the map view for QML qmlRegisterType<MapQuickView>("Esri.Samples", 1, 0, "MapView"); qmlRegisterType<ShowPopup>("Esri.Samples", 1, 0, "ShowPopupSample");}
MapQuickView* ShowPopup::mapView() const{ return m_mapView;}
// Set the view (created in QML)void ShowPopup::setMapView(MapQuickView* mapView){ if (!mapView || mapView == m_mapView) return;
m_mapView = mapView; m_mapView->setMap(m_map);
// once map is set, connect to MapQuickView mouse clicked signal connect(m_mapView, &MapQuickView::mouseClicked, this, &ShowPopup::onMouseClicked);
emit mapViewChanged();}
void ShowPopup::onIdentifyLayerCompleted(const QUuid&, IdentifyLayerResult* rawIdentifyResult){ emit taskRunningChanged(); auto identifyResult = std::unique_ptr<IdentifyLayerResult>(rawIdentifyResult);
// Invalid identify result if (!identifyResult) return;
if (!identifyResult->error().isEmpty()) { qDebug() << "Identify error occurred: " << identifyResult->error().message(); return; }
m_featureLayer->clearSelection(); if (!identifyResult->popups().isEmpty()) { GeoElement* geoElement = identifyResult->geoElements().first(); Feature* feature = static_cast<Feature*>(geoElement); m_featureLayer->selectFeature(feature);
m_popup = new Popup(geoElement, this); emit popupChanged(); }}
void ShowPopup::onMouseClicked(QMouseEvent& mouseEvent){ if (m_map->loadStatus() != LoadStatus::Loaded) return;
Layer* layer = m_map->operationalLayers()->at(0); if (layer->layerType() == LayerType::FeatureLayer) { m_featureLayer = static_cast<FeatureLayer*>(layer); }
constexpr double tolerance = 12; constexpr bool returnPopupsOnly = false; constexpr int maximumResults = 10;
m_future = m_mapView->identifyLayerAsync(m_featureLayer, mouseEvent.position(), tolerance, returnPopupsOnly, maximumResults); m_future.then(this, [this](IdentifyLayerResult* result) { onIdentifyLayerCompleted(QUuid(),result); });
if (!m_future.isValid()) qWarning() << "Future not valid.";
emit taskRunningChanged();}
bool ShowPopup::taskRunning() const{ return m_future.isRunning();}
void ShowPopup::clearSelection() const{ m_featureLayer->clearSelection();}// [WriteFile Name=ShowPopup, Category=DisplayInformation]// [Legal]// Copyright 2020 Esri.//// Licensed under the Apache License, Version 2.0 (the "License");// you may not use this file except in compliance with the License.// You may obtain a copy of the License at// http://www.apache.org/licenses/LICENSE-2.0//// Unless required by applicable law or agreed to in writing, software// distributed under the License is distributed on an "AS IS" BASIS,// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.// See the License for the specific language governing permissions and// limitations under the License.// [Legal]
#ifndef SHOWPOPUP_H#define SHOWPOPUP_H
// Qt headers#include <QFuture>#include <QMouseEvent>#include <QObject>#include <QQmlListProperty>#include <QUuid>
namespace Esri::ArcGISRuntime{class FeatureLayer;class GeoElement;class IdentifyLayerResult;class Map;class MapQuickView;class Popup;}
Q_MOC_INCLUDE("MapQuickView.h")Q_MOC_INCLUDE("Popup.h")
class ShowPopup : public QObject{ Q_OBJECT
Q_PROPERTY(Esri::ArcGISRuntime::MapQuickView* mapView READ mapView WRITE setMapView NOTIFY mapViewChanged) Q_PROPERTY(Esri::ArcGISRuntime::Popup* popup MEMBER m_popup NOTIFY popupChanged) Q_PROPERTY(bool taskRunning READ taskRunning NOTIFY taskRunningChanged)
public: explicit ShowPopup(QObject* parent = nullptr); ~ShowPopup();
static void init();
Q_INVOKABLE void clearSelection() const;
signals: void mapViewChanged(); void popupChanged(); void taskRunningChanged();
private slots: void onMouseClicked(QMouseEvent& mouseEvent); void onIdentifyLayerCompleted(const QUuid&, Esri::ArcGISRuntime::IdentifyLayerResult* rawIdentifyResult);
private: bool taskRunning() const; Esri::ArcGISRuntime::MapQuickView* mapView() const; void setMapView(Esri::ArcGISRuntime::MapQuickView* mapView);
Esri::ArcGISRuntime::Map* m_map = nullptr; Esri::ArcGISRuntime::MapQuickView* m_mapView = nullptr; Esri::ArcGISRuntime::Popup* m_popup = nullptr; Esri::ArcGISRuntime::FeatureLayer* m_featureLayer = nullptr;
QFuture<Esri::ArcGISRuntime::IdentifyLayerResult*> m_future;};
#endif // SHOWPOPUP_H// [WriteFile Name=ShowPopup, Category=DisplayInformation]// [Legal]// Copyright 2020 Esri.//// Licensed under the Apache License, Version 2.0 (the "License");// you may not use this file except in compliance with the License.// You may obtain a copy of the License at// http://www.apache.org/licenses/LICENSE-2.0//// Unless required by applicable law or agreed to in writing, software// distributed under the License is distributed on an "AS IS" BASIS,// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.// See the License for the specific language governing permissions and// limitations under the License.// [Legal]
import QtQuickimport QtQuick.Controlsimport Esri.Samplesimport Esri.ArcGISRuntime.Toolkit
Item {
// add a mapView component MapView { id: view anchors.fill: parent
Component.onCompleted: { // Set the focus on MapView to initially enable keyboard navigation forceActiveFocus(); } }
PopupView { id: popupView anchors { top: parent.top bottom: parent.bottom right: parent.right } popup: model.popup
visible: false
onVisibleChanged: { if (!visible) model.clearSelection(); } }
// Declare the C++ instance which creates the map etc. and supply the view ShowPopupSample { id: model mapView: view
onPopupChanged: popupView.visible = true }
BusyIndicator { anchors.centerIn: parent running: model.taskRunning }}// [Legal]// Copyright 2020 Esri.//// Licensed under the Apache License, Version 2.0 (the "License");// you may not use this file except in compliance with the License.// You may obtain a copy of the License at// http://www.apache.org/licenses/LICENSE-2.0//// Unless required by applicable law or agreed to in writing, software// distributed under the License is distributed on an "AS IS" BASIS,// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.// See the License for the specific language governing permissions and// limitations under the License.// [Legal]
// sample headers#include "ShowPopup.h"
// ArcGIS Maps SDK headers#include "ArcGISRuntimeEnvironment.h"
// Qt headers#include <QDir>#include <QGuiApplication>#include <QQmlApplicationEngine>
// Other headers#include "Esri/ArcGISRuntime/Toolkit/register.h"
// Platform specific headers#ifdef Q_OS_WIN#include <Windows.h>#endif
int main(int argc, char *argv[]){ Esri::ArcGISRuntime::ArcGISRuntimeEnvironment::setUseLegacyAuthentication(false); QGuiApplication app(argc, argv); app.setApplicationName(QString("ShowPopup"));
// Use of ArcGIS location services, such as basemap styles, geocoding, and routing services, // requires an access token. For more information see // https://links.esri.com/arcgis-runtime-security-auth.
// The following methods grant an access token:
// 1. User authentication: Grants a temporary access token associated with a user's ArcGIS account. // To generate a token, a user logs in to the app with an ArcGIS account that is part of an // organization in ArcGIS Online or ArcGIS Enterprise.
// 2. API key authentication: Get a long-lived access token that gives your application access to // ArcGIS location services. Go to the tutorial at https://links.esri.com/create-an-api-key. // Copy the API Key access token.
const QString accessToken = QString("");
if (accessToken.isEmpty()) { qWarning() << "Use of ArcGIS location services, such as the basemap styles service, requires" << "you to authenticate with an ArcGIS account or set the API Key property."; } else { Esri::ArcGISRuntime::ArcGISRuntimeEnvironment::setApiKey(accessToken); }
// Initialize the sample ShowPopup::init();
// Initialize application view QQmlApplicationEngine engine; // Add the import Path engine.addImportPath(QDir(QCoreApplication::applicationDirPath()).filePath("qml"));
#ifdef ARCGIS_RUNTIME_IMPORT_PATH_2 engine.addImportPath(ARCGIS_RUNTIME_IMPORT_PATH_2);#endif
Esri::ArcGISRuntime::Toolkit::registerComponents(engine);
// Set the source engine.load(QUrl("qrc:/Samples/DisplayInformation/ShowPopup/main.qml"));
return app.exec();}// Copyright 2020 Esri.
// Licensed under the Apache License, Version 2.0 (the "License");// you may not use this file except in compliance with the License.// You may obtain a copy of the License at// http://www.apache.org/licenses/LICENSE-2.0
// Unless required by applicable law or agreed to in writing, software// distributed under the License is distributed on an "AS IS" BASIS,// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.// See the License for the specific language governing permissions and// limitations under the License.
import QtQuick.Controlsimport Esri.Samples
ApplicationWindow { id: appWindow visible: true width: 800 height: 600
ShowPopup { anchors.fill: parent }}