下载:
链接: https://pan.baidu.com/s/1_DLzF52rRaZMVPbFRzW5Jg 提取码: atht
查看源码:
响应式编程
概念:响应式编程本质:众所周知,响应式编程基于观察者模式,即发布-订阅模式。
观察者模式是一种思想,即发布-订阅的思想,从中可以衍生出很多模型,本人见过的有发布者-订阅者模型、事件-事件源-监听器模型、被观察者-发射器-订阅者模型,就这三种模型而言,肯定都是属于响应式编程思想。其实本人认为,只要是观察者模式,都是响应式编程。
作为一个iOS 开发者,那么你一定用过Masnory/ SnapKit;每个优秀的框架都有一套自己的编程思想,Masnory这里使用的是经典的链式编程思想。我们不妨来学习一波。
我们平时是这样用Masnory给UI写约束布局的
UIView *view = [UIView new];
[self.view addSubview:view];
[view mas_makeConstraints:^(MASConstraintMaker *make) {
make.top.left.equalTo(self.view);
make.right.equalTo(self.view).offset(-20);
make.bottom.equalTo(self.view).offset(-200);
}];
上述代码思想是通过.符号把多行代码链接成一句代码,增强了可读性,例如a.b(2).c(3)一系列操作,那么在OC中要实现b(参数)这种调用方式,那么必然就是Block了。没错,链式编程的方法调用返回的是Block,而且调用完Block之后必然会有返回值(该返回值就是操作对象本身),这样才能链式调用,而且Block的参数就是需要内部对象操作的值。
如何实现链式操作
翻看Masonry源码
在.h的定义
在.m的实现
封装自己链式代码
通过查看Masonry源码,我们可以借鉴其优秀的思想,封装一下自己的代码,完成响应式编程创建UI控件。
平时我们自己创建一个UIButton的代码
UIButton *btn = [UIButton buttonWithType:UIButtonTypeCustom]; [btn addTarget:self action:@selector(loginBtnClick:) forControlEvents:UIControlEventTouchUpInside]; [btn setTitle:@"登录" forState:UIControlStateNormal]; btn.titleLabel.font = [UIFont systemFontOfSize:17]; [btn setBackgroundImage:[UIImage imageNamed:@"btn_bg_video_normal"] forState:UIControlStateNormal]; [btn setBackgroundImage:[UIImage imageNamed:@"btn_bg_video_pressed"] forState:UIControlStateHighlighted]; [btn setBackgroundImage:[[UIImage imageNamed:@"btn_switch_av"] mg_stretchableImage] forState:UIControlStateDisabled]; btn.layer.cornerRadius = 20.0; btn.clipsToBounds = YES; [self.view addSubview:btn]; UIButton *registBtn = [UIButton >buttonWithType:UIButtonTypeCustom]; [registBtn setTitle:@"注册" forState:UIControlStateNormal]; [registBtn setTitleColor:[UIColor colorWithHexString:@"#498ad9"] forState:UIControlStateNormal]; [registBtn addTarget:self action:@selector(registBtnClick:) forControlEvents:UIControlEventTouchUpInside]; [self.view addSubview:registBtn];
再看一下封装后的代码,看起来会比较紧凑,逼格高了 一个档次
// 登录按钮 UIButton *loginBtn = [UIButton speedCreatButtonWith:^(UIButton *button) { button.mg_Config() .mg_CornerRadius(20.0) .mg_FontSize(17) .mg_NormalText(@"登录") .mg_NormalBackgroundImage([UIImage imageNamed:@"btn_bg_video_normal"]) .mg_SelectedBackgroundImage([UIImage imageNamed:@"btn_bg_video_pressed"]) .mg_DisabledBackgroundImage([[UIImage imageNamed:@"btn_switch_av"] mg_stretchableImage]) .mg_Selector(self, @selector(loginBtnAction), UIControlEventTouchUpInside) .mg_AddTo(self.view); }]; // 注册 UIButton *registBtn = [UIButton speedCreatButtonWith:^(UIButton *button) { button.mg_Config() .mg_NormalText(@"注册") .mg_NormalTextColor([UIColor colorWithHexString:@"#498ad9"]) .mg_Selector(self, @selector(registBtnAction:), UIControlEventTouchUpInside) .mg_AddTo(self.view); }];
封装一个UILabel
只展示部分代码
.h实现
#import <UIKit/UIKit.h>
#pragma mark - UILabel
@interface UILabel (SpeedCreat)
/// 初始化
+ (UILabel *)label;
/// 初始化设置
@property (nonatomic,copy,readonly) UILabel *(^mg_Config)(void);
/// 是否可用
@property (nonatomic,assign,readonly) UILabel *(^mg_Enabled)(BOOL value);
/// 是否允许交互
@property (nonatomic,assign,readonly) UILabel *(^mg_UserInteractionEnabled)(BOOL value);
/// 是否隐藏
@property (nonatomic,assign,readonly) UILabel *(^mg_Hidden)(BOOL value);
/// frame
@property (nonatomic,assign,readonly) UILabel *(^mg_Frame)(CGRect value);
/// 文本
@property (nonatomic,copy,readonly) UILabel *(^mg_Text)(NSString *value)
@end
.m实现
#import "UIView+SpeedCreat.h"
@implementation UILabel (SpeedCreat)
+ (UILabel *)label {
return [[UILabel alloc] init];
}
- (UILabel*(^)(void))mg_Config {
return ^ () {
self.text = @"label";
[self sizeToFit];
self.font = [UIFont systemFontOfSize:14];
self.textColor = [UIColor blackColor];
self.textAlignment = NSTextAlignmentLeft;
self.numberOfLines = 1;
self.backgroundColor = [UIColor clearColor];
self.lineBreakMode = NSLineBreakByWordWrapping;
self.shadowColor = [UIColor clearColor];
self.shadowOffset = CGSizeMake(0, 0);
return self;
};
}
- (UILabel * _Nonnull (^)(BOOL))mg_Enabled {
return ^(BOOL value) {
self.enabled = value;
return self;
};
}
- (UILabel * _Nonnull (^)(BOOL))mg_UserInteractionEnabled {
return ^(BOOL value) {
self.userInteractionEnabled = value;
return self;
};
}
- (UILabel * _Nonnull (^)(CGFloat))mg_Alpha {
return ^(CGFloat value) {
self.alpha = value;
return self;
};
}
- (UILabel * _Nonnull (^)(BOOL))mg_Hidden {
return ^(BOOL value) {
self.hidden = value;
return self;
};
}
/// frame
- (UILabel*(^)(CGRect value))mg_Frame {
return ^ (CGRect value) {
self.frame = value;
return self;
};
}
/// 文字
- (UILabel*(^)(NSString *value))mg_Text {
return ^ (NSString *value) {
self.text = value;
return self;
};
}
@end
怎么使用:
导入头文件 #import "UIView+SpeedCreat.h"就可以愉快的玩耍啦
UILabel *titleLabel = [UILabel speedCreatLabelWith:^(UILabel *lb) {
lb.mg_TextAlignment(NSTextAlignmentCenter)
.mg_Text(titleText)
.mg_Font([UIFont fontWithName:@"PingFangSC-Regular" size:22])
.mg_TextColor(HEX_ARGB(@"000000"))
.mg_AddTo(self.contentView);
}];
网友评论