共用方式為


HOW TO:實作回呼函式

更新:2007 年 11 月

下列程序和範例示範 Managed 應用程式如何 (使用平台叫用) 列印本機電腦上每個視窗的控制代碼值。特別的是,程序和範例會使用 EnumWindows 函式逐步執行視窗清單,並使用 Managed 回呼函式 (Callback Function) (名為 CallBack) 列印視窗控制代碼值。

若要實作回呼函式

  1. 在繼續進行實作之前,先查看 EnumWindows 函式的簽章。EnumWindows 具有以下簽章:

    BOOL EnumWindows(WNDENUMPROC lpEnumFunc, LPARAM lParam)
    

    有個跡象可以看出這個函式需要回呼函式,就是它有個 lpEnumFunc 引數。常常可以看到 lp (長指標 (Long Pointer)) 前置詞與 Func 後置詞,組合使用於接受指向回呼函式之指標的引數名稱中。如需 Win32 函式的文件,請參閱 Microsoft Platform SDK。

  2. 建立 Managed 回呼函式。範例中宣告了一個用來接受兩個引數 (hwndlparam) 的委派型別 (Delegate Type),名稱為 CallBack。第一個引數是視窗的控制代碼;第二個引數是應用程式定義的。在這個版本中,這兩個引數都必須是整數。

    回呼函式通常會傳回非零值以表示成功,而零則表示失則。這個範例是將傳回值明確地設定為 True 以繼續進行列舉。

  3. 建立委派物件,並將它當做引數傳遞給 EnumWindows 函式。平台叫用會自動將這個委派物件轉換為熟悉的回呼格式。

  4. 在回呼函式完成工作之前,確定記憶體回收行程不會重新宣告委派。當您將委派當做參數傳遞,或是傳遞內含在結構中當做欄位的委派時,在呼叫期間不會將它回收。因此,在下面這個列舉型別的範例中,回呼函式會在呼叫傳回之前先完成它的工作,而且不會要求 Managed 呼叫端採取其他動作。

    但是,如果呼叫函式可在呼叫傳回之後再叫用,Managed 呼叫端必須採取一些步驟,以確保在回呼函式完成之前不會將委派回收。如需避免記憶體回收的詳細資訊,請參閱平台叫用的 Interop 封送處理

範例

Imports System
Imports System.Runtime.InteropServices

Public Delegate Function CallBack( _
hwnd As Integer, lParam As Integer) As Boolean

Public Class EnumReportApp

    Declare Function EnumWindows Lib "user32" ( _
       x As CallBack, y As Integer) As Integer

    Public Shared Sub Main()
        EnumWindows(AddressOf EnumReportApp.Report, 0)
    End Sub 'Main

    Public Shared Function Report(hwnd As Integer, lParam As Integer) _
    As Boolean
        Console.Write("Window handle is ")
        Console.WriteLine(hwnd)
        Return True
    End Function 'Report
End Class 'EnumReportApp
using System;
using System.Runtime.InteropServices;

public delegate bool CallBack(int hwnd, int lParam);

public class EnumReportApp {

    [DllImport("user32")]
    public static extern int EnumWindows(CallBack x, int y); 

    public static void Main() 
    {
        CallBack myCallBack = new CallBack(EnumReportApp.Report);
        EnumWindows(myCallBack, 0);
    }

   public static bool Report(int hwnd, int lParam) { 
        Console.Write("Window handle is ");
        Console.WriteLine(hwnd);
        return true;
    }
}
using namespace System::Runtime::InteropServices;

// A delegate type.
__delegate bool CallBack(int hwnd, int lParam);

// Managed type with the method to call.
__gc class EnumReport 
{
// Report the window handle.
public:
    bool Report(int hwnd, int lParam) {
       Console::Write(L"Window handle is ");
       Console::WriteLine(hwnd);
       return true;
   }
};

[DllImport("user32")] 
extern "C" int EnumWindows(CallBack* x, int y); 

void main(void) { 
    EnumReport* er = new EnumReport;
    CallBack* myCallBack = new CallBack(er, &EnumReport::Report);
    EnumWindows(myCallBack, 0); 
}

請參閱

概念

回呼函式

其他資源

呼叫 DLL 函式