Regenbogenfarben

Realmac Software hat es mit Clear vorgemacht. Regenbogenfarben, auch wenn sie davon nur einen kleinen Ausschnitt benutzen, sind toll und können etwas hermachen. Aber wie kann man solche Farben anständig berechnen? Schließlich kann man ja nicht für jede (theoretisch beliebig viele) Tabellenzelle die Farbe per Hand festlegen. Auch hier hilft Mathe!

Download

Folgende Anleitung ist zu Objective-C übertragen von Jim Bumgardners Anleitung für Javascript.

Beginnen wir mit einer einfachen Sinuswelle. Bei folgendem Code-Schnipsel wird in jedem Durchlauf der Schleife ein Grauwert als Farbe ermittelt. Diese Werte

Schwarzweißer Regenbogen
float frequency = .3;
int amplitude = 127;
int center = 128;
for (int i = 0; i < 32; i++)
{
float c = sin(frequency*i) * amplitude + center;
UIColor *color = [UIColor colorWithRed:c green:c blue:c alpha:1.0];
}

Nehmen wir nun für Rot, Grün und Blau jeweils einen anderen Wert, sondern verschieben ihn im Einheitskreis auch so, dass sie ein Dreieck bilden, so bekommen wir einen Regenbogen.

Schwarzweißer Regenbogen
float frequency = .3;
int amplitude = 127;
int center = 128;
for (int i = 0; i < 32; i++)
{
float r = sin(frequency*i) * amplitude + center;
float g = sin(frequency*i+2.0*M_PI/3.0) * amplitude + center;
float b = sin(frequency*i+4.0*M_PI/3.0) * amplitude + center;
UIColor *color = [UIColor colorWithRed:r green:g blue:b alpha:1.0];
}

Das ganze in eine Klasse gepackt und um einige Parameter verfeinert schaut das ganze dann so aus:

Schwarzweißer Regenbogen
// BRColorCircle.h
#import <UIKit/UIKit.h>
@interface BRColorCircle : NSObject
+ (UIColor*)colorWithFrequency:(float)frequency phaseShift:(float)phaseShift andLightness:(float)lightness;
@end
// BRColorCircle.m
#import "BRColorCircle.h"
@implementation BRColorCircle
+ (UIColor*)colorWithFrequency:(float)frequency phaseShift:(float)phaseShift andLightness:(float)lightness{
float center = 100.0/255.0;
float width = 155.0/255.0;
float red = (sin(frequency*phaseShift+0.0)*width+center)*lightness;
float green = (sin(frequency*phaseShift+2.0*M_PI/3.0)*width+center)*lightness;
float blue = (sin(frequency*phaseShift+4.0*M_PI/3.0)*width+center)*lightness;
return [UIColor colorWithRed:red green:green blue:blue alpha:1.0];
}
@end

Somit haben wir die Frequenz, die Rotation im Farbkreis und die Helligkeit als Parameter. In einer kleinen Test-UITableView berechne ich dann die Farben für die Zellen und für einen CAGradientLayer als Hintergrund hinzu.

UITableView Cell in bunt
int ci = indexPath.row;
float f = 0.03; // Frequenz
float s = 1.8; // Phasen-Shift
float i = 0.8; // Helligkeit
[cell
addGradientBackgroundFromColor:
[BRColorCircle
colorWithFrequency:f
phaseShift:ci+s/f
andLightness:i]
toColor:
[BRColorCircle
colorWithFrequency:f
phaseShift:ci+s/f
andLightness:i-0.05]
];

Varianten


s = 1.5, f = 0.08, ci = -indexPath.row

s = 0.0, f = 0.2, ci = -indexPath.row