这个是我以前打印查询数据的一个通用程序,动态创建输入参数
调用SQL语句完成查询-> 导出数据到EXCEL
//****************************************************
//* 该模块用于统计实现报表功能,利用EXCEL的强大功能,*
//* 巧妙的实现了求行和和求列和 *
//****************************************************
unit U_New_Report;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs,ExtCtrls, Buttons,Excel2000, OleServer,ComCtrls;
type
tarray = array of TLabeledEdit;
TF_new_Report = class(TForm)
Panel1: TPanel;
B_close: TSpeedButton;
B_Ok: TSpeedButton;
procedure FormCreate(Sender: TObject);
procedure B_closeClick(Sender: TObject);
procedure B_OkClick(Sender: TObject);
private
{ Private declarations }
AEdit:tarray;
public
{ Public declarations }
Procedure Print_Excel(RepID:string);//打印EXCEL模本
end;
var
F_new_Report: TF_new_Report;
implementation
Uses Umain,PublicPro;
{$R *.dfm}
procedure TF_new_Report.FormCreate(Sender: TObject);
var
tempSQL,PreField,ECaption,EName:string;
tempPos,num,XLeft,XTop:integer;
ParaStr,Menu_name:string;
begin
Num:=0;
XLeft:=100;
XTop:=50;
//ShowMess(NowReportID);
//1、根据配置的报表信息,生成输入的编辑框,供用户输入
if NowReportID<>'0' then
begin
with Fmain.Q1do
begin
close;
sql.Clear;
tempSQL:='select * from syspz_report where ReportID='+NowReportID;
sql.Add(tempSQL);
open;
ParaStr :=FieldByName('ParaStr').AsString;
menu_name:=FieldByName('Menu_Name').AsString;
end;
//with
end;
//if
caption:=Menu_Name;
//显示窗体标题
//2、动态生成输入框
while paraStr<>''do
begin
tempPos :=pos(';',ParaStr);
PreField:=copy(ParaStr,1,TempPos-1);
//当前参数
ECaption:=copy(PreField,1,pos(',',PreField)-1);
//编辑框的名称
EName :=copy(PreField,Pos(',',PreField)+1,Length(PreField)-1);//编辑框的name
//*生成编辑框
Inc(Num);
SetLength(AEdit, Num);
if not Assigned(AEdit[Num-1]) then
begin
AEdit[Num-1] := TLabeledEdit.Create(Self);
AEdit[Num-1].Parent := Panel1;
AEdit[Num-1].Width := 150;
AEdit[Num-1].Left := XLeft ;
AEdit[Num-1].Top := XTop + 20 * Num;
AEdit[Num-1].Visible:= True;
AEdit[Num-1].EditLabel.caption :=ECaption + ':';
AEdit[Num-1].Name :=EName;
AEdit[Num-1].LabelPosition:=lpLeft;
AEdit[Num-1].Text:='';
end;
//********
paraStr:=copy(paraStr,tempPos+1,length(ParaStr));
end;
//while
end;
procedure TF_new_Report.B_closeClick(Sender: TObject);
begin
close;
end;
procedure TF_new_Report.B_OkClick(Sender: TObject);
begin
//如果用户没有填写数据,给出出错提示
Print_Excel(NowReportID);
end;
//SumRow 格式说明: A=Sum(B#+C#)
//利用替换函数,替换#为列号。巧妙的利用EXCEL的求和功能
procedure TF_new_Report.Print_Excel(RepID:string);
var
eaImport : TExcelApplication;//
ewbImport : TExcelWorkbook;
// v
sheet : TExcelWorksheet;
//sheet
I,J,k,IrowCount,tempPos:Integer;
//循环变量
tempSQL,tempStr,PreStr:string;
//临时变量
sqlStr,FileName,FieldStr,SumRow,SumCol:string;
//ColStr:表示哪列要求和
StartCol,StartRow,ColStr:integer;
SourcePath,PrintDate:string;
begin
SourcePath:=EXTRACTFILEPATH(PARAMSTR(0)) + DirPath;
//根据报表号找出SQL语句
with Fmain.Q1do
begin
close;
sql.Clear;
tempSQL:='select * from syspz_Report where reportId=' + RepId;
sql.Add(tempSQL);
open;
IRowCount:=RecordCount;
if IRowCount=0 then
begin
ShowMess('没有该报表的记录,请确认是否添加了该报表');
exit;
end;
SqlStr :=fieldByName('SqLStr').asstring;
FieldStr:=FieldByName('FieldStr').asstring;
FileName:=SourcePath + FieldByName('Path').AsString;
StartCol:=FieldByName('StartCol').AsInteger;
StartRow:=FieldByName('StartRow').AsInteger;
SumRow :=FieldByName('SumRow').AsString;
tempStr :=FieldByName('SumCol').AsString;
SumCol :=copy(tempStr,pos('(',tempStr)+1,length(tempStr)-5);
//获取SUM(B:C
中括号的内容
end;
//往EXCEL写入数据
with Fmain.Q1do
begin
close;
sql.Clear;
//根据参数给SQL语句赋值
parameters.Clear;
sql.Add(SqlStr);
for i:=0 to high(AEdit)do
begin
parameters.ParamByName(AEdit
.Name).Value:=AEdit.Text;
//parameters.Value:=trim(AEdit.Text);
//*********************
end;
showmessage(sql.Text);
Open;
IrowCount:=RecordCount;
if IRowCount=0 then
begin
ShowMess('该报表现在暂时没有你要的数据');
exit;
end;
//打开已存在的报表,插入数据
eaImport := TExcelApplication.Create(Application);
try
eaImport.ConnectKind := ckNewInstance;
eaImport.Connect;
except
showmess('请先安装 Excel !');
eaImport.Free;
Exit;
end;
try
eaImport.Workbooks.Open(FileName,null,null,null,null,null,null,null,null,null,null,null,null,0);
eaImport.Visible[1] := true;
except
eaImport.Disconnect;
eaImport.Quit;
eaImport.Free;
showmess('无法打开文件!');
Exit;
end;
try
ewbImport := TExcelWorkbook.Create(Application);
sheet := TExcelWorksheet.Create(Application);
Fmain.SBar.panels[0].text:='正在读取数据...';
ewbImport.ConnectTo(eaImport.Workbooks[1]);
sheet.ConnectTo(ewbImport.Worksheets[1] as _Worksheet);
//打印页面设置
sheet.PageSetup.CenterFooter:=' 注:第 &P 页(总共&N页)';
sheet.PageSetup.TopMargin:=30;
sheet.PageSetup.BottomMargin:=30;
sheet.PageSetup.LeftMargin:=30;
sheet.PageSetup.RightMargin:=30;
sheet.PageSetup.CenterHorizontally:=true;//是否水平居中
//sheet.PageSetup.CenterVertically:=true;//是否垂直居中
sheet.PageSetup.Orientation:=2;
//1:竖打2:横打
sheet.PageSetup.Draft:=false;
//非草稿模式
//显示报表打印时间
PrintDate:=FormatDateTime('yyyymmdd',date);
sheet.Cells.Item[2,2]:=copy(PrintDate,1,4) + '年'
+copy(PrintDate,5,2) + '月'
+copy(PrintDate,7,2) + '日';
first;
//用循环取字符串的字段,然后插入到EXCEL表里
For i:=0 to IRowCount-1do
begin
j:=0;
k:=0;
tempStr:=FieldStr;
//*********************************************************************
//*取要显示的字符串的格式:FIELD_A,FIELD_B, * *
//* FIELD_A:表示SQL语句字段名称 *
//* , :表示字符名称分隔符号 *
//*********************************************************************
while tempStr<>''do
begin
tempPos:=pos(',',tempStr);
PreStr:=copy(tempStr,1,TempPos-1);
sheet.cells.Item[StartRow+i,StartCol+j]:=FieldByname(PreStr).asstring;
tempStr:=copy(tempStr,tempPos+1,length(tempStr));
inc(j);
end;
//while
//*********************************************************************
//*加入统计字段,使用EXCEL自带的统计功能可以实现大部分功能 20020403 *
//*统计行和字符串格式: A=SUM(B#+C#-D#);E=SUM(F#+G#-H#);
*
//* A :表示求和结果显示的列 *
//* =SUM(B#+C#-D#) :表示EXCEL里求和的表达式 *
//* # :表示列号 *
//* ;
:表示各个求和表达式的分隔符号 *
//*********************************************************************
tempStr:=SumRow;
while tempStr<>''do
begin
tempPos:=pos(';',tempStr);
PreStr :=copy(tempStr,1,TempPos-1);
//获取当前求行和的字符串
ColStr :=Trans_ColNum(copy(PreStr,1,1));
//利用函数返回字母的ASCII码
sheet.Cells.Item[StartRow+i,ColStr]:=replacing(copy(preStr,2,length(PreStr)-1),IntToStr(StartRow+i));
tempStr:=copy(tempStr,tempPos+1,length(tempStr));
inc(k);
end;
//while
next;
end;
//for
//*********************************************************************
//*加入统计字段,使用EXCEL自带的统计功能可以实现大部分功能 20020403 *
//*统计行和字符串格式: sum(A;B;C *
//* A :表示要求和的列 *
//* ;
:表示各个求和列的分隔符号 *
//*********************************************************************
tempStr:=SumCol;
sheet.Cells.Item[StartRow+IRowCount,1]:='合计:';
while tempStr<>''do
begin
tempPos:=pos(';',tempStr);
PreStr :=copy(tempStr,1,TempPos-1);
//获取当前求行和的字符串
sheet.Cells.Item[StartRow + IRowCount , Trans_ColNum(PreStr)]:='=sum(' + PreStr + IntToStr(StartRow) + ':' + PreStr + IntToStr(StartRow+IRowCount-1) + ')';
tempStr:=copy(tempStr,tempPos+1,length(tempStr));
end;
//while
//**************
//给数据加上边框
sheet.Range[sheet.Cells.Item[StartRow,StartCol],sheet.Cells.Item[StartRow+IRowCount,StartCol+J+k-1]].Borders.LineStyle :=1;
{sheet.Range[sheet.Cells.Item[4,4],sheet.Cells.Item[6,6]].Borders.LineStyle :=2;
//2到8都可以}
sheet.Disconnect;
ewbImport.Disconnect;
eaImport.Disconnect;
eaImport.Quit;
sheet.Free;
ewbImport.Free;
eaImport.Free;
Fmain.SBar.panels[0].text:='数据读取完毕。';
except
eaImport.Disconnect;
eaImport.Quit;
eaImport.Free;
showmess('文件读取错误!');
end;
//try
end;
//with
end;
end.