在Swift IOS中使用UibezierPath创建Hexagon设计

发布于 2025-01-31 20:42:20 字数 2865 浏览 3 评论 0原文

我想使用uibezierpath在下图中实现 Hexagon Shape 。但是我不知道如何创建这种六角形形状。

我尝试了以下代码:

func roundedPolygonPath(rect: CGRect, lineWidth: CGFloat, sides: NSInteger, cornerRadius: CGFloat, rotationOffset: CGFloat = 0)
     -> UIBezierPath {
        let path = UIBezierPath()
        let theta: CGFloat = CGFloat(2.0 * M_PI) / CGFloat(sides) // How much to turn at every corner
        let offset: CGFloat = cornerRadius * tan(theta / 2.0)     // Offset from which to start rounding corners
        let width = min(rect.size.width, rect.size.height)        // Width of the square

        let center = CGPoint(x: rect.origin.x + width / 2.0, y: rect.origin.y + width / 2.0)

        // Radius of the circle that encircles the polygon
        // Notice that the radius is adjusted for the corners, that way the largest outer
        // dimension of the resulting shape is always exactly the width - linewidth
        let radius = (width - lineWidth + cornerRadius - (cos(theta) * cornerRadius)) / 2.0

        // Start drawing at a point, which by default is at the right hand edge
        // but can be offset
        var angle = CGFloat(rotationOffset)

         let corner = CGPoint(x: center.x + (radius - cornerRadius) * cos(angle), y: center.y + (radius - cornerRadius) * sin(angle))
         path.move(to: CGPoint(x: corner.x + cornerRadius * cos(angle + theta), y: corner.y + cornerRadius * sin(angle + theta)))

        for _ in 0 ..< sides {
            angle += theta

            let corner = CGPoint(x: center.x + (radius - cornerRadius) * cos(angle), y: center.y + (radius - cornerRadius) * sin(angle))
            let tip = CGPoint(x: center.x + radius * cos(angle), y: center.y + radius * sin(angle))
            let start = CGPoint(x: corner.x + cornerRadius * cos(angle - theta), y: corner.y + cornerRadius * sin(angle - theta))
            let end = CGPoint(x: corner.x + cornerRadius * cos(angle + theta), y: corner.y + cornerRadius * sin(angle + theta))

            path.addLine(to: start)
            path.addQuadCurve(to: end, controlPoint: tip)
        }

         path.close()

        // Move the path to the correct origins
        let bounds = path.bounds
         let transform = CGAffineTransform(translationX: -bounds.origin.x + rect.origin.x + lineWidth / 2.0,
                                           y: -bounds.origin.y + rect.origin.y + lineWidth / 2.0)
         path.apply(transform)

        return path
    }

当前代码输出:

”

I want to achieve a hexagon shape using UIBezierPath like in the image below. But I don´t know how to create this kind of hexagon shape.

example

I´ve tried following code:

func roundedPolygonPath(rect: CGRect, lineWidth: CGFloat, sides: NSInteger, cornerRadius: CGFloat, rotationOffset: CGFloat = 0)
     -> UIBezierPath {
        let path = UIBezierPath()
        let theta: CGFloat = CGFloat(2.0 * M_PI) / CGFloat(sides) // How much to turn at every corner
        let offset: CGFloat = cornerRadius * tan(theta / 2.0)     // Offset from which to start rounding corners
        let width = min(rect.size.width, rect.size.height)        // Width of the square

        let center = CGPoint(x: rect.origin.x + width / 2.0, y: rect.origin.y + width / 2.0)

        // Radius of the circle that encircles the polygon
        // Notice that the radius is adjusted for the corners, that way the largest outer
        // dimension of the resulting shape is always exactly the width - linewidth
        let radius = (width - lineWidth + cornerRadius - (cos(theta) * cornerRadius)) / 2.0

        // Start drawing at a point, which by default is at the right hand edge
        // but can be offset
        var angle = CGFloat(rotationOffset)

         let corner = CGPoint(x: center.x + (radius - cornerRadius) * cos(angle), y: center.y + (radius - cornerRadius) * sin(angle))
         path.move(to: CGPoint(x: corner.x + cornerRadius * cos(angle + theta), y: corner.y + cornerRadius * sin(angle + theta)))

        for _ in 0 ..< sides {
            angle += theta

            let corner = CGPoint(x: center.x + (radius - cornerRadius) * cos(angle), y: center.y + (radius - cornerRadius) * sin(angle))
            let tip = CGPoint(x: center.x + radius * cos(angle), y: center.y + radius * sin(angle))
            let start = CGPoint(x: corner.x + cornerRadius * cos(angle - theta), y: corner.y + cornerRadius * sin(angle - theta))
            let end = CGPoint(x: corner.x + cornerRadius * cos(angle + theta), y: corner.y + cornerRadius * sin(angle + theta))

            path.addLine(to: start)
            path.addQuadCurve(to: end, controlPoint: tip)
        }

         path.close()

        // Move the path to the correct origins
        let bounds = path.bounds
         let transform = CGAffineTransform(translationX: -bounds.origin.x + rect.origin.x + lineWidth / 2.0,
                                           y: -bounds.origin.y + rect.origin.y + lineWidth / 2.0)
         path.apply(transform)

        return path
    }

