| Autor |
Beitrag |
F.Art
      
Beiträge: 434
|
Verfasst: Mi 11.06.03 14:20
Ich habe mein Projekt mit einem anderen Programm gejoint und möchte das wenn das Projekt gestartet wird die fremde datei in den speicher kommt oder gejoint bleibt und von meinem projekt gesteuert wird.
|
|
Andreas Pfau
      
Beiträge: 997
|
Verfasst: Mi 11.06.03 16:52
Hört sich nach einigen Dingen gleichzeitig an. Also:
- Wie du die 2. File extreheirst, ist dein Problem, duhast auch den Algo zum joinen
- Die Datei kommt auf die Festplatte. Am besten in gleiche Verzeichnis wir die 1. Anwendung, vorsicht: Dateiname prüfen, du darfst nix überschreiben! Bei überschneidung: Index anhängen ("Date0001.exe")
- OK, dann startest du die Anwendung mit
Delphi-Quelltext 1: 2: 3:
| Uses WhellApi;
ShellExecute(0, Nil, PChar('Anwendung.exe'), Nil, Nil, Sw_ShowNormal); |
- Dann willst du die Anwendung steuern... wie darf ich das verstehen? Ist die 2. Anwendung von dir? Wenn ja, mit Messages, Events, MMF, DDE... es gibt viele Möglichkeiten!
_________________ Life is a bad adventure, but the graphic is really good!
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: Mi 11.06.03 23:37
Die Anwendung ist nicht von mir ist ein HTACCESS Generator für DOS.
Also es müss per DOS mit den PArametern gestertet werden und es entsteht eine txt datei die soll mein prog wieder einlesen und anzeigen.
|
|
Andreas Pfau
      
Beiträge: 997
|
Verfasst: Do 12.06.03 16:56
Hallo,
wenn du Parameter brauchst, füge sie doch einfach hinter dem Dateinamen in ShellExecute() ein. Wenn du den TXT-Output brauchst, öffne die Datei mit TTextfile oder so. Falls du auch noch Konsolen-Output brauchst, verwende folgende endlange Prozedur, die ich mal irgendwo gefunden und modifiziert habe:
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48: 49: 50: 51: 52: 53: 54: 55: 56: 57: 58: 59: 60: 61: 62: 63: 64: 65: 66: 67: 68: 69: 70: 71: 72: 73: 74: 75: 76: 77: 78: 79: 80: 81: 82: 83: 84: 85:
| function GetConsoleOutput(const Command: String; var Output, Errors: TStringList): Boolean; var StartupInfo: TStartupInfo; ProcessInfo: TProcessInformation; SecurityAttr: TSecurityAttributes; PipeOutputRead: THandle; PipeOutputWrite: THandle; PipeErrorsRead: THandle; PipeErrorsWrite: THandle; Succeed: Boolean; Buffer: array [0..255] of Char; NumberOfBytesRead: DWORD; Stream: TMemoryStream; begin FillChar(ProcessInfo, SizeOf(TProcessInformation), 0);
FillChar(SecurityAttr, SizeOf(TSecurityAttributes), 0); SecurityAttr.nLength := SizeOf(SecurityAttr); SecurityAttr.bInheritHandle := true; SecurityAttr.lpSecurityDescriptor := nil;
CreatePipe(PipeOutputRead, PipeOutputWrite, @SecurityAttr, 0); CreatePipe(PipeErrorsRead, PipeErrorsWrite, @SecurityAttr, 0);
FillChar(StartupInfo, SizeOf(TStartupInfo), 0); StartupInfo.cb:=SizeOf(StartupInfo); StartupInfo.hStdInput := 0; StartupInfo.hStdOutput := PipeOutputWrite; StartupInfo.hStdError := PipeErrorsWrite; StartupInfo.wShowWindow := sw_Hide; StartupInfo.dwFlags := STARTF_USESHOWWINDOW or STARTF_USESTDHANDLES;
if CreateProcess(nil, PChar(command), nil, nil, true, CREATE_DEFAULT_ERROR_MODE or CREATE_NEW_CONSOLE or NORMAL_PRIORITY_CLASS, nil, nil, StartupInfo, ProcessInfo) then begin result:=true; CloseHandle(PipeOutputWrite); CloseHandle(PipeErrorsWrite);
Stream := TMemoryStream.Create; try while true do begin succeed := ReadFile(PipeOutputRead, Buffer, 255, NumberOfBytesRead, nil); if not succeed then break; Stream.Write(Buffer, NumberOfBytesRead); end; Stream.Position := 0; Output.LoadFromStream(Stream); finally Stream.Free; end; CloseHandle(PipeOutputRead);
Stream := TMemoryStream.Create; try while true do begin succeed := ReadFile(PipeErrorsRead, Buffer, 255, NumberOfBytesRead, nil); if not succeed then break; Stream.Write(Buffer, NumberOfBytesRead); end; Stream.Position := 0; Errors.LoadFromStream(Stream); finally Stream.Free; end; CloseHandle(PipeErrorsRead);
WaitForSingleObject(ProcessInfo.hProcess, INFINITE); CloseHandle(ProcessInfo.hProcess); end else begin result:=false; CloseHandle(PipeOutputRead); CloseHandle(PipeOutputWrite); CloseHandle(PipeErrorsRead); CloseHandle(PipeErrorsWrite); end; end; |
Selbsterklärend.
Moderiert von tommie-lie: Code- durch Delphi-Tags ersetzt
_________________ Life is a bad adventure, but the graphic is really good!
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: Fr 13.06.03 11:55
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25:
| procedure Split(Main_FileName, NewFromMain_Filename : string); var MainFile : TFileStream; SplitFile : TFileStream; HelpStr : string[10]; GetSize : integer; begin MainFile := TFileStream.create(Main_FileName, fmOpenReadWrite or fmShareDenyWrite); try SplitFile := TFileStream.Create(NewFromMain_Filename, fmCreate or fmShareDenyNone); try MainFile.Position := MainFile.Size - 11; MainFile.Read(HelpStr, 10); GetSize := StrToInt(HelpStr); MainFile.Position := GetSize; SplitFile.CopyFrom(MainFile, MainFile.Size-GetSize); SplitFile.Size := SplitFile.Size - 11; MainFile.Size := GetSize; finally SplitFile.Free; end; finally MainFile.Free; end; end; |
Noch ne weitere Frage:
Dieser Code splittet beide Files voneinanderer wie mache ich das das er nur die angehängt irgendwohin speichert aber nicht raus nimmt?
Es wäre auch toll wenn mir einer diesen Coder im einzelnen erklären könnte. Er ist nicht von mir.
|
|
Andreas Pfau
      
