2012-04-25 134 views
25

我有几个iOS应用程序都使用相同的端口来侦听网络信标。在主视图中,我使用viewWillDisappear在另一个视图打开时关闭端口,这非常有效。然后我注意到,如果我从主视图控制器按下主页按钮而没有打开另一个视图关闭端口,那么端口保持打开状态,而我的其他应用程序不能再监听该端口。然后我尝试使用viewWillUnload,但是当我按下主页按钮时似乎没有被调用。按下主页按钮时检测iOS

-(void)viewWillUnload 
{ 
    //[super viewWillUnload]; 
    NSLog(@"View will unload"); 
    [udpSocket close]; 
    udpSocket = nil; 
} 

查看将卸载永远不会显示在控制台,这导致我相信该方法永远不会被调用。

有没有办法检测何时按下主页按钮,所以我可以关闭我的端口?

+3

尝试使用“applicationWillTerminate”方法。:-) – 2012-04-25 22:35:09

+1

“applicationWillTerminate”方法不存在。但是,子类可以注册UIApplicationWillTerminateNotification,然后执行自己的清理或关闭。 – 2012-05-18 15:02:47

回答

39

这是你的选择

在你的应用程序代理:

- (void)applicationWillResignActive:(UIApplication *)application 
{ 
    // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state. 
    // Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game. 
} 

- (void)applicationDidEnterBackground:(UIApplication *)application 
{ 
    // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 
    // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 
} 

- (void)applicationWillTerminate:(UIApplication *)application 
{ 
    // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 
} 
+0

因为我明显同意,+1 – DGund 2012-04-26 00:40:02

+2

我有代码关闭在viewWillDisappear中的端口,它似乎并没有被调用。端口将保持打开状态,所有其他使用此端口的应用程序都会失败。我设置了一个类方法来关闭端口并从applicationDidEnterBackground调用它,并且它工作的很好 – nick 2012-04-26 04:19:16

+7

当按下Home按钮或应用程序终止时,viewWillDisappear或viewDidDisappear不会被调用。最好的解决方案是使用'UIApplicationWillResignActiveNotification'通知 – Sam 2013-10-07 10:42:09

5

viewWillUnload通常不叫除了在内存不足的情况。你最好实施application delegate methodsapplicationDidEnterBackground:applicationWillTerminate:,并在那里完成工作,或向您的应用程序的知道如何处理清理过程的部分发送通知。

5

viewWillUnload通常不会调用,除非内存不足。用这些来代替:

在应用程序委托:

- (void)applicationWillResignActive:(UIApplication *)application 
{ 
// Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state. 
// Use this method to pause ongoing tasks, disable timers, and throttle down OpenGL ES frame rates. Games should use this method to pause the game. 
} 

- (void)applicationDidEnterBackground:(UIApplication *)application 
{ 
// Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 
// If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 
} 

- (void)applicationWillTerminate:(UIApplication *)application 
{ 
// Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 
} 

或者,如果你想在你的浏览器使用代码:

- (void)viewDidDisappear:(BOOL)animated 
{ 
//Put code here 
} 

- (void)viewWillDisappear:(BOOL)animated 
{ 
//Put code here 
} 
+0

viewWill/DidDisappear将在应用程序关闭时调用。当Home Button按下时,不会将应用程序最小化到控制中心。 – khunshan 2014-08-06 11:14:30

31

处理最简单的方法就是注册在视图控制器中收到UIApplicationWillResignActiveNotification通知。

该事件在家里按下按钮,锁在一个电话

- (void) applicationWillResign{ 
    NSLog(@"About to lose focus"); 
} 

- (void) myVcInitMethod { 
    [[NSNotificationCenter defaultCenter] 
     addObserver:self 
     selector:@selector(applicationWillResign) 
     name:UIApplicationWillResignActiveNotification 
     object:nil]; 
} 
+3

为什么要传递NULL而不是nil? – mszaro 2013-08-16 18:04:51

+1

我编辑了代码以使用nil。 – PeterPurple 2013-11-29 17:58:12

+8

实际上'applicationWillResignActive'通知并不总是这样做的最好方式,因为resign active还包括(意外)向下滑动顶层菜单,或者在ios 7中新增底部菜单。'applicationDidEnterBackground'意味着您的应用程序被“最小化” ,并可从iOS 4获得。 – bobobobo 2014-01-01 18:26:28

10

在雨燕用户的情况下发出

,你可以把它写这样

override func viewDidLoad() { 
    super.viewDidLoad() 

    // code here... 

    NSNotificationCenter.defaultCenter().addObserver(
     self, 
     selector: "applicationWillResignActive:", 
     name: UIApplicationWillResignActiveNotification, 
     object: nil) 
} 

func applicationWillResignActive(notification: NSNotification) { 
    print("I'm out of focus!") 
} 

也,当你的应用程序终止时,别忘了关闭它

deinit { 

    // code here... 

    NSNotificationCenter.defaultCenter().removeObserver(self) 
} 
+0

如果你使用的是iOS 9或更高版本,你可以忘记在deinit方法中删除观察者。但是,只有当你不打算支持iOS 8或更早版本。 而且,如@ bobobobo所说,您应该使用applicationDidEnterBackground – 2017-10-20 13:20:18

2

更好的使用UIApplicationWillResignActiveUIApplicationDidBecomeActive,因为它们捕获了“顶部矩形捕获和释放事件”。 我会建议使用这根类:

class VBase: UIViewController { 
    fileprivate var listenersActivated = false 
    override func viewDidLoad() { 
     super.viewDidLoad() 
     // Do any additional setup after loading the view. 
    } 
    override func viewWillAppear(_ animated: Bool) { 
     super.viewWillAppear(animated) 
     onStart() 
    } 
    override func viewWillDisappear(_ animated: Bool) { 
     super.viewWillDisappear(animated) 
     onStop() 
     removeListeners() 
    } 
    override func didReceiveMemoryWarning() { 
     super.didReceiveMemoryWarning() 
     // Dispose of any resources that can be recreated. 
     onStop() 
     removeListeners() 
    } 

    internal func iniListeners() { 
     if (!listenersActivated) { 
      NotificationCenter.default.addObserver(self, selector: #selector(onStop), name: NSNotification.Name.UIApplicationWillResignActive, object: nil) 
      NotificationCenter.default.addObserver(self, selector: #selector(onStart), name: NSNotification.Name.UIApplicationDidBecomeActive, object: nil) 
      listenersActivated = true 
     } else { 

     } 
    } 
    internal func removeListeners() { 
     NotificationCenter.default.removeObserver(self) 
     listenersActivated = false 
    } 
    internal func onStop() { 

    } 
    internal func onStart() { 
     iniListeners() 
    } 

} 

覆盖onStop()onStart()里面孩子的捕获所有视图出现/消失

也就是说,

class SomeViewController: VBase { 

... 
    override func onStart() { 
     super.onStart() 
     someFunctionToInitialize() 
    } 
    override func onStop() { 
     super.onStop() 
     stopTimer() 
     someFunctionToDesctruction() 
    } 
}