在程序中怎样适时地修改打印机的纸张的设置(100分)

  • 主题发起人 主题发起人 ppl_72
  • 开始时间 开始时间
P

ppl_72

Unregistered / Unconfirmed
GUEST, unregistred user!
各位大虾:
由于在程序中各种报表的大小不一,导致在打印时须经常来修改打印机纸张设置,请问
在程序中怎样来实现,而不须进入win98中打印机设置进行设置。
 
rocedure SetPaperSize(X, Y: Integer);

// 这段代码绝对可用。单位是0.1mm
// A4时 Printer.Pagewidth:=1440; A5时 Printer.Pagewidth:=1049;
// B5时 Printer.Pagewidth:=1290; 16K时 Printer.Pagewidth:=1035;
// lq1600宽行打印机这个值宽度最大为42cm左右, 长度大约2m。
//改变devicemode结构
var
Device: array[0..255] of char;

Driver: array[0..255] of char;

Port: array[0..255] of char;

hDMode: THandle;

PDMode: PDEVMODE;

begin

Printer.PrinterIndex := Printer.PrinterIndex;

Printer.GetPrinter(Device, Driver, Port, hDMode);

if hDMode <> 0 then

begin

pDMode := GlobalLock(hDMode);

if pDMode <> nil then

begin

if (x = 0) or (y = 0) then

begin

{Set to legal}
pDMode^.dmFields := pDMode^.dmFields or dm_PaperSize;

{pDMode^.dmPaperSize := DMPAPER_LEGAL;
changed by wulianmin}
pDMode^.dmPaperSize := DMPAPER_FANFOLD_US;

end
else

begin

{Set to custom size}
pDMode^.dmFields := pDMode^.dmFields or
DM_PAPERSIZE or
DM_PAPERWIDTH or
DM_PAPERLENGTH;

pDMode^.dmPaperSize := DMPAPER_USER;

pDMode^.dmPaperWidth := x {SomeValueInTenthsOfAMillimeter};

pDMode^.dmPaperLength := y {SomeValueInTenthsOfAMillimeter};

end;


{Set the bin to use}
pDMode^.dmFields := pDMode^.dmFields or DMBIN_MANUAL;

pDMode^.dmDefaultSource := DMBIN_MANUAL;


GlobalUnlock(hDMode);

end;


end;


Printer.PrinterIndex := Printer.PrinterIndex;

//以下开始打印
end;

 
在执行打印前调用以下函数:
procedure SetPaperSize(X, Y: Integer);
// 单位是0.1mm
// A4时 Printer.Pagewidth:=1440; A5时 Printer.Pagewidth:=1049;
// B5时 Printer.Pagewidth:=1290; 16K时 Printer.Pagewidth:=1035;
// lq1600宽行打印机这个值宽度最大为42cm左右, 长度大约2m。
//改变devicemode结构
var
Device: array[0..255] of char;
Driver: array[0..255] of char;
Port: array[0..255] of char;
hDMode: THandle;
PDMode: PDEVMODE;
begin

Printer.PrinterIndex := Printer.PrinterIndex;
Printer.GetPrinter(Device, Driver, Port, hDMode);
if hDMode <> 0 then

begin

pDMode := GlobalLock(hDMode);
if pDMode <> nil then

begin

if (x = 0) or (y = 0) then

begin

{Set to legal}
pDMode^.dmFields := pDMode^.dmFields or dm_PaperSize;
{pDMode^.dmPaperSize := DMPAPER_LEGAL;
changed by wulianmin}
pDMode^.dmPaperSize := DMPAPER_FANFOLD_US;
end
else

begin

{Set to custom size}
pDMode^.dmFields := pDMode^.dmFields or
DM_PAPERSIZE or
DM_PAPERWIDTH or
DM_PAPERLENGTH;
pDMode^.dmPaperSize := DMPAPER_USER;
pDMode^.dmPaperWidth := x {SomeValueInTenthsOfAMillimeter};
pDMode^.dmPaperLength := y {SomeValueInTenthsOfAMillimeter};
end;

{设定纸张来源}
pDMode^.dmFields := pDMode^.dmFields or DMBIN_MANUAL;
pDMode^.dmDefaultSource := DMBIN_MANUAL;

GlobalUnlock(hDMode);
end;

end;

Printer.PrinterIndex := Printer.PrinterIndex;
//以下开始打印

end;


 
procedure TMainForm.PrintSetupDj(VWidth:integer;
Vheight:integer);
var
VwidthHigh,VwidthLow:integer;
{纸张宽度的高/低位}
VHeightHigh,VHeightLow:integer;
{纸张高度的高/低位}
Reg: TRegistry;
VPrintName:string;
VDefault_DevMode:array of byte;
VDefault_DevModeInt:integer;
VSize:integer;
begin

{数据存放低位在前,高位在后}
VwidthLow:=byte(Vwidth);
VwidthHigh:=byte(Vwidth Shr 8);{右移8位,再取低位}
VHeightLow:=byte(Vheight);
VHeightHigh:=byte(Vheight Shr 8);{右移8位,再取低位}

Reg := TRegistry.Create;
try
begin

Reg.RootKey := HKEY_LOCAL_MACHINE;
Reg.OpenKey('/Config/0001/System/CurrentControlSet/Control/Print/Printers',true);
{OpenKey:在指定的主键名不存在时,是否允许创建该主键,True表示允许。 }
VPrintName:=Reg.ReadString('Default');
Reg.OpenKey('/System/CurrentControlSet/Control/Print/Printers/'+VPrintName,True);
VSize:=Reg.GetDataSize('Default DevMode');
setlength(VDefault_DevMode,VSize);
//设置动态数组的长度