Beiträge: 997
|
Verfasst: Fr 13.06.03 13:18
Hallo,
Lass' einfach die Zeile "MainFile.Size := GetSize;" weg. Die veranlasst nämlich, dass die MainFile gekürzt wird. Also: hier dann mal die Erklärung:
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33:
| procedure Split(Main_FileName, NewFromMain_Filename : string); var MainFile : TFileStream; SplitFile : TFileStream; HelpStr : string[10]; GetSize : integer; begin MainFile := TFileStream.create(Main_FileName, fmOpenReadWrite or fmShareDenyWrite); try SplitFile := TFileStream.Create(NewFromMain_Filename, fmCreate or fmShareDenyNone); try MainFile.Position := MainFile.Size - 11; MainFile.Read(HelpStr, 10); GetSize := StrToInt(HelpStr); MainFile.Position := GetSize; SplitFile.CopyFrom(MainFile, MainFile.Size-GetSize); SplitFile.Size := SplitFile.Size - 11; finally SplitFile.Free; end; finally MainFile.Free; end; end; |
Ich hoffe, wu deißt, was Streams sind? Wenn nein, stell' dir einfach vor, das sind Objekte, mit denen man Daten speichern kann. TFileStream ist von TStream abgeleitet, und beim FileStream kommen diese Daten aus Dateien.
Übrigens: Verbesserung weil (um ein paar ns) schneller:
Delphi-Quelltext 1: 2:
| SplitFile.CopyFrom(MainFile, MainFile.Size-GetSize); SplitFile.Size := SplitFile.Size - 11; |
Ersetzen durch:
Delphi-Quelltext 1:
| SplitFile.CopyFrom(MainFile, MainFile.Size-(GetSize+10)); |
Dann werden die 10 Byte der längenangabe gleich weggelassen.
Moderiert von tommie-lie: Code- durch Delphi-Tags ersetzt
Bitte demnächst Delphi-Tags verwenden, Danke!
_________________ Life is a bad adventure, but the graphic is really good!
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: Fr 13.06.03 23:46
OK ich werde alle Daten mal im Kopf verarbeiten und melde mich später zurück.
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25:
| procedure Join (Main_FileName, Hidden_Filename : string); var MainFile : TFileStream; HiddenFile : TFileStream; SizeOfFile : Cardinal; SearchWord : string[10]; begin MainFile := TFileStream.Create(Main_FileName, fmOpenReadWrite or fmShareDenyWrite); try SizeOfFile := MainFile.Size; HiddenFile := TFileStream.Create(Hidden_Filename, fmOpenRead or fmShareDenyNone); try MainFile.Seek(0, soFromEnd); MainFile.CopyFrom(HiddenFile, 0); MainFile.Seek(0, soFromEnd); finally HiddenFile.Free; end; SearchWord := IntToStr(SizeOfFile) + #0; MainFile.Seek(0, soFromEnd); MainFile.WriteBuffer(SearchWord, SizeOf(SearchWord)); finally MainFile.Free; end; end; |
Gibt es hierbei auch noch verbesserungs Vorschläge?
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: Sa 14.06.03 13:11
Delphi-Quelltext 1:
| ShellExecute(0, Nil, PChar('C:\MD5.exe -bcdpm test User Pw'), Nil, Nil, Sw_ShowNormal); |
Das funktioniert nicht ganz wenn ich C:\MD5.exe nur eintrage dann öffnet sich kurz ein fenster aber sonst nicht.
Ich will auch noch eine andere fremnde anwendung starten.
ist auch ein dos programm aber sobal es gestertet wird muss mann noch eingaben machen die man nicht per parameter machen kann.wie bekomme ich die steuerung hin?
ICh möchte noch zusätzlich das wenn das projekt gestertet wird die datei raus gejoint wird egal ob das projekt umbenannt wurde, wie bekomme ich dies noch hin?
|
|
Andreas Pfau
      
