简体   繁体   English

如何在屏幕之间保留navigationItem.titleView?

[英]How to persist navigationItem.titleView between screen?

I am using NavigationController to manage three screens. 我正在使用NavigationController来管理三个屏幕。 All three screens share a common image as title. 所有三个屏幕共享一个共同的图像作为标题。 I set the image in the viewWillAppear in each VC as follow: 我在每个VC的viewWillAppear中设置图像如下:

self.navigationItem.titleView = myImageView

The problem is whenever a screen is pushed/popped, the navigation is animated and a new image will come from right or left. 问题是每当按下/弹出屏幕,导航动画并且新图像将来自右侧或左侧时。 I want the image to persist and remain in the middle none-animated. 我希望图像能够持续存在并且保持在中间没有动画。

Is there a way to disable this animation? 有没有办法禁用这个动画?

It's reproducible, only if you place/setting titleView code in viewWillAppear . 只有在viewWillAppear放置/设置titleView代码时,它才是可重现的。 it's moving because viewWillAppear called during forth(push) & back(pop) both operation. 它正在移动,因为viewWillAppear在第四次(push)和后退(pop)两种操作中都被调用。 Set it into viewDidLoad , it will fix this issue 将其设置为viewDidLoad ,它将解决此问题

override fun viewDidLoad() {
 super.viewDidLoad()
 self.navigationItem.titleView = myImageView
}

One more alternate solution for this problem is 这个问题的另一个替代解决方案是

var isViewDidLoadCalled = false

override fun viewDidLoad() {
     super.viewDidLoad()
     isViewDidLoadCalled = true
}

override fun viewWillAppear(_ animated: Bool) {
     super. viewWillAppear(animated)

     if (isViewDidLoadCalled) {
       self.navigationItem.titleView = myImageView
       isViewDidLoadCalled = false
     }

 }

I recommend to use, viewDidLoad to setup your titleView 我建议使用viewDidLoad来设置你的titleView

Another hard but feasible solution is: 另一个困难但可行的解决方案是

You need to use the UINavigationController delegate methods to find out when the UIViewController is being shown. 您需要使用UINavigationController委托方法来查明何时显示UIViewController Then for each UIViewController, need to make a boolean variable like isInitialized property, which help you to determine when the UIViewController is being pushed on the stack, or when it's being shown upon back of next view controller. 然后对于每个UIViewController,需要创建一个类似于isInitialized属性的布尔变量,它可以帮助您确定何时将UIViewController压入堆栈,或者何时将其显示在下一个视图控制器的后面。

Your FirstViewController: 你的FirstViewController:

func navigationController(_ navigationController: UINavigationController, willShowViewController viewController: UIViewController, animated: Bool) {
        if viewController == self {
            if self.isInitialized {
                var navigationBarAnimation = CATransition()
                navigationBarAnimation.duration = 1.5
                navigationBarAnimation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseIn)
                navigationBarAnimation.type = kCATransitionFade
                navigationBarAnimation.subtype = kCATransitionFade
                navigationBarAnimation.removedOnCompletion = true
                self.navigationController?.navigationBar?.layer?.addAnimation(navigationBarAnimation, forKey: nil)

             } else {
                    self.isInitialized = true;
             }
        }
}

func navigationController(_ navigationController: UINavigationController, didShowViewController viewController: UIViewController, animated: Bool) {
        if viewController == self {
            if self.isInitialized {
                self.navigationController?.navigationBar?.layer?.removeAllAnimations()
            }
        }
    }

Your SecondViewController: 你的SecondViewController:

func navigationController(_ navigationController: UINavigationController, willShowViewController viewController: UIViewController, animated: Bool) {
        if viewController == self {
            if !self.isInitialized {
                var navigationBarAnimation = CATransition()
                navigationBarAnimation.duration = 1.5
                navigationBarAnimation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseIn)
                navigationBarAnimation.type = kCATransitionFade
                navigationBarAnimation.subtype = kCATransitionFade
                navigationBarAnimation.removedOnCompletion = true
                self.navigationController?.navigationBar?.layer?.addAnimation(navigationBarAnimation, forKey: nil)
                        self.isInitialized = true;
                }
        }
}

func navigationController(_ navigationController: UINavigationController, didShowViewController viewController: UIViewController, animated: Bool) {
        if viewController == self {
            if self.isInitialized {
                self.navigationController?.navigationBar?.layer?.removeAllAnimations()
            }
        }
 }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM