Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Laienproblem mit Lazarus, Dateiiste zum "qualifizierten" kopieren.

1 view
Skip to first unread message

Franz Glaser

unread,
Dec 14, 2021, 11:39:23 AM12/14/21
to
Ich hoffe, dass ich hier bei den Profis niemand verärgere.

Bis jetzt kann ich mit meinem neugeschriebenen Programm einen gewählten
Unterverzeichnisbaum in eine ListBox einlesen.

Dann kann ich filenamen mit einem Mausklick auf eine Zeile die
filenamen des gewählten Unterverzeichnisses in die zweite Listbox
einlesen.

Was ich brauche sind die "Attribute" der files in der Listbox2,
besonders die Kalenderdaten, damit ich die files eventuell auf
einen anderen PC übers Netz oder auf einen USB-stick übertragen
kann.

Daran scheitere ich hoffnunfslos. Es gibt zwar mehrere Funktionen
und Prozeduren dafür aber keine davon bekomme ich unter Win10
und unter Vista (das sind die 2 PCs) zum Laufen. Die Funktionen
lierfern entweder -1 oder der Compiler verirrt sich mit den
uses und includes. Auch der "Trick mit uses DOS" scheitert an
meiner Unfähigkeit.

Natürlich möchte ich die kopierten files auf das gleiche Datum
usw. setzen wie das der Quelle aber unbedingt notwendig ist das
nicht.

Vorwiegend handelt es sich um eQSL-files, die ich mit 2 Computern
mit den Jahren gespeichert habe und die sich jetzt überlappen
sollen- Die Geschäftsfiles sind nicht mehr relevant. Aber der
alte Vista fängt an mit Spirenzchen.

Bitte um Hilfe. Franz Glaser.

Alfred Gemsa

unread,
Dec 14, 2021, 12:31:26 PM12/14/21
to
Zum Auslesen der Zeiten: Das lief bei mir unter Windows mit Delphi 7:



uses FileCtrl, DateUtils; // auf Verdacht

var CreationTime, LastWriteTime, LastAccessTime: string;

function TForm1.FT2DT(FileTime: TFileTime): TDateTime;
var
LocalFileTime: TFileTime;
SystemTime: TSystemTime;
begin
FileTimeToLocalFileTime(FileTime, LocalFileTime) ;
FileTimeToSystemTime(LocalFileTime, SystemTime) ;
Result := SystemTimeToDateTime(SystemTime) ;
end;

//+++ Hier geht's los: wähle File in FileListbox (FLB) +++

procedure TForm1.FLBClick(Sender: TObject);
var
FA: WIN32_FILE_ATTRIBUTE_DATA;
begin
if GetFileAttributesEx(pChar(FLB.FileName),GetFileExInfoStandard,@FA)
then begin
CreationTime := DateTimeToStr(FT2DT(FA.ftCreationTime));
LastWriteTime := DateTimeToStr(FT2DT(FA.ftLastWriteTime));
LastAccessTime := DateTimeToStr(FT2DT(FA.ftLastAccessTime));
Caption := 'CT: '+CreationTime+' LWT: '+LastWriteTime+' LAT:
'+LastAccessTime;;
end;
// else: error
end;


HTH
Alfred

Alfred Gemsa

unread,
Dec 14, 2021, 12:33:19 PM12/14/21
to
Am 14.12.2021 um 18:31 schrieb Alfred Gemsa:
> procedure TForm1.FLBClick(Sender: TObject);
> var
>   FA: WIN32_FILE_ATTRIBUTE_DATA;
> begin
>   if GetFileAttributesEx(pChar(FLB.FileName),GetFileExInfoStandard,@FA)
> then begin
>     CreationTime := DateTimeToStr(FT2DT(FA.ftCreationTime));
>     LastWriteTime := DateTimeToStr(FT2DT(FA.ftLastWriteTime));
>     LastAccessTime := DateTimeToStr(FT2DT(FA.ftLastAccessTime));
>     Caption := 'CT: '+CreationTime+'  LWT: '+LastWriteTime+'  LAT:
> '+LastAccessTime;;
>   end;
> // else: error
> end;

Ob alle Win32-Functions unter Lazarus existieren, weiß ich nicht.

Heiko Rost

unread,
Dec 14, 2021, 1:39:54 PM12/14/21
to
Franz Glaser schrieb:

