匿名线程不允许应用程序关闭
Anonymous Thread not letting application close
我有一个应用程序,用户可以通过交互方式或从命令行运行。在第二种模式下,程序必须在完成后退出。
这是基本的最小代码。似乎 application.terminated 从未设置过;
如何关闭此程序,w/o0 用户交互。
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.
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.
我有一个应用程序,用户可以通过交互方式或从命令行运行。在第二种模式下,程序必须在完成后退出。
这是基本的最小代码。似乎 application.terminated 从未设置过;
如何关闭此程序,w/o0 用户交互。
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.
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.