gpt4 book ai didi

delphi - 使用 StretchDIBits 使用 Delphi 6 处理条形码图像 - 输出中缺少条形线

转载 作者:行者123 更新时间:2023-12-03 15:33:21 25 4
gpt4 key购买 nike

我的应用程序是在 Delphi 6 中开发的。由于后台处理和大量数据(消耗大约 60MB - 120MB 物理内存),这是一个资源密集型应用程序。该应用程序的功能之一是在进行某些处理后创建条形码图像。如果用户继续生成条形码,那么至少十分之一的条形码会丢失行。我们有以下步骤生成输出:

  1. 在内存中创建条形码图像(TImage)。图像的高度为 10 像素。我们使用pf24位像素格式。
  2. 根据打印机 Canvas 调整内存中图像的大小并将其传递到打印机 Canvas 。步骤#2的代码如下:
<小时/>
procedure PrintBitmap(ARect:TRect; Bitmap:TBitmap);
var
Info: PBitmapInfo;
InfoSize: dword{Integer};
Image: Pointer;
ImageSize: dword{ integer};
iReturn : integer ;
iWidth,iHeight :integer;
begin
try
with Bitmap do
begin
iReturn := 1;
GetDIBSizes( Handle, InfoSize, ImageSize );
GetMem( Info, InfoSize );
try
getMem( Image, ImageSize );
try
GetDIB(Handle, Palette, Info^, Image^);
try
with Info^.bmiHeader do
begin
SetStretchBltMode(Printer.Canvas.handle,HALFTONE);
iReturn := **StretchDIBits**(Printer.Canvas.Handle, ARect.Left, ARect.Top,
ARect.Right - ARect.Left, ARect.Bottom - ARect.Top,
0, 0, biWidth, biHeight, Image, Info^, DIB_RGB_COLORS, SRCCOPY);
end;
except on E:Exception do
begin
gobjLog.pWritetoLog(0,'RptWrks2','PrintBitmap','Exception in StretchDIBits with message '+e.Message);
end;
end
finally
FreeMem(Image, ImageSize);
end;
finally
FreeMem(Info, InfoSize);
end;
end
except on E:Exception do
begin
gobjLog.pWritetoLog(0,'RptWrks2','PrintBitmap','Exception in PrintBitMap with message '+e.Message);
end;

end;

我们检查问题出在步骤 #2 中,因为生成的条形码图像没有任何问题。 (我们注释掉了第 2 步,并将输出作为 BMP 文件来确认这一点)。

此外,我们尝试了以下解决方法:

  1. 我们使用 TExcellentImagePrinter 组件来执行调整大小操作。但是,问题并没有得到解决。
  2. 我们添加了 SETPROCESSWORKINGSETSIZE WinAPI 调用来减少/刷新应用程序使用的当前内存。
  3. 我们在代码中包含了 Sleep(3000),以便 Windows 能够为图像分配内存。然而,包括 sleep 可以降低此错误的发生频率。

您能提供一些建议吗?

最佳答案

我使用此功能打印条形码非常成功。它假设位图是100%缩放的条形码(每个x像素是条形码条纹),高度无关紧要,可能只有1px。

线索是使用 fillrect 打印条形码而不是位图:该函数只是“读取”条形码并使用 fillrect 将其绘制到某个 Canvas 上。如果生成的比例(xFactor = aToRect 宽度到条形码宽度)是整数或足够大的实数(对于打印机来说没有问题),则可以毫无问题地读取打印的条形码。它也适用于 PDF 打印机。

您只需生成一个 100% 缩放的条形码位图(正如您已经做的那样;高度可以是 1px;条形码的颜色必须是 clBlack)并将其传递到 aFromBMP 参数中。 aToCanvas 将成为您的打印机 Canvas 。 aToRect 是打印机 Canvas 中的目标矩形。 aColor 是目标条形码的颜色(可能是所有颜色)。

procedure PrintBarCodeFromBitmap(const aFromBMP: TBitmap;
const aToCanvas: TCanvas; const aToRect: TRect;
const aColor: TColor = clBlack);
var I, xStartRect: Integer;
xFactor: Double;
xColor: TColor;
xLastBrush: TBrush;
begin
xLastBrush := TBrush.Create;
try
xLastBrush.Assign(aToCanvas.Brush);

aToCanvas.Brush.Color := aColor;
aToCanvas.Brush.Style := bsSolid;

xFactor := (aToRect.Right-aToRect.Left)/aFromBMP.Width;

xStartRect := -1;
for I := 0 to aFromBMP.Width do begin
if I < aFromBMP.Width then
xColor := aFromBMP.Canvas.Pixels[I, 0]
else
xColor := clWhite;

if (xStartRect < 0) and (xColor = clBlack) then begin
xStartRect := I;
end else if (xStartRect >= 0) and (xColor <> clBlack) then begin
aToCanvas.FillRect(
Rect(
Round(aToRect.Left+xStartRect*xFactor),
aToRect.Top,
Round(aToRect.Left+I*xFactor),
aToRect.Bottom));
xStartRect := -1;
end;
end;
finally
aToCanvas.Brush.Assign(xLastBrush);

xLastBrush.Free;
end;
end;

关于delphi - 使用 StretchDIBits 使用 Delphi 6 处理条形码图像 - 输出中缺少条形线,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9869886/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com