
We’ve got a basic starting app set up in Part One and so now in Part Two we’ll create user location detection using the Vue Native geolocation API for mobile devices.
Privacy laws, either platform or legal requirements, demand that a user provide permission to allow an app obtain the user’s location. The geolocation API has built-in methods to handle the authorization flow.
The current Device API example in the Vue Native docs does not function as expected so we need to modify the code. The result will be a text display of the user location.
Template
The output needs to be wrapped in a template and a container gives us somewhere to put stuff. Views are used for content display and <view>’s may be embedded in other views.
Here we have a button implemented with the <touchable-opacity> Vue Native basic button component. “on-press” calls the “getLocation” method. The “{{ location }}” is the placeholder for the location data. For now, we’ll output all the data returned in “coords” from the “getLocation” method.
The “errorMessage” placeholder is fairly obvious.
<template>
<view class="container">
<touchable-opacity :on-press="getLocation">
<text class="text-field-title">Get Location</text>
</touchable-opacity>
<text class="text-field-title">Location:</text>
<text>{{ location }}</text>
<text class="text-error">{{ errorMessage }}</text>
</view>
</template>
Script
To start we need a couple of modules from Expo: Location and Permissions.
The “getLocation” method is the core logic.
For now, the data function returns two values: location which will have all the data from detecting the user location which will include lat, lng, altitude plus more. Then there is a placeholder for error messages.
There are a number of permissions required from a user such as camera or accelerometer access, and, of course, location which may be derived from device gps or other methods such as wifi location.
So, the Permissions API requires a specific argument that the user agrees to share. The API will display a dialog to the user allowing “always”, “when using app” and “deny”. Fairly self evident but there is a condition that we will address later where the user has globally denied access in the device settings.
Upon “allow” the code executes “getCurrentPositionAsync” and this obviously gets the user location. The actual data returned is an object named “coords” which is accessed by dot notation and then assigned to “location” that is displayed on the device screen.
<script>
import * as Location from "expo-location";
import * as Permissions from "expo-permissions";
export default {
data: function() {
return {
location: "",
errorMessage: ""
};
},
methods: {
getLocation: function() {
Permissions.askAsync(Permissions.LOCATION)
.then(status => {
if (!status.granted) {
this.errorMessage = "Permission to access location was denied";
} else if (status.granted) {
Location.getCurrentPositionAsync({}).then(location1 => {
this.location = location1.coords;
this.errorMessage = "";
});
}
})
.catch(err => {
console.log(err);
});
}
}
};
</script>
Style
Pretty standard styling but one thing to note when referring to Expo or React Native documentation is that Vue Native requires Hyphen-case or PasCalCase for style properties and names as well as in the script section for component names and other definitions.
<style>
.container {
background-color: white;
align-items: center;
justify-content: center;
flex: 1;
}
.text-field-title {
color: blue;
font-size: 18;
margin: 10;
}
.text-error {
color: red;
}
</style>
Result
Tadaa! Output to the screen is lat/lng in decimal degrees, altitude in meters, some accuracy data, and speed and direction if moving. Each of these parameters may be individually accessed by dot notation such as:
this.lng = location.coords.longitude
Note the ‘this’ which has to refer to a data parameter of “lng”. “{{ lng }}” can then be used to output to the device screen.
Next
In the next Tech Note, we’ll look at passing the location data as a prop to a map component to show user’s location on a map.