导航栏过渡动画

时间:2020-02-29 14:35:42

标签: ios swift

我有两个视图控制器,我正在使用推推显示它们。我的故事板如下:

enter image description here

但是我想在第二个视图控制器上使用独立的导航栏。为此,我编写了以下代码:

override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)
    self.navigationController?.setNavigationBarHidden(true, animated: true)
    self.navigationController?.interactivePopGestureRecognizer?.delegate = nil
    placeNavigationBar()
}

override func viewWillDisappear(_ animated: Bool) {
    super.viewWillDisappear(animated)
    self.navigationController?.setNavigationBarHidden(false, animated: true)
}


var normalButton: UIButton!
var counter = 0
let item = UINavigationItem()
let navigationBar = UINavigationBar()
private func placeNavigationBar() {



    let backButtonImage = UIImage(named: "backButton")
    normalButton = UIButton(frame: CGRect(x: 0, y: 0, width: backButtonImage!.size.width, height: backButtonImage!.size.height))
    normalButton.setImage(backButtonImage, for: .normal)

    normalButton.setTitleColor(.systemBlue, for: .normal)
    normalButton.contentHorizontalAlignment = .leading
    normalButton.contentVerticalAlignment = .center
    normalButton.titleEdgeInsets = UIEdgeInsets(top: 0, left: 3.0, bottom: 0.0, right: -3.0)
    normalButton.contentEdgeInsets = UIEdgeInsets(top: 0, left: -10, bottom: 0, right: 0)

    let backBarButton = UIBarButtonItem(customView: normalButton)
    backBarButton.tintColor = .systemBlue


    let leftLabel = UILabel()
    leftLabel.text = "anony-12345678645"
    leftLabel.textColor = .black

    let profilePicture = UIImageView(frame: CGRect(x: 0, y: 0, width: 30, height: 30))
    profilePicture.translatesAutoresizingMaskIntoConstraints = false
    profilePicture.image = #imageLiteral(resourceName: "test2")
    profilePicture.contentMode = .scaleAspectFill


    profilePicture.clipsToBounds = true

    profilePicture.widthAnchor.constraint(equalToConstant: 30).isActive = true
    profilePicture.heightAnchor.constraint(equalToConstant: 30).isActive = true
    profilePicture.layer.cornerRadius = 15


    item.leftBarButtonItems = [backBarButton, UIBarButtonItem(customView: profilePicture) ,UIBarButtonItem(customView: leftLabel)]


    navigationBar.isTranslucent = false
    navigationBar.barTintColor = .white

    self.view.addSubview(navigationBar)
    navigationBar.translatesAutoresizingMaskIntoConstraints = false

    navigationBar.leftAnchor.constraint(equalTo: view.leftAnchor).isActive = true
    navigationBar.rightAnchor.constraint(equalTo: view.rightAnchor).isActive = true
    navigationBar.topAnchor.constraint(equalTo: view.safeAreaLayoutGuide.topAnchor).isActive = true



    navigationBar.items = [item]
    navigationBar.delegate = self
}

它运行良好,但我对导航栏过渡动画不满意。该视频显示了现在的样子:

https://www.youtube.com/watch?v=1wakUhA940c

我想要什么:

https://youtu.be/h3-HzKQsxWc

检查两个视频上的导航栏过渡,在第二个视频中,导航栏位于第一个视图控制器的导航栏的顶部。但是在第一个视频中,第二个导航栏只是将第一个导航栏推到屏幕外。

如何在第二个视频中实现相同的翻译?

2 个答案:

答案 0 :(得分:0)

我做了类似的操作,其中初始控制器具有一个自定义的导航栏,并且我所做的是使用navigationController.setNavigationBarHidden(_, animated: true)在每个控制器的viewWillAppear方法上调用true在主控制器上,false在其余控制器上。

您可以执行相同的操作,然后在视图中添加单独的UINavigationBar。如果正确设置其约束(基本上将其固定在控制器的safeArea.top上),它将扩展到安全区域。

您必须直接访问导航栏而不是控制器的navigationItem来填充导航栏,但这没什么大不了的,您将获得所需的转换。

如果您希望在堆栈中的所有控制器之间发生这种情况,只需隐藏导航控制器上的导航栏,然后自己在每个视图上设置一个导航栏即可。

答案 1 :(得分:0)

您不喜欢的实际上是iOS的默认行为,即动画。现在,做自己喜欢的事情的一种方法是制作自己的导航栏。

您可以使用以下方法在viewWillAppear方法中隐藏或显示(切换)导航栏的可见性:

/// Shows the navigation bar.
public func showNavBar(animated: Bool) {
    self.navigationController?.setNavigationBarHidden(false, animated: animated)
}

/// Hides the navigation bar.
public func hideNavBar(animated: Bool) {
    self.navigationController?.setNavigationBarHidden(true, animated: animated)
}

然后开始在Storyboard中进行导航栏的布局。

最后,利用模拟指标,例如选择顶部栏,可以帮助您直观地看到自己在做什么。

enter image description here