Ignore:
Timestamp:
Apr 16, 2024, 11:43:51 AM (4 weeks ago)
Author:
chronos
Message:
  • Modified: Optimized scaled bitmap drawing.
File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/Packages/DpiControls/Dpi.Common.pas

    r538 r539  
    6666  XNative, YNative: Integer;
    6767  DstPixelWidth, DstPixelHeight: Integer;
     68  NewX, NewY: Integer;
    6869begin
    6970  if Frac(ScreenInfo.Dpi / 96) = 0 then
    7071  begin
    7172    // Use faster non-fractional scaling
    72     Result := BitBlt(Dest.Canvas.Handle, X, Y, Width, Height, Src.Canvas.Handle, XSrc, YSrc, Rop);
     73    Result := BitBlt(Dest.Canvas.Handle, X, Y, Width, Height, Src.Canvas.Handle,
     74      XSrc, YSrc, Rop);
    7375    Exit;
    7476  end;
     
    101103  SrcPixel := TPixelPointer.Create(Src.NativeBitmap);
    102104  DstPixel := TPixelPointer.Create(Dest.NativeBitmap);
    103   for YY := 0 to Height - 1 do begin
    104     DstPixelHeight := ScaleToNative(Y + YY + 1) - ScaleToNative(Y + YY);
    105     for DstPixelY := 0 to DstPixelHeight - 1 do begin
    106       for XX := 0 to Width - 1 do begin
    107         SrcPixel.SetXY(ScaleToNative(XSrc + XX), ScaleToNative(YSrc + YY));
    108         DstPixel.SetXY(ScaleToNative(X + XX), ScaleToNative(Y + YY) + DstPixelY);
    109         DstPixelWidth := ScaleToNative(X + XX + 1) - ScaleToNative(X + XX);
    110         for DstPixelX := 0 to DstPixelWidth - 1 do begin
    111 {$IFDEF DEBUG}
    112           if SrcPixel.PosValid and DstPixel.PosValid then
    113 {$ENDIF}
    114             if Rop = SRCCOPY then begin
    115               DstPixel.PixelB := SrcPixel.PixelB;
    116               DstPixel.PixelG := SrcPixel.PixelG;
    117               DstPixel.PixelR := SrcPixel.PixelR;
    118             end else
    119             if Rop = SRCPAINT then begin
    120               DstPixel.PixelB := SrcPixel.PixelB or DstPixel.PixelB;
    121               DstPixel.PixelG := SrcPixel.PixelG or DstPixel.PixelG;
    122               DstPixel.PixelR := SrcPixel.PixelR or DstPixel.PixelR;
    123             end else
    124             if Rop = SRCAND then begin
    125               DstPixel.PixelB := SrcPixel.PixelB and DstPixel.PixelB;
    126               DstPixel.PixelG := SrcPixel.PixelG and DstPixel.PixelG;
    127               DstPixel.PixelR := SrcPixel.PixelR and DstPixel.PixelR;
    128             end else
    129             if Rop = DSTINVERT then begin
    130               DstPixel.PixelB := not DstPixel.PixelB;
    131               DstPixel.PixelG := not DstPixel.PixelG;
    132               DstPixel.PixelR := not DstPixel.PixelR;
    133             end else begin
    134               raise Exception.Create(SUnsupportedPaintOperationType);
    135             end;
    136           DstPixel.NextPixel;
     105  if Rop = SRCCOPY then begin
     106    for YY := 0 to Height - 1 do begin
     107      NewY := ScaleToNative(Y + YY);
     108      DstPixelHeight := ScaleToNative(Y + YY + 1) - NewY;
     109      SrcPixel.SetXY(0, ScaleToNative(YSrc + YY));
     110      for DstPixelY := 0 to DstPixelHeight - 1 do begin
     111        DstPixel.SetXY(0, NewY + DstPixelY);
     112        for XX := 0 to Width - 1 do begin
     113          SrcPixel.SetX(ScaleToNative(XSrc + XX));
     114          NewX := ScaleToNative(X + XX);
     115          DstPixel.SetX(NewX);
     116          DstPixelWidth := ScaleToNative(X + XX + 1) - NewX;
     117          for DstPixelX := 0 to DstPixelWidth - 1 do begin
     118            DstPixel.PixelRGB := SrcPixel.PixelARGB;
     119            DstPixel.NextPixel;
     120          end;
    137121        end;
    138122      end;
    139       //DstPixel.NextLine;
    140     end;
    141   end;
     123    end;
     124  end else
     125  if Rop = SRCPAINT then begin
     126    for YY := 0 to Height - 1 do begin
     127      NewY := ScaleToNative(Y + YY);
     128      DstPixelHeight := ScaleToNative(Y + YY + 1) - NewY;
     129      SrcPixel.SetXY(0, ScaleToNative(YSrc + YY));
     130      for DstPixelY := 0 to DstPixelHeight - 1 do begin
     131        DstPixel.SetXY(0, NewY + DstPixelY);
     132        for XX := 0 to Width - 1 do begin
     133          SrcPixel.SetX(ScaleToNative(XSrc + XX));
     134          NewX := ScaleToNative(X + XX);
     135          DstPixel.SetX(NewX);
     136          DstPixelWidth := ScaleToNative(X + XX + 1) - NewX;
     137          for DstPixelX := 0 to DstPixelWidth - 1 do begin
     138            DstPixel.PixelRGB := SrcPixel.PixelARGB or DstPixel.PixelARGB;
     139            DstPixel.NextPixel;
     140          end;
     141        end;
     142      end;
     143    end;
     144  end else
     145  if Rop = SRCAND then begin
     146    for YY := 0 to Height - 1 do begin
     147      NewY := ScaleToNative(Y + YY);
     148      DstPixelHeight := ScaleToNative(Y + YY + 1) - NewY;
     149      SrcPixel.SetXY(0, ScaleToNative(YSrc + YY));
     150      for DstPixelY := 0 to DstPixelHeight - 1 do begin
     151        DstPixel.SetXY(0, NewY + DstPixelY);
     152        for XX := 0 to Width - 1 do begin
     153          SrcPixel.SetX(ScaleToNative(XSrc + XX));
     154          NewX := ScaleToNative(X + XX);
     155          DstPixel.SetX(NewX);
     156          DstPixelWidth := ScaleToNative(X + XX + 1) - NewX;
     157          for DstPixelX := 0 to DstPixelWidth - 1 do begin
     158            DstPixel.PixelRGB := SrcPixel.PixelARGB and DstPixel.PixelARGB;
     159            DstPixel.NextPixel;
     160          end;
     161        end;
     162      end;
     163    end;
     164  end else
     165  if Rop = DSTINVERT then begin
     166    for YY := 0 to Height - 1 do begin
     167      NewY := ScaleToNative(Y + YY);
     168      DstPixelHeight := ScaleToNative(Y + YY + 1) - NewY;
     169      SrcPixel.SetXY(0, ScaleToNative(YSrc + YY));
     170      for DstPixelY := 0 to DstPixelHeight - 1 do begin
     171        DstPixel.SetXY(0, NewY + DstPixelY);
     172        for XX := 0 to Width - 1 do begin
     173          SrcPixel.SetX(ScaleToNative(XSrc + XX));
     174          NewX := ScaleToNative(X + XX);
     175          DstPixel.SetX(NewX);
     176          DstPixelWidth := ScaleToNative(X + XX + 1) - NewX;
     177          for DstPixelX := 0 to DstPixelWidth - 1 do begin
     178            DstPixel.PixelRGB := not DstPixel.PixelARGB;
     179            DstPixel.NextPixel;
     180          end;
     181        end;
     182      end;
     183    end;
     184  end else raise Exception.Create(SUnsupportedPaintOperationType);
    142185  Dest.EndUpdate;
    143186  Result := True;
Note: See TracChangeset for help on using the changeset viewer.