Autor Beitrag
Tossi65
Hält's aus hier
Beiträge: 9

Win 7, Win 8.1
D2010
BeitragVerfasst: Mo 01.02.16 22:59 
Guten Abend Kollegen,
ich habe ein leidiges Problem. Ich will Programme, welche vom Betriebssystem verknüpft sind, aufrufen. Eigentlich geht es ganz gut.
ausblenden 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:
26:
27:
28:
29:
  procedure ShellExecute_AndWait(ASequenz: PSequenz; Params: string);
    var
      exInfo: TShellExecuteInfo;
      Ph: DWORD;
    begin
      FillChar(exInfo, SizeOf(exInfo), 0);
      with exInfo do
      begin
        cbSize := SizeOf(exInfo);
        fMask := SEE_MASK_NOCLOSEPROCESS or SEE_MASK_FLAG_DDEWAIT;
        Wnd := GetActiveWindow();
        ExInfo.lpVerb := 'open';
        ExInfo.lpParameters := PChar(Params);
        lpFile := PChar(ASequenz.Pfad);
        nShow := SW_SHOWNORMAL;
      end;
      if ShellExecuteEx(@exInfo) then
        Ph := exInfo.HProcess
      else
      begin
        ShowMessage(SysErrorMessage(GetLastError));
        Exit;
      end;

        while WaitForSingleObject(ExInfo.hProcess, 50) <> WAIT_OBJECT_0 do
          Application.ProcessMessages;

      CloseHandle(Ph);
    end;


Mit dieser Funktion geht es auch ganz gut. Aber das wäre zu einfach. Ich möchte dem Programm auch eine Anzeigedauer mitgeben. SOll heißen nach 30 Sekunden soll das Progeamm schließen. Ich habe schon einiges probiert. Unter anderem auch mit:
ausblenden volle Höhe 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:
26:
27:
28:
29:
30:
31:
32:
      ZeroMemory(@myInfo, SizeOf(SHELLEXECUTEINFO));
      myInfo.cbSize := SizeOf(SHELLEXECUTEINFO);
      myInfo.fMask := SEE_MASK_NOCLOSEPROCESS or SEE_MASK_FLAG_NO_UI;
      myInfo.lpFile := PChar(FileName);
      myInfo.lpParameters := PChar(Parameters);
      if Hide then
        myInfo.nShow := SW_HIDE
      else
        myInfo.nShow := SW_SHOWNORMAL;
      // start file
      ExitCode := 0;
      Result := ShellExecuteEx(@myInfo);
      // if process could be started
      if Result then
      begin
        // wait on process ?
        iWaitRes:=0;
        if (Wait > 0then
        begin    //WaitForSingleObject
          iWaitRes := WaitForSingleObject(myInfo.hProcess, Wait);
          // timeout reached ?
          if (iWaitRes = WAIT_TIMEOUT) then
          begin
            Result := False;
            TerminateProcess(myInfo.hProcess, 0);
          end;
          // get the exitcode
          GetExitCodeProcess(myInfo.hProcess, ExitCode);
        end;
        // close handle, because SEE_MASK_NOCLOSEPROCESS was set
        CloseHandle(myInfo.hProcess);
      end;

Das funktioniert aber nicht mit der Windows Faxanzeige oder mit LibreOffice, IEXplorer. Dort ist (myInfo.hProcess = 0, weil durch DDE aufgerufen.

Hat jemand eine bessere Idee?

Hintergrund:
Ich möchte eine Zusammenstellung von Dokumenten und Bidern hintereinander laufen lassen, wobei die Bilder nach x Sekunden automatisch schießen und das nächste Dokument oder Bild
erscheint.(SlideShow)

Crosspost: forum.delphi-treff.d...ID=444852#post444852

Moderiert von user profile iconNarses: Quote- durch Delphi-Tags ersetzt
Moderiert von user profile iconNarses: Topic aus VCL (Visual Component Library) verschoben am Mo 01.02.2016 um 23:38
Moderiert von user profile iconChristian S.: Crosspost vermerkt

_________________
Mfg
Tossi
jasocul
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 6325
Erhaltene Danke: 128

Windows 7 + Windows 10
Tokyo Prof + CE
BeitragVerfasst: Di 02.02.16 10:10 
Mal abgesehen davon, dass das offensichtlich nicht trivial ist, halte ich die Vorgehensweise nicht für gut.
Bei mir sind Grafik-Dateien mit Photoshop verknüpft. Wenn man jetzt für die Bilder eine Slide-Show macht und dafür jedesmal Photoshop öffnet und dann wieder schließt, ist das nicht optimal. Dazu kommt, dass du nicht beurteilen kannst, wie lange der Start der verknüpften Anwendung dauert. Für die Slide-Show kann dann die Zeitscheibe zu klein sein.

Leider weiß ich nicht, wofür die Anwendung genutzt werden soll, aber ich würde komplett anders vorgehen. Für das Programm muss hinterlegt werden, welche Programme die entsprechenden Dateien öffnen sollen. Viele Programme kannst du als OLE-Objekte in dein eigenes Programm integrieren. Dadurch behältst du die Kontrolle.

Text-Dokumente kann heute jeder auch als PDF bereitstellen. Dafür gibt es Freeware-Komponenten. Für Grafiken bietet Delphi von Haus aus schon Möglichkeiten. Du bist im Prinzip nicht auf externe Programme angewiesen.

Ich habe schon vor ähnlichen Problemen gestanden und habe zum Beispiel Word-Dateien embedded dargestellt. Bei PDF-Dateien hängt es vom Einsatzgebiet ab. Da nutze ich beide Möglichkeiten. Für Grafiken hatte ich bisher keinen Bedarf. Aber ich habe ein sehr kontrollierbares Umfeld. Wäre das nicht der Fall, gäbe ich den Anwendern klare Vorgaben oder würde die Kontrolle komplett ins eigene Programm aufnehmen.

EDIT:
Da fällt mir gerade noch ein, dass es sogar falsch sein kann, die verknüpfte Anwendung zu schließen. Was passiert, wenn die Anwendung schon geöffnet war und dort Dokumente ich Bearbeitung sind? Dann musst du zusätzlich sicherstellen, dass für die Anwendung eine neue Instanz erzeugt wird. Das geht, aber dafür muss die Anwendung kennen, wenn ich mich richtig erinnere. Du stehst also wieder vor dem Problem, dass du dich nicht auf eine Verknüpfung verlassen kannst. BTW: Was machst du, wenn es keine verknüpfte Anwendung gibt?
Tossi65 Threadstarter
Hält's aus hier
Beiträge: 9

Win 7, Win 8.1
D2010
BeitragVerfasst: Di 02.02.16 10:54 
Vielen Dank jasocul,
du hast mir eine andere Sichtweise auf die Problematik gegeben. Ich werde mir darüber Gedanken machen.