(一)自定义alert控件,有取消和确定两个按钮,分别定义了- (void)clickLeftButton:(UIButton *)leftButton inView:(UIView *)inView;和- (void)clickRightButton:(UIButton *)rightButton inView:(UIView *)inView(必须实现);
#import <UIKit/UIKit.h>
@protocol ITTAlertViewDelegate <NSObject>
- (void)clickRightButton:(UIButton *)rightButton inView:(UIView *)inView;
@optional
- (void)clickLeftButton:(UIButton *)leftButton inView:(UIView *)inView;
- (void)clcikCloseButton:(UIButton *)closeButton inView:(UIView *)inview;
@end
@interface ITTAlertView : UIView
@property (nonatomic,strong) id<ITTAlertViewDelegate> delegate;
@property (nonatomic,strong) UILabel *lblContent;
@property (nonatomic,strong) UILabel *lblTitle;
/**
* 初始化ITTAlertView
*/
- (instancetype)initWithFrame:(CGRect)frame Title:(NSString *)title content:(NSString *)contentString
leftButtonTitle:(NSString *)leftButtonTitle rightButtonTitle:(NSString *)rightButtonTitle;
/**
* 显示ITTAlertView
*/
- (void)showAlertView;
- (void)setAlertContentColor:(UIColor *)color font:(CGFloat)fontSize;
- (void)setAlertTitleColor:(UIColor *)color;
@end
(二)title的高度固定,而content的高度随文字长度自适应;
#import "ITTAlertView.h"
#define kAlertWidth 260
#define kAlertHeight 220
#define kColor [UIColor colorWithRed:0 green:160.0f/255 blue:223.0f/255 alpha:1.0]
#define kPhone @"400-6918-322"
@interface ITTAlertView ()
{
UIView *alert;
CGRect mainFrame;
CGFloat alertHieght;
}
@property (nonatomic,strong) UIView *backImageView;
@end
@implementation ITTAlertView
#define kTitleYOffset 15.0f
#define kTitleTopOffset 20.0f
#define kTitleHeight 20.0f
#define kContentOffset 15.0f
#define kBetweenLabelOffset 20.0f
#define kContentHeight 90.0f
#define kContentTopOffset 15.0f
/**
* 初始化ITTAlertView
*/
- (instancetype)initWithFrame:(CGRect)frame
Title:(NSString *)title
content:(NSString *)contentString
leftButtonTitle:(NSString *)leftButtonTitle
rightButtonTitle:(NSString *)rightButtonTitle
{
self = [super initWithFrame:frame];
if (self)
{
[self initAlertViewFrame];
self.lblTitle = [[UILabel alloc] initWithFrame:CGRectMake(kTitleYOffset, kTitleTopOffset, kAlertWidth - 2 * kTitleYOffset, kTitleHeight)];
self.lblTitle.text = title;
self.lblTitle.font = [UIFont systemFontOfSize:15.0f];
self.lblTitle.textColor = kColor;
self.lblTitle.textAlignment = NSTextAlignmentCenter;
[alert addSubview:self.lblTitle];
self.lblContent = [[UILabel alloc] initWithFrame:CGRectMake(kTitleYOffset, kTitleTopOffset + kTitleHeight + kContentTopOffset, kAlertWidth - 2 * kTitleYOffset, kContentHeight)];
self.lblContent.text = contentString;
self.lblContent.font = [UIFont systemFontOfSize:13.0f];
CGFloat height = [self.lblContent.text boundingRectWithSize:CGSizeMake(kAlertWidth - 2 * kTitleYOffset, MAXFLOAT) options:NSStringDrawingUsesFontLeading | NSStringDrawingUsesLineFragmentOrigin attributes:@{NSFontAttributeName:self.lblContent.font} context:nil].size.height;
CGRect newFrame = self.lblContent.frame;
newFrame.size.height = height;
self.lblContent.frame = newFrame;
self.lblContent.numberOfLines = 0;
self.lblContent.textAlignment = NSTextAlignmentCenter;
[alert addSubview:self.lblContent];
if (leftButtonTitle){
CGFloat width = (kAlertWidth - 2*kTitleYOffset - kBetweenLabelOffset)/2;
UIButton *leftButton = [[UIButton alloc] initWithFrame:CGRectMake(kTitleYOffset, CGRectGetMaxY(_lblContent.frame)+kContentTopOffset, width, 30.0f)];
[leftButton setTitle:leftButtonTitle forState:UIControlStateNormal];
[leftButton setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[leftButton setBackgroundColor:kColor];
[leftButton addTarget:self action:@selector(clickLeftButton:) forControlEvents:UIControlEventTouchUpInside];
[alert addSubview:leftButton];
UIButton *rightButton = [[UIButton alloc] initWithFrame:CGRectMake(CGRectGetMaxX(leftButton.frame) + kTitleYOffset, CGRectGetMaxY(_lblContent.frame)+kContentTopOffset, width, 30.0f)];
[rightButton setTitle:rightButtonTitle forState:UIControlStateNormal];
[rightButton setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[rightButton setBackgroundColor:kColor];
[rightButton addTarget:self action:@selector(clickRightButton:) forControlEvents:UIControlEventTouchUpInside];
[alert addSubview:rightButton];
alertHieght = CGRectGetMaxY(rightButton.frame)+kTitleTopOffset;
}else {
UIButton *rightButton = [[UIButton alloc] initWithFrame:CGRectMake(kTitleYOffset, CGRectGetMaxY(_lblContent.frame)+kContentTopOffset, kAlertWidth - 2 * kTitleYOffset, 30.0f)];
[rightButton setTitle:rightButtonTitle forState:UIControlStateNormal];
[rightButton setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[rightButton setBackgroundColor:kColor];
[rightButton addTarget:self action:@selector(clickRightButton:) forControlEvents:UIControlEventTouchUpInside];
[alert addSubview:rightButton];
alertHieght = CGRectGetMaxY(rightButton.frame)+kTitleTopOffset;
}
//重新设置alert的高度,以及center;
[self alertAutoHeight];
}
return self;
}
//设置ITTAlertView的frame
- (void)initAlertViewFrame
{
self.frame = [self mainScreenFrame];
self.opaque = YES;
self.backgroundColor = [UIColor clearColor];
[self makeBackgroundView];
[self makeAlertPopupView];
}
//创建背景view,并设置相关的属性
- (void)makeBackgroundView
{
self.backImageView = [[UIView alloc] initWithFrame:[UIScreen mainScreen].bounds];
self.backImageView.backgroundColor = [UIColor blackColor];
self.backImageView.alpha = 0.6f;
[self addSubview:self.backImageView];
}
/**
* 显示ITTAlertView
*/
- (void)showAlertView
{
[[UIApplication sharedApplication].keyWindow addSubview:self];
[self showAlertSpring];
}
//创建alertView
- (void)makeAlertPopupView
{
CGRect frame = CGRectMake(0, 0, kAlertWidth, kAlertHeight);
CGRect screen = [self mainScreenFrame];
alert = [[UIView alloc]initWithFrame:frame];
alert.center = CGPointMake(CGRectGetWidth(screen) / 2, CGRectGetHeight(screen) / 2);
alert.layer.masksToBounds = YES;
alert.backgroundColor = [UIColor colorWithWhite:1.0f alpha:1.0f];
alert.layer.cornerRadius = 6.0f;
[self addSubview:alert];
}
- (void)alertAutoHeight
{
CGRect screen = [self mainScreenFrame];
CGRect frame = alert.frame;
frame.size.height = alertHieght;
alert.frame = frame;
alert.center = CGPointMake(CGRectGetWidth(screen) / 2, CGRectGetHeight(screen) / 2);
}
//设置view的初始位置
#pragma mark - View Animation Methods
- (void)moveAlertPopupView
{
CGRect screen = [self mainScreenFrame];
CATransform3D move = CATransform3DIdentity;
CGFloat initAlertViewYPosition = (CGRectGetHeight(screen) + CGRectGetHeight(alert.frame)) / 2;
move = CATransform3DMakeTranslation(0, -initAlertViewYPosition, 0);
move = CATransform3DRotate(move, M_PI / 180, 0, 0, 1.0f);
alert.layer.transform = move;
}
//alert左右摇摆动画
- (void)showAlertShake
{
CATransform3D leftShake = CATransform3DMakeTranslation(-2.0f, 0.0f, 0.0f);
leftShake = CATransform3DRotate(leftShake, -2.0f * M_PI / 180, 0, 0, 1.0f);
CATransform3D rightShake = CATransform3DMakeTranslation(2.0f, 0.0f, 0.0f);
rightShake = CATransform3DRotate(rightShake, 2.0f * M_PI / 180, 0, 0, 1.0f);
alert.layer.transform = leftShake;
[UIView animateWithDuration:0.05f
delay:0.0f
options:UIViewAnimationOptionAutoreverse | UIViewAnimationOptionRepeat
animations:^{
[UIView setAnimationRepeatCount:3.0f];
alert.layer.transform = rightShake;
} completion:^(BOOL finished) {
if (finished)
{
CATransform3D move = CATransform3DIdentity;
alert.layer.transform = move;
}
}];
}
//弹出动画,带弹跳效果,弹跳系数1.0 -- 越接近0弹跳效果越强
- (void)showAlertSpring
{
CAKeyframeAnimation *keyAnima = [CAKeyframeAnimation animationWithKeyPath:@"transform"];
keyAnima.duration = 0.4f;
keyAnima.values = @[
[NSValue valueWithCATransform3D:CATransform3DMakeScale(0.01f, 0.01f, 1.0f)],
[NSValue valueWithCATransform3D:CATransform3DMakeScale(1.1f, 1.1f, 1.0f)],
[NSValue valueWithCATransform3D:CATransform3DMakeScale(0.9f, 0.9f, 1.0f)],
[NSValue valueWithCATransform3D:CATransform3DIdentity]
];
keyAnima.keyTimes = @[@0.2f, @0.5f, @0.75f, @1.0f];
keyAnima.timingFunctions = @[
[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut],
[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut],
[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]
];
[alert.layer addAnimation:keyAnima forKey:nil];
}
//从窗口移除view并附带动画
- (void)removeFromSuperview
{
[UIView animateWithDuration:0.4f animations:^{
alert.alpha = 0;
}];
CAKeyframeAnimation *keyAnima = [CAKeyframeAnimation animationWithKeyPath:@"transform"];
keyAnima.duration = 0.4f;
keyAnima.values = @[
[NSValue valueWithCATransform3D:CATransform3DMakeScale(1.1f, 1.1f, 1.0f)],
[NSValue valueWithCATransform3D:CATransform3DMakeScale(1.0f, 1.0f, 1.0f)],
[NSValue valueWithCATransform3D:CATransform3DMakeScale(0.0f, 0.0f, 1.0f)]
];
keyAnima.keyTimes = @[@0.2f, @0.5f, @0.75f];
keyAnima.timingFunctions = @[
[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut],
[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut],
[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]
];
keyAnima.delegate = self;
[alert.layer addAnimation:keyAnima forKey:nil];
}
//蒙版frame
- (CGRect)mainScreenFrame
{
return [UIScreen mainScreen].bounds;
}
- (void)clickRightButton:(UIButton *)sender
{
[self removeFromSuperview];
if (self.delegate && [self.delegate respondsToSelector:@selector(clickRightButton:inView:)]){
[self.delegate clickRightButton:sender inView:self];
}
}
- (void)clickLeftButton:(UIButton *)sender
{
[self removeFromSuperview];
if (self.delegate && [self.delegate respondsToSelector:@selector(clickLeftButton:inView:)]){
[self.delegate clickLeftButton:sender inView:self];
}
}
- (void)clickCloseButton:(UIButton *)sender
{
[self removeFromSuperview];
if (self.delegate && [self.delegate respondsToSelector:@selector(clcikCloseButton:inView:)]){
[self.delegate clcikCloseButton:sender inView:self];
}
}
//设置阴影
- (void)setShadowStyle:(UIButton *)currentButton
{
currentButton.layer.shadowOffset = CGSizeMake(1, 1);
currentButton.layer.shadowOpacity = 0.6f;
currentButton.layer.shadowRadius = 0.5f;
}
- (void)setAlertTitleColor:(UIColor *)color
{
_lblTitle.textColor = color;
}
- (void)setAlertContentColor:(UIColor *)color font:(CGFloat)fontSize
{
NSMutableAttributedString *attributeString = [[NSMutableAttributedString alloc] initWithString:_lblContent.text];
[attributeString addAttribute:NSForegroundColorAttributeName value:color range:[_lblContent.text rangeOfString:kPhone]];
[attributeString addAttribute:NSFontAttributeName value:[UIFont systemFontOfSize:fontSize] range:[_lblContent.text rangeOfString:kPhone]];
_lblContent.attributedText = attributeString;
}
- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag
{
[self.backImageView removeFromSuperview];
self.backImageView = nil;
[super removeFromSuperview];
}
@end
(三)总结
一个比较常规、中规中矩的alert自定义控件,旨在于学习自定义控件的效果和简单的动画,并不涉及很深的技术。