Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Unit in Thread packen?! (https://www.delphipraxis.net/59040-unit-thread-packen.html)

XeRo 16. Dez 2005 10:30


Unit in Thread packen?!
 
Liste der Anhänge anzeigen (Anzahl: 1)
Hi ich verwende die Unit von Florian Bernd(Anhang).
Sie Scannt das Netzwerk nach PC's.
Ich will die Unit in einen Thread packen damit das Programm auch beim Scannen noch reagiert. Nur habe ich keine Ahnung wie...kann mir das jemand sagen/machen?

petergensfeld 16. Dez 2005 10:41

Re: Unit in Thread packen?!
 
Hallo,

im wesentlichen solltest Du eine neue Klasse von TThread ableiten, in der Du die Execute-Methode überschreibst:

Delphi-Quellcode:
type
  TScanThread = class(TThread)
  public
    procedure Execute; override;
    // ...
  end;

// ...

procedure TScanThread.Execute;
begin
  // hierin zeitaufwändige Scan-Routine platzieren
end;
// Edit: Ansonsten schau mal in der Hilfe unter TThread nach!

Gruß Dirk

XeRo 16. Dez 2005 11:42

Re: Unit in Thread packen?!
 
:gruebel:
Also wenn ich die Unit "starte" mit:
Delphi-Quellcode:
procedure TForm1.BitBtn1Click(Sender: TObject);
begin
ActiveConnections.ScanNetworkResources(1,RESOURCEDISPLAYTYPE_GENERIC,listbox1.Items);
end;
dann muss ich
Code:
ActiveConnections.ScanNetworkResources(1,RESOURCEDISPLAYTYPE_GENERIC,listbox1.Items);
ins

Delphi-Quellcode:
procedure TScanThread.Execute;
begin
 ActiveConnections.ScanNetworkResources(1,RESOURCEDISPLAYTYPE_GENERIC,listbox1.Items);
end;
schreiben?

Und wie Ruf ich das dann auf?!
Leider Hilft mir die Hilfe nichts.... :wall:

mgubler 16. Dez 2005 11:47

Re: Unit in Thread packen?!
 
wie meinst du das :
Zitat:

Zitat von XeRo
:gruebel:
Also wenn ich die Unit "starte" mit:
Delphi-Quellcode:
procedure TForm1.BitBtn1Click(Sender: TObject);
begin
ActiveConnections.ScanNetworkResources(1,RESOURCEDISPLAYTYPE_GENERIC,listbox1.Items);
end;
dann muss ich
Code:
ActiveConnections.ScanNetworkResources(1,RESOURCEDISPLAYTYPE_GENERIC,listbox1.Items);
ins

Delphi-Quellcode:
procedure TScanThread.Execute;
begin
 ActiveConnections.ScanNetworkResources(1,RESOURCEDISPLAYTYPE_GENERIC,listbox1.Items);
end;
schreiben?

Und wie Ruf ich das dann auf?!
Leider Hilft mir die Hilfe nichts.... :wall:


du musst dann meines erachtens TScanThread.Execute aufrufen.
Und dann macht der das.
Wie wäre es denn damit???

XeRo 16. Dez 2005 11:51

Re: Unit in Thread packen?!
 
Genau das geht eben nicht...
auf die Idee wär ich eh selber gekommen.

Zacherl 16. Dez 2005 11:53

Re: Unit in Thread packen?!
 
Dann musst du eine Instanz von TScanThread erzeugen und Execute aufrufen:
Delphi-Quellcode:
var
  ScanThread: TScanThread;
begin
  ScanThread := TScanThread.Create(true);
  ScanThread.Execute;
  ScanThread.Free;
end;
Florian

NicoDE 16. Dez 2005 12:06

Re: Unit in Thread packen?!
 
Die Execute-Methode wird beim Create aufgerufen. Der Code könnte so aussehen:
Delphi-Quellcode:
var
  ScanThread: TScanThread;
begin
  ScanThread := TScanThread.Create(True);
  try
    ScanThread.FreeOnTerminate := False;
    ScanThread.Resume();
    ScanThread.WaitFor();
    // ...Daten aus dem Thread holen...
  finally
    ScanThread.Free();
  end;
end;

Zacherl 16. Dez 2005 12:08

Re: Unit in Thread packen?!
 
Der Parameter CreateSuspensed in der Create Methode legt fest, ob Execute direkt aufgerufen wird. Wenn der Parameter true ist, wird der Thread eingefroren, bis Execute aufgerufen wird.

XeRo 16. Dez 2005 12:10

Re: Unit in Thread packen?!
 
Liste der Anhänge anzeigen (Anzahl: 1)
Auch das habe ich versucht...
bewirkt aber leider nicht dass das Programm wärend dem Scanvorgang reagiert.
Hab mal das Programm in den Anhang gegeben...

Könnt ihr euch das mal ansehen?

Angel4585 16. Dez 2005 12:16

Re: Unit in Thread packen?!
 
kann rar hier nicht öffnen, aber wenn du in nem Thread eine Schleife wie:

Delphi-Quellcode:
while i > 0 do
 inc(i);
hast , dann solltest du ab und zu ein Sleep rein machen, da der Thread sonst du gesamten Ressourcen des Programms in anspruch nimmt un der rest des Programms nicht reagieren kann.

Das sieht dann so aus:

Delphi-Quellcode:
while i>0 do
 begin
 if (i div 100) = 0 then
  sleep(1);
 inc(i);
 end;
(ich mach das in dem Beispiel nur alle 100 i's , dürfte ausreichen)

das heisst für dich, das du in die Unit oder zwischen die Funktionsaufrufe noch ein paar sleeps einbauen musst.

MfG Angel4585

NicoDE 16. Dez 2005 12:53

Re: Unit in Thread packen?!
 
Delphi-Quellcode:
unit Unit1;

interface

uses
  Windows, SysUtils, Classes, Controls, Forms, StdCtrls;

type
  TScanThread = class(TThread)
  private
    FList: TStringList;
  public
    constructor Create(CreateSuspended: Boolean); virtual;
    destructor Destroy(); override;
    procedure Execute(); override;
    property List: TStringList read FList;
  end;

type
  TForm1 = class(TForm)
    ListBox1: TListBox;
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
    ScanTerminated: Boolean;
    procedure OnScanTerminated(Sender: TObject);
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

uses
  ActiveConnections;

{$R *.dfm}

{ TScanThread }

constructor TScanThread.Create(CreateSuspended: Boolean);
begin
  // inherited (angehalten)
  inherited Create(True);
  // private Variablen initialisieren
  FList := TStringList.Create();
  // fortsetzen falls gefordert
  if not CreateSuspended then
    Resume();
end;

destructor TScanThread.Destroy();
begin
  // private Variablen freigeben
  FList.Free();
  // inherited
  inherited Destroy();
end;

procedure TScanThread.Execute();
begin
  // was auch immer...
  ScanNetworkResources(RESOURCETYPE_DISK, RESOURCEDISPLAYTYPE_GENERIC, FList);
end;

{ TForm1 }

procedure TForm1.OnScanTerminated(Sender: TObject);
begin
  // scan beendet
  ScanTerminated := True;
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
  // Button deaktivieren (Schutz for Doppelklick)
  Button1.Enabled := False;
  try
    // ScanThread erzeugen (angehalten)
    with TScanThread.Create(True) do
    try
      // Beim Beenden nicht freigeben (wir brauchen Zugriff auch die Liste)
      FreeOnTerminate := False;
      // ScanTerminated initialisieren
      ScanTerminated := False;
      // Ereignisroutine setzen
      OnTerminate := OnScanTerminated;
      // nun den Thread arbeiten lassen
      Resume();
      // Warten bis der Thread fertig ist
      while not ScanTerminated do
        // Solange die GUI reagieren lassen...
        Application.ProcessMessages();
      // Ergebnisliste holen
      ListBox1.Items.Text := List.Text;
    finally
      // Thread freigeben
      Free();
    end;
  finally
    // Button reaktivieren
    Button1.Enabled := True;
  end;
end;

end.

XeRo 19. Dez 2005 06:53

Re: Unit in Thread packen?!
 
vielen dank...funktioniert super...auf das wär ich nie gekommen...


Alle Zeitangaben in WEZ +1. Es ist jetzt 12:10 Uhr.

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz