I am using Word Automation from a Delphi application and it is very slow. I stripped my code to a minimum, and hoped that someone with some experience would tell me where I was wrong (and I really hope that I didn’t do it so that I could speed it up)
The essence of automation in my application is related to bookmarks. The application opens a document with some special bookmarks, goes through them and changes them based on their names. The real version is also strongly associated with document variables and field codes. A typical document contains 50-80 bookmarks, some of which are attached. I also use some temporary documents to create blocks of text and images that are sequentially placed in the created document. The attached code is a VERY stripped-down version without this function, but it displays unwanted behavior (i.e. time to create a document). In the attached sample, it takes about 2.5 seconds to create a document. A typical real document takes about 30-40 seconds, sometimes more.
I hope someone says, “You are doing this all wrong. When you do Word Automation from Delphi, you should always remember XXX!”
Since the complete project, even if it is completely exhausted, is quite large, I made this small application. If there is a clear mistake in the way I do this, it will hopefully be apparent from this code.
Create a new VCL Forms application. Open Word and create a new document. Enter the text in the first line, mark it and insert a bookmark. Enter the text in the second line and mark it too. Save the file as 'c: \ temp \ bm.doc' as a Word 97-2003 document. After starting the application, you should have a new document (c: \ temp \ bm_generated.doc) with a random number in the first line and without bookmarks.
unit Unit1;
interface
uses
Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics,
Vcl.Controls, Vcl.Forms, Vcl.Dialogs, OleServer, WordXP, Vcl.StdCtrls;
type
TForm1 = class(TForm)
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
procedure TForm1.Button1Click(Sender: TObject);
var
vWordApp : TWordApplication;
vDoc : WordDocument;
vFileName : OleVariant;
vIndex : OleVariant;
vBookmark : Bookmark;
vSave : OleVariant;
begin
vWordApp := TWordApplication.Create(nil);
try
vWordApp.ConnectKind := ckNewInstance;
vWordApp.Connect;
vFileName := 'c:\temp\bm.doc';
vDoc := vWordApp.Documents.Open(vFileName, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam);
//Replace bookmark text with random string:
vIndex := 1;
vBookmark := vDoc.Bookmarks.Item(vIndex);
vBookmark.Range.Text := inttostr(random(10000)); //Will also delete the bookmark!
//Delete bookmark content and bookmark
vIndex := 1; //This will be the bookmark that was originally the first, since that was deleted when we sat the text
vBookmark := vDoc.Bookmarks.Item(vIndex);
vWordApp.Selection.SetRange(vBookmark.Range.Start, vBookmark.Range.End_);
vWordApp.Selection.Text := '';
vFileName := 'c:\temp\bm_generated.doc';
vDoc.SaveAs2000(vFileName, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam);
vWordApp.NormalTemplate.Saved := true; //For å slippe spørsmål om "normal.dot" skal lagres
vSave := wdDoNotSaveChanges;
vWordApp.Quit(vSave);
vWordApp.Disconnect;
finally
vWordApp.Free;
end;
end;
end.