0

我将我的子类UINavigationController化为使用 UIRTLNavigationController.m 从右到左执行推送(非正常行为)我已在此问题的底部添加并收到以下警告:

 nested push animation can result in corrupted navigation bar
 Finishing up a navigation transition in an unexpected state. Navigation Bar subview tree might get corrupted.

我研究了这些错误并发现了一个阻止您接收它们的类:https ://github.com/Plasma/BufferedNavigationController

我已将 BufferedNavigationController .h 和 .m 添加到我的项目中,将 BufferedNavigationController.h 中的行更改为:@interface BufferedNavigationController : UIRTLNavigationController 并将 BufferedNavigationController 设置为我UINavigationController在 IB 中的自定义子类。

视图仍在从右向左移动,在 BufferedNavigationController 内部调用了方法,但我仍然收到有关嵌套的警告,并且 ..Navigation Bar 子视图树可能已损坏..

任何帮助,将不胜感激。

UIRTLNavigationController.m:

#import "UIRTLNavigationController.h"


@implementation UIRTLNavigationController

- (id)initWithRootViewController:(UIViewController *)rootViewController
{
        self = [super initWithRootViewController:rootViewController];
        if (!self)
                return nil;
        return self;
}

- (void)pushViewController:(UIViewController *)viewController animated:(BOOL)animated
{
        NSLog(@"pushViewController");
        // Add the viewController and a fake controller without animation. Then pop the fake controller with animation.
        UIViewController *fakeController = [[[UIViewController alloc] init] autorelease];
        [super setViewControllers:[[self viewControllers] arrayByAddingObjectsFromArray:[NSArray arrayWithObjects:viewController, fakeController, nil]] animated:NO];
        [super popViewControllerAnimated:animated];
}

- (void)popViewControllerAnimatedStep2:(UIViewController *)viewController
{
        // Push the new top controller with animation
        [super pushViewController:viewController animated:YES];
        // Remove the view that should have been popped
        NSMutableArray *arr = [NSMutableArray arrayWithArray:[self viewControllers]];
        [arr removeObjectAtIndex:[[self viewControllers] count]-2];
        [super setViewControllers:[NSArray arrayWithArray:arr] animated:NO];
}

- (UIViewController *)popViewControllerAnimated:(BOOL)animated
{
        NSLog(@"popViewControllerAnimated");

        if (animated)
        {
                // Save the controller that should be on top after this pop operation
                UIViewController *newTopController = [[self viewControllers] objectAtIndex:[[self viewControllers] count]-2];
                // Remove it from the stack. Leave the view that should be popped on top
                NSMutableArray *arr = [NSMutableArray arrayWithArray:[self viewControllers]];
                [arr removeObjectAtIndex:[[self viewControllers] count]-2];
                [super setViewControllers:[NSArray arrayWithArray:arr] animated:NO];
                // Schedule the next step
                [self performSelector:@selector(popViewControllerAnimatedStep2:) withObject:newTopController afterDelay:0];
                return [arr objectAtIndex:[arr count]-1];
        }
        return [super popViewControllerAnimated:NO];
}

- (void)dealloc {
    [super dealloc];
}


@end
4

2 回答 2

0

我不知道您是否正在创建自定义 UINavigationController 只是为了执行自定义转换,如果这样做,有一种更简单的方法可以做到这一点。像下面的代码

-(void)makeMyCustomAnimation {
      YourDestinationViewController *destinationController = [YourDestinationViewController 
                                                             alloc] initWithNib.....];//add the missing code fot ini

  CATransition* transition = [CATransition animation];
  transition.duration = .25; //you can change this value to fit your needs
  transition.timingFunction = [CAMediaTimingFunction functionWithName: 
                                           kCAMediaTimingFunctionEaseInEaseOut]; 
                                           //kCAMediaTimingFunctionLinear
                                           //kCAMediaTimingFunctionEaseIn
                                           //kCAMediaTimingFunctionEaseOut
                                           //kCAMediaTimingFunctionEaseInEaseOut
                                           //kCAMediaTimingFunctionDefault

   transition.type = kCATransitionPush; //kCATransitionMoveIn;
                                     //kCATransitionPush,  
                                     //kCATransitionReveal
                                     //kCATransitionFade

   transition.subtype = kCATransitionFromRight; 
                       //kCATransitionFromLeft,
                       //kCATransitionFromRight 
                       //kCATransitionFromTop, 
                      //kCATransitionFromBottom

[self.navigationController.view.layer addAnimation:transition
                                                            forKey:kCATransition];

[self.navigationController pushViewController:destinationController animated:NO];

}

您可以通过更改subtype值来更改过渡的方向。(我可能设置了错误的子类型值,我一直在混合它们)

您也可以使用相同的方法来pop处理视图控制器。我

如果你想使用 segues 可以使用它,只需创建一个自定义 segue 并-(void)perform通过添加前面的代码和一些添加来覆盖该方法,你必须获得视图控制器[self sourceViewController];[self destinationViewController];

于 2013-05-19T12:09:00.060 回答
-1

对我来说,问题是一个接一个地推动控制器,这导致了一个接一个的过渡动画。这个链接帮助了我: https ://github.com/Plasma/BufferedNavigationController/blob/master/BufferedNavigationController.m

我从这个堆栈溢出答案中得到它:iOS:popViewController 意外行为

于 2014-05-28T15:48:07.947 回答