說(shuō)一下相關(guān)的問(wèn)題:
有的時(shí)候我們需要設(shè)置按鈕的各個(gè)狀態(tài),一般比較常見(jiàn)的就是設(shè)置三種狀態(tài):UIControlStateNormal、UIControlStateSelected、UIControlStateHighlighted
設(shè)置UIControlStateNormal,設(shè)置按鈕的一般狀態(tài)。
設(shè)置UIControlStateSelected,設(shè)置按鈕的selected狀態(tài)(selected可不是選中狀態(tài))。
設(shè)置UIControlStateHighlighted,設(shè)置按鈕的選中狀態(tài),也就是按住的效果。
直接上問(wèn)題:
1、當(dāng)設(shè)置了UIControlStateNormal、UIControlStateSelected、這兩種狀態(tài)的時(shí)候,當(dāng)按鈕處于selected = YES的時(shí)候,當(dāng)前的按鈕的狀態(tài)是UIControlStateSelected,按住按鈕,會(huì)發(fā)現(xiàn)按鈕變成了UIControlStateNormal狀態(tài),松開(kāi)手就會(huì)發(fā)現(xiàn)按鈕又變成了UIControlStateSelected狀態(tài)。
UIButton *tempBtn = [UIButton buttonWithType:UIButtonTypeCustom];
tempBtn.frame = CGRectMake(100, 100, 200, 100);
[tempBtn addTarget:self action:@selector(clickBtn:) forControlEvents:UIControlEventTouchUpInside];
tempBtn.selected = YES;
// 設(shè)置按鈕在 Normal 下的狀態(tài)屬性
[tempBtn setTitle:@"Normal" forState:UIControlStateNormal];
[tempBtn setTitleColor:[UIColor blueColor] forState:UIControlStateSelected];
[tempBtn setBackgroundImage:[UIImage imageNamed:@"normalBack"] forState:UIControlStateNormal];
// 設(shè)置按鈕在 Selected 下的狀態(tài)屬性
[tempBtn setTitle:@"Selected" forState:UIControlStateSelected];
[tempBtn setTitleColor:[UIColor redColor] forState:UIControlStateSelected];
// 設(shè)置按鈕在 Highlighted 下的狀態(tài)屬性
[tempBtn setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted];
[self.view addSubview:tempBtn];
設(shè)置完成的狀態(tài),因?yàn)?strong>selected = YES,當(dāng)前的按鈕的狀態(tài)是UIControlStateSelected

按住按鈕,會(huì)發(fā)現(xiàn)按鈕變成了UIControlStateNormal狀態(tài),松開(kāi)手就會(huì)發(fā)現(xiàn)按鈕又變成了UIControlStateSelected狀態(tài)。

上面這種狀態(tài)顯然不是我們期望的
2、設(shè)置了UIControlStateNormal、UIControlStateSelected、UIControlStateHighlighted三種狀態(tài),當(dāng)selected = NO的時(shí)候,當(dāng)前按鈕處于UIControlStateNormal狀態(tài),當(dāng)按住按鈕的時(shí)候按鈕的狀態(tài)變成了UIControlStateHighlighted狀態(tài),這個(gè)是正常的。
不正常的顯示效果:當(dāng)selected = YES的時(shí)候,當(dāng)前按鈕處于UIControlStateSelected狀態(tài),當(dāng)按住按鈕的時(shí)候按鈕的狀態(tài)變成了UIControlStateNormal狀態(tài),這個(gè)是不正常的。
先看一下正常的效果:當(dāng)selected = NO的時(shí)候,當(dāng)前按鈕處于UIControlStateNormal狀態(tài),當(dāng)按住按鈕的時(shí)候按鈕的狀態(tài)變成了UIControlStateHighlighted狀態(tài),這個(gè)是正常的。
UIButton *tempBtn1 = [UIButton buttonWithType:UIButtonTypeCustom];
tempBtn1.frame = CGRectMake(100, 300, 200, 100);
[tempBtn1 addTarget:self action:@selector(clickBtn:) forControlEvents:UIControlEventTouchUpInside];
// 設(shè)置按鈕在 Normal 下的狀態(tài)屬性
[tempBtn1 setTitle:@"Normal" forState:UIControlStateNormal];
[tempBtn1 setTitleColor:[UIColor blueColor] forState:UIControlStateSelected];
[tempBtn1 setBackgroundImage:[UIImage imageNamed:@"normalBack"] forState:UIControlStateNormal];
// 設(shè)置按鈕在 Selected 下的狀態(tài)屬性
[tempBtn1 setTitle:@"Selected" forState:UIControlStateSelected];
[tempBtn1 setTitleColor:[UIColor redColor] forState:UIControlStateSelected];
// 設(shè)置按鈕在 Highlighted 下的狀態(tài)屬性
[tempBtn1 setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted];
[self.view addSubview:tempBtn1];
默認(rèn)創(chuàng)建完畢后的狀態(tài),按鈕的狀態(tài)是UIControlStateNormal
背景顏色較淺。

