2

私のアプリの最初の ViewController には 2 つのコンテナー ビューがあります。最初のビューには、アプリのメイン コンテンツを制御する UINavigationController である ViewController が含まれています。最初の VC の 2 番目のコンテナー ビューは、ナビゲーション バーが配置される場所のすぐ下に UILabels が配置された小さなストリップです。

メイン コンテンツ VC のナビゲーション スタックの最初の VC では、ナビゲーション バーが非表示になっています。後続のすべての VC では、最初の VC の 2 番目のコンテナー ビューと共にナビゲーション バーが表示されます。アプリがナビゲーション スタックの最初の VC から離れたときに、2 番目のコンテナー VC でアニメーション化したいと思います。

私の質問は、ナビゲーション スタックで VC をプッシュ/ポップするときにナビゲーション コントローラーが実行するアニメーションと一致するように、どのアニメーションを作成する必要があるかということです。私は現在使用しています:

[UIView animateWithDuration:0.27f delay:0 options:UIViewAnimationOptionCurveEaseOut animations:^{
    self.playerCardVC.frame = secondFrame;
} completion:nil];

しかし、Navigation Bar がアニメーション化されて表示されるときとは正確に一致していません。どんな考え/アイデアも大歓迎です。

アップデート:

最初の質問に投稿されたアニメーションを微調整するとともに、この問題に対する回答をオンラインで検索してきましたが、アニメーションが表示されるときにナビゲーション バーと完全に一致しているようには見えません。正しい方向へのコメントやポイントは本当に高く評価されます.

4

2 に答える 2

0

上記の説明からビュー階層とナビゲーション デザインを理解するのは非常に困難です。おそらく、スクリーンショットやスケッチを投稿できますか?

UINavigationController の標準の水平プッシュ/ポップ アニメーションをオーバーライドできます。これを行うには、カスタム UINavigationControllerDelegate オブジェクトとその他いくつかのものを定義します。下記参照。

navController と navControllerDelegate を次のようにセットアップします。

UINavigationController *navigationController = [[UINavigationController alloc] init];
self.navigationControllerDelegate = [[NavigationControllerDelegate alloc] init];
navigationController.delegate = self.navigationControllerDelegate;

NavigationControllerDelegate クラスは次のようになります。

@interface NavigationControllerDelegate : NSObject <UINavigationControllerDelegate>

@end


#import "NavigationControllerDelegate.h"
#import "CrossFadePushAnimator.h"
#import "CrossFadePopAnimator.h"

@interface NavigationControllerDelegate ()

@property (nonatomic, strong) CrossFadePushAnimator* pushAnimator;
@property (nonatomic, strong) CrossFadePopAnimator* popAnimator;

@end

@implementation NavigationControllerDelegate

- (id)init
{
    self = [super init];
    if (self)
    {
        self.pushAnimator = [CrossFadePushAnimator new];
        self.popAnimator = [CrossFadePopAnimator new];
    }

    return self;
}

- (id<UIViewControllerAnimatedTransitioning>)navigationController:(UINavigationController *)navigationController animationControllerForOperation:(UINavigationControllerOperation)operation fromViewController:(UIViewController *)fromVC toViewController:(UIViewController *)toVC
    {
    if (operation == UINavigationControllerOperationPop)
    {
        return self.popAnimator;
    }
    else if (operation == UINavigationControllerOperationPush)
    {
        return self.pushAnimator;
    }

    return nil;
}

- (id<UIViewControllerInteractiveTransitioning>)navigationController:(UINavigationController *)navigationController interactionControllerForAnimationController:(id<UIViewControllerAnimatedTransitioning>)animationController
{
    return nil;
}

pushAnimator は次のようになります。

@interface CrossFadePushAnimator ()

@property (nonatomic, strong) id<UIViewControllerContextTransitioning> transitionContext;

@end

@implementation CrossFadePushAnimator

- (NSTimeInterval)transitionDuration:(id <UIViewControllerContextTransitioning>)transitionContext
{
    return AnimationDuration;
}

