マウスホイールの逆転

解決


たく  2007-01-03 05:48:14  No: 64150

たびたび、お世話になります。

そのプログラムを起動中は、単純にマウスホイールの回転を逆にしたいんですが、
このためには、システムフックを掛ける必要があると思います。

そこで、DLLを作ってみたんですが、WM_MOUSEWHEELが返すパラメータが良くわかりません。
どの変数をいじれば良いでしょうか?
よろしく、お願い致します。

LRESULT CALLBACK MouseHookProc( int nCode, WPARAM wp, LPARAM lp)
{
  if( nCode < 0 || nCode == HC_NOREMOVE )
    return CallNextHookEx( hMyHook, nCode, wp, lp );

  if( wp == WM_MOUSEWHEEL )
  {
//    char str[64];
//    wsprintf(str, "lp = %x ", lp);
//    MessageBox(NULL, str, "Dll", MB_OK);
    lp = 0 - lp;

    //MessageBox( NULL, "ホイール回転", "Message", MB_OK );
    
    return CallNextHookEx( hMyHook, nCode, wp, lp );
  }
  else
    return CallNextHookEx( hMyHook, nCode, wp, lp );

  return TRUE;
}


瀬戸っぷ  2007-01-03 08:53:36  No: 64151

> そこで、DLLを作ってみたんですが、WM_MOUSEWHEELが返すパラメータが良くわかりません。
> どの変数をいじれば良いでしょうか?

まずは、MSDNを見ましょう。

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/winui/winui/windowsuserinterface/userinput/mouseinput/mouseinputreference/mouseinputmessages/wm_mousewheel.asp

LPARAMにはマウスの座標が、
WPARAMにはホイールの状態と、キーの状態が入っているようです。
HIWORD(上位16Bit)にホイールの状態が、
LOWORD(下位16Bit)にキーの状態が入ってます。
GET_KEYSTATE_WPARAM()マクロとGET_WHEEL_DELTA_WPARAM()マクロでそれぞれ取り出せますから、
ホイールの状態を反転(-1を掛ければOK?)して、
MAKEWPARAM()マクロで再度WPARAM型にすればいいのではないでしょうか?


瀬戸っぷ  2007-01-03 09:01:06  No: 64152

あう…フックはやったことないので、ちょっと調査が足りなかったようです。

ということで、猫でものページを。
http://www.kumei.ne.jp/c_lang/sdk2/sdk_162.htm

フックのLPATAMにMOUSEHOOKSTRUCT構造体へのポインタが入るようで。
マウスメッセージ系にはLPARAMにカーソルの座標が入っているようですので、
こちらはMOUSEHOOKSTRUCT構造体のptメンバーでしょう。
消去法で行くと…dwExtraInfoメンバーがマウスメッセージ系のWPARAMに当たるのでしょうか…


たく  2007-01-03 19:33:56  No: 64153

瀬戸っぷさま
ご指導有難うございました。
あ、これか、と思って
    MOUSEHOOKSTRUCT *pmh;
    pmh = (MOUSEHOOKSTRUCT *)lp;
  if( wp == WM_MOUSEWHEEL )
  {
    char str[64];
    wsprintf(str, "pt = %x\n Code = %x\n TestCode = %x \nExtraInfo = %x ",pmh->pt, pmh->hwnd, pmh->wHitTestCode, pmh->dwExtraInfo);
    MessageBox(NULL, str, "Dll", MB_OK);
    return CallNextHookEx( hMyHook, nCode, wp, lp );
  }
として見たんですが、ホイール回転時dwExtraInfoには0しか入っていませんでした。
事前に、MFCで作った
BOOL CWheelReverseView::PreTranslateMessage(MSG* pMsg) 
{
    if( pMsg->message == WM_MOUSEWHEEL )
    {
        pMsg->wParam = 0-(pMsg->wParam);  //ホイールの回転方向
    }
    return CFormView::PreTranslateMessage(pMsg);
}
こちらでは、wParamでは正転で00780000、逆転でff880000が入っていたんですが


瀬戸っぷ  2007-01-03 23:04:13  No: 64154

> として見たんですが、ホイール回転時dwExtraInfoには0しか入っていませんでした。

あら、そうでしたか…
そうなると私にはちょっと判らないです。

「WM_MOUSEWHEEL フック」でググってみました。
http://msdn.microsoft.com/library/ja/default.asp?url=/library/ja/jpipc/html/_win32_lowlevelmouseproc.asp

LowLevelMouseProc()でのMSLLHOOKSTRUCT構造体ではWM_MOUSEWHEELでのWPARAMが取れそうです。
が、システムフックとは違いますかね。