{读取二进制值,Name为二进制值名称,Buffer为接收缓冲区,BufSize为缓冲区大小,返回为实际读取的字节数。}
reg.ReadBinaryData('Default DevMode',VDefault_DevMode[0],VSize);

{设置当前纸张为自定义纸张:代码256}
VDefault_DevMode[40]:=byte(26127);
VDefault_DevMode[41]:=byte(26127 Shr 8);

VDefault_DevMode[46]:=byte(256);
VDefault_DevMode[47]:=byte(256 Shr 8);

VDefault_DevMode[277]:=byte(11008);
VDefault_DevMode[278]:=byte(11008 Shr 8);

{设定纸长}
VDefault_DevMode[48]:=VHeightLow;
VDefault_DevMode[49]:=VHeightHigh;
{设定纸长}
VDefault_DevMode[50]:=VwidthLow;
VDefault_DevMode[51]:=VwidthHigh;
try
reg.WriteBinaryData('Default DevMode',VDefault_DevMode[0],VSize);
finally
// freemem(buffer);
end;

end
finally
Reg.CloseKey;
Reg.Free;
inherited;
end;

end;

 
什么绝对可用?我就是用不了
 
可以使用Tdevicemode结构,修改tdevicemode就相当修打印机的驱动程序。
 
如何在WINDOWS中控制打印字体的长宽,而不受限于SIZE 的限制


首先为了达到这个功能,可以采用Windows的逻辑字体(LogFont)

可以使用 CreateFont 或 CreateFontIndirect 这两个Windows API

函数来定义任何想要的字体,由于 CreateFont 所需的参数甚多通常

我们使用 CreateFontIndirect 来建立所需的逻辑字体,这个API函数

在Delphi中的声明为

function CreateFontIndirect(const p1: TLogFont): HFONT;
stdcall;

其中只有一个参数 p1: TLogfont

所有有关字体的参数完全通过这个

TLogfont结构来传送,Windows将根据结构中的内容创建出相应的逻辑

字体,在Delphi的Windows.pas中TLogFont是这样定义的


TLogFontA = packed record

lfHeight: Longint;

lfWidth: Longint;

lfEscapement: Longint;

lfOrientation: Longint;

lfWeight: Longint;

lfItalic: Byte;

lfUnderline: Byte;

lfStrikeOut: Byte;

lfCharSet: Byte;

lfOutPrecision: Byte;

lfClipPrecision: Byte;

lfQuality: Byte;

lfPitchAndFamily: Byte;

lfFaceName: array[0..LF_FACESIZE - 1] of AnsiChar;

end;


TLogFontW = packed record

lfHeight: Longint;

lfWidth: Longint;

lfEscapement: Longint;

lfOrientation: Longint;

lfWeight: Longint;

lfItalic: Byte;

lfUnderline: Byte;

lfStrikeOut: Byte;

lfCharSet: Byte;

lfOutPrecision: Byte;

lfClipPrecision: Byte;

lfQuality: Byte;

lfPitchAndFamily: Byte;

lfFaceName: array[0..LF_FACESIZE - 1] of WideChar;

end;


TLogFont = TLogFontA;


其中涉及到很多参数,其中


lfHeight: Longint;

指定以逻辑单位标定的字体高度,取值可为正负或零,对于需要随意

定义字体高度的情况下通常取负值,以保证获得实际尺寸的字体。


lfWidth: Longint;

用于指定字体的平均宽度,由于Windows系统下的大多数字体都是比例

字体因而采用平均宽度这个表示方法。若指定为0,则系统会自动根据

适当的比例自动处理宽度。


lfEscapement: Longint;

指定输出方向与当前坐标系X轴之间的以十分之一度为单位的角度。


lfOrientation: Longint;

指定每个字符与当前坐标系X轴之间的以十分之一度为单位的角度。在

Windows95中这个值等同于lfEscpement。


lfWeight: Longint;

指定范围为从0至1000的字体加重程度,400是标准字体700为加重字体,

0表示采用默认值。


lfItalic: Byte;

不为0表示采用斜体字。


lfUnderline: Byte;

不为0表示带下划线。


lfStrikeOut: Byte;

不为0表示带穿透线。


lfCharSet: Byte;

指定字体集。


lfOutPrecision: Byte;

指定输出精度。用于确定对前面一些设定值的精确程度。


lfClipPrecision: Byte;

指定裁剪精度。裁剪是Windows图形环境下的一种特殊处理,简单说就是

去掉图形中落在视图以外的部分,有助于提高图形的处理速度。


lfQuality: Byte;

指定输出质量。


lfPitchAndFamily: Byte;

指定字体的Pitch和Family。


lfFaceName: array[0..LF_FACESIZE - 1] of AnsiChar;

指定采用的字体名称。


在建立逻辑字体时,我们通常使用


lfHeight和lfWidth来确定字体的尺寸,使用lfEscapement和lfOrientation

来确定字体的输出方向,使用lfWeight

lfItalic

lfUnderline


lfStrikeOut

来确定字体的加重,斜体,下划线和穿透线,使用lfCharSet

来确定字体的字符集,通常采用系统默认的字符集。

对于lfOutPrecision

lfClipPrecision

lfQuality一般应用于对屏幕之外

的输出设备,通常采用默认值。采用lfPitchAndFamily来确定采用定宽或可

变字体和字体的家族。以lfFaceName来通过名称选择采用的字体。

另外应当注意在Windows环境下,每种字体具体输出为何种形式取决于很多

因素,需要对以上这些参数进行有效的组合才能达到所要的效果。
 

Similar threads

D
回复
0
查看
867
DelphiTeacher的专栏
D
D
回复
0
查看
836
DelphiTeacher的专栏
D
D
回复
0
查看
785
DelphiTeacher的专栏
D
后退
顶部