rmrs / react-native-settings

Allows access to various Android and iOS device settings using React Native
MIT License
226 stars 35 forks source link

My listener is called multiple time #57

Open Daybayzayd opened 4 years ago

Daybayzayd commented 4 years ago

Issue

Hello. I'm new in React Native, so maybe it's totally my fault. I tried to listen the location change with the DeviceEventEmitter. It works fine, but everytime i switch my location, my listener is fired 4 times. Always 4 times.

/**
 * Sample React Native App
 * https://github.com/facebook/react-native
 *
 * @format
 * @flow strict-local
 */

import React, { useEffect } from 'react';
import { DeviceEventEmitter } from 'react-native';
import RNSettings from 'react-native-settings';

const App: () => React$Node = () => {
  console.log('App compoment ..................');
  // const manager = new BleManager();

  useEffect(() => {
    console.log('useEffect Listener');

    const listenLocation = (result) => {
      console.log('listener', result);
      // setHasLocationOn(result[RNSettings.LOCATION_SETTING] === RNSettings.ENABLED);
    };

    RNSettings.getSetting(RNSettings.LOCATION_SETTING).then((result) => {
      console.log('result', result);
      // setHasLocationOn(result === RNSettings.ENABLED);
    });
    DeviceEventEmitter.addListener(RNSettings.GPS_PROVIDER_EVENT, listenLocation);

    console.log(DeviceEventEmitter.listeners(RNSettings.GPS_PROVIDER_EVENT));

    // return () => {
    //   console.log('remove listener');
    //   DeviceEventEmitter.removeListener(RNSettings.GPS_PROVIDER_EVENT, listenLocation);
    // };
  }, []);

  return <>{/* <Home2 manager={manager} /> */}</>;
};

export default App;

The App component is rendered only once. The useEffect is fired only once (in my logs). But when i switch location on/off, the logs show me "listener ..." 4 times.

Sorry if it's my fault or if i misunderstood something. I tried outside the useEffect it's same, i tried with a useEffect and with the callback to unregister when component is unmounted, but it's never fired (and it's logic) inside my useEffect.


Project Files

Android

Click To Expand

#### `MainApplication.java`: ```java package com.tteesstt; import android.app.Application; import android.content.Context; import com.facebook.react.PackageList; import com.facebook.react.ReactApplication; import android.content.IntentFilter; import io.rumors.reactnativesettings.RNSettingsPackage; import io.rumors.reactnativesettings.receivers.GpsLocationReceiver; import com.oblador.vectoricons.VectorIconsPackage; import com.polidea.reactnativeble.BlePackage; import com.facebook.react.ReactInstanceManager; import com.facebook.react.ReactNativeHost; import com.facebook.react.ReactPackage; import com.facebook.soloader.SoLoader; import java.lang.reflect.InvocationTargetException; import java.util.List; public class MainApplication extends Application implements ReactApplication { private final ReactNativeHost mReactNativeHost = new ReactNativeHost(this) { @Override public boolean getUseDeveloperSupport() { return BuildConfig.DEBUG; } @Override protected List getPackages() { @SuppressWarnings("UnnecessaryLocalVariable") List packages = new PackageList(this).getPackages(); // Packages that cannot be autolinked yet can be added manually here, for example: // packages.add(new MyReactNativePackage()); return packages; } @Override protected String getJSMainModuleName() { return "index"; } }; @Override public ReactNativeHost getReactNativeHost() { return mReactNativeHost; } @Override public void onCreate() { super.onCreate(); registerReceiver(new GpsLocationReceiver(), new IntentFilter("android.location.PROVIDERS_CHANGED")); SoLoader.init(this, /* native exopackage */ false); initializeFlipper(this, getReactNativeHost().getReactInstanceManager()); } /** * Loads Flipper in React Native templates. Call this in the onCreate method with something like * initializeFlipper(this, getReactNativeHost().getReactInstanceManager()); * * @param context * @param reactInstanceManager */ private static void initializeFlipper( Context context, ReactInstanceManager reactInstanceManager) { if (BuildConfig.DEBUG) { try { /* We use reflection here to pick up the class that initializes Flipper, since Flipper library is not available in release mode */ Class aClass = Class.forName("com.tteesstt.ReactNativeFlipper"); aClass .getMethod("initializeFlipper", Context.class, ReactInstanceManager.class) .invoke(null, context, reactInstanceManager); } catch (ClassNotFoundException e) { e.printStackTrace(); } catch (NoSuchMethodException e) { e.printStackTrace(); } catch (IllegalAccessException e) { e.printStackTrace(); } catch (InvocationTargetException e) { e.printStackTrace(); } } } } ``` #### `AndroidManifest.xml`: ```xml ```


Environment

Click To Expand

**`react-native info` output:** ``` OUTPUT GOES HERE ``` - **Platform that you're experiencing the issue on**: - [ ] Android

GerardCasadevall commented 4 years ago

The same problem, the listener is fired 4 times.