第一、发送定位
IMG_9726.png IMG_9728.png IMG_9727.pngviewController
#import "ViewController.h"
#import <MAMapKit/MAMapKit.h>
#import <AMapFoundationKit/AMapFoundationKit.h>
#import <AMapLocationKit/AMapLocationKit.h>
#import <AMapSearchKit/AMapSearchKit.h>
#import "resultTableViewCell.h"
#define mapHeight 350
@interface ViewController ()<MAMapViewDelegate,AMapLocationManagerDelegate,AMapSearchDelegate>
@property(strong,nonatomic)MAMapView * mapView;
@property(strong,nonatomic)AMapLocationManager * locationManager;//
@property(strong,nonatomic)MAPointAnnotation * centerAnnotation;
@property(strong,nonatomic)AMapSearchAPI * search;
@property(copy,nonatomic)NSArray <AMapPOI *> * pois;
@property(strong,nonatomic)UISearchController * searchC;
@end
@implementation ViewController
-(void)viewDidLoad
{
[super viewDidLoad];
[self.tableView registerNib:[UINib nibWithNibName:@"resultTableViewCell" bundle:[NSBundle mainBundle]] forCellReuseIdentifier:@"resultTableViewCellId"];
///把地图添加至view
[self.view addSubview:self.mapView];
//检索页
self.tableView.tableHeaderView = self.searchC.searchBar;
}
//移动结束地图回调
- (void)mapView:(MAMapView *)mapView mapDidMoveByUser:(BOOL)wasUserAction;
{
self.centerAnnotation.lockedToScreen = YES;
self.centerAnnotation.lockedScreenPoint = CGPointMake([UIScreen mainScreen].bounds.size.width/2 , mapHeight/2);
[mapView addAnnotation:self.centerAnnotation];
[self searchWithLatitude:self.centerAnnotation.coordinate.latitude longitude:self.centerAnnotation.coordinate.longitude];
}
/* POI 搜索回调. */
- (void)onPOISearchDone:(AMapPOISearchBaseRequest *)request response:(AMapPOISearchResponse *)response
{
if (response.pois.count == 0)
{
return;
}
if ([request isKindOfClass:[AMapPOIAroundSearchRequest class]]) {
NSLog(@"周边搜索");
}
else
{
NSLog(@"关键词搜索");
}
self.pois = response.pois;
[self.tableView reloadData];
//解析response获取POI信息,具体解析见 Demo
}
- (void)mapViewRequireLocationAuth:(CLLocationManager *)locationManager
{
}
-(void)amapLocationManager:(AMapLocationManager *)manager doRequireLocationAuth:(CLLocationManager *)locationManager
{
[locationManager requestAlwaysAuthorization];
}
- (void)updateSearchResultsForSearchController:(UISearchController *)searchController
{
[self searchWithKey:searchController.searchBar.text];
[self.tableView reloadData];
NSLog(@"编辑:%@",searchController.searchBar.text);
NSLog(@"是否活跃状态:%d",searchController.active);
}
#pragma mark - <经纬度POI搜索>
-(void)searchWithLatitude:(CGFloat)latitude longitude:(CGFloat)longitude
{
AMapPOIAroundSearchRequest *request = [[AMapPOIAroundSearchRequest alloc] init];
request.location = [AMapGeoPoint locationWithLatitude: latitude longitude:longitude];
// request.keywords = @"电影院";
/* 按照距离排序. */
request.sortrule = 0;
request.requireExtension = YES;
//
[self.search AMapPOIAroundSearch:request];
}
#pragma mark - <关键词POI搜索>
-(void)searchWithKey:(NSString *)key
{
AMapPOIKeywordsSearchRequest *request = [[AMapPOIKeywordsSearchRequest alloc] init];
request.keywords = key;
// request.city = @"北京";
// request.types = @"高等院校";
request.requireExtension = YES;
/* 搜索SDK 3.2.0 中新增加的功能,只搜索本城市的POI。*/
request.cityLimit = YES;
request.requireSubPOIs = YES;
[self.search AMapPOIKeywordsSearch:request];
}
#pragma mark - <lazy init>
-(MAMapView *)mapView
{
if (!_mapView) {
///初始化地图
_mapView = [[MAMapView alloc] initWithFrame:CGRectMake(0, 0, [UIScreen mainScreen].bounds.size.width, mapHeight)];
_mapView.mapType = MAMapTypeStandard;
_mapView.showsScale = NO;
_mapView.showsCompass = NO;
_mapView.delegate = self;
//伸缩比例
[_mapView setZoomLevel:15.1 animated:YES];
///如果您需要进入地图就显示定位小蓝点
_mapView.showsUserLocation = YES;
//追踪小蓝点
_mapView.userTrackingMode = MAUserTrackingModeFollow;
}
return _mapView;
}
-(AMapSearchAPI *)search
{
if (!_search) {
_search = [[AMapSearchAPI alloc] init];
_search.delegate = self;
}
return _search;
}
-(AMapLocationManager *)locationManager
{
if (!_locationManager) {
_locationManager = [[AMapLocationManager alloc]init];
_locationManager.delegate = self;
// 带逆地理信息的一次定位(返回坐标和地址信息)
[_locationManager setDesiredAccuracy:kCLLocationAccuracyHundredMeters];
// 定位超时时间,最低2s,此处设置为2s
_locationManager.locationTimeout =2;
// 逆地理请求超时时间,最低2s,此处设置为2s
_locationManager.reGeocodeTimeout = 2;
// 带逆地理(返回坐标和地址信息)。将下面代码中的 YES 改成 NO ,则不会返回地址信息。
[_locationManager requestLocationWithReGeocode:YES completionBlock:^(CLLocation *location, AMapLocationReGeocode *regeocode, NSError *error) {
if (error)
{
NSLog(@"locError:{%ld - %@};", (long)error.code, error.localizedDescription);
if (error.code == AMapLocationErrorLocateFailed)
{
return;
}
}
NSLog(@"latitude:%lf longitude:%lf", location.coordinate.latitude,location.coordinate.longitude);
if (regeocode)
{
NSLog(@"reGeocode:%@", regeocode);
}
[self searchWithLatitude:location.coordinate.latitude longitude:location.coordinate.longitude];
}];
}
return _locationManager;
}
-(UISearchController *)searchC
{
if (!_searchC) {
_searchC = [[UISearchController alloc]initWithSearchResultsController:nil];
_searchC.delegate = self;
_searchC.searchResultsUpdater = self;
_searchC.obscuresBackgroundDuringPresentation=NO;
}
return _searchC;
}
-(MAPointAnnotation *)centerAnnotation
{
if (!_centerAnnotation) {
_centerAnnotation = [[MAPointAnnotation alloc]init];
}
return _centerAnnotation;
}
#pragma mark - <UITableViewDataSource、UITableViewDelegate>
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return self.pois.count;
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
resultTableViewCell * cell = [tableView dequeueReusableCellWithIdentifier:@"resultTableViewCellId"];
cell.poi = self.pois[indexPath.row];
return cell;
}
-(UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section
{
return self.mapView;
}
-(CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section
{
return [self.searchC.searchBar.text isEqualToString:@""]?mapHeight:0;
}
-(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
return 60;
}
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
AMapPOI * poi = self.pois[indexPath.row];
[self.mapView setCenterCoordinate:CLLocationCoordinate2DMake(poi.location.latitude, poi.location.longitude) animated:YES];
[self searchWithLatitude:self.centerAnnotation.coordinate.latitude longitude:self.centerAnnotation.coordinate.longitude];
[self.searchC.searchBar setShowsCancelButton:NO animated:YES];
[self.searchC.searchBar resignFirstResponder];
self.searchC.searchBar.text = @"";
[self.tableView reloadData];
}
@end
resultTableViewCell
#import "resultTableViewCell.h"
@interface resultTableViewCell()
@property (weak, nonatomic) IBOutlet UILabel *titleLabel;
@property (weak, nonatomic) IBOutlet UILabel *contentLabel;
@end
@implementation resultTableViewCell
- (void)awakeFromNib {
[super awakeFromNib];
// Initialization code
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
[super setSelected:selected animated:animated];
// Configure the view for the selected state
}
-(void)setPoi:(AMapPOI *)poi
{
_poi = poi;
self.titleLabel.text = poi.name;
self.contentLabel.text = poi.address;
}
@end
Podfile
platform :ios, '9.0'
#第三方库
def third_pods
pod 'AMap3DMap'
pod 'AMapLocation'
pod 'AMapSearch'
end
#私有库
def internel_pods
end
target 'gaoDeMap' do
third_pods
target 'gaoDeMapTests' do
end
target 'gaoDeMapUITests' do
end
end
info.plist增加权限
Privacy - Location Always and When In Use Usage Description
Privacy - Location Always Usage Description
Privacy - Location When In Use Usage Description
第二、发送定位
IMG_9723.png IMG_9724.png IMG_9725.pngViewController
#import "ViewController.h"
#import <AMapLocationKit/AMapLocationKit.h>
#import "secondViewController.h"
#define kRoutePlanInfoViewHeight 200
@interface ViewController ()<AMapLocationManagerDelegate>
@property(strong,nonatomic)AMapLocationManager * locationManager;
@property(strong,nonatomic)UIButton * startBtn;
@property(strong,nonatomic)AMapNaviPoint * startPoint;
@end
@implementation ViewController
-(void)viewDidLoad
{
[super viewDidLoad];
[self.view addSubview:self.startBtn];
[self initLocationManager];
}
-(UIButton *)startBtn
{
if (!_startBtn) {
_startBtn = [[UIButton alloc]initWithFrame:CGRectMake(100, 100, 200, 50)];
[_startBtn setTitle:@"开始导航" forState:0];
_startBtn.titleLabel.font = [UIFont systemFontOfSize:30];
[_startBtn setTitleColor:[UIColor whiteColor] forState:0];
_startBtn.backgroundColor = [UIColor greenColor];
[_startBtn addTarget:self action:@selector(startAction) forControlEvents:UIControlEventTouchUpInside];
}
return _startBtn;
}
-(void)startAction
{
secondViewController * secondVC = [[secondViewController alloc]init];
secondVC.startPoint = self.startPoint;
//市民中心的经纬度
secondVC.endPoint = [AMapNaviPoint locationWithLatitude:22.5436700000 longitude:114.0596400000];
[self presentViewController:secondVC animated:YES completion:nil];
}
-(void)initLocationManager
{
if (!_locationManager) {
_locationManager = [[AMapLocationManager alloc]init];
_locationManager.delegate = self;
// 带逆地理信息的一次定位(返回坐标和地址信息)
[_locationManager setDesiredAccuracy:kCLLocationAccuracyHundredMeters];
// 定位超时时间,最低2s,此处设置为2s
_locationManager.locationTimeout =2;
// 逆地理请求超时时间,最低2s,此处设置为2s
_locationManager.reGeocodeTimeout = 2;
// 带逆地理(返回坐标和地址信息)。将下面代码中的 YES 改成 NO ,则不会返回地址信息。
[_locationManager requestLocationWithReGeocode:YES completionBlock:^(CLLocation *location, AMapLocationReGeocode *regeocode, NSError *error) {
if (error)
{
NSLog(@"locError:{%ld - %@};", (long)error.code, error.localizedDescription);
if (error.code == AMapLocationErrorLocateFailed)
{
return;
}
}
NSLog(@"latitude:%lf longitude:%lf", location.coordinate.latitude,location.coordinate.longitude);
if (regeocode)
{
NSLog(@"reGeocode:%@", regeocode);
}
//定位本地经纬度作为起始点
self.startPoint = [AMapNaviPoint locationWithLatitude:location.coordinate.latitude longitude:location.coordinate.longitude];
}];
}
}
@end
secondViewController
#import <UIKit/UIKit.h>
#import <AMapNaviKit/AMapNaviKit.h>
#import <MAMapKit/MAMapKit.h>
#import <AMapLocationKit/AMapLocationKit.h>
NS_ASSUME_NONNULL_BEGIN
@interface secondViewController : UIViewController
@property(strong,nonatomic)AMapNaviPoint * startPoint;
@property(strong,nonatomic)AMapNaviPoint * endPoint;
@end
NS_ASSUME_NONNULL_END
#import "secondViewController.h"
#import "SpeechSynthesizer.h"
@interface secondViewController ()<AMapNaviDriveViewDelegate,AMapNaviDriveManagerDelegate>
@property(strong,nonatomic)AMapNaviDriveView * driveView;
@end
@implementation secondViewController
-(void)viewDidLoad
{
[super viewDidLoad];
[self initDriveView];
[self initDriveManager];
[[AMapNaviDriveManager sharedInstance] calculateDriveRouteWithStartPoints:@[self.startPoint]
endPoints:@[self.endPoint]
wayPoints:nil
drivingStrategy:17];
}
- (void)initDriveView
{
if (self.driveView == nil)
{
self.driveView = [[AMapNaviDriveView alloc] initWithFrame:self.view.bounds];
self.driveView.autoresizingMask = UIViewAutoresizingFlexibleWidth|UIViewAutoresizingFlexibleHeight;
[self.view addSubview:self.driveView];
[self.driveView setDelegate:self];
}
}
- (void)initDriveManager
{
[[AMapNaviDriveManager sharedInstance] setDelegate:self];
//将driveView添加为导航数据的Representative,使其可以接收到导航诱导数据
[[AMapNaviDriveManager sharedInstance] addDataRepresentative:self.driveView];
}
#pragma mark - <AMapNaviDriveViewDelegate>
- (void)driveManagerOnCalculateRouteSuccess:(AMapNaviDriveManager *)driveManager
{
NSLog(@"onCalculateRouteSuccess");
//算路成功后开始GPS导航
[[AMapNaviDriveManager sharedInstance] startGPSNavi];
//显示路径或开启导航
}
- (BOOL)driveManagerIsNaviSoundPlaying:(AMapNaviDriveManager *)driveManager
{
return [[SpeechSynthesizer sharedSpeechSynthesizer] isSpeaking];
}
- (void)driveManager:(AMapNaviDriveManager *)driveManager playNaviSoundString:(NSString *)soundString soundStringType:(AMapNaviSoundType)soundStringType
{
NSLog(@"playNaviSoundString:{%ld:%@}", (long)soundStringType, soundString);
//采用系统语音播报(文字转语音)
[[SpeechSynthesizer sharedSpeechSynthesizer] speakString:soundString];
}
#pragma mark - <dealloc>
- (void)dealloc
{
[[AMapNaviDriveManager sharedInstance] stopNavi];
[[AMapNaviDriveManager sharedInstance] removeDataRepresentative:self.driveView];
[[AMapNaviDriveManager sharedInstance] setDelegate:nil];
BOOL success = [AMapNaviDriveManager destroyInstance];
NSLog(@"单例是否销毁成功 : %d",success);
}
@end
语音播报需要自己做,高德只给了我们语音的文字,我们可以采用系统的AVFoundation框架下的 SpeechSynthesizer ,也可以采用其他第三方的科大讯飞之类的 实现文字转语音
屏幕快照 2019-11-08 上午10.52.16.png创建一个单例 SpeechSynthesizer
#import <Foundation/Foundation.h>
NS_ASSUME_NONNULL_BEGIN
@interface SpeechSynthesizer : NSObject
@property(assign,nonatomic)BOOL isSpeaking;
+(instancetype)sharedSpeechSynthesizer;
-(void)speakString:(NSString *)str;
@end
NS_ASSUME_NONNULL_END
#import "SpeechSynthesizer.h"
#import <AVFoundation/AVFoundation.h>
@interface SpeechSynthesizer()<AVSpeechSynthesizerDelegate>
@property(strong,nonatomic)AVSpeechSynthesizer * avSpeaker;
@end
@implementation SpeechSynthesizer
+(instancetype)sharedSpeechSynthesizer;
{
static SpeechSynthesizer * speechSynthesizer = nil;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
if (speechSynthesizer == nil) {
speechSynthesizer = [[SpeechSynthesizer alloc]init];
//初始化语音合成器
speechSynthesizer.avSpeaker = [[AVSpeechSynthesizer alloc] init];
speechSynthesizer.avSpeaker.delegate = speechSynthesizer;
}
});
return speechSynthesizer;
}
-(void)speakString:(NSString *)str
{
//初始化要说出的内容
AVSpeechUtterance *utterance = [[AVSpeechUtterance alloc] initWithString:str];
//设置语速,语速介于AVSpeechUtteranceMaximumSpeechRate和AVSpeechUtteranceMinimumSpeechRate之间
//AVSpeechUtteranceMaximumSpeechRate
//AVSpeechUtteranceMinimumSpeechRate
//AVSpeechUtteranceDefaultSpeechRate
utterance.rate = 0.5;
//设置音高,[0.5 - 2] 默认 = 1
//AVSpeechUtteranceMaximumSpeechRate
//AVSpeechUtteranceMinimumSpeechRate
//AVSpeechUtteranceDefaultSpeechRate
utterance.pitchMultiplier = 1;
//设置音量,[0-1] 默认 = 1
utterance.volume = 1;
//读一段前的停顿时间
utterance.preUtteranceDelay = 1;
//读完一段后的停顿时间
utterance.postUtteranceDelay = 1;
//设置声音,是AVSpeechSynthesisVoice对象
//AVSpeechSynthesisVoice定义了一系列的声音, 主要是不同的语言和地区.
//voiceWithLanguage: 根据制定的语言, 获得一个声音.
//speechVoices: 获得当前设备支持的声音
//currentLanguageCode: 获得当前声音的语言字符串, 比如”ZH-cn”
//language: 获得当前的语言
//通过特定的语言获得声音
AVSpeechSynthesisVoice *voice = [AVSpeechSynthesisVoice voiceWithLanguage:@"zh-CN"];
//通过voicce标示获得声音
//AVSpeechSynthesisVoice *voice = [AVSpeechSynthesisVoice voiceWithIdentifier:AVSpeechSynthesisVoiceIdentifierAlex];
utterance.voice = voice;
//开始朗读
[[SpeechSynthesizer sharedSpeechSynthesizer].avSpeaker speakUtterance:utterance];
}
#pragma mark - AVSpeechSynthesizerDelegate
//已经开始
- (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer didStartSpeechUtterance:(AVSpeechUtterance *)utterance{
[SpeechSynthesizer sharedSpeechSynthesizer].isSpeaking = YES ;
}
//已经说完
- (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer didFinishSpeechUtterance:(AVSpeechUtterance *)utterance{
[SpeechSynthesizer sharedSpeechSynthesizer].isSpeaking = NO;
//如果朗读要循环朗读,可以在这里再次调用朗读方法
//[_avSpeaker speakUtterance:utterance];
}
//已经暂停
- (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer didPauseSpeechUtterance:(AVSpeechUtterance *)utterance{
[SpeechSynthesizer sharedSpeechSynthesizer].isSpeaking = NO;
}
//已经继续说话
- (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer didContinueSpeechUtterance:(AVSpeechUtterance *)utterance{
[SpeechSynthesizer sharedSpeechSynthesizer].isSpeaking = YES;
}
//已经取消说话
- (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer didCancelSpeechUtterance:(AVSpeechUtterance *)utterance{
[SpeechSynthesizer sharedSpeechSynthesizer].isSpeaking = NO;
}
//将要说某段话
- (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer willSpeakRangeOfSpeechString:(NSRange)characterRange utterance:(AVSpeechUtterance *)utterance{
}
@end
podfile文件
# Uncomment the next line to define a global platform for your project
platform :ios, '9.0'
#第三方库
def third_pods
pod 'AMap3DMap'
pod 'AMapLocation'
pod 'AMapSearch'
pod 'AMapNavi'
end
#私有库
def internel_pods
end
target 'gaoDeMap' do
third_pods
internel_pods
target 'gaoDeMapTests' do
end
target 'gaoDeMapUITests' do
end
end
网友评论