あとは…フィルタドライバとかでしょうか??
どれも触ったことありませんが。

……さらに検索続行…
http://slashdot.jp/~A7M/journal/180100
http://www.aofactory.net/log/eid237.html

MOUSEHOOKSTRUCTEX構造体なんてのがあるようです。
MOUSEHOOKSTRUCT構造体に追加のメンバを含んだものみたいですね。

# MOUSEHOOKSTRUCT構造体についてSDKのヘッダファイルを
# grepすれば見つけられたのか…
# いつもならやること多いんだけど、今回はやってなかった。


たく  2007-01-04 01:23:03  No: 64155

瀬戸っぷさま
有難うございました。

typedef struct {
    MOUSEHOOKSTRUCT MOUSEHOOKSTRUCT;
    DWORD mouseData;
} MOUSEHOOKSTRUCTEX, *PMOUSEHOOKSTRUCTEX;  を宣言して

LRESULT CALLBACK MouseHookProc( int nCode, WPARAM wp, LPARAM lp)
{
  if( nCode < 0 || nCode == HC_NOREMOVE )
    return CallNextHookEx( hMyHook, nCode, wp, lp );

    MOUSEHOOKSTRUCTEX *pmh;
  short Delta ;
    pmh = (MOUSEHOOKSTRUCTEX *)lp;

  if( wp == WM_MOUSEWHEEL )
  {
    char str[64];
    Delta = HIWORD(pmh->mouseData);
    
    pmh->mouseData = 0 - pmh->mouseData;

    wsprintf( str, "元データ   = %x \n変換データ = %x", Delta, HIWORD(pmh->mouseData));
    MessageBox(NULL, str, "DLL", MB_OK );
  }
  return CallNextHookEx( hMyHook, nCode, wp, lp );
}
としたら、正転78逆転ffff88が取れるようになりました。

でも、このままフックを掛けてもホイールは逆転してくれませんでした。
なんでかな?
あと、少しのような気がします。頑張って見ます。


たく  2007-01-04 07:12:57  No: 64156

下のやり方で、当初思っていた、正転で00780000、逆転でff880000をmouseDataに
セット出来るようになったと思うんですが、マウスを逆転することはできませんでした。
どうも、ココをいじっただけではダメなのかなと思い出しました。
returnを返さなければ、ホイールの回転を止められるので、フック自体は
効いているんですが、

どなたか、情報をお持ちでしたら、お教えください。

LRESULT CALLBACK MouseHookProc( int nCode, WPARAM wp, LPARAM lp)
{
  if( nCode < 0 || nCode == HC_NOREMOVE )
    return CallNextHookEx( hMyHook, nCode, wp, lp );

    MOUSEHOOKSTRUCTEX *pmh;
  short Delta ;
  unsigned long MouData;

    pmh = (MOUSEHOOKSTRUCTEX *)lp;

  if( wp == WM_MOUSEWHEEL )
  {
    char str[64];
    Delta = HIWORD(pmh->mouseData);
    Delta = 0 - Delta;

    MouData = (unsigned int)Delta;
    MouData = MouData << 16;

    pmh->mouseData = MouData;

    wsprintf( str, "変換データ = %x", pmh->mouseData);
    MessageBox(NULL, str, "DLL", MB_OK );
  }
  return CallNextHookEx( hMyHook, nCode, wp, lp );
}


たく  2007-01-08 04:25:00  No: 64157

あるサイトを拝見して、以下のようなコードで逆転できました。
有難うございました。
LRESULT CALLBACK MouseHookProc( int nCode, WPARAM wp, LPARAM lp)
{
  if( nCode < 0 || nCode == HC_NOREMOVE )      //nCodeが負、HC_NOREMOVEの時は何もしない
    return CallNextHookEx( hMyHook, nCode, wp, lp );

  MSG* msg = (MSG*)lp;

  if( msg->message == WM_MOUSEWHEEL )        //メッセージがホイール回転の場合
  {                        //呼び出し元ハンドルを条件に加えると、呼び出したWindow上のみになる
    short delta;
    USHORT mkbtn;

    delta = HIWORD( msg->wParam );        //上位バイト取得
    mkbtn = LOWORD( msg->wParam );        //下位バイト取得

    delta = 0 - delta;              //移動量の正負逆転

    msg->wParam = MAKEWPARAM( mkbtn, delta );  //パラメータセット
  }
  return CallNextHookEx( hMyHook, nCode, wp, lp );
}


たく  2007-01-08 04:25:48  No: 64158

解決のチェックを忘れてました。


※返信する前に利用規約をご確認ください。

※Google reCAPTCHA認証からCloudflare Turnstile認証へ変更しました。






  このエントリーをはてなブックマークに追加