Search code examples
swiftswift4.2

Button gradient not working after ios 12 (Swift 4.2)


With the coming of ios 12 and swift 4.2 my code is not working anymore. It used to be a gradient from left-to-right, dark purple-to-light-purple button. How can I fix this?

// Gives the button gradient values
func setGradientButton(colorOne: UIColor, colorTwo: UIColor, x1: Double, y1: Double, x2: Double, y2: Double) {

    let gradientLayer = CAGradientLayer()
    gradientLayer.frame = bounds
    gradientLayer.colors = [colorOne.cgColor, colorTwo.cgColor]
    gradientLayer.locations = [0.0, 0.0]
    gradientLayer.startPoint = CGPoint(x: x1, y: y1)
    gradientLayer.endPoint = CGPoint(x: x2, y: y2)

    layer.insertSublayer(gradientLayer, at: 0)
}


// Sets UI elements
func setUI(_ label : UILabel, _ button : UIButton) {

    let colorOne = UIColor(red: 119.0 / 255.0, green: 85.0 / 255.0, blue: 254.0 / 255.0, alpha: 100.0)
    let colorTwo = UIColor(red: 177.0 / 255.0, green: 166.0 / 255.0, blue: 251.0 / 255.0, alpha: 100.0)

    button.setGradientButton(colorOne: colorOne, colorTwo: colorTwo, x1: 0.0, y1: 50, x2: 150, y2: 50)
    button.layer.cornerRadius = 4
    button.clipsToBounds = true
}

Solution

  • I can't assume why your code has worked before, but I see that you got a few problems with your CAGradientLayer setup.

    At first, the locations array. According to Apple Documentation this value "defines the location of each gradient stop". So if you want your gradient to start with one color and end with another, you need to set your locations like that

    gradientLayer.locations = [0.0, 1.0]
    

    Another problem is startPoint and endPoint. Again, from documentation:

    The point is defined in the unit coordinate space and is then mapped to the layer’s bounds rectangle when drawn.

    So your points values should be between 0.0 and 1.0. In unit coordinate space (0.0, 0.0) is the top-left corner of your view and (1.0, 1.0) is the bottom-right. If you want to get a horizontal gradient, you need to set points like that

    gradientLayer.startPoint = CGPoint(x: 0, y: 0.5)
    gradientLayer.endPoint = CGPoint(x: 1, y: 0.5)
    

    Hope it helps you.