แอพของฉันที่ทำงานได้ดีบน iOS 7 ไม่สามารถทำงานกับ iOS 8 SDK
CLLocationManager
ไม่ส่งคืนตำแหน่งและฉันไม่เห็นแอปของฉันภายใต้การตั้งค่า -> บริการระบุตำแหน่ง ฉันทำการค้นหาโดย Google เกี่ยวกับปัญหานี้ แต่ไม่มีอะไรเกิดขึ้น มีอะไรผิดปกติ?
แอพของฉันที่ทำงานได้ดีบน iOS 7 ไม่สามารถทำงานกับ iOS 8 SDK
CLLocationManager
ไม่ส่งคืนตำแหน่งและฉันไม่เห็นแอปของฉันภายใต้การตั้งค่า -> บริการระบุตำแหน่ง ฉันทำการค้นหาโดย Google เกี่ยวกับปัญหานี้ แต่ไม่มีอะไรเกิดขึ้น มีอะไรผิดปกติ?
คำตอบ:
ฉันลงเอยด้วยการแก้ปัญหาของตัวเอง
เห็นได้ชัดว่าใน iOS 8 SDK requestAlwaysAuthorization
(สำหรับตำแหน่งพื้นหลัง) หรือrequestWhenInUseAuthorization
(เฉพาะตำแหน่งที่อยู่ด้านหน้า) CLLocationManager
จะต้องทำการโทรก่อนที่จะเริ่มอัปเดตตำแหน่ง
นอกจากนี้ยังมีความต้องการที่จะNSLocationAlwaysUsageDescription
หรือNSLocationWhenInUseUsageDescription
สำคัญในการInfo.plist
ที่มีข้อความที่จะแสดงในพรอมต์ การเพิ่มสิ่งเหล่านี้ช่วยแก้ปัญหาของฉันได้
หวังว่ามันจะช่วยคนอื่น
แก้ไข: สำหรับข้อมูลเพิ่มเติมเพิ่มเติมดูได้ที่: Core-Location-Manager-Changes-in-ios-8
ฉันกำลังดึงผมออกด้วยปัญหาเดียวกัน Xcode ให้ข้อผิดพลาด:
กำลังพยายามเริ่ม
MapKit
การอัปเดตตำแหน่งโดยไม่ต้องแจ้งขออนุมัติตำแหน่ง ต้องโทร-[CLLocationManager requestWhenInUseAuthorization]
หรือ-[CLLocationManager requestAlwaysAuthorization]
ก่อน
แต่แม้ว่าคุณจะใช้วิธีใดวิธีหนึ่งดังกล่าวข้างต้นก็จะไม่แจ้งให้ผู้ใช้จนกว่าจะมีรายการใน info.plist สำหรับหรือNSLocationAlwaysUsageDescription
NSLocationWhenInUseUsageDescription
เพิ่มบรรทัดต่อไปนี้ใน info.plist ของคุณโดยที่ค่าสตริงแสดงถึงเหตุผลที่คุณต้องการเข้าถึงตำแหน่งผู้ใช้
<key>NSLocationWhenInUseUsageDescription</key>
<string>This application requires location services to work</string>
<key>NSLocationAlwaysUsageDescription</key>
<string>This application requires location services to work</string>
ฉันคิดว่ารายการเหล่านี้อาจหายไปตั้งแต่ฉันเริ่มโครงการนี้ใน Xcode 5 ฉันเดาว่า Xcode 6 อาจเพิ่มรายการเริ่มต้นสำหรับคีย์เหล่านี้ แต่ยังไม่ได้รับการยืนยัน
คุณสามารถหาข้อมูลเพิ่มเติมเกี่ยวกับการตั้งค่าทั้งสองนี้ได้ที่นี่
เพื่อให้แน่ใจว่าสามารถใช้งานร่วมกับ iOS 7 ได้คุณควรตรวจสอบว่าผู้ใช้นั้นใช้งาน iOS 8 หรือ iOS 7 หรือไม่ตัวอย่างเช่น
#define IS_OS_8_OR_LATER ([[[UIDevice currentDevice] systemVersion] floatValue] >= 8.0)
//In ViewDidLoad
if(IS_OS_8_OR_LATER) {
[self.locationManager requestAlwaysAuthorization];
}
[self.locationManager startUpdatingLocation];
if ([self.locationManager respondsToSelector:@selector(requestAlwaysAuthorization)]) { ...
requestAlwaysAuthorization
วิธีการคืออะไร วิธีการแก้ปัญหาเพิ่มเติมของฉันคือการใช้สายนี้ในคำสั่งแทนการเรียกวิธีปกติ:if
[self.locationManager performSelector:@selector(requestAlwaysAuthorization)];
บางทีนี่อาจจะเป็นที่เห็นได้ชัดสำหรับคนอื่น ๆ แต่มันใช้เวลาพอสมควรที่จะคิดออก ฉันคิดว่ามันเป็นทางออกที่ถูกต้องจนกว่า Xcode 6 สุดท้ายจะวางจำหน่าย
__IPHONE_OS_VERSION_MAX_ALLOWED
( #if __IPHONE_OS_VERSION_MAX_ALLOWED >= 80000
)
- (void)startLocationManager
{
locationManager = [[CLLocationManager alloc] init];
locationManager.delegate = self;
locationManager.distanceFilter = kCLDistanceFilterNone; //whenever we move
locationManager.desiredAccuracy = kCLLocationAccuracyBest;
[locationManager startUpdatingLocation];
[locationManager requestWhenInUseAuthorization]; // Add This Line
}
และไปยังไฟล์ info.plist ของคุณ
ตามเอกสารของ Apple:
ตั้งแต่ iOS 8 ต้องมี a NSLocationWhenInUseUsageDescription
หรือNSLocationAlwaysUsageDescription
ค่าคีย์ในไฟล์ Info.plist ของแอปของคุณ นอกจากนี้ยังจำเป็นต้องขออนุญาตจากผู้ใช้ก่อนที่จะลงทะเบียนเพื่ออัปเดตตำแหน่งไม่ว่าจะเป็นการโทร[self.myLocationManager requestWhenInUseAuthorization]
หรือ[self.myLocationManager requestAlwaysAuthorization]
ขึ้นอยู่กับความต้องการของคุณ สตริงที่คุณป้อนลงใน Info.plist จะปรากฏขึ้นในกล่องโต้ตอบที่ตามมา
หากผู้ใช้ให้สิทธิ์มันเป็นธุรกิจตามปกติ หากพวกเขาปฏิเสธการอนุญาตตัวแทนจะไม่ได้รับแจ้งการอัปเดตตำแหน่ง
- (void)viewDidLoad
{
[super viewDidLoad];
self.locationManager = [[CLLocationManager alloc] init];
self.locationManager.delegate = self;
if([self.locationManager respondsToSelector:@selector(requestAlwaysAuthorization)]){
NSUInteger code = [CLLocationManager authorizationStatus];
if (code == kCLAuthorizationStatusNotDetermined && ([self.locationManager respondsToSelector:@selector(requestAlwaysAuthorization)] || [self.locationManager respondsToSelector:@selector(requestWhenInUseAuthorization)])) {
// choose one request according to your business.
if([[NSBundle mainBundle] objectForInfoDictionaryKey:@"NSLocationAlwaysUsageDescription"]){
[self.locationManager requestAlwaysAuthorization];
} else if([[NSBundle mainBundle] objectForInfoDictionaryKey:@"NSLocationWhenInUseUsageDescription"]) {
[self.locationManager requestWhenInUseAuthorization];
} else {
NSLog(@"Info.plist does not contain NSLocationAlwaysUsageDescription or NSLocationWhenInUseUsageDescription");
}
}
}
[self.locationManager startUpdatingLocation];
}
> #pragma mark - CLLocationManagerDelegate
- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error
{
NSLog(@"didFailWithError: %@", error);
UIAlertView *errorAlert = [[UIAlertView alloc]
initWithTitle:@"Error" message:@"Failed to Get Your Location" delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil];
[errorAlert show];
}
- (void)locationManager:(CLLocationManager *)manager didUpdateToLocation:(CLLocation *)newLocation fromLocation:(CLLocation *)oldLocation
{
NSLog(@"didUpdateToLocation: %@", newLocation);
CLLocation *currentLocation = newLocation;
if (currentLocation != nil) {
longitudeLabel.text = [NSString stringWithFormat:@"%.8f", currentLocation.coordinate.longitude];
latitudeLabel.text = [NSString stringWithFormat:@"%.8f", currentLocation.coordinate.latitude];
}
}
ใน iOS 8 คุณต้องทำสองสิ่งพิเศษเพื่อให้ตำแหน่งทำงานได้: เพิ่มรหัสลงใน Info.plist ของคุณและขอการอนุญาตจากผู้จัดการสถานที่เพื่อขอให้เริ่ม มีปุ่ม Info.plist สองปุ่มสำหรับการอนุมัติตำแหน่งใหม่ ต้องใช้หนึ่งหรือทั้งสองคีย์นี้ หากไม่มีคีย์ใดอยู่คุณสามารถเรียกใช้ startUpdatingLocation ได้ แต่ตัวจัดการตำแหน่งจะไม่เริ่มต้นจริง ๆ มันจะไม่ส่งข้อความความล้มเหลวไปยังผู้รับมอบสิทธิ์อย่างใดอย่างหนึ่ง (เนื่องจากไม่เคยเริ่มเลยก็ไม่สามารถล้มเหลว) มันจะล้มเหลวถ้าคุณเพิ่มคีย์หนึ่งหรือทั้งสองอย่าง แต่ลืมขออนุญาตอย่างชัดเจน ดังนั้นสิ่งแรกที่คุณต้องทำคือการเพิ่มคีย์อย่างใดอย่างหนึ่งหรือทั้งสองอย่างต่อไปนี้ลงในไฟล์ Info.plist ของคุณ:
คีย์ทั้งสองนี้ใช้เป็นสตริง
ซึ่งเป็นคำอธิบายว่าทำไมคุณถึงต้องใช้บริการหาที่ตั้ง คุณสามารถป้อนสตริงเช่น“ ต้องระบุตำแหน่งเพื่อค้นหาว่าคุณอยู่ที่ไหน” ซึ่งใน iOS 7 สามารถแปลเป็นภาษาท้องถิ่นได้ในไฟล์ InfoPlist.strings
โซลูชันของฉันซึ่งสามารถรวบรวมได้ใน Xcode 5:
#ifdef __IPHONE_8_0
NSUInteger code = [CLLocationManager authorizationStatus];
if (code == kCLAuthorizationStatusNotDetermined && ([self.locationManager respondsToSelector:@selector(requestAlwaysAuthorization)] || [self.locationManager respondsToSelector:@selector(requestWhenInUseAuthorization)])) {
// choose one request according to your business.
if([[NSBundle mainBundle] objectForInfoDictionaryKey:@"NSLocationAlwaysUsageDescription"]){
[self.locationManager requestAlwaysAuthorization];
} else if([[NSBundle mainBundle] objectForInfoDictionaryKey:@"NSLocationWhenInUseUsageDescription"]) {
[self.locationManager requestWhenInUseAuthorization];
} else {
NSLog(@"Info.plist does not contain NSLocationAlwaysUsageDescription or NSLocationWhenInUseUsageDescription");
}
}
#endif
[self.locationManager startUpdatingLocation];
รหัสเก่าสำหรับการถามตำแหน่งจะไม่ทำงานใน iOS 8 คุณสามารถลองวิธีนี้เพื่อขออนุมัติตำแหน่ง:
- (void)requestAlwaysAuthorization
{
CLAuthorizationStatus status = [CLLocationManager authorizationStatus];
// If the status is denied or only granted for when in use, display an alert
if (status == kCLAuthorizationStatusAuthorizedWhenInUse || status == kCLAuthorizationStatusDenied) {
NSString *title;
title = (status == kCLAuthorizationStatusDenied) ? @"Location services are off" : @"Background location is not enabled";
NSString *message = @"To use background location you must turn on 'Always' in the Location Services Settings";
UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:title
message:message
delegate:self
cancelButtonTitle:@"Cancel"
otherButtonTitles:@"Settings", nil];
[alertView show];
}
// The user has not enabled any location services. Request background authorization.
else if (status == kCLAuthorizationStatusNotDetermined) {
[self.locationManager requestAlwaysAuthorization];
}
}
- (void)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(NSInteger)buttonIndex
{
if (buttonIndex == 1) {
// Send the user to the Settings for this app
NSURL *settingsURL = [NSURL URLWithString:UIApplicationOpenSettingsURLString];
[[UIApplication sharedApplication] openURL:settingsURL];
}
}
ใน iOS 8 คุณต้องทำสองสิ่งพิเศษเพื่อให้ตำแหน่งทำงานได้: เพิ่มรหัสลงใน Info.plist ของคุณและขอการอนุญาตจากผู้จัดการสถานที่เพื่อขอให้เริ่ม
info.plist:
<key>NSLocationUsageDescription</key>
<string>I need location</string>
<key>NSLocationAlwaysUsageDescription</key>
<string>I need location</string>
<key>NSLocationWhenInUseUsageDescription</key>
<string>I need location</string>
เพิ่มไปยังรหัสของคุณ
if (IS_OS_8_OR_LATER)
{
[locationmanager requestWhenInUseAuthorization];
[locationmanager requestAlwaysAuthorization];
}
ข้อผิดพลาดทั่วไปหนึ่งข้อสำหรับนักพัฒนา Swift:
ทำให้แน่ใจว่าคุณแรกเพิ่มมูลค่าให้กับ plist สำหรับการอย่างใดอย่างหนึ่งหรือNSLocationWhenInUseUsageDescription
NSLocationAlwaysUsageDescription
หากคุณยังไม่เห็นหน้าต่างปรากฏขึ้นเพื่อขอการอนุญาตให้ดูเพื่อดูว่าคุณวางบรรทัดvar locationManager = CLLocationManager()
ในวิธีการของ View Controller viewDidLoad
หรือไม่ ถ้าคุณทำเช่นนั้นแม้ว่าคุณจะโทรlocationManager.requestWhenInUseAuthorization()
มา นี่เป็นเพราะหลังจากที่ viewDidLoad ดำเนินการตัวแปร locationManager จะถูกจัดสรรคืน
การแก้ปัญหาคือการหาบรรทัดvar locationManager = CLLocationManager()
ที่ด้านบนของวิธีการเรียน
ก่อน[locationManager startUpdatingLocation];
เพิ่มคำขอบริการระบุตำแหน่ง iOS8:
if([locationManager respondsToSelector:@selector(requestAlwaysAuthorization)])
[locationManager requestAlwaysAuthorization];
แก้ไขแอปInfo.plist
และเพิ่มคีย์NSLocationAlwaysUsageDescription
ด้วยค่าสตริงที่จะแสดงต่อผู้ใช้ (ตัวอย่างเช่นWe do our best to preserve your battery life.
)
หากแอปของคุณต้องการบริการระบุตำแหน่งขณะที่แอปเปิดอยู่ให้แทนที่:
requestAlwaysAuthorization
ด้วยrequestWhenInUseAuthorization
และ
NSLocationAlwaysUsageDescription
NSLocationWhenInUseUsageDescription
กับ
ฉันทำงานกับแอพที่อัปเกรดเป็น iOS 8 และบริการระบุตำแหน่งหยุดทำงาน คุณอาจได้รับและเกิดข้อผิดพลาดในพื้นที่ Debug ดังนี้:
Trying to start MapKit location updates without prompting for location authorization. Must call -[CLLocationManager requestWhenInUseAuthorization] or -[CLLocationManager requestAlwaysAuthorization] first.
ฉันทำขั้นตอนที่รบกวนน้อยที่สุด เพิ่มNSLocationAlwaysUsageDescription
รายการแรกลงใน info.plist ของคุณ:
แจ้งให้ทราบฉันไม่ได้กรอกค่าสำหรับคีย์นี้ ยังใช้งานได้และฉันไม่ได้กังวลเพราะนี่เป็นแอพในบ้าน นอกจากนี้มีชื่อเรื่องที่ขอให้ใช้บริการระบุตำแหน่งดังนั้นฉันจึงไม่ต้องการทำอะไรซ้ำซ้อน
ต่อไปฉันสร้างเงื่อนไขสำหรับ iOS 8:
if ([self.locationManager respondsToSelector:@selector(requestAlwaysAuthorization)]) {
[_locationManager requestAlwaysAuthorization];
}
หลังจากนี้locationManager:didChangeAuthorizationStatus:
วิธีการโทร:
- (void)locationManager:(CLLocationManager *)manager didChangeAuthorizationStatus: (CLAuthorizationStatus)status
{
[self gotoCurrenLocation];
}
โซลูชันที่มีความเข้ากันได้แบบย้อนหลัง:
SEL requestSelector = NSSelectorFromString(@"requestWhenInUseAuthorization");
if ([CLLocationManager authorizationStatus] == kCLAuthorizationStatusNotDetermined &&
[self.locationManager respondsToSelector:requestSelector]) {
[self.locationManager performSelector:requestSelector withObject:NULL];
} else {
[self.locationManager startUpdatingLocation];
}
ตั้งค่าคีย์ NSLocationWhenInUseUsageDescription ใน Info.plist ของคุณ
locationManager: (CLLocationManager *)manager didFailWithError: (NSError *)error
คุณควรจะจัดการกับตัวเองว่า อย่างไรก็ตามเขาลืมเพิ่ม startUpdatingLocation ไปที่คำสั่ง if ดังนั้นหลังจากที่พวกเขายอมรับหรือปฏิเสธมันก็ไม่ได้เรียก startUpdateLocation
โซลูชันที่มีความเข้ากันได้แบบย้อนกลับซึ่งไม่ได้สร้างคำเตือน Xcode:
SEL requestSelector = NSSelectorFromString(@"requestWhenInUseAuthorization");
if ([CLLocationManager authorizationStatus] == kCLAuthorizationStatusNotDetermined &&
[self.locationManager respondsToSelector:requestSelector]) {
((void (*)(id, SEL))[self.locationManager methodForSelector:requestSelector])(self.locationManager, requestSelector);
[self.locationManager startUpdatingLocation];
} else {
[self.locationManager startUpdatingLocation];
}
การตั้งค่าที่สำคัญในของคุณNSLocationWhenInUseUsageDescription
Info.plist
สำหรับ iOS เวอร์ชัน 11.0 ขึ้นไปติดตั้งที่สำคัญในของคุณNSLocationAlwaysAndWhenInUseUsageDescription
Info.plist
พร้อมกับปุ่มอื่น ๆ 2 ปุ่ม
นี่เป็นปัญหากับ iOS 8 เพิ่มลงในรหัสของคุณ
if (IS_OS_8_OR_LATER)
{
[locationmanager requestWhenInUseAuthorization];
[locationmanager requestAlwaysAuthorization];
}
และไปที่ info.plist:
<key>NSLocationUsageDescription</key>
<string>I need location</string>
<key>NSLocationAlwaysUsageDescription</key>
<string>I need location</string>
<key>NSLocationWhenInUseUsageDescription</key>
<string>I need location</string>
NSLocationUsageDescription
ไม่ได้ใช้บน iOS8 +
ในการเข้าถึงตำแหน่งผู้ใช้ใน iOS 8 คุณจะต้องเพิ่ม
NSLocationAlwaysUsageDescription in the Info.plist
การดำเนินการนี้จะขอให้ผู้ใช้รับสิทธิ์ในการรับตำแหน่งปัจจุบัน
Objective-C ขั้นตอน ปฏิบัติตามคำแนะนำด้านล่าง:
สำหรับ iOS-11 สำหรับ iOS 11 ให้ดูที่คำตอบนี้:การเข้าถึงตำแหน่ง iOS 11
จำเป็นต้องเพิ่มสองปุ่มลงใน plist และส่งข้อความดังภาพด้านล่าง:
1. NSLocationAlwaysAndWhenInUseUsageDescription
2. NSLocationWhenInUseUsageDescription
3. NSLocationAlwaysUsageDescription
NSLocationWhenInUseUsageDescription
locationManager = [[CLLocationManager alloc] init];
locationManager.delegate = self;
locationManager.desiredAccuracy = kCLLocationAccuracyThreeKilometers;
if([locationManager respondsToSelector:@selector(requestWhenInUseAuthorization)]){
[locationManager requestWhenInUseAuthorization];
}else{
[locationManager startUpdatingLocation];
}
วิธีการมอบหมาย
#pragma mark - Lolcation Update
- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error
{
NSLog(@"didFailWithError: %@", error);
UIAlertView *errorAlert = [[UIAlertView alloc]
initWithTitle:@"Error" message:@"Failed to Get Your Location" delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil];
[errorAlert show];
}
-(void)locationManager:(CLLocationManager *)manager didChangeAuthorizationStatus:(CLAuthorizationStatus)status
{
switch (status) {
case kCLAuthorizationStatusNotDetermined:
case kCLAuthorizationStatusRestricted:
case kCLAuthorizationStatusDenied:
{
// do some error handling
}
break;
default:{
[locationManager startUpdatingLocation];
}
break;
}
}
- (void)locationManager:(CLLocationManager *)manager
didUpdateLocations:(NSArray *)locations
{
CLLocation *location = [locations lastObject];
userLatitude = [NSString stringWithFormat:@"%f", location.coordinate.latitude] ;
userLongitude = [NSString stringWithFormat:@"%f",location.coordinate.longitude];
[locationManager stopUpdatingLocation];
}
ขั้นตอนที่รวดเร็ว
ทำตามคำแนะนำด้านล่าง:
สำหรับ iOS-11 สำหรับ iOS 11 ให้ดูที่คำตอบนี้:การเข้าถึงตำแหน่ง iOS 11
จำเป็นต้องเพิ่มสองปุ่มลงใน plist และส่งข้อความดังภาพด้านล่าง:
1. NSLocationAlwaysAndWhenInUseUsageDescription
2. NSLocationWhenInUseUsageDescription
3. NSLocationAlwaysUsageDescription
import CoreLocation
class ViewController: UIViewController ,CLLocationManagerDelegate {
var locationManager = CLLocationManager()
//MARK- Update Location
func updateMyLocation(){
locationManager.delegate = self;
locationManager.desiredAccuracy = kCLLocationAccuracyThreeKilometers;
if locationManager.respondsToSelector(#selector(CLLocationManager.requestWhenInUseAuthorization)){
locationManager.requestWhenInUseAuthorization()
}
else{
locationManager.startUpdatingLocation()
}
}
วิธีการมอบหมาย
//MARK: Location Update
func locationManager(manager: CLLocationManager, didFailWithError error: NSError) {
NSLog("Error to update location :%@",error)
}
func locationManager(manager: CLLocationManager, didChangeAuthorizationStatus status: CLAuthorizationStatus) {
switch status {
case .NotDetermined: break
case .Restricted: break
case .Denied:
NSLog("do some error handling")
break
default:
locationManager.startUpdatingLocation()
}
}
func locationManager(manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
let location = locations.last! as CLLocation
var latitude = location.coordinate.latitude
var longitude = location.coordinate.longitude
}
สำหรับผู้ที่ใช้Xamarinฉันต้องเพิ่มคีย์NSLocationWhenInUseUsageDescription
ไปที่ info.plist ด้วยตนเองเนื่องจากไม่สามารถใช้งานได้ในรายการแบบเลื่อนลงทั้งใน Xamarin 5.5.3 Build 6 หรือ XCode 6.1 - มี NSLocationUsageDescription
อยู่ในรายการเท่านั้นและนั่นทำให้CLLocationManager
ต้องดำเนินการต่อไป ล้มเหลวอย่างเงียบ ๆ
// ** Don't forget to add NSLocationWhenInUseUsageDescription in MyApp-Info.plist and give it a string
self.locationManager = [[CLLocationManager alloc] init];
self.locationManager.delegate = self;
// Check for iOS 8. Without this guard the code will crash with "unknown selector" on iOS 7.
if ([self.locationManager respondsToSelector:@selector(requestWhenInUseAuthorization)]) {
[self.locationManager requestWhenInUseAuthorization];
}
[self.locationManager startUpdatingLocation];
// Location Manager Delegate Methods
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations
{
NSLog(@"%@", [locations lastObject]);
}
ผู้ช่วยเล็ก ๆ น้อย ๆ สำหรับคุณทุกคนที่มีไฟล์ Info.plist มากกว่าหนึ่งไฟล์ ...
find . -name Info.plist | xargs -I {} /usr/libexec/PlistBuddy -c 'Add NSLocationWhenInUseUsageDescription string' {}
มันจะเพิ่มแท็กที่จำเป็นลงในไฟล์ Info.plist ทั้งหมดในไดเรกทอรีปัจจุบัน (และโฟลเดอร์ย่อย)
อีกอย่างคือ:
find . -name Info.plist | xargs -I {} /usr/libexec/PlistBuddy -c 'Set NSLocationWhenInUseUsageDescription $YOURDESCRIPTION' {}
มันจะเพิ่มคำอธิบายของคุณไปยังไฟล์ทั้งหมด
เก็บกุญแจโกโก้ข้อมูลไว้ที่ปลายนิ้วของคุณเสมอสำหรับการอัปเดตเหล่านี้นี่คือลิงค์:
สนุก.
ฉันได้รับข้อผิดพลาดที่คล้ายกันใน iOS9 (ทำงานกับ Xcode 7 และ Swift 2): พยายามเริ่มการอัปเดตตำแหน่ง MapKit โดยไม่แจ้งให้ขออนุญาตระบุตำแหน่ง ต้องเรียก - [CLLocationManager RequestWhenInUseAuthorization] หรือ - [CLLocationManager requestAlwaysAuthorization] ก่อน ฉันกำลังติดตามกวดวิชา แต่ผู้สอนใช้ iOS8 และ Swift 1.2 มีการเปลี่ยนแปลงบางอย่างใน Xcode 7 และ Swift 2 ฉันพบรหัสนี้และทำงานได้ดีสำหรับฉัน (ถ้ามีคนต้องการความช่วยเหลือ):
import UIKit
import MapKit
import CoreLocation
class MapViewController: UIViewController, MKMapViewDelegate, CLLocationManagerDelegate {
// MARK: Properties
@IBOutlet weak var mapView: MKMapView!
let locationManager = CLLocationManager()
override func viewDidLoad() {
super.viewDidLoad()
self.locationManager.delegate = self
self.locationManager.desiredAccuracy = kCLLocationAccuracyBest
self.locationManager.requestWhenInUseAuthorization()
self.locationManager.startUpdatingLocation()
self.mapView.showsUserLocation = true
}
// MARK: - Location Delegate Methods
func locationManager(manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
let location = locations.last
let center = CLLocationCoordinate2D(latitude: location!.coordinate.latitude, longitude: location!.coordinate.longitude)
let region = MKCoordinateRegion(center: center, span: MKCoordinateSpan(latitudeDelta: 1, longitudeDelta: 1))
self.mapView.setRegion(region, animated: true)
}
func locationManager(manager: CLLocationManager, didFailWithError error: NSError) {
print("Errors: " + error.localizedDescription)
}
}
ในที่สุดฉันก็ใส่ข้อมูลนั้นไว้ใน info.plist: รายการคุณสมบัติข้อมูล: NSLocationWhenInUseUsageDescription Value: แอปต้องการเซิร์ฟเวอร์ตำแหน่งที่ตั้งสำหรับพนักงาน
เพื่อเข้าถึงตำแหน่งผู้ใช้ใน iOS คุณต้องเพิ่มสองปุ่ม
NSLocationWhenInUseUsageDescription
NSLocationAlwaysUsageDescription
ลงในไฟล์ Info.plist
<key>NSLocationWhenInUseUsageDescription</key>
<string>Because I want to know where you are!</string>
<key>NSLocationAlwaysUsageDescription</key>
<string>Want to know where you are!</string>
ดูภาพด้านล่างนี้
เพิ่มคีย์NSLocationWhenInUseUsageDescription
หรือNSLocationAlwaysUsageDescription
(ใช้พื้นหลัง GPS) ด้วยสตริงที่ขอให้ใช้ GPS ในinfo.plist
แต่ละเป้าหมาย
ขออนุญาตจากที่ทำงาน:
[self initLocationManager: locationManager];
อยู่ที่ไหนinitLocationManager
:
// asks for GPS authorization on iOS 8
-(void) initLocationManager:(CLLocationManager *) locationManager{
locationManager = [[CLLocationManager alloc]init];
if([locationManager respondsToSelector:@selector(requestAlwaysAuthorization)])
[locationManager requestAlwaysAuthorization];
}
โปรดจำไว้ว่าหากคีย์ไม่ได้อยู่ในinfo.plist
แต่ละเป้าหมายสำหรับแต่ละแอปจะไม่ถามผู้ใช้ if
ให้เข้ากันได้กับ iOS 7 และrespondsToSelector:
วิธีการรับประกันความเข้ากันได้ในอนาคตมากกว่าแค่การแก้ปัญหาสำหรับ iOS 7 และ 8
ปัญหาสำหรับฉันคือคลาสที่CLLocationManagerDelegate
เป็นแบบส่วนตัวซึ่งป้องกันไม่ให้วิธีการมอบหมายทั้งหมดถูกเรียก คิดว่ามันไม่ใช่สถานการณ์ทั่วไป แต่คิดว่าฉันจะพูดถึงมันในกรณีที่ไม่ช่วยใคร
ฉันเพิ่มคีย์เหล่านั้นInfoPlist.strings
ในiOS 8.4, iPad mini 2มันใช้ได้เช่นกัน ผมไม่ได้ตั้งค่าใด ๆ ที่สำคัญเช่นในของฉันNSLocationWhenInUseUsageDescription
Info.plist
InfoPlist.strings :
"NSLocationWhenInUseUsageDescription" = "I need GPS information....";
ฐานของเธรดนี้กล่าวว่าas in iOS 7
สามารถแปลเป็นภาษาท้องถิ่นใน InfoPlist.strings InfoPlist.strings
ในการทดสอบของฉันคีย์เหล่านั้นสามารถกำหนดค่าได้โดยตรงในแฟ้ม
ดังนั้นสิ่งแรกที่คุณต้องทำคือการเพิ่มปุ่ม> ต่อไปนี้หนึ่งปุ่มหรือทั้งสองอย่างลงในไฟล์ Info.plist ของคุณ:
- NSLocationWhenInUseUsageDescription
- NSLocationAlwaysUsageDescription
คีย์ทั้งสองนี้ใช้สายอักขระซึ่งเป็นคำอธิบายว่าทำไมคุณจึงต้องใช้บริการระบุตำแหน่ง คุณสามารถป้อนสตริงเช่น“ ต้องระบุตำแหน่งเพื่อค้นหาว่าคุณอยู่ที่ไหน” ซึ่งในiOS 7สามารถแปลเป็นภาษาท้องถิ่นได้ในไฟล์ InfoPlist.strings
UPDATE:
ฉันคิดว่า@IOS
วิธีการนั้นดีกว่า เพิ่มคีย์ไปที่Info.plist
มีค่าว่างและเพิ่มสตริงที่โลคัลInfoPlist.strings
ไลซ์แล้ว