2017-02-20 62 views
0

我有一個應用程序,用戶可以以交互方式或從命令行運行。在第二種模式下,程序必須在完成時退出。匿名線程不讓應用程序關閉

這裏是基本的最小代碼。看來,application.terminated從未設置;

如何讓此程序關閉,無用戶交互。

unit Unit4; 

interface 

uses 
    Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics, 
    Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls ; 

type 
    TForm4 = class(TForm) 
    Button1: TButton; 
    procedure Button1Click(Sender: TObject); 
    private 
    procedure DoSomeStuff; 
    { Private declarations } 
    public 
    { Public declarations } 
    end; 

var 
    Form4: TForm4; 

implementation 

{$R *.dfm} 

procedure TForm4.Button1Click(Sender: TObject); 
var 
    anonThread : TThread; 
begin 
    anonThread := TThread.CreateAnonymousThread(procedure 
    begin 
    while not application.terminated do 
    begin 
     doSomeStuff; 
    end; 
    end); 
    anonThread.Start; 

end; 

procedure TForm4.DoSomeStuff; 
var 
    i : integer; 
begin 
    for i := 0 to 10 do 
    begin 
     beep; 
     sleep(100); 
    end; 
    application.Terminate; 
end; 


end. 

回答

1

Application.Terminated屬性不Application.Run()(或至少一個手動循環調用Application.ProcessMessages())在主UI線程沒有消息循環工作。這是因爲Application.Terminate()只是將WM_QUIT消息發送到調用線程的消息隊列。 Application.Terminated在處理該消息之前未設置。控制檯應用程序通常不會調用Application.Run(),因此Application.Terminated無法在控制檯應用程序上運行。

你應該重新設計你的代碼,以消除Application並在控制檯模式下你TForm,如依賴:

program MyApp; 

uses 
    MyWorkUnit, Unit4; 

begin 
    if IsRunInCommandLineMode then 
    begin 
    DoSomeStuff; 
    end else 
    begin 
    Application.Initialize; 
    Application.CreateForm(TForm4, Form4) 
    Application.Run; 
    end; 

end. 

unit MyWorkUnit; 

interface 

procedure DoSomeStuff; 

implementation 

procedure DoSomeStuff; 
var 
    i : Integer; 
begin 
    for i := 0 to 10 do 
    begin 
    Beep; 
    Sleep(100); 
    end; 
end; 

end. 

unit Unit4; 

interface 

uses 
    Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics, 
    Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls; 

type 
    TForm4 = class(TForm) 
    Button1: TButton; 
    procedure Button1Click(Sender: TObject); 
    private 
    { Private declarations } 
    public 
    { Public declarations } 
    end; 

var 
    Form4: TForm4; 

implementation 

{$R *.dfm} 

uses 
    MyWorkUnit; 

procedure TForm4.Button1Click(Sender: TObject); 
begin 
    TThread.CreateAnonymousThread(
     procedure 
     begin 
     while not Application.Terminated do 
      DoSomeStuff; 
     end 
    ).Start;  
end; 

end.