Swift Animate


动画都是通过设置起始状态,结束状态,经过时间三个步骤实现的

Spring动画

一般usingSpringWithDamping设置为0.3或0.4

UIView.animate(
 withDuration: 0.3,
    delay: 0,
    usingSpringWithDamping: 0.4,//弹性阻尼 0-1
    initialSpringVelocity: 10,//初始弹簧速度
    options: [],
    animations: {
        self.menuBarAnimate()
},
    completion: nil
)

通过改变约束形成动画

改变约束常量constant

动画的函数withDuration设置时间

UIView.animate(withDuration: 0.3) {
    self.menuBarAnimate()
}

func menuBarAnimate() {
    menuHeight.constant = menuIsOpen ? 200 : 100
    btnTrailing.constant = menuIsOpen ? 20 : 8
    let angle = menuIsOpen ? CGFloat.pi/4 : 0 //2.按钮的旋转动画
    buttonMenu.transform = CGAffineTransform(rotationAngle: angle)
    
    view.layoutIfNeeded()//1.让根视图立刻重新布局
}

image的初始化,设置动画和销毁


func showItem(_ index: Int) {
        let imageView = UIImageView(image: UIImage(named: "summericons_100px_0\(index).png"))
        imageView.backgroundColor = UIColor(red: 0.0, green: 0.0, blue: 0.0, alpha: 0.5)
        imageView.layer.cornerRadius = 5.0//设置圆角属性需要加layer
        //1.用代码写的控件,默认情况下xcode会帮我们推断出约束,我们要自定义约束,所以定为false
        imageView.translatesAutoresizingMaskIntoConstraints = false
        view.addSubview(imageView)//在根视图上加子视图
        
        //1.设定初始约束
        let conWidth = imageView.widthAnchor.constraint(equalToConstant: 100)
        let conHight = imageView.heightAnchor.constraint(equalTo: imageView.widthAnchor)
        let conX = imageView.centerXAnchor.constraint(equalTo: view.centerXAnchor)
//        let conY = imageView.bottomAnchor.constraint(equalTo: view.bottomAnchor, constant: 100)
        let conY = imageView.topAnchor.constraint(equalTo: view.bottomAnchor)
        //传入约束
        NSLayoutConstraint.activate([conWidth,conHight,conX,conY])
        //约束生效
        view.layoutIfNeeded()
        
//        设定结束约束+经过时间
        UIView.animate(
            withDuration: 0.5,//时间
            delay: 0,//延迟多久
            usingSpringWithDamping: 0.4,
            initialSpringVelocity: 10,
            options: .curveEaseOut,//动画的类型
            animations: {//动画过程中要进行的操作
                conWidth.constant = 150
                conY.constant = -300
                self.view.layoutIfNeeded()
        },
            completion: nil
        )
        
//没有Spring的动画
//        UIView.animate(
//            withDuration: 0.5,               //时间
//            delay: 0,                        //延迟多久
//            options: .curveEaseOut,          //动画的类型
//            animations: {                    //动画过程中要进行的操作
//                conWidth.constant = 150
//                conY.constant = -300
//                self.view.layoutIfNeeded()
//        },
//
//            completion: nil          //动画结束
//        )
        
        //延迟一会消失
        UIView.animate(
            withDuration: 0.5,
            delay: 1.5,
            animations: {
                conWidth.constant = 100
                conY.constant = 0
                self.view.layoutIfNeeded()
        }) { _ in
            //销毁ImageView
            imageView.removeFromSuperview()
        }
    }
    
    
}

改变约束的乘数multiplier

其实multiplier值无法改变,但是可以设置两个multiplier不同的约束,在不同的情况设置他们的isActive

1.添加约束并且把Priority变小,取消Installed在这里插入图片描述

2.添加到view controller

@IBOutlet weak var titleCenterX: NSLayoutConstraint!
@IBOutlet weak var titleCenterXOpen: NSLayoutConstraint!

3.设置isActive

UIView.animate(withDuration: 0.3) {
    self.menuBarAnimate()
}

func menuBarAnimate() {
    //1.对居中对齐的约束改变,先添加一个约束然后设置isActive
    titleCenterXOpen.isActive = menuIsOpen
    titleCenterX.isActive = !menuIsOpen
    
    view.layoutIfNeeded()//1.让根视图立刻重新布局
}

通过改变元素的属性形成动画

改变alpha值

两个不同背景淡入淡出的无缝切换

func fade(toImage: UIImage, showEffects: Bool) {
    //背景图的imageview的淡出淡入
    //在View中放置两个ImageView一个淡出后下面一个消失,由此做到两个View的淡出淡入
    let temp = UIImageView(frame: bgImageView.frame)
    temp.image = toImage
    temp.alpha = 0 //完全透明
    view.insertSubview(temp, aboveSubview: bgImageView)//设置该ImageView在bgImageView的上面
    
    UIView.animate(
        withDuration: 0.5,
        animations: {
            temp.alpha = 1
    }) { _ in
        self.bgImageView.image = toImage
        temp.removeFromSuperview()
    }
    
    //雪景view的淡出淡入
    UIView.animate(withDuration: 1) {
        self.snowView.alpha = showEffects ? 1 : 0
    }
}

改变transform的translation

func duplicateLabel(label: UILabel) -> UILabel {
   let newLabel = UILabel(frame: label.frame)
    newLabel.font = label.font
    newLabel.textAlignment = label.textAlignment
    newLabel.textColor = label.textColor
    newLabel.backgroundColor = label.backgroundColor
    return newLabel
}

func moveLabel(currentLabel:UILabel,toText:String) {
    //新建一个临时label
    let temp = duplicateLabel(label: currentLabel)
    temp.text = toText
    temp.transform = CGAffineTransform(translationX: 80, y: 0)
    temp.alpha = 0
    view.addSubview(temp)
    
    //移出当前label+移入临时label
    UIView.animate(
        withDuration: 0.5,
        animations: {
            currentLabel.transform = CGAffineTransform(translationX: 80, y: 0)
            currentLabel.alpha = 0
            
            temp.transform = .identity//还原transform值
            temp.alpha = 1
            
    }) { _ in
        currentLabel.text = toText
        currentLabel.transform = .identity
        currentLabel.alpha = 1
        temp.removeFromSuperview()
    }
    //上述动作完成后更新实际label的text,并remove掉临时label
}

关键帧动画

func planeDepart() {
    let y = planeImage.center.y
    let x = planeImage.center.x
    UIView.animateKeyframes(
        withDuration: 1,
        delay: 0,
        animations: {
            //1.右移80,上移10
            UIView.addKeyframe(withRelativeStartTime: 0, relativeDuration: 0.25) {
                self.planeImage.center.x += 80
                self.planeImage.center.y += 10
            }
            //2.逆时针旋转22.5
            UIView.addKeyframe(withRelativeStartTime: 0.1, relativeDuration: 0.4) {
                self.planeImage.transform = CGAffineTransform(rotationAngle: -.pi/8)
            }
            //3.往右上移出屏幕,淡出
            UIView.addKeyframe(withRelativeStartTime: 0.25, relativeDuration: 0.25) {
                self.planeImage.center.x += 100
                self.planeImage.center.y -= 50
                self.planeImage.alpha = 0
            }
            //4.回到屏幕左边,准备淡入
            UIView.addKeyframe(withRelativeStartTime: 0.5, relativeDuration: 0.01) {
                self.planeImage.center.x = 0
                self.planeImage.center.y = y
                self.planeImage.transform = .identity
            }
            //5.回到原先位置,淡入
            UIView.addKeyframe(withRelativeStartTime: 0.55, relativeDuration: 0.45) {
                self.planeImage.center.x = x
                self.planeImage.center.y = y
                self.planeImage.alpha = 1
            }
    },
        completion: nil
    )
}
发布了19 篇原创文章 · 获赞 8 · 访问量 1443

猜你喜欢

转载自blog.csdn.net/qq_44864362/article/details/104202859