Select features in scene layer

View on GitHub

Identify features in a scene to select.

Screenshot of Select features in scene layer sample

Use case

You can select features to visually distinguish them with a selection color or highlighting. This can be useful to demonstrate the physical extent or associated attributes of a feature, or to initiate another action such as centering that feature in the scene view.

How to use the sample

Tap on a building in the scene layer to select it. Deselect buildings by tapping away from the buildings.

How it works

  1. Create an instance of ArcGISSceneLayer, passing in the URL to a scene layer service.
  2. Use the onSingleTapGesture on the SceneView to get the screen tapped location.
  3. Use SceneViewProxy.identify(layer:screenPoint:tolerance:maximumResults:) to identify features in the scene.
  4. From the resulting IdentifyLayerResult, get the list of identified GeoElements.
  5. Get the first Feature in the list and use ArcGISSceneLayer.selectFeature(features:).

Relevant API

  • ArcGISSceneLayer
  • Scene
  • SceneView
  • SceneViewProxy
  • SceneViewReader

About the data

This sample shows a Brest France Buildings Scene hosted on ArcGIS Online.

Tags

3D, buildings, identify, model, query, search, select

Sample Code

SelectFeaturesInSceneLayerView.swift
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
// Copyright 2024 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
//
//   https://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 ArcGIS
import SwiftUI

struct SelectFeaturesInSceneLayerView: View {
    /// The error shown in the error alert.
    @State private var error: Error?

    /// The point on the screen where the user tapped.
    @State private var tapPoint: CGPoint?

    /// The scene layer that is added on top of the scene.
    @State private var sceneLayer = ArcGISSceneLayer(url: .brestBuildingService)

    /// A scene with topographic basemap and a 3D buildings layer.
    @State private var scene: ArcGIS.Scene = {
        // Creates a scene and sets an initial viewpoint.
        let scene = Scene(basemapStyle: .arcGISTopographic)
        // Sets an initial camera location.
        let camera = Camera(
            latitude: 48.38282,
            longitude: -4.49779,
            altitude: 40,
            heading: 41.65,
            pitch: 71.2,
            roll: 0
        )
        // Sets initial viewpoint to camera position at point.
        scene.initialViewpoint = Viewpoint(boundingGeometry: camera.location, camera: camera)
        // Creates a surface and adds an elevation source.
        let surface = Surface()
        surface.addElevationSource(ArcGISTiledElevationSource(url: .worldElevationService))
        // Sets the surface to the scene's base surface.
        scene.baseSurface = surface
        return scene
    }()

    /// Adds feature layer to scene in initialization.
    init() {
        scene.addOperationalLayer(sceneLayer)
    }

    var body: some View {
        SceneViewReader { sceneViewProxy in
            SceneView(scene: scene)
            // Captures location of tap on screen.
                .onSingleTapGesture { screenPoint, _ in
                    tapPoint = screenPoint
                }
                .task(id: tapPoint) {
                    // Clears the previous selections.
                    sceneLayer.clearSelection()
                    do {
                        guard let locationPoint = tapPoint else { return }
                        // Gets the identify results from the tap point.
                        let result = try await sceneViewProxy.identify(
                            on: sceneLayer,
                            screenPoint: locationPoint,
                            tolerance: 10
                        )
                        // Gets the first feature from the identify results.
                        guard let feature = result.geoElements.first as? ArcGISFeature else { return }
                        // Selects the feature in the scene layer.
                        sceneLayer.selectFeature(feature)
                    } catch {
                        self.error = error
                    }
                }
        }
        .errorAlert(presentingError: $error)
    }
}

private extension URL {
    /// The URL of a Brest, France buildings scene service.
    static var brestBuildingService: URL {
        URL(string: "https://tiles.arcgis.com/tiles/P3ePLMYs2RVChkJx/arcgis/rest/services/Buildings_Brest/SceneServer/layers/0")!
    }

    /// The URL of the Terrain 3D ArcGIS REST Service.
    static var worldElevationService: URL {
        URL(string: "https://elevation3d.arcgis.com/arcgis/rest/services/WorldElevation3D/Terrain3D/ImageServer")!
    }
}

#Preview {
    SelectFeaturesInSceneLayerView()
}

Your browser is no longer supported. Please upgrade your browser for the best experience. See our browser deprecation post for more details.

You can no longer sign into this site. Go to your ArcGIS portal or the ArcGIS Location Platform dashboard to perform management tasks.

Your ArcGIS portal

Create, manage, and access API keys and OAuth 2.0 developer credentials, hosted layers, and data services.

Your ArcGIS Location Platform dashboard

Manage billing, monitor service usage, and access additional resources.

Learn more about these changes in the What's new in Esri Developers June 2024 blog post.

Close