> Bis jetzt kann ich mit meinem neugeschriebenen Programm einen gewählten
> Unterverzeichnisbaum in eine ListBox einlesen.
>
> Dann kann ich filenamen mit einem Mausklick auf eine Zeile die
> filenamen des gewählten Unterverzeichnisses in die zweite Listbox
> einlesen.
>
> Was ich brauche sind die "Attribute" der files in der Listbox2,
> besonders die Kalenderdaten, damit ich die files eventuell auf
> einen anderen PC übers Netz oder auf einen USB-stick übertragen
> kann.
>
> Daran scheitere ich hoffnunfslos. Es gibt zwar mehrere Funktionen
> und Prozeduren dafür aber keine davon bekomme ich unter Win10
> und unter Vista (das sind die 2 PCs) zum Laufen. Die Funktionen
> lierfern entweder -1 oder der Compiler verirrt sich mit den
> uses und includes. Auch der "Trick mit uses DOS" scheitert an
> meiner Unfähigkeit.

Dafür sollte SysUtil ausreichen.

Wenn Du die Dateien mir FindFirst/FindNext einliest, bekommst Du das
Änderungsdatum im Feld time des entsprechenden TSearchRec. Wenn Du nur
den Dateinamen hast, kannst Du die Funktion FileAge benutzen. Folgendes
funktioniert unter Windows 10 in einem Konsolenprogramm, Vista zum
Testen habe ich nicht:

program konsole4;

uses
SysUtils;

const pfad = 'd:\temp_d\';

var
Info: TSearchRec;
Count: longint;
NameLang : String;

begin
Count := 0;
if FindFirst(pfad+'*', faAnyFile, Info) = 0 then
begin
repeat
Inc(Count);
with Info do
begin
namelang := pfad+name;
if (Attr and faDirectory) = faDirectory then
begin
Write('VERZ : ');
write(DateTimeToStr(FileDateToDateTime(time)),' ');
write('------------------- ');
end
else
begin
Write('DATEI: ');
write(DateTimeToStr(FileDateToDateTime(time)),' ');
write(DateTimeToStr(FileDateToDateTime(FileAge(namelang))),' ');
end;
writeln(name);
end;
until FindNext(info) <> 0;
FindClose(Info);
end;
Write('Ende, weiter mit RETURN...');
readln;
end.


> Natürlich möchte ich die kopierten files auf das gleiche Datum
> usw. setzen wie das der Quelle aber unbedingt notwendig ist das
> nicht.

Das kann schwierig sein. Es gibt zwei Möglichkeiten, zumindest das
Änderungsdatum einzustellen

SysUtils - FileSetDate
LazFileUtils - FileSetDateUTF8

Die Funktionen stellen aber höchstwahrscheinlich nur die Zeit der
letzten Änderung ein. Das unter Windows üblicherweise benutzte
Dateisystem NTFS hat zusätzlich noch Zeiten für Dateierzeugung und
letzten Zugriff, wenn Du diese ändern willst, mußt Du wahrscheinlich die
Windows-API direkt aufrufen.

> Vorwiegend handelt es sich um eQSL-files, die ich mit 2 Computern
> mit den Jahren gespeichert habe und die sich jetzt überlappen
> sollen- Die Geschäftsfiles sind nicht mehr relevant. Aber der
> alte Vista fängt an mit Spirenzchen.

Nur als Anregung, weil ich mich damit nicht auskenne: Kannst Du bei dem
Format sicher sein, daß auf beiden Computern nicht zwei Dateien mit
selbem Namen, aber unterschiedlichem Inhalt existieren? Wenn nicht,
reicht ein einfacher Vergleich auf Dateiebene nicht aus, sondern Du mußt
in Deinem Programm den Inhalt der Dateien irgendwie miteinander
vergleichen.

Gruß Heiko
--
Jeder Zwang ist Gift für die Seele.
Ludwig Börne

Sieghard Schicktanz

unread,
Dec 14, 2021, 2:13:05 PM12/14/21
to
Hallo Franz Glaser,

Du schriebst am Tue, 14 Dec 2021 17:39:21 +0100:

> Bis jetzt kann ich mit meinem neugeschriebenen Programm einen
> gewählten Unterverzeichnisbaum in eine ListBox einlesen.
...
> Bitte um Hilfe. Franz Glaser.

Muß das mit einem selbergeschriebenen Programm gemacht werden?
Sonst würde ich das einfach mit 'nem x-beliebigen File-Manager machen,
Total Commander oder DoubleCommander z.B. Wenn's partout nix anderes
geben sollte, sogar mit dem (Windows) Explorer...

