Applying Gradient to UIImage Smoothly

回眸只為那壹抹淺笑 提交于 2019-12-03 07:42:58

SWIFT 3

func imageWithGradient(img:UIImage!) -> UIImage {

    UIGraphicsBeginImageContext(img.size)
    let context = UIGraphicsGetCurrentContext()

    img.draw(at: CGPoint(x: 0, y: 0))

    let colorSpace = CGColorSpaceCreateDeviceRGB()
    let locations:[CGFloat] = [0.0, 1.0]

    let bottom = UIColor(red: 0, green: 0, blue: 0, alpha: 0.5).cgColor
    let top = UIColor(red: 0, green: 0, blue: 0, alpha: 0).cgColor

    let colors = [top, bottom] as CFArray

    let gradient = CGGradient(colorsSpace: colorSpace, colors: colors, locations: locations)

    let startPoint = CGPoint(x: img.size.width/2, y: 0)
    let endPoint = CGPoint(x: img.size.width/2, y: img.size.height)

    context!.drawLinearGradient(gradient!, start: startPoint, end: endPoint, options: CGGradientDrawingOptions(rawValue: UInt32(0)))

    let image = UIGraphicsGetImageFromCurrentImageContext()

    UIGraphicsEndImageContext()

    return image!
}

I tried this out in a Swift playground, I couldn't replicate the exact issue you are describing, however here are some suggestions that you could try.

You could change the way you set up the stops in the gradient, I think it would make more sense to instead of shifting the gradient using the stops, shift the start point, i.e instead of starting from the top edge, start from the vertical center, something like this

UIGraphicsBeginImageContext(image.size)
var context = UIGraphicsGetCurrentContext()

image.drawAtPoint(CGPointMake(0, 0))

let colorSpace = CGColorSpaceCreateDeviceRGB()
let locations:[CGFloat] = [0.0, 1.0]
let bottom = UIColor(red: 0, green: 0, blue: 0, alpha: 0.5).CGColor
let top = UIColor(red: 0, green: 0, blue: 0, alpha: 0).CGColor

let gradient = CGGradientCreateWithColors(colorSpace,
               [top, bottom], locations)

let startPoint = CGPointMake(image.size.width / 2, image.size.height / 2)
let endPoint = CGPointMake(image.size.width / 2, image.size.height)
CGContextDrawLinearGradient(context, gradient, startPoint, endPoint, 0)

let finalImage = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()

Notice locations is now 0 and 1, while the startPoint y coordinate has shifted downwards.

Alternatively, look at passing kCGGradientDrawsBeforeStartLocation as an option to CGContextDrawLinearGradient, as that could also make a difference.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!