高度自定義的STDPickerView

年前的某天棚潦,公司的UI拿了張?jiān)O(shè)計(jì)圖讓我看下能否實(shí)現(xiàn)令漂,隨意一瞥發(fā)現(xiàn)只是個(gè)PickerView,心想著用UIPickerView封裝一下還不是so easy的事情丸边,然而接下去了解了需求后才發(fā)現(xiàn)沒(méi)那么簡(jiǎn)單......

需要實(shí)現(xiàn)的效果

具體需求如下:

  • 需要能自定義選中顏色及未選中顏色叠必,且跟隨滾動(dòng)實(shí)時(shí)變化;
  • 需要能自定義選中指示器妹窖;
  • 需要滾動(dòng)效果是平面滾動(dòng)纬朝;

根據(jù)上面的需求,翻看了下UIPickerView的接口并寫代碼測(cè)試了下后發(fā)現(xiàn)情況不容樂(lè)觀:

  • UIPickerView默認(rèn)不支持選中顏色設(shè)置骄呼,可通過(guò)自定義view實(shí)現(xiàn)共苛,但是無(wú)法跟隨滾動(dòng)實(shí)時(shí)變化判没;
  • UIPickerView原生不支持設(shè)置選中指示器樣式;
  • UIPickerView默認(rèn)滾動(dòng)效果為類曲面滾動(dòng)隅茎,且不支持設(shè)置澄峰;

到現(xiàn)在已經(jīng)基本確定UIPickerView的方案已經(jīng)被斃了,不過(guò)沒(méi)關(guān)系辟犀,原生沒(méi)法實(shí)現(xiàn)那么就自己實(shí)現(xiàn)一個(gè)俏竞,于是 STDPickerView 就在這種情況下誕生了:

STDPickerView 是什么

STDPickerView 是基于 UICollectionView 封裝的選擇控件,兼容UIPickerView大部分接口堂竟,并增加了多個(gè)定制化接口魂毁,可實(shí)現(xiàn)更多的效果!STDPickerView 效果圖如下:

默認(rèn)樣式
分割選中指示器
垂直分割線
自定義view

STDPickerView 怎么使用

  • 初始化
STDPickerView *pickerView = [[STDPickerView alloc] init];
      
pickerView.dataSource = self;
pickerView.delegate = self;
  
/*
    STDPickerViewSelectionIndicatorStyleNone:無(wú)選中指示器
    STDPickerViewSelectionIndicatorStyleDefault:默認(rèn)選中指示器
    STDPickerViewSelectionIndicatorStyleDivision: 分段選中指示器
    STDPickerViewSelectionIndicatorStyleCustom:自定義選中指示器出嘹,需實(shí)現(xiàn) selectionIndicatorViewInPickerView: 代理方法
*/
pickerView.selectionIndicatorStyle = STDPickerViewSelectionIndicatorStyleDefault;
  
/* 
    默認(rèn)情況下席楚,如果同時(shí)實(shí)現(xiàn)了titleForRow以及viewForRow數(shù)據(jù)源方法,
    則會(huì)優(yōu)先使用viewForRow方法返回自定義view税稼,
    此時(shí)可設(shè)置 forceItemTypeText = YES 來(lái)指定使用titleForRow方法
*/
pickerView.forceItemTypeText = YES;
  
//是否顯示垂直分割線
pickerView.showVerticalDivisionLine = YES;
      
//設(shè)置pickerView四周的間距
pickerView.edgeInsets = UIEdgeInsetsMake(0, 20, 0, 20);
  
//設(shè)置component之間的間距
pickerView.spacingOfComponents = 30;
  
//僅在文本模式下有效
pickerView.textColor = kLightTextColor;
pickerView.selectedTextColor = kGlobalColor;
pickerView.font = [UIFont systemFontOfSize:16];
  
...
  
[self.view addSubview:pickerView];
  • 通用數(shù)據(jù)源及代理方法
#pragma mark - STDPickerViewDataSource
  
//返回component數(shù)目
- (NSInteger)numberOfComponentsInPickerView:(UIPickerView *)pickerView
{
    return 1;
}
  
//返回row數(shù)目
- (NSInteger)pickerView:(STDPickerView *)pickerView numberOfRowsInComponent:(NSInteger)component
{
    return self.items.count;
}
  
  
#pragma mark - STDPickerViewDelegate
  
//返回條目高度
- (CGFloat)pickerView:(STDPickerView *)pickerView rowHeightForComponent:(NSInteger)component
{
    return 60;
}
  
