Интерполяция цветов градиента (как с NSGradient) на iOS?

AppKit недоступен в iOS, поэтому я искал замену.

В частности, я искал метод замены для:

- (NSColor *)interpolatedColorAtLocation: (CGFloat)location

Мне нужен способ определить градиент и найти значение цвета на основе входного местоположения (float).


person Rahul Iyer    schedule 02.12.2013    source источник


Ответы (2)


Если вам действительно нужен объект градиента (для рисования градиента?), вы можете использовать уровень CG CGGradient "класс".

Что касается интерполяции цвета в определенном месте градиента, все, что вам нужно знать, это два окружающих цвета (относительно вашего заданного местоположения) и интерполяция между ними (тогда t будет местоположением между 0.0..1.0 относительно двух цветов, а не весь градиент):

- (UIColor *)colorByInterpolatingWith:(UIColor *)color factor:(CGFloat)factor {
    factor = MIN(MAX(t, 0.0), 1.0);

    const CGFloat *startComponent = CGColorGetComponents(self.CGColor);
    const CGFloat *endComponent = CGColorGetComponents(color.CGColor);

    float startAlpha = CGColorGetAlpha(self.CGColor);
    float endAlpha = CGColorGetAlpha(color.CGColor);

    float r = startComponent[0] + (endComponent[0] - startComponent[0]) * factor;
    float g = startComponent[1] + (endComponent[1] - startComponent[1]) * factor;
    float b = startComponent[2] + (endComponent[2] - startComponent[2]) * factor;
    float a = startAlpha + (endAlpha - startAlpha) * factor;

    return [UIColor colorWithRed:r green:g blue:b alpha:a];
}

Пример использования:

UIColor *purpleColor = [[UIColor redColor] colorByInterpolatingWith:[UIColor blueColor] factor:0.5];
person Regexident    schedule 02.12.2013
comment
Не стесняйтесь портировать stackoverflow.com/a/45268258/5389500 на iOS ^^ - person Sentry.co; 23.07.2017

Быстрая версия (macOS)

Эта цветовая интерполяция может быть достигнута с помощью простой строки:

let color = NSColor.green.interpolate(.blue, 0.5)

Добавьте это расширение в свой проект:

   extension NSColor{
    /**
     * Interpolates between two NSColors
     * EXAMPLE: NSColor.green.interpolate(.blue, 0.5)
     * NOTE: There is also a native alternative: NSColor.green.blended(withFraction: 0.5, of: .blue)
     */
    func interpolate(_ to:NSColor,_ scalar:CGFloat)->NSColor{
        func interpolate(_ start:CGFloat,_ end:CGFloat,_ scalar:CGFloat)->CGFloat{
            return start + (end - start) * scalar
        }
        let fromRGBColor:NSColor = self.usingColorSpace(.genericRGB)!
        let toRGBColor:NSColor = to.usingColorSpace(.genericRGB)!
        let red:CGFloat = interpolate(fromRGBColor.redComponent, toRGBColor.redComponent,scalar)
        let green:CGFloat = interpolate(fromRGBColor.greenComponent, toRGBColor.greenComponent,scalar)
        let blue:CGFloat = interpolate(fromRGBColor.blueComponent, toRGBColor.blueComponent,scalar)
        let alpha:CGFloat = interpolate(fromRGBColor.alphaComponent, toRGBColor.alphaComponent,scalar)
        return NSColor.init(red: red, green: green, blue: blue, alpha: alpha)
    }
}

Анимация ниже была получена с помощью этого расширения и AnimLib.

введите здесь описание изображения

person Sentry.co    schedule 23.07.2017