Current code output:

example

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

甩你一脸翔 2025-02-07 20:42:20

对于这种形状,我从中拿了两个中心,然后从那起矩形六边形

func customPolygonPath(rect: CGRect, lineWidth: CGFloat, sides: NSInteger, cornerRadius: CGFloat, rotationOffset: CGFloat = 0)
-> UIBezierPath {
    let path = UIBezierPath()
    
    
    let theta: CGFloat = CGFloat(2.0 * M_PI) / CGFloat(sides) // How much to turn at every corner
    let offset: CGFloat = cornerRadius * tan(theta / 2.0)     // Offset from which to start rounding corners
    let width = min(rect.size.width, rect.size.height)        // Width of the square
    let height = max(rect.size.width, rect.size.height)
    
    let upperCenter = CGPoint(x: rect.origin.x + width / 2.0, y: rect.origin.y + width / 2.0)
    let bottomCenter = CGPoint(x: upperCenter.x, y: height - upperCenter.y)
    
    
    
    let center = CGPoint(x: rect.origin.x + width / 2.0, y: rect.origin.y + height / 2.0)
    
    // Radius of the circle that encircles the polygon
    // Notice that the radius is adjusted for the corners, that way the largest outer
    // dimension of the resulting shape is always exactly the width - linewidth
    let radius = (width - lineWidth + cornerRadius - (cos(theta) * cornerRadius)) / 2.0
    
    // Start drawing at a point, which by default is at the right hand edge
    // but can be offset
    var angle = CGFloat(rotationOffset)
    let bottomCorner = CGPoint(x: bottomCenter.x + (radius - cornerRadius) * cos(angle), y: bottomCenter.y + (radius - cornerRadius) * sin(angle))
    path.move(to: CGPoint(x: bottomCorner.x + cornerRadius * cos(angle + theta), y: bottomCorner.y + cornerRadius * sin(angle + theta)))
    //        print("corner:::\(corner)")
    //        print("point:::\(CGPoint(x: corner.x + cornerRadius * cos(angle + theta), y: corner.y + cornerRadius * sin(angle + theta)))")
    
    for i in 0 ..< sides {
        angle += theta
        if i == 0 || i == 4 || i == 5 {
            //bottomCenter
            let corner = CGPoint(x: bottomCenter.x + (radius - cornerRadius) * cos(angle), y: bottomCenter.y + (radius - cornerRadius) * sin(angle))
            let tip = CGPoint(x: bottomCenter.x + radius * cos(angle), y: bottomCenter.y + radius * sin(angle))
            let start = CGPoint(x: corner.x + (cornerRadius * cos(angle - theta)), y: corner.y + (cornerRadius * sin(angle - theta)))
            let end = CGPoint(x: corner.x + (cornerRadius * cos(angle + theta)), y: corner.y + (cornerRadius * sin(angle + theta)))
            
            path.addLine(to: start)
            path.addQuadCurve(to: end, controlPoint: tip)
        }else {
            //upperCenter
            let corner = CGPoint(x: upperCenter.x + (radius - cornerRadius) * cos(angle), y: upperCenter.y + (radius - cornerRadius) * sin(angle))
            let tip = CGPoint(x: upperCenter.x + radius * cos(angle), y: upperCenter.y + radius * sin(angle))
            let start = CGPoint(x: corner.x + cornerRadius * cos(angle - theta), y: corner.y + cornerRadius * sin(angle - theta))
            let end = CGPoint(x: corner.x + cornerRadius * cos(angle + theta), y: corner.y + cornerRadius * sin(angle + theta))
            path.addLine(to: start)
            path.addQuadCurve(to: end, controlPoint: tip)
        }
    }
    
    path.close()
    
    //         Move the path to the correct origins
    let bounds = path.bounds
    let transform = CGAffineTransform(translationX: 0,
                                      y: 0)
    path.apply(transform)
    
    return path
}