//選中了某個(gè)條目
- (void)pickerView:(STDPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component
{
    NSLog(@"pickerView - didSelectRow %zd inComponent %zd", row, component);
}
  
//若selectionIndicatorStyle = STDPickerViewSelectionIndicatorStyleCustom烦秩,則需實(shí)現(xiàn)以下方法
- (UIView *)selectionIndicatorViewInPickerView:(STDPickerView *)pickerView
{
    UIView *view = [[UIView alloc] init];
      
    view.backgroundColor = kGlobalColorWithAlpha(0.3);
      
    view.layer.cornerRadius = 5;
    view.layer.masksToBounds = YES;
      
    return view;
}
  
...
  • 默認(rèn)選中樣式
#pragma mark - STDPickerViewDataSource
  
// 返回item的標(biāo)題
(注:若同時(shí)實(shí)現(xiàn)了 pickerView: viewForRow:forComponent:reusingView: 優(yōu)先采用后者,此時(shí)可通過(guò)設(shè)置 forceItemTypeText = YES 來(lái)強(qiáng)制使用本方法)
- (NSString *)pickerView:(STDPickerView *)pickerView titleForRow:(NSInteger)row forComponent:(NSInteger)component
{
    return self.items[row];
}
  • 自定義選中樣式
#pragma mark - STDPickerViewDataSource
  
// 返回item的自定義view娶聘,優(yōu)先級(jí)較高
(注:若同時(shí)實(shí)現(xiàn)了 pickerView: titleForRow:forComponent: 且 forceItemTypeText = YES 則本方法無(wú)效)
- (UIView *)pickerView:(STDPickerView *)pickerView viewForRow:(NSInteger)row forComponent:(NSInteger)component reusingView:(UIView *)view
{
    UILabel *label = (UILabel *)view;
      
    if (!label) {
        label = [[UILabel alloc] init];
          
        label.textAlignment = NSTextAlignmentCenter;
    }
      
    label.textColor = kLightTextColor;
    label.transform = CGAffineTransformIdentity;
    label.text = self.items[row];
      
    return label;
}
  
#pragma mark - STDPickerViewDelegate
  
//可在此方法及willDeselectRow中實(shí)現(xiàn)自定義的切換效果
- (void)pickerView:(STDPickerView *)pickerView willSelectRow:(NSInteger)row inComponent:(NSInteger)component
{
    UILabel *label = (UILabel *)[pickerView viewForRow:row forComponent:component];
      
    [UIView animateWithDuration:0.25 animations:^{
        label.transform = CGAffineTransformMakeScale(1.5, 1.5);
    }];
      
    label.textColor = kGlobalColor;    
}
  
- (void)pickerView:(STDPickerView *)pickerView willDeselectRow:(NSInteger)row inComponent:(NSInteger)component
{
    UILabel *label = (UILabel *)[pickerView viewForRow:row forComponent:component];
      
    [UIView animateWithDuration:0.25 animations:^{
        label.transform = CGAffineTransformIdentity;
    }];
      
    label.textColor = kLightTextColor;
}

目前 STDPickerView 已經(jīng)開源到GitHub上并支持CocoaPods集成闻镶,歡迎大家下載與star!

GitHub: https://github.com/XuQibin/STDPickerView

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末丸升,一起剝皮案震驚了整個(gè)濱河市铆农,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌狡耻,老刑警劉巖墩剖,帶你破解...
    沈念sama閱讀 221,635評(píng)論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異夷狰,居然都是意外死亡岭皂,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,543評(píng)論 3 399
  • 文/潘曉璐 我一進(jìn)店門沼头,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)爷绘,“玉大人,你說(shuō)我怎么就攤上這事进倍⊥林粒” “怎么了?”我有些...
    開封第一講書人閱讀 168,083評(píng)論 0 360
  • 文/不壞的土叔 我叫張陵猾昆,是天一觀的道長(zhǎng)陶因。 經(jīng)常有香客問(wèn)我,道長(zhǎng)垂蜗,這世上最難降的妖魔是什么楷扬? 我笑而不...
    開封第一講書人閱讀 59,640評(píng)論 1 296
  • 正文 為了忘掉前任解幽,我火速辦了婚禮,結(jié)果婚禮上烘苹,老公的妹妹穿的比我還像新娘躲株。我一直安慰自己,他們只是感情好镣衡,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,640評(píng)論 6 397
  • 文/花漫 我一把揭開白布徘溢。 她就那樣靜靜地躺著,像睡著了一般捆探。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上站粟,一...
    開封第一講書人閱讀 52,262評(píng)論 1 308
  • 那天黍图,我揣著相機(jī)與錄音,去河邊找鬼奴烙。 笑死助被,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的切诀。 我是一名探鬼主播揩环,決...
    沈念sama閱讀 40,833評(píng)論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼幅虑!你這毒婦竟也來(lái)了丰滑?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,736評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤倒庵,失蹤者是張志新(化名)和其女友劉穎褒墨,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體擎宝,經(jīng)...
    沈念sama閱讀 46,280評(píng)論 1 319
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡郁妈,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,369評(píng)論 3 340
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了绍申。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片噩咪。...
    茶點(diǎn)故事閱讀 40,503評(píng)論 1 352
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖极阅,靈堂內(nèi)的尸體忽然破棺而出胃碾,到底是詐尸還是另有隱情,我是刑警寧澤涂屁,帶...
    沈念sama閱讀 36,185評(píng)論 5 350
  • 正文 年R本政府宣布书在,位于F島的核電站,受9級(jí)特大地震影響拆又,放射性物質(zhì)發(fā)生泄漏儒旬。R本人自食惡果不足惜栏账,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,870評(píng)論 3 333
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望栈源。 院中可真熱鬧挡爵,春花似錦、人聲如沸甚垦。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,340評(píng)論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)艰亮。三九已至闭翩,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間迄埃,已是汗流浹背疗韵。 一陣腳步聲響...
    開封第一講書人閱讀 33,460評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留侄非,地道東北人蕉汪。 一個(gè)月前我還...
    沈念sama閱讀 48,909評(píng)論 3 376
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像逞怨,于是被迫代替她去往敵國(guó)和親者疤。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,512評(píng)論 2 359

推薦閱讀更多精彩內(nèi)容