使用Facebook开源代码FBShimmering封装进度显示的ShimmeCircleView

简介:

使用Facebook开源代码FBShimmering封装进度显示的ShimmeCircleView

效果图:

静态图:

源码:

ShimmeCircleView.h 与 ShimmeCircleView.m

//
//  ShimmeCircleView.h
//  YouXianMingClock
//
//  Created by YouXianMing on 14-10-13.
//  Copyright (c) 2014年 YouXianMing. All rights reserved.
//

#import <UIKit/UIKit.h>

@interface ShimmeCircleView : UIView

/**
 *  时候开启闪光效果,默认是 NO
 */
@property (nonatomic, assign) BOOL             shimmering;

/**
 *  当 shimmering 开启时,进入到闪光状态中的动画时间,默认值是 0.3.
 */
@property (nonatomic, assign) CFTimeInterval   shimmeringBeginFadeDuration;

/**
 *  当 shimmering 结束时,从闪光动画退出到正常的时间,默认值是 0.3.
 */
@property (nonatomic, assign) CFTimeInterval   shimmeringEndFadeDuration;

/**
 *  The opacity of the content before it is shimmering. Defaults to 0.3.
 */
@property (nonatomic, assign) CGFloat          shimmeringOpacity;

/**
 *  The time interval between shimmerings in seconds. Defaults to 0.6.
 */
@property (nonatomic, assign) CFTimeInterval   shimmeringPauseDuration;

/**
 *  圆的颜色,默认为红色
 */
@property (nonatomic, assign) UIColor         *shapeColor;

/**
 *  圆的线宽度,默认为1
 */
@property (nonatomic, assign) CGFloat          shapeLineWidth;

/**
 *  动画时间间隔
 */
@property (nonatomic, assign) CFTimeInterval   strokeAnimationDuration;

/**
 *  更新shapeLayer(修改后必须更新path才能够生效)
 */
- (void)updateShapeLayer;

- (void)doPOPBasicEndAnimationToValue:(CGFloat)value;
- (void)doPOPBasicStartAnimationToValue:(CGFloat)value;

@end


//
//  ShimmeCircleView.m
//  YouXianMingClock
//
//  Created by YouXianMing on 14-10-13.
//  Copyright (c) 2014年 YouXianMing. All rights reserved.
//

#import "ShimmeCircleView.h"
#import "FBShimmering.h"
#import "FBShimmeringLayer.h"
#import "FBShimmeringView.h"
#import "POP.h"

/**
 *  将角度转换为弧度
 *
 *  @param d 角度
 *
 *  @return 弧度
 */
#define DEGREES__TO__RADIANS(d)  ((d) * M_PI / 180.f)


@interface ShimmeCircleView ()

{
    CAShapeLayer       *_shapeLayer; // 形状的layer
    FBShimmeringLayer  *_showLayer;  // 辉光的layer
}

@end


@implementation ShimmeCircleView

- (instancetype)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        // 创建FBShimmeringLayer
        if (_showLayer == nil) {
            _showLayer                             = [FBShimmeringLayer new];
            _showLayer.frame                       = self.bounds;
            _showLayer.position                    = self.center;
            _showLayer.shimmering                  = NO;          // 默认设置关闭
            _showLayer.shimmeringBeginFadeDuration = 0.3;         // 开始进入闪光时候的时间
            _showLayer.shimmeringEndFadeDuration   = 0.3;         // 从闪光进入没有闪光时候的时间
            _showLayer.shimmeringOpacity           = 0.3;
            _showLayer.shimmeringPauseDuration     = 0.6f;
            [self.layer addSublayer:_showLayer];
        }
        
        // 制造形状的layer
        if (_shapeLayer == nil) {
            _shapeLayer             = [CAShapeLayer layer];
            _shapeLayer.lineWidth   = 1.f;
            _shapeLayer.strokeEnd   = 0.f;
            _shapeLayer.strokeColor = [UIColor redColor].CGColor;
            _shapeLayer.fillColor   = [UIColor clearColor].CGColor;   // 设置填充颜色为透明
            _shapeLayer.path        = [self createCirclePath].CGPath;
            _showLayer.contentLayer = _shapeLayer;
        }
    }
    return self;
}

- (void)updateShapeLayer
{
    if (_shapeColor) {
        _shapeLayer.strokeColor = _shapeColor.CGColor;
    }
    
    if (_shapeLineWidth > 0) {
        _shapeLayer.lineWidth = _shapeLineWidth;
        _shapeLayer.path      = [self createCirclePath].CGPath; // 更新path
    }
}

- (void)doPOPBasicEndAnimationToValue:(CGFloat)value
{
    [self doStrokeEndAnimationFromValue:_shapeLayer.strokeEnd
                                toValue:value
                             shapeLayer:_shapeLayer
                               duration:(_strokeAnimationDuration > 0 ? _strokeAnimationDuration : 0.4f)
                     timingFunctionName:nil];
}

