transistorsoft / flutter_background_geolocation

Sophisticated, battery-conscious background-geolocation & geofencing with motion-detection
https://www.transistorsoft.com/shop/products/flutter-background-geolocation
Other
633 stars 234 forks source link

Location updates are not happening unless I open Google Maps first for a moment #1303

Closed tiitha closed 1 month ago

tiitha commented 2 months ago

Your Environment

• No issues found!

JsonEncoder encoder = JsonEncoder.withIndent(" ");

class TrackerWidget extends StatefulWidget { String geoape_token = ""; Map settings = {};

reloadTrackerSettings() => createState().reloadTrackerSettings(); getTrackerState() => createState().getTrackerState();

@override _TrackerWidgetState createState() => _TrackerWidgetState(); TrackerWidget();

void setGeoApeToken(String token) { geoape_token = token; } }

class _TrackerWidgetState extends State {

IconData i = Icons.play_arrow; bool _trackerStarted = false; bool? _isMoving = false; bool _enabled = false; String _motionActivity = ""; String _trackingLabel = "Not Tracking"; String _odometer = ""; String _content = ""; String _gpsUpdate = ""; String _geoapeUpload = ""; String _track_token = ""; String _share_token = "";

int _uploaded = 0; String _uploadedTxt = "";

@override void initState() { super.initState(); _trackerStarted = false; _trackingLabel = "Not Tracking"; _isMoving = false; _enabled = false; _content = ''; _odometer = '0'; _uploaded = 0; _gpsUpdate = "never"; _geoapeUpload = "never"; _uploadedTxt = "0 kb"; initializeDateFormatting();

bg.BackgroundGeolocation.onLocation(_onLocation, _onLocationError);
bg.BackgroundGeolocation.onHttp(_onHttp);

bg.BackgroundGeolocation.ready(bg.Config(
    desiredAccuracy: bg.Config.DESIRED_ACCURACY_HIGH, // NAVIGATION is for IOS ONLY !!
    distanceFilter: 1.0,
    stopTimeout: 5,
    preventSuspend: true, // IOS only!
    stationaryRadius: 25, // IOS only!
    disableElasticity: true,
    disableMotionActivityUpdates: true,
    notification: bg.Notification(
        title: "GeoApe Tracker",
        text: "Tracking your location in background"
    ),
    stopOnTerminate: false,
    startOnBoot: true,
    locationTemplate: '{"lat":<%= latitude %>,"lon":<%= longitude %>, "alt": <%= altitude %>, "spd": <%= speed %>, "brn": <%= heading %>, "bat": <%= battery.level %>, "time": "<%= timestamp %>" }',
    autoSync: true,
    autoSyncThreshold: 5,
    batchSync: true,
    maxBatchSize: 2678400,
    method: "POST",
    url: "https://domain/upload.php?track=${_track_token}",
    headers: {
      'Content-Type': 'application/x-www-form-urlencoded',
      'Geoape-Auth': widget.geoape_token
    },
    params: {},
    extras: {},
    debug: true,
    logLevel: bg.Config.LOG_LEVEL_INFO,
    reset: false
)).then((bg.State state) {
  print("Ready to rock.. !");
  _enableTracker(false);
});

}

Future getTrackerState() async { bg.State s = await bg.BackgroundGeolocation.state; return s.enabled; }

Future reloadTrackerSettings() async {

print("Loading settings");
Map<dynamic, dynamic> settings = await Geoape.getSettings();

_track_token = settings['track_token'];
_share_token = settings['share_token'];

await bg.BackgroundGeolocation.setConfig(bg.Config(
    desiredAccuracy: int.parse(settings['accuracy']),
    autoSyncThreshold: Geoape.getIntervalValue(int.parse(settings['interval'])),
    url: "https://domain/upload.php?track=$settings['track_token']",
    params: {
      'action' : 'update_track',
      'token': settings['track_token']
    }
)).then((state) {
  print('[setConfig] success: ${state}');
});

}

void _onHttp(bg.HttpEvent response) {

print('[http] success? ${response.success}, status? ${response.status}, body: ${response.responseText}');

try {
  var d = json.decode(response.responseText);
  setState(() {
    _uploaded += int.parse(d['b'].toString());
    _uploadedTxt = "${(_uploaded/1024).round()} kb";
    _geoapeUpload = DateFormat('HH:mm:ss').format(DateTime.now()).toString();
  });
} catch(ex) {
  print(ex);
}

} _enableTracker(enabled) async {

if (enabled) {
  print("Location permissions: ");

  if (await Permission.location.serviceStatus.isEnabled) {
    print("location serviceStatus is enabled");
  } else {
    print("location serviceStatus is NOT enabled");
  }

  if (await Permission.location.status.isGranted) {
    print("permission is granted");
  } else {
    print("permission is NOT granted");
  }
  if (await Permission.location.status.isPermanentlyDenied) {
    print("permission is permanently denied!");
  }

  if (await Permission.locationAlways.request().isGranted == false) {
    ScaffoldMessenger.of(context).showSnackBar(const SnackBar(
      content: Text("GeoApe tracker doesn't have access to your location!\nPlease check the Location sharing settings!"),
    ));
    return;
  }

  bg.State state = await bg.BackgroundGeolocation.start();
  print('[start] success $state');
  print(_share_token);
  print(_track_token);

  setState(() {
    _trackingLabel = "Currently Tracking";
    _enabled = state.enabled;
    _isMoving = state.isMoving;
    _trackerStarted = enabled;
  });

} else {
  bg.State state = await bg.BackgroundGeolocation.stop();
  print('[stop] success: $state');
  bg.BackgroundGeolocation.sync();

  setState(() {
    _trackingLabel = "Not Tracking";
    _enabled = state.enabled;
    _isMoving = state.isMoving;
    _trackerStarted = enabled;
  });

}

} void _onLocationError(bg.LocationError le) { print("LocationError: "+le.message+", "+le.code.toString()); } void _onLocation(bg.Location location) async { print('[location] - $location'); print(". (${await getTrackerState()})"); _gpsUpdate = DateFormat('HH:mm:ss').format(DateTime.now()).toString(); String odometerKM = (location.odometer / 1000.0).toStringAsFixed(1); setState(() { _odometer = odometerKM; }); }

void _startNewTrack() async { await reloadTrackerSettings(); String track = await Geoape.generateTrackToken(widget.geoape_token); print("track: ${track}");

String shareToken = await Geoape.startTracking( widget.geoape_token, track);

setState(() {
  _share_token = shareToken;
  _track_token = track;
  _uploaded = 0;
  _geoapeUpload = "never";
  _uploadedTxt = "0 kb";
});

bg.BackgroundGeolocation.setOdometer(0.0);
_odometer = '0.0';
reloadTrackerSettings();
_enableTracker(true);

} void _startStopTracker() { if (_trackerStarted) { _enableTracker(false); } else { print("continue or start over?"); final act = CupertinoActionSheet( title: const Text('POSITION TRACKING'), message: const Text('Do You want to continue your previouew track\nor start a new one?'), actions: [ CupertinoActionSheetAction( child: Text('CONTINUE LAST TRACK', style: DefaultTextStyle.of(context).style.apply(fontSizeFactor: 1)), onPressed: () { _enableTracker(true); Navigator.of(context, rootNavigator: true).pop("1"); }, ), CupertinoActionSheetAction( child: Text('START A NEW TRACK', style: DefaultTextStyle.of(context).style.apply(fontSizeFactor: 1)), onPressed: () { _startNewTrack(); Navigator.of(context, rootNavigator: true).pop("1"); }, ) ], cancelButton: CupertinoActionSheetAction( child: Text('CANCEL', style: DefaultTextStyle.of(context).style.apply(fontSizeFactor: 1)), onPressed: () { Navigator.pop(context); }, )); showCupertinoModalPopup( context: context, builder: (BuildContext context) => act);

}

}

}


## Expected Behavior
After starting the tracker i expect the tracker to start and gather location data + upload it on a predefined interval. 

## Actual Behavior
Location information is not updated. If i request last known location manually, it knows where it is, but onLocation IS NOT triggered automatically. 
**How ever!** If I open Google maps app, my app starts receiving the location information as it should and works as expected (both on foreground and on the background). I'm not sure why the tracker doesn't receive location updates without me first looking at the google maps app. After using google maps to kick off the location updates, my app works perfectly, updates the location regardless of if the app is on the screen or on the background etc.

## Steps to Reproduce
<!--- reproduce this issue; include code to reproduce, if relevant -->
1.
2.
3.
4.

## Context
I wanted to start tracking the location of the device.

## Debug logs
<!-- include iOS / Android logs
- ios XCode logs,
- use #getLog #emailLog methods (@see docs)
- Android: $ adb logcat -s TSLocationManager
-->
<details>
    <summary>Logs</summary>

``` <!-- syntax-highligting:  DO NOT REMOVE -->
[ga_logs.log](https://github.com/user-attachments/files/15522023/ga_logs.log)

christocracy commented 2 months ago

It’s because you’re using the emulator. See wiki “Debugging”.

go outside with a real device and walk at least 200 meters.

tiitha commented 2 months ago

The exact same thing happened with Samsung Galaxy Tab Active5 (Android 14), travelled about 6km with a car and tested it some times. Otherwise I would have suspected the emulators' location issues or sth. I'll give it another try tomorrow

christocracy commented 2 months ago

Also see https://dontkillmyapp.com

tiitha commented 2 months ago

Also see https://dontkillmyapp.com

I would agree in the case if the app wouldn't work while being on the background etc, but it works .. just after the google maps trick .. and not before..

christocracy commented 2 months ago

Samsung Galaxy Tab Active5

This looks like a wifi-only tablet. test on a phone with GPS.

tiitha commented 2 months ago

Samsung Galaxy Tab Active5

This looks like a wifi-only tablet. test on a phone with GPS.

Looking at the specification it seems that it has GPS: https://www.samsung.com/uk/tablets/others/galaxy-tab-active5-green-128gb-sm-x306bzgaeea/#specs "Navigation: GPS, GLONASS, BDS, GALILEO, QZSS" .. And looking at Google Maps App it can show my real-time location as it should. Further more: my own application works just fine AFTER I have used google maps for a second. Might there be some kind of subscription or initialization issue of GPS notifications or sth?

christocracy commented 2 months ago

Might there be some kind of subscription or initialization issue of GPS notifications or sth?

No.

github-actions[bot] commented 1 month ago

This issue is stale because it has been open for 30 days with no activity.

github-actions[bot] commented 1 month ago

This issue was closed because it has been inactive for 14 days since being marked as stale.