Получить текущую ориентацию устройства (расширение приложения)
Как получить текущую ориентацию устройства в расширении приложения, я попытался использовать два метода, но не имел успеха.
-
Он всегда возвращает UIDeviceOrientationUnknown
[[UIDevice currentDevice] orientation]
-
В нем отображается красное сообщение о том, что 'sharedApplication недоступно в iOS (расширение приложения)
[[UIApplication sharedApplication] statusBarOrientation];
-
Я также добавляю наблюдателя, но не получаю вызов.
[[NSNotificationCenter defaultCenter] addObserver:self.view selector:@selector(notification_OrientationWillChange:) name:UIApplicationWillChangeStatusBarOrientationNotification object:nil];
- (void)notification_OrientationWillChange:(NSNotification*)n
{
UIInterfaceOrientation orientation = (UIInterfaceOrientation)[[n.userInfo objectForKey:UIApplicationStatusBarOrientationUserInfoKey] intValue];
if (orientation == UIInterfaceOrientationLandscapeLeft)
[self.textDocumentProxy insertText:@"Left"];
if (orientation == UIInterfaceOrientationLandscapeRight)
[self.textDocumentProxy insertText:@"Right"];
}
Итак, как можно получить текущую ориентацию устройства.
Ответы
Ответ 1
Я нашел способ, по которому мы могли бы вычислить нашу ориентацию устройства таким образом в (расширение приложения)
- (void)viewDidLayoutSubviews
{
if(self.view.frame.size.width > self.view.frame.size.height)
NSLog(@"Landscape");
else
NSLog(@"Portrait");
}
Он дает мне правильную ориентацию, но все же не получается, поскольку устройство LandscapeLeft или LandscapeRight, а также Портрет или PortraitUpsideDown.
По-прежнему нужна помощь.
Ответ 2
У меня появилась идея!
extension UIScreen {
var orientation: UIInterfaceOrientation {
let point = coordinateSpace.convertPoint(CGPointZero, toCoordinateSpace: fixedCoordinateSpace)
if point == CGPointZero {
return .Portrait
} else if point.x != 0 && point.y != 0 {
return .PortraitUpsideDown
} else if point.x == 0 && point.y != 0 {
return .LandscapeLeft
} else if point.x != 0 && point.y == 0 {
return .LandscapeRight
} else {
return .Unknown
}
}
}
EDIT: В Swift 4 вы можете:
extension UIScreen {
var orientation: UIInterfaceOrientation {
let point = coordinateSpace.convert(CGPoint.zero, to: fixedCoordinateSpace)
switch (point.x, point.y) {
case (0, 0):
return .portrait
case let (x, y) where x != 0 && y != 0:
return .portraitUpsideDown
case let (0, y) where y != 0:
return .landscapeLeft
case let (x, 0) where x != 0:
return .landscapeRight
default:
return .unknown
}
}
}
Ответ 3
Метод наблюдателя будет вызван, если вы добавите это раньше:
[[UIDevice currentDevice] beginGeneratingDeviceOrientationNotifications];
Изменить: я использую UIApplicationDidChangeStatusBarOrientationNotification
для наблюдателя
И в моем методе я проверяю:
UIDeviceOrientation orientation = [[UIDevice currentDevice] orientation];
BOOL isPortrait = UIDeviceOrientationIsPortrait(orientation);
Редактировать 2- Xcode 6.2 - iOS 7 и 8
Похоже, что если вы хотите использовать это как на iOS 7, так и на 8, приведенный выше код даст неправильный результат в iOS 7.
Итак, я использую что-то еще, потому что на iOS 7 ограничения mainScreen никогда не изменятся, но на iOS 8 изменится, если ориентация изменится.
У меня есть 3 макроса, которые дадут мне правильный размер ширины и высоты экрана, независимо от версии iOS:
#define IOS_VERSION_OLDER_THAN_8 ([[[UIDevice currentDevice] systemVersion] floatValue] < 8.0)
#define SCREEN_WIDTH_CALCULATED (IOS_VERSION_OLDER_THAN_8 ? (UIInterfaceOrientationIsPortrait([UIApplication sharedApplication].statusBarOrientation) ? [[UIScreen mainScreen] bounds].size.width : [[UIScreen mainScreen] bounds].size.height) : [[UIScreen mainScreen] bounds].size.width)
#define SCREEN_HEIGHT_CALCULATED (IOS_VERSION_OLDER_THAN_8 ? (UIInterfaceOrientationIsPortrait([UIApplication sharedApplication].statusBarOrientation) ? [[UIScreen mainScreen] bounds].size.height : [[UIScreen mainScreen] bounds].size.width) : [[UIScreen mainScreen] bounds].size.height)
Затем, когда выдается уведомление, я проверяю ориентацию следующим образом:
BOOL isPortrait = SCREEN_WIDTH_CALCULATED < SCREEN_HEIGHT_CALCULATED;
Это будет работать на iOS 7 и iOS 8, но я не проверял более старые версии Xcode, только 6.2
Это вернется только в том случае, если устройство находится на портретном или альбомном уровне, не все 4 типа ориентации
Ответ 4
Вы можете посмотреть эту библиотеку и forks. Он использует CoreMotion для определения ориентации устройства, поэтому он может работать в среде с ограниченным расширением приложения.
Ответ 5
Я знаю это поздно, но ошибка в этом вопросе была в этой строке:
[[NSNotificationCenter defaultCenter] addObserver:self.view selector:@selector(notification_OrientationWillChange:) name:UIApplicationWillChangeStatusBarOrientationNotification object:nil];
addObserver:self.view
неверно, уведомление должно быть прикреплено к self
для вызова. Работайте также на iOS8.
Ответ 6
Этот код не даст вам точного UIDeviceOrientation, но вы сможете узнать, находится ли он в портретном или ландшафтном режиме
BOOL isLandScape = !(self.view.frame.size.width == ([[UIScreen mainScreen] bounds].size.width*([[UIScreen mainScreen] bounds].size.width<[[UIScreen mainScreen] bounds].size.height))+([[UIScreen mainScreen] bounds].size.height*([[UIScreen mainScreen] bounds].size.width>[[UIScreen mainScreen] bounds].size.height)));