Transparente Pixel berechnen

Übersicht BlitzMax, BlitzMax NG Allgemein

Neue Antwort erstellen

Der Eisvogel

Betreff: Transparente Pixel berechnen

BeitragFr, Nov 26, 2010 22:21
Antworten mit Zitat
Benutzer-Profile anzeigen
Hallo
Ich habe derzeit das Problem, dass ich 2 Pixmaps habe, die ich übereinander legen will, dafür verwenden ich 2 For-Next-Schleifen, die jeweils Read- und WritePixel aufrufen. Jetzt das Problem: Wenn der Pixel des darüberzulegenden Pixmaps Teil-Transparent ist, oder auch komplett Transparent ist, dann wird es dennoch im unteren Pixmap übermalt, und ich erhalte zum Schluss nur das obere Pixmap. Also muss ich die Pixeldaten des unteren und oberen Pixmaps irgendwie zusammenrechnen im Bezug auf die Transparenz, dabei sollte allerdings auch die Quantität des Alpha-Channels bewahrst werden, was heißt dass wenn ich 2 mal 50% Transparenz habe, dass es trotzdem zum Schluss noch Tranzparent ist. Ich habe aber leider keinerlei Ansatz, wie ich die Pixel-Daten zusammenrechnen kann. Weiß jemand von euch wie das geht, oder kann mir eine Erklärung im Internet zeigen?

MfG
Der Eisvogel
Ungarische Notation kann nützlich sein.
BlitzMax ; Blitz3D
Win 7 Pro 64 Bit ; Intel Core i7-860 ; 8 GB Ram ; ATI HD 5750 1 GB
Projekte: Window-Crasher
Ich liebe es mit der WinAPI zu spielen.

BladeRunner

Moderator

BeitragFr, Nov 26, 2010 22:27
Antworten mit Zitat
Benutzer-Profile anzeigen
für A R G B gilt:
(A1 +a2)/2 = benötigter Wert.
Zu Diensten, Bürger.
Intel T2300, 2.5GB DDR 533, Mobility Radeon X1600 Win XP Home SP3
Intel T8400, 4GB DDR3, Nvidia GF9700M GTS Win 7/64
B3D BMax MaxGUI

Stolzer Gewinner des BAC#48, #52 & #92

Der Eisvogel

BeitragFr, Nov 26, 2010 22:38
Antworten mit Zitat
Benutzer-Profile anzeigen
Danke, aber das versteh ich nicht ganz. Meinst du damit folgendes:
Code: [AUSKLAPPEN]
(A1 +a2)/2 = NewA
(R1 +r2)/2 = NewR
(G1 +g2)/2 = NewG
(B1 +b2)/2 = NewB


Dann wäre es immer nur 50% Alpha. Ich bin zu doof das richtig zu interpretieren. Sorry.
Ungarische Notation kann nützlich sein.
BlitzMax ; Blitz3D
Win 7 Pro 64 Bit ; Intel Core i7-860 ; 8 GB Ram ; ATI HD 5750 1 GB
Projekte: Window-Crasher
Ich liebe es mit der WinAPI zu spielen.

Xeres

Moderator

BeitragFr, Nov 26, 2010 22:41
Antworten mit Zitat
Benutzer-Profile anzeigen
Das ist einfach der Mittelwert jeder Komponente... Taschenrechner oder ausprobieren zeigt dir ja, was dabei raus kommt.
Win10 Prof.(x64)/Ubuntu 16.04|CPU 4x3Ghz (Intel i5-4590S)|RAM 8 GB|GeForce GTX 960
Wie man Fragen richtig stellt || "Es geht nicht" || Video-Tutorial: Sinus & Cosinus
T
HERE IS NO FAIR. THERE IS NO JUSTICE. THERE IS JUST ME. (Death, Discworld)

Der Eisvogel

BeitragFr, Nov 26, 2010 22:44
Antworten mit Zitat
Benutzer-Profile anzeigen
Ja, das meine ich ja, es ist immer der Mittelwert, aber was wenn ich 10%, 20% oder 30% Alpha habe? Das muss doch irgendwie im Bezug auf den Alpha-Channel berechnet werden, oder?

EDIT: Und wenn der Alpha-Channel des oberen Pixmaps 0 ist, dann bleibt der Alpha-Channel des unteren gleich, und wird nicht kleiner, aber das kann ja so nicht funktionieren.
Ungarische Notation kann nützlich sein.
BlitzMax ; Blitz3D
Win 7 Pro 64 Bit ; Intel Core i7-860 ; 8 GB Ram ; ATI HD 5750 1 GB
Projekte: Window-Crasher
Ich liebe es mit der WinAPI zu spielen.

