//
// ZZTabBarButton.h
// ZZ_APP主流框架
//
// Created by ZZ_Macpro on 15/9/25.
// Copyright (c) 2015年 ZZ_Macpro. All rights reserved.
//
#import <UIKit/UIKit.h>
@interface ZZTabBarButton : UIButton
/**
* tabbar 上面的子控件只能是UITabBarItem
*/
@property (nonatomic, weak) UITabBarItem *item;
@end
//
// ZZTabBarButton.m
// ZZ_APP主流框架
//
// Created by ZZ_Macpro on 15/9/25.
// Copyright (c) 2015年 ZZ_Macpro. All rights reserved.
//
// 图标的比例
#define ZZTabBarButtonImageRatio 0.65
#import "ZZTabBarButton.h"
#import "ZZBadgeButton.h"
const double ZZTabBarImageRatio = 0.65;
#define ZZTabBarButtonTitleColor (iOS7 ? [UIColor blackColor] : [UIColor whiteColor])
#define ZZTabBarButtonTitleSelectedColor (iOS7 ? ZZColor(236, 103, 0) : ZZColor(253, 163, 25))
@interface ZZTabBarButton()
@property (weak, nonatomic) ZZBadgeButton *badgeButton;
@end
@implementation ZZTabBarButton
- (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
// 1.图片居中
self.imageView.contentMode = UIViewContentModeCenter;
// 2.文字居中
self.titleLabel.textAlignment = NSTextAlignmentCenter;
self.titleLabel.font = [UIFont systemFontOfSize:11];
[self setTitleColor:ZZTabBarButtonTitleSelectedColor forState:UIControlStateSelected];
[self setTitleColor:ZZTabBarButtonTitleColor forState:UIControlStateNormal];
// 3.设置选中时的背景图片
if (!iOS7) {
[self setBackgroundImage:[UIImage resizedImageWithName:@"tabbar_slider"] forState:UIControlStateSelected];
}
// 4.添加一个显示红色提醒数字的按钮
[self setupBadgeButton];
}
return self;
}
- (void)setupBadgeButton
{
ZZBadgeButton *badgeButton = [[ZZBadgeButton alloc] init];
badgeButton.autoresizingMask = UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleBottomMargin;
[self addSubview:badgeButton];
self.badgeButton = badgeButton;
}
/**
* 目的是去掉父类在高亮时所做的操作
*/
- (void)setHighlighted:(BOOL)highlighted {}
#pragma mark - 覆盖父类的2个方法
#pragma mark 设置按钮标题的frame
- (CGRect)titleRectForContentRect:(CGRect)contentRect {
CGFloat titleY = contentRect.size.height * ZZTabBarImageRatio;
CGFloat titleH = contentRect.size.height - titleY;
CGFloat titleW = contentRect.size.width;
return CGRectMake(0, titleY, titleW, titleH);
}
#pragma mark 设置按钮图片的frame
- (CGRect)imageRectForContentRect:(CGRect)contentRect {
CGFloat imageH = contentRect.size.height * ZZTabBarImageRatio;
CGFloat imageW = contentRect.size.width;
return CGRectMake(0, 0, imageW, imageH);
}
- (void)setItem:(UITabBarItem *)item
{
_item = item;
// 1.利用KVO监听item属性值的改变
[item addObserver:self forKeyPath:@"title" options:NSKeyValueObservingOptionNew context:nil];
[item addObserver:self forKeyPath:@"image" options:NSKeyValueObservingOptionNew context:nil];
[item addObserver:self forKeyPath:@"selectedImage" options:NSKeyValueObservingOptionNew context:nil];
[item addObserver:self forKeyPath:@"badgeValue" options:NSKeyValueObservingOptionNew context:nil];
// 2.属性赋值
[self observeValueForKeyPath:nil ofObject:nil change:nil context:nil];
}
/**
* KVO监听必须在监听器释放的时候,移除监听操作
* 通知也得在释放的时候移除监听
*/
- (void)dealloc
{
[self.item removeObserver:self forKeyPath:@"title"];
[self.item removeObserver:self forKeyPath:@"image"];
[self.item removeObserver:self forKeyPath:@"selectedImage"];
[self.item removeObserver:self forKeyPath:@"badgeValue"];
}
/**
* 监听item的属性值改变
*
* @param keyPath 哪个属性改变了
* @param object 哪个对象的属性改变了
*/
- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
{
[self setTitle:self.item.title forState:UIControlStateNormal];
[self setImage:self.item.image forState:UIControlStateNormal];
[self setImage:self.item.selectedImage forState:UIControlStateSelected];
// 设置提醒数字
self.badgeButton.value = self.item.badgeValue;
CGFloat badgeButtonX = self.frame.size.width - self.badgeButton.frame.size.width - 5;
CGFloat badgeButtonY = 2;
self.badgeButton.frame = CGRectMake(badgeButtonX, badgeButtonY, 0, 0);
}
@end
//
// ZZTabBar.h
// ZZ_APP主流框架
//
// Created by ZZ_Macpro on 15/9/25.
// Copyright (c) 2015年 ZZ_Macpro. All rights reserved.
//
#import <UIKit/UIKit.h>
@class ZZTabBar;
@protocol ZZTabBarDelegate <NSObject>
@optional
/**
* ZZTabBar上面的按钮被选中了
*
* @param tabBar 被点击的ZZTabBar
* @param from 原来按钮的位置
* @param to 新被选中按钮的位置
*/
- (void)tabBar:(ZZTabBar *)tabBar didSelectedButtonFrom:(NSInteger)from to:(NSInteger)to;
/**
* ZZTabBar中间的加号按钮被点击了
*/
- (void)tabBarDidClickedPlusButton:(ZZTabBar *)tabBar;
@end
@interface ZZTabBar : UIView
/**
* 添加按钮
*
* @param item 模型数据
*/
- (void)addTabBarButtonWithItem:(UITabBarItem *)item;
/**
* 代理 命名以及在理解上需要加强
*/
@property (nonatomic, weak) id<ZZTabBarDelegate> delegate;
@end
//
// ZZTabBar.m
// ZZ_APP主流框架
//
// Created by ZZ_Macpro on 15/9/25.
// Copyright (c) 2015年 ZZ_Macpro. All rights reserved.
//
#import "ZZTabBar.h"
#import "ZZTabBarButton.h"
@interface ZZTabBar()
/**
* 存放tabBar上面的按钮
*/
@property (nonatomic, strong) NSMutableArray *tabBarButtons;
/**
* tabBar上被选中的按钮
*/
@property (nonatomic, weak) ZZTabBarButton *selectedButton;
/**
* 中间增加的加号按钮
*/
@property (nonatomic, weak) UIButton *plusButton;
@end
@implementation ZZTabBar
/**
* tabBarButtons懒加载 只初始化一次 不用管他何时创建
*/
- (NSMutableArray *)tabBarButtons
{
if (_tabBarButtons == nil) {
_tabBarButtons = [NSMutableArray array];
}
return _tabBarButtons;
}
/**
* 初始化 在初始化中添加加号按钮
*/
- (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
if (!iOS7) {
self.backgroundColor = [UIColor colorWithPatternImage:[UIImage imageWithName:@"tabbar_background"]];
}
[self addPlusBtn];
}
return self;
}
/**
* 添加+号按钮
*/
- (void)addPlusBtn
{
// 1.创建按钮
UIButton *plusButton = [UIButton buttonWithType:UIButtonTypeCustom];
// 2.设置背景图片
UIImage *bg = [UIImage imageWithName:@"tabbar_compose_button"];
[plusButton setBackgroundImage:bg forState:UIControlStateNormal];
[plusButton setBackgroundImage:[UIImage imageWithName:@"tabbar_compose_button_highlighted"] forState:UIControlStateHighlighted];
// 3.设置顶部的加号按钮
[plusButton setImage:[UIImage imageWithName:@"tabbar_compose_icon_add"] forState:UIControlStateNormal];
[plusButton setImage:[UIImage imageWithName:@"tabbar_compose_icon_add_highlighted"] forState:UIControlStateHighlighted];
// 4.监听按钮点击
[plusButton addTarget:self action:@selector(plusClick) forControlEvents:UIControlEventTouchUpInside];
[self addSubview:plusButton];
/**
* 对其进行引用后续进行操作
*/
self.plusButton = plusButton;
}
/**
* 监听加号点击
*/
- (void)plusClick
{
// 通知代理
if ([self.delegate respondsToSelector:@selector(tabBarDidClickedPlusButton:)]) {
[self.delegate tabBarDidClickedPlusButton:self];
}
}
- (void)addTabBarButtonWithItem:(UITabBarItem *)item
{
// 1.创建按钮
ZZTabBarButton *button = [[ZZTabBarButton alloc] init];
// 2.传递模型数据
button.item = item;
// 3.添加按钮
[button addTarget:self action:@selector(buttonClick:) forControlEvents:UIControlEventTouchDown];
[self addSubview:button];
[self.tabBarButtons addObject:button];
// 4.默认选中
if (self.tabBarButtons.count == 1) {
[self buttonClick:button];
}
}
- (void)buttonClick:(ZZTabBarButton *)button
{
// 0.通知代理
if ([self.delegate respondsToSelector:@selector(tabBar:didSelectedButtonFrom:to:)]) {
[self.delegate tabBar:self didSelectedButtonFrom:self.selectedButton.tag to:button.tag];
}
// 1.控制器选中按钮
self.selectedButton.selected = NO;
button.selected = YES;
self.selectedButton = button;
}
/**
* 布局子控件
*/
- (void)layoutSubviews
{
[super layoutSubviews];
// 1.4个按钮 固定的尺寸所以不需要写在循环里面节约性能
CGFloat buttonW = self.frame.size.width / 5;
CGFloat buttonH = self.frame.size.height;
for (int index = 0; index < self.tabBarButtons.count; index++) {
ZZTabBarButton *button = self.tabBarButtons[index];
button.tag = index;
CGFloat buttonX = index * buttonW;
if (index >= 2) {
buttonX += buttonW;
}
// 循环一次 值变化一次 所以这里才是如何用一个变量 表示出所有的控件
button.frame = CGRectMake(buttonX, 0, buttonW, buttonH);
}
// 2.中间的+按钮
self.plusButton.bounds = (CGRect){CGPointZero, self.plusButton.currentBackgroundImage.size};
self.plusButton.center = CGPointMake(self.frame.size.width * 0.5, self.frame.size.height * 0.5);
}
@end