callback/zh CN

From Lazarus wiki
Jump to navigationJump to search

回调函数

Lazarus 中广泛运用了回调函数,其实事件都是通过“回调”实现的。

 type
  TForm = class(TForm)
    btn: TButton;
    procedure btnClick(Sender: TObject);
  end;
 ...
  procedure TForm.btnClick(Sender: TObject);
  begin
   // 干活的代码
  end;

btnClick 方法是 TButton 实现的一个回调函数。

除了窗体的用户界面组件之外,回调函数还用于很多已链接的

库的回调

DWORD LpprogressRoutine(
  LARGE_INTEGER TotalFileSize,
  LARGE_INTEGER TotalBytesTransferred,
  LARGE_INTEGER StreamSize,
  LARGE_INTEGER StreamBytesTransferred,
  DWORD dwStreamNumber,
  DWORD dwCallbackReason,
  HANDLE hSourceFile,
  HANDLE hDestinationFile,
  LPVOID lpData
)
TMyForm = class( TForm )
  progressbar: TProgressbar;
  bIsAborted: boolean;
  ...
end;

  // CopyFileEx 所需的回调函数
function _CopyCallback( 
  TotalFileSize, TotalBytesTransferred, StreamSize, StreamBytesTransferred: Int64; 
  dwStreamNumber, dwCallbackReason: DWORD;
  hSourceFile, hDestinationFile: THandle; 
  f: TMyForm ): DWORD; stdcall;
var
  newpos: Integer;
const
  PROCESS_CONTINUE = 0;
begin
  result := PROCESS_CONTINUE;
  if dwCallbackReason = CALLBACK_CHUNK_FINISHED then begin
    newpos := Round( TotalBytesTransferred / TotalFileSize * 100 );
    with f.Progressbar do
      if newpos <> Position then
        Position := newpos;
    Application.ProcessMessages();
  end;
end;

...

  // 将 fromfile 复制为 'tofile',在 myFor.Progressbar 中显示进度,并可响应 myForm.bIsAborted 中止操作
result := CopyFileEx(  'fromfile', 'tofile', @_CopyCallback, pointer(myForm), @myForm.bIsAborted, 0 );