AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

Geht das noch schneller? - Bitmap-Verrechnung

Ein Thema von Harry Stahl · begonnen am 22. Nov 2014 · letzter Beitrag vom 5. Jan 2015
Antwort Antwort
Seite 1 von 2  1 2      
Benutzerbild von Harry Stahl
Harry Stahl

Registriert seit: 2. Apr 2004
Ort: Bonn
2.479 Beiträge
 
Delphi 11 Alexandria
 
#1

Geht das noch schneller? - Bitmap-Verrechnung

  Alt 22. Nov 2014, 02:00
Mit dieser Funktion wird eine 32-Bitmap - unter Berücksichtigung der Transparenz auf einen Konstanten Untergrund (die Hintergrund-Bitmap) gemalt.

Mal abgesehen von Parallel-Berechnung mit TParallel (was ich schon erledigt habe, hier die einfache Version, um die Funktion leichter nachvollziehen zu können), kann man das noch irgendwie schneller berechnen?

Delphi-Quellcode:
// Setz vorraus, dass die Bitmaps die gleiche Größe haben!!!
procedure Draw32BitToBitmapold(const BitOben: TBitmap; BitUnten: TBitmap);
var
  h,w,i: Integer;
  RGBA_Unten, RGBA_Oben: pRGBALine;
begin
  For h := 0 to BitUnten.Height-1 do begin
    RGBA_Unten := BitUnten.ScanLine[h];
    RGBA_Oben := BitOben.ScanLine[h];

    For w:= 0 to BitUnten.Width-1 do begin
      if RGBA_Oben^[w].rgbReserved = 0 then begin
        // unten bleibt
      end else begin
        i := Round (RGBA_Unten^[w].rgbBlue - ((RGBA_Unten^[w].rgbBlue - RGBA_Oben^[w].rgbBlue) / 255 * RGBA_Oben^[w].rgbReserved));
        if i < 0 then RGBA_Unten^[w].rgbBlue := 0 else if i > 255 then RGBA_Unten^[w].rgbBlue := 255 else RGBA_Unten^[w].rgbBlue := i;

        i := Round (RGBA_Unten^[w].rgbGreen - ((RGBA_Unten^[w].rgbGreen - RGBA_Oben^[w].rgbGreen) / 255 * RGBA_Oben^[w].rgbReserved));
        if i < 0 then RGBA_Unten^[w].rgbGreen := 0 else if i > 255 then RGBA_Unten^[w].rgbGreen := 255 else RGBA_Unten^[w].rgbGreen := i;

        i := Round (RGBA_Unten^[w].rgbRed - ((RGBA_Unten^[w].rgbRed - RGBA_Oben^[w].rgbRed) / 255 * RGBA_Oben^[w].rgbReserved));
        if i < 0 then RGBA_Unten^[w].rgbRed := 0 else if i > 255 then RGBA_Unten^[w].rgbRed := 255 else RGBA_Unten^[w].rgbRed := i;

        RGBA_Unten^[w].rgbReserved := 255;
      end;
   end;
  end;
end;
  Mit Zitat antworten Zitat
hstreicher

Registriert seit: 21. Nov 2009
220 Beiträge
 
Delphi 10.2 Tokyo Professional
 
#2

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 22. Nov 2014, 08:21
schneller wird es wenn man die Formeln umbau so dass mit Integer anstatt Floats gerechnet wird,

und die geschachtelten Abfragen so umstellen dass das wahrscheinlich häuftigste Ergebnis zuerst abgeprüft wird
um den 2. Vergleich zu vermeiden
  Mit Zitat antworten Zitat
Benutzerbild von Harry Stahl
Harry Stahl

Registriert seit: 2. Apr 2004
Ort: Bonn
2.479 Beiträge
 
Delphi 11 Alexandria
 
#3

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 22. Nov 2014, 08:52
Mhh, wenn ich integer verwende, wird es ungenau. Aber wäre vielleicht akeptabel, wenn es nur um Anzeige eines Ergebnisses geht ( im Unterschied zu einem konkret weiterverwendbaren Ergebnis).

Das wahrscheinlichste Ergebis ist, dass der Wert zwischen 0 und 255 liegt, aber das muss ich zuvor durch Überprüfung sicherstellen, komme da also nicht dran vorbei...
  Mit Zitat antworten Zitat
Benutzerbild von Bernhard Geyer
Bernhard Geyer

Registriert seit: 13. Aug 2002
17.171 Beiträge
 
Delphi 10.4 Sydney
 
#4

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 22. Nov 2014, 09:10
Hast du eigentlich schon mal mit AQTime geprüft?

Ich vermute wenn du für RGBA_Unten^[w] und Co. Lokale Variablen verwendest wird es auch schneller
Windows Vista - Eine neue Erfahrung in Fehlern.
  Mit Zitat antworten Zitat
Benutzerbild von himitsu
himitsu

Registriert seit: 11. Okt 2003
Ort: Elbflorenz
43.199 Beiträge
 
Delphi 12 Athens
 
#5

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 22. Nov 2014, 09:38
Parallele Berechnung mehrerer Bytes = Streaming-Funktionen ala 3DNow!, MMX, SSE, AVX, FMA

Da kann man "gleichzeitig", in einem Thread, mit 128 Bit (z.B. 8 Byte) oder gar 256 Bit rechnen, also mit mindestens 2 Color-Dingern (a 4 Bytes) in einem Rutsch.
Garbage Collector ... Delphianer erzeugen keinen Müll, also brauchen sie auch keinen Müllsucher.
my Delphi wish list : BugReports/FeatureRequests

Geändert von himitsu (22. Nov 2014 um 09:59 Uhr)
  Mit Zitat antworten Zitat
