Agontuk / react-native-geolocation-service

React native geolocation service for iOS and android
https://www.npmjs.com/package/react-native-geolocation-service
MIT License
1.61k stars 292 forks source link

watchPosition() triggers every second (iOS) #233

Open GunnarAK opened 3 years ago

GunnarAK commented 3 years ago

As the title implies watchPosition() triggers every second for me. Setup:

let positionWatcher: ?number = null;
export function watchPosition(): { remove: () => any } {
  if (positionWatcher == null) {
    positionWatcher = Geolocation.watchPosition(
      (position: Position) => {
        console.log("watchPosition() - change!");
        redux.store.dispatch(
          redux.actions.location.setLocation(position, null)
        );
      },
      (error: PositionError) => {
        console.warn("watchPosition() - ERROR", error);
        redux.store.dispatch(redux.actions.location.setLocation(null, error));
      }
    );
    console.log("watchPosition() - listener added");
  }
  return {
    remove: () => {
      Geolocation.clearWatch(positionWatcher);
      positionWatcher = null;
      console.log("watchPosition() - removed");
    }
  };
}

The same holds true when having the following options added to watchPosition():

{
  enableHighAccuracy: false,
  interval: 20000, // millis, Android-only
  fastestInterval: 5000, // millis, Android-only
  distanceFilter: 50, // meters
  useSignificantChanges: true // iOS-only
}

Use in component:

import { watchPosition } from "...";

class MapComponent extends Component<Props, State> {
  positionWatcher: ?{ remove: () => any } = null;

  componentDidMount() {
    this.positionWatcher = watchPosition();
  }

  componentWillUnmount() {
    this.positionWatcher && this.positionWatcher.remove();
  }
}

In my console I can see the listener being added only once. Also the removal of said listener happens as expected, which assures me there are no other listeners active.

This is only happening on iOS (14)

>> react-native info
System:
    OS: macOS 10.15.7
    CPU: (16) x64 Intel(R) Core(TM) i9-9880H CPU @ 2.30GHz
    Memory: 1.04 GB / 16.00 GB
    Shell: 5.7.1 - /bin/zsh
  Binaries:
    Node: 13.7.0 - /usr/local/bin/node
    Yarn: Not Found
    npm: 6.14.5 - /usr/local/bin/npm
    Watchman: 4.9.0 - /usr/local/bin/watchman
  Managers:
    CocoaPods: 1.10.0 - /Users/gunnark/.rvm/gems/ruby-2.6.3/bin/pod
  SDKs:
    iOS SDK:
      Platforms: iOS 14.2, DriverKit 20.0, macOS 11.0, tvOS 14.2, watchOS 7.1
    Android SDK:
      API Levels: 28, 29
      Build Tools: 28.0.3, 29.0.3, 30.0.1, 30.0.2
      System Images: android-29 | Google APIs Intel x86 Atom, android-29 | Google Play Intel x86 Atom
      Android NDK: Not Found
  IDEs:
    Android Studio: 3.6 AI-192.7142.36.36.6392135
    Xcode: 12.2/12B45b - /usr/bin/xcodebuild
  Languages:
    Java: 1.8.0_232 - /usr/bin/javac
    Python: 2.7.16 - /usr/bin/python
  npmPackages:
    @react-native-community/cli: ^4.0.1 => 4.13.1 
    react: 16.9.0 => 16.9.0 
    react-native: ~0.61.5 => 0.61.5 
  npmGlobalPackages:
    *react-native*: Not Found
Agontuk commented 3 years ago

Not sure what the issue is, using useSignificantChanges: true means ios will wait a long period of time before triggering next update. So it should not happen. Is this happening in real device or in simulator ?

GunnarAK commented 3 years ago

Hi Agontuk, yes this is happening on a real device, iOS 14. image I changed the console.log's as such:

console.log("watchPosition - change", positionWatcher);

As can be seen in the screenshot just 1 watcher is active.

The first two logs with "watchPosition - change" take their time, but after I see it getting triggered every second. Finishing this post it has reached 300+ logs.

Agontuk commented 3 years ago

Not sure what the issue is. Can you try running the example project and see if it behaves the same way ?

TamasFarago commented 1 year ago

It's updating for me every second too. Could you solve it?

SnehasisSahoo commented 3 months ago

I am facing the same issue, I am only working with Android can't say for IOS, and here is my options object:

{
    interval: 5000,
    timeout: 10000,
    maximumAge: 0,
    enableHighAccuracy: true,
    distanceFilter: 0,
    fastestInterval: 5000,
}

And the here is my config:

Geolocation.setRNConfiguration({
  authorizationLevel: 'always',
  enableBackgroundLocationUpdates: true,
  locationProvider: 'auto',
});

When the distance filter is set to 0, (as per as docs when set to 0 filter is removed, default is 100), the interval option is being neglected, although i am setting it to 5 seconds, its generating points rapidly every second.

Here is the result:

 LOG  {"coords": {"accuracy": 11.45981216430664, "altitude": -53.4263916015625, "heading": 0, "latitude": 22.46255064, "longitude": 88.36568368, "speed": 0}, "extras": {"maxCn0": 32, "meanCn0": 23, "satellites": 13}, "mocked": false, "timestamp": 1715871599000}  8:29:58 pm points generated!
 LOG  {"coords": {"accuracy": 11.193303108215332, "altitude": -53.4288330078125, "heading": 0, "latitude": 22.46255063, "longitude": 88.36568368, "speed": 0}, "extras": {"maxCn0": 33, "meanCn0": 22, "satellites": 14}, "mocked": false, "timestamp": 1715871600000}  8:29:59 pm points generated!
 LOG  {"coords": {"accuracy": 11.19205093383789, "altitude": -53.4283447265625, "heading": 0, "latitude": 22.46255062, "longitude": 88.36568368, "speed": 0}, "extras": {"maxCn0": 32, "meanCn0": 22, "satellites": 15}, "mocked": false, "timestamp": 1715871601000} 8:30:00 pm points generated!
 LOG  {"coords": {"accuracy": 11.20115852355957, "altitude": -53.412567138671875, "heading": 0, "latitude": 22.46255054, "longitude": 88.36568366, "speed": 0}, "extras": {"maxCn0": 33, "meanCn0": 21, "satellites": 16}, "mocked": false, "timestamp": 1715871602000} 8:30:01 pm points generated!

as you can see i have printed the time stamp after each of them.

this is really giving me a hard time. Please provide a fix.

device tested on: POCO m2 pro.