I'm trying to convert my UIView to this shape with UIBezierPath
, currently I'm only able to do the left bottom corner, seeking for help for adding other corners.
Code for left bottom only.
let mask = CAShapeLayer()
mask.frame = self.innerLayout.layer.bounds
let path = UIBezierPath()
let radius: CGFloat = 50
let rect = mask.bounds
path.move(to: rect.origin)
path.addLine(to: CGPoint(x: rect.maxX, y: rect.minY))
path.addLine(to: CGPoint(x: rect.maxX, y: rect.maxY))
path.addLine(to: CGPoint(x: rect.minX + radius, y: rect.maxY))
path.addArc(withCenter: CGPoint(x: rect.minX, y: rect.maxY), radius: radius, startAngle: 0, endAngle: CGFloat(M_PI_2 * 3), clockwise: false)
mask.path = path.cgPath
self.innerLayout.layer.mask = mask
I did couple of trials for adding other corners but my UIView
got funny shapes. I simply added this by copying and pasting (and changing origin), I believe we will use this part of the code 4 times to add 4 corners
path.move(to: CGPoint(x: rect.maxX, y: rect.maxY)
path.addLine(to: CGPoint(x: rect.maxX, y: rect.minY))
path.addLine(to: CGPoint(x: rect.maxX, y: rect.maxY))
path.addLine(to: CGPoint(x: rect.minX + radius, y: rect.maxY))
path.addArc(withCenter: CGPoint(x: rect.minX, y: rect.maxY), radius: radius, startAngle: 0, endAngle: CGFloat(M_PI_2 * 3), clockwise: false)
Here's a complete example to be run in Playground. Such geometric shapes are always tricky. It's very easy to get coordinates wrong or have an arc go into the wrong direction.
import UIKit
import PlaygroundSupport
class ConcaveConrnerViewController : UIViewController {
override func loadView() {
let view = UIView()
view.backgroundColor = .white
let frame = CGRect(x: 100, y: 200, width: 200, height: 200)
let subView = UIView(frame: frame)
subView.backgroundColor = .red
let mask = CAShapeLayer()
mask.frame = subView.layer.bounds
let path = UIBezierPath()
let radius: CGFloat = 50
let rect = mask.bounds
path.move(to: CGPoint(x: rect.minX + radius, y: rect.minY))
path.addLine(to: CGPoint(x: rect.maxX - radius, y: rect.minY))
path.addArc(withCenter: CGPoint(x: rect.maxX, y: rect.minY), radius: radius, startAngle: CGFloat(Double.pi / 2 * 2), endAngle: CGFloat(Double.pi / 2 * 3), clockwise: false)
path.addLine(to: CGPoint(x: rect.maxX, y: rect.maxY - radius))
path.addArc(withCenter: CGPoint(x: rect.maxX, y: rect.maxY), radius: radius, startAngle: CGFloat(Double.pi / 2 * 1), endAngle: CGFloat(Double.pi / 2 * 2), clockwise: false)
path.addLine(to: CGPoint(x: rect.minX + radius, y: rect.maxY))
path.addArc(withCenter: CGPoint(x: rect.minX, y: rect.maxY), radius: radius, startAngle: CGFloat(Double.pi / 2 * 0), endAngle: CGFloat(Double.pi / 2 * 1), clockwise: false)
path.addLine(to: CGPoint(x: rect.minX, y: rect.minY + radius))
path.addArc(withCenter: CGPoint(x: rect.minX, y: rect.minY), radius: radius, startAngle: CGFloat(Double.pi / 2 * 3), endAngle: CGFloat(Double.pi / 2 * 0), clockwise: false)
path.close()
mask.path = path.cgPath
subView.layer.mask = mask
view.addSubview(subView)
self.view = view
}
}
PlaygroundPage.current.liveView = ConcaveConrnerViewController()