- (void)doPOPBasicStartAnimationToValue:(CGFloat)value
{
    [self doStrokeStartAnimationFromValue:_shapeLayer.strokeStart
                                  toValue:value
                               shapeLayer:_shapeLayer
                                 duration:(_strokeAnimationDuration > 0 ? _strokeAnimationDuration : 0.4f)
                       timingFunctionName:nil];
}

/**
 *  根据frame值创建圆形的贝塞尔曲线
 *
 *  @return 圆形的贝塞尔曲线
 */
- (UIBezierPath *)createCirclePath
{
    UIBezierPath *path = \
        [UIBezierPath bezierPathWithArcCenter:CGPointMake(self.bounds.size.height / 2.f,
                                                          self.bounds.size.width / 2.f)
                                       radius:self.bounds.size.height / 2.f - _shapeLayer.lineWidth / 2.f
                                   startAngle:DEGREES__TO__RADIANS(-90)
                                     endAngle:DEGREES__TO__RADIANS(270)
                                    clockwise:YES];
    
    return path;
}

#pragma mark - 重写各种setter方法
/**
 *  重写shimmering的setter,getter方法
 */
@synthesize shimmering = _shimmering;
- (BOOL)shimmering {
    return _shimmering;
}
- (void)setShimmering:(BOOL)shimmering {
    _shimmering = shimmering;
    _showLayer.shimmering = shimmering;
}

/**
 *  重写shimmeringBeginFadeDuration的setter,getter方法
 */
@synthesize shimmeringBeginFadeDuration = _shimmeringBeginFadeDuration;
- (CFTimeInterval)shimmeringBeginFadeDuration {
    return _shimmeringBeginFadeDuration;
}
- (void)setShimmeringBeginFadeDuration:(CFTimeInterval)shimmeringBeginFadeDuration {
    _shimmeringBeginFadeDuration = shimmeringBeginFadeDuration;
    _showLayer.shimmeringBeginFadeDuration = shimmeringBeginFadeDuration;
}

/**
 *  重写shimmeringEndFadeDuration的setter,getter方法
 */
@synthesize shimmeringEndFadeDuration = _shimmeringEndFadeDuration;
- (CFTimeInterval)shimmeringEndFadeDuration {
    return _shimmeringEndFadeDuration;
}
- (void)setShimmeringEndFadeDuration:(CFTimeInterval)shimmeringEndFadeDuration {
    _shimmeringEndFadeDuration = shimmeringEndFadeDuration;
    _showLayer.shimmeringEndFadeDuration = shimmeringEndFadeDuration;
}

/**
 *  重写shimmeringOpacity的setter,getter方法
 */
@synthesize shimmeringOpacity = _shimmeringOpacity;
- (CGFloat)shimmeringOpacity {
    return _shimmeringOpacity;
}
- (void)setShimmeringOpacity:(CGFloat)shimmeringOpacity {
    _shimmeringOpacity = shimmeringOpacity;
    _showLayer.shimmeringOpacity = shimmeringOpacity;
}

/**
 *  重写shimmeringPauseDuration的setter,getter方法
 */
@synthesize shimmeringPauseDuration = _shimmeringPauseDuration;
- (CFTimeInterval)shimmeringPauseDuration {
    return _shimmeringPauseDuration;
}
- (void)setShimmeringPauseDuration:(CFTimeInterval)shimmeringPauseDuration {
    _shimmeringPauseDuration = shimmeringPauseDuration;
    _showLayer.shimmeringPauseDuration = shimmeringPauseDuration;
}

#pragma mark - 私有方法

/**
 *  StrokeEnd动画
 *
 *  @param fromValue 初始值
 *  @param toValue   结束值
 *  @param layer     被动画的CAShapeLayer
 *  @param duration  动画时间
 *  @param name      动画时间类型,可以选择的类型如下:kCAMediaTimingFunctionLinear kCAMediaTimingFunctionEaseIn kCAMediaTimingFunctionEaseOut kCAMediaTimingFunctionEaseInEaseOut kCAMediaTimingFunctionDefault
 */
- (void)doStrokeEndAnimationFromValue:(CGFloat)fromValue
                              toValue:(CGFloat)toValue
                           shapeLayer:(CAShapeLayer *)layer
                             duration:(CFTimeInterval)duration
                   timingFunctionName:(NSString *)name
{
    POPBasicAnimation *pathAnimation = [POPBasicAnimation animationWithPropertyNamed:kPOPShapeLayerStrokeEnd];
    pathAnimation.duration           = duration;
    if (name) {
        pathAnimation.timingFunction = [CAMediaTimingFunction functionWithName:name];
    }
    pathAnimation.fromValue          = [NSNumber numberWithFloat:fromValue];
    pathAnimation.toValue            = [NSNumber numberWithFloat:toValue];
    [layer pop_addAnimation:pathAnimation forKey:nil];
}

/**
 *  StrokeStart动画
 *
 *  @param fromValue 初始值
 *  @param toValue   结束值
 *  @param layer     被动画的CAShapeLayer
 *  @param duration  动画时间
 *  @param name      动画时间类型,可以选择的类型如下:kCAMediaTimingFunctionLinear kCAMediaTimingFunctionEaseIn kCAMediaTimingFunctionEaseOut kCAMediaTimingFunctionEaseInEaseOut kCAMediaTimingFunctionDefault
 */