- (void)animateTransition:(id<UIViewControllerContextTransitioning>)transitionContext
{
    UIViewController* toViewController = [transitionContext viewControllerForKey:UITransitionContextToViewControllerKey];
//    UIViewController* fromViewController = [transitionContext viewControllerForKey:UITransitionContextFromViewControllerKey];

    [[transitionContext containerView] addSubview:toViewController.view];
    toViewController.view.alpha = 1.0f;

    // We are using CAAnimation instead of UIView animation because we need the UIToolbar blur layer to animate
    CABasicAnimation *fade = [CABasicAnimation animationWithKeyPath:@"opacity"];
    fade.fromValue = @0;
    fade.toValue = @1;
    fade.duration = [self transitionDuration:transitionContext];
    fade.removedOnCompletion = YES;
    fade.delegate = self;

    self.transitionContext = transitionContext;
    [toViewController.view.layer addAnimation:fade forKey:AnimationKey];
}

- (void)animationDidStop:(CAAnimation *)theAnimation finished:(BOOL)flag
{
    [self.transitionContext completeTransition:![self.transitionContext transitionWasCancelled]];
    self.transitionContext = nil;
}

popAnimator は pushAnimator に似ています。

お役に立てれば!

于 2014-09-05T00:40:11.347 に答える
0

上記の説明からビュー階層とナビゲーション デザインを理解するのは非常に困難です。おそらく、スクリーンショットやスケッチを投稿できますか?

UINavigationController の標準の水平プッシュ/ポップ アニメーションをオーバーライドできます。これを行うには、カスタム UINavigationControllerDelegate オブジェクトとその他いくつかのものを定義します。下記参照。

navController と navControllerDelegate を次のようにセットアップします。

UINavigationController *navigationController = [[UINavigationController alloc] init];
self.navigationControllerDelegate = [[NavigationControllerDelegate alloc] init];
navigationController.delegate = self.navigationControllerDelegate;

NavigationControllerDelegate クラスは次のようになります。

@interface NavigationControllerDelegate : NSObject <UINavigationControllerDelegate>

@end


#import "NavigationControllerDelegate.h"
#import "CrossFadePushAnimator.h"
#import "CrossFadePopAnimator.h"

@interface NavigationControllerDelegate ()

@property (nonatomic, strong) CrossFadePushAnimator* pushAnimator;
@property (nonatomic, strong) CrossFadePopAnimator* popAnimator;

@end

@implementation NavigationControllerDelegate

- (id)init
{
    self = [super init];
    if (self)
    {
        self.pushAnimator = [CrossFadePushAnimator new];
        self.popAnimator = [CrossFadePopAnimator new];
    }

    return self;
}

- (id<UIViewControllerAnimatedTransitioning>)navigationController:(UINavigationController *)navigationController animationControllerForOperation:(UINavigationControllerOperation)operation fromViewController:(UIViewController *)fromVC toViewController:(UIViewController *)toVC
    {
    if (operation == UINavigationControllerOperationPop)
    {
        return self.popAnimator;
    }
    else if (operation == UINavigationControllerOperationPush)
    {
        return self.pushAnimator;
    }

    return nil;
}

- (id<UIViewControllerInteractiveTransitioning>)navigationController:(UINavigationController *)navigationController interactionControllerForAnimationController:(id<UIViewControllerAnimatedTransitioning>)animationController
{
    return nil;
}

pushAnimator は次のようになります。

@interface CrossFadePushAnimator ()

@property (nonatomic, strong) id<UIViewControllerContextTransitioning> transitionContext;

@end

@implementation CrossFadePushAnimator

- (NSTimeInterval)transitionDuration:(id <UIViewControllerContextTransitioning>)transitionContext
{
    return AnimationDuration;
}

- (void)animateTransition:(id<UIViewControllerContextTransitioning>)transitionContext
{
    UIViewController* toViewController = [transitionContext viewControllerForKey:UITransitionContextToViewControllerKey];

    [[transitionContext containerView] addSubview:toViewController.view];
    toViewController.view.alpha = 1.0f;

    // I'm using CABasicAnimation here for a specific reason, but you could also use the animation method you use above.
    CABasicAnimation *fade = [CABasicAnimation animationWithKeyPath:@"opacity"];
    fade.fromValue = @0;
    fade.toValue = @1;
    fade.duration = [self transitionDuration:transitionContext];
    fade.removedOnCompletion = YES;
    fade.delegate = self;

    self.transitionContext = transitionContext;
    [toViewController.view.layer addAnimation:fade forKey:AnimationKey];
}

- (void)animationDidStop:(CAAnimation *)theAnimation finished:(BOOL)flag
{
    [self.transitionContext completeTransition:![self.transitionContext transitionWasCancelled]];
    self.transitionContext = nil;
}

popAnimator は pushAnimator に似ています。

お役に立てれば!

于 2014-09-05T00:41:46.853 に答える