Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[New] Show device location using indoor positioning #462

Merged
merged 76 commits into from
Aug 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
76 commits
Select commit Hold shift + click to select a range
e96b6a1
add in files
chriswebb09 Jul 16, 2024
b0d7d86
update license
chriswebb09 Jul 16, 2024
68793b9
add in functionality
chriswebb09 Jul 16, 2024
2372cc0
working indoor navigation
chriswebb09 Jul 17, 2024
c8f8422
add in image
chriswebb09 Jul 17, 2024
d751f9a
check for older method if indoors definition is not present
chriswebb09 Jul 17, 2024
aaad56c
add in comments
chriswebb09 Jul 17, 2024
d9885af
move more logic to model
chriswebb09 Jul 19, 2024
a9be32c
add in mapIsLoaded state check
chriswebb09 Jul 19, 2024
b5b5ef6
move loading boolean to model
chriswebb09 Jul 19, 2024
a9385f3
make update location private
chriswebb09 Jul 19, 2024
9901fae
update access
chriswebb09 Jul 19, 2024
1ffffe8
update comment
chriswebb09 Jul 19, 2024
1ee954a
update method names
chriswebb09 Jul 19, 2024
f27c828
Merge branch 'v.next' into chriswebb/New-ShowDeviceLocationUsingIndoo…
chriswebb09 Jul 22, 2024
d2ee695
move location manager out of function
chriswebb09 Jul 22, 2024
6f7a4a5
remove DataSourceType
chriswebb09 Jul 22, 2024
f8a5e37
use older map data
chriswebb09 Jul 23, 2024
0ee84de
remove redundant isLoading
chriswebb09 Jul 23, 2024
da1cc64
add in screenshot
chriswebb09 Jul 23, 2024
9ba7395
remove older code
chriswebb09 Jul 23, 2024
87da1a3
update for suggested changes
chriswebb09 Jul 23, 2024
f9e9d01
remove files from copy files
chriswebb09 Jul 23, 2024
f261da0
update
chriswebb09 Jul 23, 2024
b567797
add in files to copy files
chriswebb09 Jul 23, 2024
ff0f6fc
Merge branch 'v.next' into chriswebb/New-ShowDeviceLocationUsingIndoo…
chriswebb09 Jul 23, 2024
ce05827
Merge branch 'v.next' into chriswebb/New-ShowDeviceLocationUsingIndoo…
chriswebb09 Jul 24, 2024
038c604
update UI
chriswebb09 Jul 24, 2024
c04263e
remove published from variable
chriswebb09 Jul 25, 2024
b020388
update variable names
chriswebb09 Jul 25, 2024
560f014
move locationDisplay logic together
chriswebb09 Jul 25, 2024
497b3dd
format so that only one decimal place is showing
chriswebb09 Jul 25, 2024
7389f58
update method name to reflect full logic so there are no unexpected s…
chriswebb09 Jul 25, 2024
f07bf98
remove spacer views and use max height instead
chriswebb09 Jul 25, 2024
cb9707d
update method name to reflect changed functionality
chriswebb09 Jul 25, 2024
8d0395e
update comments
chriswebb09 Jul 25, 2024
21e9391
update method names to clarify side effects
chriswebb09 Jul 25, 2024
3049e89
locationDisplay does not need to be published
chriswebb09 Jul 25, 2024
7ab944c
cleanup variable order in model
chriswebb09 Jul 25, 2024
e48dc6c
update comment to better explain method functionality
chriswebb09 Jul 25, 2024
2262ce9
move more of the isLoading changes into the model.
chriswebb09 Jul 25, 2024
22ebd0b
add in changes for code review
chriswebb09 Aug 1, 2024
dfecb0b
update formatter
chriswebb09 Aug 2, 2024
21b5723
update readme
chriswebb09 Aug 2, 2024
f481774
add in readme
chriswebb09 Aug 2, 2024
b53c213
update image
chriswebb09 Aug 2, 2024
f7470ff
Merge remote-tracking branch 'origin/v.next' into chriswebb/New-ShowD…
chriswebb09 Aug 6, 2024
084005c
Merge branch 'v.next' into chriswebb/New-ShowDeviceLocationUsingIndoo…
chriswebb09 Aug 7, 2024
f446cdb
add in updates to reflect phils comments
chriswebb09 Aug 7, 2024
797e86e
update to reflect changes in readme
chriswebb09 Aug 7, 2024
ec7d083
Update Shared/Samples/Show device location using indoor positioning/S…
chriswebb09 Aug 7, 2024
f738944
update for changes progressview
chriswebb09 Aug 7, 2024
abbe29c
Merge branch 'chriswebb/New-ShowDeviceLocationUsingIndoorPositioning'…
chriswebb09 Aug 7, 2024
9856841
move text logic
chriswebb09 Aug 7, 2024
84d98bc
update display text method
chriswebb09 Aug 8, 2024
8ca3ab8
update comments
chriswebb09 Aug 8, 2024
f293092
update comment
chriswebb09 Aug 8, 2024
2ac63c2
update floor yoda logic
chriswebb09 Aug 9, 2024
95fd011
refactor text display to stack views
chriswebb09 Aug 9, 2024
172f723
update to use swiftui text formatting
chriswebb09 Aug 9, 2024
b62083a
update for multiline text
chriswebb09 Aug 9, 2024
32277d0
remove properties, update comment and fix text string formatting
chriswebb09 Aug 9, 2024
3d1623b
fix whitespace
chriswebb09 Aug 9, 2024
cbeaae8
Merge branch 'v.next' into chriswebb/New-ShowDeviceLocationUsingIndoo…
chriswebb09 Aug 10, 2024
f3009f7
Merge branch 'v.next' into chriswebb/New-ShowDeviceLocationUsingIndoo…
yo1995 Aug 15, 2024
817c88c
Clean up the view.
yo1995 Aug 15, 2024
523ba05
Update screenshot using real data.
yo1995 Aug 15, 2024
8524d30
Small changes to the view.
yo1995 Aug 15, 2024
4a79804
Refactor the data model.
yo1995 Aug 15, 2024
155256c
Update README.
yo1995 Aug 15, 2024
43ba841
Fix typo in function name.
yo1995 Aug 15, 2024
d3cf623
Merge branch 'v.next' into chriswebb/New-ShowDeviceLocationUsingIndoo…
yo1995 Aug 19, 2024
69c6fc1
Apply suggestions from code review.
yo1995 Aug 19, 2024
ef1f0b9
Deprecate corner radius API.
yo1995 Aug 19, 2024
30e8421
Change error enum to struct.
yo1995 Aug 19, 2024
6065a10
Merge branch 'v.next' into chriswebb/New-ShowDeviceLocationUsingIndoo…
yo1995 Aug 19, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 20 additions & 0 deletions Samples.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -192,6 +192,7 @@
883C121929C914E100062FF9 /* DownloadPreplannedMapAreaView.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = E070A0A2286F3B6000F2B606 /* DownloadPreplannedMapAreaView.swift */; };
88F93CC129C3D59D0006B28E /* CreateAndEditGeometriesView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 88F93CC029C3D59C0006B28E /* CreateAndEditGeometriesView.swift */; };
88F93CC229C4D3480006B28E /* CreateAndEditGeometriesView.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = 88F93CC029C3D59C0006B28E /* CreateAndEditGeometriesView.swift */; };
9503056E2C46ECB70091B32D /* ShowDeviceLocationUsingIndoorPositioningView.Model.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9503056D2C46ECB70091B32D /* ShowDeviceLocationUsingIndoorPositioningView.Model.swift */; };
950D5B0D2C2CC35D00DF2E4E /* hydrography in Resources */ = {isa = PBXBuildFile; fileRef = 950D5B0C2C2CC35D00DF2E4E /* hydrography */; settings = {ASSET_TAGS = (AddEncExchangeSet, ); }; };
9529D1942C01676200B5C1A3 /* SelectFeaturesInSceneLayerView.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = 954AEDED2C01332600265114 /* SelectFeaturesInSceneLayerView.swift */; };
9537AFB42C2208B5000923C5 /* AddENCExchangeSetView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9537AFB32C2208B5000923C5 /* AddENCExchangeSetView.swift */; };
Expand All @@ -211,10 +212,13 @@
95D2EE0F2C334D1600683D53 /* ShowServiceAreaView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 95D2EE0E2C334D1600683D53 /* ShowServiceAreaView.swift */; };
95DEB9B62C127A92009BEC35 /* ShowViewshedFromPointOnMapView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 95DEB9B52C127A92009BEC35 /* ShowViewshedFromPointOnMapView.swift */; };
95DEB9B82C127B5E009BEC35 /* ShowViewshedFromPointOnMapView.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = 95DEB9B52C127A92009BEC35 /* ShowViewshedFromPointOnMapView.swift */; };
95E0DBCA2C503E2500224A82 /* ShowDeviceLocationUsingIndoorPositioningView.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = 95F891282C46E9D60010EBED /* ShowDeviceLocationUsingIndoorPositioningView.swift */; };
95E0DBCB2C503E2500224A82 /* ShowDeviceLocationUsingIndoorPositioningView.Model.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = 9503056D2C46ECB70091B32D /* ShowDeviceLocationUsingIndoorPositioningView.Model.swift */; };
95E980712C26183000CB8912 /* BrowseOGCAPIFeatureServiceView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 95E980702C26183000CB8912 /* BrowseOGCAPIFeatureServiceView.swift */; };
95E980742C26189E00CB8912 /* BrowseOGCAPIFeatureServiceView.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = 95E980702C26183000CB8912 /* BrowseOGCAPIFeatureServiceView.swift */; };
95F3A52B2C07F09C00885DED /* SetSurfaceNavigationConstraintView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 95F3A52A2C07F09C00885DED /* SetSurfaceNavigationConstraintView.swift */; };
95F3A52D2C07F28700885DED /* SetSurfaceNavigationConstraintView.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = 95F3A52A2C07F09C00885DED /* SetSurfaceNavigationConstraintView.swift */; };
95F891292C46E9D60010EBED /* ShowDeviceLocationUsingIndoorPositioningView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 95F891282C46E9D60010EBED /* ShowDeviceLocationUsingIndoorPositioningView.swift */; };
D70082EB2ACF900100E0C3C2 /* IdentifyKMLFeaturesView.swift in Sources */ = {isa = PBXBuildFile; fileRef = D70082EA2ACF900100E0C3C2 /* IdentifyKMLFeaturesView.swift */; };
D70082EC2ACF901600E0C3C2 /* IdentifyKMLFeaturesView.swift in Copy Source Code Files */ = {isa = PBXBuildFile; fileRef = D70082EA2ACF900100E0C3C2 /* IdentifyKMLFeaturesView.swift */; };
D7010EBF2B05616900D43F55 /* DisplaySceneFromMobileScenePackageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = D7010EBC2B05616900D43F55 /* DisplaySceneFromMobileScenePackageView.swift */; };
Expand Down Expand Up @@ -538,6 +542,8 @@
dstPath = "";
dstSubfolderSpec = 7;
files = (
95E0DBCA2C503E2500224A82 /* ShowDeviceLocationUsingIndoorPositioningView.swift in Copy Source Code Files */,
95E0DBCB2C503E2500224A82 /* ShowDeviceLocationUsingIndoorPositioningView.Model.swift in Copy Source Code Files */,
D71C90A52C6C252F0018C63E /* StyleGeometryTypesWithSymbolsView.Views.swift in Copy Source Code Files */,
D71C90A42C6C252B0018C63E /* StyleGeometryTypesWithSymbolsView.swift in Copy Source Code Files */,
3E9F77742C6A6E670022CAB5 /* QueryFeatureCountAndExtentView.swift in Copy Source Code Files */,
Expand Down Expand Up @@ -855,6 +861,7 @@
79D84D0D2A815C5B00F45262 /* AddCustomDynamicEntityDataSourceView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AddCustomDynamicEntityDataSourceView.swift; sourceTree = "<group>"; };
883C121429C9136600062FF9 /* DownloadPreplannedMapAreaView.MapPicker.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DownloadPreplannedMapAreaView.MapPicker.swift; sourceTree = "<group>"; };
88F93CC029C3D59C0006B28E /* CreateAndEditGeometriesView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CreateAndEditGeometriesView.swift; sourceTree = "<group>"; };
9503056D2C46ECB70091B32D /* ShowDeviceLocationUsingIndoorPositioningView.Model.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShowDeviceLocationUsingIndoorPositioningView.Model.swift; sourceTree = "<group>"; };
950D5B0C2C2CC35D00DF2E4E /* hydrography */ = {isa = PBXFileReference; lastKnownFileType = folder; path = hydrography; sourceTree = "<group>"; };
9537AFB32C2208B5000923C5 /* AddENCExchangeSetView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AddENCExchangeSetView.swift; sourceTree = "<group>"; };
9537AFD62C220EF0000923C5 /* ExchangeSetwithoutUpdates */ = {isa = PBXFileReference; lastKnownFileType = folder; path = ExchangeSetwithoutUpdates; sourceTree = "<group>"; };
Expand All @@ -868,6 +875,7 @@
95DEB9B52C127A92009BEC35 /* ShowViewshedFromPointOnMapView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShowViewshedFromPointOnMapView.swift; sourceTree = "<group>"; };
95E980702C26183000CB8912 /* BrowseOGCAPIFeatureServiceView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = BrowseOGCAPIFeatureServiceView.swift; sourceTree = "<group>"; };
95F3A52A2C07F09C00885DED /* SetSurfaceNavigationConstraintView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SetSurfaceNavigationConstraintView.swift; sourceTree = "<group>"; };
95F891282C46E9D60010EBED /* ShowDeviceLocationUsingIndoorPositioningView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ShowDeviceLocationUsingIndoorPositioningView.swift; sourceTree = "<group>"; };
D70082EA2ACF900100E0C3C2 /* IdentifyKMLFeaturesView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = IdentifyKMLFeaturesView.swift; sourceTree = "<group>"; };
D7010EBC2B05616900D43F55 /* DisplaySceneFromMobileScenePackageView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DisplaySceneFromMobileScenePackageView.swift; sourceTree = "<group>"; };
D701D72B2A37C7F7006FF0C8 /* bradley_low_3ds */ = {isa = PBXFileReference; lastKnownFileType = folder; path = bradley_low_3ds; sourceTree = "<group>"; };
Expand Down Expand Up @@ -1268,6 +1276,7 @@
D7EF5D712A269E2D00FEBDE5 /* Show coordinates in multiple formats */,
E004A6E728493BBB002A1FE6 /* Show device location */,
0044CDD72995C352004618CE /* Show device location history */,
95F8912A2C46E9F00010EBED /* Show device location using indoor positioning */,
4D126D6829CA1B6000CFB7A7 /* Show device location with NMEA data sources */,
D722BD1E2A420D7E002C2087 /* Show extruded features */,
00ABA94B2BF671FC00C0488C /* Show grid */,
Expand Down Expand Up @@ -1883,6 +1892,15 @@
path = "Set surface navigation constraint";
sourceTree = "<group>";
};
95F8912A2C46E9F00010EBED /* Show device location using indoor positioning */ = {
isa = PBXGroup;
children = (
95F891282C46E9D60010EBED /* ShowDeviceLocationUsingIndoorPositioningView.swift */,
9503056D2C46ECB70091B32D /* ShowDeviceLocationUsingIndoorPositioningView.Model.swift */,
);
path = "Show device location using indoor positioning";
sourceTree = "<group>";
};
D70082E72ACF8F6C00E0C3C2 /* Identify KML features */ = {
isa = PBXGroup;
children = (
Expand Down Expand Up @@ -3096,12 +3114,14 @@
isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647;
files = (
95F891292C46E9D60010EBED /* ShowDeviceLocationUsingIndoorPositioningView.swift in Sources */,
1C2538562BABACFD00337307 /* AugmentRealityToNavigateRouteView.swift in Sources */,
1C2538572BABACFD00337307 /* AugmentRealityToNavigateRouteView.ARSceneView.swift in Sources */,
D76929FA2B4F79540047205E /* OrbitCameraAroundObjectView.swift in Sources */,
79D84D132A81711A00F45262 /* AddCustomDynamicEntityDataSourceView.swift in Sources */,
102B6A372BFD5B55009F763C /* IdentifyFeaturesInWMSLayerView.swift in Sources */,
E000E7602869E33D005D87C5 /* ClipGeometryView.swift in Sources */,
9503056E2C46ECB70091B32D /* ShowDeviceLocationUsingIndoorPositioningView.Model.swift in Sources */,
4D2ADC6729C50BD6003B367F /* AddDynamicEntityLayerView.Model.swift in Sources */,
E004A6E928493BCE002A1FE6 /* ShowDeviceLocationView.swift in Sources */,
1C26ED192A859525009B7721 /* FilterFeaturesInSceneView.swift in Sources */,
Expand Down
chriswebb09 marked this conversation as resolved.
Show resolved Hide resolved
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
# Show device location using indoor positioning

Show your device's real-time location while inside a building by using signals from indoor positioning beacons.

![Show device location using indoor positioning](show-device-location-using-indoor-positioning.png)

## Use case

An indoor positioning system (IPS) allows you to locate yourself and others inside a building in real time. Similar to GPS, it puts a blue dot on indoor maps and can be used with other location services to help navigate to any point of interest or destination, as well as provide an easy way to identify and collect geospatial information at their location.

## How to use the sample

When the device is within range of an IPS beacon, toggle "Show Location" to change the visibility of the location indicator in the map view. The system will ask for permission to use the device's location if the user has not yet used location services in this app. It will then start the location display with auto-pan mode set to `navigation`.

When there are no IPS beacons nearby or other errors occur while initializing the indoors location data source, it will seamlessly fall back to the current device location as determined by GPS.

## How it works

1. Load an IPS-aware map. This can be a web map hosted as a portal item in ArcGIS Online, an Enterprise Portal, or a mobile map package (.mmpk) created with ArcGIS Pro.
2. Create and load an `IndoorPositioningDefinition` (stored with the map), then create an `IndoorsLocationDataSource` from it. See the details about creating the location data source in the "[`Additional information`](#additional-information)" section below.
3. Handle location change events to respond to floor changes or read other metadata for locations.
4. Assign the `IndoorsLocationDataSource` to the map view's location display.
5. Enable and disable the map view's location display using `start()` and `stop()`. Device location will appear on the display as a blue dot and update as the user moves throughout the space.
6. Use the `autoPanMode` property to change how the map behaves when location updates are received.

## Relevant API

* ArcGISFeatureTable
* FeatureTable
* IndoorPositioningDefinition
* IndoorsLocationDataSource
* LocationDisplay
* LocationDisplay.AutoPanMode
* Map
* MapView

## About the data

This sample uses an [IPS-aware web map](https://www.arcgis.com/home/item.html?id=8fa941613b4b4b2b8a34ad4cdc3e4bba) that displays Building L on the Esri Redlands campus. Please note: you would only be able to use the indoor positioning functionalities when you are inside this building. Swap the web map to test with your own IPS setup.

## Additional information

* Location and Bluetooth permissions are required for this sample.
* You could initialize the `IndoorsLocationDataSource` from individual feature tables stored in different data sources, such as map, mobile geodatabase, and feature services. With version 200.5 and higher, you can construct the `IndoorsLocationDataSource` using a single `IndoorPositioningDefinition` available in your IPS-aware map. In short…
* If an `IndoorPositioningDefinition` is available in your IPS-aware map, use it to construct `IndoorsLocationDataSource`.
* If your map does not have an `IndoorPositioningDefinition`, construct the location data source from individual feature tables as described in [Manually create an indoor location data source](https://developers.arcgis.com/swift/device-location/indoor-positioning/#manually-create-an-indoor-location-data-source) documentation.
* To learn more about IPS, read the [Indoor positioning](https://developers.arcgis.com/swift/device-location/indoor-positioning/) article on ArcGIS Developer website.
* To learn more about how to deploy the indoor positioning system, read the [Deploy ArcGIS IPS](https://doc.arcgis.com/en/ips/latest/get-started/introduction-to-the-deployment-of-arcgis-ips.htm) article.

## Tags

beacon, BLE, blue dot, Bluetooth, building, facility, GPS, indoor, IPS, location, map, mobile, navigation, site, transmitter
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
{
"category": "Maps",
"description": "Show your device's real-time location while inside a building by using signals from indoor positioning beacons.",
"ignore": false,
"images": [
"show-device-location-using-indoor-positioning.png"
],
"keywords": [
"BLE",
"Bluetooth",
"GPS",
"IPS",
"beacon",
"blue dot",
"building",
"facility",
"indoor",
"location",
"map",
"mobile",
"navigation",
"site",
"transmitter",
"ArcGISFeatureTable",
"FeatureTable",
"IndoorPositioningDefinition",
"IndoorsLocationDataSource",
"LocationDisplay",
"LocationDisplay.AutoPanMode",
"Map",
"MapView"
],
"redirect_from": [],
"relevant_apis": [
"ArcGISFeatureTable",
"FeatureTable",
"IndoorPositioningDefinition",
"IndoorsLocationDataSource",
"LocationDisplay",
"LocationDisplay.AutoPanMode",
"Map",
"MapView"
],
"snippets": [
"ShowDeviceLocationUsingIndoorPositioningView.swift",
"ShowDeviceLocationUsingIndoorPositioningView.Model.swift"
],
"title": "Show device location using indoor positioning"
}
Loading
Loading