使用约束的 UIImageView 的折叠和展开动画

Posted

技术标签:

【中文标题】使用约束的 UIImageView 的折叠和展开动画【英文标题】:Fold and unfold animation of UIImageView using constraints 【发布时间】:2019-10-28 20:49:08 【问题描述】:

正如您在下面的代码中看到的,我正在尝试使用约束制作折叠/展开动画。当然灰色背景有折叠/展开动画,但图像本身没有。

如何获得与图像本身相同的折叠/展开效果?

class ViewController2: UIViewController 
    var folded: Bool = false
    var imagen: UIImageView!
    private var foldConstraint: NSLayoutConstraint!
    override func viewDidLoad() 
        super.viewDidLoad()
        view.backgroundColor = .white
        let imagen = UIImageView(contentMode: .scaleAspectFill, image: #imageLiteral(resourceName: "gpointbutton"))
        imagen.translatesAutoresizingMaskIntoConstraints = false
        imagen.backgroundColor = .gray
        view.addSubview(imagen)
        self.imagen = imagen
        imagen.centerXAnchor.constraint(equalTo: view.centerXAnchor).isActive = true
        imagen.centerYAnchor.constraint(equalTo: view.centerYAnchor).isActive = true
        foldConstraint = imagen.heightAnchor.constraint(equalToConstant: 0)
        createAnimationButton()
    
    private func createAnimationButton() 
        let button = UIButton(title: "Animate", titleColor: .blue)
        button.translatesAutoresizingMaskIntoConstraints = false
        button.addAction(for: .touchUpInside)  [weak self] (_) in
            guard let self = self else  return 
            self.folded = !self.folded
            if self.folded 
                self.foldConstraint.isActive = true
                UIView.animate(withDuration: 0.5) 
                    self.imagen.setNeedsLayout()
                    self.imagen.superview?.layoutIfNeeded()
                
             else 
                self.foldConstraint.isActive = false
                UIView.animate(withDuration: 0.5) 
                    self.imagen.setNeedsLayout()
                    self.imagen.superview?.layoutIfNeeded()
                
            
        
        view.addSubview(button)
        button.centerXAnchor.constraint(equalTo: view.centerXAnchor).isActive = true
        button.bottomAnchor.constraint(equalTo: view.safeAreaLayoutGuide.bottomAnchor).isActive = true
    

【问题讨论】:

【参考方案1】:

这里需要注意的是widthheight约束设置为0(准确来说还包括0.1),同样是隐藏的。

那么你需要设置height约束大于0.1

foldConstraint = imagen.heightAnchor.constraint(equalToConstant: 0)

替换成这个,暂时设为1

foldConstraint = imagen.heightAnchor.constraint(equalToConstant: 1)

在动画结束时隐藏

        self.folded = !self.folded
        if self.folded 
            self.foldConstraint.isActive = true
            UIView.animate(withDuration: 1, animations: 
                self.imagen.setNeedsLayout()
                self.imagen.superview?.layoutIfNeeded()
            )  (completion) in
                self.imagen.isHidden = true
            
         else 
            self.imagen.isHidden = false
            self.foldConstraint.isActive = false
            UIView.animate(withDuration: 1, animations: 
                 self.imagen.setNeedsLayout()
                 self.imagen.superview?.layoutIfNeeded()
             )
        

更新:

scaleAspectFill不适合动画,应该设置为scaleAspectFit

let imagen = UIImageView(contentMode: .scaleAspectFit, image: #imageLiteral(resourceName: "gpointbutton"))

【讨论】:

嗨。感谢您的回复,并对误解表示抱歉,但我想创建 UIImageView 的折叠和展开动画,而不仅仅是隐藏它。我已经更改了问题的标题和描述。 是的,该程序已经过您的代码测试。你可以试试看。不要这么快做出决定。 @Ricardo 你需要改变高度的约束,仔细阅读我的回答 我做了,效果是一样的。图片只是隐藏或取消隐藏,没有折叠和展开动画。 你是怎么改的,因为我用你的代码写了demo,动画是可以的,是否加'foldConstraint = imagen.heightAnchor.constraint(equalToConstant: 1)'

以上是关于使用约束的 UIImageView 的折叠和展开动画的主要内容,如果未能解决你的问题,请参考以下文章

如何动态计算自定义展开/可折叠 UITableViewCell 的高度

展开和折叠视图上的标准 Cocoa 控件

高度约束动画“跳跃”

返回导航到根视图控制器后,折叠的大标题导航栏变得展开

在约束上动画更改 UITableView 节标题的高度

点击时UITableViewCell高度问题