如何检测iPhone上的屏幕锁定/解锁事件?当用户解锁时,我想从我的iPhone应用程序显示通知提醒。 (就像在Android中用于屏幕解锁的广播接收器一样。)
答案 0 :(得分:24)
检查一下,我想检测锁定/解锁事件,我通过达尔文通知解决了它。
您可以在设备被"com.apple.springboard.lockcomplete"
锁定时检测到事件。
//call back
static void displayStatusChanged(CFNotificationCenterRef center, void *observer, CFStringRef name, const void *object, CFDictionaryRef userInfo)
{
// the "com.apple.springboard.lockcomplete" notification will always come after the "com.apple.springboard.lockstate" notification
NSString *lockState = (NSString*)name;
NSLog(@"Darwin notification NAME = %@",name);
if([lockState isEqualToString:@"com.apple.springboard.lockcomplete"])
{
NSLog(@"DEVICE LOCKED");
}
else
{
NSLog(@"LOCK STATUS CHANGED");
}
}
-(void)registerforDeviceLockNotif
{
//Screen lock notifications
CFNotificationCenterAddObserver(CFNotificationCenterGetDarwinNotifyCenter(), //center
NULL, // observer
displayStatusChanged, // callback
CFSTR("com.apple.springboard.lockcomplete"), // event name
NULL, // object
CFNotificationSuspensionBehaviorDeliverImmediately);
CFNotificationCenterAddObserver(CFNotificationCenterGetDarwinNotifyCenter(), //center
NULL, // observer
displayStatusChanged, // callback
CFSTR("com.apple.springboard.lockstate"), // event name
NULL, // object
CFNotificationSuspensionBehaviorDeliverImmediately);
}
答案 1 :(得分:3)
其实我想要退出应用程序并锁定iPhone, 过了一段时间我解锁了iPhone,然后退出应用程序 显示通知或警告启动应用程序。
你不能在iPhone上这样做。
答案 2 :(得分:1)
您可能需要在AppDelegate
中实施以下方法:
告诉代表该应用程序现在在后台。
- (void)applicationDidEnterBackground:(UIApplication *)application
告诉代理该应用程序已变为活动状态。
- (void)applicationDidBecomeActive:(UIApplication *)application
告诉代理该应用程序即将变为非活动状态。
- (void)applicationWillResignActive:(UIApplication *)application
答案 3 :(得分:1)
要在swift 5中检测应用程序内部的锁定/解锁,这仅对我有用:
override func viewDidLoad() {
super.viewDidLoad()
NotificationCenter.default.addObserver(self, selector: #selector(applicationDidBecomeActive), name: UIApplication.willEnterForegroundNotification, object: nil)
NotificationCenter.default.addObserver(self, selector: #selector(applicationDidEnterBackground), name: UIApplication.didEnterBackgroundNotification, object: nil)
}
@objc func applicationDidBecomeActive(notification: NSNotification) {
print("ACTIVE")
}
@objc func applicationDidEnterBackground(notification: NSNotification) {
print("BACKGROUND")
}
答案 4 :(得分:0)
在将应用提交到App Store时,您不能使用com.apple.springboard.lockcomplete
或com.apple.springboard.lockstate
,因为您的应用是私有API,因此将被拒绝。
com.apple.springboard.lockcomplete
通知并非总是在com.apple.springboard.lockstate
通知之后出现,它可能会更早或更晚发生。您需要设置一个计时器来等待该事件。
因此,这是在Swift 5中检测屏幕锁定和解锁状态的方法:
struct NotificationName {
// Listen to CFNotification, and convert to Notification
public static let lockComplete = Notification.Name("NotificationName.lockComplete")
public static let lockState = Notification.Name("NotificationName.lockState")
// Handle lockComplete and lockState Notification to post locked or unlocked notification.
public static let locked = Notification.Name("NotificationName.locked")
public static let unlocked = Notification.Name("NotificationName.unlocked")
}
func addNotificationObservers() {
let lockCompleteString = "com.apple.springboard.lockcomplete"
let lockString = "com.apple.springboard.lockstate"
// Listen to CFNotification, post Notification accordingly.
CFNotificationCenterAddObserver(CFNotificationCenterGetDarwinNotifyCenter(),
nil,
{ (_, _, _, _, _) in
NotificationCenter.default.post(name: NotificationName.lockComplete, object: nil)
},
lockCompleteString as CFString,
nil,
CFNotificationSuspensionBehavior.deliverImmediately)
CFNotificationCenterAddObserver(CFNotificationCenterGetDarwinNotifyCenter(),
nil,
{ (_, _, _, _, _) in
NotificationCenter.default.post(name: NotificationName.lockState, object: nil)
},
lockString as CFString,
nil,
CFNotificationSuspensionBehavior.deliverImmediately)
// Listen to Notification and handle.
NotificationCenter.default.addObserver(self,
selector: #selector(onLockComplete),
name: NotificationName.lockComplete,
object: nil)
NotificationCenter.default.addObserver(self,
selector: #selector(onLockState),
name: NotificationName.lockState,
object: nil)
}
// nil means don't know; ture or false means we did or did not received such notification.
var receiveLockStateNotification: Bool? = nil
// when we received lockState notification, use timer to wait 0.3s for the lockComplete notification.
var waitForLockCompleteNotificationTimer: Timer? = nil
var receiveLockCompleteNotification: Bool? = nil
// When we received lockComplete notification, invalidate timer and refresh lock status.
@objc
func onLockComplete() {
if let timer = waitForLockCompleteNotificationTimer {
timer.invalidate()
waitForLockCompleteNotificationTimer = nil
}
receiveLockCompleteNotification = true
changeIsLockedIfNeeded()
}
// When we received lockState notification, refresh lock status.
@objc
func onLockState() {
receiveLockStateNotification = true
changeIsLockedIfNeeded()
}
func changeIsLockedIfNeeded() {
guard let state = receiveLockStateNotification, state else {
// If we don't receive lockState notification, return.
return
}
guard let complete = receiveLockCompleteNotification else {
// If we don't receive lockComplete notification, wait 0.3s.
// If nothing happens in 0.3s, then make sure we don't receive lockComplete, and refresh lock status.
waitForLockCompleteNotificationTimer = Timer.scheduledTimer(withTimeInterval: 0.3, repeats: false, block: { _ in
self.receiveLockCompleteNotification = false
self.changeIsLockedIfNeeded()
})
return
}
// When we determined lockState and lockComplete notification is received or not.
// We can update the device lock status by 'complete' value.
NotificationCenter.default.post(
name: complete ? NotificationName.locked : NotificationName.unlocked,
object: nil
)
// Reset status.
receiveLockStateNotification = nil
receiveLockCompleteNotification = nil
}
答案 5 :(得分:-2)
从当前视图控制器中,您应该为UIApplicationDidEnterBackgroundNotification添加一个观察者,并在解除视图控制器时删除观察者
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didEnterBackground) name:UIApplicationDidEnterBackgroundNotification object:nil];