5

v8 エンジンが組み込まれた小さなコンソール アプリケーションがあり、キー イベントを登録するためのフックを追加したいと考えています。以前は Qt と QtScript を使用していたとき、これはすべて機能していましたが、VC++ 2008 で直接 C++ に移植しています。アプリケーションはコンパイルおよび実行されますが、フックは呼び出されません。関連するコードは次のとおりです。

main() で

HWND hwndC = GetConsoleWindow() ;
    HINSTANCE hInst = (HINSTANCE)GetWindowLong( hwndC, GWL_HINSTANCE );
    if (SetWindowsHookEx(WH_KEYBOARD_LL, HookProc, hInst, NULL) == 0) {
        printf("Failed to set hook\n");
    } else {
        printf("Hook established\n");
    }
    g->RunScript(argc,argv);

そして手続き:

LRESULT CALLBACK HookProc(int nCode, WPARAM wParam, LPARAM lParam)
{
    printf("HookProc called\n");
    PKBDLLHOOKSTRUCT p = (PKBDLLHOOKSTRUCT) (lParam);
    if (wParam == WM_KEYDOWN) {
       keyDown(p,g);
    } else if (wParam == WM_KEYUP) {
        keyUp(p,g);
    }
    fflush(stdout);
    return CallNextHookEx(NULL, nCode, wParam, lParam);
}

これは基本的に、v8 サンプル コードから shell.cc を拡張したものです。どういうわけかブロックされているのだろうか?自分がここで何をしているのかよくわかっていないことは認めます。ただ遊んで学んでいるだけですが、これには困惑しました。

keyDown の内部には、次のようなものがあります。

    v8::Handle<v8::String> callback_name = v8::String::New("onKeyDown");
    v8::Handle<v8::Value> callback_val = g->_context->Global()->Get(callback_name);
    if (!callback_val->IsFunction()) {
        printf("No onKeyDown handler found\n");
        return;
    }
    v8::Handle<v8::Function> callback = v8::Handle<v8::Function>::Cast(callback_val);
    const int argc = 1;
    v8::Handle<v8::Value> argv[argc] = { v8::Int32::New(char(p->vkCode)) };
    printf("Calling onKeyDown\n");
    v8::Handle<v8::Value> result = callback->Call(g->_context->Global(), argc, argv);

これらのいくつかは最終的に実際には機能しない可能性がありますが、プログラムを実行して次のように定義すると、呼び出されることはありません: onKeyDown = function(key) {...}; onKeyDown が正常に機能していることがわかります。バインドされたすべての C++ メソッドなどを JS から使用できるため、このことは私をバタバタさせています。

何か助けがあれば、おそらくいくつかの教材へのポインタをいただければ幸いです。

明確にするために、c のこの関数: LRESULT CALLBACK HookProc(int nCode, WPARAM wParam, LPARAM lParam) が呼び出されることも、printf が表示されることもありません。フックが確立されます。

/ジェイソン

4

2 に答える 2

8

WH_KEYBOARD_LL のような低レベルのフックでは、アプリケーションがメッセージ ループをポンピングする必要があります。これは、Windows がスレッドに割り込んで、登録した HookProc コールバックを呼び出す唯一の方法です。

コンソール モード アプリは、通常の Windows GUI アプリのようにメッセージ ループを送りません。スニペットから判断すると、追加するのも簡単ではありません。スレッドを作成する必要があります。

于 2011-08-07T18:23:40.163 に答える
1

ひょっとしたら、この機能があなたの役に立ちますか? GetAsyncKeyState

于 2011-08-07T19:16:26.033 に答える