每个拐角的不同拐角半径Swift 3-iOS
我想在Swift-3中为视图设置不同的角半径,我可以将每个角的半径设置为相同的值,就像下面的帖子中提到的一样 有没有办法按以下格式设置角半径? 左上角半径:18 右上角半径:18 右下角半径:3每个拐角的不同拐角半径Swift 3-iOS,ios,swift3,cornerradius,Ios,Swift3,Cornerradius,我想在Swift-3中为视图设置不同的角半径,我可以将每个角的半径设置为相同的值,就像下面的帖子中提到的一样 有没有办法按以下格式设置角半径? 左上角半径:18 右上角半径:18 右下角半径:3 左下角半径:18您可以将默认的图层。拐角半径设置为最小值,然后将图层遮罩的边框设置为较大值 let demoView = UIView(frame: CGRect(x: 100, y: 200, width: 100, height: 100)) demoView.backgroundColor = U
左下角半径:18您可以将默认的
图层。拐角半径
设置为最小值,然后将图层遮罩的边框设置为较大值
let demoView = UIView(frame: CGRect(x: 100, y: 200, width: 100, height: 100))
demoView.backgroundColor = UIColor.red
demoView.layer.cornerRadius = 3.0
let maskPath = UIBezierPath(roundedRect: demoView.bounds,
byRoundingCorners: [.topLeft, .topRight, .bottomLeft],
cornerRadii: CGSize(width: 18.0, height: 0.0))
let maskLayer = CAShapeLayer()
maskLayer.path = maskPath.cgPath
demoView.layer.mask = maskLayer
view.addSubview(demoView)
是否要为每个角点添加唯一的角点值 是否要在此之后添加边框 我有一个解决方案如下: 首先,添加一个我制作的
UIBezierPath
扩展名:
扩展UIBezierPath{
便利初始化(shouldldroundrect-rect:CGRect,topLeftRadius:CGSize=.zero,topLeftRadius:CGSize=.zero,bottomLeftRadius:CGSize=.zero,bottomrightdradius:CGSize=.zero){
self.init()
let path=CGMutablePath()
设topLeft=rect.origin
设topRight=CGPoint(x:rect.maxX,y:rect.minY)
设bottomRight=CGPoint(x:rect.maxX,y:rect.maxY)
设bottomLeft=CGPoint(x:rect.minX,y:rect.maxY)
如果topLeftRadius!=0{
移动路径(到:CGPoint(x:topLeft.x+topLeftRadius.width,y:topLeft.y))
}否则{
移动路径(到:CGPoint(x:topLeft.x,y:topLeft.y))
}
如果topRightRadius!=0{
path.addLine(to:CGPoint(x:topRight.x-topRightRadius.width,y:topRight.y))
添加曲线(到:CGPoint(x:topRight.x,y:topRight.y+topRightRadius.height),控制1:CGPoint(x:topRight.x,y:topRight.y),控制2:CGPoint(x:topRight.x,y:topRight.y+topRightRadius.height))
}否则{
addLine(to:CGPoint(x:topRight.x,y:topRight.y))
}
如果bottomRightRadius!=0{
addLine(to:CGPoint(x:bottomRight.x,y:bottomRight.y-bottomRightRadius.height))
添加曲线(到:CGPoint(x:bottomRight.x-bottomRightRadius.width,y:bottomRight.y),控件1:CGPoint(x:bottomRight.x,y:bottomRight.y),控件2:CGPoint(x:bottomRight.x-bottomRightRadius.width,y:bottomRight.y))
}否则{
addLine(to:CGPoint(x:bottomRight.x,y:bottomRight.y))
}
如果bottomLeftRadius!=0{
addLine(to:CGPoint(x:bottomLeft.x+bottomLeftRadius.width,y:bottomLeft.y))
添加曲线(到:CGPoint(x:bottomLeft.x,y:bottomLeft.y-bottomLeftRadius.height),控件1:CGPoint(x:bottomLeft.x,y:bottomLeftRadius.y),控件2:CGPoint(x:bottomLeft.x,y:bottomLeft.y-bottomLeftRadius.height))
}否则{
addLine(to:CGPoint(x:bottomLeft.x,y:bottomLeft.y))
}
如果topLeftRadius!=0{
addLine(to:CGPoint(x:topLeft.x,y:topLeft.y+topLeftRadius.height))
添加曲线(到:CGPoint(x:topLeft.x+topLeftRadius.width,y:topLeft.y),控件1:CGPoint(x:topLeft.x,y:topLeft.y),控件2:CGPoint(x:topLeft.x+topLeftRadius.width,y:topLeft.y))
}否则{
addLine(to:CGPoint(x:topLeft.x,y:topLeft.y))
}
path.closeSubpath()
cgPath=path
}
}
然后,添加此ui视图
扩展名:
扩展UIView{
func圆角(左上:CGFloat=0,右上:CGFloat=0,左下:CGFloat=0,右下:CGFloat=0){/(左上:CGFloat,右上:CGFloat,左下:CGFloat,右下:CGFloat){
设topLeftRadius=CGSize(宽度:topLeft,高度:topLeft)
设topRightRadius=CGSize(宽度:topRight,高度:topRight)
让bottomLeftRadius=CGSize(宽度:bottomLeft,高度:bottomLeft)
让bottomRightRadius=CGSize(宽度:bottomRight,高度:bottomRight)
设maskPath=UIBezierPath(shouldRoundRect:bounds,topLeftRadius:topLeftRadius,topRightRadius:topRightRadius,bottomLeftRadius:bottomLeftRadius,bottomRightRadius:bottomRightRadius)
let shape=CAShapeLayer()
shape.path=maskPath.cgPath
layer.mask=形状
}
}
最后,调用方法
myView.roundCorners(左上:10,右上:20,左下:30,右下:40)
显然,layer.borderRadius无法正常工作,因此请使用CAShapeLayer
和以前创建的路径创建一个边框
let borderLayer=CAShapeLayer()
borderLayer.path=(myView.layer.mask!as!CAShapeLayer).path!//重用贝塞尔路径
borderLayer.strokeColor=UIColor.red.cgColor
borderLayer.fillColor=UIColor.clear.cgColor
borderLayer.lineWidth=5
borderLayer.frame=myView.bounds
myView.layer.addSublayer(边界层)
瞧!一个基于@Kirill Dobryakov的略微改进和简化的答案。当你看到曲线时,你知道它不是理想的圆形(例如,查看侧面40和半径20),曲线会留下非常小但明显的不规则。我甚至不知道这是怎么可能的,但无论如何,最可靠的方法是使用圆弧,它可以形成理想的圆角,同时也是一个
@ibdesignable
组件:
extension UIBezierPath {
convenience init(shouldRoundRect rect: CGRect, topLeftRadius: CGFloat, topRightRadius: CGFloat, bottomLeftRadius: CGFloat, bottomRightRadius: CGFloat){
self.init()
let path = CGMutablePath()
let topLeft = rect.origin
let topRight = CGPoint(x: rect.maxX, y: rect.minY)
let bottomRight = CGPoint(x: rect.maxX, y: rect.maxY)
let bottomLeft = CGPoint(x: rect.minX, y: rect.maxY)
if topLeftRadius != 0 {
path.move(to: CGPoint(x: topLeft.x + topLeftRadius, y: topLeft.y))
} else {
path.move(to: topLeft)
}
if topRightRadius != 0 {
path.addLine(to: CGPoint(x: topRight.x - topRightRadius, y: topRight.y))
path.addArc(tangent1End: topRight, tangent2End: CGPoint(x: topRight.x, y: topRight.y + topRightRadius), radius: topRightRadius)
}
else {
path.addLine(to: topRight)
}
if bottomRightRadius != 0 {
path.addLine(to: CGPoint(x: bottomRight.x, y: bottomRight.y - bottomRightRadius))
path.addArc(tangent1End: bottomRight, tangent2End: CGPoint(x: bottomRight.x - bottomRightRadius, y: bottomRight.y), radius: bottomRightRadius)
}
else {
path.addLine(to: bottomRight)
}
if bottomLeftRadius != 0 {
path.addLine(to: CGPoint(x: bottomLeft.x + bottomLeftRadius, y: bottomLeft.y))
path.addArc(tangent1End: bottomLeft, tangent2End: CGPoint(x: bottomLeft.x, y: bottomLeft.y - bottomLeftRadius), radius: bottomLeftRadius)
}
else {
path.addLine(to: bottomLeft)
}
if topLeftRadius != 0 {
path.addLine(to: CGPoint(x: topLeft.x, y: topLeft.y + topLeftRadius))
path.addArc(tangent1End: topLeft, tangent2End: CGPoint(x: topLeft.x + topLeftRadius, y: topLeft.y), radius: topLeftRadius)
}
else {
path.addLine(to: topLeft)
}
path.closeSubpath()
cgPath = path
}
}
@IBDesignable
open class VariableCornerRadiusView: UIView {
private func applyRadiusMaskFor() {
let path = UIBezierPath(shouldRoundRect: bounds, topLeftRadius: topLeftRadius, topRightRadius: topRightRadius, bottomLeftRadius: bottomLeftRadius, bottomRightRadius: bottomRightRadius)
let shape = CAShapeLayer()
shape.path = path.cgPath
layer.mask = shape
}
@IBInspectable
open var topLeftRadius: CGFloat = 0 {
didSet { setNeedsLayout() }
}
@IBInspectable
open var topRightRadius: CGFloat = 0 {
didSet { setNeedsLayout() }
}
@IBInspectable
open var bottomLeftRadius: CGFloat = 0 {
didSet { setNeedsLayout() }
}
@IBInspectable
open var bottomRightRadius: CGFloat = 0 {
didSet { setNeedsLayout() }
}
override open func layoutSubviews() {
super.layoutSubviews()
applyRadiusMaskFor()
}
}
最好的方法是在iOS 11之后,这样看起来更平滑
func roundCorners(_ corners: UIRectCorner, radius: CGFloat) {
clipsToBounds = true
layer.cornerRadius = radius
layer.maskedCorners = CACornerMask(rawValue: corners.rawValue)
}
对于原始答案:请参阅此答案:与预期一样有效。非常感谢。它与border不起作用。还有吗?谢谢。我不知道为什么此答案的分数如此低。这是最好的答案。涵盖了各个方面。可以简化一点,例如,而不是
path.addLine(to:CGPoint(x:topLeft.x,y:topLeft.y))
if可以是path.addLine(to:top:left)
和许多类似的行。答案很好,但我正在尝试应用阴影..然后阴影不应用@ArashAfsharpour@MaulikshahUIView上的阴影?或按钮?我有奇怪的行为(即,只有左上角的玉米)