一分钱,一分货(报表打印控件的原代码已在这儿公布,请已在这儿排排座的DFW们来拿钱拿货) (100分)

  • 主题发起人 主题发起人 blueboy
  • 开始时间 开始时间
算我一个: Lanyubox@21cn.com
 
我想把原码粘贴在这儿,免得一个个的发E太麻烦,但程序有一百多K,我
曾试过一次,失败了。我在这儿征求过你们的意见呀,就是没人理我!看来你
们都誓在夺分嘛。[:)]
 
谢谢 pursuer@163.net
 
好像可以联系网站管理人员,是有空间的。但我也不知道现在谁能管理这台主机,
难办呀!想起来了,你可以申请一个免费主页空间,放到那上面,在给我们一个
地址。要不你就把它分成几份,一份一份贴吧!辛苦你了!
 
请上传到:
http://www.playicq.com/default.asp
 
tang_xue@x263.net
谢谢!
 
算了,还是按 pxie 的方法吧,分两次在这儿贴,有劳各位自已去拼接吧。
 
{
说明一下:
1、该程序原来在D3下面开发,在粘贴前在D5下试了一下,可以用,其他版本没试过,不敢作出保证。
2、大家使用中有什么意见或建议,可以在这儿发表,但因 blueboy 工作比较忙,没有时间帮大家修改了,望见谅。
3、本控件主要由blueboy设计,YelloBoy编程。YelloBoy当时刚接触DELPHI,一些代码段或许编得不是很好,希望大家眼光不要太挑剔哦。[:(!]
}
//(第一部分)
{==============================================================================
程 序 名:printf
类 型:控件
类 名:TPrint
继 承 类:TComponent
功 能:1.支持TLabel、TPanel、TEdit、TCombobox、THeader、TDataTimePicker、TImage、
TShape、TMaskEdit、TstringGrid、TDbgrid、TMemo、TSGAccess、TmergeGrid 的打印;
编 程:佚 名
初版日期:1997.
版 本:Ver 1.0
使用说明:
该控件用于打印放在ScrollBox中的各种可视化小控件或由它们组合而成的报表,使用方法如下:
1、在Form 上放置一个TScrollBox类控件作为安置“报表”的容器;
2、在ScrollBox中按照你的需要在指定的位置安放各种小控件,调好位置和大小;
3、给ScrollBox中各种小控件的tag赋1-5的值,以定义小控件的作用(见接口文档的描述)
4、在Form放置一个PrintF 控件,并设置它的ScrollingName 为刚才设计好的ScrollBox;
5、执行PrintF 的 Excute 方法即可出现打印界面。
如不想在屏幕上显示报表,可令 ScrollBox.Visible:=false;
还可以用Tpanel组合拼成各种复杂表头。
-------------------------------- 修 改 记 录 ----------------------------------
修改日期:1998.10
修 改 者:BlueBoy、YelloBoy
修改内容:
1.增加打印预览功能;
2.增加按指定放大倍数进行打印的功能;
3.增加选择打印起止页码的功能;
4.增加打印页码位置、格式、字体大小的功能;
5.增加自动重复打印表头、页头、表尾、页尾的功能;
6.增加StringGrid、Dbgrid自动添加空行置满页的功能;
7.用坐标原点的方法修改获取各控件的Top、Left的计算方法;
8.增加Panel嵌套打印功能;
9.修改PrintImage;
10.增加支持 TSGAccess控件的打印功能;
11.增加支持TMergeGrid控件的打印功能;
版 本:Ver 2.0
-------------------------------- 接 口 文 档 ----------------------------------
定 义:(ScrollBox中的构件的Tag=)
1. 表头(自动根据表体调整位置)
2. 页头(固定在每页头位置)
3. 表体(循环)
4. 页脚(固定在每页脚位置)
5. 表尾(自动根据表体调整位置)
6. 对于Edit和DBedit,当helpcontext=100时,打印边框
变量定义:
FScrollingName:TscrollingWinControl;
(SCROLLBOX)
C : array[0..255] of char;
(处理数据串的中间变量)
PageNumber:integer;
(打印机的页数)
tmpString:string;
(中间串)
Format : Word;
(打印机的打印格式)
R: TRect;
(打印、预览块)
CLen : integer;
()
ScaleX, ScaleY:Real;
(预览窗口、打印机纸张与用户窗口的比例)
pageBottom: integer;
(纸下方应留的高度)
PDC : HDC;
(预览窗口、打印机的描述表)
PDCCanvas:TCanvas;
(预览窗口、打印机的画布)
SW : TScrollingWinControl;
(SCROLLBOX)
WidthSet,HeightSet:integer;
(纸LEFT、TOP应留的高度)
RowTop: integer;
(ROWTOP)
FGroupString:TStrings;
(TSTRINGS)
ifPreview:boolean;
(是否预览的中间变量)
pagetotal:integer;
(预览的总页数)
startpage:integer;
(预览的开始页)
endpage:integer;
(预览的结束页)
pageRowNum:integer;
(对于GRID类的构件每页的行数)
scalebynum:integer;
(预览的放大次数)
ifmove:boolean;
(是否移动)
mousex,mousey:integer;
(鼠标位置)
foottop:integer;
(表脚在预览窗口、打印机的逻辑物理TOP)
footheight:double;
(表脚的逻辑Height)
realfoottop:integer;
(表脚在预览窗口、打印机的物理TOP)
属 性:
1. ScrollingName (连接的ScrollBox的名称)
2. Scale (打印的比例)
3. ifAutoScale (是否根据纸张自动调节比例)
4. ifShowForm (是否显示预览窗口)
5. ImageList (连接的ImageList的名称)
6. PageNopos (打印页注的位置)
7. PageNoConent (打印页注的内容)
8. PageNoConentFontSize (打印页注的字体大小)
9. ifShowPageNo (是否显示页注)
10. ifLasterPrint (是否LasterPrint)
11. ifPrintEmptyLine (是否打印空行置满页)
方 法:
1. Create
2. Excute (开始执行打印作业)
3. Destroy
-------------------------------------------------------------------------------
修改日期:1999.3
修 改 者:YelloBoy
修改内容:1.支持mergeGrid的打印;
2.stringgrid支持折行打印;
3.修改打印弹出的对话框的界面;
属 性:ifWordWrap (是否折行打印)
变 量:PageRowNumw (折行打印时,每页行数的记录数组)
-------------------------------------------------------------------------------
修改日期:2000.3
修 改 者:YelloBoy
修改内容:1.支持DBtext、DBedit、DBmemo、radiobutton、checkbox的打印;
2.修改stringgrid错误;
3.增加了打印机的设置;
4.增加了edit打印边框的功能;
属 性:printsetup(打印机的设置属性)
}
//{$define psgaccess} // 用于确定是否打印用户构件(目前为TPSgAccess),如编译出错屏蔽掉该行
//{$define MergeGrid} // 用于确定是否打印用户构件(目前为TMergeGrid),如编译出错屏蔽掉该行
unit printf ;
interface
uses
windows,SysUtils,Buttons,WinTypes, WinProcs, Classes, Graphics, Controls,dialogs,{MyLabel,}
Forms,Messages, Grids, Printers,StdCtrls,ExtCtrls, ComCtrls,Mask,{Chartfx,Chart2fx,}DBGrids,
dbctrls{$ifdef psgaccess},PSGaccess{$endif}{$ifdef MergeGrid},mergegrid{$endif} ;
type
TPagePos=(ppTopLeft,ppTopMiddle,ppTopRight,ppBottomLeft,ppBottomMiddle,ppBottomRight);
TTPageSize=(sDefault,sCustom,sA3,sA4,sA5,sB4,sB5,sExcutive,sLegal,sLetter);
TPrintSetup=class(TPersistent)
private
fSetOrientation:TPrinterOrientation;
fPageSize:Ttpagesize;
fpageheight:integer;
fpagewidth:integer;
fReFresh:boolean;
fprintproperties:Tstrings;
ftest:string;
public
procedure setpagehw(inval:Ttpagesize);
procedure setpageheight(inval:integer);
procedure setpagewidth(inval:integer);
procedure SetPrintProperties(inval:Tstrings);
procedure getprintsetuplist;
procedure setRefresh(inval:boolean);
function gettest:string;
published
property SetOrientation:TPrinterOrientation read fSetOrientation write fSetOrientation;
property PageSize:Ttpagesize read fPageSize write setpagehw;
property PageHeight:integer read fpageheight write setpageheight;
property pagewidth:integer read fpagewidth write setpagewidth;
property printproperties:tstrings read fprintproperties write SetPrintProperties;
property Refresh:boolean read fRefresh write setRefresh;
property Test:string read gettest write ftest;
end;

TPrint = class(TComponent)
private
FScrollingName:TscrollingWinControl;
C : array[0..255] of char;
PageNumber:integer;
tmpString:string;
Format : Word;
R: TRect;
CLen : integer;
FLasterPrint:Boolean;
ScaleX, ScaleY:Real;
pageBottom: integer;
PDC : HDC;
PDCCanvas:TCanvas;
SW : TScrollingWinControl;
WidthSet,HeightSet:integer;
RowTop: integer;
FGroupString:TStrings;
fscale:double;
fautoscale:boolean;
fifShowForm:boolean;
ifPreview:boolean;
fimagelist:TImagelist;
fPagepos:Tpagepos;
fPageNOconent:string;
fPageNOconentsize:integer;
fifShowPageNo:boolean;
fifprintEmptyLine:boolean;
fifwordWrap:boolean;
fifNumRight:boolean;
fprintsetup:Tprintsetup;
pagetotal:integer;
startpage:integer;
endpage:integer;
pageRowNum:integer;
scalebynum:integer;
ifmove:boolean;
mousex:integer;
mousey:integer;
foottop:integer;
footheight:double;
realfoottop:integer;
PageRowNumw:array[1..5000] of integer;
// function GetInitialValues: TStrings;
// procedure SetInitialValues(Value: TStrings);
procedure PrintPage;
procedure PrintPageHeader;
procedure PrintTableHeader;
procedure PrintTable;
procedure PrintTableBottom;
procedure PrintPageBottom;
procedure printpagenum;
procedure PrintBevel(Bevel:TBevel);
procedure PrintItem(controlItem:integer);
function ScaleToPrinter(R:TRect):TRect;
procedure PrintMemo(MC:TMemo);
procedure PrintDbMemo(MC:TDbMemo);
procedure PrintEdit(MC:TMemo);
procedure printDBedit(MC:TDBedit);
procedure PrintRadioButton(MC:TRadioButton);
procedure printRadiogroup(MC:Tradiogroup);
procedure printDBRadiogroup(MC:TDBradiogroup);
procedure PrintCheckBox(MC:TCheckBox);
procedure PrintLabel(MC:TLabel);
procedure printDBtext(MC:TDBtext);
procedure PrintShape(SC:TShape);
procedure PrintStringGrid(SGC:TStringGrid);
procedure PrintStringGridW(SGC:TSTringGrid);
{procedure PrintChart(Chart: TChartFX);}
{procedure PrintCheckBox(CB: TCheckBox);}
procedure PrintImage(IC: TImage);
procedure PrintPanel(Panel:TPanel);
procedure PrintDBGrid(DGC:TDBGrid);
procedure PrintHeader(MC:THeader);
function AnalyString(i:integer;
var c:string):integer;
function isNumber(strings: PChar):Boolean;
procedure ClearString_C ;
procedure PrintForm;
function begin
Print:Boolean;
procedure FormClose(sender:Tobject);
procedure FormPrintOnClick(sender:Tobject);
procedure FormCheckboxOnCheck(sender:Tobject);
procedure FormEditOnchange(sender:Tobject);
procedure FormBitbtn_PreviewOnclick(sender:Tobject);
procedure FormBitbtn_setupOnClick(sender:Tobject);
procedure FormResize(sender:Tobject);
procedure FormBitBtn_priorClick(sender:Tobject);
procedure FormBitbtn_nextClick(sender:Tobject);
procedure Image1MouseDown(Sender: TObject;
Button: TMouseButton;
Shift: TShiftState;
X, Y: Integer);
procedure Image1MouseUp(Sender: TObject;
Button: TMouseButton;
Shift: TShiftState;
X, Y: Integer);
procedure initform;
procedure getrownum(SGC:TSTringGrid);
procedure getrownumw(SGC:TSTringGrid);
procedure setprintsetup(inval:Tprintsetup);
procedure getprintsetup;
procedure updateprintsetup;
{$ifdef MergeGrid}
procedure printmergegrid(SGC:Tmergegrid);
function Max(i1,i2:Integer):Integer;
function Min(i1,i2:Integer):Integer;
{$endif}
public
constructor Create(AOwner: TComponent);
override;
destructor Destroy;
override;
function Execute:Boolean;
published
property ScrollingName: TScrollingWinControl read FScrollingName
write FScrollingName;
property ifLasterPrint:Boolean read FLasterPrint write FLasterPrint;
//property GroupString:TStrings read GetInitialValues
//write SetInitialValues;
property Scale:double read fscale write fscale ;
property ifAutoScale:boolean read fautoscale write fautoscale;
property ifShowForm:boolean read fifShowForm write fifShowForm;
property ImageList:Timagelist read fimagelist write fimagelist;
property PageNopos:tpagepos read fpagepos write fpagepos ;
property PageNoConent:string read fpageNOconent write fpageNOconent;
property PageNoConentFontSize:integer read fpageNoconentsize write fpageNoconentsize;
property ifShowPageNo:boolean read fifShowPageNo write fifShowPageNo;
property ifPrintEmptyLine:boolean read fifprintEmptyline write fifprintemptyline;
property ifWordWrap:boolean read fifWordWrap write fifWordWrap;
property ifNumRight:boolean read fifNumRight write fifNumRight;
property Printsetup:Tprintsetup read fprintsetup write setprintsetup;
end;

procedure Register;
implementation
procedure Register;
begin
RegisterComponents('PrintF', [TPrint]);
end;

function Tprintsetup.gettest:string;
begin
if fpageheight>100 then
result:='height>100'
else
result:='height<100';
end;

procedure Tprintsetup.setpageheight(inval:integer);
begin
fpageheight:=inval;
if fpageheight<>0 then
fpagesize:=sCustom;
end;

procedure Tprintsetup.setpagewidth(inval:integer);
begin
fpagewidth:=inval;
if fpagewidth>0 then
fpagesize:=sCustom;
end;

procedure Tprintsetup.setRefresh(inval:boolean);
begin
frefresh:=inval;
fprintproperties.Clear;
getprintsetuplist;
end;

procedure Tprintsetup.getprintsetuplist;
var
Device : array[0..cchDeviceName - 1] of Char;
Driver : array[0..(MAX_PATH -1)] of Char;
Port : array[0..32]of Char;
hDMode : THandle;
pDMode : PDevMode;
begin
Printer.GetPrinter(Device,Driver,Port,hDMode);
if hDMode<>0 then
begin
pDMode := GlobalLock(hDMode);
if pDMode<>nil then
begin
//get print properties and set printpropertis
with pDMode^do
begin
with fprintpropertiesdo
begin
Add('dmDeviceName='+string(dmDeviceName));
Add('dmSpecVersion='+inttostr(dmSpecVersion));
Add('dmDriverVersion='+inttostr(dmDriverVersion));
Add('dmSize='+inttostr(dmSize));
Add('dmDriverExtra='+inttostr(dmDriverExtra));
Add('dmFields='+inttostr(dmFields));
if pDMode.dmOrientation=DMORIENT_PORTRAIT then
Add('dmOrientation=poPortrait')
else
Add('dmOrientation=poLandscape');
Add('dmPaperSize='+inttostr(dmPaperSize));
Add('dmPaperLength='+inttostr(dmPaperLength));
Add('dmPaperWidth='+inttostr(dmPaperWidth));
Add('dmScale='+inttostr(dmScale));
Add('dmCopies='+inttostr(dmCopies));
Add('dmDefaultSource='+inttostr(dmDefaultSource));
Add('dmPrintQuality='+inttostr(dmPrintQuality));
Add('dmColor='+inttostr(dmColor));
Add('dmDuplex='+inttostr(dmDuplex));
Add('dmYResolution='+inttostr(dmYResolution));
Add('dmTTOption='+inttostr(dmTTOption));
end;
end;
//end get
ResetDC(Printer.Handle,pDMode^);
GlobalUnlock(hDMode);
end;
end;
end;

procedure Tprintsetup.setpagehw(inval:Ttpagesize);
begin
fpagesize:=inval;
case fpagesize of
sA3,sA4,sA5,sB4,sB5,sExcutive,sLegal,sLetter:
begin
fpageheight:=0;
fpagewidth:=0;
end;
sCustom :begin
fpageheight:=1900;
fpagewidth:=1140;
end;
else
fpageheight:=0;
fpagewidth:=0;
end;
end;

procedure Tprintsetup.SetPrintProperties(inval:Tstrings);
begin
if inval<>nil then
begin
fprintproperties.Assign(inval);
frefresh:=false;
end;
end;

constructor TPrint.Create(AOwner: TComponent);
begin
inherited Create(AOwner);
FGroupString := TStringList.Create;
fscale:=1.0;
fautoscale:=false;
fifShowForm:=true;
fpagepos:=ppBottomRight;
fpageNoconent:='第#页 共$页';
fpageNoconentsize:=7;
fifshowpageno:=false;
fifprintemptyline:=false;
fifWordWrap:=false;
fifNumright:=false;
ifPreview:=false;
scalebynum:=1;
foottop:=0;
footheight:=0;
realfoottop:=0;
pagetotal:=1;
startpage:=0;
endpage:=0;
pageRowNum:=0;
ifmove:=false;
fprintsetup:=Tprintsetup.Create;
fprintsetup.fPageSize:=sDefault;
fprintsetup.fprintproperties:=tstringlist.Create;
getprintsetup;
fprintsetup.getprintsetuplist;
fprintsetup.Refresh:=false;
end;

procedure Tprint.getprintsetup;
var
Device : array[0..cchDeviceName - 1] of Char;
Driver : array[0..(MAX_PATH -1)] of Char;
Port : array[0..32]of Char;
hDMode : THandle;
pDMode : PDevMode;
begin
Printer.GetPrinter(Device,Driver,Port,hDMode);
if hDMode<>0 then
begin
pDMode := GlobalLock(hDMode);
if pDMode<>nil then
begin
if pDMode.dmOrientation=DMORIENT_PORTRAIT then
fprintsetup.SetOrientation:=poPortrait
else
fprintsetup.SetOrientation:=poLandscape;
case pDMode^.dmPaperSize of
DMPAPER_A3 :fprintsetup.PageSize:=sA3;
DMPAPER_A4 :fprintsetup.PageSize:=sA4;
DMPAPER_A5 :fprintsetup.PageSize:=sA5;
DMPAPER_B4 :fprintsetup.PageSize:=sB4;
DMPAPER_B5 :fprintsetup.PageSize:=sB5;
DMPAPER_EXECUTIVE:fprintsetup.PageSize:=sExcutive;
DMPAPER_LEGAL :fprintsetup.PageSize:=sLegal;
DMPAPER_LETTER :fprintsetup.PageSize:=sLetter;
else
fprintsetup.PageSize:=sDefault;
end;
fprintsetup.fpageheight:=pDMode^.dmPaperLength;
fprintsetup.fpagewidth:=pDMode^.dmPaperwidth;
ResetDC(Printer.Handle,pDMode^);
GlobalUnlock(hDMode);
end;
end;
end;

procedure Tprint.setprintsetup(inval:Tprintsetup);
begin
if inval<>nil then
fprintsetup.Assign(inval);
end;

procedure TPrint.ClearString_C ;
var
k: integer ;
begin
for k := 0 to 255do
C[k] := #0 ;
end;

procedure Tprint.UpdatePrintSetup;
var
Device : array[0..cchDeviceName - 1] of Char;
Driver : array[0..(MAX_PATH -1)] of Char;
Port : array[0..32]of Char;
hDMode : THandle;
pDMode : PDevMode;
begin
Printer.GetPrinter(Device,Driver,Port,hDMode);
if hDMode<>0 then
begin
pDMode := GlobalLock(hDMode);
if pDMode<>nil then
begin
//set papersize
case printsetup.fPageSize of
sCustom:
begin
//dmPaperSize 必 须 设 置 成256
// pDMode^.dmPaperLength:= 1140;
// pDMode^.dmPaperWidth := 1900;
pDMode^.dmPaperSize := 256;
pDMode^.dmPaperLength:= fprintsetup.fpageheight;
pDMode^.dmPaperWidth := fprintsetup.fpagewidth;
end;
sA3:pDMode^.dmPaperSize := DMPAPER_A3;
sA4:pDMode^.dmPaperSize := DMPAPER_A4;
sA5:pDMode^.dmPaperSize := DMPAPER_A5;
sB4:pDMode^.dmPaperSize := DMPAPER_B4;
sB5:pDMode^.dmPaperSize := DMPAPER_B5;
sExcutive:pDMode^.dmPaperSize := DMPAPER_EXECUTIVE;
sLegal:pDMode^.dmPaperSize := DMPAPER_LEGAL;
sLetter:pDMode^.dmPaperSize := DMPAPER_LETTER;
else
pDMode^.dmPaperSize := DMPAPER_A4;
end;
pDMode^.dmFields := pDMode^.dmFields or DM_PAPERSIZE;
pDMode^.dmFields := pDMode^.dmFields or DM_PAPERLENGTH;
pDMode^.dmFields := pDMode^.dmFields or DM_PAPERWIDTH;
//set Orientation
if fprintsetup.fSetOrientation=poPortrait then
pDMode^.dmOrientation:=DMORIENT_PORTRAIT
else
pDMode^.dmOrientation:=DMORIENT_LANDSCAPE;
ResetDC(Printer.Handle,pDMode^);
GlobalUnlock(hDMode);
end;
end;
end;

function TPrint.Execute:Boolean;
begin
updateprintsetup;
try
begin
if fifShowForm then
printform
else
begin
PDCCanvas:=printer.Canvas;
begin
Print;
end;
end;
except
result:=false;
exit;
end;
result:=true;
end;

function TPrint.begin
Print:boolean;
begin
PageNumber:=1;
SW:=ScrollingName;
PrintPage;
result := true ;
end;

destructor TPrint.Destroy;
begin
FGroupString.Free;
inherited Destroy;
end;

{procedure TPrint.SetInitialValues(Value: TStrings);
begin
FGroupString.Assign(Value);
end;
}
{function TPrint.GetInitialValues: TStrings;
begin
Result := FGroupString;
end;
}
function TPrint.ScaleToPrinter(R:TRect):TRect;
begin
R.Top :=Round((R.Top +SW.VertScrollBar.Position)*ScaleY+0.5)+HeightSet;
R.Left :=Round((R.Left+SW.HorzScrollBar.Position)*ScaleX+0.5)+WidthSet;
R.Bottom:=Round((R.Bottom+SW.VertScrollBar.Position)*ScaleY+0.5)+HeightSet;
R.Right :=Round((R.Right +SW.HorzScrollBar.Position)*ScaleX+0.5)+WidthSet;
R.Left:=R.Left-1;
R.Top:=R.Top-1;
Result := R;
end;

function TPrint.isNumber(strings:PChar):Boolean;
var
i: integer ;
begin
if fifNumright then
isnumber:=false
else
begin
if strcomp(strings,'')=0 then
begin
isNUmber:=false;
exit;
end;
for i:=0 to strLen(strings)-1do
if ((strings>'9') or (strings<'0')) AND (strings<>'.') then
begin
isNumber:=False;
exit;
end;
isNumber:=True;
end;
end;

procedure TPrint.PrintMemo(MC:TMemo);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
linesPerPage,foo:integer ;
i,j:integer;
s1,s2:string;
begin
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size:=round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size:=round(MC.Font.Size*scalex);//+0.5);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
if MC.Align = alNone then
begin
R.Left :=MC.ClientOrigin.x-FScrollingName.ClientOrigin.x;
R.Top := MC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
R.Right := R.Left + MC.Width;
R.Bottom := R.Top + MC.Height;
end
else
begin
R.Left :=MC.ClientOrigin.x-FScrollingName.ClientOrigin.x-1;
R.Top := MC.ClientOrigin.y-FScrollingName.ClientOrigin.y-2;
R.Right := R.Left + MC.Width;//-Panel.BevelWidth;
R.Bottom := R.Top + MC.Height;//-Panel.BevelWidth;
end;
{R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Right:=r.Left+MC.Width;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Right;//+70;}
R := ScaleToPrinter(R);
if MC.BorderStyle = bsSingle then
PDCCanvas.Rectangle(R.Left, R.Top, R.Right,R.Bottom);
Format := DT_LEFT or DT_WORDBREAK or DT_SINGLELINE or DT_VCENTER;
linesPerPage := 0 ;
for foo :=0 to MC.Lines.Count-1do
begin
R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Right:=r.Left+MC.Width;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Right+70;
if foo>0 then
begin
R.Top :=R.Top + 3 ;
R.Left :=R.Left ;
end;
R.Top :=R.Top+(MC.Font.Size+3)*foo;
R.Bottom:=R.top+(MC.Font.Size+3);
if (R.top > Printer.PageHeight/ScaleY-PageBottom) AND { added by xzh}
(foo < MC.Lines.Count-1) then
begin
if linesPerPage = 0 then
linesPerPage := foo ;
if ((foo mod linesPerPage) = 0 ) then
begin
PrintPageBottom ;
PrintPageHeader ;
R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Right:=r.Left+MC.Width;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom:=R.Top+MC.Height;
PDCCanvas.Font := MC.Font ;
PDCCanvas.Font.Size := round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(MC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle ;
if MC.BorderStyle = bsSingle then
begin
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left, R.Top, R.Right,R.Bottom);
end;
end;
{ end of i mod linesPerPage }
R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Right:=r.Left+MC.Width;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Right+70;
if foo>0 then
begin
R.Top :=R.Top + 3 ;
R.Left :=R.Left ;//原+3
end;
R.Top:=R.Top+(MC.Font.Size+3)*(foo mod LinesPerPage);
R.Bottom:=R.Top+(MC.Font.Size+3);
end;
{ end next page}
R := ScaleToPrinter(R);
ClearString_C ;
s1:= MC.Lines.Strings[foo];
s2:='';
j:=0;
for i:=1 to length(s1)do
begin
if (copy(s1,i,1)<>' ') or (j>=(i div 25)) then
begin
s2:=s2+copy(s1,i,1);
if (copy(s1,i,1)=' ') then
J:=j+1 else
j:=0;
end else
begin
j:=j+1;
end;
end;
StrPCopy(C,s2);
if ifpreview then
PDCCanvas.TextOut(r.left,r.top,C)
else
WinProcs.DrawText(PDC, C, StrLen(C), R, Format);
end;
{ for all lines }
end;

procedure TPrint.PrintDbMemo(MC:TDbMemo);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
linesPerPage,foo:integer ;
i,j:integer;
s1,s2:string;
begin
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size:=round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size:=round(MC.Font.Size*scalex);//+0.5);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
if MC.Align = alNone then
begin
R.Left :=MC.ClientOrigin.x-FScrollingName.ClientOrigin.x;
R.Top := MC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
R.Right := R.Left + MC.Width;
R.Bottom := R.Top + MC.Height;
end
else
begin
R.Left :=MC.ClientOrigin.x-FScrollingName.ClientOrigin.x-1;
R.Top := MC.ClientOrigin.y-FScrollingName.ClientOrigin.y-2;
R.Right := R.Left + MC.Width;//-Panel.BevelWidth;
R.Bottom := R.Top + MC.Height;//-Panel.BevelWidth;
end;
{R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Right:=r.Left+MC.Width;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Right;//+70;}
R := ScaleToPrinter(R);
if MC.BorderStyle = bsSingle then
PDCCanvas.Rectangle(R.Left, R.Top, R.Right,R.Bottom);
Format := DT_LEFT or DT_WORDBREAK or DT_SINGLELINE or DT_VCENTER;
linesPerPage := 0 ;
for foo :=0 to MC.Lines.Count-1do
begin
R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Right:=r.Left+MC.Width;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Right+70;
if foo>0 then
begin
R.Top :=R.Top + 3 ;
R.Left :=R.Left ;
end;
R.Top :=R.Top+(MC.Font.Size+3)*foo;
R.Bottom:=R.top+(MC.Font.Size+3);
if (R.top > Printer.PageHeight/ScaleY-PageBottom) AND { added by xzh}
(foo < MC.Lines.Count-1) then
begin
if linesPerPage = 0 then
linesPerPage := foo ;
if ((foo mod linesPerPage) = 0 ) then
begin
PrintPageBottom ;
PrintPageHeader ;
R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Right:=r.Left+MC.Width;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom:=R.Top+MC.Height;
PDCCanvas.Font := MC.Font ;
PDCCanvas.Font.Size := round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(MC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle ;
if MC.BorderStyle = bsSingle then
begin
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left, R.Top, R.Right,R.Bottom);
end;
end;
{ end of i mod linesPerPage }
R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Right:=r.Left+MC.Width;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Right+70;
if foo>0 then
begin
R.Top :=R.Top + 3 ;
R.Left :=R.Left ;//原+3
end;
R.Top:=R.Top+(MC.Font.Size+3)*(foo mod LinesPerPage);
R.Bottom:=R.Top+(MC.Font.Size+3);
end;
{ end next page}
R := ScaleToPrinter(R);
ClearString_C ;
s1:= MC.Lines.Strings[foo];
s2:='';
j:=0;
for i:=1 to length(s1)do
begin
if (copy(s1,i,1)<>' ') or (j>=(i div 25)) then
begin
s2:=s2+copy(s1,i,1);
if (copy(s1,i,1)=' ') then
J:=j+1 else
j:=0;
end else
begin
j:=j+1;
end;
end;
StrPCopy(C,s2);
if ifpreview then
PDCCanvas.TextOut(r.left,r.top,C)
else
WinProcs.DrawText(PDC, C, StrLen(C), R, Format);
end;
{ for all lines }
end;

procedure TPrint.PrintEdit(MC:TMemo);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Height:integer;
begin
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size :=round(MC.Font.Size*fscale);
if ifpreview then
PDCcanvas.Font.Size:=round(MC.Font.Size*scaleX-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
if isNumber(C) then
begin
Format := DT_RIGHT or DT_SINGLELINE or DT_VCENTER;
r.left:=r.left-20;
r.Right:=r.right-5;
end else
begin
Format := DT_LEFT OR DT_WORDBREAK or DT_SINGLELINE or DT_VCENTER;
r.Right:=r.Right+20;
end;
Height:=R.Bottom-R.Top;
R.Bottom := R.Top+Height;
///////////////////////
if isnumber(c) then
begin

r.Top:=r.top+trunc((mc.height-Mc.Font.Size)/2);
r.Bottom:=r.top+MC.Height;
r.Right:=r.Right-5;
r.Left:=r.Left-5;
end else
begin
r.Top:=r.top+trunc((mc.height-Mc.Font.Size)/2);
r.Left:=r.Left+trunc((mc.Font.Size)/2);
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
/////////////////////////
R := ScaleToPrinter(R);
CLen := MC.GetTextBuf(C,255);
if ifpreview then
PDCCanvas.TextOut(R.left,R.top,C)
else
WinProcs.DrawText(PDC, C, strlen(c), R, Format);
if MC.HelpContext=100 then
begin
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
Format := DT_SINGLELINE or DT_VCENTER;
R.Top := MC.ClientOrigin.y-SW.ClientOrigin.y-1;
R.Bottom := R.Top+MC.Height;
R.Left := MC.ClientOrigin.x-SW.ClientOrigin.x-1;
R.Right := R.Left+MC.Width;
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom);
end;

end;

procedure TPrint.PrintDBEdit(MC:TDBedit);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Height:integer;
begin
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size :=round(MC.Font.Size*fscale);
if ifpreview then
PDCcanvas.Font.Size:=round(MC.Font.Size*scaleX-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
if isNumber(C) then
begin
Format := DT_RIGHT or DT_SINGLELINE or DT_VCENTER;
r.left:=r.left-20;
r.Right:=r.right-5;
end else
begin
Format := DT_LEFT OR DT_WORDBREAK or DT_SINGLELINE or DT_VCENTER;
r.Right:=r.Right+20;
end;
Height:=R.Bottom-R.Top;
R.Bottom := R.Top+Height;
///////////////////////
if isnumber(c) then
begin

r.Top:=r.top+trunc((mc.height-Mc.Font.Size)/2);
r.Bottom:=r.top+MC.Height;
r.Right:=r.Right-5;
r.Left:=r.Left-5;
end else
begin
r.Top:=r.top+trunc((mc.height-Mc.Font.Size)/2);
r.Left:=r.Left+trunc((mc.Font.Size)/2);
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
/////////////////////////
R := ScaleToPrinter(R);
if MC.DataSource.DataSet.Active<>false then
if MC.DataSource.DataSet.RecordCount<>0 then
begin
clen:=0;
CLen:= strlen(pchar(MC.field.asstring));
if ifpreview then
PDCCanvas.TextOut(R.left,R.top,pchar(MC.field.asstring))
else
WinProcs.DrawText(PDC, pchar(MC.field.asstring), clen, R, Format);
end;
if MC.HelpContext=100 then
begin
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
Format := DT_SINGLELINE or DT_VCENTER;
R.Top := MC.ClientOrigin.y-SW.ClientOrigin.y-1;
R.Bottom := R.Top+MC.Height;
R.Left := MC.ClientOrigin.x-SW.ClientOrigin.x-1;
R.Right := R.Left+MC.Width;
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom);
end;

end;

procedure TPrint.PrintDBRadiogroup(MC:TDBRadiogroup);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Height:integer;
lsstr:string;
begin
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size :=round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(MC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
R.Left :=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Top := MC.ClientOrigin.y-sw.ClientOrigin.y;
R.Right := R.Left + MC.Width+70;
R.Bottom := R.Top + MC.Height;
//*****************//
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
//*****************//
Height := R.Bottom-R.Top;
R.Bottom := R.Top+Height;
//******************//
//临时使用
R.Top:=R.Top+trunc((R.Bottom-R.Top-Mc.Font.Size)/2);
R.Left:=R.Left+Mc.Font.Size;
//******************//
R := ScaleToPrinter(R);
Format := DT_LEFT or DT_SINGLELINE or DT_VCENTER;
lsstr:='';
if mc.ItemIndex>=0 then
lsstr:='⊙ '+mc.Items.Strings[mc.itemindex];
CLen := strlen(pchar(lsstr));
WinProcs.DrawText(PDC, pchar(lsstr), CLen, R, Format);
end;

procedure TPrint.PrintRadiogroup(MC:TRadiogroup);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Height:integer;
lsstr:string;
begin
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size :=round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(MC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
R.Left :=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Top := MC.ClientOrigin.y-sw.ClientOrigin.y;
R.Right := R.Left + MC.Width+70;
R.Bottom := R.Top + MC.Height;
//*****************//
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
//*****************//
Height := R.Bottom-R.Top;
R.Bottom := R.Top+Height;
//******************//
//临时使用
R.Top:=R.Top+trunc((R.Bottom-R.Top-Mc.Font.Size)/2);
R.Left:=R.Left+Mc.Font.Size;
//******************//
R := ScaleToPrinter(R);
Format := DT_LEFT or DT_SINGLELINE or DT_VCENTER;
lsstr:='';
if mc.ItemIndex>=0 then
lsstr:='⊙ '+mc.Items.Strings[mc.itemindex];
CLen := strlen(pchar(lsstr));
WinProcs.DrawText(PDC, pchar(lsstr), CLen, R, Format);
end;

procedure TPrint.PrintRadiobutton(MC:TRadioButton);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Height:integer;
lsstr:string;
begin
//MC.Font.size:=MC.Font.size+3;
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size :=round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(MC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
//R.Left := MC.Left;
//R.Top := MC.Top;
//R.Right := MC.Left + MC.Width+70;
//R.Bottom := MC.Top + MC.Height;
//R := MC.BoundsRect;
// modi by hq
R.Left :=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Top := MC.ClientOrigin.y-sw.ClientOrigin.y;
R.Right := R.Left + MC.Width+70;
R.Bottom := R.Top + MC.Height;
//*****************//
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
//*****************//
Height := R.Bottom-R.Top;
R.Bottom := R.Top+Height;
R := ScaleToPrinter(R);
Format := DT_LEFT or DT_SINGLELINE or DT_VCENTER;
if MC.Alignment = taCenter then
Format := Format or DT_CENTER;
{ if MC.Alignment = taRightJustify then
Format := Format or DT_RIGHT;}
lsstr:='';
if mc.Checked then
lsstr:='⊙ '+mc.Caption
else
lsstr:='◎ '+mc.Caption;
CLen := strlen(pchar(lsstr));
WinProcs.DrawText(PDC, pchar(lsstr), CLen, R, Format);
end;

procedure TPrint.PrintCheckBox(MC:TCheckBox);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Height:integer;
lsstr:string;
begin
//MC.Font.size:=MC.Font.size+3;
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size :=round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(MC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
//R.Left := MC.Left;
//R.Top := MC.Top;
//R.Right := MC.Left + MC.Width+70;
//R.Bottom := MC.Top + MC.Height;
//R := MC.BoundsRect;
// modi by hq
R.Left :=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Top := MC.ClientOrigin.y-sw.ClientOrigin.y;
R.Right := R.Left + MC.Width+70;
R.Bottom := R.Top + MC.Height;
//*****************//
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
//*****************//
Height := R.Bottom-R.Top;
R.Bottom := R.Top+Height;
R := ScaleToPrinter(R);
Format := DT_LEFT or DT_SINGLELINE or DT_VCENTER;
if MC.Alignment = taCenter then
Format := Format or DT_CENTER;
{if MC.Alignment = taRightJustify then
Format := Format or DT_RIGHT;}
lsstr:='';
if mc.Checked then
lsstr:='■ '+mc.Caption
else
lsstr:='□ '+mc.Caption;
CLen := strlen(pchar(lsstr));
WinProcs.DrawText(PDC, pchar(lsstr), CLen, R, Format);
end;

procedure TPrint.PrintLabel(MC:TLabel);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Height,i:integer;
begin
//MC.Font.size:=MC.Font.size+3;
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size :=round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(MC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
//R.Left := MC.Left;
//R.Top := MC.Top;
//R.Right := MC.Left + MC.Width+70;
//R.Bottom := MC.Top + MC.Height;
//R := MC.BoundsRect;
// modi by hq
R.Left :=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Top := MC.ClientOrigin.y-sw.ClientOrigin.y;
R.Right := R.Left + MC.Width+70;
R.Bottom := R.Top + MC.Height;
//*****************//
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
//*****************//
Height := R.Bottom-R.Top;
R.Bottom := R.Top+Height;
R := ScaleToPrinter(R);
Format := DT_LEFT or DT_SINGLELINE or DT_VCENTER;
if MC.WordWrap then
Format := format or DT_WORDBREAK;
if MC.Alignment = taCenter then
Format := Format or DT_CENTER;
{ if MC.Alignment = taRightJustify then
Format := Format or DT_RIGHT;}
CLen := MC.GetTextBuf(C,255);
for i:=0 to CLen-1do
if (C='%') AND (C[i+1]='%') then
break;
if i < CLen-1 then
begin
C:=CHR(PageNumber div 10+ORD('0'));
if C='0' then
C:=' ';
C[i+1]:=CHR(PageNumber mod 10+ORD('0'));
end;
if (Clen>2) and (pagenumber<1) then
begin
strcat(C,' ');clen:=strlen(c);
end;
WinProcs.DrawText(PDC, C, CLen, R, Format);
end;

procedure TPrint.PrintDBtext(MC:TDBtext);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Height:integer;
begin
if MC.DataSource.DataSet.Active=false then
exit;
if MC.DataSource.DataSet.RecordCount=0 then
exit;
//MC.Font.size:=MC.Font.size+3;
PDCCanvas.Font := MC.Font;
PDCCanvas.Font.Size :=round(MC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(MC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
//R.Left := MC.Left;
//R.Top := MC.Top;
//R.Right := MC.Left + MC.Width+70;
//R.Bottom := MC.Top + MC.Height;
//R := MC.BoundsRect;
// modi by hq
R.Left :=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Top := MC.ClientOrigin.y-sw.ClientOrigin.y;
R.Right := R.Left + MC.Width+70;
R.Bottom := R.Top + MC.Height;
//*****************//
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
//*****************//
Height := R.Bottom-R.Top;
R.Bottom := R.Top+Height;
R := ScaleToPrinter(R);
Format := DT_LEFT or DT_SINGLELINE or DT_VCENTER;
if MC.Alignment = taCenter then
Format := Format or DT_CENTER;
{ if MC.Alignment = taRightJustify then
Format := Format or DT_RIGHT;}
clen:=0;
if MC.field.asstring='' then
exit;
CLen:= strlen(pchar(MC.field.asstring));
WinProcs.DrawText(PDC, pchar(MC.field.asstring), CLen, R, Format);
end;

procedure TPrint.PrintShape(SC:TShape);
var
H, W, S : integer;
begin
{PrintShape}
PDCCanvas.Pen := SC.Pen;
PDCCanvas.Pen.Width := PDCCanvas.Pen.Width;
PDCCanvas.Brush := SC.Brush;
//R := ScaleToPrinter(SC.BoundsRect);
R.Left:=sc.ClientOrigin.x-SW.ClientOrigin.x;
R.Top:=sc.ClientOrigin.y-sw.ClientOrigin.y;
R.Right:=R.Left+sc.Width;
R.Bottom:=R.Top+sc.Height;
//**********************//
if (sC.Tag=4) or (sC.Tag=5) then
begin
R.Top := realfoottop+(sC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=sC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+sC.Height;
R.Right:=R.Left+sC.Width;
end;
//**********************//
//modify by hq
R:=scaletoprinter(R);
W := R.Right - R.Left;
H := R.Bottom - R.Top;
if W < H then
S := W else
S := H;
if SC.Shape in [stSquare, stRoundSquare, stCircle] then
begin
Inc(R.Left, (W - S) div 2);
Inc(R.Top, (H - S) div 2);
W := S;
H := S;
end;
with PDCCanvasdo
case SC.Shape of
stRectangle, stSquare:
PDCCanvas.Rectangle(R.Left+Pen.Width div 2, R.Top+Pen.Width div 2,
R.Left +W- Pen.Width +1, R.Top + H- Pen.Width +1);
stRoundRect, stRoundSquare:
PDCCanvas.RoundRect(R.Left, R.Top, R.Left + W, R.Top + H, S div 4, S div 4);
stCircle, stEllipse:
PDCCanvas.Ellipse(R.Left, R.Top, R.Left + W, R.Top + H);
end;
end;
{PrintShape}
function TPrint.AnalyString(i:integer;var c:string):integer;
var
j,posi,k:integer;
mark:integer;
begin
mark:=1;
posi:=1;
k:=0;
for j:=1 to Length(FGroupString)do
begin
case mark of
1: if FGroupString[j]='''' then
mark:=2;
2: if FGroupString[j]='''' then
begin
mark:=3;
{ c[0]:=chr(posi-1);}
SetLength(c,posi-1) ;
end
else
begin
c[posi]:=FGroupString[j];
posi:=posi+1;
end;
3: if (FGroupString[j]>='0') AND (FGroupString[j]<='9') then
k:=k*10+ord(FGroupString[j])-ord('0');
end;
end;
AnalyString:=k;
end;
{ ***************************************************************** }
procedure TPrint.PrintStringGrid(SGC:TStringGrid);
label
rplabel1;
var
TopR: array[0..255] of TRect;
Col_Widths:array[0..255] of integer;
T : TRect;
leftRow : integer;
J,K,m,n,i,v,ColLeft,RowRight:integer;
stringGridTop:array[0..255] of string;
if_repeat_top:boolean;
all,allnow:integer;
real:integer;
ifPrintTop:boolean;
begin

// showmessage(sgc.name);
//SGC.Font.size:=SGC.Font.size+3;
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size :=round(SGC.Font.Size*fscale+0.5);
if ifpreview then
PDCCanvas.Font.Size :=round(SGC.Font.Size*scalex-0.50);
PDCCanvas.Pen.Width:=Round(ScaleX);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
Format := DT_SINGLELINE or DT_VCENTER or DT_SINGLELINE or DT_VCENTER;
RowTop :=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
{ if pagerownum=0 then
begin
getrownum(sgc);
endpage:=round(SGC.RowCount/pagerowNum+0.5);
pagetotal:=endpage;
end;
}
leftRow:=0;
RowRight:=0;
m:=0;
for k:=0 to fGroupString.Count-1do
begin
j:=AnalyString(k,tmpString);
if j=0 then
begin
j:=Round(Printer.PageHeight/ScaleY)-PageBottom-(SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y);
i:=(SGC.CellRect(0,0).Bottom-SGC.CellRect(0,0).Top+1);
j:=(j div i)-m+1;
if(j>(SGC.RowCount-m)) then
j:= SGC.RowCount-m
else
begin
leftRow:=SGC.RowCount-m-j;
end;
end;

R.Top := (SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y)+
(SGC.CellRect(0,0).Bottom-SGC.CellRect(0,0).Top+1)*m;
R.Right := (SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x);
R.Bottom := (SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y)+
(SGC.CellRect(0,0).Bottom-SGC.CellRect(0,0).Top+1)*(m+j);
R.Left := R.Right -40;
T:=R;
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left, R.Top, R.Right, R.Bottom);
m:=m+j;
T.Bottom:=T.Top+SGC.CellRect(0,0).Bottom-SGC.CellRect(0,0).Top+1;
for n:=1 to length(tmpString)do
begin
R:=T;
T.Top:=T.Top+SGC.CellRect(0,0).Bottom-SGC.CellRect(0,0).Top+1;
T.Bottom:=T.Top+SGC.CellRect(0,0).Bottom-SGC.CellRect(0,0).Top+1;
R := ScaleToPrinter(R);
C[0]:=tmpString[n];
C[1]:=tmpString[n+1];
//留用 WinProcs.DrawText(PDC,C,2,R,(DT_VCENTER or DT_CENTER or DT_SINGLELINE));
{ n:=n+1;}
end;

end;

if pagerowNum=0 then
all:=SGC.RowCount - 1
else
if (endpage*pagerownum)<(SGC.RowCount - 1) then
all:=endpage*pagerownum
else
all:=SGC.RowCount - 1;
if SGC.FixedRows=1 then
if_repeat_top := TRUE
else
if_repeat_top := false;
if (sgc.FixedRows=1) and (startpage>0) then
v:=0+startpage*pagerowNum-startpage+1
else
v:=startpage*pagerowNum;
{if (sgc.FixedRows=1) and (startpage>2) then
real:=0+2*pagerowNum+(startpage-2)*(pagerowNum)
else
real:=0+startpage*pagerowNum;}
if (sgc.FixedRows=1) and (startpage>0) then
real:=0+startpage*pagerowNum-startpage+1
else
real:=0+startpage*pagerowNum;
if (not ifpreview) and (startpage<>0) and (if_repeat_top=true) then
ifprinttop:=true
else
ifprinttop:=false;
for K :=real to alldo
begin
rplabel1:
if (if_repeat_top = TRUE) and (v < K) then
if_repeat_top := False;
//留用
ColLeft :=(SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x);
for J:= 0 to SGC.ColCount - 1do
begin
if if_repeat_top = False then
begin
R := SGC.CellRect(J, K);
R.Top := RowTop;
R.Bottom := R.Top+SGC.RowHeights[k]+1;
R.Left := ColLeft;
if SGC.ColWidths[j]=0 then
R.Right := R.Left+SGC.ColWidths[j]
else
R.Right := R.Left+SGC.ColWidths[j]+1;
end
else
begin
R.Top := RowTop;
R.Bottom := R.Top+SGC.RowHeights[k]+1;
R.Left := ColLeft;
if SGC.ColWidths[j]=0 then
R.Right := R.Left+SGC.ColWidths[j]
else
R.Right := R.Left+SGC.ColWidths[j]+1;
end;

//为了增加打印下一页的stringGrid头标题,先读出并存储头标题信息;
//if K = 0 then
if ((k=startpage*pagerownum-startpage+1)and (startpage>0) )or( (k=startpage*pagerownum) and (startpage<1) )then
// if (k-all)=0 then
// if (k-startpage*pagerownum)=0 then
begin
stringgridTop[J] := SGC.Cells[J,0];
topR[J] := R;
Col_Widths[J] := SGC.ColWidths[J];
end;
//OK
if R.Right >= R.Left then
begin
R := ScaleToPrinter(R);
if J=SGC.ColCount-1 then
RowRight:=R.Right-1;
PDCCanvas.Brush.Style := bsClear;
ClearString_C ;
{ Added By XZH }
if (if_repeat_top = FALSE) then
StrPCopy(C, SGC.Cells[J,K])
else
begin
if ifpreview then
//打印头标题
StrPCopy(C,stringGridTop[J])
else
if startpage=0 then
StrPCopy(C,stringGridTop[J])
else
if pagenumber<>1 then
StrPCopy(C,stringGridTop[J])
else
if ifprinttop then
StrPCopy(C,stringGridTop[J])
else
StrPCopy(C, SGC.Cells[J,K]);
end;
if ifpreview then
begin
if ((k=startpage*pagerownum-startpage+1)and (startpage>0) )then
if sgc.FixedRows=1 then
StrPCopy(C,stringGridTop[J]);
end;
Format:=(DT_EXPANDTABS or DT_WORDBREAK)or (DT_VCENTER or DT_SINGLELINE);
if ifpreview then
begin
if isNumber(C) then
begin
Format:=Format or DT_RIGHT;R.Right :=R.Right-round(4*fscale);
end else
begin
Format:=Format or DT_LEFT;
R.Left :=R.Left +round(4*fscale);
end;
end else
begin
if isNumber(C) then
begin
Format:=Format or DT_RIGHT;R.Right :=R.Right-round(10*fscale);
end else
begin
Format:=Format or DT_LEFT;
R.Left :=R.Left +round(10*fscale);
end;
end;
Clen:=Strlen(C);
WinProcs.DrawText(PDC, C, CLen, R,Format);
if ifpreview then
if_repeat_top:= FALSE;
if ifpreview then
begin
if isNumber(C) then
R.Right:=R.Right+round(4*fscale) else
R.Left:=R.Left-round(4*fscale);
end else
begin
if isNumber(C) then
R.Right:=R.Right+round(10*fscale) else
R.Left:=R.Left-round(10*fscale);
end;
if (goHorzLine in SGC.Options)then
begin
R.bottom:=r.bottom-1;
PDCCanvas.MoveTo(R.Left,R.Top);
PDCCanvas.LineTo(R.Right,R.Top);
PDCCanvas.MoveTo(R.Left,R.Bottom);
PDCCanvas.LineTo(R.Right,R.Bottom);
end ;
if (goVertline in SGC.Options)then
begin
R.Right:=R.Right-1;
PDCCanvas.MoveTo(R.Left,R.Top);
PDCCanvas.LineTo(R.Left,R.Bottom);
PDCCanvas.MoveTo(R.Right,R.Top);
PDCCanvas.LineTo(R.Right,R.Bottom);
end;
//if (k=startpage*pagerownum) then
//if (k=all) then
if ((k=startpage*pagerownum-startpage+1)and (startpage>0) )or( (k=startpage*pagerownum) and (startpage<1) )then
begin
PDCCanvas.MoveTo(R.Left,R.Top);
PDCCanvas.LineTo(r.Right,R.Top);
end;
if (k=all) then
begin
PDCCanvas.MoveTo(R.Left,R.bottom);
PDCCanvas.LineTo(r.Right,R.bottom);
end;
if j=0 then
begin
PDCCanvas.MoveTo(R.Left,R.top);
PDCCanvas.LineTo(r.left,R.bottom);
end;
if j=SGC.ColCount - 1 then
begin
PDCCanvas.MoveTo(R.right,R.top);
PDCCanvas.LineTo(r.right,R.bottom);
end;
if SGC.fixedcols=1 then
if (j=0) then
begin

PDCCanVas.MoveTo(R.left,r.bottom);
PDCCanvas.LineTo(R.right,R.bottom);
Pdccanvas.MoveTo(R.right,R.top);
PDCCanvas.LineTo(R.right,R.Bottom);
end;
if SGC.fixedrows=1 then
//if k=startpage*pagerownum then
//if k=all then
if ((k=startpage*pagerownum-startpage+1)and (startpage>0) )or( (k=startpage*pagerownum) and (startpage<1) )then
begin
Pdccanvas.MoveTo(R.left,R.bottom);
PDCCanvas.LineTo(R.right,R.Bottom);
Pdccanvas.MoveTo(R.right,R.top);
PDCCanvas.LineTo(R.right,R.Bottom);
end;
if (J=0) and (
((C[0]='?) and (C[1]='?)) or
((C[0]='?) and (C[1]='?)) or
((C[0]='?) and (C[1]='?)) or
((C[0]='?) and (C[1]='?)) or
((C[0]='?) and (C[1]='?)) or
((C[0]='?) and (C[1]='?)) or
((C[0]='?) and (C[1]='?)) or
((C[0]='?) and (C[1]='?)) or
((C[0]='?) and (C[1]='?))) then
begin
if Rowright=0 then
begin
for i:=0 to SGC.ColCount-1do
RowRight:=RowRight+SGC.ColWidths+1;
RowRight:=Round(((SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x)+RowRight+SW.HorzScrollBar.Position)*ScaleX)+WidthSet-1;
end;
{ PDCCanvas.MoveTo(R.Left,R.Top+1);
PDCCanvas.LineTo(RowRight,R.Top+1);
PDCCanvas.MoveTo(RowRight,R.Top+1);
PDCCanvas.LineTo(Rowright,R.Bottom);}
StrPCopy(C, SGC.Cells[1,K]);
Format:=(DT_EXPANDTABS or DT_WORDBREAK)or (DT_VCENTER
or DT_SINGLELINE) or DT_LEFT;
Clen:=Strlen(C);
if ifpreview then
begin
R.Left:=R.Right+round(4*fscale);
R.Right:=RowRight-round(4*fscale);
end else
begin
R.Left:=R.Right+round(10*fscale);
R.Right:=RowRight-round(10*fscale);
end;
// 留用 WinProcs.DrawText(PDC, C, CLen, R,Format);
// break ;
end;
if SGC.ColWidths[j]=0 then
ColLeft := ColLeft+SGC.ColWidths[j]
else
ColLeft := ColLeft+SGC.ColWidths[j]+1;
end;
end;
{next column}
RowTop := RowTop + SGC.RowHeights[k]+1;
////////////
//if ifpreview and (k=startpage*pagerownum) and (k>0) then
//if ifpreview and (k=all) and (k>0) then
if ifpreview and (k>0) and (((startpage>0) and (k=startpage*pagerownum-startpage+1))or((startpage<1)and(k=startpage*pagerownum))) then
begin
colleft:=(SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x);
for J:= 0 to SGC.ColCount - 1do
begin
R := SGC.CellRect(J, K);
R.Top := RowTop;
R.Bottom := R.Top+SGC.RowHeights[k]+1;
R.Left :=colleft;
if SGC.ColWidths[j]=0 then
R.Right := R.Left+SGC.ColWidths[j]
else
R.Right := R.Left+SGC.ColWidths[j]+1;
if ((k=startpage*pagerownum-startpage+1)and (startpage>0) )or( (k=startpage*pagerownum) and (startpage<1) )then
//if (k-all)=0 then
//if (k-startpage*pagerownum+startpage)=0 then
begin
stringgridTop[J] := SGC.Cells[J,0];
topR[J] := R;
Col_Widths[J] := SGC.ColWidths[J];
end;
if R.Right >= R.Left then
begin
R := ScaleToPrinter(R);
if J=SGC.ColCount-1 then
RowRight:=R.Right-1;
PDCCanvas.Brush.Style := bsClear;
ClearString_C ;
StrPCopy(C, SGC.Cells[J,K]);
Format:=(DT_EXPANDTABS or DT_WORDBREAK)or (DT_VCENTER or DT_SINGLELINE);
if ifpreview then
begin
if isNumber(C) then
begin
Format:=Format or DT_RIGHT;R.Right :=R.Right-round(4*fscale);
end else
begin
Format:=Format or DT_LEFT;
R.Left :=R.Left +round(4*fscale);
end;
end else
begin
if isNumber(C) then
begin
Format:=Format or DT_RIGHT;R.Right :=R.Right-round(10*fscale);
end else
begin
Format:=Format or DT_LEFT;
R.Left :=R.Left +round(10*fscale);
end;
end;
Clen:=Strlen(C);
if sgc.FixedRows=1 then
WinProcs.DrawText(PDC, C, CLen, R,Format);
if ifpreview then
begin
if isNumber(C) then
R.Right:=R.Right+round(4*fscale) else
R.Left:=R.Left-round(4*fscale);
end else
begin
if isNumber(C) then
R.Right:=R.Right+round(10*fscale) else
R.Left:=R.Left-round(10*fscale);
end;
if (goHorzLine in SGC.Options)then
begin
R.bottom:=r.bottom-1;
PDCCanvas.MoveTo(R.Left,R.Top);
PDCCanvas.LineTo(R.Right,R.Top);
PDCCanvas.MoveTo(R.Left,R.Bottom);
PDCCanvas.LineTo(R.Right,R.Bottom);
end ;
if (goVertline in SGC.Options)then
begin
R.Right:=R.Right-1;
PDCCanvas.MoveTo(R.Left,R.Top);
PDCCanvas.LineTo(R.Left,R.Bottom);
PDCCanvas.MoveTo(R.Right,R.Top);
PDCCanvas.LineTo(R.Right,R.Bottom);
end;
//if (k=startpage*pagerownum) then
//if (k=startpage*pagerownum-startpage) then
if ((k=startpage*pagerownum-startpage+1)and (startpage>0) )or( (k=startpage*pagerownum) and (startpage<1) )then
begin
PDCCanvas.MoveTo(R.Left,R.Top);
PDCCanvas.LineTo(r.Right,R.Top);
end;
if (k=all) then
begin
PDCCanvas.MoveTo(R.Left,R.bottom);
PDCCanvas.LineTo(r.Right,R.bottom);
end;
if j=0 then
begin
PDCCanvas.MoveTo(R.Left,R.top);
PDCCanvas.LineTo(r.left,R.bottom);
end;
if j=SGC.ColCount - 1 then
begin
PDCCanvas.MoveTo(R.right,R.top);
PDCCanvas.LineTo(r.right,R.bottom);
end;
if SGC.fixedcols=1 then
if (j=0) then
begin

PDCCanVas.MoveTo(R.left,r.bottom);
PDCCanvas.LineTo(R.right,R.bottom);
Pdccanvas.MoveTo(R.right,R.top);
PDCCanvas.LineTo(R.right,R.Bottom);
end;
if SGC.fixedrows=1 then
//if k=startpage*pagerownum then
//if k=startpage*pagerownum-startpage then
if ((k=startpage*pagerownum-startpage+1)and (startpage>1) )or( (k=startpage*pagerownum) and (startpage<=1) )then
begin
Pdccanvas.MoveTo(R.left,R.bottom);
PDCCanvas.LineTo(R.right,R.Bottom);
Pdccanvas.MoveTo(R.right,R.top);
PDCCanvas.LineTo(R.right,R.Bottom);
end;
StrPCopy(C, SGC.Cells[1,K]);
Format:=(DT_EXPANDTABS or DT_WORDBREAK)or (DT_VCENTER
or DT_SINGLELINE) or DT_LEFT;
Clen:=Strlen(C);
if ifpreview then
begin
R.Left:=R.Right+round(4*fscale);
R.Right:=RowRight-round(4*fscale);
end else
begin
R.Left:=R.Right+round(10*fscale);
R.Right:=RowRight-round(10*fscale);
end;
// WinProcs.DrawText(PDC, C, CLen, R,Format);
// break ;
end;
if SGC.colWidths[j]=0 then
ColLeft := ColLeft+SGC.ColWidths[j]
else
ColLeft := ColLeft+SGC.ColWidths[j]+1;
end;
if sgc.FixedRows=1 then
RowTop := RowTop + SGC.RowHeights[k]+1;
end;
//end ifpreview and k>0 and num>1
///////
if ifpreview then
if ((RowTop+SGC.RowHeights[k]+1+PageBottom/scaley) >round((PDCcanvas.ClipRect.Bottom-PDCcanvas.ClipRect.Top-PageBottom)/scaley+0.5)) AND (k<SGC.RowCount-1) then
begin

for i:=SGC.ColCount-1do
wnto 1 do
begin
R.Left:=colleft-sgc.colwidths-1;
r.Top:=rowtop;
r.Right:=colleft;
r.bottoM:=r.top;
R:=scaletoprinter(r);
PDCcanvas.MoveTo(r.Right,r.Top);
pdccanvas.LineTo(r.left,r.top);
colleft:=colleft-sgc.colwidths-1;
end;
printPageHeader;
printTableHeader;
if pagerownum=0 then
begin
// getrownum(sgc);
pagerowNum:=k+1;
endpage:=round(SGC.RowCount/pagerowNum+0.5);
pagetotal:=endpage;
end;
//原程序
break;
end;
if ifprinttop then
begin
ifprinttop:=false;
goto rplabel1;
end;
if ((RowTop+SGC.RowHeights[k]+1+PageBottom/scaley) >round((Printer.PageHeight-PageBottom)/ScaleY)+0.5) AND (k<SGC.RowCount-1) then
begin
// break;
{if not (goHorzLine in SGC.Options)then
with PDCCanvasdo
begin
MoveTo(Round(((SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x)+SW.HorzScrollBar.Position)*ScaleX)+WidthSet,R.Bottom);
LineTo(R.Right,R.Bottom);
end;
}
if startpage=endpage then
break;
printtablebottom;
printPageBottom;
printPageHeader;
printTableHeader;
if fifshowpageno then
printPagenum;
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size := round(SGC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(SGC.Font.Size*scalex-0.50);
if SGC.FixedRows=1 then
if_repeat_top := TRUE
else
if_repeat_top := false;
v := k;
RowTop:=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size :=round(SGC.Font.Size*fscale);
if ifpreview then
PDCCanvas.font.size:=round(SGC.font.size*scalex-0.50);
/////
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
if(leftRow>0) then
begin
i:=Round(Printer.PageHeight/ScaleY -PageBottom-(SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y))
div (SGC.CellRect(0,0).Bottom-SGC.CellRect(0,0).Top+1);
R.Top := SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
R.Right := SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x;
if(leftRow<i) then
begin
R.Bottom := (SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y)+(SGC.CellRect(0,0).Bottom-
SGC.CellRect(0,0).Top+1)*leftRow;
leftRow:=0;
end
else
begin
R.Bottom := (SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y)+(SGC.CellRect(0,0).Bottom-
SGC.CellRect(0,0).Top+1)*(i+1);
leftRow:=leftRow-i-1;
end;
R.Left := R.Right -40;
T:=R;
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left, R.Top, R.Right, R.Bottom);
end;
if if_repeat_top then
goto rplabel1;
end;
end;
{for all row}
{ if not (goHorzLine in SGC.Options)then
with PDCCanvasdo
begin
MoveTo(Round(((SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x)+SW.HorzScrollBar.Position)*ScaleX)+WidthSet,R.Bottom);
LineTo(RowRight,R.Bottom);
end;
}
//*****************************//
//showmessage(inttostr(k));
//以下为打空行
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size :=round(SGC.Font.Size*fscale+0.5);
if ifpreview then
PDCCanvas.Font.Size :=round(SGC.Font.Size*scalex-0.50);
PDCCanvas.Pen.Width:=Round(ScaleX);
PDC := PDCCanvas.Handle;
if fifprintemptyline then
begin
for i:=1 to 50do
begin
colleft:=(SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x);
for j:=0 to SGC.ColCount-1do
begin
R.Left:=colleft;
R.Right:=r.Left+SGC.ColWidths[j]+1;
R.Top:=rowtop;
R.Bottom:=R.Top+SGC.RowHeights[0]+1;
r:=scaletoprinter(r);
if ifpreview then
if ((RowTop+SGC.RowHeights[0]+1+PageBottom/scaley) >round((PDCcanvas.ClipRect.Bottom-PDCcanvas.ClipRect.Top-PageBottom)/scaley+0.5)) then
exit
else
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom)
else
if ((RowTop+SGC.RowHeights[0]+1+PageBottom/scaley) >round((Printer.PageHeight-PageBottom)/ScaleY)+0.5) then
exit
else
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom);

ColLeft := ColLeft+SGC.ColWidths[j]+1;
end;
RowTop := RowTop + SGC.RowHeights[0]+1;
end;
end;
end;
{================================================================== }
procedure Tprint.getrownum(SGC:TSTringGrid);
var i:integer;
begin
RowTop :=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
for i:=0 to sgc.RowCount-1do
begin
if ((RowTop+(SGC.RowHeights[0])*i+1+PageBottom/scaley) >round((Printer.PageHeight-PageBottom)/ScaleY)+0.5) then
begin
pagerownum:=i+1;
exit;
end;
end;
pagerownum:=sgc.RowCount-1;
end;
{===================================================================}
 
//第二部分
{===================================================================}
procedure Tprint.getrownumw(SGC:TSTringGrid);
var
i,J,K,rowtop:integer;
totallines:integer;
memo_ts:Tmemo;
F:Tform;
begin
{pagetotal:integer;
startpage:integer;
endpage:integer;}
pagetotal:=1;
F:=tform(self.findcomponent('Form_preview'));
memo_ts:=tmemo.Create(self);
with memo_tsdo
begin
parent:=F;
name:='memo_lsmeo';
font:=sgc.Font;
visible:=false;
end;
RowTop :=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
for K :=0 to SGC.RowCount-1do
begin
//
totallines:=1;
for j:=0 to SGC.ColCount-1do
begin
with memo_tsdo
begin
lines.Clear;
width:=sgc.ColWidths[j];
memo_Ts.Lines.Text:=sgc.Cells[j,k];
end;

if totallines<=memo_ts.Lines.Count then
totallines:=memo_ts.Lines.Count;
end;
if ((RowTop+SGC.RowHeights[k]*totallines+1+PageBottom/scaley) >round((PDCcanvas.ClipRect.Bottom-PDCcanvas.ClipRect.Top-PageBottom)/scaley+0.5)) AND (k<SGC.RowCount-1) then
begin
if pagetotal=1 then
pagerownumw[pagetotal]:=k
else
begin
pagerownumw[pagetotal]:=k;
for i:=1 to pagetotal-1do
pagerownumw[pagetotal]:=pagerownumw[pagetotal]-pagerownumw;
end;
RowTop :=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
pagetotal:=pagetotal+1;
end;
//
RowTop := RowTop + SGC.RowHeights[k]*totallines;//+1;
end;
memo_ts.free;
end;

procedure Tprint.PrintStringGridW(SGC:TSTringGrid);
label
rplabel1;
var
J,K,i,h,ColLeft,rowtop:integer;
//if_repeat_top:boolean;
all:integer;
totallines:integer;
memo_ts:Tmemo;
F:Tform;
startline:integer;
begin
F:=tform(self.findcomponent('Form_preview'));
memo_ts:=tmemo.Create(self);
with memo_tsdo
begin
parent:=F;
name:='memo_lsmeo';
font:=sgc.Font;
visible:=false;
end;
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size :=round(SGC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(SGC.Font.Size*scalex-0.50);
PDCCanvas.Pen.Width:=Round(ScaleX);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
Format := DT_SINGLELINE or DT_VCENTER or DT_SINGLELINE or DT_VCENTER;
RowTop :=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
if pagerowNum=0 then
all:=SGC.RowCount - 1
else
if (endpage*pagerownum)<(SGC.RowCount - 1) then
all:=endpage*pagerownum
else
all:=SGC.RowCount - 1;
{if SGC.FixedRows>=1 then
if_repeat_top := TRUE
else
if_repeat_top := false;}
startline:=0;
for i:=1 to startpagedo
startline:=startline+pagerownumw;
for K :=0+startline to alldo
begin
rplabel1:
ColLeft :=(SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x);
//
totallines:=1;
for j:=0 to SGC.ColCount-1do
begin
with memo_tsdo
begin
lines.Clear;
width:=sgc.ColWidths[j];
memo_Ts.Lines.Text:=sgc.Cells[j,k];
end;
if totallines<=memo_ts.Lines.Count then
totallines:=memo_ts.Lines.Count;
end;
{if ifpreview then
if ((RowTop+SGC.RowHeights[k]*totallines+1+PageBottom/scaley) >round((PDCcanvas.ClipRect.Bottom-PDCcanvas.ClipRect.Top-PageBottom)/scaley+0.5)) AND (k<SGC.RowCount-1) then
begin
printPageHeader;
printTableHeader;
if pagerownum=0 then
begin
pagerowNum:=k+1;
endpage:=round(SGC.RowCount/pagerowNum+0.5);
pagetotal:=endpage;
end;
break;
end;
}
//
for J:= 0 to SGC.ColCount - 1do
begin
R.Left:=colleft;
R.Top:=rowtop;
R.Bottom:=rowtop+SGC.RowHeights[k]*totallines;
if sgc.ColWidths[j]=0 then
R.Right:=colleft+sGC.ColWidths[j]
else
R.Right:=colleft+sGC.ColWidths[j]+1;
R:=scaletoprinter(r);
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom);
//
with memo_tsdo
begin
lines.Clear;
width:=sgc.ColWidths[j];
memo_ts.Lines.Text:=sgc.Cells[j,k];
end;
for h:=0 to totallinesdo
begin
R.Left:=colleft;
R.Top:=rowtop+h*SGC.RowHeights[k];
R.Bottom:=rowtop+(h+1)*SGC.RowHeights[k];
if sgc.ColWidths[k]=0 then
R.Right:=colleft+sGC.ColWidths[j]
else
R.Right:=colleft+sGC.ColWidths[j]+1;
Format:=(DT_EXPANDTABS or DT_WORDBREAK)or (DT_VCENTER or DT_SINGLELINE);
if ifpreview then
begin
if isNumber(C) then
begin
Format:=Format or DT_RIGHT;R.Right :=R.Right-round(4*fscale);
end else
begin
Format:=Format or DT_LEFT;
R.Left :=R.Left +round(4*fscale);
end;
end else
begin
if isNumber(C) then
begin
Format:=Format or DT_RIGHT;R.Right :=R.Right-round(10*fscale);
end else
begin
Format:=Format or DT_LEFT;
R.Left :=R.Left +round(10*fscale);
end;
end;
R:=scaletoprinter(r);
clearstring_c;
StrPCopy(C, memo_ts.Lines[h]);
Clen:=Strlen(C);
if SGC.ColWidths[J]<>0 then
if ifpreview then
pdccanvas.TextOut(r.left,r.top+3,c)
else
WinProcs.DrawText(PDC, C, CLen, R,Format);
// WinProcs.DrawText(PDC, C, CLen, R,Format);
end;
//
if sgc.ColWidths[j]=0 then
colleft:=colleft+sgc.colwidths[j]
else
colleft:=colleft+sgc.colwidths[j]+1;
end;
//end j

RowTop := RowTop + SGC.RowHeights[k]*totallines;//+1;
if ((RowTop+SGC.RowHeights[k]*totallines+1+PageBottom/scaley) >round((Printer.PageHeight-PageBottom)/ScaleY)+0.5) AND (k<SGC.RowCount-1) then
begin
if startpage=endpage then
break;
printPageBottom;
printPageHeader;
printTableHeader;
if fifshowpageno then
printPagenum;
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size := round(SGC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(SGC.Font.Size*scalex-0.50);
{if SGC.FixedRows>=1 then
if_repeat_top := TRUE
else
if_repeat_top := false;}
RowTop:=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size :=round(SGC.Font.Size*fscale);
PDC := PDCCanvas.Handle;
goto rplabel1;
end;
end;
//end k
memo_ts.free;
end;

{================================================================== }
{$ifdef MergeGrid}
procedure Tprint.printmergegrid(SGC:Tmergegrid);
label
rplabel1;
var
J,K,v,ColLeft:integer;
if_repeat_top:boolean;
all,allnow:integer;
MergeRect:Tmergedcellrect;
lsi,lsj:integer;
lsleft,lsright,lstop,lsbottom,
maxrow,maxcol,minrow,mincol:integer;
begin
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size :=round(SGC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(SGC.Font.Size*scalex-0.50);
PDCCanvas.Pen.Width:=Round(ScaleX);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
Format := DT_SINGLELINE or DT_VCENTER or DT_SINGLELINE or DT_VCENTER;
RowTop :=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
if pagerowNum=0 then
all:=SGC.RowCount - 1
else
if (endpage*pagerownum)<(SGC.RowCount - 1) then
all:=endpage*pagerownum
else
all:=SGC.RowCount - 1;
if SGC.FixedRows>=1 then
if_repeat_top := TRUE
else
if_repeat_top := false;
v:=startpage*pagerowNum;
for K :=0+startpage*pagerowNum to alldo
begin
rplabel1:
if (if_repeat_top = TRUE) and (v < K) then
if_repeat_top := False;
ColLeft :=(SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x);
for J:= 0 to SGC.ColCount - 1do
begin
mergerect:=sgc.MergedCells.MergedCellAt(j,k).Rect;
lsleft:=mergerect.LeftCol;
lsright:=mergerect.RightCol;
lstop:=mergerect.TopRow;
lsbottom:=mergerect.BottomRow;
maxcol:=max(lsleft,lsright);
mincol:=min(lsleft,lsright);
maxrow:=max(lstop,lsbottom);
minrow:=min(lstop,lsbottom);
R := SGC.CellRect(J, K);
if j=mincol then
R.Left:=colleft;
if j>mincol then
begin
lsj:=0;
for lsi:=mincol to j-1do
lsj:=lsj-sgc.ColWidths[lsi];
R.Left:=colleft+lsj;
end;
if k=minrow then
r.Top:=rowtop;
if k>minrow then
begin
lsj:=0;
for lsi:=minrow to k-1do
lsj:=lsj-sgc.RowHeights[lsi];
R.Top:=rowtop+lsj;
end;
lsj:=0;
for lsi:=mincol to maxcoldo
lsj:=lsj+SGC.ColWidths[lsi];
R.Right:=R.Left+lsj;
lsj:=0;
for lsi:=minrow to maxrowdo
lsj:=lsj+SGC.RowHeights[lsi];
R.Bottom:=R.Top+lsj;
R:=scaletoprinter(R);
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom);
StrPCopy(C, SGC.Cells[j,K]);
if (maxcol<>mincol) or (maxrow<>minrow) then
format:=(DT_EXPANDTABS or DT_WORDBREAK)or (DT_CENTER
or DT_SINGLELINE) or DT_LEFT
else
Format:=(DT_EXPANDTABS or DT_WORDBREAK)or (DT_VCENTER
or DT_SINGLELINE) or DT_LEFT;
Clen:=Strlen(C);
//if (maxrow<>minrow) then
R.Top:=R.Top+(((R.Bottom-R.Top) Div 2)-(SGC.Font.Size div 2)-2);
WinProcs.DrawText(PDC, C, CLen, R,Format);
colleft:=colleft+sgc.colwidths[j];//+1;
end;
//end j
RowTop := RowTop + SGC.RowHeights[k];//+1;
if ifpreview then
if ((RowTop+SGC.RowHeights[k]+1+PageBottom/scaley) >round((PDCcanvas.ClipRect.Bottom-PDCcanvas.ClipRect.Top-PageBottom)/scaley+0.5)) AND (k<SGC.RowCount-1) then
begin
printPageHeader;
printTableHeader;
if pagerownum=0 then
begin
pagerowNum:=k+1;
endpage:=round(SGC.RowCount/pagerowNum+0.5);
pagetotal:=endpage;
end;
break;
end;
if ((RowTop+SGC.RowHeights[k]+1+PageBottom/scaley) >round((Printer.PageHeight-PageBottom)/ScaleY)+0.5) AND (k<SGC.RowCount-1) then
begin
if startpage=endpage then
break;
printPageBottom;
printPageHeader;
printTableHeader;
if fifshowpageno then
printPagenum;
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size := round(SGC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(SGC.Font.Size*scalex-0.50);
if SGC.FixedRows>=1 then
if_repeat_top := TRUE
else
if_repeat_top := false;
v := k;
RowTop:=SGC.ClientOrigin.y-FScrollingName.ClientOrigin.y;
PDCCanvas.Font := SGC.Font;
PDCCanvas.Font.Size :=round(SGC.Font.Size*fscale);
PDC := PDCCanvas.Handle;
goto rplabel1;
end;
end;
//end k

//以下为打空行
if fifprintemptyline then
begin
rowtop:=rowtop;
if (SGC.fixedrows=0) then
allnow:=endpage*pagerownum-2
else
allnow:=endpage*pagerownum-2;
if (k=all+1) and (all<endpage*pagerownum) then
for k:=all to allnowdo
begin
colleft:=(SGC.ClientOrigin.x-FScrollingName.ClientOrigin.x);
for j:=0 to SGC.ColCount-1do
begin
R.Left:=colleft;
R.Right:=r.Left+SGC.ColWidths[j];
R.Top:=rowtop;
R.Bottom:=R.Top+SGC.RowHeights[k];
r:=scaletoprinter(r);
PDCCanvas.Rectangle(R.Left,R.Top,R.Right , R.Bottom);
ColLeft := ColLeft+SGC.ColWidths[j];
end;
RowTop := RowTop + SGC.RowHeights[k];
end;
end;
end;
{$endif}

{ ================================================================= }
{procedure TPrint.PrintChart(Chart: TChartFX);
begin
R := ScaleToPrinter(Chart.BoundsRect);
if Chart.BorderStyle > 0 then
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom);
ChartFX.chart_Paint(Chart.Handle, PDC, R.Left, R.Top, R.Right, R.Bottom, 1, 0);
end;
}
procedure TPrint.PrintBevel(Bevel:TBevel);
begin
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
Format := DT_SINGLELINE or DT_VCENTER;
R.Top := Bevel.ClientOrigin.y-SW.ClientOrigin.y;
R.Bottom := R.Top+Bevel.Height;
R.Left := Bevel.ClientOrigin.x-SW.ClientOrigin.x;
R.Right := R.Left+Bevel.Width;
R := ScaleToPrinter(R);
PDCCanvas.Brush.Style := bsClear;
PDCCanvas.Pen.Width:=Round(ScaleX);
if (Bevel.Height=1)or (Bevel.Height=2) OR (BEVEL.Shape=BSTOPLINE) then
begin
PDCCanvas.Moveto(R.Left,R.Top);
PDCCanvas.Lineto(R.Right,R.Top);
END else
if (Bevel.Width=1) OR (Bevel.Width=2) OR (BEVEL.Shape=BSLEFTLINE)then
begin
PDCCanvas.Moveto(R.Left,R.Top);
PDCCanvas.Lineto(R.LEFT,R.Bottom);
END else
if (BEVEL.Shape=BSRIGHTLINE)then
begin
PDCCanvas.Moveto(R.RIGHT,R.Top);
PDCCanvas.Lineto(R.RIGHT,R.Bottom);
END else
if (BEVEL.Shape=BSBOTTOMLINE)then
begin
PDCCanvas.Moveto(R.LEFT,R.BOTTOM);
PDCCanvas.Lineto(R.RIGHT,R.Bottom);
END else
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom);
end;

procedure TPrint.PrintPanel(Panel:TPanel);
var
i: integer ;
begin
PDCCanvas.Font := Panel.Font;
PDCCanvas.Font.Size := round(Panel.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(Panel.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
Format := DT_SINGLELINE or DT_VCENTER;
if Panel.Align <> alNone then
begin
R.Left :=Panel.ClientOrigin.x-FScrollingName.ClientOrigin.x+Panel.BevelWidth;
R.Top := Panel.ClientOrigin.y-FScrollingName.ClientOrigin.y;//+Panel.BevelWidth;
R.Right := R.Left + Panel.Width;
R.Bottom := R.Top + Panel.Height;
end
else
begin
R.Left :=Panel.ClientOrigin.x-FScrollingName.ClientOrigin.x;//+Panel.BevelWidth;
R.Top := Panel.ClientOrigin.y-FScrollingName.ClientOrigin.y;//+Panel.BevelWidth;
R.Right := R.Left + Panel.Width;//-Panel.BevelWidth;
R.Bottom := R.Top + Panel.Height;//-Panel.BevelWidth;
end;
if (panel.Tag=4) or (panel.Tag=5) then
if Panel.Align <> alNone then
begin
R.Left :=Panel.ClientOrigin.x-FScrollingName.ClientOrigin.x-Panel.BevelWidth;
R.Top := realfoottop+(Panel.ClientOrigin.y-sw.ClientOrigin.y-foottop)-Panel.BevelWidth;
R.Right := R.Left + Panel.Width;
R.Bottom := R.Top + Panel.Height;
end else
begin
R.Left :=Panel.ClientOrigin.x-FScrollingName.ClientOrigin.x-Panel.BevelWidth;
R.Top := realfoottop+(Panel.ClientOrigin.y-sw.ClientOrigin.y-foottop)-Panel.BevelWidth;
R.Right := R.Left + Panel.Width-Panel.BevelWidth;
R.Bottom := R.Top + Panel.Height-Panel.BevelWidth;
end;

if R.Right >= R.Left then
begin
R := ScaleToPrinter(R);
PDCCanvas.Brush.Style := bsClear;
if (Panel.BorderStyle <> BsNone) or
(Panel.BevelInner <> bvNone) or
(Panel.BevelOuter <> bvNone) then
//原此句没有,现判断若不等于,则不画Panelde的边框
PDCCanvas.Rectangle(R.Left,R.Top,R.Right,R.Bottom);
CLearString_C ;
StrPCopy(C,Panel.Caption);
WinProcs.DrawText(PDC, C, StrLen(C), R,
((DT_EXPANDTABS or DT_WORDBREAK) or (DT_SINGLELINE
or DT_VCENTER) or DT_CENTER));
format:=DT_VCENTER or DT_CENTER or DT_SINGLELINE;
for i:= 0 to Panel.ControlCount-1do
if Panel.Controls.Tag >0 then
begin
//**************************************//
if (Panel.Controls is THeader) then
PrintHeader(THeader(Panel.Controls));
if (Panel.Controls is Tradiobutton) then
Printradiobutton(Tradiobutton(Panel.Controls));
if (Panel.Controls is Tradiogroup) then
Printradiogroup(Tradiogroup(Panel.Controls));
if (Panel.Controls is TDBradiogroup) then
PrintDBradiogroup(TDBradiogroup(Panel.Controls));
if (Panel.Controls is Tcheckbox) then
Printcheckbox(Tcheckbox(Panel.Controls));
if (Panel.Controls is TLabel) then
PrintLabel(Tlabel(Panel.Controls));
if (Panel.Controls is TDBtext) then
PrintDBtext(TDBtext(Panel.Controls));
if (Panel.Controls is TPanel) then
PrintPanel(TPanel(Panel.Controls));
if ((Panel.Controls is tedit) or
(Panel.Controls is TCustomComboBox)) or
(Panel.Controls is Tdatetimepicker) then
PrintEdit(TMemo(Panel.Controls));
if (Panel.Controls is Tdbedit) then
Printdbedit(Tdbedit(Panel.Controls));
if (Panel.Controls is TShape) then
PrintShape(TShape(Panel.Controls));
{ if (Panel.Controls is TChartFX) then
PrintChart(TChartFX(Panel.Controls));}
if (Panel.Controls is TCustomCheckBox) then
PrintCheckBox(TCheckBox(Panel.Controls));
if (Panel.Controls is TImage) then
PrintImage(TImage(Panel.Controls));
if (Panel.Controls is TBevel) then
PrintBevel(TBevel(Panel.Controls));
if (Panel.Controls is TMemo ) then
begin
PrintMemo(TMemo(Panel.Controls));
//exit;
end;
if (Panel.Controls is TDbMemo ) then
begin
PrintDbMemo(TDbMemo(Panel.Controls));
//exit;
end;
if (Panel.Controls is TRichEdit ) then
begin
PrintMemo(TMemo(Panel.Controls));
//exit;
end;
{$ifdef psgaccess}
if (panel.controls is TSGAccess) then
if fifWordWrap then
begin
getrownumw(TStringGrid(Panel.Controls));
PrintStringGridW(tstringgrid(TSGAccess(panel.controls).myStringGrid));
end
else
printstringgrid(tstringgrid(TSGAccess(panel.controls).myStringGrid));
{$endif}
{$ifdef MergeGrid}
if (panel.Controls is Tmergegrid) then
begin
printmergegrid(Tmergegrid(panel.controls));
exit;
end;
{$endif}
if (Panel.Controls is TStringGrid) then
if fifWordWrap then
begin
getrownumw(TStringGrid(Panel.Controls));
PrintStringGridW(TStringGrid(Panel.Controls));
end
else
PrintStringGrid(TStringGrid(Panel.Controls));
if (Panel.Controls is TDBGrid) then
PrintDBGrid(TDBGrid(Panel.Controls));
end;
end;

end;

{procedure TPrint.PrintCheckBox(CB: TCheckBox);
var
BR : TRect;
W, H : integer;
begin
PDCCanvas.Font := CB.Font;
PDC := PDCCanvas.Handle;
W := Round(12 * ScaleX);
H := Round(12 * ScaleY);
R.Left:=CB.ClientOrigin.x-SW.ClientOrigin.x;
R.Top:=CB.ClientOrigin.y-SW.ClientOrigin.y;
R.Right:=R.Left+CB.Width;
R.Bottom:=R.Top+CB.Height;
if (CB.Tag=4) or (CB.Tag=5) then
begin
R.Top := realfoottop+(CB.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=CB.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+CB.Height;
R.Right:=R.Left+CB.Width;
end;
R:=scaletoprinter(R);
BR := R;
BR.Top := R.Top + ((R.Bottom - R.Top) div 2) - (H div 2);
BR.Bottom := BR.Top + H;
if (not CB.Ctl3d) and (CB.Alignment = taLeftJustify) then
begin
BR.Right := R.Right;
BR.Left := R.Right - W;
R.Right := R.Right - W;
end
else
begin
BR.Right := R.Left + w;
BR.Left := R.Left;
R.Left := R.Left + W;
end;
PDCCanvas.Rectangle(BR.Left, BR.Top, BR.Right, BR.Bottom);
if CB.Checked then
with PDCCanvasdo
begin
PDCCanvas.Pen.Width := PDCCanvas.Pen.Width - 1;
MoveTo(BR.Left, BR.Top);
LineTo(BR.Right, BR.Bottom);
MoveTo(BR.Right, BR.Top);
LineTo(BR.Left, BR.Bottom);
end;
Format := DT_SINGLELINE or DT_VCENTER;
CLen := CB.GetTextBuf(C,255);
WinProcs.DrawText(PDC, C, CLen, R, Format);
end;
}
procedure TPrint.PrintImage(IC: TImage);
begin
R.Left:=ic.ClientOrigin.x-sw.ClientOrigin.x;
R.Top:=IC.ClientOrigin.y-SW.ClientOrigin.y;
R.Right:=R.Left+IC.Width;
R.Bottom:=R.Top+IC.Height;
if (iC.Tag=4) or (iC.Tag=5) then
begin
R.Top := realfoottop+(iC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=iC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+iC.Height;
R.Right:=R.Left+iC.Width;
end;
R:=scaletoprinter(R);
PDCCanvas.StretchDraw(R, IC.Picture.Graphic);
end;

procedure TPrint.PrintPage;
var
{i,}j:integer;
F:TForm;
S:Tscrollbox;
T:timage;
P:tpanel;
H,W:integer;
Xscal,Yscal:double;
lsbl:double;
begin
{PrintPage}
//get scrollbox's top,bottom,left,right,height,width

//*************************************//
foottop:=0;
footheight:=0;
realfoottop:=0;
for j:=0 to SW.ControlCount-1do
begin
if SW.Controls[j].Tag =4 then
begin
foottop:=sw.Controls[j].Top;
footheight:=sw.Controls[j].Height;
break;
end;
if SW.Controls[j].Tag =5 then
begin
foottop:=sw.Controls[j].Top;
footheight:=sw.Controls[j].Height;
break;
end;
end;
if foottop<>0 then
for j:=0 to SW.ControlCount-1do
begin
if SW.Controls[j].Tag =4 then
begin
if sw.Controls[j].top<foottop then
begin
footheight:=foottop-sw.Controls[j].top+footheight;
foottop:=sw.Controls[j].top;
end;
if sw.Controls[j].top-foottop+sw.Controls[j].height>footheight then
footheight:=sw.Controls[j].top-foottop+sw.Controls[j].height;
end;
if SW.Controls[j].Tag =5 then
begin
if sw.Controls[j].top<foottop then
begin
footheight:=foottop-sw.Controls[j].top+footheight;
foottop:=sw.Controls[j].top;
end;
if sw.Controls[j].top-foottop+sw.Controls[j].height>footheight then
footheight:=sw.Controls[j].top-foottop+sw.Controls[j].height;
end;
end;
//*************************************//
if ifpreview then
begin
F:=tform(self.findcomponent('Form_preview'));
S:=Tscrollbox(f.findcomponent('scrollbox_canvas'));
P:=tpanel(S.findcomponent('Panel_canvas'));
H:=round(p.Height*9.5/10);
W:=round(p.Width*9.5/10);
T:=timage(p.findcomponent('image'));
T.Height:=H;
T.Width:=W;
Xscal:=printer.PageWidth/W;
Yscal:=printer.PageHeight/H;
if Xscal>yscal then
begin
t.Width:=W;
t.Height:=round(W*printer.PageHeight/printer.PageWidth);
t.Left:=round((p.Width-t.width)/2);
t.Top:=round((P.height-t.height)/2);
end else
begin
t.height:=H;
t.width:=round(H*printer.PageWidth/printer.PageHeight);
t.Left:=round((p.Width-t.width)/2);
t.Top:=round((P.height-t.height)/2);
end;
t.Canvas.Pen.Color:=clgreen;
t.canvas.pen.Width:=3;
t.Canvas.Rectangle(0,0,t.width,t.height);
j:=WinProcs.GetDeviceCaps(printer.handle,LOGPIXELSX);
if j>=300 then
ifLasterPrint:=True
else
ifLasterPrint:=False;
ifLasterPrint:=True;
if iflasterprint then
begin
ScaleX:=t.Width*3.09*j/300/printer.pagewidth;
ScaleY:=t.Height*3.40*j/300/printer.PageHeight;
end else
begin
ScaleX:=t.Width*3.15*j/300/printer.pagewidth;
ScaleY:=t.Height*3.50*j/300/printer.PageHeight;
end;
if fautoscale=true then
begin
if sw.HorzScrollBar.Range=0 then
fscale:=1
else
begin
if sw.HorzScrollBar.Range<>0 then
fscale:=T.Width*0.875/scalex/sw.HorzScrollBar.Range
else
fscale:=T.Width*0.875/scalex/800;
if sw.VertScrollBar.Range<>0 then
if T.Height*0.875/scaley/sw.VertScrollBar.Range<fscale then
fscale:=T.Height*0.875/scaley/sw.VertScrollBar.Range
else
if T.Height*0.875/scaley/600<fscale then
fscale:=T.Height*0.875/scaley/600;
end;
end;
if fscale<>0 then
begin
ScaleX:=ScaleX*fscale;
ScaleY:=ScaleY*fscale;
end;
if SW.HorzScrollBar.Range=0 then
WidthSet:=round(t.width/20)
else
if T.Width>SW.HorzScrollBar.Range*ScaleX then
WidthSet:=Round(T.Width-SW.HorzScrollBar.Range*ScaleX) div 2
else
WidthSet:=round(t.width/20);
if T.Width<T.Height then
begin
HeightSet:=round(t.Height/20);
pageBottom:=round(t.Height/20);
end
else
begin
HeightSet:=round(t.Height/20);
if ifLasterPrint then
pageBottom:=round(t.Height/20)
else
pageBottom:=round(t.Height/20);
end;
PDCCanvas:=T.Canvas;
PDC :=PDCcanvas.Handle;
footheight:=round((footheight+SW.VertScrollBar.Position)*scaley);//+pagebottom;
lsbl:=footheight;
footheight:=t.Height-pagebottom-footheight;
realfoottop:=round((footheight-pagebottom)/scaley-SW.VertScrollBar.Position);
pagebottom:=pagebottom+round(lsbl*0.5);
PDCCanvas.Pen.Width := Round(ScaleX);
PDCCanvas.Pen.Color := clBlack;
PDCCanvas.Pen.Style := psSolid;
PDCCanvas.Brush.Style := bsClear;
printPageHeader;
printTableHeader;
if fifshowpageno then
printpagenum;
printTable;
printTableBottom;
printPageBottom;
end
//********************************//
else
begin
Printer.begin
Doc;
PDCCanvas:=printer.Canvas;
PDC := PDCCanvas.Handle;
j:=WinProcs.GetDeviceCaps(PDC,LOGPIXELSX);
if j>=300 then
ifLasterPrint:=True
else
ifLasterPrint:=False;
ifLasterPrint:=True;
if iflasterprint then
begin
ScaleX:=3.09*j/300;
ScaleY:=3.40*j/300;
end else
begin
ScaleX:=3.15*j/300;
ScaleY:=3.50*j/300;
end;
if fautoscale=true then
begin
if sw.HorzScrollBar.Range<>0 then
fscale:=printer.PageWidth*0.875/scalex/sw.HorzScrollBar.Range
else
fscale:=printer.PageWidth*0.875/scalex/800;
if sw.VertScrollBar.Range<>0 then
if printer.PageHeight*0.875/scaley/sw.VertScrollBar.Range<fscale then
fscale:=printer.PageHeight*0.875/scaley/sw.VertScrollBar.Range
else
if printer.PageHeight*0.875/scaley/600<fscale then
fscale:=printer.PageHeight*0.875/scaley/600;
{fscale:=printer.PageWidth*0.875/scalex/sw.HorzScrollBar.Range;
if printer.PageHeight*0.875/scaley/sw.VertScrollBar.Range<fscale then
fscale:=printer.PageHeight*0.875/scaley/sw.VertScrollBar.Range;}
end;
if fscale<>0 then
begin
ScaleX:=ScaleX*fscale;
ScaleY:=ScaleY*fscale;
end;
if SW.HorzScrollBar.Range=0 then
WidthSet:=0
else
if Printer.PageWidth>SW.HorzScrollBar.Range*ScaleX then
WidthSet:=Round(Printer.PageWidth-SW.HorzScrollBar.Range*ScaleX) div 2
else
WidthSet:=0;
if Printer.PageWidth<Printer.PageHeight then
begin
HeightSet:=round(printer.PageHeight/20);
pageBottom:=round(printer.pageheight/20);
end
else
begin
HeightSet:=round(printer.PageHeight/20);
if ifLasterPrint then
pageBottom:=round(printer.PageHeight/20)
else
pageBottom:=round(printer.PageHeight/20);
end;

footheight:=round((footheight+SW.VertScrollBar.Position)*scaley);
lsbl:=footheight;
footheight:=printer.PageHeight-pagebottom-footheight;
realfoottop:=round((footheight-pagebottom)/scaley-SW.VertScrollBar.Position);
pagebottom:=pagebottom+round(lsbl*0.5);
PDCCanvas.Pen.Width := Round(ScaleX);
PDCCanvas.Pen.Color := clBlack;
PDCCanvas.Pen.Style := psSolid;
PDCCanvas.Brush.Style := bsClear;
printPageHeader;
printTableHeader;
if fifshowpageno then
printpagenum;
printTable;
printTableBottom;
printPageBottom;
printer.Enddoc;
end;
end;

procedure Tprint.printpagenum;
label label100;
var str,str1,thestr:string;
A:integer;
R:trect;
strlength:integer;
begin
thestr:=fpageNoconent;
str:='';
str1:='';
label100:
A:=pos('#',thestr);
if A<>0 then
begin
str1:=copy(thestr,1,A-1);
if ifpreview then
str1:=str1+inttostr(startpage+1)+copy(thestr,A+1,length(thestr))
//else
str1:=str1+inttostr(pagenumber)+copy(thestr,A+1,length(thestr))
else
str1:=str1+inttostr(startpage+pagenumber)+copy(thestr,A+1,length(thestr))
end else
str1:=thestr;
A:=pos('$',str1);
if A<>0 then
begin
str:=copy(str1,0,A-1);
str:=str+inttostr(pagetotal)+copy(str1,A+1,length(str1));
end else
str:=str1;
thestr:=str;
if (pos('#',thestr)<>0) or (pos('$',thestr)<>0) then
goto label100;
PDCcanvas.Font.Charset:=GB2312_CHARSET;
PDCcanvas.Font.Size:=fpageNoconentsize;
if ifpreview then
begin
PDCcanvas.Font.Size:=round(fpageNoconentsize*scalex);
strlength:=strlen(pchar(str));
strlength:=Round((strlength-4)*PDCcanvas.Font.Size);
end else
begin
strlength:=strlen(pchar(str));
strlength:=Round((strlength-4)*(fpageNoconentsize*scalex));
end;
case fpagepos of
ppTopLeft,ppTopMiddle,ppTopRight: R.Top:=round((PDCCanvas.ClipRect.bottom-PDCCanvas.ClipRect.top)/40-1.5-fpageNoconentsize*scalex/2);
ppBottomLeft,ppBottomMiddle,ppBottomRight:R.Top:=round((PDCCanvas.ClipRect.bottom-PDCCanvas.ClipRect.top)*39/40-1.5-fpageNoconentsize*scalex);
else
R.Top:=round(heightset*19+heightset/4-1.5);
end;
case fpagepos of
ppTopLeft,ppBottomLeft: R.Left:=round((PDCCanvas.ClipRect.Right-PDCCanvas.ClipRect.Left)/20);
ppBottomMiddle,ppTopMiddle:R.Left:=round((PDCCanvas.ClipRect.Right-PDCCanvas.ClipRect.Left)/2-strlength/2);
ppBottomRight,ppTopRight: R.Left:=round((PDCCanvas.ClipRect.Right-PDCCanvas.ClipRect.Left)*19/20-strlength);
else
R.Left:=round((PDCCanvas.ClipRect.Right-PDCCanvas.ClipRect.Left)/2-strlength/2-0.5);
end;
R.Right:=R.Left+strlength;
R.Bottom:=R.Top+Round((fpageNoconentsize*scalex+1+SW.VertScrollBar.Position)*ScaleY+0.5);//+heightset;
if not ifpreview then
//WinProcs.DrawText(PDC, pchar(str),strlen(pchar(str)), R,Format)
PDCCanvas.TextOut(r.left,r.top,STR)
else
begin

PDCCanvas.TextOut(r.left,r.top,STR);
end;
end;

procedure TPrint.printTableHeader;
var
controlItem: integer ;
begin
for controlItem := 0 to SW.ControlCount-1do
if SW.Controls[controlItem].Tag =1 then
printItem(controlItem);
end;

procedure TPrint.printPageHeader;
var
controlItem: integer ;
begin

if PageNumber>1 then
begin
Printer.NewPage;
end;
PDC := PDCCanvas.Handle;
PDCCanvas.Pen.Width := Round(ScaleX);
PDCCanvas.Pen.Color := clBlack;
PDCCanvas.Pen.Style := psSolid;
PDCCanvas.Brush.Style := bsClear;
for ControlItem := 0 to SW.ControlCount-1do
if SW.Controls[ControlItem].Tag =2 then
begin
printItem(controlItem);
end;
end;

procedure TPrint.printTable;
var
controlItem: integer ;
begin
for ControlItem := 0 to SW.ControlCount-1do
begin
if SW.Controls[ControlItem].Tag =3 then
if (not (SW.Controls[controlItem] is Tdbgrid)) and (not (SW.Controls[controlItem] is tstringgrid)) then
printItem(controlItem);
end;
for ControlItem := 0 to SW.ControlCount-1do
begin
if SW.Controls[ControlItem].Tag =3 then
if (SW.Controls[controlItem] is Tdbgrid) or (SW.Controls[controlItem] is tstringgrid) then
printItem(controlItem);
end;
end;

procedure TPrint.printPageBottom;
var
controlItem: integer ;
begin

for ControlItem := 0 to SW.ControlCount-1do
if SW.Controls[ControlItem].Tag =4 then
begin
printItem(controlItem);
end;
PageNumber:=PageNumber+1;
end;

procedure TPrint.printTableBottom;
var
controlItem: integer ;
begin
for ControlItem := 0 to SW.ControlCount-1do
if SW.Controls[ControlItem].Tag =5 then
begin
printItem(controlItem);
end;
end;

procedure TPrint.printItem(controlItem:integer);
begin
if sw.Controls[controlItem].tag=3 then
begin
if startpage=0 then
begin
if (SW.Controls[controlItem] is THeader) then
PrintHeader(THeader(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TRadiobutton) then
PrintRadiobutton(TRadioButton(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TRadiogroup) then
PrintRadiogroup(TRadiogroup(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TDBRadiogroup) then
PrintDBRadiogroup(TDBRadiogroup(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is Tcheckbox) then
Printcheckbox(Tcheckbox(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TLabel) then
PrintLabel(Tlabel(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TDBtext) then
PrintDBtext(TDBtext(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TPanel) then
PrintPanel(TPanel(SW.Controls[controlItem]));
if ((SW.Controls[controlItem] is tedit) or
(SW.Controls[controlItem] is TCustomComboBox)) or
(SW.Controls[controlItem] is Tdatetimepicker) then
PrintEdit(TMemo(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TDBedit) then
PrintDBedit(TDBedit(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TShape) then
PrintShape(TShape(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TImage) then
PrintImage(TImage(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TBevel) then
PrintBevel(TBevel(SW.Controls[controlItem]));
end;
if (SW.Controls[controlItem] is TMemo ) then
begin
PrintMemo(TMemo(SW.Controls[controlItem]));
//exit;
end;
if (SW.Controls[controlItem] is TDbMemo ) then
begin
PrintDbMemo(TDbMemo(SW.Controls[controlItem]));
//exit;
end;
if (SW.Controls[controlItem] is TRichEdit ) then
begin
PrintMemo(TMemo(SW.Controls[controlItem]));
// exit;
end;
{$ifdef psgaccess}
if (sw.controls[controlItem] is TSGAccess) then
if fifWordWrap then
begin
getrownumw(TStringGrid(SW.Controls[controlitem]));
PrintStringGridW(tstringgrid(tsgaccess(sw.controls[controlitem]).myStringGrid));
end
else
printstringgrid(tstringgrid(tsgaccess(sw.controls[controlitem]).myStringGrid));
{$endif}
{$ifdef MergeGrid}
if (SW.Controls[controlItem] is Tmergegrid) then
begin
printmergegrid(Tmergegrid(SW.controls[controlitem]));
exit;
end;
{$endif}
if (SW.Controls[controlItem] is TDBGrid) then
PrintDBGrid(TDBGrid(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TStringGrid) then
if fifWordWrap then
begin
getrownumw(TStringGrid(SW.Controls[controlitem]));
PrintStringGridW(TStringGrid(SW.Controls[controlitem]))
end
else
PrintStringGrid(TStringGrid(SW.Controls[controlItem]));
end else
begin
if (SW.Controls[controlItem] is THeader) then
PrintHeader(THeader(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TRadiobutton) then
PrintRadiobutton(TRadiobutton(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TRadiogroup) then
PrintRadiogroup(TRadiogroup(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TDBRadiogroup) then
PrintDBRadiogroup(TDBRadiogroup(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is Tcheckbox) then
Printcheckbox(Tcheckbox(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TLabel) then
PrintLabel(Tlabel(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TDBtext) then
PrintDBtext(TDBtext(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TPanel) then
PrintPanel(TPanel(SW.Controls[controlItem]));
if ((SW.Controls[controlItem] is Tedit) or
(SW.Controls[controlItem] is TCustomComboBox)) or
(SW.Controls[controlItem] is Tdatetimepicker) then
PrintEdit(TMemo(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TDBedit) then
PrintDBedit(TDBEDIT(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TShape) then
PrintShape(TShape(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TImage) then
PrintImage(TImage(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TBevel) then
PrintBevel(TBevel(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TMemo ) then
begin
PrintMemo(TMemo(SW.Controls[controlItem]));
//exit;
end;
if (SW.Controls[controlItem] is TDbMemo ) then
begin
PrintDbMemo(TDbMemo(SW.Controls[controlItem]));
//exit;
end;
if (SW.Controls[controlItem] is TRichEdit ) then
begin
PrintMemo(TMemo(SW.Controls[controlItem]));
// exit;
end;
{$ifdef psgaccess}
if (sw.controls[controlItem] is TSGAccess) then
if fifWordWrap then
begin
getrownumw(tstringgrid(tsgaccess(sw.controls[controlitem]).myStringGrid));
PrintStringGridW(tstringgrid(tsgaccess(sw.controls[controlitem]).myStringGrid));
end else
printstringgrid(tstringgrid(tsgaccess(sw.controls[controlitem]).myStringGrid));
{$endif}
{$ifdef MergeGrid}
if (SW.Controls[controlItem] is Tmergegrid) then
begin
printmergegrid(Tmergegrid(SW.controls[controlItem]));
exit;
end;
{$endif}
if (SW.Controls[controlItem] is TDBGrid) then
PrintDBGrid(TDBGrid(SW.Controls[controlItem]));
if (SW.Controls[controlItem] is TStringGrid) then
if fifWordWrap then
PrintStringGridW(TStringGrid(SW.Controls[controlItem]))
else
PrintStringGrid(TStringGrid(SW.Controls[controlItem]));
end;
end;

procedure TPrint.PrintDBGrid(DGC:TDBGrid);
var
T,X : TRect;
leftRow,fieldi,fieldr : integer;
I,J,K,m,n,ColLeft,IndicatorWidth:integer;
rowCount,cellHeight,cellWidth:integer;
all,l:integer;
lstop:integer;
begin
if DGC.DataSource.DataSet.RecordCount=0 then
exit;
PDCCanvas.Font := DGC.Font;
PDCCanvas.Font.Size := round(DGC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(DGC.Font.Size*scalex-0.50);
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
Format := DT_SINGLELINE or DT_VCENTER;
if dgIndicator in DGC.Options then
IndicatorWidth:=12 else
IndicatorWidth:=0;
leftRow:=0;
RowTop :=DGC.Top;
m:=0;
rowCount:=DGC.DataSource.DataSet.RecordCount;
cellheight:=Round(DGC.Font.Size+6);
for k:=0 to fGroupString.Count-1do
begin
j:=AnalyString(k,tmpString);
if j=0 then
begin
j:=round(Printer.PageHeight/ScaleY -PageBottom-DGC.Top);
i:=cellHeight;
j:=(j div i)-m+1;
if(j>(rowCount-m)) then
j:= rowCount-m
else
begin
leftRow:=rowCount-m-j+1;
if not(dgTitles in DGC.Options) then
begin
leftRow:=leftRow-1;
end;
end;
end;
R.Top := DGC.Top+cellHeight*m;
R.Right := DGC.Left+IndicatorWidth;
R.Bottom := DGC.Top+cellHeight*(m+j);
R.Left := R.Right -40;
T:=R;
m:=m+j;
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left, R.Top, R.Right, R.Bottom);
R.Top := DGC.Top+cellHeight*m;
R.Right := DGC.Left+IndicatorWidth;
R.Left := R.Right-40;
for n:=1 to length(tmpString)do
begin
R:=T;
R.Bottom:=R.top+cellHeight;
T.Top:=T.Top+cellHeight;
T.Bottom:=T.Top+cellHeight;
R := ScaleToPrinter(R);
C[0]:=tmpString[n];
C[1]:=tmpString[n+1];
WinProcs.DrawText(PDC, C, 2, R,
(DT_CENTER or DT_VCENTER or DT_SINGLELINE));
end;
end;

DGC.DataSource.DataSet.First;
if not(dgTitles in DGC.Options) then
i:=1
else
i:=0;
if pagerowNum=0 then
all:=rowCount
else
if (endpage*pagerownum)<(rowCount) then
all:=endpage*pagerownum
else
all:=rowCount;
if i+startpage*pagerowNum>0 then
for l:=1 to i+startpage*pagerowNum-1do
DGC.DataSource.DataSet.Next;
for K :=i+startpage*pagerowNum to alldo
//for K := i to rowCountdo
begin

ColLeft :=DGC.Left+IndicatorWidth;
fieldi:=0;
fieldr:=0;
for J:= 0 to DGC.FieldCount - 1do
begin
//if K=0 then
if (k-startpage*pagerowNum)=0 then
if not(dgTitles in DGC.Options) then
continue;
while (DGC.DataSource.DataSet.Fields[fieldi].Visible=False)do
fieldi:=fieldi+1;
//cellWidth :=DGC.Columns.Items[fieldi].width+1;
//[fieldi].Grid.Width;
cellWidth :=DGC.Columns.Items[fieldr].width+1;
R.Top := RowTop;
R.Bottom := R.Top+cellHeight;
R.Left := ColLeft;
R.Right := R.Left+cellWidth;
if R.Right >= R.Left then
begin
X := R;
R := ScaleToPrinter(R);
PDCCanvas.Brush.Style := bsClear;
if dgColLines in DGC.Options then
//print grid lines or not
PDCCanvas.Rectangle(R.Left, R.Top, R.Right, R.Bottom);
//if K=0 then
if (k-startpage*pagerowNum)=0 then
StrPCopy(C,DGC.DataSource.DataSet.Fields[fieldi].DisplayLabel)
else
begin
if (DGC.DataSource.DataSet.Fields[fieldi].asString = '00/01/01') then
StrPCopy(C,' ')
else
StrPCopy(C,DGC.DataSource.DataSet.Fields[fieldi].AsString);
end ;
R.Left :=R.Left+7;
R.Right :=R.Right-7;
Format:=(DT_EXPANDTABS or DT_WORDBREAK) or (DT_SINGLELINE
or DT_VCENTER);
if K=0 then
Format := Format or DT_LEFT
else
begin
if taLeftJustify = DGC.DataSource.DataSet.Fields[fieldi].Alignment then
Format := Format or DT_LEFT;
if taRightJustify = DGC.DataSource.DataSet.Fields[fieldi].Alignment then
Format := Format or DT_RIGHT;
if taCenter = DGC.DataSource.DataSet.Fields[fieldi].Alignment then
Format := Format or DT_CENTER;
end;
if not ifpreview then
WinProcs.DrawText(PDC, C, StrLen(C), R,Format)
else
PDCcanvas.TextOut(r.left-3,r.top+3,c);
ColLeft := ColLeft+cellWidth;
end;
fieldi:=fieldi+1;
fieldr:=fieldr+1;
end;
//end of a cell,next row
RowTop := RowTop + cellHeight;
//
if ifpreview then
if ((RowTop+cellHeight+PageBottom/scaley)>round((PDCcanvas.ClipRect.Bottom-PDCcanvas.ClipRect.Top-PageBottom)/scaley+0.5)) AND (k<RowCount) then
begin
printPageHeader;
if pagerownum=0 then
begin
pagerowNum:=k;
endpage:=round(RowCount/pagerowNum+0.5);
pagetotal:=endpage;
end;
break;
end;
//
if ((RowTop+ cellHeight+PageBottom/scaley)>round((Printer.PageHeight-pageBottom+0.5)/scaley+0.5)) AND (k<RowCount) then
begin
if startpage=endpage then
break;
printPageBottom;
printPageHeader;
printtableheader;
if fifshowpageno then
printpagenum;
RowTop:=DGC.Top;
PDCCanvas.Font := DGC.Font;
PDCCanvas.Font.Size := round(DGC.Font.Size*fscale);
if ifpreview then
PDCCanvas.Font.Size :=round(DGC.Font.Size*scalex-0.50);
if (dgTitles in DGC.Options) then
begin
ColLeft :=DGC.Left+IndicatorWidth;
fieldi:=0;
fieldr:=0;
for j:=0 to DGC.FieldCount - 1do
begin
StrPCopy(C,DGC.DataSource.DataSet.Fields[fieldi].DisplayLabel);
while (DGC.DataSource.DataSet.Fields[fieldi].Visible=False)do
fieldi:=fieldi+1;
//cellWidth :=DGC.Columns.Items[fieldi].width+1;
cellWidth :=DGC.Columns.Items[fieldr].width+1;
R.Left:=colleft;
R.Right:=r.Left+cellwidth;
R.Top:=rowtop;
R.Bottom:=R.Top+cellheight;
R:=scaletoprinter(r);
WinProcs.DrawText(PDC, C, StrLen(C), R,Format);
PDCCanvas.Rectangle(R.Left,R.Top,R.Right , R.Bottom);
fieldi:=fieldi+1;
fieldr:=FIELdr+1;
ColLeft := ColLeft+cellwidth;
end;
RowTop := RowTop + cellheight;
end;
//
if(leftRow>0) then
begin
i:=Round(Printer.PageHeight/ScaleY -PageBottom-DGC.Top)div cellHeight;
R.Top := DGC.Top;
R.Right := DGC.Left+IndicatorWidth;
if(leftRow<i) then
begin
R.Bottom := DGC.Top+cellHeight*leftRow;leftRow:=0;
end
else
begin
R.Bottom := DGC.Top+cellHeight*(i+1);leftRow:=leftRow-i-1;
end;
R.Left := R.Right -40;
T:=R;
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left, R.Top, R.Right, R.Bottom);
end;
end;
if K>0 then
DGC.DataSource.DataSet.Next;
end;
//*****************************//
//以下为打空行
if fifprintemptyline then
begin
rowtop:=rowtop;
if (k=all+1) and (all<endpage*pagerownum) then
for k:=all to endpage*pagerownum-1do
begin
ColLeft :=DGC.Left+IndicatorWidth;
fieldi:=0;
for j:=0 to DGC.FieldCount - 1do
begin
cellWidth :=DGC.Columns.Items[fieldi].width+1;
R.Left:=colleft;
R.Right:=r.Left+cellwidth;
R.Top:=rowtop;
R.Bottom:=R.Top+cellheight;
r:=scaletoprinter(r);
PDCCanvas.Rectangle(R.Left,R.Top,R.Right , R.Bottom);
fieldi:=fieldi+1;
ColLeft := ColLeft+cellwidth;
end;
RowTop := RowTop + cellheight;
end;
end;
end;

{ ================================================================= }
procedure TPrint.PrintHeader(MC:THeader);
const
Alignments: array[TAlignment] of Word = (DT_LEFT, DT_RIGHT, DT_CENTER);
var
Bottom,Top,Width:integer;
i: integer ;
begin
PDCCanvas.Font := MC.Font;
PDC := PDCCanvas.Handle;
{so DrawText knows about font}
R.Left:=MC.ClientOrigin.x-SW.ClientOrigin.x;
R.Top:=MC.ClientOrigin.y-SW.ClientOrigin.y;
R.Right:=R.Left+Mc.Width;
R.Bottom:=R.Top+MC.Height;
if (MC.Tag=4) or (MC.Tag=5) then
begin
R.Top := realfoottop+(MC.ClientOrigin.y-sw.ClientOrigin.y-foottop);
R.Left:=MC.ClientOrigin.x-sw.ClientOrigin.x;
R.Bottom:=R.Top+MC.Height;
R.Right:=R.Left+MC.Width;
end;
bottom := R.Bottom ;
top := R.Top ;
Width := R.Left ;
Format := DT_VCENTER or DT_SINGLELINE or DT_LEFT ;
for i:=0 to MC.Sections.Count-1do
begin
R.top := top ;
R.bottom := bottom ;
R.Left := Width ;
R.Right := R.left+MC.sectionWidth ;
R := ScaleToPrinter(R);
PDCCanvas.Rectangle(R.Left, R.Top, R.Right,R.Bottom);
StrPCopy(C,MC.Sections.Strings);
WinProcs.DrawText(PDC, C, StrLen(C), R, Format);
width := width+MC.sectionWidth ;
end;
end;

procedure TPrint.PrintForm;
var Form_preview:TForm;
Bitbtn_Print:TBitbtn;
Bitbtn_Preview:TBitbtn;
Bitbtn_close:TBitbtn;
BitBtn_setup:TBitbtn;
BitBtn_prior:TBitbtn;
Bitbtn_next:TBitBtn;
Scrollbox_canvas:Tscrollbox;
Checkbox_autoscale:TCheckbox;
Edit_scale:TComboBox;
Label_scale:TLabel;
Panel_Btn:TPanel;
Panel_Canvas:TPanel;
Image:TImage;
i:integer;
str:string;
begin
form_preview:=tform.Create(self);
with form_previewdo
begin
windowstate:=wsMaximized;
name:='form_preview';
caption:='打印对话框';
font.Name:='宋体';
font.Size:=9;
onshow:=FormBitbtn_PreviewOnclick;
onresize:=Formresize;
end;
Panel_Btn:=tpanel.Create(form_preview);
with panel_btndo
begin
parent:=form_preview;
name:='panel_btn';
caption:='';
height:=30;
align:=altop;
end;
scrollbox_canvas:=tscrollbox.Create(form_preview);
with scrollbox_canvasdo
begin
parent:=form_preview;
name:='scrollbox_canvas';
align:=alclient;
end;
Panel_Canvas:=tpanel.Create(scrollbox_canvas);
with Panel_Canvasdo
begin
parent:=scrollbox_canvas;
name:='Panel_Canvas';
caption:='';
height:=30;
top:=0;
left:=0;
height:=screen.Height-round((panel_btn.Height+24)*1.25);
width:=screen.Width-5;
bevelouter:=bvnone;
end;
Bitbtn_close:=TBitbtn.Create(Panel_Btn);
with Bitbtn_closedo
begin
parent:=Panel_Btn;
name:='Bitbtn_close';
left:=10;
top:=2;
width:=80;
hint:='返回';
showhint:=true;
caption:='返回(&amp;X)';
onclick:=formclose;
end;
Bitbtn_setup:=TBitbtn.Create(Panel_Btn);
with Bitbtn_setupdo
begin
parent:=Panel_Btn;
name:='Bitbtn_setup';
left:=90;
top:=2;
width:=80;
hint:='设置打印机属性';
showhint:=true;
caption:='设置(&amp;S)';
onclick:=FormBitbtn_setupOnClick;
end;
Bitbtn_Preview:=TBitbtn.Create(Panel_Btn);
with Bitbtn_Previewdo
begin
parent:=Panel_Btn;
name:='Bitbtn_Preview';
left:=170;
top:=2;
width:=80;
hint:='预览';
showhint:=true;
caption:='预览(&amp;V)';
onclick:=FormBitbtn_PreviewOnclick;
end;
Bitbtn_Print:=TBitbtn.Create(Panel_Btn);
with Bitbtn_Printdo
begin
parent:=Panel_Btn;
name:='Bitbtn_Print';
left:=250;
top:=2;
width:=80;
hint:='开始打印';
showhint:=true;
caption:='打印(&amp;P)';
onclick:=FormPrintOnClick;
end;
Bitbtn_Prior:=TBitbtn.Create(Panel_Btn);
with Bitbtn_priordo
begin
parent:=Panel_Btn;
name:='Bitbtn_Prior';
left:=330;
top:=2;
width:=80;
hint:='前一页';
showhint:=true;
caption:='前页(&amp;B)';
onclick:=FormBitBtn_priorClick;
end;
Bitbtn_next:=TBitbtn.Create(Panel_Btn);
with Bitbtn_nextdo
begin
parent:=Panel_Btn;
name:='Bitbtn_next';
left:=410;
top:=2;
width:=80;
hint:='后一页';
showhint:=true;
caption:='后页(&amp;N)';
onclick:=FormBitbtn_nextClick;
end;
Checkbox_autoscale:=TCheckbox.Create(Panel_Btn);
with Checkbox_autoscale do
begin
parent:=Panel_Btn;
left:=500;
top:=8;
width:=80;
name:='Checkbox_autoscale';
caption:='自动缩放';
showhint:=true;
hint:='根据纸张大小自动选择缩放比例';
checked:=false;
OnClick:=FormCheckboxOnCheck;
end;
Label_scale:=TLabel.Create(Panel_Btn);
with Label_scale do
begin
parent:=Panel_Btn;
left:=520;
top:=10;
width:=200;
name:='Label_scale';
caption:='打印比例:';
visible:=false;
end;
Edit_scale:=TComboBox.Create(Panel_Btn);
with Edit_scaledo
begin
parent:=Panel_Btn;
left:=590;
top:=4;
width:=55;
text:='1.0';
showhint:=true;
hint:='选择打印缩放比例';
style:=csDropDownList;
name:='Edit_scale';
items.Add('自定义');
for i:=1 to 50do
begin
str:=floattostr(i/10*100);
str:=copy(str,1,3);
str:=str+'%';
items.Add(str) ;
end;
itemindex:=round(scale*10);
onchange:=FormEditOnchange;
end;

Image:=Timage.Create(Panel_canvas);
with Imagedo
begin
parent:=Panel_canvas;
left:=0;
top:=5;
height:=600;
width:=800;
name:='image';
onmousedown:=Image1MouseDown;
onmouseup:=image1mouseup;
end;
if not (fimagelist=NIL) then
for i:=0 to fimagelist.Countdo
case i of
1:fimagelist.GetBitmap(0,BitBtn_close.glyph);
2:fimagelist.getbitmap(1,BitBtn_setup.Glyph);
3:fimagelist.getbitmap(2,Bitbtn_Preview.Glyph);
4:fimagelist.GetBitmap(3,Bitbtn_Print.Glyph);
5:fimagelist.GetBitmap(4,BitBtn_prior.Glyph);
6:fimagelist.GetBitmap(5,BitBtn_next.Glyph);
end;
scalebynum:=1;
if ifautoscale then
begin
edit_scale.Visible:=false;
checkbox_autoscale.Checked:=true;
end;
try
form_preview.ShowModal;
finally
form_preview.free;
end;
end;

procedure Tprint.initform;
var F:tform;
S:Tscrollbox;
P:tpanel;
begin
F:=tform(self.findcomponent('Form_preview'));
s:=Tscrollbox(f.findcomponent('scrollbox_canvas'));
P:=tpanel(s.findcomponent('Panel_canvas'));
p.left:=0;
p.top:=0;
end;

procedure Tprint.FormClose(sender:Tobject);
var F:tform;
begin
F:=tform(self.findcomponent('Form_preview'));
f.close;
end;

procedure Tprint.Image1MouseUp(Sender: TObject;
Button: TMouseButton;
Shift: TShiftState;
X, Y: Integer);
var F:Tform;
P:tpanel;
s:Tscrollbox;
begin
F:=tform(self.findcomponent('Form_preview'));
s:=Tscrollbox(f.findcomponent('scrollbox_canvas'));
P:=tpanel(s.findcomponent('Panel_canvas'));
if button=mbleft then
begin
P.left:=p.left+x-mousex;
p.TOp:=p.top+y-mousey;
ifmove:=false;
end;
end;

procedure Tprint.Image1MouseDown(Sender: TObject;
Button: TMouseButton;
Shift: TShiftState;
X, Y: Integer);
var F:Tform;
P:tpanel;
s:Tscrollbox;
begin
F:=tform(self.findcomponent('Form_preview'));
s:=Tscrollbox(f.findcomponent('scrollbox_canvas'));
P:=tpanel(s.findcomponent('Panel_canvas'));
if button=mbleft then
begin
ifmove:=true;
mousex:=x;
mousey:=y;
if ssdouble in shift then
begin
if scalebynum=1 then
begin
p.ScaleBy(180,100);
p.top:=2*s.ClientOrigin.y-p.ClientOrigin.y;
p.left:=2*s.ClientOrigin.x-p.ClientOrigin.x;
scalebynum:=scalebynum+1;
FormBitbtn_PreviewOnclick(sender);
exit;
end;
if scalebynum=2 then
begin
p.ScaleBy(100,180);
p.top:=2*s.ClientOrigin.y-p.ClientOrigin.y;
p.left:=2*s.ClientOrigin.x-p.ClientOrigin.x;
scalebynum:=scalebynum-1;
FormBitbtn_PreviewOnclick(sender);
exit;
end;
end;
end;
end;


procedure Tprint.FormBitBtn_priorClick(sender:Tobject);
begin
if startpage<>0 then
begin
startpage:=startpage-1;
TBitbtn(TPanel(TBitbtn(sender).parent).findcomponent('Bitbtn_next')).enabled:=true;
end;
if startpage=0 then
Tbitbtn(sender).enabled:=false;
FormBitbtn_PreviewOnclick(sender);
end;

procedure Tprint.FormBitbtn_nextClick(sender:Tobject);
begin
if startpage<>pagetotal-1 then
begin
startpage:=startpage+1;
if endpage<=startpage then
endpage:=endpage+1;
TBitbtn(TPanel(TBitbtn(sender).parent).findcomponent('Bitbtn_Prior')).enabled:=true;
end;
if startpage=pagetotal-1 then
Tbitbtn(sender).enabled:=false;
FormBitbtn_PreviewOnclick(sender);
end;

procedure Tprint.FormResize(sender:Tobject);
begin
if Tform(sender).active then
FormBitbtn_PreviewOnclick(sender);
end;

procedure Tprint.FormBitbtn_setupOnClick(sender:Tobject);
var D:Tprintdialog;
begin
D:=Tprintdialog.create(self);
D.Options:=[poPageNums, poWarning, poHelp];//, poPrintToFile, poSelection, poDisablePrintToFile];
D.MinPage:=0;
D.MaxPage:=pagetotal-1;
D.FromPage:=startpage;
d.ToPage:=pagetotal-1;
if D.execute then
begin
startpage:=D.FromPage;
endpage:=D.ToPage+1;
FormBitbtn_PreviewOnclick(sender);
end;
end;

procedure TPrint.FormBitbtn_PreviewOnclick(sender:Tobject);
var F:tform;
P:tpanel;
I:TImage;
S:Tscrollbox;
begin
F:=tform(self.findcomponent('Form_preview'));
s:=tscrollbox(f.findcomponent('scrollbox_canvas'));
P:=tpanel(s.findcomponent('Panel_canvas'));
I:=timage(p.findcomponent('image'));
I.free;
I:=Timage.Create(P);
with Ido
begin
parent:=P;
left:=0;
top:=15;
height:=600;
width:=800;
name:='image';
cursor:=crhandpoint;
onmousedown:=Image1MouseDown;
onmouseup:=image1mouseup;

end;
ifPreview:=true;
begin
print;
initform;
end;

procedure TPrint.FormEditOnchange(sender:Tobject);
var E:TEdit;
lsstr:string;
begin
E:=TEdit(sender);
if E.Text<>'自定义' then
begin
lsstr:=E.Text;
lsstr:=copy(lsstr,1,length(lsstr)-1);
try
fscale:=strtofloat(lsstr)/100;
except
end;
pagetotal:=1;
startpage:=0;
endpage:=0;
pageRowNum:=0;
TBitbtn(TPanel(TCombobox(sender).parent).findcomponent('Bitbtn_Prior')).enabled:=true;
TBitbtn(TPanel(TCombobox(sender).parent).findcomponent('Bitbtn_next')).enabled:=true;
FormBitbtn_PreviewOnclick(sender);
end else
begin
lsstr:=InputBox('缩放比例输入对话框', '请输入(%):', '100');
// lsstr:=copy(lsstr,1,length(lsstr)-1);
try
fscale:=strtofloat(lsstr)/100;
except
fscale:=1.0;
showmessage('输入错误,请再试!')
end;
pagetotal:=1;
startpage:=0;
endpage:=0;
pageRowNum:=0;
TBitbtn(TPanel(TCombobox(sender).parent).findcomponent('Bitbtn_Prior')).enabled:=true;
TBitbtn(TPanel(TCombobox(sender).parent).findcomponent('Bitbtn_next')).enabled:=true;
FormBitbtn_PreviewOnclick(sender);
end;
end;

procedure TPrint.FormCheckboxOnCheck(sender:Tobject);
var C:Tcheckbox;
E:TCombobox;
L:TLabel;
P:Tpanel;
lsstr:string;
begin
c:=tcheckbox(sender);
P:=TPanel(c.parent);
E:=TCombobox(P.findcomponent('Edit_scale'));
L:=Tlabel(p.findcomponent('Label_scale'));
if c.Checked then
begin
e.Visible:=false;
l.Visible:=false;
fautoscale:=true;
end else
begin
e.Visible:=true;
l.Visible:=true;
if e.Text<>'自定义' then
begin
lsstr:=E.text;
lsstr:=copy(lsstr,1,length(lsstr)-1);
fscale:=strtofloat(lsstr)/100;
end else
begin
fscale:=1.0;
end;
fautoscale:=false;
end;
pagetotal:=1;
startpage:=0;
endpage:=0;
pageRowNum:=0;
TBitbtn(TPanel(Tcheckbox(sender).parent).findcomponent('Bitbtn_Prior')).enabled:=true;
TBitbtn(TPanel(Tcheckbox(sender).parent).findcomponent('Bitbtn_next')).enabled:=true;
FormBitbtn_PreviewOnclick(sender);
end;

procedure Tprint.FormPrintOnClick(sender:Tobject);
begin
ifpreview:=false;
PDCCanvas:=printer.Canvas;
begin
print;
end;
{$ifdef MergeGrid}
function Tprint.Max(i1,i2:Integer):Integer;
begin
Result:=i1;
if i2>i1 then
Result:=i2;
end;

function tprint.Min(i1,i2:Integer):Integer;
begin
Result:=i1;
if i2<i1 then
Result:=i2;
end;

{$endif}
end.
 
> 是呀,还是blueboy明白道理,反正我的网速快,随便你贴多长都没没关系!呵呵
> 不过为了照顾速度慢的你可以另外开几个帖子,分段贴上来,只要把帖子号在这里
> 公布一下,让大家知道就行了。
哇,你真厉害,果然够长!我刚想说可以另开帖子贴上来的,没有提交成功,再刷新
就有发现了这个剧长的帖子!谢谢啦,保存起来 :-)
 
好东西哦。先存起来。呵呵。
其实打个包传到网上吧,要是没有地方放的话,先mail 给我? wzca@sina.com
我提供一个地方。呵呵。
先谢了。
 
这么长
写了多长时间
打字都要几天了
 
Email给我吧 yj5637899@163.net
 
都贴出来了还要我发E?你们可真懒。自已粘贴吧。[:)]
 
不知我是一百零几?
 
我copy,paste都累,太长了
 
好家伙,佩服佩服。
 
echo_delphi@x263.net
 

Similar threads

D
回复
0
查看
2K
DelphiTeacher的专栏
D
D
回复
0
查看
1K
DelphiTeacher的专栏
D
D
回复
0
查看
1K
DelphiTeacher的专栏
D
后退
顶部