Find the color partway between two others with lerp(_:t:), for your own blends, chart scales or animations. It takes the other color and how far to go, from 0 (this color) to 1 (the other), and returns a value of the same type:
let start = OKLCHColor(hex: "#00B386") // the travel app's brand color, at hue 166.99
let end = Color.proSky._200.toOKLCH() // Reykjavík's pale sky blue, at hue 230
start.lerp(end, t: 0.5) // OKLCHColor(l: 0.772, c: 0.110, h: 198.5), #4BCACFSteps for a chart or an animation#
Call it with evenly spaced values of t to get a scale of colors between two ends:
let start = OKLCHColor(hex: "#00B386")
let end = Color.proSky._200.toOKLCH()
let scale = (0...4).map { start.lerp(end, t: Double($0) / 4).toColor() }Which space to mix in#
OKLCHColorandLCHColortake the short way around the hue wheel, so the middle keeps its chroma.OKLabColor,LABColor,RGBColorandXYZColormix in a straight line, so the middle can come out grayer. The same pair halfway in OKLab is #64C9C1, where OKLCH gives #4BCACF.
For gradients, use proGradient(), which also keeps colors inside Display P3 and eases between the ends. To mix two tokens and keep dark mode, use blend(with:by:).
How it behaves#
OKLCHColor and LCHColor round t to three decimal places. No type fits the result into Display P3, and alpha is mixed along with the color. Both colors need the same type, so convert one first, as in Color.proSky._200.toOKLCH().
API#
public extension OKLCHColor { func lerp(_ other: OKLCHColor, t: CGFloat) -> OKLCHColor }
public extension OKLabColor { func lerp(_ other: OKLabColor, t: CGFloat) -> OKLabColor }
public extension LCHColor { func lerp(_ other: LCHColor, t: CGFloat) -> LCHColor }
public extension LABColor { func lerp(_ other: LABColor, t: CGFloat) -> LABColor }
public extension RGBColor { func lerp(_ other: RGBColor, t: CGFloat) -> RGBColor }
public extension XYZColor { func lerp(_ other: XYZColor, t: CGFloat) -> XYZColor }| Parameter | Type | What it does |
|---|---|---|
other | same type | The color at t: 1. |
t | CGFloat | How far to go, from 0 (this color) to 1 (other). |
It returns a new value of the same type, t of the way from this color to other.
Sources#
- The ColorSpace folder, where each type's
Interpolationfile defineslerp(_:t:).
See also
- .blend(with:by:) Mix two colors into one that follows dark mode, or fade a color out cleanly.
- .proGradient() Fill cards and buttons with gradients that stay vivid end to end, in light and dark mode.
- .toOKLCH() Read a color's lightness, chroma and hue the way the palette sees them, to compare or adjust it.
- How gradients blend and ease Why plain gradients turn gray, how each blend travels between colors, and where easing puts them.