谢谢cqwty的热心帮助!
今天试着写一个简单的多线程程序。即将上面的视频变成简单的画线,来测试一下运行效果如何。
程序包括一个主界面单元和一个画线的线程。主界面有两个panel和两个paintbox,两个按钮和一个memo。主界面代码如下:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, ExtCtrls, WriteLineThread;
type
TForm1 = class(TForm)
Panel1: TPanel;
Panel2: TPanel;
Memo1: TMemo;
Button1: TButton;
Button2: TButton;
PaintBox1: TPaintBox;
PaintBox2: TPaintBox;
procedure Button1Click(Sender: TObject);
procedure FormShow(Sender: TObject);
procedure Button2Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
var
NowPanel: integer;
//记录现在的线程数,以判断线应该画在哪个paintbox上
TempThread: TThread;
{$R *.dfm}
procedure TForm1.FormShow(Sender: TObject);
begin
NowPanel := 0;
//初始线程数为0
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
if NowPanel = 2 then
exit;
//只能创建两个线程
NowPanel := NowPanel + 1;
TempThread := WriteLine.Create(NowPanel);
//创建画线线程
memo1.Lines.Add(inttostr(TempThread.ThreadID));
end;
procedure TForm1.Button2Click(Sender: TObject);
begin
TempThread.Terminate;
end;
end.
线程代码如下:
unit WriteLineThread;
interface
uses
Classes, SysUtils;
type
WriteLine = class(TThread)
private
{ Private declarations }
procedure WritePanelLine();
//画线主函数
procedure writeline();
//对vcl的操作,即在paintbox上画线
protected
procedure Execute;
override;
public
constructor Create(var NowPanel: integer);
end;
implementation
uses unit1;
var
NowPanelNumber: integer;
//记录当前线程号,即应该在哪个paintbox上画线
X,Y,H: integer;
//坐标和线长度
{ WriteLineThread }
procedure WriteLine.Execute;
begin
{ Place thread code here }
WritePanelLine;
end;
constructor WriteLine.Create(var NowPanel: integer);
begin
NowPanelNumber := NowPanel;
X := 10;
Y := 10;
H := 10;
FreeOnTerminate := true;
inherited Create(false);
end;
procedure WriteLine.WritePanelLine();
begin
while not Terminateddo
begin
synchronize(writeline);
X := X + 5;
H := H + 5;
sleep(2000);
end
end;
procedure WriteLine.writeline();
begin
if NowPanelNumber = 1 then
begin
//在paintbox1上画线
Form1.PaintBox1.Canvas.MoveTo(X,Y);
Form1.PaintBox1.Canvas.LineTo(X,Y+H);
end
else
begin
//在paintbox2上画线
Form1.PaintBox2.Canvas.MoveTo(X,Y);
Form1.PaintBox2.Canvas.LineTo(X,Y+H);
end;
end;
end.
运行程序,只有一个线程时正常。如果有两个画线线程,则paintbox1并不被绘制,paintbox2被绘制,而且速度较快(本来应该sleep(2000)),这时按下主界面上的button2,即终止掉后一个线程,发现paintbox2仍然被绘制,但速度变慢。感觉就是当有两个线程时,两个线程都在绘制paintbox2。问题可能出在NowPanelNumber的值上,但我想这是两个被分别创建的线程,线程内变量的值应该是相互独立的吧,怎么会互相影响??