You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift实现类似Facebook评论页的全屏导航推送转场

解决iOS模态呈现带导航栏的全屏转场(仿Facebook评论页效果)

我之前折腾过好多次这个需求!就是Facebook那种点击帖子后,评论页全屏滑出来的模态效果,连导航栏一起跟着转场动,而不是只弹出VC内部的内容对吧?给你两个亲测有效的实现方案:

方案一:自定义转场动画 + UINavigationController包裹

核心思路是把你的评论VC用导航控制器包裹,让整个导航控制器参与模态转场动画,而不是只动内部VC的视图:

  1. 先准备好你的评论ViewController,比如CommentViewController,给它配置好导航栏的按钮、样式(比如设置navigationItem.title、leftBarButtonItem)
  2. 创建自定义转场动画器,实现转场协议:
class FullScreenSlideAnimator: NSObject, UIViewControllerAnimatedTransitioning {
    // 转场时长,可根据需求调整
    func transitionDuration(using transitionContext: UIViewControllerContextTransitioning?) -> TimeInterval {
        return 0.35
    }
    
    func animateTransition(using transitionContext: UIViewControllerContextTransitioning) {
        guard let toNavVC = transitionContext.viewController(forKey: .to) as? UINavigationController,
              let toView = toNavVC.view else { return }
        
        let container = transitionContext.containerView
        // 初始位置设为屏幕右侧(如果要从底部滑入就改y值为container.height)
        toView.frame = CGRect(x: container.bounds.width, y: 0, width: container.bounds.width, height: container.bounds.height)
        container.addSubview(toView)
        
        UIView.animate(withDuration: transitionDuration(using: transitionContext),
                       delay: 0,
                       options: .curveEaseOut) {
            toView.frame = container.bounds
        } { finished in
            transitionContext.completeTransition(!transitionContext.transitionWasCancelled)
        }
    }
}
  1. 在触发转场的VC里,设置模态的代理和样式:
// 实例化评论VC并包裹进导航控制器
let commentVC = CommentViewController()
let navVC = UINavigationController(rootViewController: commentVC)
// 设置自定义模态样式
navVC.modalPresentationStyle = .custom
navVC.transitioningDelegate = self
// 弹出模态VC
present(navVC, animated: true)
  1. 让触发转场的VC遵守UIViewControllerTransitioningDelegate,并返回自定义动画器:
extension YourSourceViewController: UIViewControllerTransitioningDelegate {
    func animationController(forPresented presented: UIViewController, presenting: UIViewController, source: UIViewController) -> UIViewControllerAnimatedTransitioning? {
        return FullScreenSlideAnimator()
    }
}

方案二:利用iOS13+的PageSheet模态(更简单)

如果你的APP只需要支持iOS13及以上,这个方案几乎零成本:
直接把评论VC包裹进导航控制器,用系统的pageSheet模态样式,再配置成全屏展示:

let commentVC = CommentViewController()
let navVC = UINavigationController(rootViewController: commentVC)

if #available(iOS 13.0, *) {
    navVC.modalPresentationStyle = .pageSheet
    // 配置为全屏展示,隐藏底部抓手(可选)
    if let sheet = navVC.sheetPresentationController {
        sheet.detents = [.large()]
        sheet.prefersGrabberVisible = false
        sheet.largestUndimmedDetentIdentifier = .none // 背景完全变暗
    }
} else {
    // iOS13以下用全屏模态
    navVC.modalPresentationStyle = .fullScreen
}

present(navVC, animated: true)

系统自带的转场动画会自动让整个导航栏跟着一起滑入,效果非常接近Facebook的样式,而且不需要写自定义动画代码。

关键注意点

  • 绝对不要直接模态CommentViewController然后在内部手动加导航栏!那样导航栏是VC的子视图,不会参与模态转场动画,必须用UINavigationController包裹后再模态。
  • 如果需要自定义返回逻辑,在CommentViewController里设置navigationItem.leftBarButtonItem,点击时调用dismiss(animated: true),这样按钮会跟着导航栏一起参与转场。

内容的提问来源于stack exchange,提问作者pmax1

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.20 08:04:41