繁体   English   中英

Expo React native 在模拟器中请求位置权限,但在内置应用程序中没有

[英]Expo React native asks for location permissions in simulator but not in built app

应用程序已经运行了一段时间,但现在它没有提示用户提供位置许可,这导致使用位置的功能失败。 在运行 expo go 的模拟器和物理设备上,都会提示用户授予位置数据的权限。(iOS 和 Android)它需要的所有其他权限都要求提供相机和日历(p)

export default function CheckIn(props) {
const { todayEvents } = useSelector(({ checkin }) => checkin);

const [venueIdd, setVenueId] = useState(0);
const [modalVisible, setModalVisible] = useState(false);
  const [status, setStatus] = useState(null);
  const [backgroundLocationPermission, setBackgroundLocationPermission] =
    useState(null);
  const dispatch = useDispatch();

  TaskManager.defineTask("updateLocation", ({ data: { locations }, error }) => {
    if (error) {
      return;
    }
    dispatch(sendBackgroundLocation(locations[0].coords, venueIdd));
  });
  async function registerBackgroundFetchAsync() {
    return BackgroundFetch.registerTaskAsync(BACKGROUND_FETCH_TASK, {
      minimumInterval: 60 * 15, // 15 minutes
      stopOnTerminate: false, // android only,
      startOnBoot: true, // android only
    });
  }

  async function unregisterBackgroundFetchAsync() {
    return BackgroundFetch.unregisterTaskAsync(BACKGROUND_FETCH_TASK);
  }

  React.useEffect(() => {
    dispatch(getTodaysEvents());

    const askPermission = async () => {
      let getForeground = await Location.getForegroundPermissionsAsync();
      if (getForeground.status !== "granted") {
      let { status } = await Location.requestForegroundPermissionsAsync();
      if (status !== "granted") {
        Alert.alert("Permission to access location was denied");
        return;
      } else {
        let backgroundPermissions =
          await Location.requestBackgroundPermissionsAsync();
        if (backgroundPermissions.status == "granted") {
          await AsyncStorage.setItem("background_permission", "true");
        }
      }
      }
    };
    askPermission();
  }, []);
  const checkIn = async (index) => {
    let temp = [...todayEvents];
    temp[index].isCheckedIn = true;
    setVenueId(temp[index].venueId);

    const backgroundStatus = await AsyncStorage.getItem(
      "background_permission"
    );

    // if (backgroundStatus !== null) {
    Location.startLocationUpdatesAsync("updateLocation", {
      timeInterval: 120,
      distanceInterval: 0.01,
      foregroundService: {
        notificationTitle: "Company title",
        notificationBody:
          "Information in body",
      },
      accuracy: Location.Accuracy.Highest,
    }).then((response) => {
      // console.log("RESPONSE LOCATION", response);
    });
    // }

    setTimeout(() => {
      const stopped = Location.stopLocationUpdatesAsync("updateLocation");
    }, 43200000);

    let { coords } = await Location.getCurrentPositionAsync();
    dispatch(userCheckIn({ lat: coords.latitude, long: coords.longitude }));
  };
  const checkOut = async (index) => {
    const stopped = Location.stopLocationUpdatesAsync("updateLocation");

    let temp = todayEvents;

    temp[index].isCheckedIn = false;
    //dispatch(userCheckOut()); // This is what I commented out
    // And the two rows below is added
    let { coords } = await Location.getCurrentPositionAsync();
    dispatch(userCheckOut({ lat: coords.latitude, long: coords.longitude }));
  };
  const review = (index, value) => {
    setModalVisible(true);
    setTimeout(() => {
      setModalVisible(false);
      setTimeout(() => {
        props.navigation.goBack();
      }, 300);
    }, 1500);
    let temp = todayEvents;
    temp[index].review = value;
    dispatch(giveEventFeedBack(temp[index]));
  };

从 app.json 以下 iOS 定义位置权限

NSLocationAlwaysUsageDescription NSLocationWhenInUseUsageDescription

对于 Android

ACCESS_BACKGROUND_LOCATION
ACCESS_COARSE_LOCATION
ACCESS_FINE_LOCATION

有一种情况是,用户最近为该权限选择了NEVER ASK AGAIN选项。 下次应用程序尝试询问它时,请求会以denied状态静默解析,而不会启动请求权限弹出模式。

如果是这种情况,应用可以强制用户在应用设置中手动授予权限

你可以像这样处理这种情况


const permission = await Location.getForegroundPermissionsAsync();

// Detect if you can request this permission again

if (!permission.canAskAgain || permission.status === "denied") {
  /**
   *   Code to open device setting then the user can manually grant the app
   *  that permission
   */

  Linking.openSettings();
} else {
  if (permission.status === "granted") {
    // Your actually code require this permission
  }
}



虽然上述解决方案不起作用,请查看 Expo SDK 44 - https://github.com/expo/expo/issues/issues/

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM