Wie konvertiere ich ein RGBA-Farbtupel, Beispiel (96, 96, 96, 202), in ein entsprechendes RGB-Farbtupel?
Bearbeiten:
Ich möchte einen RGB-Wert erhalten, der dem RGBA-Tupel auf weißem Hintergrund am ähnlichsten ist.
Wie konvertiere ich ein RGBA-Farbtupel, Beispiel (96, 96, 96, 202), in ein entsprechendes RGB-Farbtupel?
Bearbeiten:
Ich möchte einen RGB-Wert erhalten, der dem RGBA-Tupel auf weißem Hintergrund am ähnlichsten ist.
Antworten:
Ich habe Johannes 'Antwort positiv bewertet, weil er damit Recht hat.
* Es wurden einige Kommentare abgegeben, dass meine ursprüngliche Antwort nicht korrekt war. Es funktionierte, wenn die Alpha-Werte vom Normalen invertiert wurden. Per Definition funktioniert dies jedoch in den meisten Fällen nicht. Ich habe daher die folgende Formel aktualisiert, um für den Normalfall korrekt zu sein. Dies entspricht der Antwort von @ hkurabko unten *
Eine spezifischere Antwort bezieht jedoch den Alpha-Wert in das tatsächliche Farbergebnis ein, basierend auf einer undurchsichtigen Hintergrundfarbe (oder "matt", wie es genannt wird).
Hierfür gibt es einen Algorithmus (über diesen Wikipedia-Link):
Source
.BGColor
Hinweis : Wenn die Hintergrundfarbe ebenfalls transparent ist, müssen Sie den Vorgang zuerst wiederholen (erneut eine Matte auswählen), um das Quell-RGB für diesen Vorgang zu erhalten.Jetzt ist die Konvertierung definiert als (hier im vollständigen Pseudocode!):
Source => Target = (BGColor + Source) =
Target.R = ((1 - Source.A) * BGColor.R) + (Source.A * Source.R)
Target.G = ((1 - Source.A) * BGColor.G) + (Source.A * Source.G)
Target.B = ((1 - Source.A) * BGColor.B) + (Source.A * Source.B)
Um die endgültigen 0-255-Werte für Target
Sie zu erhalten, multiplizieren Sie einfach alle normalisierten Werte mit 255 und stellen Sie sicher, dass Sie 255 begrenzen, wenn einer der kombinierten Werte 1,0 überschreitet (dies ist eine Überbelichtung, und es gibt komplexere Algorithmen, die sich damit befassen die eine Ganzbildverarbeitung usw. beinhalten).
BEARBEITEN: In Ihrer Frage sagten Sie, Sie möchten einen weißen Hintergrund - in diesem Fall korrigieren Sie BGColor einfach auf 255.255.255.
hm ... in Bezug auf
http://en.wikipedia.org/wiki/Alpha_compositing#Alpha_blending
Die von Andras Zoltan bereitgestellte Lösung sollte leicht geändert werden in:
Source => Target = (BGColor + Source) =
Target.R = ((1 - Source.A) * BGColor.R) + (Source.A * Source.R)
Target.G = ((1 - Source.A) * BGColor.G) + (Source.A * Source.G)
Target.B = ((1 - Source.A) * BGColor.B) + (Source.A * Source.B)
Diese geänderte Version funktioniert gut für mich, weil in prev. Version rgba (0,0,0,0) mit mattem rgb (ff, ff, ff) wird in rgb (0,0,0) geändert.
In meinem Fall wollte ich ein RGBA-Image in RGB konvertieren und Folgendes funktionierte wie erwartet:
rgbImage = cv2.cvtColor(npimage, cv2.COLOR_RGBA2RGB)
Dies hängt vom verwendeten Farbraum ab. Wenn sich die RGBA im vormultiplizierten Farbraum befindet und halbtransparent ist, müssen Sie Alpha teilen, um die richtige RGB-Farbe zu erhalten. Wenn sich die Farbe im nicht vormultiplizierten Farbraum befindet, können Sie den Alphakanal einfach verwerfen.
Hier ist eine praktische SASS-Funktion gemäß den Antworten von Andras und hkurabko.
@function rgba_blend($fore, $back) {
$ored: ((1 - alpha($fore)) * red($back) ) + (alpha($fore) * red($fore));
$ogreen: ((1 - alpha($fore)) * green($back) ) + (alpha($fore) * green($fore));
$oblue: ((1 - alpha($fore)) * blue($back) ) + (alpha($fore) * blue($fore));
@return rgb($ored, $ogreen, $oblue);
}
Verwendung:
$my_color: rgba(red, 0.5); // build a color with alpha for below
#a_div {
background-color: rgba_blend($my_color, white);
}
mix($color, white, $alpha*100)
Hier ist ein Java-Code (funktioniert mit Android API 24):
//int rgb_background = Color.parseColor("#ffffff"); //white background
//int rgba_color = Color.parseColor("#8a000000"); //textViewColor
int defaultTextViewColor = textView.getTextColors().getDefaultColor();
int argb = defaultTextViewColor;
int alpha = 0xFF & (argb >> 24);
int red = 0xFF & (argb >> 16);
int green = 0xFF & (argb >> 8);
int blue = 0xFF & (argb >> 0);
float alphaFloat = (float)alpha / 255;
String colorStr = rgbaToRGB(255, 255, 255, red, green, blue, alphaFloat);
Funktion:
protected String rgbaToRGB(int rgb_background_red, int rgb_background_green, int rgb_background_blue,
int rgba_color_red, int rgba_color_green, int rgba_color_blue, float alpha) {
float red = (1 - alpha) * rgb_background_red + alpha * rgba_color_red;
float green = (1 - alpha) * rgb_background_green + alpha * rgba_color_green;
float blue = (1 - alpha) * rgb_background_blue + alpha * rgba_color_blue;
String redStr = Integer.toHexString((int) red);
String greenStr = Integer.toHexString((int) green);
String blueStr = Integer.toHexString((int) blue);
String colorHex = "#" + redStr + greenStr + blueStr;
//return Color.parseColor(colorHex);
return colorHex;
}