Beiträge: 997
|
Verfasst: Sa 14.06.03 17:41
Hallo,
du schreibst so tolle sätze... was willst du? Ich verstehe das so, dass du EXE2 aus EXE1 extrahieren willst, egal wie EXE1 heißt? Wenn das so ist, nimm "ParamStr(0)", das gibt den ersten Konsolenparameter zurück (also den Dateinnamen).
Dass sich das Fenster nur kurz öffnet, ist klar. Das kann man meines Wissens nur umgehen, wenn man die Dateioptionen ändernt ("Beim beenden sofot schließen"). Wie man das mit der API macht, weiß ich nicht. Oder schreib' eine Batch-File, und schreib hinter den Konsolenparameter zu Starten "@Pause", das geht auch.
Parameter zur Laufzeit übergeben? Null Problemo, nimm' diese enlange Prozedur oben, die fängt alle Befehle ab, und wenn ein Eingabe erwartet wird, kannst du sie übergeben. Müsste zumindest gehen, irgendwie.
_________________ Life is a bad adventure, but the graphic is really good!
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: Sa 14.06.03 23:20
Ich habe leider fast nichts verstanden. Ich bin Anfänger und verstehe die Begriffe nicht so.
Also wenn ich ein dos fenster öffne und C:\MD5.exe -bcdpm test User Pw
eingebe erstellt er mir das file was ich haben möchte aber wenn das per Delphi (siehe Oben) mache nicht. Dann habe ich noch eine andere dos datei die beim normalen dos aufruf wie die MD5.exe ist aber dann zusätzlich noch eingabe aufforderung haben will. ich möchte dazu wissen wie ich das 2. programm steuern kann.
|
|
Andreas Pfau
      
Beiträge: 997
|
Verfasst: Sa 14.06.03 23:45
Hallo,
ich glaube, du musst für DOS-Anwendungen den Interpreter erst aufrufen. Das ist:
- Unter 95/98/Me "Command.com"
- Unter NT/2k/XP "Cmd.exe"
Also etwa so:
"Cmd.exe C:\Pfad\Anwendung.exe -Parameter1 -Parameter2"
_________________ Life is a bad adventure, but the graphic is really good!
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: So 15.06.03 00:44
Das funktioniert auch nicht. Ich denke man müsste das dos fenster offen halten als ob man die verknüpfung des dos anklicken würde
|
|
Andreas Pfau
      
Beiträge: 997
|
Verfasst: So 15.06.03 11:26
Sorry...a bin da mit meinem Latein am Ende 
_________________ Life is a bad adventure, but the graphic is really good!
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: So 15.06.03 11:54
ICh möchte noch zusätzlich das wenn das projekt gestertet wird die datei raus gejoint wird egal ob das projekt umbenannt wurde, wie bekomme ich dies noch hin?
|
|
Andreas Pfau
      
Beiträge: 997
|
Verfasst: So 15.06.03 13:34
Den aktuellen Dateinamen (incl. Pfad) erfährst du mit "ParamStr(0)". Nur den Dateinamen kannst du mit "ExtractFileName()" extrahieren.
_________________ Life is a bad adventure, but the graphic is really good!
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: So 15.06.03 14:25
Wenn ich es so mache:
Delphi-Quelltext 1:
| Split(ParamStr(0), 'C:\Normal.exe'); |
kommt immer
Quelltext 1:
| Datei D:/....exe kann nicht geöffnet werden. Der Prozess kann nicht auf die Datei zugreifen, da sie von einem anderen Prozess verwendet wird. |
und
Delphi-Quelltext 1:
| CopyFile(ParamStr(0), 'C:\Generatoren.exe', TRUE); |
will es auch nicht.
|
|
Andreas Pfau
      
Beiträge: 997
|
Verfasst: So 15.06.03 18:24
Hallo,
müsste am FileSharing liegen. Ändere
Quelltext 1:
| MainFile := TFileStream.Create(Main_FileName, fmOpenReadWrite or fmShareDenyWrite); |
durch
Quelltext 1:
| MainFile := TFileStream.Create(Main_FileName, fmOpenRead or fmShareDenyNone); |
Dann müsstest du eigentlich Zugriff bekommen.
_________________ Life is a bad adventure, but the graphic is really good!
|
|
F.Art 
      
Beiträge: 434
|
Verfasst: So 15.06.03 18:44
THX so geht es.
Nun müsste das mit den DOS aufrufen richtig funktionieren.
Ich habe auch schon etwas mit Eine Exe-Datei in einer Applikation einbinden und sie ausführen experimentiert.
Die Exe wurde eingebunden aber das aufrufen ist noch fehlerhaft.
|
|
|