I rewrote the multithreading example to do the trick.
This requires trunk compiler.
The procedure "test" can also be implemented as anonymous procedure. (However, codetools are not fully ready for this yet)
This approach should also work with current compiler, but then the procedure "test" must be global and cannot access local variables.
Breakpoints in the procedure "test" do not work with FPDebug, but work with GDB.
I am not experienced with freepascal, but I think this should work and solve the problem.
The procedure "test" is in the codeflow of the thread, but is executed asynchronously
and concurrent by the main GUI thread. Usually threads must do time critical or timeconsuming work and only want to wait, if nothing is to do. Therefore I believe it is an advantage, when the GUI stuff is not done by the sub-thread, and it is an advantage when the sub-thread does not need a message loop.
{$modeswitch functionreferences}
{$modeswitch anonymousfunctions}
// {$warn 5036 off}// "Warning: (5036) Local variable "$Capturer" does not seem to be initialized"
{$macro on}
{$define proc:= procedure}
{$define func:= function}
{$define b_ := begin}
{$define e_ := end}
type
TProcref = reference to procedure;
procedure TMyThread.Execute;
var
newStatus: string;
Form2:TForm=Nil;
procedure test;
begin
Form1.Caption := 'Form1 '+newstatus;
Form2.Caption := 'Form2 '+newstatus;
end;
begin
newstatus := 'TMyThread Starting ...';
//"proc" is a macro and expands to "procedure". This avoids a Codetools Problem.
Queue(proc begin
Form2 := TForm.Create(Nil);
Form2.Show;
Form2.Caption := '************ This is a Test';
end);
sleep(1000);
Queue(TProcref(@test));
while (not Terminated) and (True {any condition required}) do
begin
//here goes the code of the main thread loop
newStatus := 'TMyThread Time: ' + FormatDateTime('YYYY-MM-DD HH:NN:SS', Now);
if NewStatus <> fStatusText then
begin
fStatusText := newStatus;
Queue(TProcref(@test));
end;
sleep(50); // fStatusText alternatively the thread may wait for an event. E.g., external I/O
end;
Synchronize(proc begin Form2.free; end); //make sure the GUI Queue is empty, before procedure exits
end;
Remark:
Queue() should only be used, when short term blocking of the thread
must be prevented.
In most other cases
Synchronize() is mostly the better choice.