Issue
As i want to use location information in my Ionic 5/Capacitor app, i wrote a first version of a wrapper around the Geolocation API.
The issue is, that when i inject this service and call startReceivingLocationUpdates()
i get the following error:
core.js:6014 ERROR TypeError: Cannot read property 'locationSubject' of undefined
at locationCallback (location.service.ts:51)
at window.navigator.geolocation.watchPosition.Object.enableHighAccuracy (geolocation.js:30)
at ZoneDelegate.invoke (zone-evergreen.js:359)
at Object.onInvoke (core.js:39699)
at ZoneDelegate.invoke (zone-evergreen.js:358)
at Zone.runGuarded (zone-evergreen.js:134)
at zone-evergreen.js:118
My location service
import { Injectable } from '@angular/core';
import { Geolocation, GeolocationOptions, GeolocationPosition } from '@capacitor/core';
import { BehaviorSubject, Observable } from 'rxjs';
const locationOptions: GeolocationOptions = {
enableHighAccuracy: true,
requireAltitude: false
};
@Injectable({
providedIn: 'root'
})
export class LocationService {
private locationSubject = new BehaviorSubject<GeolocationPosition>(null);
private watchId: string = null;
constructor() {
}
receivingLocationUpdates(): boolean {
return this.watchId != null;
}
startReceivingLocationUpdates()
{
if(this.watchId !== null)
return;
this.watchId = Geolocation.watchPosition(locationOptions, this.locationCallback);
}
stopReceivingLocationUpdates()
{
if(this.watchId === null)
return;
Geolocation.clearWatch({id: this.watchId })
.then(_ => {
this.watchId = null;
});
}
subscribe(): Observable<GeolocationPosition>
{
return this.locationSubject.asObservable();
}
private locationCallback(location: GeolocationPosition) {
this.locationSubject.next(location);
}
}
What am i doing wrong?
Solution
The issue here is likely that you are losing what 'this' is pointing at, since the callback function (locationCallBack) gets executed within different scope than your class.
To fix this you should either bind the execution scope or make this transparent.
Try using fat arrow function:
private locationCallback = (location: GeolocationPosition) => {
this.locationSubject.next(location);
}
Alternatively you can:
- pass your class's 'this' scope
- bind 'this' using .bind(this) approach
Answered By - Sergey Rudenko
0 comments:
Post a Comment
Note: Only a member of this blog may post a comment.