--
(Weitergabe von Adressdaten, Telefonnummern u.ä. ohne Zustimmung
nicht gestattet, ebenso Zusendung von Werbung oder ähnlichem)
-----------------------------------------------------------
Mit freundlichen Grüßen, S. Schicktanz
-----------------------------------------------------------

Franz Glaser

unread,
Dec 15, 2021, 6:17:41 AM12/15/21
to
Am 14/12/2021 um 18:31 schrieb Alfred Gemsa:
> Am 14.12.2021 um 17:39 schrieb Franz Glaser:
>> Ich hoffe, dass ich hier bei den Profis niemand verärgere.
>>
>> Bis jetzt kann ich mit meinem neugeschriebenen Programm einen gewählten
>> Unterverzeichnisbaum in eine ListBox einlesen.
>>
>> Dann kann ich filenamen mit einem Mausklick auf eine Zeile die
>> filenamen des gewählten Unterverzeichnisses in die zweite Listbox
>> einlesen.
>> [...]
Schnelles Danke erst an die bisherigen Antworter, ich werde das
ausprobieren.

GL

Franz Glaser

unread,
Dec 15, 2021, 8:47:48 AM12/15/21
to
Am 14/12/2021 um 19:43 schrieb Sieghard Schicktanz:

>> Bitte um Hilfe. Franz Glaser.

> Muß das mit einem selbergeschriebenen Programm gemacht werden?
> Sonst würde ich das einfach mit 'nem x-beliebigen File-Manager machen,
> Total Commander oder DoubleCommander z.B. Wenn's partout nix anderes
> geben sollte, sogar mit dem (Windows) Explorer...


Am Ende geht es darum, dass "schlafende" eQSL-Karten von der
eQSL-Datenbank gelesen werden und in die QRZ.COM logbook-
Datenbank per ADIF als gelesen eingetragen werden sollen.
Auch in einen Logbook Ausdruck.

Ich bremse meine QSOs schon gewaltig ein, weil mir die
folgende Bürokratie über den Kopf wächst. Je mehr ich da
automatisieren kann, desto lustiger werden die QSOs wieder.

Danke.

Franz Glaser

unread,
Dec 18, 2021, 11:33:25 AM12/18/21
to
Jetzt hänge ich seit Stunden an einem viel trivialeren Problem fest.

Ich habe 2 FileListen auf 2 ListBox-en nebeneinander, die ich
miteinander vergleiche. Das Vergleichen funktioniert.

Aber ich muss ja in die Zeilen ein Symbol ( '=' ) an einer Stelle
eintragen. Das macht mich krank. Ich habe es bis jetzt so weit
gebracht, dass ich die Zeile aus den Item[I] auf einen Sxxx - String
einlese, das '=' statt eines ' ' mit Copy()+'='+Copy(...P+2...)
in einen anderen String schreibe. Der neue String mit dem '=' ist ok!

Aber ich finde keine Methode, den neuen String in die Items-Liste
an der alten Stelle hinein zu übertragen. Der ist gleich lang und hat
keine UTF.

Meine bisherigen Programme haben immer nur eine zusätzliche Zeile
mit Add() oder mit Insert(..,..) zugefügt aber nie eine Zeile
überschreiben oder löschen und an der gleichen Stelle
inserten müssen. Replace tut nichts und Remove stürzt ab.

Die Alternative wäre, 2 neue, leere ListBoxen zu beschreiben und dann
mit Clear in die alte zu übertragen. Das ist aber auf dem Bild-
schirm ist Schrittbetrieb sehr lästig. Außerdem ist die Sortiererei
schwierig zu behalten.

Zugeben muss ich, dass ich damit überhaupt nicht gerechnet habe.

Memo kann das mit einem Delete und Insert aber Listbox kanns nicht.

Aber Memo hat den Sortierer (in meinam Fall nach
IntToString(Double(date))) nicht.


GL

Alfred Gemsa

unread,
Dec 18, 2021, 12:29:24 PM12/18/21
to
Am 18.12.2021 um 17:33 schrieb Franz Glaser:

> Aber ich finde keine Methode, den neuen String in die Items-Liste
> an der alten Stelle hinein zu übertragen. Der ist gleich lang und hat
> keine UTF.

Länge ist egal.

> Meine bisherigen Programme haben immer nur eine zusätzliche Zeile
> mit Add() oder mit Insert(..,..) zugefügt aber nie eine Zeile
> überschreiben oder löschen und an der gleichen Stelle
> inserten müssen. Replace tut nichts und Remove stürzt ab.