mpmxyz

BeitragFr, Nov 26, 2010 22:49
Antworten mit Zitat
Benutzer-Profile anzeigen
Ich beziehe mich jetzt auf Alphawerte von 0 bis 1:
Um die Formeln zu erhalten, sollte man sich vorstellen, wie die Farbe der Hintergrundpixel mit den Bildern kombiniert wird.
Die Hintergrundfarbe sei H.
Die Durchlässigkeit eines Pixels entspricht 1-Alpha des Pixels.
H wird zuerst zusammen mit dem unteren Bild, dem Bild 1, vermischt:
Code: [AUSKLAPPEN]
Zwischenergebnis=H*(1-Alpha1)+Farbe1*Alpha1

Nun wird diese Farbe mit dem zweiten Bild kombiniert:
Code: [AUSKLAPPEN]
Endergebnis=(H*(1-Alpha1)+Farbe1*Alpha1)*(1-Alpha2)+Farbe2*Alpha2
=H*(1-Alpha1)*(1-Alpha2)+Farbe1*Alpha1*(1-Alpha2)+Farbe2*Alpha2
=H*(1-Alpha1)*(1-Alpha2)+(1-(1-Alpha1)*(1-Alpha2))*[(Farbe1*Alpha1*(1-Alpha2)+Farbe2*Alpha2)/(1-(1-Alpha1)*(1-Alpha2))]

Aus dieser Gleichung lassen sich die Formeln für die Farbe und den Alphawert der Kombination entnehmen:
Code: [AUSKLAPPEN]
Alpha=(1-(1-Alpha1)*(1-Alpha2))
Farbe=(Farbe1*Alpha1*(1-Alpha2)+Farbe2*Alpha2)/(1-(1-Alpha1)*(1-Alpha2))


Achtung: Wenn Alpha 0 ist, lässt sich durch die Division durch 0 kein eindeutiger Wert für die Farbe bestimmen! Man kann ihn hier stattdessen frei wählen.

Die richtige Lösung ist also etwas komplizierter als ein einfacher Mittelwert. Wink
mfG
mpmxyz
Edit: Bei meinem Ansatz geht es darum, dass das nacheinander abfolgende Zeichnen der zwei Pixmaps durch das Zeichnen einer Pixmap ersetzt wird.
Moin Moin!
Projekte: DBPC CodeCruncher Mandelbrot-Renderer
  • Zuletzt bearbeitet von mpmxyz am Fr, Nov 26, 2010 22:55, insgesamt einmal bearbeitet

Xeres

Moderator

BeitragFr, Nov 26, 2010 22:52
Antworten mit Zitat
Benutzer-Profile anzeigen
"nicht funktionieren" ist hier - wie immer - keine gute Beschreibung.
Möchtest du den kleineren oder den größeren Alphawert? Dann benutzte die Funktionen Min bzw. Max.
Kommt halt darauf an, was für ein Ergebnis dir vorschwebt.
Win10 Prof.(x64)/Ubuntu 16.04|CPU 4x3Ghz (Intel i5-4590S)|RAM 8 GB|GeForce GTX 960
Wie man Fragen richtig stellt || "Es geht nicht" || Video-Tutorial: Sinus & Cosinus
T
HERE IS NO FAIR. THERE IS NO JUSTICE. THERE IS JUST ME. (Death, Discworld)

Der Eisvogel

BeitragFr, Nov 26, 2010 23:00
Antworten mit Zitat
Benutzer-Profile anzeigen
Mir schwebt das vor, was durch DrawImage img1 und DrawImage img2 gemalt werden würde. Nur das ich es in den Pixmaps direkt brache, also muss ich es selber berechnen.

@mpmxyz: Danke, dass schaut schonmal kompliziert aus, so wie ich es mir vorgestellt hatte, aber irgendetwas geht immernoch schief. Die Stellen, an den das obere Pixmap nicht tranzparent ist, werden jetzt einfach Schwarz dargestellt. Hier mein Berechnungs-Code:
BlitzMax: [AUSKLAPPEN]
Local argb1:Int = ReadPixel(dst, x, y)
Local argb2:Int = ReadPixel(src, x, y)
Local a1:Int, r1:Int, g1:Int, b1:Int
Local a2:Int, r2:Int, g2:Int, b2:Int