for this kind of shape i took two center points and make rectangle hexagon from that

func customPolygonPath(rect: CGRect, lineWidth: CGFloat, sides: NSInteger, cornerRadius: CGFloat, rotationOffset: CGFloat = 0)
-> UIBezierPath {
    let path = UIBezierPath()
    
    
    let theta: CGFloat = CGFloat(2.0 * M_PI) / CGFloat(sides) // How much to turn at every corner
    let offset: CGFloat = cornerRadius * tan(theta / 2.0)     // Offset from which to start rounding corners
    let width = min(rect.size.width, rect.size.height)        // Width of the square
    let height = max(rect.size.width, rect.size.height)
    
    let upperCenter = CGPoint(x: rect.origin.x + width / 2.0, y: rect.origin.y + width / 2.0)
    let bottomCenter = CGPoint(x: upperCenter.x, y: height - upperCenter.y)
    
    
    
    let center = CGPoint(x: rect.origin.x + width / 2.0, y: rect.origin.y + height / 2.0)
    
    // Radius of the circle that encircles the polygon
    // Notice that the radius is adjusted for the corners, that way the largest outer
    // dimension of the resulting shape is always exactly the width - linewidth
    let radius = (width - lineWidth + cornerRadius - (cos(theta) * cornerRadius)) / 2.0
    
    // Start drawing at a point, which by default is at the right hand edge
    // but can be offset
    var angle = CGFloat(rotationOffset)
    let bottomCorner = CGPoint(x: bottomCenter.x + (radius - cornerRadius) * cos(angle), y: bottomCenter.y + (radius - cornerRadius) * sin(angle))
    path.move(to: CGPoint(x: bottomCorner.x + cornerRadius * cos(angle + theta), y: bottomCorner.y + cornerRadius * sin(angle + theta)))
    //        print("corner:::\(corner)")
    //        print("point:::\(CGPoint(x: corner.x + cornerRadius * cos(angle + theta), y: corner.y + cornerRadius * sin(angle + theta)))")
    
    for i in 0 ..< sides {
        angle += theta
        if i == 0 || i == 4 || i == 5 {
            //bottomCenter
            let corner = CGPoint(x: bottomCenter.x + (radius - cornerRadius) * cos(angle), y: bottomCenter.y + (radius - cornerRadius) * sin(angle))
            let tip = CGPoint(x: bottomCenter.x + radius * cos(angle), y: bottomCenter.y + radius * sin(angle))
            let start = CGPoint(x: corner.x + (cornerRadius * cos(angle - theta)), y: corner.y + (cornerRadius * sin(angle - theta)))
            let end = CGPoint(x: corner.x + (cornerRadius * cos(angle + theta)), y: corner.y + (cornerRadius * sin(angle + theta)))
            
            path.addLine(to: start)
            path.addQuadCurve(to: end, controlPoint: tip)
        }else {
            //upperCenter
            let corner = CGPoint(x: upperCenter.x + (radius - cornerRadius) * cos(angle), y: upperCenter.y + (radius - cornerRadius) * sin(angle))
            let tip = CGPoint(x: upperCenter.x + radius * cos(angle), y: upperCenter.y + radius * sin(angle))
            let start = CGPoint(x: corner.x + cornerRadius * cos(angle - theta), y: corner.y + cornerRadius * sin(angle - theta))
            let end = CGPoint(x: corner.x + cornerRadius * cos(angle + theta), y: corner.y + cornerRadius * sin(angle + theta))
            path.addLine(to: start)
            path.addQuadCurve(to: end, controlPoint: tip)
        }
    }
    
    path.close()
    
    //         Move the path to the correct origins
    let bounds = path.bounds
    let transform = CGAffineTransform(translationX: 0,
                                      y: 0)
    path.apply(transform)
    
    return path
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文