Если lineWidth
одинаково для всех штрихов, настройка innerCornerRadius
на (outerCornerRadius - lineWidth)
появляется для получения желаемого эффекта; это особый случай. Если вы не верите в следующее, я призываю вас проверить это. Реальные отношения, регулирующие это, выглядят так:
l i = внутренняя ширина линии
l o = ширина внешней линии
r i = внутренний радиус угла
r o = внешний радиус угла
l i / 2 + r i = r o - l o / 2
Таким образом:
r i = r o - (l i / 2 + l o / 2)
Если l i = l o = l, то: r i = r o - l
/*
The following should be inserted into a UIView subclass that has a size of ~280, ~200.
lineWidthInner/2 + radiusInner = radiusOuter - lineWidthOuter/2
radiusInner = radiusOuter - (lineWidthOuter + lineWidthInner)/2
That is to say that the inner corner radius is equal to the outer corner radius
minus the average of the lineWidth's.
innerInsetMargin = outerInsetMargin + (lineWidthOuter + lineWidthInner)/2
The amount a line must be inset (insetMargin) is the previous line's insetMargin + the
average of the previous and current lineWidth's. In the case in which the
outermost line's outer edge touches the bound of rect, the insetMargin is equal
to the sum of all previous lineWidth's plus half of the current lineWidth.
Shutting off anti-aliasing is required to prevent alpha-blending of the non-rectilinear
parts of the line with the background. I am not sure how to gracefully sidestep this.
Insights into this would be appreciated.
*/
-(void)drawRect:(CGRect)rect {
CGContextRef context = UIGraphicsGetCurrentContext();
CGContextSetFillColorWithColor(context, UIColor.blackColor.CGColor);
CGContextFillRect(context, rect);
CGContextSetShouldAntialias(context,NO);
NSArray *colors = [NSArray arrayWithObjects:
(id)UIColor.greenColor.CGColor,
(id)UIColor.lightGrayColor.CGColor,
(id)UIColor.yellowColor.CGColor,
(id)UIColor.blueColor.CGColor,
(id)UIColor.redColor.CGColor, nil];
//Change lineWidth, lineWidthIncrement, or currentCornerRadius as you see fit
CGFloat lineWidthIncrement = 1.0;
CGFloat lineWidth = 10.0;
CGFloat currentCornerRadius = 100.0;
CGFloat insetMargin = lineWidth/2;
do {
CGContextSaveGState(context);
CGContextSetStrokeColorWithColor(context, (CGColorRef)[colors objectAtIndex:(lcv % colors.count)]);
CGContextSetLineWidth(context, lineWidth);
CGContextAddPath(context, [UIBezierPath bezierPathWithRoundedRect:CGRectInset(rect, insetMargin, insetMargin) cornerRadius:currentCornerRadius].CGPath);
CGContextStrokePath(context);
CGContextRestoreGState(context);
lineWidth += lineWidthIncrement;
currentCornerRadius -= 0.5 * (lineWidth + (lineWidth - lineWidthIncrement));//-0.5*(lwi+lwo)
insetMargin += 0.5 * (lineWidth + (lineWidth - lineWidthIncrement));
} while(currentCornerRadius>0);
}