Location
Overview
Spectacles grants access to the device’s GPS coordinates, opening up a world of possibilities for location-based experiences with the Location API.

To use location services, users must be logged in and paired with their Snapchat account, and their location permission must be enabled. Users are also expected to be connected to the internet.
Getting Started
Prerequisites
Lens Studio v5.7.0 or later
Spectacles OS v5.60.000 or later
Setup Instructions
To access the location API on Spectacles, you need to declare your Lens permission to use the RawLocationModule. For more information on how to declare permissions, refer to the Permission Overview documentation.
require('LensStudio:RawLocationModule');
Location and Heading
Location can be retrieved through the Location Service API. You can retrieve the user's current position through getCurrentPosition, and their heading through onNorthAlignedOrientationUpdate.
Make sure the right accuracy for your use case is selected using GeoLocationAccuracy
Heading accuracy improves as you walk around due to automatic calibration adjustments
Example
- TypeScript
- JavaScript
require('LensStudio:RawLocationModule');
@component
export class LocationExample extends BaseScriptComponent {
latitude: number;
longitude: number;
altitude: number;
horizontalAccuracy: number;
verticalAccuracy: number;
timestamp: Date;
locationSource: string;
private repeatUpdateUserLocation: DelayedCallbackEvent;
private locationService: LocationService;
onAwake() {
this.createEvent('OnStartEvent').bind(() => {
this.createAndLogLocationAndHeading();
});
this.repeatUpdateUserLocation = this.createEvent('DelayedCallbackEvent');
this.repeatUpdateUserLocation.bind(() => {
// Get users location.
this.locationService.getCurrentPosition(
function (geoPosition) {
//Check if location coordinates have been updated based on timestamp
if (
this.timestamp === undefined ||
this.timestamp.getTime() != geoPosition.timestamp.getTime()
) {
this.latitude = geoPosition.latitude;
this.longitude = geoPosition.longitude;
this.horizontalAccuracy = geoPosition.horizontalAccuracy;
this.verticalAccuracy = geoPosition.verticalAccuracy;
print('long: ' + this.longitude);
print('lat: ' + this.latitude);
if (geoPosition.altitude != 0) {
this.altitude = geoPosition.altitude;
print('altitude: ' + this.altitude);
}
this.timestamp = geoPosition.timestamp;
}
},
function (error) {
print(error);
}
);
// Acquire next location update in 1 second, increase this value if required for AR visualisation purposes such as 0.5 or 0.1 seconds
this.repeatUpdateUserLocation.reset(1.0);
});
}
createAndLogLocationAndHeading() {
// Create location handler
this.locationService = GeoLocation.createLocationService();
// Set the accuracy
this.locationService.accuracy = GeoLocationAccuracy.Navigation;
// Acquire heading orientation updates
var onOrientationUpdate = function (northAlignedOrientation) {
//Providing 3DoF north aligned rotation in quaternion form
let heading = GeoLocation.getNorthAlignedHeading(northAlignedOrientation);
print('Heading orientation: ' + heading.toFixed(3));
// Convert to a 2DoF rotation for plane rendering purposes
var rotation = (heading * Math.PI) / 180;
print(
'Screen transform rotation: ' + quat.fromEulerAngles(0, 0, rotation)
);
};
this.locationService.onNorthAlignedOrientationUpdate.add(
onOrientationUpdate
);
// Acquire next location immediately with zero delay
this.repeatUpdateUserLocation.reset(0.0);
}
}
require('LensStudio:RawLocationModule');
let locationService = null;
const repeatUpdateUserLocation = script.createEvent('DelayedCallbackEvent');
repeatUpdateUserLocation.bind(() => {
// Get users location.
locationService.getCurrentPosition(
function (geoPosition) {
//Check if location coordinates have been updated based on timestamp
let geoPositionTimestampMs = geoPosition.timestamp.getTime();
if (timestampLastLocation != geoPositionTimestampMs) {
script.latitude = geoPosition.latitude;
script.longitude = geoPosition.longitude;
script.horizontalAccuracy = geoPosition.horizontalAccuracy;
script.verticalAccuracy = geoPosition.vertical;
print('lat: ' + geoPosition.latitude);
print('long: ' + geoPosition.longitude);
if (geoPosition.altitude != 0) {
script.altitude = geoPosition.altitude;
print('altitude: ' + geoPosition.altitude);
}
print('location source: ' + geoPosition.locationSource);
timestampLastLocation = geoPositionTimestampMs;
}
},
function (error) {
print(error);
}
);
// Acquire next location update in 1 second, increase this value if required for AR visualisation purposes such as 0.5 or 0.1 seconds
repeatUpdateUserLocation.reset(1.0);
});
function createAndLogLocationAndHeading() {
// Create location handler
locationService = GeoLocation.createLocationService();
// Set the accuracy
locationService.accuracy = GeoLocationAccuracy.Navigation;
// Acquire heading orientation updates
var onOrientationUpdate = function (northAlignedOrientation) {
//Providing 3DoF north aligned rotation in quaternion form
let heading = GeoLocation.getNorthAlignedHeading(northAlignedOrientation);
print('Heading orientation: ' + heading.toFixed(3));
// Convert to a 2DoF rotation for plane rendering purposes
var rotation = (heading * Math.PI) / 180;
script.screenTransform.rotation = quat.fromEulerAngles(0, 0, rotation);
};
locationService.onNorthAlignedOrientationUpdate.add(onOrientationUpdate);
// Acquire next location immediately with zero delay
repeatUpdateUserLocation.reset(0.0);
}
script.createEvent('OnStartEvent').bind(() => {
createAndLogLocationAndHeading();
});
Location and Heading visualisation
Spectacles provides one template to assist in getting started with location services.
The Outdoor Navigation Template serves as an example for providing directions using location and heading information. It describes how to visualise content in a 2D map or AR view.
2D Map
The 2D map component provides functionality which includes zooming and scrolling of a 2D map, follow-me functionality, manual generation of pins, automatic points of interest generation using the Snap Places API, and simultaneous AR view content visualization. The Snap Places API allows developers to bring Snapchat map features into their lenses, enabling interaction with nearby places.
For using the Snapchat Places API, Extended Permissions are required when combined with the Location Service for automatic pin generation.
AR view
The AR view provides a system for visualizing points of interest with AR functionality. Here is a breakdown of the components needed to enable this mode which are provided within the template:
- Navigation accuracy : Requires selecting Navigation accuracy level within the LocationService. This ensures that the AR features align accurately with the user's geographical position.
- Location Source : The AR view will benefit from utilizing a
FUSED_LOCATION
source, which combines various location signals for optimal accuracy and reliability. This is activated automatically when selecting Navigation accuracy. - 6DoF Pose : Utilizes latitude, longitude, altitude, and north-aligned orientation to create a six degrees of freedom (6DoF) pose, allowing for precise rendering of AR content.
- Pins on 2D Map : Pins can be created manually by users or automatically populated using the Snap Places API. For the latter, this requires extended permissions and the use of an experimental API whenever combined with the Location Service.
- AR View Visuals :
- Displays existing pins from the 2D map.
- Provides directional guidance via white arrows to point the user towards the points of interest.
- Shows a red dot when a point of interest should be in view.
- Displays the distance from the user to these points of interest.
The specific implementation details can be found on the provided Outdoor Navigation template.
Known Limitations
Location
- It may take a moment for the Lens to initialize and provide location data on the first run if there is no active internet connection.
- Navigation accuracy mode performance might degrade at night time
Heading
- After a new SnapOS is installed, heading orientation can take a moment to initialise. This is due to a calibration process that occurs in the background which is invisible to the user. This calibration process can be accelerated using the steps below:
- Just after a SnapOS upgrade, wear your Spectacles with the display turned on.
- Rotate the device for about 20 seconds. This involves looking around, turning around, and looking up and down to cover several directions.