ImageFx.pas
上传用户:ctlcnc
上传日期:2021-12-10
资源大小:4933k
文件大小:18k
源码类别:

2D图形编程

开发平台:

Delphi

  1. unit ImageFx;
  2. //---------------------------------------------------------------------------
  3. // ImageFx.pas                                          Modified: 18-Ago-2005
  4. // Image and pixel routines                                       Version 1.1
  5. //---------------------------------------------------------------------------
  6. //
  7. // Changes since v1.0:
  8. //
  9. //   * Moved several routines from AsphyreBmp.pas for processing certain
  10. //     bitmaps and their patterns.
  11. //   + Added alpha-channel extraction routines
  12. //
  13. //---------------------------------------------------------------------------
  14. // The contents of this file are subject to the Mozilla Public License
  15. // Version 1.1 (the "License"); you may not use this file except in
  16. // compliance with the License. You may obtain a copy of the License at
  17. // http://www.mozilla.org/MPL/
  18. //
  19. // Software distributed under the License is distributed on an "AS IS"
  20. // basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the
  21. // License for the specific language governing rights and limitations
  22. // under the License.
  23. //---------------------------------------------------------------------------
  24. interface
  25. //---------------------------------------------------------------------------
  26. uses
  27.  Types, Classes, SysUtils, Graphics, Math, CommonDef;
  28. //---------------------------------------------------------------------------
  29. // RenderLineAlpha()
  30. //
  31. // Renders source scanline with alpha-channel onto destination address.
  32. // The source alpha-channel is multiplied by the specified Alpha coefficient.
  33. //   Alpha can be [0..255]
  34. //---------------------------------------------------------------------------
  35. procedure RenderLineAlpha(Source, Dest: Pointer; Count, Alpha: Integer); stdcall;
  36. //---------------------------------------------------------------------------
  37. // RenderLineAlphaAdd()
  38. //
  39. // Renders source scanline  onto destination address.
  40. // The source is multiplied bu its alpha-channel and Alpha coefficient.
  41. //   Alpha can be [0..255]
  42. //---------------------------------------------------------------------------
  43. procedure RenderLineAlphaAdd(Source, Dest: Pointer; Count, Alpha: Integer); stdcall;
  44. //---------------------------------------------------------------------------
  45. // RenderLineDiffuse()
  46. //
  47. // Similar in effect to RenderLineAlpha() except that source pixels are also
  48. // multiplied by the specified color.
  49. //---------------------------------------------------------------------------
  50. procedure RenderLineDiffuse(Source, Dest: Pointer; Count: Integer;
  51.  Diffuse: Longword); stdcall;
  52. //---------------------------------------------------------------------------
  53. // BlendPixels()
  54. //
  55. // This function blends two pixels together by the specified alpha value.
  56. //---------------------------------------------------------------------------
  57. function BlendPixels(Px0, Px1: Longword; Alpha: Integer): Longword; stdcall;
  58. //---------------------------------------------------------------------------
  59. // ShrinkLine2x()
  60. //
  61. // Resamples source scanlines into a single line of half length.
  62. //---------------------------------------------------------------------------
  63. procedure ShrinkLine2x(Src0, Src1, Dest: Pointer;
  64.  PixCount: Integer); stdcall;
  65. //---------------------------------------------------------------------------
  66. // Pixel2Gray()
  67. //
  68. // Transforms the specified 32-bit RGB pixel into grayscale (approx)
  69. //---------------------------------------------------------------------------
  70. function Pixel2Gray(Pixel: Longword): Longword; stdcall;
  71. //---------------------------------------------------------------------------
  72. // Pixel2GrayEx()
  73. //
  74. // Transforms the specified 32-bit RGB pixel into grayscale floating point
  75. // value. This version is more precise than Pixel2Gray but slower.
  76. //---------------------------------------------------------------------------
  77. function Pixel2GrayEx(Pixel: Cardinal): Real;
  78. //---------------------------------------------------------------------------
  79. // ExtractAlpha()
  80. //
  81. // This takes ttwo grayscale pixels rendered on two different backgrounds
  82. // and attempts to extract original pixel and its alpha-channel.
  83. //---------------------------------------------------------------------------
  84. procedure ExtractAlpha(Src1, Src2, Bk1, Bk2: Real; out Alpha, Px: Real);
  85. //---------------------------------------------------------------------------
  86. // ExtractAlpha()
  87. //
  88. // This takes the grayscale graphics rendered on two different backgrounds
  89. // and attempts to extract original image and its alpha-channel.
  90. //---------------------------------------------------------------------------
  91. procedure FindAlphaChannel(Dest, Image0, Image1: TBitmap; Bk1, Bk2: Cardinal);
  92. //---------------------------------------------------------------------------
  93. // ClearBitmap()
  94. //
  95. // This routine takes the specified image, converts its bitdepth to 32-bit
  96. // and then fills the surface with the specified color.
  97. //---------------------------------------------------------------------------
  98. procedure ClearBitmap(Image: TBitmap; Color: Longword);
  99. //---------------------------------------------------------------------------
  100. // TileBitmap()
  101. //
  102. // Takes source bitmap and attempts to tile its patterns on destination
  103. // bitmap using different pattern accomodation.
  104. //---------------------------------------------------------------------------
  105. procedure TileBitmap(Dest, Source: TBitmap; const TexSize, InPSize,
  106.  OutPSize: TPoint; NeedMask: Boolean; MaskColor: Cardinal; Tolerance: Integer);
  107. //---------------------------------------------------------------------------
  108. implementation
  109. //---------------------------------------------------------------------------
  110. procedure RenderLineAlpha(Source, Dest: Pointer; Count, Alpha: Integer); stdcall;
  111. asm
  112.  push esi
  113.  push edi
  114.  push ebx
  115.  mov esi, Source       // ESI -> source pointer
  116.  mov edi, Dest         // EDI -> destination pointer
  117.  mov ecx, Count        // ECX -> a number of pixels to process
  118.  pxor mm7, mm7         // MM7 -> zero register
  119.  mov eax, 0FFFFFFFFh
  120.  movd mm2, eax
  121.  punpcklbw mm2, mm7    // MM2 -> 255,255,255,255 (words)
  122.  mov eax, 01010101h
  123.  movd mm3, eax
  124.  punpcklbw mm3, mm7    // MM3 -> 1, 1, 1, 1 (words)
  125.  paddusw mm2, mm3      // MM2 -> 256,256,256,256 (words)
  126.  mov eax, Alpha
  127.  and eax, 0FFh
  128.  mov ebx, eax
  129.  shl ebx, 8
  130.  or eax , ebx
  131.  shl ebx, 8
  132.  or eax , ebx
  133.  movd mm3, eax
  134.  punpcklbw mm3, mm7    // MM3 -> alpha,alpha,alpha
  135.  // Pixel processing loop.
  136.  // On entry, these registers are defined:
  137.  //  ESI - source
  138.  //  EDI - dest
  139.  //  ECX - pixel count
  140.  //   MM2 - 256,256,256,256
  141.  //   MM3 - alpha,alpha,alpha
  142.  //   MM7 - zero
  143. @rLoop:
  144.  mov eax, [esi]        // EAX -> source pixel
  145.  movd mm0, eax
  146.  punpcklbw mm0, mm7    // MM0 -> source pixel (words)
  147.  shr eax, 24
  148.  mov ebx, eax
  149.  shl ebx, 8
  150.  or eax, ebx
  151.  shl ebx, 8
  152.  or eax, ebx
  153.  movd mm4, eax
  154.  punpcklbw mm4, mm7    // MM4 -> srcA, srcA, srcA (words)
  155.  pmullw mm4, mm3
  156.  psrlw mm4, 8          // MM4 -> srcA * alpha (words)
  157. // pmullw mm0, mm4
  158. // psrlw mm0, 8
  159.  movd mm5, [edi]
  160.  punpcklbw mm5, mm7    // MM5 -> dest pixel (words)
  161.  pmullw mm0, mm4       // MM0 -> source pixel, multiplied by alpha-channel
  162.  psrlw mm0, 8
  163.  movq mm6, mm2
  164.  psubusw mm6, mm4      // MM6 -> inverse alpha channel (words)
  165.  pmullw mm5, mm6
  166.  psrlw mm5, 8          // MM5 -> dest pixel, multiplied by inverse alpha-channel
  167.  paddusw mm0, mm5
  168.  packuswb  mm0, mm7    // MM0 -> final pixel (bytes)
  169.  movd [edi], mm0
  170.  add esi, 4
  171.  add edi, 4
  172.  dec ecx
  173.  jnz @rLoop
  174.  emms
  175.  pop ebx
  176.  pop edi
  177.  pop esi
  178. end;
  179. //---------------------------------------------------------------------------
  180. procedure RenderLineAlphaAdd(Source, Dest: Pointer; Count, Alpha: Integer); stdcall;
  181. asm
  182.  push esi
  183.  push edi
  184.  push ebx
  185.  mov esi, Source       // ESI -> source pointer
  186.  mov edi, Dest         // EDI -> destination pointer
  187.  mov ecx, Count        // ECX -> a number of pixels to process
  188.  pxor mm7, mm7         // MM7 -> zero register
  189.  mov eax, Alpha
  190.  and eax, 0FFh
  191.  mov ebx, eax
  192.  shl ebx, 8
  193.  or eax , ebx
  194.  shl ebx, 8
  195.  or eax , ebx
  196.  movd mm3, eax
  197.  punpcklbw mm3, mm7    // MM3 -> alpha,alpha,alpha
  198.  // Pixel processing loop.
  199.  // On entry, these registers are defined:
  200.  //  ESI - source
  201.  //  EDI - dest
  202.  //  ECX - pixel count
  203.  //   MM3 - alpha,alpha,alpha
  204.  //   MM7 - zero
  205. @rLoop:
  206.  mov eax, [esi]        // EAX -> source pixel
  207.  movd mm0, eax
  208.  punpcklbw mm0, mm7    // MM0 -> source pixel (words)
  209.  shr eax, 24
  210.  mov ebx, eax
  211.  shl ebx, 8
  212.  or eax, ebx
  213.  shl ebx, 8
  214.  or eax, ebx
  215.  movd mm4, eax
  216.  punpcklbw mm4, mm7    // MM4 -> srcA, srcA, srcA (words)
  217.  pmullw mm4, mm3
  218.  psrlw mm4, 8          // MM4 -> srcA * alpha (words)
  219.  movd mm5, [edi]
  220.  punpcklbw mm5, mm7    // MM5 -> dest pixel (words)
  221.  pmullw mm0, mm4       // MM0 -> source pixel, multiplied by alpha-channel
  222.  psrlw mm0, 8
  223.  paddusw mm0, mm5
  224.  packuswb  mm0, mm7    // MM0 -> final pixel (bytes)
  225.  movd [edi], mm0
  226.  add esi, 4
  227.  add edi, 4
  228.  dec ecx
  229.  jnz @rLoop
  230.  emms
  231.  pop ebx
  232.  pop edi
  233.  pop esi
  234. end;
  235. //---------------------------------------------------------------------------
  236. procedure RenderLineDiffuse(Source, Dest: Pointer; Count: Integer;
  237.  Diffuse: Longword); stdcall;
  238. asm
  239.  push esi
  240.  push edi
  241.  push ebx
  242.  mov esi, Source       // ESI -> source pointer
  243.  mov edi, Dest         // EDI -> destination pointer
  244.  mov ecx, Count        // ECX -> a number of pixels to process
  245.  pxor mm7, mm7         // MM7 -> zero register
  246.  mov eax, 0FFFFFFFFh
  247.  movd mm6, eax
  248.  punpcklbw mm6, mm7    // MM6 -> 255,255,255,255 (words)
  249.  mov eax, 01010101h
  250.  movd mm0, eax
  251.  punpcklbw mm0, mm7    // MM0 -> 1, 1, 1, 1 (words)
  252.  paddusw mm6, mm0      // MM6 -> 256,256,256,256 (words)
  253.  mov eax, Diffuse
  254.  movd mm5, eax
  255.  punpcklbw mm5, mm7    // MM5 -> diffuse color (words)
  256.  // Pixel processing loop.
  257.  // On entry, these registers are defined:
  258.  //  ESI - source
  259.  //  EDI - dest
  260.  //  ECX - pixel count
  261.  //   MM5 - diffuse color
  262.  //   MM6 - 256,256,256,256
  263.  //   MM7 - zero
  264. @rLoop:
  265.  mov eax, [esi]        // EAX -> source pixel
  266.  movd mm0, eax
  267.  punpcklbw mm0, mm7    // MM0 -> source pixel (words)
  268.  pmullw mm0, mm5
  269.  psrlw mm0, 8          // MM0 -> "diffused" pixel (words)
  270.  movq mm1, mm0
  271.  packuswb mm1, mm7
  272.  movd eax, mm1         // eax -> diffused pixel
  273.  // extract alpha-channel from diffused pixel
  274.  shr eax, 24
  275.  mov ebx, eax
  276.  shl ebx, 8
  277.  or eax, ebx
  278.  shl ebx, 8
  279.  or eax, ebx
  280.  movd mm4, eax
  281.  punpcklbw mm4, mm7    // MM4 -> alpha, alpha, alpha (words)
  282.  movd mm3, [edi]
  283.  punpcklbw mm3, mm7    // MM3 -> dest pixel (words)
  284.  pmullw mm0, mm4       // MM0 -> source pixel, multiplied by alpha-channel
  285.  psrlw mm0, 8
  286.  movq mm1, mm6
  287.  psubusw mm1, mm4      // MM1 -> inverse alpha channel (words)
  288.  pmullw mm3, mm1
  289.  psrlw mm3, 8          // MM3 -> dest pixel, multiplied by inverse alpha-channel
  290.  paddusw mm0, mm3
  291.  packuswb  mm0, mm7    // MM0 -> final pixel (bytes)
  292.  movd [edi], mm0
  293.  add esi, 4
  294.  add edi, 4
  295.  dec ecx
  296.  jnz @rLoop
  297.  emms
  298.  pop ebx
  299.  pop edi
  300.  pop esi
  301. end;
  302. //---------------------------------------------------------------------------
  303. function BlendPixels(Px0, Px1: Longword; Alpha: Integer): Longword; stdcall;
  304. asm
  305.  pxor mm7, mm7
  306.  mov eax, 0FFFFFFFFh
  307.  movd mm6, eax
  308.  punpcklbw mm6, mm7    // MM6 -> 255,255,255,255 (words)
  309.  mov eax, 01010101h
  310.  movd mm0, eax
  311.  punpcklbw mm0, mm7    // MM0 -> 1, 1, 1, 1 (words)
  312.  paddusw mm6, mm0      // MM6 -> 256,256,256,256 (words)
  313.  mov eax, Alpha
  314.  and eax, 0FFh
  315.  mov ecx, eax
  316.  shl ecx, 8
  317.  or  eax, ecx
  318.  shl ecx, 8
  319.  or  eax, ecx
  320.  shl ecx, 8
  321.  or eax, ecx
  322.  movd mm2, eax
  323.  punpcklbw mm2, mm7    // MM2 -> alpha,alpha,alpha
  324.  movd mm0, Px0
  325.  movd mm1, Px1
  326.  punpcklbw mm0, mm7
  327.  punpcklbw mm1, mm7
  328.  pmullw mm0, mm2
  329.  psrlw mm0, 8
  330.  psubusw mm6, mm2
  331.  pmullw mm1, mm6
  332.  psrlw mm1, 8
  333.  paddusw mm0, mm1
  334.  packuswb  mm0, mm7
  335.  movd eax, mm0
  336.  emms
  337.  mov Result, eax
  338. end;
  339. //---------------------------------------------------------------------------
  340. procedure ShrinkLine2x(Src0, Src1, Dest: Pointer;
  341.  PixCount: Integer); stdcall;
  342. begin
  343.  asm
  344.   push edi
  345.   push esi
  346.   push ebx
  347.   mov ecx, PixCount
  348.   mov esi, Src0
  349.   mov edx, Src1
  350.   mov edi, Dest
  351.   pxor mm7, mm7
  352.  @ConvLoop:
  353.   movd mm0, [esi]
  354.   punpcklbw mm0, mm7
  355.   movd mm1, [esi + 4]
  356.   punpcklbw mm1, mm7
  357.   paddsw mm0, mm1
  358.   movd mm2, [edx]
  359.   punpcklbw mm2, mm7
  360.   movd mm3, [edx + 4]
  361.   punpcklbw mm3, mm7
  362.   paddsw mm0, mm2
  363.   paddsw mm0, mm3
  364.   psrlw  mm0, 2
  365.   packuswb  mm0, mm7
  366.   movd [edi], mm0
  367.   add esi, 8
  368.   add edx, 8
  369.   add edi, 4
  370.   dec ecx
  371.   jnz @ConvLoop
  372.   emms
  373.   pop ebx
  374.   pop esi
  375.   pop edi
  376.  end;
  377. end;
  378. //---------------------------------------------------------------------------
  379. function Pixel2Gray(Pixel: Longword): Longword; stdcall;
  380. const
  381.  rConst = 5;
  382.  gConst = 8;
  383.  bConst = 3;
  384. asm
  385.  push ebx
  386.  mov eax, Pixel
  387.  mov ecx, eax
  388.  and eax, 0FFh
  389.  imul eax, rConst
  390.  mov ebx, eax
  391.  mov eax, ecx
  392.  shl eax, 16
  393.  shr eax, 24
  394.  imul eax, gConst
  395.  add ebx, eax
  396.  mov eax, ecx
  397.  shl eax, 8
  398.  shr eax, 24
  399.  imul eax, bConst
  400.  add ebx, eax
  401.  shr ebx, 4
  402.  mov Result, ebx
  403.  pop ebx
  404. end;
  405. //---------------------------------------------------------------------------
  406. function Pixel2GrayEx(Pixel: Cardinal): Real;
  407. begin
  408.  Result:= ((Pixel and $FF) * 0.3 + ((Pixel shr 8) and $FF) * 0.59 +
  409.   ((Pixel shr 16) and $FF) * 0.11) / 255.0;
  410. end;
  411. //---------------------------------------------------------------------------
  412. procedure ExtractAlpha(Src1, Src2, Bk1, Bk2: Real; out Alpha, Px: Real);
  413. begin
  414.  Alpha:= (1.0 - (Src2 - Src1)) / (Bk2 - Bk1);
  415.  Px:= Src1;
  416.  if (Alpha > 0.0) then
  417.   Px:= (Src1 - (1.0 - Alpha) * Bk1) / Alpha;
  418. end;
  419. //---------------------------------------------------------------------------
  420. procedure FindAlphaChannel(Dest, Image0, Image1: TBitmap; Bk1, Bk2: Cardinal);
  421. var
  422.  Index   : Integer;
  423.  ScanIndx: Integer;
  424.  BackValue1: Real;
  425.  BackValue2: Real;
  426.  Pixel1: Real;
  427.  Pixel2: Real;
  428.  Pixel : Real;
  429.  Alpha : Real;
  430.  Read0: PCardinal;
  431.  Read1: PCardinal;
  432.  Write: PCardinal;
  433.  Color: Cardinal;
  434. begin
  435.  BackValue1:= Pixel2GrayEx(Bk1);
  436.  BackValue2:= Pixel2GrayEx(Bk2);
  437.  if (Image0.PixelFormat <> pf32bit) then Image0.PixelFormat:= pf32bit;
  438.  if (Image1.PixelFormat <> pf32bit) then Image1.PixelFormat:= pf32bit;
  439.  Dest.Width := Image0.Width;
  440.  Dest.Height:= Image0.Height;
  441.  if (Dest.PixelFormat <> pf32bit) then Dest.PixelFormat:= pf32bit;
  442.  for ScanIndx:= 0 to Dest.Height - 1 do
  443.   begin
  444.    Read0:= Image0.Scanline[ScanIndx];
  445.    Read1:= Image1.Scanline[ScanIndx];
  446.    Write:= Dest.Scanline[ScanIndx];
  447.    for Index:= 0 to Dest.Width - 1 do
  448.     begin
  449.      // retreive source grayscale pixels
  450.      Pixel1:= Pixel2GrayEx(Read0^);
  451.      Pixel2:= Pixel2GrayEx(Read1^);
  452.      // calculate alpha-value and original pixel
  453.      ExtractAlpha(Pixel1, Pixel2, BackValue1, BackValue2, Alpha, Pixel);
  454.      // convert normalized pixel to color index
  455.      Color:= Round(Pixel * 255.0);
  456.      // prepare a 24-bit RGB color
  457.      Color:= Color or (Color shl 8) or (Color shl 16);
  458.      // add alpha-channel to 24-bit RGB color and write it to destination
  459.      Write^:= Color or (Round(Alpha * 255.0) shl 24);
  460.      // move through pixels
  461.      Inc(Read0);
  462.      Inc(Read1);
  463.      Inc(Write);
  464.     end;
  465.   end;
  466. end;
  467. //---------------------------------------------------------------------------
  468. procedure ClearBitmap(Image: TBitmap; Color: Longword);
  469. var
  470.  j, i: Integer;
  471.  px: PCardinal;
  472. begin
  473.  if (Image.PixelFormat <> pf32bit) then Image.PixelFormat:= pf32bit;
  474.  Color:= DisplaceRB(Color);
  475.  for j:= 0 to Image.Height - 1 do
  476.   begin
  477.    px:= Image.Scanline[j];
  478.    for i:= 0 to Image.Width - 1 do
  479.     begin
  480.      px^:= Color;
  481.      Inc(px);
  482.     end;
  483.   end;
  484. end;
  485. //---------------------------------------------------------------------------
  486. procedure UnmaskAlpha(Dest: TBitmap);
  487. var
  488.  i, j: Integer;
  489.  pl: PLongword;
  490. begin
  491.  Dest.PixelFormat:= pf32bit;
  492.  for j:= 0 to Dest.Height - 1 do
  493.   begin
  494.    pl:= Dest.Scanline[j];
  495.    for i:= 0 to Dest.Width - 1 do
  496.     begin
  497.      pl^:= pl^ or $FF000000;
  498.      Inc(pl);
  499.     end;
  500.   end;
  501. end;
  502. //---------------------------------------------------------------------------
  503. procedure TileBitmap(Dest, Source: TBitmap; const TexSize, InPSize,
  504.  OutPSize: TPoint; NeedMask: Boolean; MaskColor: Cardinal; Tolerance: Integer);
  505. var
  506.  SrcInRow: Integer;
  507.  SrcInCol: Integer;
  508.  SrcCount: Integer;
  509.  DstInRow: Integer;
  510.  DstInCol: Integer;
  511.  ImgInTex: Integer;
  512.  TexCount: Integer;
  513.  AuxMem  : Pointer;
  514.  AuxPitch: Integer;
  515.  SrcIndex: Integer;
  516.  TexIndex: Integer;
  517.  PatIndex: Integer;
  518.  DestPt  : TPoint;
  519.  SrcPt   : TPoint;
  520.  Index   : Integer;
  521.  MemAddr : Pointer;
  522.  DestIndx: Integer;
  523. begin
  524.  // Step 1. Determine source attributes
  525.  SrcInRow:= Source.Width div InPSize.X;
  526.  SrcInCol:= Source.Height div InPSize.Y;
  527.  SrcCount:= SrcInRow * SrcInCol;
  528.  // Step 2. Determine destination attributes
  529.  DstInRow:= TexSize.X div OutPSize.X;
  530.  DstInCol:= TexSize.Y div OutPSize.Y;
  531.  ImgInTex:= DstInRow * DstInCol;
  532.  TexCount:= Ceil(SrcCount / ImgInTex);
  533.  // Step 3. Allocate auxiliary memory
  534.  AuxPitch:= InPSize.X * 4;
  535.  AuxMem  := AllocMem(AuxPitch);
  536.  // Step 4. Prepare source and destination images
  537.  if (Source.PixelFormat <> pf32bit) then UnmaskAlpha(Source);
  538.  Dest.Width := TexSize.X;
  539.  Dest.Height:= TexSize.Y * TexCount;
  540.  ClearBitmap(Dest, $00000000);
  541.  // Step 5. Place individual patterns
  542.  SrcIndex:= 0;
  543.  for TexIndex:= 0 to TexCount - 1 do
  544.   for PatIndex:= 0 to ImgInTex - 1 do
  545.    begin
  546.     DestPt.X:= (PatIndex mod DstInRow) * OutPSize.X;
  547.     DestPt.Y:= ((PatIndex div DstInRow) mod DstInCol) * OutPSize.Y;
  548.     SrcPt.X := (SrcIndex mod SrcInRow) * InPSize.X;
  549.     SrcPt.Y := ((SrcIndex div SrcInRow) mod SrcInCol) * InPSize.Y;
  550.     // render scanlines
  551.     for Index:= 0 to InPSize.Y - 1 do
  552.      begin
  553.       // prepare source pointer
  554.       MemAddr:= Pointer(Integer(Source.Scanline[(Index + SrcPt.Y)]) + (SrcPt.X * 4));
  555.       if (NeedMask) then
  556.        begin
  557.         LineConvMasked(MemAddr, AuxMem, InPSize.X, Tolerance,
  558.          DisplaceRB(MaskColor));
  559.        end else Move(MemAddr^, AuxMem^, InPSize.X * 4);
  560.       DestIndx:= DestPt.Y + (TexSize.Y * TexIndex) + Index;
  561.       MemAddr:= Pointer(Integer(Dest.Scanline[DestIndx]) + (DestPt.X * 4));
  562.       Move(AuxMem^, MemAddr^, AuxPitch);
  563.      end;
  564.     Inc(SrcIndex);
  565.     if (SrcIndex >= SrcCount) then Break;
  566.    end;
  567.  // Step 6. Release auxiliary memory
  568.  FreeMem(AuxMem);
  569. end;
  570. //---------------------------------------------------------------------------
  571. end.