Change UIButton border color on highlight
Solution 1
You were on the right track. Check the code below, it elaborates on this, but what you'll want to do is link selectors to different control events on your button. One for touchDown
to change the shadow to red, and another for touchUpInside
to change the shadow back when you lift your finger.
Additionally, I see you've asked several questions on Stack Overflow and have yet to mark any as the correct answer. To continue to receive help on this website, you will need to start marking correct answers to your questions.
[myButton addTarget:self action:@selector(highlightBorder) forControlEvents:UIControlEventTouchDown];
[myButton addTarget:self action:@selector(unhighlightBorder) forControlEvents:UIControlEventTouchUpInside];
- (void)highlightBorder
{
myButton.layer.borderColor = [[UIColor redColor]CGColor];
}
- (void)unhighlightBorder
{
myButton.layer.borderColor = [[UIColor blueColor]CGColor];
//additional code for an action when the button is released can go here.
}
NOTE: Other options for UIControlEvents
include:
enum {
UIControlEventTouchDown = 1 << 0,
UIControlEventTouchDownRepeat = 1 << 1,
UIControlEventTouchDragInside = 1 << 2,
UIControlEventTouchDragOutside = 1 << 3,
UIControlEventTouchDragEnter = 1 << 4,
UIControlEventTouchDragExit = 1 << 5,
UIControlEventTouchUpInside = 1 << 6,
UIControlEventTouchUpOutside = 1 << 7,
UIControlEventTouchCancel = 1 << 8,
UIControlEventValueChanged = 1 << 12,
UIControlEventEditingDidBegin = 1 << 16,
UIControlEventEditingChanged = 1 << 17,
UIControlEventEditingDidEnd = 1 << 18,
UIControlEventEditingDidEndOnExit = 1 << 19,
UIControlEventAllTouchEvents = 0x00000FFF,
UIControlEventAllEditingEvents = 0x000F0000,
UIControlEventApplicationReserved = 0x0F000000,
UIControlEventSystemReserved = 0xF0000000,
UIControlEventAllEvents = 0xFFFFFFFF
};
Solution 2
The SWIFT 2.x answer to your problem:
➜ Just override the highlighted property with "didSet" observer.
override var highlighted: Bool {
didSet {
switch highlighted {
case true:
layer.borderColor = UIColor.lightGrayColor().CGColor
case false:
layer.borderColor = UIColor.blackColor().CGColor
}
}
}
Swift 3:
override var isHighlighted: Bool {
didSet {
switch isHighlighted {
case true:
layer.borderColor = UIColor.lightGray.cgColor
case false:
layer.borderColor = UIColor.black.cgColor
}
}
}
Solution 3
You can override setHighlighted
and setSelected
methods in UIButton subclass. From there you just tweak border color like following:
- (void)setHighlighted:(BOOL)highlighted {
[super setHighlighted:highlighted];
[self tweakState:highlighted];
}
- (void)setSelected:(BOOL)selected {
[super setSelected:selected];
[self tweakState:selected];
}
- (void)tweakState:(BOOL)state {
if (state) {
self.layer.borderColor = [_highlightedBorderColor CGColor];
}
else {
self.layer.borderColor = [_defaultBorderColor CGColor];
}
}
Solution 4
Swift 4 :
override var isHighlighted: Bool {
didSet {
layer.borderColor = isHighlighted ? UIColor.lightGray.cgColor : UIColor.black.cgColor
}
}
Solution 5
Self contained solution:
static UIColor *BorderColor()
{
return [UIColor grayColor];
}
static UIColor *HighlightedBorderColor()
{
return [UIColor lightGrayColor];
}
@interface BorderedButton : UIButton
@end
@implementation BorderedButton
- (instancetype)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
self.layer.borderColor = BorderColor().CGColor;
self.layer.cornerRadius = 4.0;
self.layer.borderWidth = 1.0;
}
return self;
}
- (void)setHighlighted:(BOOL)highlighted
{
[super setHighlighted:highlighted];
self.layer.borderColor = (highlighted) ? HighlightedBorderColor().CGColor : BorderColor().CGColor;
}
@end
Thanks to @josip-b!
Related videos on Youtube
JohnWickham
Updated on October 27, 2020Comments
-
JohnWickham over 3 years
I've got a simple custom UIButton, to which I added:
button.layer.bordercolor = [[UIColor blueColor]CGColor];
However, I want to change the .bordercolor when the button is highlighted. I tried adding an action to the button's touchDown action that changes the .bordercolor to red, but when the user lifts their finger, it stays red rather than returning to blue. Any ideas?
-
JohnWickham almost 12 yearsThanks, this works very well if the button receives the touch up inside action, however what if the user were to cancel the touch by dragging their finger off the button? Any idea how I could handle that? Thanks again!
-
Mick MacCallum almost 12 years@JohnWickham sure, there's another touch event called touchDragOutside that would probably do the trick.
-
cohen72 over 10 yearsto handle dragging outside, I find that this works: [button addTarget:self action:@selector(unhighlightBorder) forControlEvents:UIControlEventTouchCancel];
-
Mikhail over 8 yearsTo handle dragging outside, use UIControlEventTouchDragExit
-
Tib almost 8 yearslightweight and "swift styled" solution - works great, thanks!
-
0xWood over 6 yearsJust bare in mind you'll need to handle redrawing on bounds changes
-
Anton Ogarkov over 5 years
if ... else
solution would fit here better. Usingswitch ... case
looks to be too complicated :) -
Ing. Ron over 4 yearsSee here for SWFIT button observer syntax: stackoverflow.com/questions/40272274/…
-
Mads Buus over 4 yearsYeah, don't use case trye/false. Ternary operator is the way to go in these cases (see fethicas answer)