Reputation: 18729
My goal is to create a custom UIButton
subclass, that creates a round (or round rect) button with some additional features.
After some searching, I found that simply setting the cornerRadius
of the button layer is the easiest way to make the button round:
@implementation MyRoundButton
-(id)initWithFrame:(CGRect)frame{
if (self = [super initWithFrame:frame])
[self setupView];
return self;
}
-(id)initWithCoder:(NSCoder *)aDecoder{
if(self = [super initWithCoder:aDecoder])
[self setupView];
return self;
}
-(void)setupView {
self.layer.cornerRadius = MIN(self.frame.size.height, self.frame.size.width) / 2.0;
}
This works fine to, as long as I do not override drawRect:
- (void)drawRect:(CGRect)rect {
[super drawRect:rect];
}
Of course I would like to add some custom drawing code to drawRect:
but even if only [super drawRect:rect]
the button is not round anymore: It drawn as rectangle within its bounds.
How is this possible? How can overriding a method with a simple super call change the behavior at all?
How can I avoid this problem? I already tried to let the layer unchanged and to simply draw the background manually in drawRect:
. However the button draws its background rect anyway and my custom drawing is on top of it.
So, how to solve this?
Upvotes: 1
Views: 746
Reputation: 15597
The layer in your example conceptually contains a background with a corner radius, but the empty override of drawRect:
causes that to be ignored. That's because, ordinarily, an instance of UIView
depends on its built-in layer (an instance of CALayer
) to render its content, so drawRect:
isn't called. However, the layer is capable of delegating drawing behavior to its view, and will do so if you implement drawRect:
.
If you're simply subclassing UIView
, this shouldn't present any problem. However, subclassing a framework component such as UIButton
is a bit dicier. One potential issue is the call to -[super drawRect:]
; it's hard to know precisely what mischief that might cause, but that may be the source of the problem. By default, a UIButton
doesn't need to do any custom drawing; it contains a nested instance of a private class, UIButtonLabel
, that draws the button's title.
Instead of trying to override the drawing behavior of a class whose inner details are private, consider using one or more static images and simply setting the button's background image property for one or more states.
Upvotes: 2
Reputation: 77490
See if this changes anything...
-(void)setupView {
self.layer.cornerRadius = MIN(self.frame.size.height, self.frame.size.width) / 2.0;
self.clipsToBounds = YES;
}
Upvotes: 0