内存警告是否会破坏呈现视图控制器?

发布于 2024-12-29 08:11:03 字数 1839 浏览 4 评论 0原文

我有一个 iPad 应用程序,它有一个主视图控制器,然后是一个设置视图控制器。当我的主视图显示设置视图时,我会全屏显示设置视图。设置视图中有一个关闭按钮,该按钮可以工作 - 直到出现内存警告。如果屏幕上显示设置按钮时出现内存警告,它将拒绝关闭。

换句话说,这有效:

  • 应用程序启动 ->显示主视图 ->显示设置视图 ->关闭设置视图

这不会:

  • 应用程序启动 ->显示主视图 ->显示设置视图 -> 内存警告 ->关闭设置视图

设置视图将保留在那里。

我在第一代 iPad 上的 iOS 5 上运行这个应用程序。 (我不支持 iOS 4。)

我该如何解决这个问题?

编辑:

这是我用于显示设置视图的代码:

- (void) showSettings{

    if (!self.settingsViewController) {

    //Create the navigation controller and the root view for the settings panel
    SettingsViewController *settingsRootView = [[SettingsViewController alloc] initWithStyle:UITableViewStyleGrouped];
    UINavigationController *settingsView = [[UINavigationController alloc] initWithRootViewController:settingsRootView];
    [settingsRootView release];

    //Configure the animation and modal style, and the navigation bar's color

    [settingsView.navigationBar setTintColor:kDarkGrayColor];

    //Enable the settings flag
    [self setSettingsIsActive:YES]; 

    //Configure the presentation
    [settingsView setModalPresentationStyle:UIModalPresentationFullScreen];
    [settingsView setModalTransitionStyle:UIModalTransitionStyleFlipHorizontal];

    self.settingsViewController = settingsView;

    [settingsView release];
    }

    //present and release the settings panel
    [self presentViewController:self.settingsViewController animated:YES completion:^{

    }];

}

这是我隐藏它的方法:

//This method reloads some stuff and 
- (void) dismissSettings{

    //
    //  ... Reload some other stuff...
    //

    //Dismiss the settings panel
    [self dismissViewControllerAnimated:YES completion:^{

    //
    //  ... Reload some other stuff...
    //

    }]; 
}

I have an iPad app which has a main view controller, and then a settings view controller. When my main view presents the settings view, I present the settings view in full screen. There is a dismiss button in the settings view, which works - until a memory warning occurs. If a memory warning occurs while the settings button is onscreen, it will refuse to dismiss.

In other words, this works:

  • App Launch -> Show Main View -> Show Settings View -> Dismiss Settings View

This doesn't:

  • App Launch -> Show Main View -> Show Settings View ->Memory Warning -> Dismiss Settings View

The settings view will just stay there.

I'm running this app on iOS 5 on a first generation iPad. (I'm not supporting iOS 4.)

How can I fix this?

Edit:

Here's my code for showing the settings view:

- (void) showSettings{

    if (!self.settingsViewController) {

    //Create the navigation controller and the root view for the settings panel
    SettingsViewController *settingsRootView = [[SettingsViewController alloc] initWithStyle:UITableViewStyleGrouped];
    UINavigationController *settingsView = [[UINavigationController alloc] initWithRootViewController:settingsRootView];
    [settingsRootView release];

    //Configure the animation and modal style, and the navigation bar's color

    [settingsView.navigationBar setTintColor:kDarkGrayColor];

    //Enable the settings flag
    [self setSettingsIsActive:YES]; 

    //Configure the presentation
    [settingsView setModalPresentationStyle:UIModalPresentationFullScreen];
    [settingsView setModalTransitionStyle:UIModalTransitionStyleFlipHorizontal];

    self.settingsViewController = settingsView;

    [settingsView release];
    }

    //present and release the settings panel
    [self presentViewController:self.settingsViewController animated:YES completion:^{

    }];

}

And here's how I hide it:

