I have a problem in an app I'm doing in Delphi 2.0: I can't create a new
file with a TFileStream object. What I'm trying to do is create a kind of
Tab-separated ANSI file. But when I choose a non-existing filename in
sdlExport (which is a TSaveDialog) I get an exception when I call
TFileStream.Create. And if I choose an already existing file, I get garbage
in the first half of the file, even the part where I write the
stringconstants. BTW tblCombination is a TTable object, where I get the
data, and the data is OK, I have checked it.
Here is the code:
var
CurStr : String;
WriteLength,
FieldCounter : Integer;
fstExport : TFileStream;
if sdlExport.Execute then
begin
fstExport := TFileStream.Create(sdlExport.FileName,fmOpenWrite);
try
CurStr := 'ContactID' + #9 + 'Contact' + #9 + 'Code' + #9 +
'Number' + #9 + 'Departement' + #9 + 'Address1' + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
CurStr := 'Address2' + #9 + 'Address3' + #9 + 'ZIPCode' + #9 +
'City' + #9 + 'Address' + #9 + 'Address2' + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
CurStr := 'Address3' + #9 + 'ZIPCODE' + #9 + 'City' + #9 +
'County_UK' + #9 + 'State_USA' + #9 + 'Country' + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
CurStr := 'Telephone' + #9 + 'Telephone2' + #9 + 'Telefax' + #9 +
'OurContact' + #9 + 'UserID' + #9 + 'Category' + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
CurStr := 'Branche' + #9 + 'TurnAround' + #9 + 'NumEmp' + #9 +
'Various' + #9 + 'Registered' + #9 + 'RegisteredBy' + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
CurStr := 'LastChange' + #9 + 'LastChange' + #9 + 'Stop' + #9 +
'ID' + #9 + 'Number' + #9 + 'MrMrs' + #9 + 'Title' + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
CurStr := 'FirstName' + #9 + 'LastName' + #9 + 'Direktetlf' + #9 +
'PrivatePhone' + #9 + 'DirectFax' + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
CurStr := 'MobilePhone' + #9 + 'Beeper' + #9 + 'EMail' + #9 +
'Address' + #9 + 'ZIPcode' + #9 + 'City' + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
CurStr := 'Born' + #9 + 'Commentary' + #9 + 'OurContact' + #9 +
'Various' + #9 + 'Empty' + #9 + 'End' + #9 + #13 + #10;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
with tblCombination do
begin
First;
while not(EOF) do
begin
for FieldCounter := 0 to FieldCount - 1 do
begin
CurStr := Fields[FieldCounter].AsString + #9;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
end;
CurStr := 'End' + #9 + #13 + #10;
WriteLength := fstExport.Write(CurStr,Length(CurStr));
if (WriteLength < Length(CurStr)) then
raise E_PREDA_ExportError.Create('Write problem');
Next;
end;
end;
except
on E : E_PREDA_ExportError do
MessageDlg('An error occured during write',mtError,[mbOK],0);
end;
fstExport.Free;
end;
--
CUL8R dude! \|/
@ @
Jens +-----------------------oOO-(_)-OOo-----------------------+
| Internet jb...@image.dk CompuServe 100437,2475 |
| FidoNet 2:235/142 VirNet 9:451/238 |
| OS2Net 81:445/49 Fax +45 - 3537 - 7006 |
+---------------------------------------------------------+
to create a brand new file (i.e., when you choose a non-existant filename
in sdlExport) you need the fmCreate file open mode; e.g.
fstExport := TFileStream.Create(sdlExport.FileName,fmCreate);
]- try
]- CurStr := 'ContactID' + #9 + 'Contact' + #9 + 'Code' + #9 +
]- 'Number' + #9 + 'Departement' + #9 + 'Address1' + #9;
]- WriteLength := fstExport.Write(CurStr,Length(CurStr));
I don't have D2, so I can't comment with any authority on this.
I can however show you some stuff that works -- and some stuff
that doesn't work -- in D1. Maybe that will help...
Program Duh;
uses SysUtils, Classes, Dialogs;
Var
F : TFileStream;
T : TextFile;
P : PChar;
R : array[0..255] of char;
S1, S2 : string;
BEGIN
S1 := 'This is a test!';
F := TFileStream.Create('erase-me.dat', fmCreate);
{= Writing Strings =}
{= this doesn't work (you get the string's length byte written as the
first character in the file, and you don't get the exclamation point) =
F.Write(S1, length(S1));
{====}
{= this DOES work =
F.Write(S1[1], length(S1));
{====}
{= Writing PChars =}
{= with extended syntax on this works =
StrPLCopy(R, S1, length(S1));
F.Write(R, length(S1));
{====}
{= this works too =}
GetMem(P, length(S1)+1);
StrPLCopy(P, S1, length(S1));
F.Write(P^, length(S1));
FreeMem(P, length(S1)+1);
{= but this...
F.Write(P, length(S1));
= fails miserably; the file is complete garbage =}
{====}
F.Free;
AssignFile(T, 'erase-me.dat');
reset(T);
read(T, S2);
CloseFile(T);
ShowMessage('Original : [' + S1 + ']' + #13 + 'Revised : [' + S2 + ']');
END.
HTH
Mark Vaughan
>I have a problem in an app I'm doing in Delphi 2.0: I can't create a new
>file with a TFileStream object. What I'm trying to do is create a kind of
>Tab-separated ANSI file. But when I choose a non-existing filename in
>sdlExport (which is a TSaveDialog) I get an exception when I call
>TFileStream.Create.
To create a file, use fmCreate as the mod. The fmOpenWrite mode opens
an existing file for writing.
> And if I choose an already existing file, I get garbage
>in the first half of the file, even the part where I write the
>stringconstants...
> WriteLength := fstExport.Write(CurStr,Length(CurStr));
The argument to write must be the data, not a reference to the data.
Delphi figures out the rest for you. A string in D2 is really a
pointer, so you must dereference the pointer to write the data, e.g.,
CurStr[1].
--
Ray Lischner, Tempest Software, Inc., Corvallis, Oregon, USA
Author of Secrets of Delphi 2 (http://www.tempest-sw.com/secrets/)
Just a guess off the top of my head... Have you tried this
fstExport := TFileStream.Create(sdlExport.FileName,fmOpenWrite or
fmCreate); I don't have Delphi handy, so not sure if fmCreate is the
correct constant, but think it is close.
FWIW
--
Steve Esser, JCPenney Telemarketing, ses...@jcpenney.com
{Of course this is only me talking, not JCPenney.}