Perform a viewshed analysis from a defined vantage point.

Use case
A 3D viewshed analysis is a type of visual analysis you can perform on a scene. The viewshed shows what can be seen from a given location. The output is an overlay with two different colors - one representing the visible areas (green) and the other representing the obstructed areas (red). Viewshed analysis is a form of “exploratory analysis”, which means the results are calculated on the current scale of the data, and the results are generated very quickly. If more “conclusive” results are required, consider using a GeoprocessingTask to perform a viewshed instead.
How to use the sample
Use the sliders to change the properties (heading, pitch, etc.), of the viewshed and see them updated in real time. To move the viewshed, double touch and drag your finger across the screen. Lift your finger to stop moving the viewshed.
How it works
- Create a
LocationViewshedpassing in the observer location, heading, pitch, horizontal/vertical angles, and min/max distances. - Set the property values on the viewshed instance for location, direction, range, and visibility properties.
Relevant API
- AnalysisOverlay
- ArcGISSceneLayer
- ArcGISTiledElevationSource
- LocationViewshed
- Viewshed
About the data
The scene shows a buildings layer in Brest, France hosted on ArcGIS Online.
Tags
3D, frustum, scene, viewshed, visibility analysis
Sample Code
// [WriteFile Name=ViewshedLocation, Category=Analysis]// [Legal]// Copyright 2018 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 QtQuick.Layouts
Dialog { id: colorDialog property alias red: redSlider.value property alias green: greenSlider.value property alias blue: blueSlider.value property alias alpha: alphaSlider.value readonly property color color: Qt.rgba(red, green, blue, alpha);
title: "Pick a color" standardButtons: Dialog.Ok | Dialog.Cancel
function setColor(c) { red = c.r; green = c.g; blue = c.b; alpha = c.a; }
GridLayout { columns: 2 Rectangle { Layout.columnSpan: 2 Layout.fillWidth: true height: redSlider.height border { color: "black" width: 1 } radius: 2 color: colorDialog.color }
Text { text: "Red" }
Slider { id: redSlider }
Text { text: "Green" }
Slider { id: greenSlider }
Text { text: "Blue" }
Slider { id: blueSlider }
Text { text: "Alpha" }
Slider { id: alphaSlider } }}// [WriteFile Name=ViewshedLocation, Category=Analysis]// [Legal]// Copyright 2017 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 "ViewshedLocation.h"
// ArcGIS Maps SDK headers#include "AnalysisListModel.h"#include "AnalysisOverlay.h"#include "AnalysisOverlayListModel.h"#include "ArcGISTiledElevationSource.h"#include "Camera.h"#include "ElevationSourceListModel.h"#include "LocationViewshed.h"#include "MapTypes.h"#include "Point.h"#include "Scene.h"#include "SceneQuickView.h"#include "SpatialReference.h"#include "Surface.h"
// Qt headers#include <QFuture>
using namespace Esri::ArcGISRuntime;
ViewshedLocation::ViewshedLocation(QQuickItem* parent /* = nullptr */): QQuickItem(parent){}
void ViewshedLocation::init(){ // Register classes for QML qmlRegisterType<SceneQuickView>("Esri.Samples", 1, 0, "SceneView"); qmlRegisterType<ViewshedLocation>("Esri.Samples", 1, 0, "ViewshedLocationSample");}
void ViewshedLocation::componentComplete(){ QQuickItem::componentComplete();
// Create a scene and give it to the SceneView m_sceneView = findChild<SceneQuickView*>("sceneView");
Scene* scene = new Scene(BasemapStyle::ArcGISTopographic, this); Surface* surface = new Surface(this); surface->elevationSources()->append( new ArcGISTiledElevationSource( QUrl("https://elevation3d.arcgis.com/arcgis/rest/services/WorldElevation3D/Terrain3D/ImageServer"), this)); scene->setBaseSurface(surface); m_sceneView->setArcGISScene(scene);
// Add an Analysis Overlay m_analysisOverlay = new AnalysisOverlay(this); m_sceneView->analysisOverlays()->append(m_analysisOverlay);
// set initial viewpoint setInitialViewpoint();
// connect signals connectSignals();}
void ViewshedLocation::setInitialViewpoint(){ // Set a viewpoint double x = 6.86088; double y = 45.3604; double z = 3582.55; Point point(x, y, z, SpatialReference(4326)); double heading = 345; double pitch = 70; double roll = 0; Camera camera(point, heading, pitch, roll); m_sceneView->setViewpointCameraAsync(camera);}
void ViewshedLocation::connectSignals(){ // on mouse click perform the location viewshed connect(m_sceneView, &SceneQuickView::mouseClicked, this, [this](QMouseEvent& event) { if (!m_locationViewshed) createViewshed(event.position().x(), event.position().y()); else { const Point pt = m_sceneView->screenToBaseSurface(event.position().x(), event.position().y()); m_locationViewshed->setLocation(pt); } });
connect(m_sceneView, &SceneQuickView::mousePressedAndHeld, this, [this](QMouseEvent& event) { if (!m_locationViewshed) createViewshed(event.position().x(), event.position().y());
m_calculating = true; });
connect(m_sceneView, &SceneQuickView::mouseMoved, this, [this](QMouseEvent& event) { if (m_calculating) { const Point pt = m_sceneView->screenToBaseSurface(event.position().x(), event.position().y()); m_locationViewshed->setLocation(pt); } });
connect(m_sceneView, &SceneQuickView::mouseReleased, this, [this] { m_calculating = false; });}
void ViewshedLocation::createViewshed(double x, double y){ const Point pt = m_sceneView->screenToBaseSurface(x, y);
// Create the Location Viewshed m_locationViewshed = new LocationViewshed(pt, m_heading, m_pitch, m_horizontalAngle, m_veriticalAngle, m_minDistance, m_maxDistance, this); m_locationViewshed->setVisible(m_viewshedVisible);
// Add the Viewshed to the Analysis Overlay m_analysisOverlay->analyses()->append(m_locationViewshed);
return;}
// Getters/Setters for each Q_PROPERTYbool ViewshedLocation::isViewshedVisible() const{ return m_viewshedVisible;}
void ViewshedLocation::setViewshedVisible(bool viewshedVisible){ if (m_locationViewshed) { if (m_locationViewshed->isVisible() == viewshedVisible) return;
m_viewshedVisible = viewshedVisible; m_locationViewshed->setVisible(viewshedVisible); } else { if (m_viewshedVisible == viewshedVisible) return;
m_viewshedVisible = viewshedVisible; }
emit viewshedVisibleChanged();}
bool ViewshedLocation::isFrustumOutlineVisible() const{ return m_locationViewshed ? m_locationViewshed->isFrustumOutlineVisible() : m_frustumVisible;}
void ViewshedLocation::setFrustumOutlineVisible(bool frustumVisible){ if (m_locationViewshed) { if (m_locationViewshed->isFrustumOutlineVisible() == frustumVisible) return;
m_frustumVisible = frustumVisible; m_locationViewshed->setFrustumOutlineVisible(frustumVisible); } else { if (m_frustumVisible == frustumVisible) return;
m_frustumVisible = frustumVisible; }
emit frustumVisibleChanged();}
double ViewshedLocation::minDistance() const{ return m_locationViewshed ? m_locationViewshed->minDistance() : m_minDistance;}
void ViewshedLocation::setMinDistance(double minDistance){ if (m_locationViewshed) { if (m_locationViewshed->minDistance() == minDistance) return;
m_minDistance = minDistance; m_locationViewshed->setMinDistance(minDistance); } else { if (m_minDistance == minDistance) return;
m_minDistance = minDistance; }
emit minDistanceChanged();}
double ViewshedLocation::maxDistance() const{ return m_locationViewshed ? m_locationViewshed->maxDistance() : m_maxDistance;}
void ViewshedLocation::setMaxDistance(double maxDistance){ m_maxDistance = maxDistance;
if (m_locationViewshed) { if (m_locationViewshed->maxDistance() == maxDistance) return;
m_maxDistance = maxDistance; m_locationViewshed->setMaxDistance(maxDistance); } else { if (m_maxDistance == maxDistance) return;
m_maxDistance = maxDistance; }
emit maxDistanceChanged();}
double ViewshedLocation::horizontalAngle() const{ return m_locationViewshed ? m_locationViewshed->horizontalAngle() : m_horizontalAngle;}
void ViewshedLocation::setHorizontalAngle(double horizontalAngle){ if (m_locationViewshed) { if (m_locationViewshed->horizontalAngle() == horizontalAngle) return;
m_horizontalAngle = horizontalAngle; m_locationViewshed->setHorizontalAngle(horizontalAngle); } else { if (m_horizontalAngle == horizontalAngle) return;
m_horizontalAngle = horizontalAngle; }
emit horizontalAngleChanged();}
double ViewshedLocation::verticalAngle() const{ return m_locationViewshed ? m_locationViewshed->verticalAngle() : m_veriticalAngle;}
void ViewshedLocation::setVerticalAngle(double verticalAngle){ if (m_locationViewshed) { if (m_locationViewshed->verticalAngle() == verticalAngle) return;
m_veriticalAngle = verticalAngle; m_locationViewshed->setVerticalAngle(verticalAngle); } else { if (m_veriticalAngle == verticalAngle) return;
m_veriticalAngle = verticalAngle; }
emit verticalAngleChanged();}
double ViewshedLocation::heading() const{ return m_locationViewshed ? m_locationViewshed->heading() : m_heading;}
void ViewshedLocation::setHeading(double heading){ if (m_locationViewshed) { if (m_locationViewshed->heading() == heading) return;
m_heading = heading; m_locationViewshed->setHeading(heading); } else { if (m_heading == heading) return;
m_heading = heading; }
emit headingChanged();}
double ViewshedLocation::pitch() const{ return m_locationViewshed ? m_locationViewshed->pitch() : m_pitch;}
void ViewshedLocation::setPitch(double pitch){ if (m_locationViewshed) { if (m_locationViewshed->pitch() == pitch) return;
m_pitch = pitch; m_locationViewshed->setPitch(pitch); } else { if (m_pitch == pitch) return;
m_pitch = pitch; }
emit pitchChanged();}
QColor ViewshedLocation::visibleColor() const{ return LocationViewshed::visibleColor();}
void ViewshedLocation::setVisibleColor(const QColor& visibleColor){ if (LocationViewshed::visibleColor() == visibleColor) return;
LocationViewshed::setVisibleColor(visibleColor);
emit visibleColorChanged();}
QColor ViewshedLocation::obstructedColor() const{ return LocationViewshed::obstructedColor();}
void ViewshedLocation::setObstructedColor(const QColor& obstructedColor){ if (LocationViewshed::obstructedColor() == obstructedColor) return;
LocationViewshed::setObstructedColor(obstructedColor);
emit obstructedColorChanged();}// [WriteFile Name=ViewshedLocation, Category=Analysis]// [Legal]// Copyright 2017 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 VIEWSHEDLOCATION_H#define VIEWSHEDLOCATION_H
// Qt headers#include <QColor>#include <QQuickItem>
namespace Esri::ArcGISRuntime{class SceneQuickView;class LocationViewshed;class AnalysisOverlay;}
class ViewshedLocation : public QQuickItem{ Q_OBJECT
public: explicit ViewshedLocation(QQuickItem* parent = nullptr); ~ViewshedLocation() override = default;
void componentComplete() override; static void init();
Q_PROPERTY(bool viewshedVisible READ isViewshedVisible WRITE setViewshedVisible NOTIFY viewshedVisibleChanged) Q_PROPERTY(bool frustumVisible READ isFrustumOutlineVisible WRITE setFrustumOutlineVisible NOTIFY frustumVisibleChanged) Q_PROPERTY(double minDistance READ minDistance WRITE setMinDistance NOTIFY minDistanceChanged) Q_PROPERTY(double maxDistance READ maxDistance WRITE setMaxDistance NOTIFY maxDistanceChanged) Q_PROPERTY(double horizontalAngle READ horizontalAngle WRITE setHorizontalAngle NOTIFY horizontalAngleChanged) Q_PROPERTY(double verticalAngle READ verticalAngle WRITE setVerticalAngle NOTIFY verticalAngleChanged) Q_PROPERTY(double heading READ heading WRITE setHeading NOTIFY headingChanged) Q_PROPERTY(double pitch READ pitch WRITE setPitch NOTIFY pitchChanged) Q_PROPERTY(QColor visibleColor READ visibleColor WRITE setVisibleColor NOTIFY visibleColorChanged) Q_PROPERTY(QColor obstructedColor READ obstructedColor WRITE setObstructedColor NOTIFY obstructedColorChanged)
bool isViewshedVisible() const; void setViewshedVisible(bool viewshedVisible);
bool isFrustumOutlineVisible() const; void setFrustumOutlineVisible(bool frustumVisible);
double minDistance() const; void setMinDistance(double minDistance);
double maxDistance() const; void setMaxDistance(double maxDistance);
double horizontalAngle() const; void setHorizontalAngle(double horizontalAngle);
double verticalAngle() const; void setVerticalAngle(double verticalAngle);
double heading() const; void setHeading(double heading);
double pitch() const; void setPitch(double pitch);
QColor visibleColor() const; void setVisibleColor(const QColor& visibleColor);
QColor obstructedColor() const; void setObstructedColor(const QColor& obstructedColor);
signals: void viewshedVisibleChanged(); void frustumVisibleChanged(); void minDistanceChanged(); void maxDistanceChanged(); void horizontalAngleChanged(); void verticalAngleChanged(); void headingChanged(); void pitchChanged(); void visibleColorChanged(); void obstructedColorChanged();
private: void connectSignals(); void setInitialViewpoint(); void createViewshed(double x, double y);
Esri::ArcGISRuntime::SceneQuickView* m_sceneView = nullptr; Esri::ArcGISRuntime::LocationViewshed* m_locationViewshed = nullptr; Esri::ArcGISRuntime::AnalysisOverlay* m_analysisOverlay = nullptr;
bool m_viewshedVisible = true; bool m_frustumVisible = false; double m_minDistance = 50; double m_maxDistance = 1000; double m_horizontalAngle = 45; double m_veriticalAngle = 90; double m_heading = 0; double m_pitch = 90; bool m_calculating = false;};
#endif // VIEWSHEDLOCATION_H// [WriteFile Name=ViewshedLocation, Category=Analysis]// [Legal]// Copyright 2017 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 QtQuick.Windowimport Esri.Samples
ViewshedLocationSample { id: viewshedSample clip: true width: 800 height: 600
SceneView { id: sceneView objectName: "sceneView" anchors.fill: parent
Component.onCompleted: { // Set the focus on SceneView to initially enable keyboard navigation forceActiveFocus(); }
Rectangle { anchors { right: parent.right bottom: sceneView.attributionTop margins: 10 } visible: !optionPanel.visible width: 45 height: width color: "white" radius: 25
Image { anchors.centerIn: parent source: "qrc:/Samples/Analysis/ViewshedLocation/settings.png" width: 40 height: width }
MouseArea { anchors.fill: parent onClicked: optionPanel.visible = true; } }
Rectangle { id: optionPanel anchors { right: parent.right top: parent.top bottom: sceneView.attributionTop } width: 260 visible: false color: "white" opacity: 0.85
Flickable { anchors { fill: parent margins: 5 } contentWidth: parent.width contentHeight: parent.height flickableDirection: Flickable.VerticalFlick
Column { id: optionColumn spacing: 10 width: optionPanel.width
Item { width: parent.width height: 25
Text { text: "Viewshed Options" anchors.horizontalCenter: parent.horizontalCenter font.pixelSize: 18 font.underline: true
}
Rectangle { anchors { right: parent.right verticalCenter: parent.verticalCenter } width: 45 height: width color: "transparent"
Image { anchors.centerIn: parent source: "qrc:/Samples/Analysis/ViewshedLocation/close.png" width: 40 height: width }
MouseArea { anchors.fill: parent onClicked: optionPanel.visible = false; } } }
Item { width: parent.width height: 25
Text { anchors.verticalCenter: parent.verticalCenter width: parent.width * 0.75 text: qsTr("Viewshed Visible") font.pixelSize: 14 }
Switch { anchors { right: parent.right margins: 10 verticalCenter: parent.verticalCenter } checked: true onCheckedChanged: viewshedSample.viewshedVisible = checked; } }
Item { width: parent.width height: 25
Text { anchors.verticalCenter: parent.verticalCenter width: parent.width * 0.75 text: qsTr("Frustum Outline Visible") font.pixelSize: 14 }
Switch { anchors { right: parent.right margins: 10 verticalCenter: parent.verticalCenter } checked: false onCheckedChanged: viewshedSample.frustumVisible = checked; } }
ViewshedSlider { titleText: qsTr("Min Distance (m)") parameterValue: viewshedSample.minDistance minValue: 1 maxValue: 2000 onParameterValueChanged: viewshedSample.minDistance = parameterValue; }
ViewshedSlider { titleText: qsTr("Max Distance (m)") parameterValue: viewshedSample.maxDistance minValue: 1 maxValue: 2000 onParameterValueChanged: viewshedSample.maxDistance = parameterValue; }
ViewshedSlider { titleText: qsTr("Vertical Angle") parameterValue: viewshedSample.verticalAngle minValue: 1 maxValue: 120 onParameterValueChanged: viewshedSample.verticalAngle = parameterValue; }
ViewshedSlider { titleText: qsTr("Horizontal Angle") parameterValue: viewshedSample.horizontalAngle minValue: 1 maxValue: 120 onParameterValueChanged: viewshedSample.horizontalAngle = parameterValue; }
ViewshedSlider { titleText: qsTr("Heading") parameterValue: viewshedSample.heading minValue: 1 maxValue: 359 onParameterValueChanged: viewshedSample.heading = parameterValue; }
ViewshedSlider { titleText: qsTr("Pitch") parameterValue: viewshedSample.pitch minValue: 1 maxValue: 179 onParameterValueChanged: viewshedSample.pitch = parameterValue; }
Row { width: parent.width height: 25 spacing: 5
Text { anchors.verticalCenter: parent.verticalCenter width: parent.width * 0.75 text: qsTr("Visible Color") font.pixelSize: 14 }
Rectangle { anchors { margins: 10 verticalCenter: parent.verticalCenter } width: 25 height: width border { color: "black" width: 1 } color: viewshedSample.visibleColor radius: 4
MouseArea { anchors.fill: parent onClicked: { visibleColorDialog.open(); } } } }
Row { width: parent.width height: 25 spacing: 5
Text { anchors.verticalCenter: parent.verticalCenter width: parent.width * 0.75 text: qsTr("Obstructed Color") font.pixelSize: 14 }
Rectangle { anchors { margins: 10 verticalCenter: parent.verticalCenter } width: 25 height: width border { color: "black" width: 1 } color: viewshedSample.obstructedColor radius: 4
MouseArea { anchors.fill: parent onClicked: { obstructedColorDialog.open(); } } } } } } } }
ColorDialog { id: visibleColorDialog modal: true x: Math.round(parent.width - width) / 2 y: Math.round(parent.height - height) / 2 onAccepted: { viewshedSample.visibleColor = visibleColorDialog.color; } onOpened: { setColor(viewshedSample.visibleColor); } }
ColorDialog { id: obstructedColorDialog modal: true x: Math.round(parent.width - width) / 2 y: Math.round(parent.height - height) / 2 onAccepted: { viewshedSample.obstructedColor = obstructedColorDialog.color; } onOpened: { setColor(viewshedSample.obstructedColor); } }}// [WriteFile Name=ViewshedLocation, Category=Analysis]// [Legal]// Copyright 2017 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.Controls
Column { id: root width: parent.width spacing: 5
property string titleText property real parameterValue property real minValue: 1 property real maxValue: 179
Text { width: 80 text: titleText font.pixelSize: 14 }
Row { width: parent.width height: 25 spacing: 5
Slider { anchors.verticalCenter: parent.verticalCenter orientation: Qt.Horizontal from: minValue to: maxValue width: parent.width * 0.75 value: parameterValue
onValueChanged: { parameterValue = value; } }
Text { anchors.verticalCenter: parent.verticalCenter horizontalAlignment: Text.AlignRight text: Math.round(parameterValue) font.pixelSize: 14 } }}// [Legal]// Copyright 2017 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 "ViewshedLocation.h"
// ArcGIS Maps SDK headers#include "ArcGISRuntimeEnvironment.h"
// Qt headers#include <QCommandLineParser>#include <QDir>#include <QGuiApplication>#include <QQmlEngine>#include <QQuickView>#include <QSurfaceFormat>
// Platform specific headers#ifdef Q_OS_WIN#include <Windows.h>#endif
#define STRINGIZE(x) #x#define QUOTE(x) STRINGIZE(x)
int main(int argc, char *argv[]){ Esri::ArcGISRuntime::ArcGISRuntimeEnvironment::setUseLegacyAuthentication(false);#if defined(Q_OS_LINUX) && !defined(Q_OS_ANDROID) // Linux requires 3.2 OpenGL Context // in order to instance 3D symbols QSurfaceFormat fmt = QSurfaceFormat::defaultFormat(); fmt.setVersion(3, 2); QSurfaceFormat::setDefaultFormat(fmt);#endif
QGuiApplication app(argc, argv); app.setApplicationName(QString("Viewshed Location"));
// 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 ViewshedLocation::init();
// Initialize application view QQuickView view; view.setResizeMode(QQuickView::SizeRootObjectToView);
QString arcGISRuntimeImportPath = QUOTE(ARCGIS_RUNTIME_IMPORT_PATH);
#if defined(LINUX_PLATFORM_REPLACEMENT) // on some linux platforms the string 'linux' is replaced with 1 // fix the replacement paths which were created QString replaceString = QUOTE(LINUX_PLATFORM_REPLACEMENT); arcGISRuntimeImportPath = arcGISRuntimeImportPath.replace(replaceString, "linux", Qt::CaseSensitive);#endif
// Add the import Path view.engine()->addImportPath(QDir(QCoreApplication::applicationDirPath()).filePath("qml")); // Add the Runtime and Extras path view.engine()->addImportPath(arcGISRuntimeImportPath);
// Set the source view.setSource(QUrl("qrc:/Samples/Analysis/ViewshedLocation/ViewshedLocation.qml"));
view.show();
return app.exec();}