变量问题 (100分)

  • 主题发起人 nullbert
  • 开始时间
为何不贴出myprint的完整代码?
我怀疑出错的是colnum:=colnum+1;之后的语句。
 
代码是这样的

unit Unit1;

interface

uses Windows, SysUtils, Classes, Graphics, Forms, Controls, StdCtrls,
Buttons, ExtCtrls, Dialogs,dbgrids,printers;

type
Tprintdlg = class(TForm)
OKBtn: TButton;
CancelBtn: TButton;
Button1: TButton;
ScrollBox1: TScrollBox;
Panel1: TPanel;
Image1: TImage;
PageSetupDialog1: TPageSetupDialog;
procedure Button1Click(Sender: TObject);
procedure reportmetafile;
private

public
{ Public declarations }
end;

var
printdlg: Tprintdlg;
dbgrid1:tdbgrid;

procedure mypreview(dbgrid:tdbgrid);export;

implementation

{$R *.dfm}

procedure mypreview(dbgrid:tdbgrid);
begin
dbgrid1:=dbgrid;
printdlg:=tprintdlg.Create(application);

try
with printdlg do
begin
reportmetafile;
image1.Picture.Metafile.Clear;
image1.Picture.Metafile.LoadFromFile('page1.wmf');
if showmodal=mrok then
begin
//printer.begindoc;
//printer.Canvas.Draw(0,0,image1.Picture.metafile);
//printer.enddoc;
end;
end;
finally
printdlg.Free;
end;
end;

procedure Tprintdlg.Button1Click(Sender: TObject);
begin
with pagesetupdialog1 do
if execute then
begin
reportmetafile;
image1.picture.metafile.clear;
image1.picture.metafile.loadfromfile('page1.wmf');
end;
end;


procedure tprintdlg.reportmetafile;
const
leftblank=1;
topblank=1;
rightblank=1;
bottomblank=2;
var
i,r,j,pagenum:integer;
pointx,pointy,pointscale:integer;
printstep:integer;
x,y:integer;
s,metafilename:string;
rownum,colnum:array of integer;
mymetafile:tmetafile;
mymetafilecanvas:tmetafilecanvas;
begin
setlength(rownum,20);
setlength(colnum,20);
for i:=0 to 20-1 do
begin
rownum:=0;
colnum:=0;
end;
r:=0;
j:=1;
pagenum:=1;
dbgrid1.datasource.dataset.First;

PointX:=Trunc(GetDeviceCaps(Printer.Handle,LOGPIXELSX)/2.54);
PointY:=Trunc(GetDeviceCaps(Printer.Handle,LOGPIXELSY)/2.54);
PointScale:=Trunc(GetDeviceCaps(Printer.Handle,LOGPIXELSX)/Screen.PixelsPerInch+1.5);
printer.Canvas.Font.Name:='宋体';
printer.canvas.Font.Size:=10;
s:='出货分类统计表';
PrintStep:=printer.canvas.TextHeight(s)+16;

while not dbgrid1.datasource.dataset.Eof do
begin
mymetafile:=tmetafile.Create;
mymetafilecanvas:=tmetafilecanvas.create(mymetafile,printer.handle);


x:=PointX*LeftBlank;
y:=PointY*TopBlank;

while (not dbgrid1.datasource.dataset.Eof) and ((y+printstep)<(Printer.PageHeight-PointY*BottomBlank)) do
begin
for i:=0 to DBGrid1.FieldCount-1 do
begin
if (x+DBGrid1.Columns.Items.Width*PointScale)<=(Printer.PageWidth-PointX*RightBlank) then
begin
if i=0 then
begin
mymetafilecanvas.moveto(x,y+200);
mymetafilecanvas.lineto(x,y+200+printstep);
end;
mymetafilecanvas.moveto(x,y+200);
mymetafilecanvas.lineto(x+dbgrid1.Columns.Items.Width*pointscale,y+200);
if y=PointY*TopBlank then
begin
mymetafilecanvas.Font.Name:='黑体';
mymetafilecanvas.Font.Size:=96;
mymetafilecanvas.TextOut((Printer.PageWidth-printer.Canvas.TextWidth(s)) div 2,y+8,s);
mymetafilecanvas.Font.Name:='宋体';
mymetafilecanvas.Font.Size:=68;
mymetafilecanvas.TextOut(x+8,y+8+200,DBGrid1.Columns.Title.Caption);
mymetafilecanvas.moveto(x+dbgrid1.Columns.Items.Width*pointscale,y+200);
mymetafilecanvas.lineto(x+dbgrid1.Columns.Items.Width*pointscale,y+200+printstep);
colnum[j]:=colnum[j]+1;
end
else
begin
mymetafilecanvas.TextOut(x+8,y+200+8,DBGrid1.Fields.asString);
mymetafilecanvas.moveto(x+dbgrid1.Columns.Items.Width*pointscale,y+200);
mymetafilecanvas.lineto(x+dbgrid1.Columns.Items.Width*pointscale,y+200+printstep);
end;
end;
x:=x+DBGrid1.Columns.Items.Width*PointScale;
end;
if not (y=PointY*TopBlank) then
dbgrid1.datasource.dataset.next;
x:=PointX*LeftBlank;
y:=y+PrintStep;
end;



if j=1 then
begin
r:=dbgrid1.datasource.dataset.recno;
pagenum:=trunc(dbgrid1.datasource.dataset.recordcount/r)+1;
end;
for i:=0 to colnum[j]-1 do
begin
mymetafilecanvas.moveto(x,y+200);
mymetafilecanvas.lineto(x+dbgrid1.Columns.Items.Width*pointscale,y+200);
x:=x+dbgrid1.Columns.Items.width*pointscale;
end;
x:=pointx*leftblank;
mymetafilecanvas.TextOut(x+8,y+200+8,'第'+inttostr(j)+'页'+''+''+'共'+inttostr(pagenum)+'页');
rownum[j]:=dbgrid1.datasource.dataset.recno-rownum[j-1];



