我正在创建一个地图应用程序,但我遇到了一个问题,即一旦授予权限,应用程序就不会显示用户位置。
使用的包
- permission_handler
- google_maps_flutter.dart'
我已经对位置权限进行了排序,但一旦授予权限,应用程序就不会显示用户位置。如果我重新运行该应用程序,它就会重新运行。
这让我非常沮丧,如果有人能告诉我一旦授予权限,如何显示用户的当前位置,我将不胜感激?
这是代码
import 'package:flutter/material.dart';
import 'package:ManchesterMaps/models/locales.dart';
import 'package:ManchesterMaps/widgets/drawers/map_drawer.dart';
import 'package:ManchesterMaps/widgets/home_pages/my_places/list_places.dart';
import 'package:ManchesterMaps/widgets/home_pages/settings/preferences.dart';
import 'package:ManchesterMaps/widgets/home_pages/the_map/the_map.dart';
import 'package:ManchesterMaps/widgets/home_pages/uni_security/uni_security_info.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter_localizations/flutter_localizations.dart';
import 'package:circular_bottom_navigation/circular_bottom_navigation.dart';
import 'package:circular_bottom_navigation/tab_item.dart';
import './theme.dart' as Theme;
void main() => runApp(App());
class App extends StatefulWidget {
@override
_AppState createState() => _AppState();
}
class _AppState extends State<App> with WidgetsBindingObserver {
PageController controller = PageController();
int selected = 0;
//BottomBar list
List<TabItem> tabItems = List.of([
new TabItem(Icons.home, "Campus Map", Theme.UniColors.primaryColour[500],
labelStyle: TextStyle(
color: Theme.UniColors.primaryColour[500],
fontWeight: FontWeight.normal)),
new TabItem(Icons.search, "Search", Theme.UniColors.primaryColour[500],
labelStyle: TextStyle(
color: Theme.UniColors.primaryColour[500],
fontWeight: FontWeight.normal)),
new TabItem(Icons.place, "My Places", Theme.UniColors.primaryColour[500],
labelStyle: TextStyle(
color: Theme.UniColors.primaryColour[500],
fontWeight: FontWeight.normal)),
new TabItem(
Icons.security, "Security Info", Theme.UniColors.primaryColour[500],
labelStyle: TextStyle(
color: Theme.UniColors.primaryColour[500],
fontWeight: FontWeight.normal)),
new TabItem(Icons.settings, "Settings", Theme.UniColors.primaryColour[500],
labelStyle: TextStyle(
color: Theme.UniColors.primaryColour[300],
fontWeight: FontWeight.normal)),
]);
// Show Map Page
CircularBottomNavigationController _navigationController =
new CircularBottomNavigationController(0);
@override
Widget build(BuildContext context) {
//Locale myLocale = Localizations.localeOf(context);
return MaterialApp(
localizationsDelegates: [
// A class which loads the translations from JSON files
const AppLocalizationsDelegate(),
// Built-in localization of basic text for Material widgets
GlobalMaterialLocalizations.delegate,
// Built-in localization for text direction LTR/RTL
GlobalWidgetsLocalizations.delegate,
GlobalCupertinoLocalizations.delegate,
],
supportedLocales: [
const Locale('en', ''),
const Locale('fr', ''),
const Locale('ar', ''),
const Locale('de', ''),
const Locale('es', ''),
const Locale('hi', ''),
],
onGenerateTitle: (BuildContext context) =>
AppLocalizations.of(context).title,
color: Theme.UniColors.primaryColour[300],
theme: Theme.uniThemeData,
home: Scaffold(
body: Stack(
children: <Widget>[
PageView(
children: <Widget>[
Container(
child: TheMap(),
),
Container(
child: Center(child: Text("Page 2")),
),
Container(
child: ListPlaces(),
),
Container(
child: UniSecurityInfo(),
),
Container(
child: Preferences(),
),
],
controller: controller,
onPageChanged: (num) {
controller.animateToPage(
_navigationController.value,
curve: Curves.ease,
duration: Duration(milliseconds: 300),
);
},
),
],
),
extendBody: true,
bottomNavigationBar: CircularBottomNavigation(
tabItems,
controller: _navigationController,
selectedCallback: (int selected) {
_navigationController.value = selected;
switch (selected) {
case 0:
{
controller.animateToPage(0,
curve: Curves.easeIn,
duration: Duration(milliseconds: 300));
break;
}
case 1:
{
controller.animateToPage(1,
curve: Curves.easeIn,
duration: Duration(milliseconds: 300));
break;
}
case 2:
{
controller.animateToPage(2,
curve: Curves.easeIn,
duration: Duration(milliseconds: 300));
break;
}
case 3:
{
controller.animateToPage(3,
curve: Curves.easeIn,
duration: Duration(milliseconds: 300));
break;
}
case 4:
{
controller.animateToPage(4,
curve: Curves.easeIn,
duration: Duration(milliseconds: 300));
break;
}
}
},
),
drawer: MapDrawer(),
),
);
}
}
import 'dart:async';
import 'package:flutter/material.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:google_maps_flutter/google_maps_flutter.dart';
import 'package:geolocator/geolocator.dart';
class TheMap extends StatefulWidget {
TheMap({Key key}) : super(key: key);
_TheMapState createState() => _TheMapState();
}
class _TheMapState extends State<TheMap> with WidgetsBindingObserver {
PermissionStatus _status;
Completer<GoogleMapController> _mapController = Completer();
LatLng _centre;
Position currentLocation;
MapType _currentMapType = MapType.normal;
FutureOr<GoogleMapController> get controller => null;
// check permissions
@override
void initState() {
super.initState();
WidgetsBinding.instance.addObserver(this);
// Check location permission has been granted
PermissionHandler()
.checkPermissionStatus(PermissionGroup
.locationWhenInUse) //check permission returns a Future
.then(_updateStatus); // handling in callback to prevent blocking UI
}
//double distanceInMeters = await Geolocator().distanceBetween(52.2165157, 6.9437819, 52.3546274, 4.8285838);
// method that is called on map creation and takes a MapController as a parameter
void _onMapCreated(GoogleMapController controller) {
PermissionHandler()
.checkPermissionStatus(PermissionGroup
.locationWhenInUse) //check permission returns a Future
.then(_updateStatus); // handling in callback to prevent blocking UI
_mapController.complete(
controller); // manages camera function (position, animation, zoom).
}
Future<Position> locateUser() async {
return Geolocator()
.getCurrentPosition(desiredAccuracy: LocationAccuracy.high);
}
//TODO: Get Users' location
getUserLocation() async {
currentLocation = await locateUser();
setState(() {
_centre = LatLng(currentLocation.latitude ?? 53.467125,
currentLocation.longitude ?? -2.233966);
});
print('centre $_centre');
}
@override
Widget build(BuildContext context) {
return Stack(
children: <Widget>[
GoogleMap(
onMapCreated: _onMapCreated,
initialCameraPosition: // required parameter that sets the starting camera position. Camera position describes which part of the world you want the map to point at.
CameraPosition(
target: LatLng(53.467125, -2.233966), zoom: 14.5, tilt: 0.0),
scrollGesturesEnabled: true,
tiltGesturesEnabled: true,
compassEnabled: true,
rotateGesturesEnabled: true,
myLocationEnabled: true,
mapType: _currentMapType,
zoomGesturesEnabled: true,
),
],
);
}
@override
void dispose() {
WidgetsBinding.instance.removeObserver(this);
super.dispose();
}
// check permissions when app is resumed
// this is when permissions are changed in app settings outside of app
void didChangeAppLifecycleState(AppLifecycleState state) {
if (state == AppLifecycleState.resumed) {
PermissionHandler()
.checkPermissionStatus(PermissionGroup.locationWhenInUse)
.then(_updateStatus);
}
print("STATE -> $state");
}
/*void _askPermission() {
PermissionHandler().requestPermissions(
[PermissionGroup.locationWhenInUse]).then(_onStatusRequested);
}*/
void _onStatusRequested(Map<PermissionGroup, PermissionStatus> statuses) {
final status = statuses[PermissionGroup.locationWhenInUse];
if (status != PermissionStatus.granted) {
// On iOS if "deny" is pressed, open App Settings
PermissionHandler().openAppSettings();
} else {
//_updateStatus(status);
print("STATUS -> $status");
}
}
void _updateStatus(PermissionStatus status) {
if (status != _status) {
// check status has changed
setState(() {
_status = status; // update
_onMapCreated(controller);
});
} else {
if (status != PermissionStatus.granted) {
print("REQUESTING PERMISSION");
PermissionHandler().requestPermissions(
[PermissionGroup.locationWhenInUse]).then(_onStatusRequested);
}
}
}
}
我是不是错过了一些显而易见的东西?
非常感谢您的帮助。
感谢
我收到了一个目标!=null错误,通过添加CircularProgressIndicator((修复了此错误
children: <Widget>[
Container(
decoration: BoxDecoration(
// Login Box
image: _buildBackgroundImage(),
),
),
_userLocation == null
? CircularProgressIndicator()
: GoogleMap(
onMapCreated: _onMapCreated,
initialCameraPosition: // required parameter that sets the starting camera position. Camera position describes which part of the world you want the map to point at.
CameraPosition(
target: _userLocation,
zoom: 14.5,
tilt: 0.0), //LatLng(53.467125, -2.233966)
scrollGesturesEnabled: true,
tiltGesturesEnabled: true,
compassEnabled: true,
rotateGesturesEnabled: true,
myLocationEnabled: true,
mapType: _currentMapType,
zoomGesturesEnabled: true,
),
],