Анимированная смена изображения на панели навигации в Swift - PullRequest
0 голосов
/ 07 ноября 2018

У меня есть изображение на панели навигации ViewController, созданного в раскадровке, и свойство розетки для изображения, и я хочу анимировать переход к другому изображению. Контроллер представления запускается модально с использованием перехода.

У меня нет проблем с анимацией затухания изображения путем изменения его альфа-значения. Однако, если я изменю изображение, а не исчезну, анимации не будет. Вместо этого новое изображение становится видимым, как только страница загружается. Это верно, независимо от того, поместил ли я код анимации в viewDidLoad или viewWillAppear. Мне бы хотелось, чтобы эта анимация появлялась только один раз при загрузке представления, однако я попробовал ее в viewWillAppear, чтобы посмотреть, смогу ли я вообще получить эффект.

Вот мой код

// in viewdidload or viewwillappear
   let newImage = UIImage(named: "headshot.png")
    UIView.transition(with: self.imageView,
                      duration:0.5,
                      options: .transitionCrossDissolve,
                      animations: { self.ImageView.image = newImage },
                      completion: nil)

Есть ли что-то особенное в анимации изображения на панели навигации относительно обычного вида? Или что мне нужно сделать, чтобы оживить изменение изображения в панели навигации?

1 Ответ

0 голосов
/ 07 ноября 2018

Причина, по которой ваше изображение не анимируется, заключается в том, что с точки зрения компилятора замена изображения другим (как при вставке изображения) - это действие atomic . Это означает, что self.ImageView.image = newImage - это строка, которая происходит за один шаг. То есть в любой момент времени ваш imageView либо имеет newImage в качестве свойства image, либо его нет. Изменения в состоянии, которые происходят атомно, как это, не могут быть оживлены с течением времени.

Другой способ взглянуть на это состоит в том, что для того, чтобы изменить продолжительность вашей анимации на 0.5 секунд (вместо выполнения этого действия атомарно за один шаг), компилятор XCode должен был бы буквально поместить изображение в ваш файл. imageView в битах в течение 0.5 секунд. Понятно, что это неопределенное поведение. Как компилятор узнает, какие части изображения в какое время размещать на экране?

Простое решение вашей проблемы состоит в том, чтобы иметь два отдельных imageView, один из которых начинается с прозрачного, и размещенных в одном и том же месте на вашем экране. Каждый из imageView будет иметь отдельное изображение, и вы можете переходить между этими двумя изображениями, просто затухая одно изображение, а затем затухая в другом, например, так:

class viewController: UIViewController {
    let imageView1 = UIImageView("headshot1.png")
    let imageView2 = UIImageView("headshot2.png")

    override viewDidLoad() {
        super.viewDidLoad()

        /* add imageViews to your view and place them both 
           in the middle of the screen */
        imageView1.translatesAutoresizingMaskIntoConstraints = false
        imageView1.alpha = 1.0
        self.addSubview(imageView1)

        /* notice that this imageView is completely transparent */
        imageView2.translatesAutoresizingMaskIntoConstraints = false
        imageView2.alpha = 0.0
        self.addSubview(imageView2)

        /* place both imageViews in the middle of your screen,
           with imageView1 completely visible and imageView2
           completely transparent */
        imageView1.centerXAnchor.constraint(equalTo: self.view.centerXAnchor).isActive = true
        imageView1.centerYAnchor.constraint(equalTo: self.view.centerYAnchor).isActive = true

        imageView2.centerXAnchor.constraint(equalTo: self.view.centerXAnchor).isActive = true
        imageView2.centerYAnchor.constraint(equalTo: self.view.centerYAnchor).isActive = true

        // fade out first imageView
        UIView.animate(withDuration: 0.25) {
        imageView1.alpha = 0.0
        }

        // fade in second imageView
        UIView.animate(withDuration: 0.25) {
        imageView2.alpha = 1.0
        }
    }
}

Вы также можете использовать свою функцию transition вместо моей animate функции - логика практически та же.

...