{if j=pagenum then
begin
rownum[j]:=dbgrid1.datasource.dataset.recordcount-r*(j-1);
for i:=0 to colnum[j]-1 do
begin
mymetafilecanvas.moveto(x,y+200);
mymetafilecanvas.lineto(x+dbgrid1.Columns.Items.Width*pointscale,y+200);
x:=x+dbgrid1.Columns.Items.width*pointscale;
end;
x:=pointx*leftblank;
mymetafilecanvas.TextOut(x+8,printer.PageHeight-bottomblank*pointy,'第'+inttostr(j)+'页'+''+''+'共'+inttostr(pagenum)+'页');
end
}

mymetafilecanvas.Free;
metafilename:='page'+inttostr(j)+'.wmf';
delete(metafilename,0,sizeof(metafilename));
mymetafile.Savetofile(metafilename);
mymetafile.free;
j:=j+1;
end;

dbgrid1.datasource.dataset.First;
end;

end.


 
如果打印只有一页,就不会出问题,
如果打印有两页,就会报错.
 
问题出在button1,如果你多按几次,就会报错'access vielation address at xxxx write
of address xxxx'
 
你不是说编译不能通过吗,怎么代码都变了
 
我该了一下代码
 
我怀疑是不是图元文件太大导致内存不够,
但是为什么第一次按button1就没问题,
后来就不行了,
到底是什么东西在内存中没释放掉呢
 
况且打一页就行,打两页就不行
一页和两页没什么区别呀
 
我看到就烦躁,这个Bug还是自己找吧:
先把reportmetafile;注释掉,再编译执行,以确定错误是不是发生在reportmetafile中,
......
类似地,最后找到出错的语句就好办了。
 
太长了,关于内存溢出,你可以找MemProof分析一下
问题应该在reportmetafile里面,你单步跟踪一下吧
至于procedure reportmetafile;和 dbgrid1:tdbgrid;的位置不会有问题
另外,我不知道“delete(metafilename,0,sizeof(metafilename));”有什么用


 
while not dbgrid1.datasource.dataset.Eof do begin
mymetafile:=tmetafile.Create;
mymetafilecanvas:=tmetafilecanvas.create(mymetafile,printer.handle);
。。。。
mymetafilecanvas.Free;
mymetafile.free;
end;
===============
mymetafile:=tmetafile.Create;
mymetafilecanvas:=tmetafilecanvas.create(mymetafile,printer.handle);
while not dbgrid1.datasource.dataset.Eof do begin
。。。。
end;
mymetafilecanvas.Free;
mymetafile.free;
移到外面去吧,避免内存可能释放不赢
 
你为什么不跟踪呢?如果有困难的话,这样吧:
var
printdlg: Tprintdlg;
dbgrid1:tdbgrid;
err:integer;//<======加一行
-----------
procedure tprintdlg.reportmetafile;
const
...
var
...
begin
try
err:=0;
setlength(rownum,20);
err:=1;
setlength(colnum,20);
err:=2;
........
except
showmessage(inttostr(err));//<=====嘿嘿,看来就用这个方法喽
end;

end.





 
if j=1 then
begin
r:=dbgrid1.datasource.dataset.recno;
pagenum:=trunc(dbgrid1.datasource.dataset.recordcount/r)+1;
end;
for i:=0 to colnum[j]-1 do
begin
mymetafilecanvas.moveto(x,y+200);
mymetafilecanvas.lineto(x+dbgrid1.Columns.Items.Width*pointscale,y+200);
x:=x+dbgrid1.Columns.Items.width*pointscale;
end;
x:=pointx*leftblank;
!mymetafilecanvas.TextOut(x+8,y+200+8,'第'+inttostr(j)+'页'+''+''+'共'+inttostr(pagenum)+'页');
rownum[j]:=dbgrid1.datasource.dataset.recno-rownum[j-1];
就是这个mymetafilecanvas.textout!
 
if j=1 then
begin
r:=dbgrid1.datasource.dataset.recno;
pagenum:=trunc(dbgrid1.datasource.dataset.recordcount/r)+1;
end;
for i:=0 to colnum[j]-1 do
begin
mymetafilecanvas.moveto(x,y+200);
mymetafilecanvas.lineto(x+dbgrid1.Columns.Items.Width*pointscale,y+200);
x:=x+dbgrid1.Columns.Items.width*pointscale;
end;
// x:=pointx*leftblank;
// mymetafilecanvas.TextOut(x+8,y+200+8,'第'+inttostr(j)+'页'+''+''+'共'+inttostr(pagenum)+'页');
// rownum[j]:=dbgrid1.datasource.dataset.recno-rownum[j-1];
mymetafilecanvas.Free;
! metafilename:='page'+inttostr(j)+'.wmf';
delete(metafilename,0,sizeof(metafilename));
mymetafile.Savetofile(metafilename);
mymetafile.free;
j:=j+1;
end;
删除这个mymetafilecanvas.textout!
之后,报错出在metafilename:='page'+inttostr(j)+'.wmf';
 
我http://www.to-happy.com的《大事》软件卖了不少钱,
编程语言就是delphi。你能挑出软件的错吗?
 
接受答案了.
 

Similar threads

S
回复
0
查看
1K
SUNSTONE的Delphi笔记
S
S
回复
0
查看
926
SUNSTONE的Delphi笔记
S
I
回复
0
查看
462
import
I
I
回复
0
查看
441
import
I
I
回复
0
查看
556
import
I
顶部