我正在子类化一个应用程序。我的子类窗口过程在一个DLL中。我的DLL中的子类代码看起来有点像这样(精简了、删除了其他不相关的部分)。
class FooBar
{
private delegate int WndProcDelegateType(IntPtr hWnd, int uMsg,
int wParam, int lParam);
private const int GWL_WNDPROC = (-4);
private static IntPtr oldWndProc = IntPtr.Zero;
private static WndProcDelegateType newWndProc = new
WndProcDelegateType(MyWndProc);
internal static bool bHooked = false;
[DllImport("user32.dll")]
private static extern IntPtr SetWindowLong(IntPtr hWnd, int nIndex,
WndProcDelegateType dwNewLong);
[DllImport("user32.dll")]
private static extern IntPtr SetWindowLong(IntPtr hWnd, int nIndex,
IntPtr dwNewLong);
[DllImport("user32")]
private static extern int CallWindowProc(IntPtr lpPrevWndFunc, IntPtr hWnd,
int Msg, int wParam, int lParam);
private static int MyWndProc(IntPtr lhWnd, int Msg, int wParam, int lParam)
{
switch (Msg)
{
// the usual stuff
// finally
return CallWindowProc(oldWndProc, lhWnd, Msg, wParam, lParam);
}
internal static void Hook()
{
oldWndProc = SetWindowLong(hWnd, GWL_WNDPROC, MyWndProc);
bHooked = oldWndProc != IntPtr.Zero;
}
internal static void Unhook()
{
if (bHooked) SetWindowLong(hWnd, GWL_WNDPROC, oldWndProc);
}
}
尽管我将WndProc的强引用保存在类级别的静态实例变量中,但仍然会出现此错误。
检测到回调已被垃圾回收的委托
消息:在类型为“PowerPointAddIn1!FooBar + WndProcDelegateType :: Invoke”的已垃圾回收的委托上进行了回调。这可能导致应用程序崩溃,损坏和数据丢失。当向非托管代码传递委托时,必须通过托管应用程序保持其活动状态,直到可以确保它们永远不会被调用。
我做错了什么?
FooBar
对象也没有被垃圾回收,因为引用将丢失。在调试期间,它可能运行良好,但在带有优化的发布构建中,我开始大惑不解。 - prostynick