Block高級用法——鏈?zhǔn)骄幊毯喺?/h2>

? ? ? ?我的上一篇文章《iOS程序閃退時(shí)的處理一句代碼搞定異常攔截》中提到了“鏈?zhǔn)骄幊獭保赡苡凶x者關(guān)于“鏈?zhǔn)骄幊獭睍?huì)有些疑問。關(guān)于“鏈?zhǔn)骄幊獭本W(wǎng)上也有這方面的文章,這里就簡單地談一下個(gè)人的一點(diǎn)愚見,拋磚引玉吧,有不對的地方還請各位看官指正。
? ? ? ?先看段代碼

UIBtn(@"btn1").frame_l(CGRectMake(100, 100, 100, 60))
              .backgroundColor_l([UIColor redColor])
              .action(self, @selector(action1:), UIControlEventTouchUpInside)
              .addToView(self.view);

? ? ? ?上面這句代碼,將多行代碼通過.鏈接成一句代碼,這就是鏈?zhǔn)骄幊?,也是鏈?zhǔn)骄幊痰囊粋€(gè)優(yōu)點(diǎn)特點(diǎn)。使用起來很簡潔,可讀性好。
? ? ? ?怎么才能實(shí)現(xiàn)這樣的效果呢?看到.我想很多人會(huì)想到點(diǎn)語法,在oc里我們首先會(huì)想到一個(gè)類的實(shí)例對象的屬性可以被點(diǎn)出來。那么我們怎么才能夠一直點(diǎn)下去呢?那就是不斷地返回這個(gè)實(shí)例對象。繼續(xù)往下想,什么有返回值呢?方法有返回值,但是絕大多數(shù)的方法不能用.調(diào)用啊,WTF!怎么辦。是的,還有Block啊,而且Block還可以聲明成類的屬性。
? ? ? ?分析到這,那么我們就有了一個(gè)基本的思路:在類里的屬性用Block,而且Block的返回值是該類的一個(gè)實(shí)例,然后在這個(gè)Block里我們?nèi)プ鲆恍┫鄳?yīng)的操作。
? ? ? ?下面我以UIButton為例簡單說一下。首先我們創(chuàng)建一個(gè)UIButton的Category,當(dāng)然用繼承也可以。也許有的小伙伴找不到創(chuàng)建的地方,上個(gè)圖。之后的應(yīng)該都會(huì)了。

接下來上代碼(一塊來吧,我覺得這樣直觀一些,后面再分開說),先來.h

#import <UIKit/UIKit.h>

@interface UIButton (Link)

@property (nonatomic, copy) UIButton *(^frame_l)(CGRect rect);
@property (nonatomic, copy) UIButton *(^backgroundColor_l)(UIColor *color);
@property (nonatomic, copy) UIButton *(^addToView)(UIView *view);
@property (nonatomic, copy) UIButton *(^action)(id target, SEL selector, UIControlEvents events);

UIButton * UIBtn(id name);

@end
  • 這里聲明了四個(gè)Block,分別用來設(shè)置frame,backgroundColor,要添加到的父視圖,以及Action點(diǎn)擊事件
  • 下面的c方法,是用來創(chuàng)建實(shí)例對象的,里面的參數(shù)相當(dāng)于對象名,就不用這樣[UIButton buttonWithType:UIButtonTypeCustom];創(chuàng)建了,寫起來更整潔
再來.m
#import "UIButton+Link.h"
UIButton *button;
@implementation UIButton (Link)
-(UIButton *(^)(CGRect))frame_l {
    return ^(CGRect fra) {
        button.frame = fra;
        return button;
    };
}
-(void)setFrame_l:(UIButton *(^)(CGRect))frame_l {};
-(UIButton *(^)(UIColor *))backgroundColor_l {
    return ^(UIColor *color) {
        button.backgroundColor = color;
        return button;
    };
}
-(void)setBackgroundColor_l:(UIButton *(^)(UIColor *))backgroundColor_l {};
-(UIButton *(^)(UIView *))addToView {
    return ^(UIView *view) {
        [view addSubview:button];
        return button;
    };
}
-(void)setAddToView:(UIButton *(^)(UIView *))addToView {};
-(UIButton *(^)(id, SEL, UIControlEvents))action {
    return ^(id target, SEL selector, UIControlEvents events) {
        [button addTarget:target action:selector forControlEvents:events];
        return button;
    };
}
-(void)setAction:(UIButton *(^)(id, SEL, UIControlEvents))action {};
@end
UIButton * UIBtn(id name) {
    button = [UIButton buttonWithType:UIButtonTypeCustom];
    return button;
}
  • .m主要就是實(shí)現(xiàn)屬性的getter和setter方法,這里實(shí)現(xiàn)setter是為了消除警告
  • c方法中我們對全局的button對象初始化,然后每個(gè)屬性的getter方法都返回這個(gè)對象

? ? ? ?這樣我們在使用時(shí),就達(dá)到了文章開頭那段代碼的效果,實(shí)現(xiàn)了“鏈?zhǔn)骄幊獭???梢砸恢秉c(diǎn)點(diǎn)點(diǎn)了
? ? ? ?但是現(xiàn)在Xcode對Block的提示不是太友好

當(dāng)我們按下回車之后,只會(huì)出現(xiàn)addToView不會(huì)自動(dòng)補(bǔ)齊后面的參數(shù)

? ? ? ?就說這么多吧,有興趣的童鞋可以繼續(xù)添加屬性設(shè)置。

最后來個(gè)彩蛋,關(guān)于Block

  • 在調(diào)用Block時(shí)我們都會(huì)先判斷其是否為nil,防止崩潰,通常是這樣的
if (block) {
        block();
    }

其實(shí)還可以這樣

!block ? : block();

? ? ? ?時(shí)間倉促,文章有誤之處還請各位留言指正。技術(shù)無止境,共同進(jìn)步,寫出優(yōu)雅的代碼,是我不變的追求。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容