gpt4 book ai didi

ios - 当高度改变时 UINavigationController 会切断内容吗? (动图)

转载 作者:行者123 更新时间:2023-12-02 00:40:48 26 4
gpt4 key购买 nike

我已将 UINavigationController 放入可扩展的“抽屉”中。我的目标是让导航堆栈中的每个 viewController 都有自己的“首选”高度。

假设 VC1 需要很高。当从 VC2 导航回 VC1 时,我希望它的动画高度变高。即使有滑动交互,动画逻辑似乎也能正常工作。

但是由于某种原因,navigationController中的viewController被“切断”了。他们的约束是正确的,但没有更新(?)。或者,在我再次触摸 View 之前,部分内容根本不会呈现。底部的不可见区域甚至可以接受触摸。

看一下:

gif

预期结果是 contentViewController(第一个和第二个)始终延伸到屏幕底部。他们被限制这样做,所以问题是他们在转换期间不会“渲染”(?)。

在 UINavigationController 的委托(delegate)中,我执行以下操作:

func navigationController(_ navigationController: UINavigationController, willShow viewController: UIViewController, animated: Bool) {
transitionCoordinator?.animate(alongsideTransition: { (context) in
drawer.heightConstraint.constant = targetHeight
drawer.superview?.layoutIfNeeded()
}, completion: { (context) in
print("done")
})
}

高度变化很完美。但导航中的内容不符合要求。 navigationController 被限制为前导、尾随、底部和一个存储的 heightConstraint,该 heightConstraint 会更改其常量。

一旦我触摸/拖动导航 Controller /内容,它就会立即“渲染未渲染的”,一切都很好。为什么会发生这种情况?

当检查 View 层次结构时,它看起来像这样:

enter image description here

NavigationController 的高度已达到所需高度,但内容与过渡开始时整个抽屉的高度相同,并且直到我触摸它时它才会更新。为什么?

编辑:我已将代码推送到 my GitHub如果你想看一下。但请注意,还有其他几个问题(动画等),不要介意它们。我只想知道为什么导航不会呈现“ future ”的高度。

最佳答案

您可以通过为navigationController使用自定义animationController并在自定义UIViewControllerAnimatedTransitioning实现的animateTransition函数中为destinationView设置适当的框架来解决上述问题。结果将如下面的 gif 图像所示。

enter image description here

您的自定义 UIViewControllerAnimatedTransitioning 可能如下所示。

final class TransitionAnimator: NSObject, UIViewControllerAnimatedTransitioning {
let presenting: Bool

init(presenting: Bool) {
self.presenting = presenting
}

func transitionDuration(using transitionContext: UIViewControllerContextTransitioning?) -> TimeInterval {
return TimeInterval(UINavigationController.hideShowBarDuration)
}

func animateTransition(using transitionContext: UIViewControllerContextTransitioning) {
guard let fromView = transitionContext.view(forKey: .from) else { return }
guard let toView = transitionContext.view(forKey: .to) else { return }

let duration = transitionDuration(using: transitionContext)

let container = transitionContext.containerView
if presenting {
container.addSubview(toView)
} else {
container.insertSubview(toView, belowSubview: fromView)
}

let toViewFrame = toView.frame
toView.frame = CGRect(x: presenting ? toView.frame.width : -toView.frame.width, y: toView.frame.origin.y, width: toView.frame.width, height: toView.frame.height)

UIView.animate(withDuration: duration, animations: {
toView.frame = toViewFrame
fromView.frame = CGRect(x: self.presenting ? -fromView.frame.width : fromView.frame.width, y: fromView.frame.origin.y, width: fromView.frame.width, height: fromView.frame.height)
}) { (finished) in
container.addSubview(toView)
transitionContext.completeTransition(!transitionContext.transitionWasCancelled)
}
}
}

并且,在您的导航 Controller 中提供自定义动画 Controller ,如下所示。

func navigationController(_ navigationController: UINavigationController, animationControllerFor operation: UINavigationController.Operation, from fromVC: UIViewController, to toVC: UIViewController) -> UIViewControllerAnimatedTransitioning? {
switch operation {
case .push:
return TransitionAnimator(presenting: true)
case .pop:
return TransitionAnimator(presenting: false)
default:
return nil
}
}

PS:- 我还在您的 github 存储库中提出了拉取请求。

关于ios - 当高度改变时 UINavigationController 会切断内容吗? (动图),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59124702/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com