导航控制器顶部布局指南与定制过渡荣幸 [英] Navigation controller top layout guide not honored with custom transition

查看:207
本文介绍了导航控制器顶部布局指南与定制过渡荣幸的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

短版:

在结合与iOS7定制的过渡和的UINavigationController 使用时,我有自动布局顶部的布局导向的问题。具体来说,顶面布置指南和文本视图之间的约束没有被兑现。有没有人遇到这个问题?

I am having a problem with auto layout top layout guide when used in conjunction with custom transition and UINavigationController in iOS7. Specifically, the constraint between the top layout guide and the text view is not being honored. Has anyone encountered this issue?

长版:

我已经明确地定义约束(即上,下,左,右)呈现一个视图,像这样的场景:

I have a scene which has unambiguously define constraints (i.e. top, bottom, left and right) that renders a view like so:

但是,当我使用该与导航控制器上的自定义过渡,顶部约束顶端布局导向似乎关闭,它呈现如下,仿佛顶部布局导向是在屏幕的顶部,而不是在导航控制器的底部:

But when I use this with a custom transition on the navigation controller, the top constraint to the top layout guide seems off and it renders is as follows, as if the top layout guide was at the top of the screen, rather than at the bottom of the navigation controller:

这样看来,采用自定义的过渡时,顶布局指南与导航控制器越来越困惑。约束的其余部分正在正确应用。如果我旋转设备并再次旋转它,一切都突然正确呈现,所以它不会出现是该约束不是正确定义不是一个问题。同样,当我关掉我的自定义过渡,观点正确呈现。

It would appear that the "top layout guide" with the navigation controller is getting confused when employing the custom transition. The rest of the constraints are being applied correctly. And if I rotate the device and rotate it again, everything is suddenly rendered correctly, so it does not appear to be not a matter that the constraints are not defined properly. Likewise, when I turn off my custom transition, the views render correctly.

说了这么多, _autolayoutTrace 报道称,在 UILayoutGuide 对象从歧义布局吃亏,当我运行:

Having said that, _autolayoutTrace is reporting that the UILayoutGuide objects suffer from AMBIGUOUS LAYOUT, when I run:

(lldb) po [[UIWindow keyWindow] _autolayoutTrace]

但这些布局指南是始终报告暧昧每当我看着他们即使我保证没有丢失约束(我已经做了视图控制器的习惯选择,选择添加缺少的视图控制器的限制或选择所有控件和做同样的事)。

But those layout guides are always reported as ambiguous whenever I look at them even though I've ensured that there are no missing constraints (I've done the customary selecting of view controller and choosing "Add missing constraints for view controller" or selecting all of the controls and doing the same for them).

在如何$ P $而言pcisely我做过渡,我指定符合 UIViewControllerAnimatedTransitioning animationControllerForOperation对象方法:

In terms of how precisely I'm doing the transition, I've specified an object that conforms to UIViewControllerAnimatedTransitioning in the animationControllerForOperation method:

- (id<UIViewControllerAnimatedTransitioning>)navigationController:(UINavigationController *)navigationController
                                  animationControllerForOperation:(UINavigationControllerOperation)operation
                                               fromViewController:(UIViewController*)fromVC
                                                 toViewController:(UIViewController*)toVC
{
    if (operation == UINavigationControllerOperationPush)
        return [[PushAnimator alloc] init];

    return nil;
}

@implementation PushAnimator

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

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

    [[transitionContext containerView] addSubview:toViewController.view];
    CGFloat width = fromViewController.view.frame.size.width;

    toViewController.view.transform = CGAffineTransformMakeTranslation(width, 0);

    [UIView animateWithDuration:[self transitionDuration:transitionContext] animations:^{
        fromViewController.view.transform = CGAffineTransformMakeTranslation(-width / 2.0, 0);
        toViewController.view.transform = CGAffineTransformIdentity;
    } completion:^(BOOL finished) {
        fromViewController.view.transform = CGAffineTransformIdentity;
        [transitionContext completeTransition:![transitionContext transitionWasCancelled]];
    }];
}

@end

我也做上述的再现,设置视图,而不是的变换 ,具有相同的结果。

I've also done a rendition of the above, setting the frame of the view rather than the transform, with the same result.

我也试过手动确保该约束通过调用重新应用 layoutIfNeeded 。我也试过 setNeedsUpdateConstraints setNeedsLayout

I've also tried manually make sure that the constraints are re-applied by calling layoutIfNeeded. I've also tried setNeedsUpdateConstraints, setNeedsLayout, etc.

底线,与使用顶部的布局导向的约束导航控制器的任何人结婚成功转型定制?

Bottom line, has anyone successfully married custom transition of navigation controller with constraints that use top layout guide?

推荐答案

我通过固定的 topLayoutGuide 的高度约束解决了这个。调整 edgesForExtendedLayout 不是我的选择,因为我需要在目标视图欠重叠导航栏,还使用要能布局子视图 topLayoutGuide

I solved this by fixing the height constraint of the topLayoutGuide. Adjusting edgesForExtendedLayout wasn't an option for me, as I needed the destination view to underlap the navigation bar, but also to be able to layout subviews using topLayoutGuide.

直接检查中发挥的制约表明,iOS版增加了一个高度约束到 topLayoutGuide 与值等于导航控制器导航栏的高度。除了在搭载iOS 7,使用自定义动画过渡离开约束为0的高度,他们在iOS的8个固定这一点。

Directly inspecting the constraints in play shows that iOS adds a height constraint to the topLayoutGuide with value equal to the height of the navigation bar of the navigation controller. Except, in iOS 7, using a custom animation transition leaves the constraint with a height of 0. They fixed this in iOS 8.

这是我想出了纠正约束(这是斯威夫特,但相当于应的OBJ-C工作)的解决方案。我测试过,它适用于iOS 7和8。

This is the solution I came up with to correct the constraint (it's in Swift but the equivalent should work in Obj-C). I've tested that it works on iOS 7 and 8.

func animateTransition(transitionContext: UIViewControllerContextTransitioning) {
    let fromView = transitionContext.viewControllerForKey(UITransitionContextFromViewControllerKey)!.view
    let destinationVC = transitionContext.viewControllerForKey(UITransitionContextToViewControllerKey)!
    destinationVC.view.frame = transitionContext.finalFrameForViewController(destinationVC)
    let container = transitionContext.containerView()
    container.addSubview(destinationVC.view)

    // Custom transitions break topLayoutGuide in iOS 7, fix its constraint
    if let navController = destinationVC.navigationController {
        for constraint in destinationVC.view.constraints() as [NSLayoutConstraint] {
            if constraint.firstItem === destinationVC.topLayoutGuide
                && constraint.firstAttribute == .Height
                && constraint.secondItem == nil
                && constraint.constant == 0 {
                constraint.constant = navController.navigationBar.frame.height
            }
        }
    }

    // Perform your transition animation here ...
}

这篇关于导航控制器顶部布局指南与定制过渡荣幸的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