基本
ターゲットウィンドウを処理される前に、フック(HOOK)は、メカニズムをWindowsメッセージ処理のためのプラットフォームで、アプリケーションは、フックを設定することができ、メッセージが到着したときにメッセージのいくつかの種類の指定されたウィンドウを監視するために、それとの契約は、ウィンドウが他に監視することができます作成中のプロセス。
特定の深い知識、こちらの記事を参照することができますWindowsのフックフック包括的な概要
メッセージをインターセプトする範囲に応じてフックに分けることができます
- グローバルフック、メッセージスレッドは、すべてのウィンドウをブロックします
- フックをスレッド、それだけで特定のスレッドのメッセージをブロックします
関連インタフェース機能紹介:
HHOOK SetWindowsHookEx(
int idHook, //钩子类型,如 WH_MOUSE_LL, WH_MOUSE
HOOKPROC lpfn, //拦截回调函数
HINSTANCE hmod, // dll句柄
DWORD dwThreadId // 线程Id,当为0时表示全局钩子
);
この機能は、フックをインストールするために使用されます。他のスレッドのメッセージを傍受するために、グローバルフック、DLLコールバック関数によってトリガされている必要があり、使用する初心者にはお勧めしません、システムのクラッシュを引き起こす不適切な取り扱いは、糸のフックを使用することをお勧めします。
この要求では、我々は、マウスのフックに焦点を当て、2次のマウスをフック:
- WM_MOUSE:通常のマウスフック、フックは、モジュールのマウスイベントをインターセプトすることができます。
- WM_MOUSE_LL:低レベルのマウスフックは、システム全体のマウスイベントをインターセプトすることができます。
現在のシナリオでは、我々が使用するWM_MOUSE
フックをすることができます。ことに注意WM_MOUSE_LL
指定されたスレッドを監視するために、フックのみグローバルフックタイプに適用することができ、噴射ステージは1429エラー、エラー情報を求めるプロンプトが表示されます此挂接程序只可整体设置
。
LRESULT CALLBACK MouseProc(
_In_ int nCode,
_In_ WPARAM wParam,
_In_ LPARAM lParam
);
この機能は、インターフェースのマウスフックコールバック関数を定義します
LRESULT CallNextHookEx(
HHOOK hhk,
int nCode,
WPARAM wParam,
LPARAM lParam
);
この関数は、チェーンフック電流の次に渡されるフック情報をフックするために使用されます。
BOOL UnhookWindowsHookEx(
HHOOK hhk
);
この機能は、フックをアンインストールするために使用されます。
全体的なデザイン
次のようにこの機能の全体的なデザインは、次のとおりです。
二つのビジネスロジックの主な機能:
- 登録マウスフック
- メッセージをインターセプトするローラにメッセージを変換しました
登録マウスフック
登録WM_MOUSE
マウスフックタイプのに十分な、ノート公式ドキュメントのためにここにいる、WM_MOUSE
メッセージのコールバック関数のプロトタイプのタイプは次のとおりです。
LRESULT CALLBACK MouseProc(
_In_ int nCode,
_In_ WPARAM wParam,
_In_ LPARAM lParam
);
例えば、代表的なマウスのwParamメッセージ識別子WM_MOUSEWHEEL
、WM_MOUSEMOVE
等が挙げられます。
代表lParamには、構造体のマウス・コールバック・メッセージ・タイプを指しMOUSEHOOKSTRUCT
、以下のように、構造の宣言です。
typedef struct tagMOUSEHOOKSTRUCT {
POINT pt;
HWND hwnd;
UINT wHitTestCode;
ULONG_PTR dwExtraInfo;
} MOUSEHOOKSTRUCT, *LPMOUSEHOOKSTRUCT, *PMOUSEHOOKSTRUCT;
上記構造体から、我々は懸念しているPT(画面の現在のマウス位置の座標に基づいて座標系)であり、また距離をスクロールするために、マウスのホイールを持っている必要があり、いくつかの検索の後、私は2つの場所がパラメータを持っているが見つかりました:
- 低レベルのマウスフック(WM_MOUSE_LL)コールバック関数のlParam、種類
MSLLHOOKSTRUCT
、次の文:
typedef struct tagMSLLHOOKSTRUCT {
POINT pt;
DWORD mouseData;
DWORD flags;
DWORD time;
ULONG_PTR dwExtraInfo;
} MSLLHOOKSTRUCT, *LPMSLLHOOKSTRUCT, *PMSLLHOOKSTRUCT;
マウスホイールにメッセージを傍受するとき、mouseData
上位バイトは、距離マウスホイールを表します。しかし、低レベルのフックを使用するのに適していない、グローバルフックを必要とします。
- 一般的なメッセージ・コールバックフック構造の拡張
MOUSEHOOKSTRUCTEX
、説明MSDN:
This is an extension of the MOUSEHOOKSTRUCT structure that includes information
about wheel movement or the use of the X button.
typedef struct tagMOUSEHOOKSTRUCTEX {
DWORD mouseData;
} MOUSEHOOKSTRUCTEX, *LPMOUSEHOOKSTRUCTEX, *PMOUSEHOOKSTRUCTEX;
明らかに、この構造は、一般的なメッセージ構造上の展開拡大することでmouseData
、我々が必要とするまさに、フィールドを。
メッセージをインターセプトするローラにメッセージを変換しました
上記の分析によると、私たちは今、行う必要があり、通常のローラーホイールフックメッセージとしてメッセージを変換することです。
MSDNは理解文書、wParamにローラフックマウスメッセージは、のようなWM_MOUSE_WHEELとして、メッセージ識別子です。次のようにlParamにローラフックメッセージが変換されます。
MOUSEHOOKSTRUCTEX const &eventInfo = *(MOUSEHOOKSTRUCTEX*)lParam;
// eventInfo.mouseData <-- 鼠标滚轮距离
// eventInfo.pt <-- 鼠标当前坐标
GET_WHEEL_DELTA_WPARAM
マクロmouseData
抽出ホイールスクロール距離メンバー、通常のメッセージローラWM_MOUSEWHEEL
ローラはさらに低いバイト仮想キーメッセージを含む、距離をスクロール以外のwParam。フックは、それはまた、仮想キーメッセージは、このステップを使用する必要が補完し、何のメッセージではないGetAsyncKeyState
機能を。
最後のステップは、現在のマウス座標に基づいて、現在位置のウインドウハンドルを取得、Windowsが提供するWindowFromPoint
この機能を達成するために機能します。
フックに基づいてこれは、非アクティブウィンドウのスクロールマウスの応答関数のポイントは、すべての導入完了している実現しています。
デモ参照リンク
過負荷メッセージの前処理の実装
オンライン見つけるための別の方法は、参照マウスホイールに対応して非アクティブウィンドウを
核となるアイデアはで受信した現在のマウスホイールメッセージを使用することであるPreTranslateMessage
現在のマウスオーバー位置に傍受、窓に直接処理。このソリューションは非常に簡単ですが、問題は、非現在のスレッドによって作成されたウィンドウにメッセージを送信しますマウスが、問題がある可能性がありますによって引き起こされることが、より多くのテストが必要です。
概要
どちらの実装では、あなたの参照のためのより多くのアイデアを与えています。
経験は:あなたが事の一種、唯一の方法を行う場合は、この世界では、それはあまりにも退屈だろう。