Flutter---实现定位+范围限制(距离目的地1000米才能打卡)
2023年7月4日发(作者:)
Flutter----实现定位+范围限制(距离⽬的地1000⽶才能打卡)需求:1.实现设备的定位2.当前位置和⽬标位置的1000⽶范围内才能打卡该页⾯就是简单的进去的时候就获取定位,如果定位获取到了就停⽌定位,并toast是否可以打卡的消息。采⽤的定位的插件:flutter_bmflocation: ^2.0.0-nullsafety.0##为什么使⽤百度地图的插件?⽽不是其他的插件采⽤的是百度地图的插件,这个星期尝试了三个插件,第⼀个最先使⽤的location插件,不需要申请啥开发者啥的直接可以⽤的,但是悲哀的是时不时会失灵的,怀疑是⽹络问题,回调死活进不去。第⼆个尝试的是⾼德地图的,为什么呢,搜索的时候⼤家都⽤⾼德的,所以我也去试验了⼀下,但是⾼德地图明显很久没有维护了,现在flutter是空安全的,但是它明显是⽼的,不⽀持空安全,导致调试的时候⾮常⿇烦,虽然可以⽤,但是为了以后⽅便还是被pass。然后选择了百度,明显百度有在维护,有⽀持空安全和不⽀持空安全的版本,所以选择了它。// Copyright 2013 The Flutter Authors. All rights reserved.// Use of this source code is governed by a BSD-style license that can be// found in the LICENSE file.// ignore_for_file: public_member_api_docsimport 'dart:async';import 'dart:math';import 'package:app_flutter/common/';import 'package:flutter/';import 'package:flutter/';import 'package:flutter/';import 'package:flutter_bmflocation/bdmap_location_flutter_';import 'package:flutter_bmflocation/flutter_baidu_';import 'package:flutter_bmflocation/flutter_baidu_location_android_';import 'package:flutter_bmflocation/flutter_baidu_location_ios_';class ImageUploadRoute extends StatefulWidget { ImageUploadRoute({Key? key, }) : super(key: key); final String? title; @override _ImageUploadState createState() => _ImageUploadState();}class _ImageUploadState extends State { //编辑⽂本 late TextEditingController _controller;
//定位相关 double lat1=0.0;//当前的维度 double lng1=0.0;//当前的经度 double lat2=0.0;//⽬的地的维度 double lng2=0.0;//⽬的地的经度 int limitMmeters=1000;//限制上传的距离,⼀公⾥范围内 late Map? _loationResult=null; BaiduLocation? _baiduLocation; late StreamSubscription
//初始化的时候打开定位相关 @override void initState() { ate(); _controller = TextEditingController(); /// 动态申请定位权限 _tPermission(); /// 设置ios端ak, android端ak可以直接在清单⽂件中配置 Key("jInwiO1AhcbkZyz0Z9ZL9fC88pThdGZP"); _locationListener = _ltCallback().listen((Map? result) { setState(() { _loationResult = result; print("longitude$result['longitude']"); try { _baiduLocation = p(result); isInArea();// print(_baiduLocation); } catch (e) { print(e); } }); }); _startLocation();//开启位置监听 } @override void dispose() { _e(); e(); if (null != _locationListener) { _(); } } /// 设置android端和ios端定位参数 void _setLocOption() { /// android 端设置定位参数 BaiduLocationAndroidOption androidOption = new BaiduLocationAndroidOption(); rType("bd09ll"); // 设置返回的位置坐标系类型 eedAltitude(true); // 设置是否需要返回海拔⾼度信息 eedAddres(true); // 设置是否需要返回地址信息 eedLocationPoiList(true); // 设置是否需要返回周边poi信息 eedNewVersionRgc(true); // 设置是否需要返回最新版本rgc信息 eedLocationDescribe(true); // 设置是否需要返回位置描述 nGps(true); // 设置是否需要使⽤gps ationMode(_Accuracy); // 设置定位模式 nspan(1000); // 设置发起定位请求时间间隔 Map androidMap = (); /// ios 端设置定位参数 BaiduLocationIOSOption iosOption = new BaiduLocationIOSOption(); eedNewVersionRgc(true); // 设置是否需要返回最新版本rgc信息 LocationCoordinateType( "BMKLocationCoordinateTypeBMK09LL"); // 设置返回的位置坐标系类型 ivityType("CLActivityTypeAutomotiveNavigation"); // 设置应⽤位置类型 ationTimeout(10); // 设置位置获取超时时间 iredAccuracy("kCLLocationAccuracyBest"); // 设置预期精度参数 eocodeTimeout(10); // 设置获取地址信息超时时间 tanceFilter(100); // 设置定位最⼩更新距离 owsBackgroundLocationUpdates(true); // 是否允许后台定位 seLocUpdateAutomatically(true); // 定位是否会被系统⾃动暂停 Map iosMap = (); _eLoc(androidMap, iosMap); } /// 启动定位 void _startLocation() { if (null != _locationPlugin) { if (null != _locationPlugin) { _setLocOption(); _ocation(); } } /// 停⽌定位 void _stopLocation() { if (null != _locationPlugin) { _cation(); } } double _rad(double d) { return d * pi / 180.0; } double _getDistance(double lat1, double lng1, double lat2, double lng2) { /// 单位:⽶ /// def :地球半径 double def = 6378137.0; double radLat1 = _rad(lat1); double radLat2 = _rad(lat2); double a = radLat1 - radLat2; double b = _rad(lng1) - _rad(lng2); double s = 2 * asin(sqrt(pow(sin(a / 2), 2) + cos(radLat1) * cos(radLat2) * pow(sin(b / 2), 2))); return (s * def ).roundToDouble(); } //是否在范围内? void isInArea(){ lat1=_baiduLocation?.latitude??0;//如果没值 那么0 lng1=_baiduLocation?.longitude??0;//如果没值 那么0 double distance=_getDistance(lat1,lng1,lat2,lng2); if(lat1!=0&&lng1!=0){//正确的获取到了坐标 if(limitMmeters>=distance){//在范围内允许 nterToast("允许打卡"); _stopLocation(); }else{//在范围外 nterToast("不在范围内,当前距离⽬标位置$distance⽶,打卡范围为$limitMmeters⽶"); _stopLocation(); } }else{ nterToast("位置获取中!"); } } //页⾯的控件布局 @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar(title: Text("定位"),), body:Stack( children: [ Positioned(//占满屏幕 top: 0, bottom: 0, left: 0, right: 0, child: Column( children: [ children: [ TextField( maxLines: 10, minLines: 3, controller:_controller, decoration:InputDecoration( border: , fillColor: , filled: true, hintText: "签收情况", ), ), ], )), ], ) ); }}
发布者:admin,转转请注明出处:http://www.yc00.com/xiaochengxu/1688420978a135835.html
评论列表(0条)