背景顏色變深,因?yàn)?code>UIControlStateHighlighted狀態(tài)下設(shè)置了一張背景顏色較深的背景圖片。
[tempBtn1 setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted];

看一下不正常的顯示:
代碼片段如下:

默認(rèn)創(chuàng)建完畢后的狀態(tài),當(dāng)selected = YES的時(shí)候,當(dāng)前按鈕處于UIControlStateSelected狀態(tài)

button被按住時(shí)的效果,當(dāng)按住按鈕的時(shí)候按鈕的狀態(tài)變成了UIControlStateNormal狀態(tài),這個(gè)是不正常的。

總結(jié)一下上面的效果,當(dāng)按鈕同時(shí)設(shè)置了UIControlStateNormal、UIControlStateSelected的時(shí)候,并且當(dāng)btn.selected = YES;的時(shí)候,那么這個(gè)時(shí)候按住button,button就會(huì)切換回到UIControlStateNormal狀態(tài)。
解決方案:
1、自定義一個(gè)button,并且重寫(xiě)一下- (void)setHighlighted:(BOOL)highlighted方法,里面啥也不寫(xiě)。
MyCustomBtn *customBtn = [MyCustomBtn buttonWithType:UIButtonTypeCustom];
customBtn.frame = CGRectMake(100, 320, 200, 100);
[customBtn addTarget:self action:@selector(clickBtn:) forControlEvents:UIControlEventTouchUpInside];
customBtn.selected = YES;
// 設(shè)置按鈕在 Normal 下的狀態(tài)屬性
[customBtn setTitle:@"Normal" forState:UIControlStateNormal];
[customBtn setTitleColor:[UIColor blueColor] forState:UIControlStateSelected];
[customBtn setBackgroundImage:[UIImage imageNamed:@"normalBack"] forState:UIControlStateNormal];
// 設(shè)置按鈕在 Selected 下的狀態(tài)屬性
[customBtn setTitle:@"Selected" forState:UIControlStateSelected];
[customBtn setTitleColor:[UIColor redColor] forState:UIControlStateSelected];
[self.view addSubview:customBtn];
#import "MyCustomBtn.h"
@implementation MyCustomBtn
/*
// Only override drawRect: if you perform custom drawing.
// An empty implementation adversely affects performance during animation.
- (void)drawRect:(CGRect)rect {
// Drawing code
}
*/
- (void)setHighlighted:(BOOL)highlighted
{
}
@end
這樣是重寫(xiě)了setHighlighted方法,通過(guò)在該方法打斷點(diǎn),走斷點(diǎn)可以發(fā)現(xiàn),在- (void)setHighlighted:(BOOL)highlighted這個(gè)方法不是在[customBtn setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted];調(diào)用的,而是在按住button將要進(jìn)入UIControlStateHighlighted狀態(tài)時(shí)候調(diào)用的。如果重寫(xiě)這個(gè)方法,并且在這個(gè)方法中啥也不寫(xiě)的話,那么設(shè)置了UIControlStateHighlighted也不起作用。不管btn.selected 是不是 YES。
總而言之言而總之,這樣重寫(xiě)這個(gè)方法的話
- (void)setHighlighted:(BOOL)highlighted
{
}
以后將不會(huì)再有UIControlStateHighlighted這個(gè)狀態(tài)。如果你不想要這個(gè)狀態(tài)的話,可以使用重寫(xiě)- (void)setHighlighted:(BOOL)highlighted這種方法。
那么當(dāng)btn.selected = YES的時(shí)候,按住按鈕也不會(huì)切換到UIControlStateNormal狀態(tài).
2、設(shè)置UIControlStateSelected狀態(tài)下的屬性和UIControlStateHighlighted一樣。
直接上代碼:
UIButton *tempBtn2 = [UIButton buttonWithType:UIButtonTypeCustom];
tempBtn2.frame = CGRectMake(100, 420, 200, 80);
[tempBtn2 addTarget:self action:@selector(clickBtn:) forControlEvents:UIControlEventTouchUpInside];
tempBtn2.selected = YES;
// 設(shè)置按鈕在 Normal 下的狀態(tài)屬性
[tempBtn2 setTitle:@"Normal" forState:UIControlStateNormal];
[tempBtn2 setTitleColor:[UIColor blueColor] forState:UIControlStateSelected];
[tempBtn2 setBackgroundImage:[UIImage imageNamed:@"normalBack"] forState:UIControlStateNormal];
// 設(shè)置按鈕在 Selected 下的狀態(tài)屬性
[tempBtn2 setTitle:@"Selected" forState:UIControlStateSelected];
[tempBtn2 setTitleColor:[UIColor redColor] forState:UIControlStateSelected];
// 設(shè)置按鈕在 Highlighted 下的狀態(tài)屬性
[tempBtn2 setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted];
[tempBtn2 setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted | UIControlStateSelected];
[tempBtn2 setTitleColor:[UIColor redColor] forState:UIControlStateHighlighted | UIControlStateSelected];
[tempBtn2 setTitle:@"Selected" forState:UIControlStateHighlighted | UIControlStateSelected];
[self.view addSubview:tempBtn2];
主要的代碼就是
[tempBtn2 setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted | UIControlStateSelected];
[tempBtn2 setTitleColor:[UIColor redColor] forState:UIControlStateHighlighted | UIControlStateSelected];
[tempBtn2 setTitle:@"Selected" forState:UIControlStateHighlighted | UIControlStateSelected];
完美搞定,這樣的話不管當(dāng)前按鈕的狀態(tài)是不是selected狀態(tài),那么選中的時(shí)候都可以展示深顏色的背景了。能正??吹?code>UIControlStateHighlighted狀態(tài)設(shè)置的東西了。
最后總結(jié)一下,其實(shí)我們平常寫(xiě)的設(shè)置按鈕的UIControlStateHighlighted代碼設(shè)置。我感覺(jué)應(yīng)該是這樣的。
[tempBtn2 setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted ];
等于
[tempBtn2 setBackgroundImage:[UIImage imageNamed:@"btnBackGround"] forState:UIControlStateHighlighted | UIControlStateNormal];
[tempBtn2 setTitleColor:[UIColor redColor] forState:UIControlStateHighlighted];
等于
[tempBtn2 setTitleColor:[UIColor redColor] forState:UIControlStateHighlighted | UIControlStateNormal];
設(shè)置其他UIControlStateHighlighted屬性的時(shí)候類似。
說(shuō)的更直白一點(diǎn)就是UIControlStateHighlighted狀態(tài)下對(duì)應(yīng)的屬性可以寫(xiě)兩套,一套是UIControlStateHighlighted | UIControlStateNormal,另一套是UIControlStateHighlighted | UIControlStateSelected狀態(tài)下對(duì)應(yīng)的屬性。
當(dāng)btn.selected = YES的時(shí)候,按住按鈕,按鈕調(diào)用- (void)setHighlighted:(BOOL)highlighted方法,展示的是UIControlStateHighlighted | UIControlStateSelected狀態(tài)下對(duì)應(yīng)的屬性。
當(dāng)btn.selected = NO的時(shí)候,按住按鈕,按鈕調(diào)用- (void)setHighlighted:(BOOL)highlighted方法,展示的是UIControlStateHighlighted | UIControlStateNormal或者UIControlStateHighlighted狀態(tài)下對(duì)應(yīng)的屬性。
當(dāng)btn.selected = YES的時(shí)候,按住按鈕,按鈕調(diào)用- (void)setHighlighted:(BOOL)highlighted方法,展示的是UIControlStateHighlighted | UIControlStateSelected狀態(tài)下對(duì)應(yīng)的屬性,如果沒(méi)有設(shè)置UIControlStateHighlighted | UIControlStateSelected狀態(tài)下對(duì)用的屬性,那么顯示的就是UIControlStateHighlighted+UIControlStateNormal下設(shè)置的屬性樣式。
最后獻(xiàn)上Demo地址:https://github.com/RunOfTheSnail/UIButtonDemo001
以上是我自己根據(jù)相關(guān)的運(yùn)行效果總結(jié)的,如果有哪位大神覺(jué)得有地方描述的不準(zhǔn)確,歡迎指正哈,在下感激不盡!??!