Rund um die LCL und andere Komponenten
Mathias
Beiträge: 7317 Registriert: Do 2. Jan 2014, 17:21
OS, Lazarus, FPC: Linux (die neusten Trunk)
CPU-Target: 64Bit
Wohnort: Schweiz
Beitrag
von Mathias » Do 11. Jun 2015, 18:07
Ich habe 2 Memos und eine ComboBox.
Wen ich save und anschliessend load klicke, habe ich im Memo1 den alten Inhalt von Memo1 und Memo2.
Memo2 und ComboBox bleibt leer.
Wieso ?
Code: Alles auswählen
type TfloatArray=array[0..9]of single;
procedure TForm1.saveClick(Sender: TObject);
var
stream:TFileStream;
fa:TfloatArray;
begin
stream:=TFileStream.Create('test.bin',fmCreate);
stream.Write(fa, SizeOf(fa));
Memo1.Lines.SaveToStream(stream);
Memo1.Clear;
Memo2.Lines.SaveToStream(stream);
Memo2.Clear;
ComboBox1.Items.SaveToStream(stream);
ComboBox1.Clear;
stream.Free;
end;
procedure TForm1.loadClick(Sender: TObject);
var
stream:TFileStream;
fa:TfloatArray;
begin
stream:=TFileStream.Create('test.bin',fmOpenRead);
stream.Read(fa, SizeOf(fa));
Memo1.Lines.LoadFromStream(stream);
Memo2.Lines.LoadFromStream(stream);
ComboBox1.Items.LoadFromStream(stream);
stream.Free;
end;
Mit Lazarus sehe ich grün
Mit Java und C/C++ sehe ich rot
Michl
Beiträge: 2513 Registriert: Di 19. Jun 2012, 12:54
Beitrag
von Michl » Do 11. Jun 2015, 22:18
MMn müsstest du einfach die Position entsprechend setzen. Ich habe das mal so probiert, mit einem leeren Projekt. Es wird alles wie erwartet geladen:
Code: Alles auswählen
procedure TForm1.loadClick(Sender: TObject);
var
stream:TFileStream;
fa:TfloatArray;
begin
stream:=TFileStream.Create('test.bin',fmOpenRead);
stream.Read(fa, SizeOf(fa));
Memo1.Lines.LoadFromStream(stream);
Stream.Position:=SizeOf(fa);
Memo2.Lines.LoadFromStream(stream);
Stream.Position:=SizeOf(fa);
ComboBox1.Items.LoadFromStream(stream);
stream.Free;
end;
Code: Alles auswählen
type
TLiveSelection = (lsMoney, lsChilds, lsTime);
TLive = Array[0..1] of TLiveSelection;
Warf
Beiträge: 2306 Registriert: Di 23. Sep 2014, 17:46
OS, Lazarus, FPC: Win10 | Linux
CPU-Target: x86_64
Beitrag
von Warf » Fr 12. Jun 2015, 12:22
Das problem ist LoadFromStream ließt bis EOF, un da du die Zeilen einfach hinter einander klatschst wird einfach die gesamte Datei in das erste Memo gelesen, und nichts bleibt mehr für die anderen Komponenten übrig. Um das zu umgehen musst du die Größe der Texte speichern Beispiel:
Code: Alles auswählen
procedure SaveLinesToStream(sl: TStrings; str: TStream);
var buff: Cardinal;
begin
if not Assigned(str) then
exit;
buff:=Length(sl.Text);
str.Write(buff, SizeOf(buff));
sl.SaveToStream(str);
end;
procedure LoadLinesFromStream(sl: TStrings; str: TStream);
var buff: Cardinal;
ms: TMemoryStream;
begin
if not Assigned(str) then
exit;
ms:=TMemoryStream.Create;
try
str.Read(buff, SizeOf(buff));
ms.CopyFrom(str, buff);
ms.Seek(0, soFromBeginning);
sl.LoadFromStream(ms);
finally
ms.Free;
end;
end;
Mathias
Beiträge: 7317 Registriert: Do 2. Jan 2014, 17:21
OS, Lazarus, FPC: Linux (die neusten Trunk)
CPU-Target: 64Bit
Wohnort: Schweiz
Beitrag
von Mathias » Fr 12. Jun 2015, 18:31
Irgendwie sehe ich da keinen Sinn dahinter.
Ist bei einem Stream nicht die Idee dahinter, das man mehrere Sachen auf einmal speichern kann ?
Bei der FPC-Quelle wird tatsächlich ohne Längen-Angabe gespeichert.
Code: Alles auswählen
Procedure TStrings.SaveToStream(Stream: TStream);
Var
S : String;
begin
S:=Text;
if S = '' then Exit;
Stream.WriteBuffer(Pointer(S)^,Length(S));
end;
Mit Lazarus sehe ich grün
Mit Java und C/C++ sehe ich rot
wp_xyz
Beiträge: 5456 Registriert: Fr 8. Apr 2011, 09:01
Beitrag
von wp_xyz » Fr 12. Jun 2015, 19:32
Die Hauptanwendung von TStrings.SavetoStream verwendet den Stream für sich allein, daher ist die Längeninformation unnötig.
Mathias
Beiträge: 7317 Registriert: Do 2. Jan 2014, 17:21
OS, Lazarus, FPC: Linux (die neusten Trunk)
CPU-Target: 64Bit
Wohnort: Schweiz
Beitrag
von Mathias » Fr 12. Jun 2015, 20:09
Du meinst es kommt von da her:
Code: Alles auswählen
Procedure TStrings.SaveToFile(const FileName: string);
Var TheStream : TFileStream;
begin
TheStream:=TFileStream.Create(FileName,fmCreate);
try
SaveToStream(TheStream);
finally
TheStream.Free;
end;
end;
Jetzt sehe ich den Sinn, bei speichern einer Text-Datei sind Längen-Angaben ein Müll.
Mit Lazarus sehe ich grün
Mit Java und C/C++ sehe ich rot