vds_ios/VDS/Extensions/UIColor.swift
Matt Bruce 54abcf8c8d added comments to the UIColor extension
Signed-off-by: Matt Bruce <matt.bruce@verizon.com>
2023-05-26 16:45:03 -05:00

196 lines
7.5 KiB
Swift

//
// UIColor.swift
// VDS
//
// Created by Matt Bruce on 7/22/22.
//
import Foundation
import UIKit
import VDSColorTokens
extension UIColor {
//--------------------------------------------------
// MARK: - Functions
//--------------------------------------------------
/// Convenience to get a grayscale UIColor where the same value is used for red, green, and blue
/// - Parameters:
/// - rgb: red, green, and blue
/// - alpha: alphay
/// - Returns: UIColor that will be grayscale
public class func grayscale(rgb: Int, alpha: CGFloat = 1.0) -> UIColor {
let grayscale = CGFloat(rgb) / 255.0
return UIColor(red: grayscale, green: grayscale, blue: grayscale, alpha: alpha)
}
/// Convenience to get an 8-Bit UIColor based on RGB values
/// - Parameters:
/// - red: Value for Red
/// - green: Value for Green
/// - blue: Value for Blue
/// - alpha: Value for Alpha
/// - Returns: UIColor for the values above
public class func color8Bits(red: Int, green: Int, blue: Int, alpha: CGFloat = 1.0) -> UIColor {
return UIColor(red: CGFloat(red) / 255.0, green: CGFloat(green) / 255.0, blue: CGFloat(blue) / 255.0, alpha: alpha)
}
/// Convenience to get an UIColor based on RGB values
/// - Parameters:
/// - red: Value for Red
/// - green: Value for Green
/// - blue: Value for Blue
/// - alpha: Value for Alpha
/// - Returns: UIColor for the values above
public class func color8Bits(red: CGFloat, green: CGFloat, blue: CGFloat, alpha: CGFloat = 1.0) -> UIColor {
return UIColor(red: red / 255.0, green: green / 255.0, blue: blue / 255.0, alpha: alpha)
}
/// Gets UIColor via an 8 digit hex string.
/// - Parameters:
/// - hex: HexCode string
/// - Returns: UIColor for the values above
public class func getColorBy(hex: String) -> UIColor {
var hexint: UInt64 = 0
let scanner = Scanner(string: hex)
scanner.charactersToBeSkipped = CharacterSet(charactersIn: "#")
scanner.scanHexInt64(&hexint)
return UIColor(red: (CGFloat((hexint & 0xFF0000) >> 16)) / 255,
green: (CGFloat((hexint & 0xFF00) >> 8)) / 255,
blue: (CGFloat(hexint & 0xFF)) / 255,
alpha: 1)
}
/// Gets UIColor via an 8 digit hex string that includes transparency.
/// - Parameters:
/// - hex: HexCode string
/// - Returns: UIColor for the values above
public class func getColorWithTransparencyBy(hex: String) -> UIColor {
var hexint: UInt64 = 0
let scanner = Scanner(string: hex)
scanner.charactersToBeSkipped = CharacterSet(charactersIn: "#")
scanner.scanHexInt64(&hexint)
return UIColor(red: (CGFloat((hexint & 0xFF000000) >> 24)) / 255,
green: (CGFloat((hexint & 0xFF0000) >> 16)) / 255,
blue: (CGFloat((hexint & 0xFF00) >> 8)) / 255,
alpha: (CGFloat(hexint & 0xFF)) / 255)
}
/// Generates a gradient color for the color passed in
/// - Parameter color: Primary color for the gradient
/// - Returns: UIColor that is gradient
public class func gradientColor(_ color: UIColor?) -> UIColor {
var h: CGFloat = 0
var s: CGFloat = 0
var b: CGFloat = 0
var a: CGFloat = 0
if color?.getHue(&h, saturation: &s, brightness: &b, alpha: &a) ?? false {
return UIColor(hue: h, saturation: max(s - 0.17, 0.0), brightness: min(b - 0.03, 1.0), alpha: a)
}
return .white
}
/// Gets the hex code value for a UIColor
/// - Parameter color: UIColor intended to retrieve its hex value
/// - Returns: Hex Code
public class func hexString(for color: UIColor) -> String? {
guard let components = color.cgColor.components else { return nil }
let numberOfComponents = color.cgColor.numberOfComponents
if numberOfComponents >= 3 {
// RGB color space
let r = Int(CGFloat(components[0]) * 255)
let g = Int(CGFloat(components[1]) * 255)
let b = Int(CGFloat(components[2]) * 255)
// If alpha of color is less than 1.0 then alpha hex is relevant.
if color.cgColor.numberOfComponents == 4 && components[3] < 1.0 {
let a = Int(CGFloat(components[3]) * 255)
return String(format: "%02X%02X%02X%02X", r, g, b, a)
}
return String(format: "%02X%02X%02X", r, g, b)
} else if numberOfComponents == 2 {
// Monochromatic color space
let value = Int(CGFloat(components[0]) * 255)
// If alpha of color is less than 1.0 then alpha hex is relevant.
if components[1] < 1.0 {
let alpha = Int(CGFloat(components[1]) * 255)
return String(format: "%02X%02X%02X%02X", value, value, value, alpha)
}
return String(format: "%02X%02X%02X", value, value, value)
}
return nil
}
/// Gets the hex code value for the current UIColor
/// - Returns: Hex Code string
public var hexString: String? {
guard let components = cgColor.components else { return nil }
let numberOfComponents = cgColor.numberOfComponents
if numberOfComponents >= 3 {
// RGB color space
let r = Int(CGFloat(components[0]) * 255)
let g = Int(CGFloat(components[1]) * 255)
let b = Int(CGFloat(components[2]) * 255)
// If alpha of color is less than 1.0 then alpha hex is relevant.
if cgColor.numberOfComponents == 4 && components[3] < 1.0 {
let a = Int(CGFloat(components[3]) * 255)
return String(format: "%02X%02X%02X%02X", r, g, b, a)
}
return String(format: "%02X%02X%02X", r, g, b)
} else if numberOfComponents == 2 {
// Monochromatic color space
let value = Int(CGFloat(components[0]) * 255)
// If alpha of color is less than 1.0 then alpha hex is relevant.
if components[1] < 1.0 {
let alpha = Int(CGFloat(components[1]) * 255)
return String(format: "%02X%02X%02X%02X", value, value, value, alpha)
}
return String(format: "%02X%02X%02X", value, value, value)
}
return nil
}
/// Initialize a UIColor with a HexCode string
/// - Parameter hexString: HexCode string to convert to a UIColor
public convenience init(hexString: String) {
let hex = hexString.trimmingCharacters(in: CharacterSet.alphanumerics.inverted)
var int = UInt64()
Scanner(string: hex).scanHexInt64(&int)
let a, r, g, b: UInt64
switch hex.count {
case 3: // RGB (12-bit)
(a, r, g, b) = (255, (int >> 8) * 17, (int >> 4 & 0xF) * 17, (int & 0xF) * 17)
case 6: // RGB (24-bit)
(a, r, g, b) = (255, int >> 16, int >> 8 & 0xFF, int & 0xFF)
case 8: // ARGB (32-bit)
(a, r, g, b) = (int >> 24, int >> 16 & 0xFF, int >> 8 & 0xFF, int & 0xFF)
default:
(a, r, g, b) = (255, 0, 0, 0)
}
self.init(red: CGFloat(r) / 255, green: CGFloat(g) / 255, blue: CGFloat(b) / 255, alpha: CGFloat(a) / 255)
}
}