一尘不染

给定颜色的十六进制,如何使该颜色更浅和更暗?

swift

假设我有一个十六进制,例如:5fc9f8

是否存在接受“黑暗程度”(-10到10)并返回反映该水平的十六进制的函数?

黑暗是指添加黑色/从颜色中删除黑色。


阅读 411

收藏
2020-07-07

共1个答案

一尘不染

import UIKit

extension StringProtocol {
    subscript(range: Range<Int>) -> SubSequence {
        let start = self.index(startIndex, offsetBy: range.lowerBound, limitedBy: endIndex) ?? endIndex
        return self[start..<(self.index(start, offsetBy: range.count, limitedBy: endIndex) ?? endIndex)]
    }
    var hexaCGFloat: CGFloat { .init(strtoul(String(self), nil, 16)) }
}

extension UIColor {
    var rgb: (red: CGFloat, green: CGFloat, blue: CGFloat, alpha: CGFloat)? {
        var red: CGFloat = 0, green: CGFloat = 0, blue: CGFloat = 0, alpha: CGFloat = 0
        guard getRed(&red, green: &green, blue: &blue, alpha: &alpha) else {
            return nil
        }
        return (red, green, blue, alpha)
    }
    var hsb: (hue: CGFloat, saturation: CGFloat, brightness: CGFloat, alpha: CGFloat)? {
        var hue: CGFloat = 0, saturation: CGFloat = 0, brightness: CGFloat = 0, alpha: CGFloat = 0
        guard getHue(&hue, saturation: &saturation, brightness: &brightness, alpha: &alpha) else {
            return nil
        }
        return (hue, saturation, brightness, alpha)
    }
    var hsl: (hue: CGFloat, saturation: CGFloat, lightness: CGFloat, alpha: CGFloat)? {
        guard let rgb = rgb, let hsb = hsb else { return nil }
        let maximum = max(rgb.red, rgb.green, rgb.blue)
        let minimum = min(rgb.red, rgb.green, rgb.blue)
        let range = maximum - minimum
        let lightness = (maximum + minimum) / 2.0
        let saturation = range == 0 ? 0 : range / { return lightness < 0.5 ? lightness * 2 : 2 - (lightness * 2) }()
        return (hsb.hue, saturation, lightness, hsb.alpha)
    }
    convenience init(hue: CGFloat, saturation: CGFloat, lightness: CGFloat , alpha: CGFloat) {
        var saturation = saturation
        let lightness = lightness * 2
        saturation *= lightness <= 1 ? lightness : 2 - lightness
        self.init(hue: hue,
                  saturation: lightness == 0 ? 0 : (2 * saturation) / (lightness + saturation),
                  brightness: (lightness+saturation)/2,
                  alpha: 1)
    }
    convenience init(hexa: String, alpha: Double) {
        self.init(red:   hexa[0..<2].hexaCGFloat / 255,
                  green: hexa[2..<4].hexaCGFloat / 255,
                  blue:  hexa[4..<6].hexaCGFloat / 255,
                  alpha: .init(alpha))
    }
}

游乐场测试

let color = UIColor(hexa: "5fc9f8", alpha: 1)

if let colorHSL = color.hsl {
    let hue = colorHSL.hue
    let saturation = colorHSL.saturation
    let lightness = colorHSL.lightness
    let lighterColor = UIColor(hue: hue,
                               saturation: saturation,
                               lightness: min(lightness * 1.3, 1),
                               alpha: 1)
    let darkerColor = UIColor(hue: hue,
                              saturation: saturation,
                              lightness: max(lightness * 0.5, 0),
                              alpha: 1)
    print("lighterColor:", lighterColor, "darkerColor:", darkerColor)
}
2020-07-07