- (void)doStrokeStartAnimationFromValue:(CGFloat)fromValue
                                toValue:(CGFloat)toValue
                             shapeLayer:(CAShapeLayer *)layer
                               duration:(CFTimeInterval)duration
                     timingFunctionName:(NSString *)name
{
    POPBasicAnimation *pathAnimation = [POPBasicAnimation animationWithPropertyNamed:kPOPShapeLayerStrokeStart];
    pathAnimation.duration           = duration;
    if (name) {
        pathAnimation.timingFunction = [CAMediaTimingFunction functionWithName:name];
    }
    pathAnimation.fromValue          = [NSNumber numberWithFloat:fromValue];
    pathAnimation.toValue            = [NSNumber numberWithFloat:toValue];
    [layer pop_addAnimation:pathAnimation forKey:nil];
}

@end

以下是需要注意的地方:

以下是使用细节:

目录
相关文章
|
机器学习/深度学习 人工智能 搜索推荐
【推荐系统】Facebook经典模型GBDT+LR代码实践
【推荐系统】Facebook经典模型GBDT+LR代码实践
134 0
|
8月前
|
机器学习/深度学习 算法 决策智能
【重磅开源】Facebook开源 Nevergrad:一种用于无梯度优化的开源工具
【重磅开源】Facebook开源 Nevergrad:一种用于无梯度优化的开源工具
|
12月前
|
缓存 数据可视化 测试技术
开源多年后,Facebook这个调试工具,再登Github热门榜
让许多工程师合作开发大型应用大多会面临一个挑战,通常没有一个人知道每个模块是如何工作的,这种技能会让开发新功能、调查Bug或优化性能变得困难,为了解决这个问题,Facebook创建并开源了Flipper,一个可扩展的跨平台的调试工具,用来调试 iOS 和 Android 应用。近日又双叒登上了Github热榜。
|
机器学习/深度学习 算法 搜索推荐
【推荐系统】Facebook经典模型GBDT+LR代码实践
在CRT预估中,工业界一般是会采用逻辑回归进行处理,对用户特征画像进行建模,然后计算点击概率,评估用户是否会有点击的行为。
181 0
|
前端开发 JavaScript 测试技术
Facebook 开源可扩展文本编辑器 Lexical
Meta(原 Facebook)近日开源可扩展文本编辑器 Lexical,源代码托管在 GitHub 上采用 MIT 许可证。
392 0
Facebook 开源可扩展文本编辑器 Lexical
|
机器学习/深度学习 人工智能 JavaScript
自动写代码指日可待!Facebook迁移学习新突破,代码补全准确率超50%!(二)
程序员的工作就是取代重复、算法可替代的工作,而他们自己也在研究如何取代自己。Facebook新发表的代码补全模型准确率超50%,动动手指就能写几百行代码!
148 0
自动写代码指日可待!Facebook迁移学习新突破,代码补全准确率超50%!(二)
|
机器学习/深度学习 自然语言处理 IDE
自动写代码指日可待!Facebook迁移学习新突破,代码补全准确率超50%!(一)
程序员的工作就是取代重复、算法可替代的工作,而他们自己也在研究如何取代自己。Facebook新发表的代码补全模型准确率超50%,动动手指就能写几百行代码!
145 0
自动写代码指日可待!Facebook迁移学习新突破,代码补全准确率超50%!(一)
|
XML jenkins Java
Facebook开源静态代码分析工具Infer介绍
Infer是Facebook公司的一个开源的静态分析工具。Infer 可以分析 Objective-C, Java 或者 C 代码,用于发现潜在的问题。其作用类似于sonar和fortify。Infer更倾向于发现代码中的空指针异常、资源泄露以及内存泄漏的问题。
Facebook开源静态代码分析工具Infer介绍
|
机器学习/深度学习 人工智能 文字识别
图神经网络版本的PyTorch来了,Facebook开源GTN框架,还可对图自动微分
近日,Facebook的AI研究院发表了一篇论文「DIFFERENTIABLE WEIGHTED FINITE-STATE TRANSDUCERS」,开源了用于图网络建模的GTN框架,操作类似于PyTorch这种传统的框架,也可以进行自动微分等操作,大大提高了对图模型建模的效率。
271 0
图神经网络版本的PyTorch来了,Facebook开源GTN框架,还可对图自动微分
|
机器学习/深度学习 人工智能 自然语言处理
7.5亿美元做代码转换?一个Facebook TransCoder AI就够了!
代码的迁移和语言转换是一件很困难且昂贵的事情,澳大利亚联邦银行就曾花费5年时间,耗费7.5亿美元将其平台从COBOL转换为Java。而Facebook最近宣称,他们开发的一种神经转换编译器(neural transcompiler),可以将一种高级编程语言(如C ++,Java和Python)转换为另一种,效率飞起!
588 0
7.5亿美元做代码转换?一个Facebook TransCoder AI就够了!

相关实验场景

更多