//This method reloads some stuff and 
- (void) dismissSettings{

    //
    //  ... Reload some other stuff...
    //

    //Dismiss the settings panel
    [self dismissViewControllerAnimated:YES completion:^{

    //
    //  ... Reload some other stuff...
    //

    }]; 
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

七禾 2025-01-05 08:11:03

原则上,内存警告不会对视图控制器执行任何操作,但它会卸载当前未在屏幕上显示的视图控制器的视图。

在您的特定情况下,我会在“设置视图控制器”的代码中查找可能引用主视图控制器视图中的某些内容的任何内容。如果是这种情况,则在内存警告发生后该引用可能为零。

另外,您应该验证 didReceiveMemoryWarning 方法的实现,以查看您是否正在处理关闭该设置视图可能需要的某些内容。

在内存不足的情况下,来自那些“非活动”视图控制器的所有视图都将被卸载。由于您的 dismissSettings 方法是在主控制器上声明的,因此当调用它时,主视图中的所有元素很可能为零。我不知道“重新加载其他一些东西”代码中包含哪些类型的操作,但我猜想与视图相关的某些操作正在使该方法失败。

我建议将与视图相关的所有重新加载代码移至 viewDidAppear 方法,因为它将保证加载视图。

另一方面,我建议您在实际设置视图控制器上实现解雇方法(请记住,它应该类似于 [ self.navigationController DismissModalViewControllerAnimated:YES]; 因为您需要解雇导航控制器)。至少,这是我一直以来的做法,而且从来没有让我失望过。逻辑是我不希望非活动视图控制器运行任何逻辑。

最后,正如您提到的,您的目标是 iOS 5 及更高版本,我强烈建议您将项目转移到 ARC。做起来比看起来更容易,一旦你开始行动,那就真的很棒了。

问题的另一个可能原因是您正在使用通知调用您的解雇方法,并且您的主控制器正在取消订阅 viewDidUnload 方法上的该通知。请记住,当内存不足条件触发时,将调用 viewDidUnload 方法!

In principle, a memory warning will not do anything to your view controllers, but it will unload the views of those view controllers that are not currently being displayed on the screen.

In your particular case, I would look for anything on the code from your Settings View Controller that might be referencing something from the view of the main view controller. If that is the case, problably that reference will be nil after the memory warning occurs.

Also, you should verify your implementation of the didReceiveMemoryWarning methods, to see if you're disposing of something that might be needed to dismiss that settings view.

On a low memory condition, all the views from those 'inactive' view controllers will be unloaded. As your dismissSettings method is declared on the Main Controller, when it is called it is very possible that all the elements from your main view are nil. I don't know what kind of operations are contained in the "Reload some other stuff" code, but I guess something related to the view is making the method fail.

I would suggest moving all the reloading code related to the view to the viewDidAppear method as it will be guaranteed to have the view loaded.

On the other hand, I would recommend you to move implement the dismiss method on the actual setting view controller (remember that it should be something like [ self.navigationController dismissModalViewControllerAnimated:YES]; as you need to dismiss the navigation controller). At least, this is the way I've always done this and never has failed me. The logic being that I don't want inactive view controllers to run any logic.

Finally, as you mention that you are targeting to iOS 5 and above, I would greatly recommend moving your project to ARC. It's easier to do than what it seems, and once that you have moved, it is truly great.

Another possible reason for your problem is that you are calling to your dismiss method using notifications and that your main controller is unsubscribing from that notifications on the viewDidUnload method. Keep in mind that the viewDidUnload method will be called when the low memory condition triggers!

鸠书 2025-01-05 08:11:03

首先要找出导致内存警告的原因。使用仪器并检查是否有泄漏。如果您使用 ARC,这应该是一个问题 - 但显然出现了内存警告的严重错误。解决这个问题就解决了你的问题。

也就是说,当内存开始不足时,操作系统将关闭应用程序。后台应用程序通常是最先消失的,但很多时候,如果泄漏足够严重,则后台应用程序终止和正在运行的应用程序也终止之间的时间间隔可能很短。

First thing is to find out what is causing the memory warning. Use Instruments and check for leaks. If you are using ARC, this should be a problem - but obviously something is seriously wrong for a memory warning to occur. Fix this and you have fixed your problem.

That said, the OS will shut down applications when memory starts getting short. Background applications are usually the first to go, but many times if the leak is bad enough, the time period between when background apps are terminated and the time when the running app is also terminated can be short.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文