创建一个拉伸的半圆

Posted

技术标签:

【中文标题】创建一个拉伸的半圆【英文标题】:Creating a stretched semi circle 【发布时间】:2018-11-01 08:00:50 【问题描述】:

我正在尝试创建一个顶部有一个拉伸的半圆形裁剪的 uiview。我已经想出在下面裁剪一个半圆形,但是我似乎无法弄清楚如何使它更小,如下图所示。

在这里您会看到一个灰色图像,其中一个较小的半圆形被裁剪掉了:

到目前为止的代码:

    let path = UIBezierPath()
    path.move(to: bounds.origin)
    let center = CGPoint(x: bounds.origin.x + bounds.size.width / 2.0, y: bounds.origin.y)
    path.addArc(withCenter: center, radius: bounds.size.width / 2.0, startAngle: .pi, endAngle: 0, clockwise: false)
    path.addLine(to: CGPoint(x: bounds.origin.x + bounds.size.width, y: bounds.origin.y))
    path.addLine(to: CGPoint(x: bounds.origin.x + bounds.size.width, y: bounds.origin.y + bounds.size.height))
    path.addLine(to: CGPoint(x: bounds.origin.x, y: bounds.origin.y + bounds.size.height))
    path.close()

    let mask = CAShapeLayer()
    mask.path = path.cgPath

    layer.mask = mask

【问题讨论】:

您走在正确的道路上。尝试曲线而不是弧线。 这里是参考。 developer.apple.com/documentation/uikit/uibezierpath/…你需要两条曲线来实现你所需要的。 见developer.apple.com/documentation/uikit/uibezierpath/…。还建议您查看 bounds.midX、bounds.maxX 和它们的 Y 等效项。 bounds.origin.x 通常为零。 【参考方案1】:

试试这个

func addParabolaWithMax()  
    let path = UIBezierPath()

    let p0 = CGPoint(x: 0, y: 0)
    let p2 = CGPoint(x: self.view.frame.size.width/2, y: 100)

    let p1 = CGPoint(x: self.view.frame.size.width, y: 0)

    path.move(to: p1)
    path.addQuadCurve(to: p0, controlPoint: p2)

    path.lineWidth = 1
    path.stroke()
    let line = CAShapeLayer()
    line.path = path.cgPath;
    line.strokeColor = UIColor.black.cgColor
    line.fillColor = UIColor.blue.cgColor
    view.layer.addSublayer(line)

【讨论】:

似乎工作得很好。有没有办法让蓝色成为背景视图的颜色?所以它是透明的。 用 alpha 着色 要扭转这种情况,您需要在左下角和右下角额外添加path.addLines。【参考方案2】:
class SampleViewController: UIViewController 

    override func viewDidLoad() 
        super.viewDidLoad()
        // Do any additional setup after loading the view, typically from a nib.
    

    override func viewWillAppear(_ animated: Bool) 
        super.viewWillAppear(animated)
        view.backgroundColor = UIColor.blue
    

    override func viewWillLayoutSubviews() 
        super.viewWillLayoutSubviews()
        setMask(control: CGPoint(x: 40.0, y: 100.0))
    

    func setMask(control: CGPoint) 
        let bounds = view.bounds
        let path = UIBezierPath()
        path.move(to: CGPoint(x: bounds.minX, y: bounds.maxY))
        path.addLine(to: bounds.origin)
        let control2 = CGPoint(x: bounds.maxX - control.x, y: control.y)
        path.addCurve(to: CGPoint(x: bounds.maxX, y: bounds.minY), controlPoint1: control, controlPoint2: control2)
        path.addLine(to: CGPoint(x: bounds.maxX, y: bounds.maxY))
        path.close()
        let mask = CAShapeLayer()
        mask.path = path.cgPath
        view.layer.mask = mask

    

通过调整控制点,您可以改变曲率(iPhone X 的模拟器截图,因此是圆角!)。

【讨论】:

【参考方案3】:

由于我似乎只能将单个图像发布到答案,以下是贝塞尔曲线中控制点的工作方式以及如何通过调整控制点来更改曲线的弧度:

C2 就是bounds.max - C1.x, C1.y

【讨论】:

以上是关于创建一个拉伸的半圆的主要内容,如果未能解决你的问题,请参考以下文章

如何在android中使用xml drawable创建半圆形填充形状?

如何为圆形UIImageView创建半圆边框?

如何在半圆上对齐 D3 圆

在 ios sdk 中创建半圆形旋钮

用CSS3画一个半圆

绘制一个半圆形按钮 iOS