Ios 使用CAGradientLayer定义渐变角度

Ios 使用CAGradientLayer定义渐变角度,ios,objective-c,gradient,linear-gradients,cagradientlayer,Ios,Objective C,Gradient,Linear Gradients,Cagradientlayer,我正在尝试使用CaGradientLayer绘制角度梯度。我知道可以使用起点和终点定义角度。我可以为一些标准角度计算这些点,比如0,90,180,360等等,但是我想为任意角度计算这些点。我试着用三角法计算,但没有成功。有人能告诉我如何计算任意角度的这些点吗?这里有一种方法,可以创建一个视图,根据滑块(或任何东西)的输入,使其两种颜色的渐变360度旋转。输入的滑块值(“下面的x”变量)介于0.0和1.0之间 在0.0时,渐变为水平(顶部为颜色A,下方为颜色B),旋转360度至值1.0(与值0.0

我正在尝试使用
CaGradientLayer
绘制角度梯度。我知道可以使用
起点
终点
定义角度。我可以为一些标准角度计算这些点,比如0,90,180,360等等,但是我想为任意角度计算这些点。我试着用三角法计算,但没有成功。有人能告诉我如何计算任意角度的这些点吗?

这里有一种方法,可以创建一个视图,根据滑块(或任何东西)的输入,使其两种颜色的渐变360度旋转。输入的滑块值(“下面的x”变量)介于0.0和1.0之间

在0.0时,渐变为水平(顶部为颜色A,下方为颜色B),旋转360度至值1.0(与值0.0相同-或完全旋转)

例如,当x=0.25时,颜色A为左,颜色B为右。0.5时,颜色A在下方,颜色B在上方,0.75时,颜色A在右侧,颜色B在左侧。它从右向左逆时针旋转

它有四个参数:frame、colorA、colorB和输入值(0-1)

斯威夫特3
这在很大程度上是基于萨尔塔克·夏尔马的解决方案。我对UIView进行了扩展,我认为可读性和类型转换可以稍微改进:

extension UIView {

    func setGradient(colors: [CGColor], angle: Float = 0) {
        let gradientLayerView: UIView = UIView(frame: CGRect(x:0, y: 0, width: bounds.width, height: bounds.height))
        let gradient: CAGradientLayer = CAGradientLayer()
        gradient.frame = gradientLayerView.bounds
        gradient.colors = colors

        let alpha: Float = angle / 360
        let startPointX = powf(
            sinf(2 * Float.pi * ((alpha + 0.75) / 2)),
            2
        )
        let startPointY = powf(
            sinf(2 * Float.pi * ((alpha + 0) / 2)),
            2
        )
        let endPointX = powf(
            sinf(2 * Float.pi * ((alpha + 0.25) / 2)),
            2
        )
        let endPointY = powf(
            sinf(2 * Float.pi * ((alpha + 0.5) / 2)),
            2
        )

        gradient.endPoint = CGPoint(x: CGFloat(endPointX),y: CGFloat(endPointY))
        gradient.startPoint = CGPoint(x: CGFloat(startPointX), y: CGFloat(startPointY))

        gradientLayerView.layer.insertSublayer(gradient, at: 0)
        layer.insertSublayer(gradientLayerView.layer, at: 0)
    }

}
将它添加到一个新的或相关的Swift文件中,您只需调用
myView.setGradient(颜色:gradientColorsArray)

或者
myView.setGradient(颜色:gradientColorsArray,角度:90)
CAGradientLayer
仅支持轴向(方向)渐变。@DavidRönnqvist我知道这一点。我不是说径向梯度。我试着给轴向梯度加一个角度。所以你问的是关于三角的问题,以计算出给定角度的两点吗?@DavidRönnqvist是的,准确地说。((alpha+X)中X值表示什么
static func setGradient(view: UIView!,viewRadius: CGFloat!, color1: UIColor!, color2: UIColor!, angle: Double!, alphaValue: CGFloat!){
    let gradient = CAGradientLayer()
    
    gradient.frame =  CGRect(origin: CGPoint.zero, size: view.frame.size)
    
    gradient.colors = [color1.withAlphaComponent(alphaValue).cgColor, color2.withAlphaComponent(alphaValue).cgColor]
    let x: Double! = angle / 360.0
    let a = pow(sinf(Float(2.0 * M_PI * ((x + 0.75) / 2.0))),2.0);
    let b = pow(sinf(Float(2*M_PI*((x+0.0)/2))),2);
    let c = pow(sinf(Float(2*M_PI*((x+0.25)/2))),2);
    let d = pow(sinf(Float(2*M_PI*((x+0.5)/2))),2);
    
    gradient.endPoint = CGPoint(x: CGFloat(c),y: CGFloat(d))
    gradient.startPoint = CGPoint(x: CGFloat(a),y:CGFloat(b))
    
    view.roundCorners([.topLeft, .bottomLeft], radius: viewRadius)
    view.layer.insertSublayer(gradient, at: 0)
    
    
}
extension UIView {

    func setGradient(colors: [CGColor], angle: Float = 0) {
        let gradientLayerView: UIView = UIView(frame: CGRect(x:0, y: 0, width: bounds.width, height: bounds.height))
        let gradient: CAGradientLayer = CAGradientLayer()
        gradient.frame = gradientLayerView.bounds
        gradient.colors = colors

        let alpha: Float = angle / 360
        let startPointX = powf(
            sinf(2 * Float.pi * ((alpha + 0.75) / 2)),
            2
        )
        let startPointY = powf(
            sinf(2 * Float.pi * ((alpha + 0) / 2)),
            2
        )
        let endPointX = powf(
            sinf(2 * Float.pi * ((alpha + 0.25) / 2)),
            2
        )
        let endPointY = powf(
            sinf(2 * Float.pi * ((alpha + 0.5) / 2)),
            2
        )

        gradient.endPoint = CGPoint(x: CGFloat(endPointX),y: CGFloat(endPointY))
        gradient.startPoint = CGPoint(x: CGFloat(startPointX), y: CGFloat(startPointY))

        gradientLayerView.layer.insertSublayer(gradient, at: 0)
        layer.insertSublayer(gradientLayerView.layer, at: 0)
    }

}