Benutzerbild von Harry Stahl
Harry Stahl

Registriert seit: 2. Apr 2004
Ort: Bonn
2.479 Beiträge
 
Delphi 11 Alexandria
 
#6

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 22. Nov 2014, 10:37
@ Berhard: Klar, AQTime (Prof) ist mein ständiger Begleiter.

Lokale Variablen zu verwenden, bringt im vorliegenden Fall leider nichts, weil die Zuweisung an die lokalen Variablen in der Summe länger braucht (ca. 30%), als der Zugriff auf den Speicher:

Delphi-Quellcode:
procedure Draw32BitToBitmapNew(const BitOben: TBitmap; BitUnten: TBitmap);
var
   h,w,i: Integer;
   rublue, rugreen, rured, rureserved,
   roblue, rogreen, rored, roreserved: Byte;
   RGBA_Unten, RGBA_Oben: pRGBALine;
begin
   For h := 0 to BitUnten.Height-1 do begin
     RGBA_Unten := BitUnten.ScanLine[h];
     RGBA_Oben := BitOben.ScanLine[h];

     For w:= 0 to BitUnten.Width-1 do begin
       if RGBA_Oben^[w].rgbReserved = 0 then begin
         // unten bleibt
       end else begin
         rublue := RGBA_Unten^[w].rgbBlue;
         rugreen := RGBA_Unten^[w].rgbGreen;
         rured := RGBA_Unten^[w].rgbred;
         rureserved := RGBA_Unten^[w].rgbreserved;

         roblue := RGBA_Oben^[w].rgbBlue;
         rogreen := RGBA_Oben^[w].rgbGreen;
         rored := RGBA_Oben^[w].rgbred;
         roreserved := RGBA_Oben^[w].rgbreserved;

         i := Round (ruBlue - ((ruBlue - roBlue) / 255 * roReserved));
         if i < 0 then RGBA_Unten^[w].rgbBlue := 0 else if i > 255 then RGBA_Unten^[w].rgbBlue := 255 else RGBA_Unten^[w].rgbBlue := i;

         i := Round (ruGreen - ((ruGreen - roGreen) / 255 * roReserved));
         if i < 0 then RGBA_Unten^[w].rgbGreen := 0 else if i > 255 then RGBA_Unten^[w].rgbGreen := 255 else RGBA_Unten^[w].rgbGreen := i;

         i := Round (ruRed - ((ruRed - roRed) / 255 * roReserved));
         if i < 0 then RGBA_Unten^[w].rgbRed := 0 else if i > 255 then RGBA_Unten^[w].rgbRed := 255 else RGBA_Unten^[w].rgbRed := i;

         RGBA_Unten^[w].rgbReserved := 255;
       end;
    end;
   end;
end;
  Mit Zitat antworten Zitat
mensch72

Registriert seit: 6. Feb 2008
838 Beiträge
 
#7

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 22. Nov 2014, 10:51
man nehme einfach "MULDIV" für solche Berechnungen in Integer ohne Genauigkeitsverlust.

aus: i := Round (RGBA_Unten^[w].rgbBlue - ((RGBA_Unten^[w].rgbBlue - RGBA_Oben^[w].rgbBlue) / 255 * RGBA_Oben^[w].rgbReserved));
wird dann: i := RGBA_Unten^[w].rgbBlue - MulDiv(RGBA_Unten^[w].rgbBlue - RGBA_Oben^[w].rgbBlue, RGBA_Oben^[w].rgbReserved, 255);

Mit Zusatzvariable und nur einer Dereferenzierung am Schleifenanfang, also "col:=RGBA_Unten^[w]" und dann nur mit "col.rgbXXX" rechnen wird es nochmal schneller.
Die hier oft verwendete "255" finde ich nicht ganz so dolle, denn 0..255 sind 256 Werte, also setze man doch lieber alle "0..255" Werte mit 256 ins Verhältnis, dann gibt es auch keine Resultate > 255...

Ansonsten rechne ich das lieber komplett auf Speicherarrays und verwende simple Indexzugriffe auf vor berechnete Wertetabellen(statt ständiges "MulDiv" von zwei "8Bit" Werten) sowie das Ganze möglichst als vorzeichenlose Ganzzahlarithmetik, das ist noch schneller und damit sind dann auch so Sachen wie SSEx für weiter Filteroperationen und andere Spielereien möglich. Das führt aber hier zuweit. Einen Blick in die SourceCodes von optimierten Grafiklibs würde ich da empfehlen.
  Mit Zitat antworten Zitat
Ursa

Registriert seit: 5. Jan 2015
5 Beiträge
 
#8

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 5. Jan 2015, 06:46
Da kann man "gleichzeitig", in einem Thread.




samsung galaxy A3 schutzhülle

Geändert von Ursa ( 6. Jan 2015 um 02:27 Uhr)
  Mit Zitat antworten Zitat
Dejan Vu
(Gast)

n/a Beiträge
 
#9

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 5. Jan 2015, 06:56
Bitte antworte in vollständigen Sätzen, also: Subjekt, Prädikat, Objekt. Es ist ein wenig dadaistisch, was Du da von Dir gibst und von einfachen Menschen wie mir so nicht zu verstehen.
  Mit Zitat antworten Zitat
Thomasl

Registriert seit: 19. Jun 2006
Ort: Vreden
66 Beiträge
 
Delphi 11 Alexandria
 
#10

AW: Geht das noch schneller? - Bitmap-Verrechnung

  Alt 5. Jan 2015, 21:30
Soll das nur übereinander Angezeigt werden?
Da hätte ich auch ein Beispiel mit GDI+
da rechnet das ja die GPU zusammen?
Thomas Levering
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 1 von 2  1 2      


Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 03:59 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz