Every now and then, you'll find a windows message that has no WPF equivalent. HwndSource lets you use a WndProc to get window messages; what you may not know is that you can still use the Window class.
It's not obvious how to go from a Window to a HwndSource -- the trick is to use WindowInteropHelper to get an hwnd, then use HwndSource.FromHwnd. Once you have that, you can use HwndSource.AddHook to subclass Window's WndProc.
In this silly example, I detect WM_DESTROY and put up a MessageBox:
public partial class Window1 : Window
void Window1_Loaded(object sender, RoutedEventArgs e)
HwndSource source = HwndSource.FromHwnd(new WindowInteropHelper(this).Handle);
private static IntPtr WndProc(IntPtr hwnd, int msg, IntPtr wParam, IntPtr lParam, ref bool handled)
// Handle whatever Win32 message it is we feel like handling
if (msg == WM_DESTROY)
MessageBox.Show("I saw a WM_DESTROY!");
handled = true;
private const int WM_DESTROY = 0x0002;