You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Swift中右下角曲线位置错误问题求助

自定义View曲线不符合预期问题修复

问题描述

  • 预期实现效果:
    预期曲线效果
  • 当前实现效果:
    当前实现效果

使用的Swift代码:

class ConerViewBootomRight: UIView {
    
    required init(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)!
        setup()
    }
    
    
    override init(frame: CGRect) {
        super.init(frame: frame)
        setup()
        
    }
    //This method does the necessary UI adjustments
    func setup()
    {
        if #available(iOS 13.0, *) {
            
            let cornerRadius: CGFloat = 80.0 // Set the corner radius
            let path = UIBezierPath()
            path.move(to: CGPoint(x: 0, y: 0))
            path.addLine(to: CGPoint(x: self.bounds.width, y: 0))
            path.addLine(to: CGPoint(x: self.bounds.width, y: self.bounds.height - cornerRadius))
            path.addQuadCurve(to: CGPoint(x: self.bounds.width - cornerRadius, y: self.bounds.height), controlPoint: CGPoint(x: self.bounds.width, y: self.bounds.height))
            path.addLine(to: CGPoint(x: 0, y: self.bounds.height))
            path.close()

            let maskLayer = CAShapeLayer()
            maskLayer.path = path.cgPath
            self.layer.mask = maskLayer

         }
    }
}

问题分析与修复方案

1. 核心问题:路径绘制时机错误

在init方法中调用setup时,View的最终尺寸还未确定(比如使用AutoLayout布局时,bounds此时是初始占位尺寸),导致路径使用了错误的宽高值,曲线显示异常。

2. 曲线路径不符合预期

当前代码绘制的是小圆角,而预期是右下角向内凹陷的大弧形,需要调整贝塞尔曲线的控制点和路径节点。

修复后的代码

class ConerViewBottomRight: UIView {
    
    required init(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)!
    }
    
    override init(frame: CGRect) {
        super.init(frame: frame)
    }
    
    // 布局完成后更新遮罩路径,确保使用正确的View尺寸
    override func layoutSubviews() {
        super.layoutSubviews()
        setupMask()
    }
    
    private func setupMask() {
        let curveDepth: CGFloat = 80.0 // 调整此值控制凹陷深度
        
        let path = UIBezierPath()
        path.move(to: CGPoint(x: 0, y: 0))
        path.addLine(to: CGPoint(x: bounds.width, y: 0))
        path.addLine(to: CGPoint(x: bounds.width, y: bounds.height - curveDepth))
        // 调整控制点位置,生成向内凹陷的弧形
        path.addQuadCurve(to: CGPoint(x: bounds.width - curveDepth, y: bounds.height), 
                         controlPoint: CGPoint(x: bounds.width + curveDepth/2, y: bounds.height - curveDepth/2))
        path.addLine(to: CGPoint(x: 0, y: bounds.height))
        path.close()
        
        let maskLayer = CAShapeLayer()
        maskLayer.path = path.cgPath
        layer.mask = maskLayer
    }
}

关键改动说明

  • 将遮罩路径的生成逻辑移到layoutSubviews中,确保每次View尺寸确定后都重新绘制正确路径。
  • 调整贝塞尔曲线的控制点到View右侧外部,形成符合预期的向内凹陷弧形。
  • 修正了类名拼写错误(ConerViewBootomRight改为ConerViewBottomRight)。
  • 移除不必要的iOS版本判断,贝塞尔曲线和形状遮罩在iOS 9及以上都支持。

调整curveDepth的值可以改变凹陷的深度和弧度:数值越大,凹陷越明显。

内容的提问来源于stack exchange,提问作者shivam

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.25 22:49:54