#swift #core-location #ios8
#swift #расположение ядра #ios8
Вопрос:
Я не нашел ничего, что говорило бы о CLVisit, поэтому я пытаюсь самостоятельно изучить технологию.
Кто-нибудь знает, почему это не работает? Все ключи .plist установлены и работают.
class ViewController: UIViewController,CLLocationManagerDelegate {
var manager:CLLocationManager!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
manager = CLLocationManager()
manager.delegate = self
manager.desiredAccuracy = kCLLocationAccuracyBest
manager.requestAlwaysAuthorization()
manager.startMonitoringVisits()
}
func locationManager(manager: CLLocationManager!, didFailWithError error: NSError!) {
}
func locationManager(manager: CLLocationManager!,
didVisit visit: CLVisit!)
{
println("visit: (visit.coordinate.latitude),(visit.coordinate.longitude)")
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
}
Ответ №1:
Ваш код выглядит правильно. Я также обнаружил, что CLVisit работает не так, как я это понимал. Это сложно отлаживать, потому что вам нужно фактически покинуть свое рабочее пространство, чтобы протестировать его. 🙂
Эвристика, которую CLVisit использует для определения «посещения», не документирована, но, согласно видеоролику WWDC, вам нужно остаться на неопределенное время, прежде чем CLVisit решит, что вы посещаете, а не просто проходите мимо. У меня был очень ограниченный успех в получении обратного вызова делегата. Однажды посещение ArrivalDate было запущено примерно через две минуты в местоположении, другое — примерно через десять минут, но в большинстве случаев посещение никогда не срабатывает.
NSLog не работает для отслеживания CLVisits, если вы отсутствуете, поэтому я настроил простой объект Core Data и регистрирую все посещения:
Visits *thisVisit = [NSEntityDescription insertNewObjectForEntityForName:@"Visits" inManagedObjectContext:[self managedObjectContext]];
thisVisit.arrivalDate = visit.arrivalDate;
thisVisit.departureDate = visit.departureDate;
thisVisit.latitude = [NSNumber numberWithDouble:visit.coordinate.latitude];
thisVisit.longitude = [NSNumber numberWithDouble:visit.coordinate.longitude];
[self saveContext];
Даже когда мое устройство находится в моем домашнем местоположении в течение многих часов, я не всегда получаю событие прибытия или отправления, когда я ухожу или возвращаюсь.
РЕДАКТИРОВАТЬ: вот полный пример. Установите и используйте его в течение нескольких дней, и вы увидите проблемы с этим новым API. Я надеюсь, что это будет работать лучше в более поздних бета-версиях. Для меня это все еще довольно непоследовательно — иногда два прибытия подряд, иногда два вылета подряд, длительные задержки перед запуском visit…
Комментарии:
1. Итак, CLVisit довольно глючный, и нам следует дождаться третьей бета-версии… Я оставался в двух местах более 1 часа, и ничего не было отмечено (я использовал NSUserDefaults для хранения посещений.
2. Я использую бета-версию 2 и надежно получаю уведомления. По моему (ограниченному) опыту, уведомления об отъезде поступают чаще, поэтому часто человек получает уведомления о посещениях только при выезде из определенного места.
Ответ №2:
Я предполагаю, что вы пытаетесь получить эти вызовы делегатов, пока приложение работает в фоновом режиме; однако вы создаете экземпляр CLLocationManager в контроллере представления, который не будет создан (afaik).
Это работает для меня (я использую iOS 8, бета-версию 2, на iPad mini 2-го поколения): установите NSLocationAlwaysUsageDescription
ключ, включите фоновый режим «Обновления местоположения» в разделе «Возможности» и включите следующее в AppDelegate
:
let locationManager = CLLocationManager()
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: NSDictionary?) -> Bool {
locationManager.delegate = self
locationManager.requestAlwaysAuthorization()
locationManager.startMonitoringVisits()
return true
}
func locationManager(manager: CLLocationManager!, didVisit visit: CLVisit!) {
println("Visit: (visit)")
// I find that sending this to a UILocalNotification is handy for debugging
}
Обновление: я выдвинул пример приложения, которое работает для https://github.com/mloughran/CLVisit-POC .
Комментарии:
1. Сработало для меня на устройстве. Я не знаю, как можно было бы протестировать это в симуляторе tbh.
2. хорошо, не могу заставить CLLocationManager работать для меня на устройстве бета-версии 2. Перепробовал все предложения. Считайте, что вам повезло 😉
3. Я добавил демонстрационное приложение — может быть, посмотрите, работает ли это для вас?
4. Было бы неплохо, если бы Apple предоставила нам способ имитации CLVisits, чтобы мы могли протестировать это, не разъезжая по городу. У кого-нибудь есть идеи по имитации этих посещений?
5. Я думал об использовании файла GPX.. но не знаю, как аппаратное обеспечение выберет посещение. Какое-либо определенное количество времени требуется для того, чтобы посещение было квалифицировано как CLVisit? @mloughran пожалуйста, пролейте немного света на это. Когда вы тестировали проект github, на сколько времени вы останавливались в определенном месте? Также это работает, когда приложение убито??
Ответ №3:
Я начинаю думать, что в этом API есть серверный компонент. Мое тестовое приложение настроено в AppDelegate, и без изменений кода оно начало периодически отключать посещения только в течение последних нескольких дней. Но он пропускает некоторые и, кажется, создает другие.
Вот последние два посещения, записанные моим приложением. Эти точки по существу одинаковы (примерно в 30 футах друг от друга). Я думаю, что первое прибытие является точным, а отправление — нет. Прибытие второго визита абсолютно не произошло. В течение этого времени мое тестовое устройство не выходило из дома.
широта: xx.11852879438132 долгота: -xxx.7792256808099 Дата прибытия: 2014-06-25 12:19 ВЕЧЕРА Дата отправления: 2014-06-25 4:44 вечера
широта: xx.1185726857039 долгота: -xxx.7793685278068 Дата прибытия: 2014-06-26 5:59 Дата отправления: отдаленное будущее
Раньше я вынимал его и примерно несколько раз, и только изредка заходил на огонь.