From 76a035a2763b0ce98dd5ee351af44178fe6b1610 Mon Sep 17 00:00:00 2001 From: "Robin.Chao" Date: Sat, 12 Sep 2015 16:55:44 +0800 Subject: [PATCH] add BallSpinFadeLoader animation --- .../project.pbxproj | 6 ++ DGActivityIndicatorExample/ViewController.m | 3 +- .../DGActivityIndicatorBallSpinFadeLoader.h | 13 +++ .../DGActivityIndicatorBallSpinFadeLoader.m | 86 +++++++++++++++++++ .../DGActivityIndicatorView.h | 3 +- .../DGActivityIndicatorView.m | 3 + 6 files changed, 112 insertions(+), 2 deletions(-) create mode 100644 DGActivityIndicatorView/Animations/DGActivityIndicatorBallSpinFadeLoader.h create mode 100644 DGActivityIndicatorView/Animations/DGActivityIndicatorBallSpinFadeLoader.m diff --git a/DGActivityIndicatorExample.xcodeproj/project.pbxproj b/DGActivityIndicatorExample.xcodeproj/project.pbxproj index de0b7b9..f57bc20 100644 --- a/DGActivityIndicatorExample.xcodeproj/project.pbxproj +++ b/DGActivityIndicatorExample.xcodeproj/project.pbxproj @@ -45,6 +45,7 @@ 23D76E311B5C2BF100CD3248 /* DGActivityIndicatorBallClipRotateMultipleAnimation.m in Sources */ = {isa = PBXBuildFile; fileRef = 23D76E301B5C2BF100CD3248 /* DGActivityIndicatorBallClipRotateMultipleAnimation.m */; }; 23D76E341B5CBBD700CD3248 /* DGActivityIndicatorBallRotateAnimation.m in Sources */ = {isa = PBXBuildFile; fileRef = 23D76E331B5CBBD700CD3248 /* DGActivityIndicatorBallRotateAnimation.m */; }; 23FDAB411B5B8ED3000F636A /* DGActivityIndicatorBallPulseAnimation.m in Sources */ = {isa = PBXBuildFile; fileRef = 23FDAB401B5B8ED3000F636A /* DGActivityIndicatorBallPulseAnimation.m */; }; + 4B779891F5D7F9822D565959 /* DGActivityIndicatorBallSpinFadeLoader.m in Sources */ = {isa = PBXBuildFile; fileRef = 4B779BE1E0B67F4DE2C92A8E /* DGActivityIndicatorBallSpinFadeLoader.m */; }; /* End PBXBuildFile section */ /* Begin PBXContainerItemProxy section */ @@ -136,6 +137,8 @@ 23D76E331B5CBBD700CD3248 /* DGActivityIndicatorBallRotateAnimation.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = DGActivityIndicatorBallRotateAnimation.m; sourceTree = ""; }; 23FDAB3F1B5B8ED3000F636A /* DGActivityIndicatorBallPulseAnimation.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DGActivityIndicatorBallPulseAnimation.h; sourceTree = ""; }; 23FDAB401B5B8ED3000F636A /* DGActivityIndicatorBallPulseAnimation.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = DGActivityIndicatorBallPulseAnimation.m; sourceTree = ""; }; + 4B779312B3CDCCFAC9B06727 /* DGActivityIndicatorBallSpinFadeLoader.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DGActivityIndicatorBallSpinFadeLoader.h; sourceTree = ""; }; + 4B779BE1E0B67F4DE2C92A8E /* DGActivityIndicatorBallSpinFadeLoader.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = DGActivityIndicatorBallSpinFadeLoader.m; sourceTree = ""; }; /* End PBXFileReference section */ /* Begin PBXFrameworksBuildPhase section */ @@ -292,6 +295,8 @@ 23D76E301B5C2BF100CD3248 /* DGActivityIndicatorBallClipRotateMultipleAnimation.m */, 23413BA91B5CDA980014C2E8 /* DGActivityIndicatorBallZigZagAnimation.h */, 23413BAA1B5CDA980014C2E8 /* DGActivityIndicatorBallZigZagAnimation.m */, + 4B779312B3CDCCFAC9B06727 /* DGActivityIndicatorBallSpinFadeLoader.h */, + 4B779BE1E0B67F4DE2C92A8E /* DGActivityIndicatorBallSpinFadeLoader.m */, ); path = Animations; sourceTree = ""; @@ -430,6 +435,7 @@ 23413BAB1B5CDA980014C2E8 /* DGActivityIndicatorBallZigZagAnimation.m in Sources */, 23413BB41B5D0CD00014C2E8 /* DGActivityIndicatorBallScaleAnimation.m in Sources */, 23413BAE1B5CE4E90014C2E8 /* DGActivityIndicatorBallZigZagDeflectAnimation.m in Sources */, + 4B779891F5D7F9822D565959 /* DGActivityIndicatorBallSpinFadeLoader.m in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; diff --git a/DGActivityIndicatorExample/ViewController.m b/DGActivityIndicatorExample/ViewController.m index 5938c39..2af7c95 100644 --- a/DGActivityIndicatorExample/ViewController.m +++ b/DGActivityIndicatorExample/ViewController.m @@ -52,7 +52,8 @@ - (void)viewDidLoad { @(DGActivityIndicatorAnimationTypeRotatingSandglass), @(DGActivityIndicatorAnimationTypeRotatingTrigons), @(DGActivityIndicatorAnimationTypeTripleRings), - @(DGActivityIndicatorAnimationTypeCookieTerminator)]; + @(DGActivityIndicatorAnimationTypeCookieTerminator), + @(DGActivityIndicatorAnimationTypeBallSpinFadeLoader)]; for (int i = 0; i < activityTypes.count; i++) { DGActivityIndicatorView *activityIndicatorView = [[DGActivityIndicatorView alloc] initWithType:(DGActivityIndicatorAnimationType)[activityTypes[i] integerValue] tintColor:[UIColor whiteColor]]; diff --git a/DGActivityIndicatorView/Animations/DGActivityIndicatorBallSpinFadeLoader.h b/DGActivityIndicatorView/Animations/DGActivityIndicatorBallSpinFadeLoader.h new file mode 100644 index 0000000..6649163 --- /dev/null +++ b/DGActivityIndicatorView/Animations/DGActivityIndicatorBallSpinFadeLoader.h @@ -0,0 +1,13 @@ +// +// DGActivityIndicatorBallSpinFadeLoader.h +// CheeseDigest +// +// Created by Robin.Chao on 9/8/15. +// Copyright (c) 2015 mRocker. All rights reserved. +// + +#import "DGActivityIndicatorAnimationProtocol.h" + +@interface DGActivityIndicatorBallSpinFadeLoader : NSObject + +@end diff --git a/DGActivityIndicatorView/Animations/DGActivityIndicatorBallSpinFadeLoader.m b/DGActivityIndicatorView/Animations/DGActivityIndicatorBallSpinFadeLoader.m new file mode 100644 index 0000000..33b01d7 --- /dev/null +++ b/DGActivityIndicatorView/Animations/DGActivityIndicatorBallSpinFadeLoader.m @@ -0,0 +1,86 @@ +// +// DGActivityIndicatorBallSpinFadeLoader.m +// CheeseDigest +// +// Created by Robin.Chao on 9/8/15. +// Copyright (c) 2015 mRocker. All rights reserved. +// + +#import "DGActivityIndicatorBallSpinFadeLoader.h" + +@implementation DGActivityIndicatorBallSpinFadeLoader + + +#pragma mark - +#pragma mark DGActivityIndicatorAnimation Protocol + +- (void)setupAnimationInLayer:(CALayer *)layer withSize:(CGSize)size tintColor:(UIColor *)tintColor { + + CGFloat circleSpacing = -2; + CGFloat circleSize = (size.width - 4 * circleSpacing) / 5; + CGFloat x = (layer.bounds.size.width - size.width) / 2; + CGFloat y = (layer.bounds.size.height - size.height) / 2; + + CFTimeInterval duration = 1; + NSTimeInterval beginTime = CACurrentMediaTime(); + + NSArray *beginTimes = @[@0, @0.12, @0.24, @0.36, @0.48, @0.6, @0.72, @0.84]; + + CAKeyframeAnimation *scaleAnimation = [CAKeyframeAnimation animationWithKeyPath:@"transform.scale"]; + + scaleAnimation.keyTimes = @[@0, @0.5, @1]; + scaleAnimation.values = @[@1, @0.4, @1]; + scaleAnimation.duration = duration; + + + CAKeyframeAnimation *opacityAnimaton = [CAKeyframeAnimation animationWithKeyPath:@"opacity"]; + + + opacityAnimaton.keyTimes = @[@0, @0.5, @1]; + opacityAnimaton.values = @[@1, @0.3, @1]; + opacityAnimaton.duration = duration; + + + + + CAAnimationGroup *animationGroup = [CAAnimationGroup animation]; + animationGroup.animations = @[scaleAnimation, opacityAnimaton]; + animationGroup.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionLinear]; + animationGroup.duration = duration; + animationGroup.repeatCount = HUGE; + animationGroup.removedOnCompletion = NO; + + + for (int i = 0; i < 8; i++) { + CALayer *circle = [self circleLayer:(M_PI_4 * i) size:circleSize origin:CGPointMake(x, y) containerSize:size color:tintColor]; + animationGroup.beginTime = beginTime + [beginTimes[i] doubleValue]; + + [layer addSublayer:circle]; + [circle addAnimation:animationGroup forKey:@"animation"]; + } + +} + + +- (CALayer *)circleLayer:(CGFloat)angle size:(CGFloat)size origin:(CGPoint)origin containerSize:(CGSize)containerSize color:(UIColor *)color{ + CGFloat radius = containerSize.width/2; + CALayer *circle = [self createLayerWith:CGSizeMake(size, size) color:color]; + CGRect frame = CGRectMake((origin.x + radius * (cos(angle) + 1) - size / 2), origin.y + radius * (sin(angle) + 1) - size / 2, size, size); + circle.frame = frame; + + return circle; +} + +- (CALayer *)createLayerWith:(CGSize)size color:(UIColor *)color{ + CAShapeLayer *layer = [CAShapeLayer layer]; + UIBezierPath *path = [UIBezierPath bezierPath]; + + [path addArcWithCenter:CGPointMake(size.width / 2,size.height / 2) radius:(size.width / 2) startAngle:0 endAngle:2 * M_PI clockwise:NO]; + layer.fillColor = color.CGColor; + layer.backgroundColor = nil; + layer.path = path.CGPath; + + return layer; +} + +@end diff --git a/DGActivityIndicatorView/DGActivityIndicatorView.h b/DGActivityIndicatorView/DGActivityIndicatorView.h index 40b5e6a..7901b1e 100644 --- a/DGActivityIndicatorView/DGActivityIndicatorView.h +++ b/DGActivityIndicatorView/DGActivityIndicatorView.h @@ -40,7 +40,8 @@ typedef NS_ENUM(NSUInteger, DGActivityIndicatorAnimationType) { DGActivityIndicatorAnimationTypeRotatingSandglass, DGActivityIndicatorAnimationTypeRotatingTrigons, DGActivityIndicatorAnimationTypeTripleRings, - DGActivityIndicatorAnimationTypeCookieTerminator + DGActivityIndicatorAnimationTypeCookieTerminator, + DGActivityIndicatorAnimationTypeBallSpinFadeLoader }; @interface DGActivityIndicatorView : UIView diff --git a/DGActivityIndicatorView/DGActivityIndicatorView.m b/DGActivityIndicatorView/DGActivityIndicatorView.m index 9cde746..be3c37b 100644 --- a/DGActivityIndicatorView/DGActivityIndicatorView.m +++ b/DGActivityIndicatorView/DGActivityIndicatorView.m @@ -40,6 +40,7 @@ #import "DGActivityIndicatorRotatingTrigonAnimation.h" #import "DGActivityIndicatorTripleRingsAnimation.h" #import "DGActivityIndicatorCookieTerminatorAnimation.h" +#import "DGActivityIndicatorBallSpinFadeLoader.h" static const CGFloat kDGActivityIndicatorDefaultSize = 40.0f; @@ -191,6 +192,8 @@ - (void)setTintColor:(UIColor *)tintColor { return [[DGActivityIndicatorTripleRingsAnimation alloc]init]; case DGActivityIndicatorAnimationTypeCookieTerminator: return [[DGActivityIndicatorCookieTerminatorAnimation alloc]init]; + case DGActivityIndicatorAnimationTypeBallSpinFadeLoader: + return [[DGActivityIndicatorBallSpinFadeLoader alloc] init]; } return nil; }