Get a function result asynchronously in Delphi using Omni Thread Library

后端 未结 1 847
不思量自难忘°
不思量自难忘° 2021-02-11 00:34

I am trying to call a function from another unit/class which would take some time in performing the task and would return a string value. I couldn\'t find a good reference somet

相关标签:
1条回答
  • 2021-02-11 01:40

    You would normally use a future in a case where you want something executed in the background but still need the result in the same execution path. It basically lets you do something in the background while doing another thing in the main thread and you can then use the result of the background thread.

    What you need to use is the Async abstraction that TLama linked to:

    In your case it would be:

    procedure TForm1.DoSomething;
    var
      theFunctionResult: string;
    begin
      memo1.Lines.Add('calling a asynchronous function..');
      Parallel.Async(
        procedure
        begin
          // executed in background thread
          theFunctionResult := GetMagicString;
        end,
    
        procedure
        begin
          // executed in main thread after the async has finished
          memo1.Lines.Add(theFunctionResult);
    
          // notify that the task has been completed
          memo1.Lines.Add('Results fetched successfully.');
        end
      );
    end;
    

    This is a bit messy but you should get the idea. You need to make sure that your async code is completed before you destroy the form that owns this code (TForm1).

    If you want to try and setup a system that will call an event when the code completes then you can do something like this:

    type
      TMyEvent = procedure(const aValue: string) of object;
    
    procedure GetMagicStringInBackground(AEvent: TMyEvent);
    var
      theFunctionResult: string;
    begin
      Parallel.Async(
        procedure
        begin
          // executed in background thread
          theFunctionResult := GetMagicString;
        end,
    
        Parallel.TaskConfig.OnTerminated(
          procedure (const task: IOmniTaskControl)
          begin
            // executed in main thread after the async has finished
            if Assigned(AEvent) then
              AEvent(theFunctionResult );
          end
        )
      );
    end;
    

    You can then put the threaded code in the GetMagicString unit and just call the method above from your form passing in an event that will get called when it completes.

    0 讨论(0)
提交回复
热议问题