• DELPHI中四种EXCEL访问技术实现


    一、引言
    
    EXCEL在处理中文报表时功能非常强大,EXCEL报表访问也是信息系统开发中的一个重要内容,本文总结以往开发中所用到的几中EXCEL文件访问方法,在实际工作中也得到了很好的验证,本文列举了其中四种方法的实例与读者共享,程序已在WINDOWS2000操作系统、OFFFICE2000应用软件和DELPHI7环境下调试通过。
    
    二、ADO方式访问EXCEL文件
    
    ADO方式访问EXCEL文件时,将EXCEL文件看作一个等同Oracle、MS SQLServer等数据库的一个ODBC数据源本文应用示例主要功能是打开EXCEL文件,并实现对EXCEL文件的编辑修改功能。实现过程及主要源代码如下:
    
    1.在工程中新建窗口类TfrmADOEXCEL,在窗口中定义私有变量类型为TADOConnection的组件Conn,加入TADOTable组件ADOTabXLS、TDataSource组件DSXLS、TDBNavigator组件NavXLS 、TDBGrid组件GridXLS和TButton组件btnOpen,使用btnOpen可以打开EXCEL文件,使用NavXLS可以浏览编辑EXCEL文件数据。
    
    2.编写btnOpen组件的OnClick事件。需要注意两点,Conn组件的Extend Properties属性要定义成excel 8.0,另外,EXCEL文件中的表单名“人员信息表”作为表明时要写成“[人员信息表$]”。
    
    procedure TfrmADOEXCEL.btnOpenClick(Sender: TObject);
    
    //打开EXCEL文件代码
    
    begin
    
    Conn:=TADOConnection.Create(nil);
    
    Conn.ConnectionString:='Provider=Microsoft.Jet.OLEDB.4.0;Data Source='+ExtractFileDir(Application.ExeName)+'/PersonData.xls;Extended Properties=excel 8.0;Persist Security Info=False';
    
    Conn.LoginPrompt:=false;
    
    Conn.Connected:=true;
    
    ADOTabXLS.Connection:=Conn;
    
    ADOTabXLS.TableName:='['+'人员信息表'+'$]';
    
    ADOTabXLS.Active:=true;
    
    DSXLS.DataSet:=ADOTabXLS;
    
    GridXLS.DataSource:=DSXLS;
    
    except;
    
    FreeAndNil(Conn);
    
    end;
    
    end;
    
    三、COM方式动态访问EXCEL文件
    
    COM方式动态访问EXCEL文件时,基本方法是利用组件复用技术调用Office软件平台提供的COM服务组件,充分利用COM组件提供的方法操纵EXCEL文件。本文应用示例简单演示了如何利用COM技术将DataSet数据集的数据输出到EXCEL文件。实现过程及主要源代码如下:
    
    在工程中新建窗口类TfrmCOMEXCEL,在窗口中定义私有变量类型为TADOConnection的组件Conn,加入TADOTable组件ADOTabXLS和TButton组件btnOpen,使用btnOpen可以将数据输出到EXCEL文件。编写btnOpen组件的OnClick事件代码如下:
    
    procedure TfrmCOMEXCEL.btnOpenClick(Sender: TObject);
    
    var
    
    XL: Variant; //打开EXCEL文件的Variant变量
    
    Sheet: Variant;//指向EXCEL表单的Variant变量
    
    RecNo,I: Integer;//记录数据表的当前记录号
    
    begin
    
    try
    
    XL := CreateOleObject('Excel.Application');
    
    XL.Visible := true;
    
    if FileExists(ExtractFileDir(Application.ExeName)+'/test.xls') then
    
    begin
    
    XL.WorkBooks.Open(ExtractFileDir(Application.ExeName)+'/test.xls');
    
    end
    
    else XL.WorkBooks.Add;
    
    XL.WorkBooks[XL.WorkBooks.Count].WorkSheets[1].Name := 'test';
    
    Sheet := XL.WorkBooks[XL.WorkBooks.Count].WorkSheets[Trim('test')];
    
    RecNo := 1;
    
    ADOTabXLS.First;
    
    while not ADOTabXLS.Eof do
    
    begin
    
    for I := 0 to ADOTabXLS.FieldCount - 1 do
    
    if not (ADOTabXLS.Fields[I].DataType in [ftBlob, ftGraphic,
    
    ftParadoxOle, ftDBaseOle, ftTypedBinary,
    
    ftReference, ftDataSet, ftOraBlob, ftOraClob, ftInterface,
    
    ftIDispatch]) then
    
    begin
    
    Sheet.Cells.NumberFormat := '@';
    
    Sheet.Cells[RecNo, I+1] := ADOTabXLS.Fields[I].AsString;
    
    end;
    
    Inc(RecNo);
    
    ADOTabXLS.Next;
    
    end;
    
    try
    
    XL.WorkBooks[XL.WorkBooks.Count].SaveAs(ExtractFileDir(Application.ExeName)+'/test.xls');
    
    except ;
    
    end;
    
    end;
    
    四、扩展OLEContainer方式访问EXCEL文件
    
    在使用OLE方式访问EXCEL文件时,OLE容器在失去焦点会屏蔽正在访问的EXCEL文件操作;另外,使用in_place方式激活OLE容器时,会另外打开一个窗口,程序执行显得有些混乱,造成这些问题的主要原因是因为OLE容器响应了CM_UIDEACTIVATE消息,OLE容器不能始终保持激活状态。为此可将此消息结果使OLE容器始终处于激活状态。解决方法是重载OLE容器的CM_UIDEACTIVATE消息。在程序中临时创建重载后扩展OLE容器OLEContainerEx。代码如下:
    
    type
    
    TOleContainerEx=class(TOleContainer)
    
    private
    
    FJH: Boolean;
    
    //重写CM_UIDEACTIVATE消息响应
    
    procedure CMUIDeactivate(var Message: TMessage); message CM_UIDEACTIVATE;
    
    published
    
    property JH: Boolean read FJH write FJH;
    
    end;
    
    // 过程CMUIDeactivate的代码实现
    
    procedure TOleContainerEx.CMUIDeactivate(var Message: TMessage);
    
    begin
    
    if not JH then
    
    inherited;
    
    end;
    
    在使用TOLEContainerEx时,可采用临时创建的方式,也可进一步封装成可安装组建以便设计期使用。本文应用示例采用了临时创建的方式。在工程中新建窗口类TfrmEXOLEEXCEL,并定义Public变量 OleCon,类型为: TOleContainerEx;在窗口中定一个Tpanel类型组件panel1和Tbutton类型变量btnOpen,编写btnOpen的Click事件,主要源程序代码如下:
    
    procedure TfrmEXOLEEXCEL.btnOpenClick(Sender: TObject);
    
    begin
    
    //创建并显示扩展OLE类组件
    
    OleCon := TOleContainerEx.Create(nil);
    
    OleCon.Parent := Panel1;
    
    OleCon.Align:=alClient;
    
    OleCon.allowactivedoc := true;
    
    OleCon.AllowInPlace := True;
    
    OleCon.AutoActivate := aaGetFocus;
    
    OleCon.Anchors := [akTop,akLeft,akRight,akBottom];
    
    OleCon.Visible := True;
    
    OleCon.SizeMode := smClip;
    
    OleCon.CreateObjectFromFile(ExtractFileDir(Application.ExeName)+
    
    '/PersonData.xls',false);
    
    TOleContainerEx(OleCon).JH := True;
    
    OleCon.SetFocus;
    
    end;
    
    五、DELPHI标准组件访问EXCEL文件
    
    Delphi中封装了一组Microsoft Office自动化对象(Automation servers)。它使得我们很容易地把Office中的应用程序(Excel等)当作一个COM应用服务器进行控制。使用这组VCL组件可以在设计时进行属性设置,也可以在运行时动态访问EXCEL。利用标准组件动态访问EXCEL文件时,充分利用VCL组件提供的方法操纵EXCEL文件。本文应用示例简单演示了如何利用VCL组件将DataSet数据集的数据输出到EXCEL文件。实现过程及主要源代码如下:
    
    在工程中新建窗口类TfrmSTDCNTREXCEL,在窗口中加入TADOConnection组件ADOConnXLS,TADOTable组件ADOTabXLS、TButton组件btnOpen、TexcelApplication组件ExcelApplication1,TexcelWorkbook类组件ExcelWorkbook1和TExcelWorksheet1类组件ExcelWorksheet1,使用btnOpen可以将数据输出到EXCEL文件。编写btnOpen组件的OnClick事件代码如下。
    
    procedure TfrmSTDCNTREXCEL.btnOpenClick(Sender: TObject);
    
    var
    
    aWorksheet: _WorkSheet;
    
    tmpI,aRowIndex:integer;
    
    aStr:string;
    
    begin
    
    ADOConnXLS.ConnectionString:='Provider=Microsoft.Jet.OLEDB.4.0;Data Source='+ExtractFileDir(Application.ExeName)+'/PersonData.xls;Extended Properties=excel 8.0;Persist Security Info=False';
    
    ADOConnXLS.LoginPrompt:=false;
    
    ADOConnXLS.Connected:=true;
    
    ADOTabXLS.Connection:=ADOConnXLS;
    
    ADOTabXLS.TableName:='[人员信息表$]';
    
    ADOTabXLS.Active:=true;
    
    if ADOTabXLS.IsEmpty then exit;
    
    Try
    
    ExcelApplication1.Connect;
    
    Except
    
    MessageDlg('你还没有安装MicroSoft Excel,请先安装MicroSoft Excel!',mtError, [mbOk], 0);
    
    Abort;
    
    End;
    
    ExcelApplication1.Visible[0]:=True;
    
    ExcelApplication1.Caption := '新建EXCEL文件';
    
    ExcelWorkbook1.ConnectTo(ExcelApplication1.Workbooks.Add(EmptyParam,0));
    
    aWorksheet:=ExcelWorkbook1.WorkSheets.Add(EmptyParam,EmptyParam,EmptyParam,EmptyParam,0) as _WorkSheet;
    
    ExcelWorkSheet1.ConnectTo(aWorksheet);
    
    aRowIndex:=1;
    
    while not ADOTabXLS.Eof do
    
    begin
    
    for tmpI:=0 to ADOTabXLS.FieldCount-1 do
    
    ExcelWorksheet1.Cells.Item[aRowIndex,tmpI+1]:=ADOTabXLS.FieldList[tmpI].AsString;
    
    aRowIndex:=aRowIndex+1;
    
    ADOTabXLS.Next;
    
    end;
    
    //保存EXCEL文件,并关闭EXCEL应用程序
    
    Try
    
    aStr:=ExtractFileDir(Application.ExeName)+'/EXCEL文件.xls';
    
    ExcelWorkbook1.SaveAs(aStr,EmptyParam,EmptyParam, EmptyParam,EmptyParam,EmptyParam ,
    
    xlNoChange ,EmptyParam,EmptyParam,EmptyParam,EmptyParam,EmptyParam,0);
    
    ExcelWorksheet1.Disconnect;
    
    ExcelWorkbook1.Disconnect;
    
    ExcelApplication1.Disconnect;
    
    ADOTabXLS.Active:=false;
    
    ADOConnXLS.Connected:=false;
    
    except
    
    ExcelWorksheet1.Disconnect;
    
    ExcelWorkbook1.Disconnect;
    
    ExcelApplication1.Disconnect;
    
    ADOTabXLS.Active:=false;
    
    ADOConnXLS.Connected:=false;
    
    End;
    
    end;
    
    六、总结
    
    综上所讲,本文分别举例讨论了EXCEL文件访问的几种方法,包括ADO、COM、扩展OLEContainer和DELPHI标准组件方式。在实际应用过程中,这几种方法也各有特色。ADO方式访问EXCEL文件适用于以数据库访问方式维护EXCEL文件,COM方式动态访问编程设计与VBA访问接口方式相似,此种方法适用于EXCEL文件数据维护和复杂报表输出,扩展OLE方式访问EXCEL文件时能够保持EXCEL应用程序的友好界面,DELPHI标准组件访问方式与COM访问方式相似,但DELPHI对各类接口进行了更加友好的封装,在对COM方式不是很长熟悉的情况下,使用这种方式访问和输出数据到EXCEL文件非常有效。
    
     
  • 相关阅读:
    Linux 学习
    mac 驱动
    用wubi安装ubuntu
    Eclipse安装Svn
    XML学习
    java集合类总结
    CVS学习
    [转载]java集合类总结
    Servlet学习
    JSP介绍
  • 原文地址:https://www.cnblogs.com/chenmfly/p/4651608.html
Copyright © 2020-2023  润新知