应用程序进入后台时如何保持NSTimer?

Posted

技术标签:

【中文标题】应用程序进入后台时如何保持NSTimer?【英文标题】:How keep NSTimer when application entering background? 【发布时间】:2012-03-23 14:25:11 【问题描述】:

我来这里是因为我的问题没有找到任何解决方案:(

我正在做一个简单的应用程序,我必须(通过套接字)向服务器发送一些信息(如 GPS l/L、精度、电池电量等)。

当前代码在应用程序处于前台时工作正常。

myTimer = [NSTimer scheduledTimerWithTimeInterval: 2.0 target:self
                                                  selector: @selector(sendPosToServer:) userInfo:nil repeats: YES];
myTimer2 = [NSTimer scheduledTimerWithTimeInterval: 3.0 target:self
                                                  selector: @selector(sendBatteryToServer:) userInfo:nil repeats: YES];
myTimer3 = [NSTimer scheduledTimerWithTimeInterval: 5.0 target:self
                                                  selector: @selector(sendResToServer:) userInfo:nil repeats: YES];
myTimer4 = [NSTimer scheduledTimerWithTimeInterval: 5.0 target:self
                                                  selector: @selector(sendQResToServer:) userInfo:nil repeats: YES];
myTimer5 = [NSTimer scheduledTimerWithTimeInterval: 3.0 target:self
                                                   selector: @selector(sendPrecisionToServer:) userInfo:nil repeats: YES];

所有这些方法都被调用了。

但是当应用程序进入后台时,所有计时器都无效......我读过ios会自动停止计时器...... 我正在寻找一种在应用程序处于后台时调用方法和发送数据的方法..

我需要你的帮助:)

谢谢大家!!

【问题讨论】:

Background repeated job的可能重复 【参考方案1】:

您需要阅读有关如何在后台运行任务的指南:

Background Execution and Multitasking

这是我的一个应用程序的 applicationDidEnterBackground。当我把它放到后台时,它会做一些磁盘缓存维护:

- (void)applicationDidEnterBackground:(UIApplication *)application 

//As we are going into the background, I want to start a background task to clean up the disk caches
if ([[UIDevice currentDevice] respondsToSelector:@selector(isMultitaskingSupported)])  //Check if our iOS version supports multitasking I.E iOS 4
    if ([[UIDevice currentDevice] isMultitaskingSupported])  //Check if device supports mulitasking
        UIApplication *application = [UIApplication sharedApplication]; //Get the shared application instance

        __block UIBackgroundTaskIdentifier background_task; //Create a task object

        background_task = [application beginBackgroundTaskWithExpirationHandler: ^
            [application endBackgroundTask:background_task]; //Tell the system that we are done with the tasks
            background_task = UIBackgroundTaskInvalid; //Set the task to be invalid
            //System will be shutting down the app at any point in time now
        ];

        //Background tasks require you to use asyncrous tasks
        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^
            //Perform your tasks that your application requires                

            //I do what i need to do here.... synchronously...                

            [application endBackgroundTask: background_task]; //End the task so the system knows that you are done with what you need to perform
            background_task = UIBackgroundTaskInvalid; //Invalidate the background_task
        );
    

【讨论】:

通过这部分代码,方法被调用。它工作正常,但我可以分发它吗?【参考方案2】:

来自 Apple 文档:

实现长时间运行的后台任务对于需要更多时间的任务 执行时间来实现,你必须请求特定的权限 在后台运行它们而不会被暂停。在 iOS 中,只有 允许特定应用类型在后台运行:

在后台向用户播放有声内容的应用程序,例如音乐播放器应用程序 让用户随时了解其位置的应用程序,例如导航应用程序 支持互联网协议语音 (VoIP) 的应用程序 需要下载和处理新内容的报亭应用 从外部附件接收定期更新的应用

除非您的应用属于这些类别之一(听起来不属于),否则它将无法在后台运行。

【讨论】:

我正在向我的应用程序询问 GPS 位置。 “让用户随时了解其位置的应用程序,例如导航应用程序”也是如此?【参考方案3】:

iOS App Programming Guide 列出了允许您的应用在后台保持活动状态的活动。如果您计划通过应用商店分发您的应用,您的应用必须执行所列活动之一。如果您只是为自己编写一些东西,您也许可以将您的功能搭载在一项允许的活动上。

【讨论】:

好的。我会分发它。我正在向服务器发送有关 GPS 数据的信息。所以我认为这是伟大的,对吗? “与外部附件通信” “外部附件”是指连接到设备的东西,而不是网络上的某个服务器。因此,例如,如果您从某些通过蓝牙通信的 GPS 接收器获取 GPS 数据,那么外部附件选项可能会起作用。如果您从设备自己的 GPS 接收器获取数据,请改用定位服务。当位置发生变化时,设备会告诉您。你必须改变你的方法,因为你不能以固定的时间间隔更新服务器。 =/ 好的。我在IOS开发中很糟糕。我明白你的意思,但我不知道如何执行它 @user1147981:以防万一,如果您打算将其编写为某种“车队管理”应用程序,您应该知道它不会通过审查(App Store 审查指南)

以上是关于应用程序进入后台时如何保持NSTimer?的主要内容,如果未能解决你的问题,请参考以下文章

快速 NSTimer 在后台

进入后台状态时是不是可以在 iOS 4 设备上运行 NSThread 或 NSTimer?

如何在应用程序进入后台或终止时运行计时器

应用程序进入后台时如何保持 Swift Socket IO 运行?

我们如何让 NSTimer 在 iOS 中为我​​的音频播放器在后台运行

在进入后台和在前台检索时将 NSTimer 的时间保存到磁盘