11 Commits

Author SHA1 Message Date
Kaan Dedeoglu eeacb59a55 Make sure the presentationLayer is non-nil before trying to pause animations. Update to version 1.3.3 2016-01-27 12:07:46 +02:00
Kaan Dedeoglu ee5890b8ce Update Podspec to 1.3.2 2016-01-10 11:37:53 +02:00
Kaan Dedeoglu d116d7c380 Fix bug related to animations with progressInsideFillColor. Fix indentation 2016-01-10 11:34:56 +02:00
Kaan Dedeoglu 2ec2d6f783 Add gif to README 2015-11-12 14:39:40 +02:00
Kaan Dedeoglu 02dccb0804 Update podspec to 1.3.1 2015-11-11 13:57:45 +02:00
Kaan Dedeoglu 74c2c3c8d7 Update README.md 2015-11-11 13:56:37 +02:00
Kaan Dedeoglu f9194ec712 Add relativeDuration default value to animate methods to specify if the duration is global or specific to current angle 2015-11-11 13:52:04 +02:00
Kaan Dedeoglu 54e24f1053 Update podspec to 1.3 2015-10-16 03:38:16 +03:00
Kaan Dedeoglu 2385466f70 Update example animation call to restart it everytime the button is hit. 2015-10-16 03:37:19 +03:00
Kaan Dedeoglu ab6a4fd165 Some fixes for resizing behavior, invalidate gradient and gradient location caches when affecting properties change 2015-10-16 03:29:51 +03:00
Kaan Dedeoglu 5fe36abfe2 modify podspec for v1.2 2015-09-16 20:37:56 +03:00
6 changed files with 73 additions and 37 deletions
+2 -2
View File
@@ -1,6 +1,6 @@
Pod::Spec.new do |s|
s.name = 'KDCircularProgress'
s.version = '1.1'
s.version = '1.3.3'
s.license = 'MIT'
s.summary = 'A circular progress view with gradients written in Swift'
s.homepage = 'https://github.com/kaandedeoglu/KDCircularProgress'
@@ -11,4 +11,4 @@ Pod::Spec.new do |s|
s.source_files = 'KDCircularProgress/*.swift'
s.requires_arc = true
end
end
+64 -31
View File
@@ -171,23 +171,28 @@ public class KDCircularProgress: UIView {
self.init(frame: frame)
setColors(colors)
}
required public init(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)!
translatesAutoresizingMaskIntoConstraints = false
userInteractionEnabled = false
setInitialValues()
super.init(coder: aDecoder)!
translatesAutoresizingMaskIntoConstraints = false
userInteractionEnabled = false
setInitialValues()
refreshValues()
}
}
public override func awakeFromNib() {
checkAndSetIBColors()
}
override public class func layerClass() -> AnyClass {
return KDCircularProgressViewLayer.self
}
public override func layoutSubviews() {
super.layoutSubviews()
radius = (frame.size.width/2.0) * 0.8
}
private func setInitialValues() {
radius = (frame.size.width/2.0) * 0.8 //We always apply a 20% padding, stopping glows from being clipped
backgroundColor = .clearColor()
@@ -223,15 +228,24 @@ public class KDCircularProgress: UIView {
progressLayer.setNeedsDisplay()
}
public func animateFromAngle(fromAngle: Int, toAngle: Int, duration: NSTimeInterval, completion: ((Bool) -> Void)?) {
public func animateFromAngle(fromAngle: Int, toAngle: Int, duration: NSTimeInterval, relativeDuration: Bool = true, completion: ((Bool) -> Void)?) {
if isAnimating() {
pauseAnimation()
}
let animationDuration: NSTimeInterval
if relativeDuration {
animationDuration = duration
} else {
let traveledAngle = UtilityFunctions.Mod(toAngle - fromAngle, range: 360, minMax: (0, 360))
let scaledDuration = (NSTimeInterval(traveledAngle) * duration) / 360
animationDuration = scaledDuration
}
let animation = CABasicAnimation(keyPath: "angle")
animation.fromValue = fromAngle
animation.toValue = toAngle
animation.duration = duration
animation.duration = animationDuration
animation.delegate = self
angle = toAngle
animationCompletionBlock = completion
@@ -239,15 +253,15 @@ public class KDCircularProgress: UIView {
progressLayer.addAnimation(animation, forKey: "angle")
}
public func animateToAngle(toAngle: Int, duration: NSTimeInterval, completion: ((Bool) -> Void)?) {
public func animateToAngle(toAngle: Int, duration: NSTimeInterval, relativeDuration: Bool = true, completion: ((Bool) -> Void)?) {
if isAnimating() {
pauseAnimation()
}
animateFromAngle(angle, toAngle: toAngle, duration: duration, completion: completion)
animateFromAngle(angle, toAngle: toAngle, duration: duration, relativeDuration: relativeDuration, completion: completion)
}
public func pauseAnimation() {
let presentationLayer = progressLayer.presentationLayer() as! KDCircularProgressViewLayer
guard let presentationLayer = progressLayer.presentationLayer() as? KDCircularProgressViewLayer else { return }
let currentValue = presentationLayer.angle
progressLayer.removeAllAnimations()
animationCompletionBlock = nil
@@ -291,11 +305,25 @@ public class KDCircularProgress: UIView {
private class KDCircularProgressViewLayer: CALayer {
@NSManaged var angle: Int
var radius: CGFloat!
var radius: CGFloat! {
didSet {
invalidateGradientCache()
}
}
var startAngle: Int!
var clockwise: Bool!
var clockwise: Bool! {
didSet {
if clockwise != oldValue {
invalidateGradientCache()
}
}
}
var roundedCorners: Bool!
var gradientRotateSpeed: CGFloat!
var gradientRotateSpeed: CGFloat! {
didSet {
invalidateGradientCache()
}
}
var glowAmount: CGFloat!
var glowMode: KDCircularProgressGlowMode!
var progressThickness: CGFloat!
@@ -304,15 +332,14 @@ public class KDCircularProgress: UIView {
var progressInsideFillColor: UIColor = UIColor.clearColor()
var colorsArray: [UIColor]! {
didSet {
gradientCache = nil
locationsCache = nil
invalidateGradientCache()
}
}
var gradientCache: CGGradientRef?
var locationsCache: [CGFloat]?
private var gradientCache: CGGradientRef?
private var locationsCache: [CGFloat]?
struct GlowConstants {
static let sizeToGlowRatio: CGFloat = 0.00015
private struct GlowConstants {
private static let sizeToGlowRatio: CGFloat = 0.00015
static func glowAmountForAngle(angle: Int, glowAmount: CGFloat, glowMode: KDCircularProgressGlowMode, size: CGFloat) -> CGFloat {
switch glowMode {
case .Forward:
@@ -346,12 +373,13 @@ public class KDCircularProgress: UIView {
trackThickness = progressLayer.trackThickness
trackColor = progressLayer.trackColor
colorsArray = progressLayer.colorsArray
progressInsideFillColor = progressLayer.progressInsideFillColor
}
override init() {
super.init()
}
required init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
}
@@ -371,7 +399,7 @@ public class KDCircularProgress: UIView {
CGContextSetLineWidth(ctx, trackLineWidth)
CGContextSetLineCap(ctx, CGLineCap.Butt)
CGContextDrawPath(ctx, .FillStroke)
UIGraphicsBeginImageContextWithOptions(size, false, 0.0)
let imageCtx = UIGraphicsGetCurrentContext()
let reducedAngle = UtilityFunctions.Mod(angle, range: 360, minMax: (0, 360))
@@ -421,22 +449,22 @@ public class KDCircularProgress: UIView {
UIGraphicsPopContext()
}
func fillRectWithContext(ctx: CGContext!, color: UIColor) {
private func fillRectWithContext(ctx: CGContext!, color: UIColor) {
CGContextSetFillColorWithColor(ctx, color.CGColor)
CGContextFillRect(ctx, bounds)
}
func drawGradientWithContext(ctx: CGContext!, componentsArray: [CGFloat]) {
private func drawGradientWithContext(ctx: CGContext!, componentsArray: [CGFloat]) {
let baseSpace = CGColorSpaceCreateDeviceRGB()
let locations = locationsCache ?? gradientLocationsFromColorCount(componentsArray.count/4, gradientWidth: bounds.size.width)
let gradient: CGGradient
if let g = self.gradientCache {
gradient = g
} else {
let g = CGGradientCreateWithColorComponents(baseSpace, componentsArray, locations,componentsArray.count / 4)
guard let g = CGGradientCreateWithColorComponents(baseSpace, componentsArray, locations,componentsArray.count / 4) else { return }
self.gradientCache = g
gradient = g!
gradient = g
}
let halfX = bounds.size.width/2.0
@@ -451,7 +479,7 @@ public class KDCircularProgress: UIView {
CGContextDrawLinearGradient(ctx, gradient, startPoint, endPoint, .DrawsBeforeStartLocation)
}
func gradientLocationsFromColorCount(colorCount: Int, gradientWidth: CGFloat) -> [CGFloat] {
private func gradientLocationsFromColorCount(colorCount: Int, gradientWidth: CGFloat) -> [CGFloat] {
if colorCount == 0 || gradientWidth == 0 {
return []
} else {
@@ -469,5 +497,10 @@ public class KDCircularProgress: UIView {
return result
}
}
private func invalidateGradientCache() {
gradientCache = nil
locationsCache = nil
}
}
}
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="8191" systemVersion="15A279b" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" initialViewController="vXZ-lx-hvc">
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="8191" systemVersion="15A284" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" initialViewController="vXZ-lx-hvc">
<dependencies>
<deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="8154"/>
@@ -35,7 +35,7 @@ class ViewController: UIViewController {
}
@IBAction func animateButtonTapped(sender: UIButton) {
progress.animateToAngle(360, duration: 5) { completed in
progress.animateFromAngle(0, toAngle: 360, duration: 5) { completed in
if completed {
print("animation stopped, completed")
} else {
+5 -2
View File
@@ -8,8 +8,9 @@ Here's an example
[Youtube Link](http://youtu.be/iIdas72MXOg)
[![Screenshot](https://raw.githubusercontent.com/kaandedeoglu/KDCircularProgress/master/screenshot.png)](http://youtu.be/iIdas72MXOg)
![Screenshot](https://raw.githubusercontent.com/kaandedeoglu/KDCircularProgress/master/screenshot.gif)
![Screenshot](https://raw.githubusercontent.com/kaandedeoglu/KDCircularProgress/master/screenshot.png)
![Screenshot](https://raw.githubusercontent.com/kaandedeoglu/KDCircularProgress/master/screenshot2.jpg)
![Screenshot](https://raw.githubusercontent.com/kaandedeoglu/KDCircularProgress/master/screenshot3.jpg)
![Screenshot](https://raw.githubusercontent.com/kaandedeoglu/KDCircularProgress/master/screenshot4.jpg)
@@ -100,11 +101,13 @@ public func setColors(colors: UIColor...)
Set the colors for the progress gradient.
```swift
public func animateFromAngle(fromAngle: Int, toAngle: Int, duration: NSTimeInterval, completion: ((Bool) -> Void)?)
public func animateFromAngle(fromAngle: Int, toAngle: Int, duration: NSTimeInterval, relativeDuration: Bool = true, completion: ((Bool) -> Void)?)
```
Animate the progress from an initial value to a final value, with a completion block that fires after the animation is done.
`relativeDuration` - specify if the duration is for the specific animation or is the duration that would make a full turn.
```swift
public func animateToAngle(toAngle: Int, duration: NSTimeInterval, completion: ((Bool) -> Void)?)
```
BIN
View File
Binary file not shown.

After

Width:  |  Height:  |  Size: 861 KiB