iOS開發之實現TabBar中間凸起“+”按鈕(自定義TabBar)


參考:http://www.jianshu.com/p/46f61bc7a938,https://github.com/Mringkang/KBCustomCenterTabbar

效果:

PS:這里需要用到UIView一個分類的一些屬性,參考http://www.cnblogs.com/guitarandcode/p/5758995.html   ,圖標素材等自行上網找或者自己設計,這里就不提供了。最后在StoryBoard中選擇TabBarController對應下面自定義的TabBarController即可

 

自定義TabBar

 MyTabBar.h

 1 #import <UIKit/UIKit.h>
 2 
 3 @class MyTabBar;
 4 
 5 //MyTabBar的代理必須實現addButtonClick,以響應中間“+”按鈕的點擊事件
 6 @protocol MyTabBarDelegate <NSObject>
 7 
 8 -(void)addButtonClick:(MyTabBar *)tabBar;
 9 
10 @end
11 
12 @interface MyTabBar : UITabBar
13 
14 //指向MyTabBar的代理
15 @property (nonatomic,weak) id<MyTabBarDelegate> myTabBarDelegate;
16 
17 @end

 

MyTabBar.m

  1 #import "MyTabBar.h"
  2 #import "UIView+Category.h"
  3 
  4 #define AddButtonMargin 10
  5 
  6 @interface MyTabBar()
  7 
  8 //指向中間“+”按鈕
  9 @property (nonatomic,weak) UIButton *addButton;
 10 //指向“添加”標簽
 11 @property (nonatomic,weak) UILabel *addLabel;
 12 
 13 @end
 14 
 15 @implementation MyTabBar
 16 
 17 /*
 18 // Only override drawRect: if you perform custom drawing.
 19 // An empty implementation adversely affects performance during animation.
 20 - (void)drawRect:(CGRect)rect {
 21     // Drawing code
 22 }
 23 */
 24 
 25 -(instancetype)initWithFrame:(CGRect)frame
 26 {
 27     if(self = [super initWithFrame:frame])
 28     {
 29         //創建中間“+”按鈕
 30         UIButton *addBtn = [[UIButton alloc] init];
 31         //設置默認背景圖片
 32         [addBtn setBackgroundImage:[UIImage imageNamed:@"AddButtonIcon"] forState:UIControlStateNormal];
 33         //設置按下時背景圖片
 34         [addBtn setBackgroundImage:[UIImage imageNamed:@"AddButtonIcon-Active"] forState:UIControlStateHighlighted];
 35         //添加響應事件
 36         [addBtn addTarget:self action:@selector(addBtnDidClick) forControlEvents:UIControlEventTouchUpInside];
 37         //將按鈕添加到TabBar
 38         [self addSubview:addBtn];
 39         
 40         self.addButton = addBtn;
 41     }
 42     return self;
 43 }
 44 
 45 //響應中間“+”按鈕點擊事件
 46 -(void)addBtnDidClick
 47 {
 48     if([self.myTabBarDelegate respondsToSelector:@selector(addButtonClick:)])
 49     {
 50         [self.myTabBarDelegate addButtonClick:self];
 51     }
 52 }
 53 
 54 -(void)layoutSubviews
 55 {
 56     [super layoutSubviews];
 57     
 58     //去掉TabBar上部的橫線
 59     for (UIView *view in self.subviews)
 60     {
 61         if ([view isKindOfClass:[UIImageView class]] && view.bounds.size.height <= 1)   //橫線的高度為0.5
 62         {
 63             UIImageView *line = (UIImageView *)view;
 64             line.hidden = YES;
 65         }
 66     }
 67     
 68     //設置“+”按鈕的位置
 69     self.addButton.centerX = self.centerX;
 70     self.addButton.centerY = self.height * 0.5 - 1.5 * AddButtonMargin;
 71     //設置“+”按鈕的大小為圖片的大小
 72     self.addButton.size = CGSizeMake(self.addButton.currentBackgroundImage.size.width, self.addButton.currentBackgroundImage.size.height);
 73     
 74     //創建並設置“+”按鈕下方的文本為“添加”
 75     UILabel *addLbl = [[UILabel alloc] init];
 76     addLbl.text = @"添加";
 77     addLbl.font = [UIFont systemFontOfSize:10];
 78     addLbl.textColor = [UIColor grayColor];
 79     [addLbl sizeToFit];
 80 
 81     //設置“添加”label的位置
 82     addLbl.centerX = self.addButton.centerX;
 83     addLbl.centerY = CGRectGetMaxY(self.addButton.frame) + 0.5 * AddButtonMargin + 0.5;
 84     
 85     [self addSubview:addLbl];
 86     
 87     self.addLabel = addLbl;
 88     
 89     int btnIndex = 0;
 90     //系統自帶的按鈕類型是UITabBarButton,找出這些類型的按鈕,然后重新排布位置,空出中間的位置
 91     Class class = NSClassFromString(@"UITabBarButton");
 92     for (UIView *btn in self.subviews) {//遍歷TabBar的子控件
 93         if ([btn isKindOfClass:class]) {//如果是系統的UITabBarButton,那么就調整子控件位置,空出中間位置
 94             //每一個按鈕的寬度等於TabBar的三分之一
 95             btn.width = self.width / 3;
 96             
 97             btn.x = btn.width * btnIndex;
 98             
 99             btnIndex++;
100             //如果索引是1(即“+”按鈕),直接讓索引加一
101             if (btnIndex == 1) {
102                 btnIndex++;
103             }
104             
105         }
106     }
107     //將“+”按鈕放到視圖層次最前面
108     [self bringSubviewToFront:self.addButton];
109 }
110 
111 //重寫hitTest方法,去監聽"+"按鈕和“添加”標簽的點擊,目的是為了讓凸出的部分點擊也有反應
112 - (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event {
113     
114     //這一個判斷是關鍵,不判斷的話push到其他頁面,點擊“+”按鈕的位置也是會有反應的,這樣就不好了
115     //self.isHidden == NO 說明當前頁面是有TabBar的,那么肯定是在根控制器頁面
116     //在根控制器頁面,那么我們就需要判斷手指點擊的位置是否在“+”按鈕或“添加”標簽上
117     //是的話讓“+”按鈕自己處理點擊事件,不是的話讓系統去處理點擊事件就可以了
118     if (self.isHidden == NO)
119     {
120         
121         //將當前TabBar的觸摸點轉換坐標系,轉換到“+”按鈕的身上,生成一個新的點
122         CGPoint newA = [self convertPoint:point toView:self.addButton];
123         //將當前TabBar的觸摸點轉換坐標系,轉換到“添加”標簽的身上,生成一個新的點
124         CGPoint newL = [self convertPoint:point toView:self.addLabel];
125         
126         //判斷如果這個新的點是在“+”按鈕身上,那么處理點擊事件最合適的view就是“+”按鈕
127         if ( [self.addButton pointInside:newA withEvent:event])
128         {
129             return self.addButton;
130         }
131         //判斷如果這個新的點是在“添加”標簽身上,那么也讓“+”按鈕處理事件
132         else if([self.addLabel pointInside:newL withEvent:event])
133         {
134             return self.addButton;
135         }
136         else
137         {//如果點不在“+”按鈕身上,直接讓系統處理就可以了
138             
139             return [super hitTest:point withEvent:event];
140         }
141     }
142     else
143     {
144         //TabBar隱藏了,那么說明已經push到其他的頁面了,這個時候還是讓系統去判斷最合適的view處理就好了
145         return [super hitTest:point withEvent:event];
146     }
147 }
148 
149 @end

 

自定義TabBarController

MyTabBarController.h

1 #import <UIKit/UIKit.h>
2 
3 @interface MyTabBarController : UITabBarController
4 
5 @end

 

 

MyTabBarController.m

 1 #import "MyTabBarController.h"
 2 #import "MyTabBar.h"
 3 
 4 
 5 @interface MyTabBarController () <MyTabBarDelegate> //實現自定義TabBar協議
 6 
 7 @end
 8 
 9 @implementation MyTabBarController
10 
11 - (void)viewDidLoad {
12     [super viewDidLoad];
13     // Do any additional setup after loading the view.
14     
15     //設置TabBar上第一個Item(明細)選中時的圖片
16     UIImage *listActive = [UIImage imageNamed:@"ListIcon - Active(blue)"];
17     UITabBarItem *listItem = self.tabBar.items[0];
18     //始終按照原圖片渲染
19     listItem.selectedImage = [listActive imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
20     
21     
22     //設置TabBar上第二個Item(報表)選中時的圖片
23     UIImage *chartActive = [UIImage imageNamed:@"ChartIcon - Active(blue)"];
24     UITabBarItem *chartItem = self.tabBar.items[1];
25     //始終按照原圖片渲染
26     chartItem.selectedImage = [chartActive imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
27     
28     //創建自定義TabBar
29     MyTabBar *myTabBar = [[MyTabBar alloc] init];
30     myTabBar.myTabBarDelegate = self;
31     
32     //利用KVC替換默認的TabBar
33     [self setValue:myTabBar forKey:@"tabBar"];
34 }
35 
36 
37 -(void)viewDidLayoutSubviews
38 {
39     [super viewDidLayoutSubviews];
40     //設置TabBar的TintColor
41     self.tabBar.tintColor = [UIColor colorWithRed:89/255.0 green:217/255.0 blue:247/255.0 alpha:1.0];
42 }
43 
44 - (void)didReceiveMemoryWarning {
45     [super didReceiveMemoryWarning];
46     // Dispose of any resources that can be recreated.
47 }
48 
49 
50 
51 #pragma mark - MyTabBarDelegate
52 -(void)addButtonClick:(MyTabBar *)tabBar
53 {
54     //測試中間“+”按鈕是否可以點擊並處理事件
55     UIAlertController *controller = [UIAlertController alertControllerWithTitle:@"test" message:@"Test" preferredStyle:UIAlertControllerStyleAlert];
56     UIAlertAction *action = [UIAlertAction actionWithTitle:@"test" style:UIAlertActionStyleDefault handler:nil];
57     [controller addAction:action];
58     [self presentViewController:controller animated:YES completion:nil];
59     
60 }
61 
62 @end

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM