Delphi-PRAXiS
Seite 2 von 5     12 34     Letzte »    

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Algorithmen, Datenstrukturen und Klassendesign (https://www.delphipraxis.net/78-algorithmen-datenstrukturen-und-klassendesign/)
-   -   24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung (https://www.delphipraxis.net/205798-24-bit-bitmap-um-90-grad-drehen-resourcen-optimierung.html)

striderx 18. Okt 2020 20:15

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
Zitat:

Zitat von Harry Stahl (Beitrag 1475686)
Wobei die GDI-Funktionen offensichtlich nur mit 32-Bit-Dateien funktionieren,

Wie kommst du denn darauf? Ich arbeite hier nur mit 24 Bit-Bitmaps und alle GDI+-Funktionen klappen damit.

Harry Stahl 18. Okt 2020 21:24

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
Liste der Anhänge anzeigen (Anzahl: 1)
Ich rufe Deine Funktion wie folgt auf:

GDIPRotateFlipBitmap (bm, Rotate90FlipY);

In der Anlage siehst Du als Screenshot die Ausgangssituation und jeweils die Bilder mit Deiner Funktion gedreht, wenn es ein 24-Bit Bild ist und einmal als 32-Bit Bild.

Bei dem 24-Bit-Bild wird ein falsches Ergebnis zurück geliefert...

striderx 18. Okt 2020 21:42

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
Hallo Harry,

ich habe es gerade mehrfach ausprobiert - bei mir ist das Ergebnis immer einwandfrei.

Das muss also an etwas anderem liegen. Ggf. an der Stelle, wo du die Bitmap in das Image überträgst?

Mir fällt auch auf, dass das 32 bit-Bild größer ist als das Ursprungsbild und dass das 24 bit-Ergebnis einen zweiten, seitenverkehrten Kalenderblock enthält.


Alles Gute
Volker

Harry Stahl 18. Okt 2020 22:22

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
Also das 32-Bit wirkt nur größer, da es schon (richtig) gedreht wurde.
Das 24-Bit wurde mit Deiner Funktion "gedreht", aber hat ersichtlich nicht funktioniert.

Ich mache gleich mal zum Testen ein neues Miniprojekt und teste das mal...

Renate Schaaf 18. Okt 2020 22:47

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
Danke für die Idee mit den worker-threads, probier ich doch gleich mal aus!

Wenn man nur 2mal GetScanline aufruft, geht es auch schneller.

Renate

Harry Stahl 18. Okt 2020 22:54

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
[Nicht] Anliegend ein Testprojekt, es funktioniert weder unter Delphi XE7 (was ich derzeit noch für das Programm verwende), noch unter dem aktuellsten 10.4.1...

Wegen der Dateigröße von 14 MB (das 24-bit-Bild) musste ich das Demo kurz auf meine eigene Seite laden, lasse es solange drauf, bis Du entweder sagst, Du willst es Dir nicht ansehen oder dass Du es geladen hast:

https://www.hastasoft.de/GDITest.zip

Harry Stahl 18. Okt 2020 23:01

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
Zitat:

Zitat von Renate Schaaf (Beitrag 1475695)
Danke für die Idee mit den worker-threads, probier ich doch gleich mal aus!

Wenn man nur 2mal GetScanline aufruft, geht es auch schneller.

Renate

Gerne. Was meinst Du mit nur 2 mal aufrufen?

Ich habe ja die Original-Routine von Doberenz schon um ca. 20% Speed gesteigert, indem ich das

PEnd := Bm.scanline[bm.height-1];

vor die Schleife gesetzt habe und in der Schleife nur den gespeicherten Wert zuweisen muss. Aber "rowout := help.scanline [y];" brauche ich doch weiterhin und kann es nicht ersetzen.

Oder?

Amateurprofi 19. Okt 2020 00:41

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
@Harry:

Wenn du auf Performance aus bist, dann versuch doch mal folgendes.
Sollte deutlich schneller sein.

Achtung:
Der 64Bit-Teil in CopyColumn24 ist ungetestet, weil das Projekt mit dem ich gerade herumspiele nicht 64Bit-fähig ist.
Unter 32 Bit (mit relativ kleinen Bitmaps) ergibt meine Messung dass das doppelt so schnell läuft, wie die ursprüngliche Routine.

Delphi-Quellcode:
PROCEDURE CopyColumn24(PSource,PDest:Pointer; Count,LO:NativeInt);
asm
{$IFDEF CPUX86}// RAX=PSource, RDX=PDest, RCX=Count, Stack=LO
               push    ebx
               mov     ebp,LO
               dec     ecx
@Loop:        mov     ebx,[eax]
               mov     [edx],ebx
               add     eax,ebp
               add     edx,3
               sub     ecx,1
               jnz     @Loop
               mov     bx,[eax]
               mov     [edx],bx
               mov     bl,[eax+2]
               mov     [edx+2],bl
               pop     ebx
{$ELSE}        // RCX=PSource, RDX=PDest, R8=Count, R9=LO
               dec     r8
@Loop:        mov     eax,[rcx]
               mov     [rdx],eax
               add     rcx,r9
               add     rdx,3
               sub     r8,1
               jnz     @Loop
               mov     ax,[rcx]
               mov     [rdx],ax
               mov     al,[rcx+2]
               mov     [rdx+2],al
{$ENDIF}
end;
Delphi-Quellcode:
PROCEDURE RotateRight24(Bmp:TBitmap);
var W,H,Y,LoSource,LoDest:NativeInt; PSource,PDest:PByte; Dest:TBitmap;
begin
   W:=Bmp.Height;
   H:=Bmp.Width;
   PSource:=Bmp.ScanLine[W-1];
   LoSource:=NativeInt(Bmp.ScanLine[W-2])-NativeInt(PSource);
   Dest:=TBitmap.Create;
   Dest.PixelFormat:=pf24bit;
   Dest.SetSize(W,H);
   PDest:=Dest.ScanLine[0];
   LoDest:=NativeInt(Dest.ScanLine[1])-NativeInt(PDest);
   for Y:=H-1 downto 0 do begin
      CopyColumn24(PSource,PDest,W,LoSource);
      Inc(PSource,3);
      Inc(PDest,LoDest);
   end;
   Bmp.Assign(Dest);
   Dest.free;
end;

Renate Schaaf 19. Okt 2020 01:00

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
Zitat:

Gerne. Was meinst Du mit nur 2 mal aufrufen?
So in etwa:

Delphi-Quellcode:
procedure Drehe90Rechts24NurPointers(bm: TBitmap);
var
  P, Pend, Pdest: PRGBTriple;
  x, y, b, h: Integer;
  RowOut: PByte;
  help: TBitmap;
var
  Offs, OffsDest: NativeInt;
begin
  help := TBitmap.create;
  help.pixelformat := pf24bit;

  b := bm.height;
  h := bm.width;

  help.SetSize(b, h);
  RowOut := help.scanline[0];
  Pend := bm.scanline[bm.height - 1];
  Offs := ((h * 24 + 31) and not 31) div 8;
  OffsDest := ((b * 24 + 31) and not 31) div 8;
  for y := 0 to h - 1 do
  begin
    P := Pend;
    inc(P, y);
    Pdest := PRGBTriple(RowOut);
    for x := 0 to b - 1 do
    begin
      Pdest^ := P^;
      inc(Pdest);
      inc(NativeInt(P), Offs);
    end;
    dec(RowOut, OffsDest);
  end;

  bm.Assign(help);
  help.free;
 end;

Harry Stahl 19. Okt 2020 01:39

AW: 24-Bit Bitmap um 90 grad drehen - Resourcen-Optimierung
 
Nur Pointer bringt auch noch mal 500 ms. Hier auf dem Entwicklungs-PC in der virtuellen Maschine wird das große Bild mit Deiner Variante in ca. 5 bis 5,5 Sek. gedreht.

Mit meiner ursprünglichen Variante und den Workerthreads geht's in ca. 3 Sekunden (auf meinem Vertriebs-PC (I5-Prozessor) geht's in ca. 1 Sekunde).

Im Vergleich zu MS-Paint: das braucht auf den Entwicklungs-PC 20 Sekunden um das Bild zu drehen, auf dem Vertreibs-PC 8 Sekunden (und verbraucht nach 1 mal Drehen 4.5 GB Arbeitsspeicher, mein Programm mit Undo-Aktiv ca. 2 GB).


Alle Zeitangaben in WEZ +1. Es ist jetzt 01:43 Uhr.
Seite 2 von 5     12 34     Letzte »    

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