ios - How to resume core animation when the app back to foreground -


i have imageview , want rotate 360° time, found issue when app enters background , foreground, rotate animation stopped. , don't want re-call function rotate360degree() when app foreground, reason want rotate-animation start @ position left when entering background, instead of rotating 0 again. when call function resumerotate(), doesn't work.

the extension follow:

extension uiimageview {     // 360度旋转图片     func rotate360degree() {         let rotationanimation = cabasicanimation(keypath: "transform.rotation.z") // 让其在z轴旋转         rotationanimation.tovalue = nsnumber(value: .pi * 2.0) // 旋转角度         rotationanimation.duration = 20 // 旋转周期         rotationanimation.iscumulative = true // 旋转累加角度         rotationanimation.repeatcount = maxfloat // 旋转次数         rotationanimation.autoreverses = false         layer.add(rotationanimation, forkey: "rotationanimation")     }      // 暂停旋转     func pauserotate() {          layer.pauseanimation()     }      // 恢复旋转     func resumerotate() {          layer.resumeanimation()       }  } 

here layer extension :

var pausetime:cftimeinterval!  extension calayer {     //暂停动画     func pauseanimation() {         pausetime = converttime(cacurrentmediatime(), from: nil)         speed = 0.0         timeoffset = pausetime     }     //恢复动画     func resumeanimation() {         // 1.取出时间          pausetime = timeoffset         // 2.设置动画的属性         speed = 1.0         timeoffset = 0.0         begintime = 0.0         // 3.设置开始动画         let starttime = converttime(cacurrentmediatime(), from: nil) - pausetime         begintime = starttime     } } 

i can solve above 'stopped' issue cadisplaylink, animation not rotate position left(rotate time). wonder how solve cadisplaylink? , how above core animation?

displaylink = cadisplaylink(target: self, selector: #selector(rotateimage)) displaylink.add(to: .current, formode: .commonmodes)   func rotateimage(){           let angle =  cgfloat(displaylink.duration * double.pi / 18)           artworkimageview.transform = artworkimageview.transform.rotated(by: angle)      } 

you can uikit's higher-level block based animation api. if want continuously rotating view 20.0 second duration. can function like:

    func animateimageview()     {         uiview.animate(withduration: 10.0, delay: 0.0, options: [.beginfromcurrentstate, .repeat, .curvelinear], animations:         { [unowned self] in             var transform = self.imageview.transform             transform = transform.concatenating(cgaffinetransform(rotationangle: cgfloat.pi))             self.imageview.transform = transform         },         completion:         { _ in             uiview.animate(withduration: 10.0, delay: 0.0, options: [.beginfromcurrentstate, .curvelinear], animations:             { [unowned self] in                 var transform = self.imageview.transform                 transform = transform.concatenating(cgaffinetransform(rotationangle: cgfloat.pi / 2.0))                 self.imageview.transform = transform             })         })     } 

this rotate view 180 degrees once complete rotate 180 360 degree rotation. .repeat option cause repeat indefinitely. however, animation stop when app backgrounded. that, need save state of presentation layer of view being rotated. can storing cgaffinetransform of presentation layer , setting transform view being animated when app comes foreground. here's example uiimageview

class viewcontroller: uiviewcontroller {      @iboutlet weak var imageview: uiimageview!     var imageviewtransform = cgaffinetransform.identity      override func viewdidload()     {         super.viewdidload()         notificationcenter.default.addobserver(self, selector: #selector(self.didenterbackground), name: .uiapplicationdidenterbackground, object: nil)         notificationcenter.default.addobserver(self, selector: #selector(self.willenterforeground), name: .uiapplicationwillenterforeground, object: nil)     }      override func viewdidappear(_ animated: bool)     {         super.viewdidappear(animated)         animateimageview()     }      deinit     {         notificationcenter.default.removeobserver(self)     }      func didenterbackground()     {         imageviewtransform = imageview.layer.presentation()?.affinetransform() ?? .identity     }      func willenterforeground()     {         imageview.transform = imageviewtransform         animateimageview()     }      func animateimageview()     {         uiview.animate(withduration: 10.0, delay: 0.0, options: [.beginfromcurrentstate, .repeat, .curvelinear], animations:         { [unowned self] in             var transform = self.imageview.transform             transform = transform.concatenating(cgaffinetransform(rotationangle: cgfloat.pi))             self.imageview.transform = transform         },         completion:         { _ in             uiview.animate(withduration: 10.0, delay: 0.0, options: [.beginfromcurrentstate, .curvelinear], animations:             { [unowned self] in                 var transform = self.imageview.transform                 transform = transform.concatenating(cgaffinetransform(rotationangle: cgfloat.pi / 2.0))                 self.imageview.transform = transform             })         })     } } 

which results in this:

enter image description here


Comments

Popular posts from this blog

android - InAppBilling registering BroadcastReceiver in AndroidManifest -

python Tkinter Capturing keyboard events save as one single string -

sql server - Why does Linq-to-SQL add unnecessary COUNT()? -