ReportMachine不能打开打印机属性设置的解决方法

ReportMachine不能打开打印设置的解决方法

1、问题现象

在使用ReportMachine作为报表打印时,发现不能调用本机打印机属性设置对话框,如下图:

这里写图片描述

 点击“属性”按钮后无反应,从而不能对打印机属性进行设置。该问题同时也导致不能获取打印机设置信息。

2、问题原因

跟踪代码发现点击“属性”,会调用“PropertiesDlg”函数,RM_Printer.pas文件中,代码如下:
function TRMPrinter.PropertiesDlg: Boolean;
var
    lDevMode: THandle;
    lPDevMode: PDeviceMode;
    lHandle: THandle;
    lResult: Boolean;
begin
    FLock.Acquire;
    try
        GetDevMode(lDevMode);  //调用返回lDevMode一直为0 
        Result := False;
        lResult := FALSE;
        try
            lPDevMode := GlobalLock(lDevMode);//不能分配内存,lPDevMode 为nil.
            if Screen.ActiveForm <> nil then
                lHandle := Screen.ActiveForm.Handle
            else
                lHandle := 0;

            if lPDevMode <> nil  then  //lPDevMode 为nil,不调用打印机属性设置
                lResult := (Winspool.DocumentProperties(lHandle, PrinterHandle, PChar(PrinterInfo.Device),
                    lPDevMode^, lPDevMode^, DM_IN_BUFFER or DM_OUT_BUFFER or DM_IN_PROMPT) > 0);

            if lResult then
            begin
                SetDevMode(lDevMode);
                Result := True;
            end;

            GlobalUnlock(lDevMode);
        finally
            GlobalFree(lDevMode);
        end;
    finally
        FLock.Release;
    end;
end;
进而跟踪GetDevMode,找到RM_Printer.pas文件中GetDocumentProperties函数,代码段如下:
function TRMCustomPrinter.GetDocumentProperties: THandle;
var
    lStubDevMode: TDeviceMode;
    lPrinterInfo: TRMPrinterInfo;
begin
    FLock.Acquire;
    try
        Result := 0;
        if FDevMode = 0 then
        begin
            lPrinterInfo := RMPrinters.PrinterInfo[FPrinterIndex];
            if lPrinterInfo = nil then
                Exit;

            FDevMode := GlobalAlloc(GHND,
                DocumentProperties(0, PrinterHandle, PChar(lPrinterInfo.Device), lStubDevMode, lStubDevMode, 0));
            //这里FDevMode 执行后始终为0,函数反馈也就为0.同时,导致以下IF内代码不会执行,不能获取打印机属性信息。

            if FDevMode <> 0 then
            begin
                FPDevMode := GlobalLock(FDevMode);
                if DocumentProperties(0, PrinterHandle, PChar(lPrinterInfo.Device), FPDevMode^, FPDevMode^, DM_OUT_BUFFER) >= 0 then
                begin
                    FDefaultBin := FPDevMode^.dmDefaultSource;
                end
                else
                    FreeDevMode;
            end;
        end;
        Result := FDevMode;
    finally
        FLock.Release;
    end;
end;

3、解决办法

更改GetDocumentProperties函数中的代码
DocumentProperties(0, PrinterHandle, PChar(lPrinterInfo.Device), lStubDevMode, lStubDevMode, 0)
DocumentProperties(0, PrinterHandle, PChar(lPrinterInfo.Device), nil, nil, 0)
  完整代码如下:
function TRMCustomPrinter.GetDocumentProperties: THandle;
var
//  lStubDevMode: TDeviceMode;
    lPrinterInfo: TRMPrinterInfo;
begin
    FLock.Acquire;
    try
        Result := 0;
        if FDevMode = 0 then
        begin
            lPrinterInfo := RMPrinters.PrinterInfo[FPrinterIndex];
            if lPrinterInfo = nil then
                Exit;

            FDevMode := GlobalAlloc(GHND,
                DocumentProperties(0, PrinterHandle, PWideChar(lPrinterInfo.Device), nil, nil, 0));

            if FDevMode <> 0 then
            begin
                FPDevMode := GlobalLock(FDevMode);
                if DocumentProperties(0, PrinterHandle, PChar(lPrinterInfo.Device), FPDevMode^, FPDevMode^, DM_OUT_BUFFER) >= 0 then
                begin
                    FDefaultBin := FPDevMode^.dmDefaultSource;
                end
                else
                    FreeDevMode;
            end;
        end;
        Result := FDevMode;
    finally
        FLock.Release;
    end;
end;
1、支持屏幕打印,控制方法多样,可以打印全部rxlib控件 全部InfoPower控件,TDBGrid,TStringGrid,TImage,TEdit等,TDBGridEh,f1book, TDecisionGrid等等众多控件。   2、支持最终用户设计、修改报表,只需连接相关的数据源,指出数据的位 置(设置报表样式),无论是主从表,子报表,套表,都可迅速生成。开发 一个报表只需几分钟的时间。    3、报表样式可以保存为rmf格式,下次可通过读入使用(配合SQL脚本就可以生成 报表)。并可以把带数据的报表保存为rmp格式,在任何机器上都可以浏览、打印, 而不需要数据库。    4、生成后的报表支持修改,包括字体的设置,边框的设置,修改内容等。   5、报表编辑器内自带ado,bde,ibx,Diamond dao,dbisam等数据访问控件,可以 通过这些控件开发独立的报表制作工具。其使用方法和delphi中的控件是一样的。 6、完全、自由自定义页面、边距、字体,标题和页眉页脚,并可以在自认合适的 地方插入函数来实现当前日期,页合计,总合计等功能,合计字段可以放在页头,分 组头,并支持条件合计,对分组合计,分页合计,总计等只需简单地设置属性即可。    7、完全支持D5--D7,BCB5--BCB6。    8、报表中可以在自认合适的事件(on beforeprint,on afterprint等)中加入程 序脚本,以控制、或实现更复杂的打印效果。    9、更新迅速,可根据使用人员与用户的意见,不断的加入新的功能。    10、多种格式转换,可以把做出的报表转换为html,xls,pdf,bmp,jpeg等等格式。   11、自动对超长记录折行,超长的内容也会自动折行,中文换行不会乱码。    12、首家支持缩放打印功能,可以根据打印时选择的纸张自动缩放报表。    13、首家支持即打即停.    14、首家提供类似excel的报表设计器,给你足够灵活方表的报表设计方式。    15、首家提供双报表设计器(第一种,第二种),满足所有的需求。    16、更是提供类似于ObjectPascal的script,实现特殊功能。    17、首家提供web,IntraWeb中的报表解决方案。    18、首家提供报表压缩处理,占用内存更少,生成报表速度更快。    19、首家提供合并单元格功能,更加适应处理复杂的中文报表。    20、自动填空行,每页打印数量等细节处理更完善。
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值