blob: f13c8b083b4fa75c1b5728a73077da776e1dc64f [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
#import "UIBezierPath+Weex.h"
@implementation UIBezierPath (Weex)
// Approximation of control point positions on a bezier to simulate a quarter of a circle.
// This is 1-kappa, where kappa = 4 * (sqrt(2) - 1) / 3
static const float kCircleControlPoint = 0.447715;
+ (instancetype)wx_bezierPathWithRoundedRect:(CGRect)rect
topLeft:(CGFloat)topLeftRadius
topRight:(CGFloat)topRightRadius
bottomLeft:(CGFloat)bottomLeftRadius
bottomRight:(CGFloat)bottomRightRadius
{
UIBezierPath *path = [UIBezierPath bezierPath];
[path moveToPoint:CGPointMake(rect.origin.x + topLeftRadius, rect.origin.y)];
// +------------------+
// \\ top //
// \\+----------+//
[path addLineToPoint:CGPointMake(CGRectGetMaxX(rect) - topRightRadius, rect.origin.y)];
if (topRightRadius > 0) {
[path addCurveToPoint:CGPointMake(CGRectGetMaxX(rect), rect.origin.y + topRightRadius)
controlPoint1:CGPointMake(CGRectGetMaxX(rect) - topRightRadius * kCircleControlPoint, rect.origin.y)
controlPoint2:CGPointMake(CGRectGetMaxX(rect), rect.origin.y + topRightRadius * kCircleControlPoint)];
}
// +------------------+
// \\ top //|
// \\+----------+// |
// | |
// |rig|
// |ht |
// | |
// \\ |
// \\|
[path addLineToPoint:CGPointMake(CGRectGetMaxX(rect), CGRectGetMaxY(rect) - bottomRightRadius)];
if (bottomRightRadius > 0) {
[path addCurveToPoint:CGPointMake(CGRectGetMaxX(rect) - bottomRightRadius, CGRectGetMaxY(rect))
controlPoint1:CGPointMake(CGRectGetMaxX(rect), CGRectGetMaxY(rect) - bottomRightRadius * kCircleControlPoint)
controlPoint2:CGPointMake(CGRectGetMaxX(rect) - bottomRightRadius * kCircleControlPoint, CGRectGetMaxY(rect))];
}
// +------------------+
// \\ top //|
// \\+----------+// |
// | |
// |rig|
// |ht |
// | |
// //+----------+\\ |
// // bottom \\|
// +------------------+
[path addLineToPoint:CGPointMake(rect.origin.x + bottomLeftRadius, CGRectGetMaxY(rect))];
if (bottomLeftRadius > 0) {
[path addCurveToPoint:CGPointMake(rect.origin.x, CGRectGetMaxY(rect) - bottomLeftRadius)
controlPoint1:CGPointMake(rect.origin.x + bottomLeftRadius * kCircleControlPoint, CGRectGetMaxY(rect))
controlPoint2:CGPointMake(rect.origin.x, CGRectGetMaxY(rect) - bottomLeftRadius * kCircleControlPoint)];
}
// +------------------+
// |\\ top //|
// | \\+----------+// |
// | | | |
// |lef| |rig|
// |t | |ht |
// | | | |
// | //+----------+\\ |
// |// bottom \\|
// +------------------+
[path addLineToPoint:CGPointMake(rect.origin.x, rect.origin.y + topLeftRadius)];
if (topLeftRadius > 0) {
[path addCurveToPoint:CGPointMake(rect.origin.x + topLeftRadius, rect.origin.y)
controlPoint1:CGPointMake(rect.origin.x, rect.origin.y + topLeftRadius * kCircleControlPoint)
controlPoint2:CGPointMake(rect.origin.x + topLeftRadius * kCircleControlPoint, rect.origin.y)];
}
return path;
}
@end