z.B.
for i:=1 to 10 do
Listbox1.Items.Add(inttostr(i)); // Erzeuge 10 Einträge mit Nummer

Listbox.Items[4] := 'Hier ist die 5. Zeile'; // Überschreibe Zeile 5

oder:

Sxxx := Listbox1.Items[4];
('=' eintragen in Sxxx)
Listbox.Items[4] := Sxxx;

HTH
Alfred

Heiko Rost

unread,
Dec 18, 2021, 12:38:46 PM12/18/21
to
Franz Glaser schrieb:

> Aber ich muss ja in die Zeilen ein Symbol ( '=' ) an einer Stelle
> eintragen. Das macht mich krank. Ich habe es bis jetzt so weit
> gebracht, dass ich die Zeile aus den Item[I] auf einen Sxxx - String
> einlese, das '=' statt eines ' ' mit Copy()+'='+Copy(...P+2...)
> in einen anderen String schreibe. Der neue String mit dem '=' ist ok!
>
> Aber ich finde keine Methode, den neuen String in die Items-Liste
> an der alten Stelle hinein zu übertragen. Der ist gleich lang und hat
> keine UTF.
>
> Meine bisherigen Programme haben immer nur eine zusätzliche Zeile
> mit Add() oder mit Insert(..,..) zugefügt aber nie eine Zeile
> überschreiben oder löschen und an der gleichen Stelle
> inserten müssen. Replace tut nichts und Remove stürzt ab.

Falls ich Dich nicht vollkommen falsch verstehe, einfach dem
entsprechenden Element von Items den neuen Text zuweisen:

Liste.Items.Add('Zeile1');
Liste.Items.Add('Zeile2');
Liste.Items.Add('Zeile3');
Liste.Items[0]:='Und jetzt etwas ganz anderes';

Hier werden erst drei Einträge an die Liste angefügt und dann im ersten
(der Index beginnt mit 0) Eintrag der Text geändert.

Gruß Heiko
--
Der Mensch ist gut, nur die Nerven sind schlecht.
Mose Ya'aqob Ben-Gavriêl

Sieghard Schicktanz

unread,
Dec 18, 2021, 2:13:06 PM12/18/21
to
Hallo Franz Glaser,

Du schriebst am Sat, 18 Dec 2021 17:33:24 +0100:

> Jetzt hänge ich seit Stunden an einem viel trivialeren Problem fest.
>
> Ich habe 2 FileListen auf 2 ListBox-en nebeneinander, die ich
> miteinander vergleiche. Das Vergleichen funktioniert.
>
> Aber ich muss ja in die Zeilen ein Symbol ( '=' ) an einer Stelle

Mußt Du? Dumm, sowas, wenn's keine andere Lösung gibt. N 3. Kasten, mit
nur den "=" o.w.a.i. drin, z.B.

> in einen anderen String schreibe. Der neue String mit dem '=' ist ok!
>
> Aber ich finde keine Methode, den neuen String in die Items-Liste
> an der alten Stelle hinein zu übertragen. Der ist gleich lang und hat
> keine UTF.

Nichtmal Zuweisen an den aktuellen Eintrag (das "Item") geht?
Damit hätte ich das als erstes versucht, die Einträge sind ja
schließlich (AFAIR & AFAIK) als "ARRAY OF String" organisiert bzw.
wenigstens so ansprechbar.

Franz Glaser

unread,
Dec 18, 2021, 2:25:06 PM12/18/21
to
Fehlerursache gefunden!

> Liste.Items[0]:='Und jetzt etwas ganz anderes';

Das ist nicht zulässig, wenn die "[x] Sorted" eingeschaltet ist.
Diesen Schalter habe ich nämlich beim Bulk-Einlesen der files als
ganz praktisch gefunden womit ich "einfach nur "Add" verwenden
musste statt selber mühsam zu sortieren.

Das Datum (SearchRec.date) habe ich als
fix 12-stellige Dezimalzahl vor den langen String vorangesetzt und
mit einem ' @' beendet. Mit diesen Ziffern sortiert er perfekt.
Das aufgelöste Datum+Uhrzeit ist gleich danach in dem String und
dann die size, alles mit fester Länge, und dann '| 'filename.ext

Aber mit den [x]Sorted ist das := für die TStrings verboten.


Alles kostet was :-)


Danke, GL
0 new messages