如何在swift中显示菱形图像?

问题描述 投票:0回答:3

Image

当我给定宽度和高度 120 并应用角半径时,我想以菱形显示图像。我得到了大约的钻石形状,但没有得到精确的钻石形状,所以有人建议我这对我有帮助。

self.imageView.layer.cornerRadius = self.imageView.frame.size.width / 2
self.imageView.clipsToBounds = true
ios swift uiimageview
3个回答
24
投票

如果您有图像视图并希望将其裁剪为菱形(菱形)形状,您应该:

  • 创建菱形
    UIBezierPath
  • 将其用作
    path
    CAShapeLayer
  • CAShapeLayer
    设置为
    mask
    UIImageView
    layer

在 Swift 3 及更高版本中,可能看起来像:

extension UIView {
    func addDiamondMask(cornerRadius: CGFloat = 0) {
        let path = UIBezierPath()
        path.move(to: CGPoint(x: bounds.midX, y: bounds.minY + cornerRadius))
        path.addLine(to: CGPoint(x: bounds.maxX - cornerRadius, y: bounds.midY))
        path.addLine(to: CGPoint(x: bounds.midX, y: bounds.maxY - cornerRadius))
        path.addLine(to: CGPoint(x: bounds.minX + cornerRadius, y: bounds.midY))
        path.close()

        let shapeLayer = CAShapeLayer()
        shapeLayer.path = path.cgPath
        shapeLayer.fillColor = UIColor.white.cgColor
        shapeLayer.strokeColor = UIColor.white.cgColor
        shapeLayer.lineWidth = cornerRadius * 2
        shapeLayer.lineJoin = kCALineJoinRound
        shapeLayer.lineCap = kCALineCapRound

        layer.mask = shapeLayer
    }
}

因此,只需在图像视图上调用

addDiamondMask(cornerRadius:)
(其中
cornerRadius
是可选的)即可。

imageView.addDiamondMask()

结果:

对于 Swift 2 的演绎,请参阅 此答案的先前修订版


圆角的另一种算法可能是:

extension UIView {
    func addDiamondMask(cornerRadius: CGFloat = 0) {
        let path = UIBezierPath()

        let points = [
            CGPoint(x: bounds.midX, y: bounds.minY),
            CGPoint(x: bounds.maxX, y: bounds.midY),
            CGPoint(x: bounds.midX, y: bounds.maxY),
            CGPoint(x: bounds.minX, y: bounds.midY)
        ]

        path.move(to: point(from: points[0], to: points[1], distance: cornerRadius, fromStart: true))
        for i in 0 ..< 4 {
            path.addLine(to: point(from: points[i], to: points[(i + 1) % 4], distance: cornerRadius, fromStart: false))
            path.addQuadCurve(to: point(from: points[(i + 1) % 4], to: points[(i + 2) % 4], distance: cornerRadius, fromStart: true), controlPoint: points[(i + 1) % 4])
        }
        path.close()

        let shapeLayer = CAShapeLayer()
        shapeLayer.path = path.cgPath
        shapeLayer.fillColor = UIColor.white.cgColor
        shapeLayer.strokeColor = UIColor.clear.cgColor

        layer.mask = shapeLayer
    }

    private func point(from point1: CGPoint, to point2: CGPoint, distance: CGFloat, fromStart: Bool) -> CGPoint {
        let start: CGPoint
        let end: CGPoint

        if fromStart {
            start = point1
            end = point2
        } else {
            start = point2
            end = point1
        }
        let angle = atan2(end.y - start.y, end.x - start.x)
        return CGPoint(x: start.x + distance * cos(angle), y: start.y + distance * sin(angle))
    }

}

这里我在拐角处做了四边形贝塞尔曲线,但我认为如果菱形完全拉长的话,圆角的效果会比上面的效果稍好一些。

无论如何,这会产生:


0
投票

SWIFT 5

extension UIView {
    func addDiamondMask(cornerRadius: CGFloat = 0) {
        let path = UIBezierPath()
        path.move(to: CGPoint(x: bounds.midX, y: bounds.minY + cornerRadius))
        path.addLine(to: CGPoint(x: bounds.maxX - cornerRadius, y: bounds.midY))
        path.addLine(to: CGPoint(x: bounds.midX, y: bounds.maxY - cornerRadius))
        path.addLine(to: CGPoint(x: bounds.minX + cornerRadius, y: bounds.midY))
        path.close()

        let shapeLayer = CAShapeLayer()
        shapeLayer.path = path.cgPath
        shapeLayer.fillColor = UIColor.white.cgColor
        shapeLayer.strokeColor = UIColor.white.cgColor
        shapeLayer.lineWidth = cornerRadius * 2
        shapeLayer.lineJoin = .round
        shapeLayer.lineCap = .round

        layer.mask = shapeLayer
    }
}

0
投票
  • 如果您的视图使用许多屏幕或使用 centerlly 的视图,那么有时您会制作菱形视图,有时会制作方形视图,所以我制作了 IBDesignable 菱形 uiview 类。

进口粉底 导入 UIKit

@IBDesignable 公共类 DiamondView:UIView {

private var _cornerRadius: CGFloat = 0
private var _isDiamondShape: Bool = false

@IBInspectable override var cornerRadius: CGFloat {
    get {
        return _cornerRadius
    }
    set {
        _cornerRadius = newValue
        setNeedsLayout()
    }
}

@IBInspectable var isDiamondShape: Bool {
    get {
        return _isDiamondShape
    }
    set {
        _isDiamondShape = newValue
        setNeedsLayout()
    }
}

override public func layoutSubviews() {
    super.layoutSubviews()
    if isDiamondShape {
        addDiamondMask()
    } else {
        layer.mask = nil
    }
}

private func addDiamondMask() {
    let path = UIBezierPath()
    
    let points = [
        CGPoint(x: bounds.midX, y: bounds.minY),
        CGPoint(x: bounds.maxX, y: bounds.midY),
        CGPoint(x: bounds.midX, y: bounds.maxY),
        CGPoint(x: bounds.minX, y: bounds.midY)
    ]
    
    path.move(to: point(from: points[0], to: points[1], distance: _cornerRadius, fromStart: true))
    for i in 0..<4 {
        path.addLine(to: point(from: points[i], to: points[(i + 1) % 4], distance: _cornerRadius, fromStart: false))
        path.addQuadCurve(to: point(from: points[(i + 1) % 4], to: points[(i + 2) % 4], distance: _cornerRadius, fromStart: true), controlPoint: points[(i + 1) % 4])
    }
    path.close()
    
    let shapeLayer = CAShapeLayer()
    shapeLayer.path = path.cgPath
    shapeLayer.fillColor = UIColor.white.cgColor
    shapeLayer.strokeColor = UIColor.clear.cgColor
    
    layer.mask = shapeLayer
}

private func point(from point1: CGPoint, to point2: CGPoint, distance: CGFloat, fromStart: Bool) -> CGPoint {
    let start: CGPoint
    let end: CGPoint
    
    if fromStart {
        start = point1
        end = point2
    } else {
        start = point2
        end = point1
    }
    let angle = atan2(end.y - start.y, end.x - start.x)
    return CGPoint(x: start.x + distance * cos(angle), y: start.y + distance * sin(angle))
}

}

© www.soinside.com 2019 - 2024. All rights reserved.