10

我正在开发一个作为服务在后台运行的网络监视器应用程序。屏幕打开或关闭时是否可以收到通知/呼叫?

它通过使用以下代码存在于Android中:

private void registerScreenOnOffReceiver()
{
   IntentFilter filter = new IntentFilter(Intent.ACTION_SCREEN_ON);
   filter.addAction(Intent.ACTION_SCREEN_OFF);
   registerReceiver(screenOnOffReceiver, filter);
}

然后在屏幕打开/关闭时调用 screenOnOffReceiver。iOS有类似的解决方案吗?

编辑: 到目前为止我发现的最好的是 UIApplicationProtectedDataWillBecomeUnavailable (检测 iPhone 屏幕是否打开/关闭),但它要求用户在设备上启用数据保护(密码保护)。

4

3 回答 3

16

您可以使用Darwin 通知来监听事件。我不是 100% 确定,但在我看来,在越狱的 iOS 5.0.1 iPhone 4 上运行,这些事件之一可能是你需要的:

com.apple.iokit.hid.displayStatus
com.apple.springboard.hasBlankedScreen
com.apple.springboard.lockstate

更新:此外,当手机锁定(但不是解锁时)时会发布以下通知:

com.apple.springboard.lockcomplete

要使用它,请像这样注册事件(这仅注册一个事件,但如果这对您不起作用,请尝试其他事件):

CFNotificationCenterAddObserver(CFNotificationCenterGetDarwinNotifyCenter(), //center
                                NULL, // observer
                                displayStatusChanged, // callback
                                CFSTR("com.apple.iokit.hid.displayStatus"), // event name
                                NULL, // object
                                CFNotificationSuspensionBehaviorDeliverImmediately);

displayStatusChanged您的事件回调在哪里:

static void displayStatusChanged(CFNotificationCenterRef center, void *observer, CFStringRef name, const void *object, CFDictionaryRef userInfo) {
    NSLog(@"event received!");
    // you might try inspecting the `userInfo` dictionary, to see 
    //  if it contains any useful info
    if (userInfo != nil) {
        CFShow(userInfo);
    }
}

如果您真的希望此代码作为服务在后台运行,并且您已越狱,我建议您查看iOS Launch Daemons与您简单地在后台运行的应用程序相反,启动守护程序可以在重新启动后自动启动,您不必担心应用程序在后台运行任务的 iOS 规则。

让我们知道这是如何工作的!

于 2013-01-08T05:33:33.613 回答
2

使用较低级别的通知 API,您可以在收到通知时查询锁定状态:

#import <notify.h>

int notify_token;
notify_register_dispatch("com.apple.springboard.lockstate", &notify_token, dispatch_get_main_queue(), ^(int token) {
    uint64_t state = UINT64_MAX;
    notify_get_state(token, &state);
    NSLog(@"com.apple.springboard.lockstate = %llu", state);
});

当然,您的应用必须启动 UIBackgroundTask 才能获得通知,由于 iOS 允许的运行时间有限,这限制了该技术的实用性。

于 2014-05-30T11:33:55.637 回答
-2

当 iPhone 屏幕被锁定时,将调用 appdelegate 方法 “- (void)applicationWillResignActive:(UIApplication *)application” ,您可以检查一下。希望它可以帮助你。

于 2013-01-07T08:06:47.473 回答