2009-06-27 4 views
1

Ich entwickle eine Schnittstelle für ein Add-on zu einem Spiel. Ich kann die Spiel-API nicht verwenden (aus verschiedenen Gründen, einschließlich der Tatsache, dass der Code nicht vom Spiel abhängig sein muss) und ich muss Tastatureingaben vom Benutzer erhalten, also habe ich beschlossen, einen Tastatur-Hook (WH_KEYBOARD) zu verwenden Eingabe, wenn bestimmte Bedingungen erfüllt sind.
Das Problem ist, dass, während ich die Eingabe richtig empfangen und verarbeiten kann, wenn mein Haken TRUE anstelle CallNextHookEx zurückgibt, das System viel Zeit (weit über 800ms) dauert, bevor die Dinge wie erwartet weitergehen und das ist nicht akzeptabel weil es nicht einmal eine flüssige Tipperfahrung erlaubt.
Was ich erreichen muss, ist zu verhindern, dass die Nachricht beim Drücken der Taste den WndProc erreicht, also lautet die Frage: Was kann ich tun, um mein Ziel zu erreichen, ohne die Spieleleistung so stark zu beeinträchtigen, dass das Ergebnis inakzeptabel ist? EDIT: aufgrund spezifischer Anforderungen (Spiele mit Anticheats, die Probleme mit meinem Code erstellen können, obwohl es nicht betrügt) Subclassing der aktiven wndproc ist keine Option.KeyboardProc Rückkehr TRUE verursacht Leistungsabfälle

Antwort

0

So sehr ich meine eigene Frage nicht beantworte, habe ich die Ursache der Verzögerung gefunden. Die Message-Pump der Spiele, gegen die ich meinen Code getestet habe, wurde mit einer Weile implementiert (PeekMessage) {GetMessage ...} und das Entfernen der Tastatureingabenachricht hat irgendwie dazu geführt, dass GetMessage für einige Zeit blockiert wurde. Die Verwendung von PostMessage und WM_NULL verhinderte die Blockierung von GetMessage.

2
  1. Zuerst müssen Sie Ihre DLL in den Zielprozess injiziert werden, entweder durch Haken oder durch any other way.

  2. Finden Sie den Fenstergriff von Interesse.

  3. Die aktuelle Fensterprozedur dieses Fensters durch Aufrufen von GetWindowLongPtr (wnd, GWLP_WNDPROC) abrufen und speichern.

  4. Unterklasse das Fenster durch Aufruf von SetWindowLongPtr (wnd, GWLP_WNDPROC, & NewWndProc) wobei NewWndProc Ihre DLL-implementierte Nachrichtenprozedur ist.

Innen NewWndProc Sie Tastatur-Nachrichten verarbeiten wollen (es sind ein Dutzend von ihnen, geben Sie „Tastatureingabe“ in MSDN-Index, kann ich nicht mehr als 1 Link posten). Für den Rest von Windows rufen Nachrichten die ursprüngliche Fensterprozedur auf, die Sie während (3) gespeichert haben, und geben den zurückgegebenen Wert zurück. Rufen Sie es nicht direkt an, verwenden Sie stattdessen CallWindowProc.

Dieser Weg ist nicht sehr zuverlässig, einige Antiviren- und Anti-Bot- (z. B. "Warden-Client") Software mag es nicht, und Debugging kann eine Herausforderung sein.

Allerdings sollte es funktionieren.

+0

Vielen Dank für Ihren cleveren Vorschlag, aber wie Sie darauf hingewiesen, Anticheats wird nicht lieben, und während ich dies nicht für Betrugszwecke tun, kann ich mir nicht wirklich leisten, falsche Positive auszulösen. Der gute Teil des Tastatur-Hooks ist, dass Anticheats das nicht markieren, weil viele Programme das für legitime Zwecke verwenden ... – em70

+0

Windows-Unterklassen werden auch von vielen Programmen für legitime Zwecke verwendet. – Soonts

0

Ein Tastatur-Hook sollte Dinge nicht so langsam machen. Es gibt wahrscheinlich etwas anderes, das die 800ms Verzögerung verursacht. Ist es immer noch langsam, wenn dein Hook nichts tut und einfach TRUE zurückgibt?

+0

Ja, das Zurückgeben von TRUE ist genug, um die Verlangsamung beim Zurückgeben von FALSE zu verursachen, selbst wenn ich das Tastaturereignis verarbeite, hat das keinerlei Auswirkungen auf die Leistung (aber das ist nicht in Ordnung, da die Tastenanschläge nicht vom Spiel verarbeitet werden). Ich habe es an zwei verschiedenen Spielen mit verschiedenen Engines getestet und die Ergebnisse sind die gleichen. – em70

0

Wenn Sie verhindern möchten, dass die Nachricht in WndProc ankommt, müssen Sie die Unterklasse SetWindowLong verwenden. Auf diese Weise können Sie alle Nachrichten abfangen und entscheiden, ob sie ihre Route fortsetzen möchten.

+0

Danke, aber wie oben erwähnt, ist Unterklassen keine Option. – em70

Verwandte Themen