a1 = (argb1 Shr 24) & $FF
r1 = (argb1 Shr 16) & $FF
g1 = (argb1 Shr 8) & $FF
b1 = argb1 & $FF

a2 = (argb2 Shr 24) & $FF
r2 = (argb2 Shr 16) & $FF
g2 = (argb2 Shr 8) & $FF
b2 = argb2 & $FF

Local a:Int, r:Int, g:Int, b:Int

a = (1 - (1 - a1) * (1 - a2))
If a > 0 Then
r = (r1 * a1 * (1 - a2) + r2 * a2) / a
g = (g1 * a1 * (1 - a2) + g2 * a2) / a
b = (b1 * a1 * (1 - a2) + b2 * a2) / a
EndIf

Local argb:Int = (a Shl 24) | (r Shl 16) | (g Shl 8) | b

WritePixel(dst, dx + x, dy + y, argb)
Ungarische Notation kann nützlich sein.
BlitzMax ; Blitz3D
Win 7 Pro 64 Bit ; Intel Core i7-860 ; 8 GB Ram ; ATI HD 5750 1 GB
Projekte: Window-Crasher
Ich liebe es mit der WinAPI zu spielen.

mpmxyz

BeitragFr, Nov 26, 2010 23:03
Antworten mit Zitat
Benutzer-Profile anzeigen
Hast du meine Aussage über den Wertebereich der Alphas beachtet?
Ich ging von Gleitkommazahlen mit einem Wert von 0 bis 1 aus. (Teile die Alphawerte durch 255.0!)
mfG
mpmxyz
Moin Moin!
Projekte: DBPC CodeCruncher Mandelbrot-Renderer

Der Eisvogel

BeitragFr, Nov 26, 2010 23:08
Antworten mit Zitat
Benutzer-Profile anzeigen
Ah, Sorry. Habs auch grad gesehen. Ich habe andere Stellen in meinem Code, wo Alpha schon von 0-1 ist. Hab vergessen, dass es hier noch nicht der Fall war.
Vielen Dank mpmxyz, jetzt funktioniert es perfekt. Ich habe mein Ziel erreicht. DANKE!

MfG
Der Eisvogel
Ungarische Notation kann nützlich sein.
BlitzMax ; Blitz3D
Win 7 Pro 64 Bit ; Intel Core i7-860 ; 8 GB Ram ; ATI HD 5750 1 GB
Projekte: Window-Crasher
Ich liebe es mit der WinAPI zu spielen.

BladeRunner

Moderator

BeitragSa, Nov 27, 2010 9:10
Antworten mit Zitat
Benutzer-Profile anzeigen
Solange alpha mit einer Werteskala von 0-255 gespeichert ist (wie in Pixmaps ja so üblich) ist die Mittelwerttbildung wohl der einfache und richtige Ansatz.
Hast Du ein Bild mit 30 Alpha und eines mit 190 und addierst die beiden Pixel an dieser Stelle hat das Ergebnis eine Transparenz von (30+190) / 2 , also 110, was absolut korrekt ist.
Anders sieht es nur aus wenn man eben nicht eine Gesamttransparenz erhalten will sondern die Farbwerte entsprechend der Transparenz addieren möchte. Dann sollte aber auch die Beschreibung aussagekräftiger sein Wink
Zu Diensten, Bürger.
Intel T2300, 2.5GB DDR 533, Mobility Radeon X1600 Win XP Home SP3
Intel T8400, 4GB DDR3, Nvidia GF9700M GTS Win 7/64
B3D BMax MaxGUI

Stolzer Gewinner des BAC#48, #52 & #92

Der Eisvogel

BeitragSa, Nov 27, 2010 12:59
Antworten mit Zitat
Benutzer-Profile anzeigen
Ich hatte doch eigentlich gesagt, dass ich ein Pixmap über das andere Legen wollte. Sorry wenn das nicht richtig rüberkam, aber ich hab ja jetzt meine Lösung. Danke.

MfG
Der Eisvogel
Ungarische Notation kann nützlich sein.
BlitzMax ; Blitz3D
Win 7 Pro 64 Bit ; Intel Core i7-860 ; 8 GB Ram ; ATI HD 5750 1 GB
Projekte: Window-Crasher
Ich liebe es mit der WinAPI zu spielen.

Neue Antwort erstellen


Übersicht BlitzMax, BlitzMax NG Allgemein

Gehe zu:

Powered by phpBB © 2001 - 2006, phpBB Group