0%

AFViewShaker—— 为视图添加抖动效果

  • GitHub 源码:AFViewShaker
  • star:1100+
                            ⭐️⭐️⭐️ 

以下内容来源于官方源码、 README 文档、测试 Demo 或个人使用总结 !

AFViewShaker

About

AFViewShaker 实现了简单的 UIView 砖块抖动效果。

使用

为一个视图创建抖动效果
AFViewShaker * viewShaker = [[AFViewShaker alloc] initWithView:self.formView];
为多个视图创建抖动效果
NSArray * allFields = @[self.emailField, self.passwordField];
AFViewShaker * viewShaker = [[AFViewShaker alloc] initWithViewsArray:allFields];
使用默认参数抖动
// 抖动 AFViewShaker 实例中的所有视图
[self.viewShaker shake];

// 抖动指定的视图
[[[AFViewShaker alloc] initWithView:self.allButtons[0]] shake];
使用附带参数配置抖动
[self.viewShaker shakeWithDuration:0.6 completion:^{
    NSLog(@"Hello World!");
}];

源码

AFViewShaker.h
// 2个初始化方法
- (instancetype)initWithView:(UIView *)view;
- (instancetype)initWithViewsArray:(NSArray *)viewsArray;

// 2个抖动方法
- (void)shake;
- (void)shakeWithDuration:(NSTimeInterval)duration completion:(void (^)())completion;
AFViewShaker.m
//
//  AFViewShaker
//  AFViewShaker
//
//  Created by Philip Vasilchenko on 03.12.13.
//  Copyright (c) 2014 okolodev. All rights reserved.
//

#import "AFViewShaker.h"

// 默认延时
static NSTimeInterval const kAFViewShakerDefaultDuration = 0.5;
static NSString * const kAFViewShakerAnimationKey = @"kAFViewShakerAnimationKey";

#if __IPHONE_OS_VERSION_MAX_ALLOWED < 100000
// CAAnimationDelegate is not available before iOS 10 SDK
@interface AFViewShaker ()
#else
@interface AFViewShaker () <CAAnimationDelegate>
#endif

/** 包含视图的数组 */
@property (nonatomic, strong) NSArray * views;
/** 完成动画 */
@property (nonatomic, assign) NSUInteger completedAnimations;
/** 完成后调用 Block 对象 */
@property (nonatomic, copy) void (^completionBlock)();

@end


@implementation AFViewShaker

- (instancetype)initWithView:(UIView *)view {
    // 这里只是调用了指定初始化方法,往数组里扔了一个 View
    return [self initWithViewsArray:@[view]];
}

// 指定初始化方法
- (instancetype)initWithViewsArray:(NSArray *)viewsArray {
    self = [super init];
    if (self) {
        self.views = viewsArray;
    }
    return self;
}


#pragma mark - Public methods

- (void)shake {
    // 这里调用了下面的默认指定动画方法,传入的延时是全局静态变量
    [self shakeWithDuration:kAFViewShakerDefaultDuration completion:nil];
}

// 指定动画方法
- (void)shakeWithDuration:(NSTimeInterval)duration completion:(void (^)())completion {
    self.completionBlock = completion;
    for (UIView * view in self.views) {
        // 遍历视图,为每个视图添加动画
        [self addShakeAnimationForView:view withDuration:duration];
    }
}


#pragma mark - Shake Animation

- (void)addShakeAnimationForView:(UIView *)view withDuration:(NSTimeInterval)duration {
    CAKeyframeAnimation * animation = [CAKeyframeAnimation animationWithKeyPath:@"transform.translation.x"];
    CGFloat currentTx = view.transform.tx;

    animation.delegate = self;
    animation.duration = duration;
    // 偏移量
    animation.values = @[@(currentTx),
                         @(currentTx + 10),
                         @(currentTx - 8),
                         @(currentTx + 8),
                         @(currentTx - 5),
                         @(currentTx + 5),
                         @(currentTx)];
    // 动画时间
    animation.keyTimes = @[@(0), @(0.225), @(0.425), @(0.6), @(0.75), @(0.875), @(1)];
    animation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
    [view.layer addAnimation:animation forKey:kAFViewShakerAnimationKey];
}


#pragma mark - CAAnimation Delegate

- (void)animationDidStop:(CAAnimation *)animation finished:(BOOL)flag {
    self.completedAnimations += 1;
    if (self.completedAnimations >= self.views.count) {
        self.completedAnimations = 0;
        if (self.completionBlock) {
            // 遍历视图,当所有视图的动画完成以后就调用 Block 对象
            self.completionBlock();
        }
    }
}


@end
  • 配合 MBProgressHUD 使用:
    <!–hexoPostRenderEscape:

    //--------------------------------
    // .h
    /**
    输入文本框抖动效果

    @param view 需要抖动的文本框视图
    @param text 抖动结束后显示的 HUD 提示
    @param HUDView 呈现 HUD 的视图
    */

  • (void) shakeWithView:(UIView *)view
             HUDText:(NSString *)text
           addToView:(UIView *)HUDView;

//——————————–
// .m

  • (void) shakeWithView:(UIView *)view
             HUDText:(NSString *)text
           addToView:(UIView *)HUDView &#123;
    AFViewShaker *viewShaker = [[AFViewShaker alloc] initWithView:view];
    [viewShaker shakeWithDuration:KAFViewShakerDuration
                     completion:^&#123;
      [MBProgressHUD hql_showTextHUD:text toView:HUDView];
    }];
    }
    :hexoPostRenderEscape–>

欢迎关注我的其它发布渠道