我有使用presentModalViewController方法呈现的UIViewControllers层次结构。
我有单例,可以将所有呈现的视图控制器都抓取到数组中。
例如,我提出了控制器A,然后是B,然后是C.我将每个控制器插入索引0。
所以我的层次结构如下
C
乙
A
这是我的单身人士
@implementation PresentHelper
- (id)init
{
self = [super init];
if (self) {
self.viewControllers = [NSMutableArray new];
}
return self;
}
+ (PresentHelper *)sharedInstance
{
static dispatch_once_t pred;
static PresentHelper *sharedInstance = nil;
dispatch_once(&pred, ^{
sharedInstance = [[self alloc] init];
});
return sharedInstance;
}
- (void)backToViewControllerA
{
for (UIViewController *controller in self.viewControllers) {
[controller dismissModalViewControllerAnimated:NO];
}
[self.viewControllers removeAllObjects];
}
@end
在UIViewController
C中,我调用backToViewControllerA
方法。
因此,当我调试此方法时,我想知道为什么- viewDidLoad
方法(对于self.viewControllers中的每个控制器)在此行[controller dismissModalViewControllerAnimated:NO];
之后调用,因为我认为它不应该像这样工作,但它的工作原理。
所以,也许这不是返回视图控制器A的一种方式,但我的问题在任何情况下都与viewDidLoad方法有关。
这也是我下面的代码我如何呈现每个控制器。我有基类,每个(A,B,C控制器都是从它继承而来)。
- (void)presentModalViewController:(UIViewController *)modalViewController animated:(BOOL)animated
{
PresentHelper *presentHelper = [PresentHelper sharedInstance];
[presentHelper.viewControllers insertObject:modalViewController atIndex:0];
[super presentModalViewController:modalViewController animated:animated];
}
也得到了这条消息
NSArray在被枚举时被突变
因此我认为在解雇后我失去了我的对象,也许这就是我的问题。
答案 0 :(得分:1)
这似乎不是一个单身人士的好用。
有许多方法可以回到A.您不需要构建额外的委托方法或属性,因为每个控制器都通过它的presentingViewController
属性引用前一个。 (我将重新说明......对于iOS5 +,您可以使用内置的viewController属性presentingViewController
)。要与iOS4.3保持兼容,请创建一个属性并将其放在基类@interface
中:
@property (nonatomic, assign) UIViewController* presentingController;
同样在您的base clase界面中,声明一个方法:
- (void) dismissBackToA;
在@implementation
,@synthesize
您的媒体资源中定义dismissBackToA
- (void) dismissBackToA
{
if ([[self presentingController] respondsToSelector:@selector(dismissBackToA)]) {
[[self presentingController] performSelector:@selector(dismissBackToA)];
}
}
在你的模态现有代码中,在所呈现的VC中设置对self的引用 - 例如:
MasterViewController* BViewController = [[BViewController alloc] init];
BViewController.presentingController = self;
[self presentModalViewController:BViewController animated:YES];
现在你所要做的就是覆盖AViewController子类中的dismissBackToA
:
- (void) dismissBackToA
{
[self dismissModalViewControllerAnimated:YES];
}
这将允许您菊花链式连接任意数量的模态viewControllers ...通用dismissBackToA
将'展开'链回到A. A的覆盖方法将忽略它的模态(B)。这个应该消灭链中的所有其他控制器。 presentController
几乎是一个标准代表 - 我已经过度指定它以强调它与iOS5 +中presentingViewController
的相似性。我在nonArc内存上有点生疏,但我认为需要分配不保留。
我恐怕无法测试这100%,因为我手头没有iOS4.3模拟器......
更新
您也可以直接将链接传递给A并在需要时发送[self.referenceToA dismissModalViewControllerAnimated:YES]
,但这种方式会更加通用。
您还应该注意presentModalViewController:animated:
和dismissModalViewControllerAnimated:
在6.0中已弃用:现在您应该使用
- presentViewController:animated:completion:
- dismissViewControllerAnimated:completion:
在5.0中引入。
它们仍然可以工作,但是将其视为警告 - 您将不得不准备放弃对4.3的支持,或者让您的代码在未来以OS版本为条件。
答案 1 :(得分:0)
这不是解雇控制器的好方法。为此目的创建单例似乎是一个坏主意。到目前为止最简单的方法是使用展开segue在故事板中进行,但这只适用于iOS 6我认为(也可能是iOS 5)。如果你想在代码中这样做,那么你应该使用委托或NSNotifications让A解雇C(这也将解雇B)。此外,如果您要在代码中呈现模态视图控制器,则不应使用此折旧方法,请使用presentViewController:animated:completion:而不是。
编辑后:
你也可以从控制器C这样做:
[self.presentingViewController.presentingViewController dismissViewControllerAnimated:YES completion:nil];