Jeśli nie masz nic przeciwko odwoływaniu się do WinForms, możesz użyć bardziej zorientowanego na MVVM rozwiązania, które nie łączy usługi z widokiem. Należy utworzyć i zainicjować System.Windows.Forms.NativeWindow, które jest lekkim oknem, które może odbierać wiadomości.
public abstract class WinApiServiceBase : IDisposable
{
/// <summary>
/// Sponge window absorbs messages and lets other services use them
/// </summary>
private sealed class SpongeWindow : NativeWindow
{
public event EventHandler<Message> WndProced;
public SpongeWindow()
{
CreateHandle(new CreateParams());
}
protected override void WndProc(ref Message m)
{
WndProced?.Invoke(this, m);
base.WndProc(ref m);
}
}
private static readonly SpongeWindow Sponge;
protected static readonly IntPtr SpongeHandle;
static WinApiServiceBase()
{
Sponge = new SpongeWindow();
SpongeHandle = Sponge.Handle;
}
protected WinApiServiceBase()
{
Sponge.WndProced += LocalWndProced;
}
private void LocalWndProced(object sender, Message message)
{
WndProc(message);
}
/// <summary>
/// Override to process windows messages
/// </summary>
protected virtual void WndProc(Message message)
{ }
public virtual void Dispose()
{
Sponge.WndProced -= LocalWndProced;
}
}
Zastosowanie SpongeHandle zarejestrować wiadomości, które Cię interesują, a następnie zastąpić WndProc przetwarzać je:
public class WindowsMessageListenerService : WinApiServiceBase
{
protected override void WndProc(Message message)
{
Debug.WriteLine(message.msg);
}
}
Jedynym minusem jest to, że trzeba to System.Windows.Forms odniesienie, ale w przeciwnym razie jest to bardzo zamknięte rozwiązanie.
Więcej na ten temat można przeczytać here
Cóż, urządzenia USB (dis) łączą zdarzenia, które zdają się przechodzić przez tę pętlę wiadomości, więc nie jest źle wiedzieć, jak podłączyć się z WPF – flq
@Noldorin: Czy możesz podać referencje (artykuły/książki), które mogą pomóc rozumiem część "Ideologia projektowania i natura API jest bardzo różna w WPF od WinForms, ... dlaczego nie ma odpowiednika WndProc"? – atiyar
'WM_MOUSEWHEEL' na przykład, jedynym sposobem na niezawodne przechwycenie tych wiadomości było dodanie' WndProc' do okna WPF. To działało dla mnie, podczas gdy oficjalne narzędzie "MouseWheelEventHandler" po prostu nie działało zgodnie z oczekiwaniami. Nie byłem w stanie uzyskać prawidłowych tachionów WPF ustawionych dokładnie tak, aby uzyskać niezawodne zachowanie za pomocą 'MouseWheelEventHandler', stąd potrzeba bezpośredniego dostępu do' WndProc'. –