Flutter中使用Google Maps API加载当前位置报错求助
Flutter集成Google Maps显示当前位置报错排查
已在Flutter应用中集成Google Maps,期望地图首次加载时展示用户当前位置,参考代码实现后运行报错,流程终止于platform_channel.dart文件,报错为LateInitializationError: Field '_currentPosition' has not been initialized。
原代码
import 'dart:async'; import 'package:google_maps_flutter/google_maps_flutter.dart'; import 'package:geolocator/geolocator.dart'; import 'package:flutter/material.dart'; class MapPropertySearchResults extends StatefulWidget { const MapPropertySearchResults({super.key}); @override State<MapPropertySearchResults> createState() = _MapPropertySearchResultsState(); } class _MapPropertySearchResultsState extends State<MapPropertySearchResults> { late GoogleMapController mapController; late LatLng _currentPosition; bool _isLoading = true; @override void initState() { super.initState(); getLocation(); } getLocation() async { LocationPermission permission; permission = await Geolocator.requestPermission(); Position position = await Geolocator.getCurrentPosition( desiredAccuracy: LocationAccuracy.high); double lat = position.latitude; double long = position.longitude; LatLng location = LatLng(lat, long); setState(() { _currentPosition = location; _isLoading = false; }); } void _onMapCreated(GoogleMapController controller) { mapController = controller; } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar( title: const Text('Map'), ), body: _isLoading ? const Center(child:CircularProgressIndicator()) : GoogleMap( onMapCreated: _onMapCreated, initialCameraPosition: CameraPosition( target: _currentPosition, zoom: 16.0, ), ), ); } }
问题原因
报错核心是_currentPosition作为late修饰变量,在未完成初始化时就被GoogleMap组件访问。原代码存在以下问题:
- 未处理权限请求结果:若用户拒绝位置权限,
getCurrentPosition会直接抛出异常,导致setState从未执行,但后续可能因逻辑异常使_isLoading变为false,触发GoogleMap渲染时访问未初始化的_currentPosition。 - 无异常捕获机制:位置服务未开启、设备定位失败等场景都会导致流程中断,无法完成
_currentPosition赋值。 - 无默认位置兜底:
late变量未设置初始值,一旦赋值流程失败就会触发初始化错误。
修复后的代码
import 'dart:async'; import 'package:google_maps_flutter/google_maps_flutter.dart'; import 'package:geolocator/geolocator.dart'; import 'package:flutter/material.dart'; class MapPropertySearchResults extends StatefulWidget { const MapPropertySearchResults({super.key}); @override State<MapPropertySearchResults> createState() => _MapPropertySearchResultsState(); } class _MapPropertySearchResultsState extends State<MapPropertySearchResults> { late GoogleMapController mapController; // 设置默认位置(示例为北京中心点),避免late变量未初始化问题 LatLng _currentPosition = const LatLng(39.9042, 116.4074); bool _isLoading = true; String? _errorMsg; @override void initState() { super.initState(); getLocation(); } getLocation() async { try { // 检查权限状态 LocationPermission permission = await Geolocator.requestPermission(); if (permission == LocationPermission.denied || permission == LocationPermission.deniedForever) { setState(() { _errorMsg = "位置权限被拒绝,无法获取当前位置"; _isLoading = false; }); return; } // 检查位置服务是否开启 bool serviceEnabled = await Geolocator.isLocationServiceEnabled(); if (!serviceEnabled) { setState(() { _errorMsg = "位置服务未开启,请前往设置开启"; _isLoading = false; }); return; } // 获取当前位置 Position position = await Geolocator.getCurrentPosition( desiredAccuracy: LocationAccuracy.high); LatLng location = LatLng(position.latitude, position.longitude); setState(() { _currentPosition = location; _isLoading = false; }); } catch (e) { setState(() { _errorMsg = "获取位置失败:${e.toString()}"; _isLoading = false; }); } } void _onMapCreated(GoogleMapController controller) { mapController = controller; } @override Widget build(BuildContext context) { return Scaffold( appBar: const AppBar( title: Text('Map'), ), body: _isLoading ? const Center(child: CircularProgressIndicator()) : _errorMsg != null ? Center(child: Text(_errorMsg!)) : GoogleMap( onMapCreated: _onMapCreated, initialCameraPosition: CameraPosition( target: _currentPosition, zoom: 16.0, ), myLocationEnabled: true, // 开启内置的当前位置标记 ), ); } }
关键修改点
- 给
_currentPosition设置默认初始值,彻底避免late变量未初始化错误。 - 增加权限状态判断,处理权限被拒绝的场景,给出友好提示。
- 检查位置服务是否开启,提前拦截无效请求。
- 用
try-catch包裹整个定位流程,捕获所有可能的异常并处理。 - 开启GoogleMap的
myLocationEnabled属性,直接显示系统提供的当前位置标记。
内容的提问来源于stack exchange,提问作者LostTexan
相关产品推荐
相关产品推荐

