Skip to content

Instantly share code, notes, and snippets.

@robertmryan
Last active April 24, 2021 18:41
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save robertmryan/de2b8faefa0ab58486287595b407fbb2 to your computer and use it in GitHub Desktop.
Save robertmryan/de2b8faefa0ab58486287595b407fbb2 to your computer and use it in GitHub Desktop.
// CircleView.h
//
// Created by Robert Ryan on 4/24/21.
#import <UIKit/UIKit.h>
NS_ASSUME_NONNULL_BEGIN
IB_DESIGNABLE
@interface CircleView : UIView
@property (nonatomic) IBInspectable CGFloat startAngle;
@property (nonatomic) IBInspectable CGFloat endAngle;
@property (nonatomic) IBInspectable CGFloat percent;
@property (nonatomic) IBInspectable CGFloat lineWidth;
@property (nonatomic) IBInspectable UIColor *mainColor;
@property (nonatomic) IBInspectable UIColor *progressColor;
@end
NS_ASSUME_NONNULL_END
// and
//
// CircleView.m
//
// Created by Robert Ryan on 4/24/21.
#import "CircleView.h"
@implementation CircleView
- (instancetype)initWithCoder:(NSCoder *)coder {
self = [super initWithCoder:coder];
if (self) {
[self configure];
}
return self;
}
- (instancetype)initWithFrame:(CGRect)frame {
self = [super initWithFrame:frame];
if (self) {
[self configure];
}
return self;
}
- (void)configure {
_lineWidth = 1;
_percent = 0;
_mainColor = [UIColor lightGrayColor];
_progressColor = [UIColor darkGrayColor];
_startAngle = -M_PI_2;
_endAngle = M_PI_2 * 3;
}
- (void)drawRect:(CGRect)rect {
int radius = (self.bounds.size.width - self.lineWidth) / 2; // inset by line width
CGPoint center = CGPointMake(CGRectGetMidX(self.bounds), CGRectGetMidX(self.bounds)); // use `bounds` and `CGRectGetMidX`
CGFloat progressEndAngle = self.startAngle + (self.endAngle - self.startAngle) * self.percent; // by convention, percentages are b/w 0 and 1
UIBezierPath* bezierPathPassive = [UIBezierPath bezierPathWithArcCenter:center
radius:radius
startAngle:0
endAngle:M_PI * 2 // in iOS, use radians
clockwise:YES];
bezierPathPassive.lineWidth = self.lineWidth;
[self.mainColor setStroke];
[bezierPathPassive stroke];
UIBezierPath* bezierPathProgress = [UIBezierPath bezierPathWithArcCenter:center
radius:radius
startAngle:self.startAngle
endAngle:progressEndAngle
clockwise:YES];
bezierPathProgress.lineWidth = self.lineWidth;
[self.progressColor setStroke];
[bezierPathProgress stroke];
}
- (void)setStartAngle:(CGFloat)startAngle {
_startAngle = startAngle;
[self setNeedsDisplay];
}
- (void)setEndAngle:(CGFloat)endAngle {
_endAngle = endAngle;
[self setNeedsDisplay];
}
- (void)setPercent:(CGFloat)percent {
_percent = percent;
[self setNeedsDisplay];
}
- (void)setMainColor:(UIColor *)mainColor {
_mainColor = mainColor;
[self setNeedsDisplay];
}
- (void)setProgressColor:(UIColor *)progressColor {
_progressColor = progressColor;
[self setNeedsDisplay];
}
@end
@robertmryan
Copy link
Author

That yields (with progress set to 0.33):

Screen Shot 2021-04-24 at 11 33 50 AM

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment