【MouseGestureL】初期設定とジェスチャ案

## はじめに

2年ほど利用して知見が蓄えられたので、備忘録的にまとめておくことにしました。

## 環境

AutoHotkey(Unicode) ver.1.1.33.2
MouseGestureL.ahk ver.1.38

## 初期設定

### ジェスチャー失敗時にコンテキストメニューを表示しない

`設定`>`認識設定`
`未定義ジェスチャーの入力後に本来のマウス操作を再現しない`にチェックを入れます。

ちなみに、ver.1.3.1以前では次のように設定していました。

```:MouseGestureL.ahk
; (前略)

; Emulate trigger if gesture is not executed
; ジェスチャー未発動の場合、トリガー操作をエミュレート

; ↓追加
if (MG_Gesture != %name%__) {
  return
}
; ↑追加

CoordMode,Mouse,Screen
SetMouseDelay,-1
BlockInput,On

; (後略)
```

### Chromeのブックマークに対して右クリックを有効化

元の設定では、Chromeのブックマークバー上にあるフォルダ内のアイテムに対して、右クリックが効きません。

次のようにして右クリックを有効化します。

`設定`>`ターゲット`
![ターゲット設定.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/936879/7cf909d3-39d3-42ef-e768-ea3f7b84e217.jpeg)


### VSCodeでスクリプトを編集する

`設定`>`その他`
`スクリプトの編集に使用するエディタ`でパスを指定します。

例: `C:\tools\vscode\Code.exe`

### 認識設定の数値

`設定`>`認識設定`は以下の設定になっています。

![認識設定.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/936879/208f9153-7138-275b-876e-927ec57dcaa6.jpeg)

### 各種プラグインの導入

#### ContinuousActivation.ahk

ジェスチャー後にトリガーを離さずサブトリガーを連打することで、連続発動することができます。

例えば、「戻る」や「タブ移動」で効果を発揮します。

有志が作成した`ContinuousActivation.ahk`をプラグインとして`Include`します。

[Autohotkey専用うpろだ](https://ux.getuploader.com/autohotkeyl/download/151)よりダウンロードし、`Plugins`フォルダ内に配置します。

その後、`MouseGestureL.ahk`の600行あたりにある`MG_Check()`を以下に書き換えます。(当該ファイル内に案内あり)

```:MouseGestureL.ahk
if (!ContinuousActivation) {
  MG_Check()
}
ContinuousActivation := 0
```

そして、下記のジェスチャーを登録します。
アクション未登録だとしても、これがなければ`ContinuousActivation.ahk`が誤作動する様子です。

```
[RB_LB_]
G=RB_LB_
Default=;空でもOK
```

#### TaskVol.ahk

タスクバー上のホイール操作で音量を調整するプラグインです。

こちらも[Autohotkey専用うpろだ](https://ux.getuploader.com/autohotkeyl/download/29)からダウンロードします。

## おすすめジェスチャ一覧

特に気に入っているジェスチャーのみ掲載します。
すべてコピペで取り込み可能です。

なお、似たジェスチャーは書いていませんが、例えば`上スクロール`だけ書かれていた場合は、対称的なジェスチャーが`下スクロール`になります。

### 初級

```:上スクロール
[RB_↑_]
G=RB_U_
Default=;上スクロール<MG_CR><MG_CR>Send, {Blind}{PgUp}{PgUp}
```

```:上端スクロール
[RB_→↑_]
G=RB_RU_
Default=;上端スクロール<MG_CR><MG_CR>Send,^{Home}
```

```:戻る
[RB_←_]
G=RB_L_
Default=;戻る<MG_CR><MG_CR>Send, !{Left}
```

```:更新
[RB_↑↓_]
G=RB_UD_
Default=;更新<MG_CR><MG_CR>Send, {F5}
```

```:タブ移動
[RB_↑→_]
G=RB_UR_
Default=;次のタブ<MG_CR><MG_CR>Send, ^{Tab}
```

```:新しいタブ
[RB_→←↓_]
G=RB_RLD_
Default=;新しいタブ<MG_CR><MG_CR>Send, ^t
```

```:タブ復元
[RB_↓←_]
G=RB_DL_
Default=;閉じたタブを復元<MG_CR><MG_CR>Send, +^t
```

```:タブ・ウィンドウを閉じる
[RB_↓→_]
G=RB_DR_
Default=;タブ・ウィンドウを閉じる<MG_CR><MG_CR>Send, !{F4}
ブラウザ=;タブを閉じる<MG_CR><MG_CR>Send, ^w
```

```:ウィンドウを閉じる
[RB_↑↓→_]
G=RB_UDR_
Default=;ウィンドウを閉じる<MG_CR><MG_CR>Send, !{F4}
```

```:アドレスバーへ移動
[RB_←↑_]
G=RB_LU_
Default=;Ctrl+L<MG_CR><MG_CR>Send, ^l
```

```:新規フォルダ作成
[RB_←↓_]
G=RB_LD_
Default=;新規フォルダ作成<MG_CR><MG_CR>Send, ^+N
```

```:リネーム
[RB_↓→↑_]
G=RB_DRU_
Default=;リネーム<MG_CR><MG_CR>Send, {F2}
```

```:全選択
[RB_↑→↓_]
G=RB_URD_
Default=;全選択<MG_CR><MG_CR>Send, ^a
```

```:1行選択
[RB_↑→↓→_]
G=RB_URDR_
Default=;1行選択<MG_CR><MG_CR>Send, {Home}{Shift Down}{End}{Shift Up}
```

```:コピー
[RB_←→_]
G=RB_LR_
Default=;コピー<MG_CR><MG_CR>Send, ^c
```

```:貼り付け
[RB_→←_]
G=RB_RL_
Default=;ペースト<MG_CR><MG_CR>Send, ^v
```

```:切り取り
[RB_→↓→_]
G=RB_RDR_
Default=;カット<MG_CR><MG_CR>Send, ^x
```

```:アンドゥ
[RB_←→←_]
G=RB_LRL_
Default=;アンドゥ<MG_CR><MG_CR>Send, ^z
```

```:タスク切り換え(AltTab)
[RB_↓←↓_]
G=RB_DLD_
Default=;タスク切り替え<MG_CR><MG_CR>Send, !{Tab}
```

```:タスク切り換え(保持)
[RB_↓←↓→_]
G=RB_DLDR_
Default=;タスク切り替え(保持)<MG_CR><MG_CR>Send, ^!{Tab}
```

```:Enter
[RB_↓↑_]
G=RB_DU_
Default=;Enter<MG_CR><MG_CR>Send, {Blind}{Enter}
```

```:Backspace
[RB_←↑→_]
G=RB_LUR_
Default=;Backspace<MG_CR><MG_CR>Send, {Blind}{Backspace}
```

```:Space
[RB_←↓←]
G=RB_LDL_
Default=;Space<MG_CR><MG_CR>Send, {Blind}{Space}
```

```:Delete
[RB_→↓←_]
G=RB_RDL_
Default=;Delete<MG_CR><MG_CR>Send, {Blind}{Delete}
```

```:Tab
[RB_→←↓→_]
G=RB_RLDR_
Default=;Tab<MG_CR><MG_CR>Send, {Blind}{Tab}
```

```:Escape
[RB_←↓→←↓→_]
G=RB_LDRLDR_
Default=;ESC<MG_CR><MG_CR>Send, {Blind}{ESC}
```

```:上書き保存
[RB_←↓→_]
G=RB_LDR_
Default=;上書き保存<MG_CR><MG_CR>Send,^s
```

```:カーソル移動(左)
[RB_W↑_]
G=RB_WU_
Default=;←<MG_CR><MG_CR>Send, {Blind}{Left}
```

```:タスクバー1番目のプログラムを起動
[MB_→_]
G=MB_R_
Default=;Win + 1<MG_CR><MG_CR>Send, #{1}
```

```:タスクバー2番目のプログラムを起動
[MB_→←_]
G=MB_RL_
Default=;Win + 2<MG_CR><MG_CR>Send, #{2}
```

```:タスクバー3番目のプログラムを起動
[MB_→←→_]
G=MB_RLR_
Default=;Win + 3<MG_CR><MG_CR>Send, #{3}
```

### 中級

```:ウィンドウを隣のモニタへ移動
[MB_↑↓_]
G=MB_UD_
Default=;ウィンドウを左のモニターへ<MG_CR><MG_CR>Send, #+{Left}
```

```:右の仮想デスクトップへ移動
[MB_↑→_]
G=MB_UR_
Default=;右の仮想デスクトップ<MG_CR><MG_CR>Send, ^#{Right}
```

```:デスクトップ一覧
[MB_→←↓_]
G=MB_RLD_
Default=;デスクトップ一覧<MG_CR><MG_CR>Send, #{Tab}
```

```:タスクマネージャ
[RB_←→↑_]
G=RB_LRU_
Default=;タスクマネージャー起動<MG_CR><MG_CR>Send, ^+{Escape}
```

```:PrintScreen
[RB_↓↑↓↑_]
G=RB_DUDU_
Default=;PrintScreen<MG_CR><MG_CR>Send, {PrintScreen}
```

### 上級

上級設定では、以下のサブルーチンを用います。

```:MG_User.ahk(拡張スクリプト)
;----- ユーザー定義サブルーチン	------------------------------------------------
; 共通
RemoveToolTip:
  SetTimer, RemoveToolTip, Off
  ToolTip,
Return

;-------------------------------------------------------------------------------

```

#### 音量変更

右クリックを押しながら→↓←↓と動かし、右クリックを離さないままホイール上下で音量変更できます。

```:音量変更
[RB_→↓←↓]
G=RB_RDLD
Default=;音量変更<MG_CR><MG_CR>step_vol := 2<MG_CR><MG_CR>MG_StopNavi()<MG_CR>Sleep, 500<MG_CR>KeyWait, RButton, Up<MG_CR>SetTimer, RemoveToolTip, -500<MG_CR>n := ""<MG_CR>vol := ""<MG_CR>step_vol := ""<MG_CR>Return<MG_CR><MG_CR><MG_CR>#If, step_vol!=""<MG_CR><MG_TAB>WheelUp::volume_change(step_vol)<MG_CR><MG_TAB>WheelDown::volume_change(-step_vol)<MG_CR>#If<MG_CR><MG_CR>volume_change(step) {<MG_CR><MG_TAB>SoundGet, vol_now<MG_CR><MG_TAB>Setformat, Float, 1.0<MG_CR><MG_TAB>vol_now += step<MG_CR><MG_TAB>If (vol_now < 0) {<MG_CR><MG_TAB><MG_TAB>vol_now := 0<MG_CR><MG_TAB>} Else If (vol_now > 100) {<MG_CR><MG_TAB><MG_TAB>vol_now := 100<MG_CR><MG_TAB>}<MG_CR><MG_TAB>SoundSet, vol_now<MG_CR><MG_TAB>ToolTip, 音量  :  %vol_now%<MG_CR><MG_TAB>Return<MG_CR>}<MG_CR><MG_CR>RemoveToolTip:<MG_CR>  SetTimer, RemoveToolTip, Off<MG_CR>  ToolTip,<MG_CR>Return
```

```:音量変更(コード部分)
step_vol := 2

MG_StopNavi()
Sleep, 500
KeyWait, RButton, Up
SetTimer, RemoveToolTip, -500
n := ""
vol := ""
step_vol := ""
Return

#If, step_vol!=""
  WheelUp::volume_change(step_vol)
  WheelDown::volume_change(-step_vol)
#If

volume_change(step) {
  SoundGet, vol_now
  Setformat, Float, 1.0
  vol_now += step
  If (vol_now < 0) {
    vol_now := 0
  } Else If (vol_now > 100) {
    vol_now := 100
  }
  SoundSet, vol_now
  ToolTip, 音量  :  %vol_now%
  Return
}

RemoveToolTip:
  SetTimer, RemoveToolTip, Off
  ToolTip,
Return
```

#### 透明度変更

右クリックを押しながら←↓→↓と動かし、右クリックを離さないままホイール上下で透明度変更できます。
コードはだいぶ汚いですが動くのでヨシ!

```:透明度変更
[RB_←↓→↓]
G=RB_LDRD
Default=;透明度調整<MG_CR><MG_CR>step := 20<MG_CR>MG_StopNavi()<MG_CR>Sleep, 500<MG_CR>KeyWait, RButton, Up<MG_CR>SetTimer, RemoveToolTip, -500<MG_CR>step := ""<MG_CR>Return<MG_CR><MG_CR>#If, step!=""<MG_CR><MG_TAB>WheelUp::transparency_change(step)<MG_CR><MG_TAB>WheelDown::transparency_change(-step)<MG_CR>#If<MG_CR><MG_CR>transparency_change(step) {<MG_CR><MG_TAB>WinGet, vT, Transparent, A<MG_CR><MG_TAB>If (vT == "") {<MG_CR><MG_TAB><MG_TAB>vT := 255<MG_CR><MG_TAB>} Else {<MG_CR><MG_TAB><MG_TAB>vT += step<MG_CR><MG_TAB><MG_TAB>If (vT > 255) {<MG_CR><MG_TAB><MG_TAB><MG_TAB>vT := 255<MG_CR><MG_TAB><MG_TAB>}<MG_CR><MG_TAB><MG_TAB>If (vT < 0) {<MG_CR><MG_TAB><MG_TAB><MG_TAB>vT := 0<MG_CR><MG_TAB><MG_TAB>}<MG_CR><MG_TAB>}<MG_CR><MG_TAB>WinSet, Transparent, %vT%, A<MG_CR><MG_CR><MG_TAB>;255段階を100段階に変換<MG_CR><MG_TAB>vT_label := Round(vT / 2.55)<MG_CR><MG_CR><MG_TAB>ToolTip, 透明度  :  %vT_label%<MG_CR><MG_TAB>Return<MG_CR>}<MG_CR>
```

```:音量変更(コード部分)
;透明度調整

step := 20
MG_StopNavi()
Sleep, 500
KeyWait, RButton, Up
SetTimer, RemoveToolTip, -500
step := ""
Return

#If, step!=""
	WheelUp::transparency_change(step)
	WheelDown::transparency_change(-step)
#If

transparency_change(step) {
	WinGet, vT, Transparent, A
	If (vT == "") {
		vT := 255
	} Else {
		vT += step
		If (vT > 255) {
			vT := 255
		}
		If (vT < 0) {
			vT := 0
		}
	}
	WinSet, Transparent, %vT%, A

	;255段階を100段階に変換
	vT_label := Round(vT / 2.55)

	ToolTip, 透明度  :  %vT_label%
	Return
}
```

#### トリガーの設定

トリガー設定を下のようにすることで、確認ダイアログなどの小さなウィンドウがアクティブなときに、右クリックによってアクティブ化されないため、マウスの位置を気にすることなく、ジェスチャーで`はい` `いいえ` `キャンセル`などを選択できます。

```:トリガー設定
[RB_]
G=RB_
Default=;アクティブ化処理<MG_CR>;指定サイズ未満でアクティブ化しない<MG_CR><MG_CR>minWidth := 500<MG_CR>minHeight := 200<MG_CR><MG_CR>WinGetPos, , , width, height, A<MG_CR>If ((width>minWidth) || (height>minHeight)) {<MG_CR><MG_TAB>MouseGetPos, , , underMouseID1<MG_CR><MG_TAB>WinActivate, ahk_id %underMouseID1%<MG_CR>}<MG_CR>
```

```:トリガー設定(コード部分)
;アクティブ化処理
;指定サイズ未満でアクティブ化しない

minWidth := 500
minHeight := 200

WinGetPos, , , width, height, A
If ((width>minWidth) || (height>minHeight)) {
	MouseGetPos, , , underMouseID1
	WinActivate, ahk_id %underMouseID1%
}
```

## その他

### 画面内の一部のみでジェスチャを無効にする

XMindのマッピングエリア内で右ドラッグを利用したいため、そのエリアのみMGLを無効化したくなりました。
次のように設定します。

まず、トレイアイコンを右クリックして表示されるメニューから「拡張スクリプト編集」を選択し、`MG_Edit.ahk用`の部分に次のように入力します。

```autohotkey:MG_User.ahk
; ClassNNが一致したときにジェスチャーを無効化するための関数
; ただし無変換押下時は無効化しない
; 「無効にする」=「Return 1」

compareClassNN(set_class_nn) {
  MouseGetPos, , , , got_class_nn

  If (GetKeyState("vk1D", "P")) {
    Return 0
  }

  If (set_class_nn==got_class_nn) {
    Return 1
  }

  Return 0
}
```

そして、`MGLの設定画面`>`ターゲット`>`ジェスチャー無効`に、`カスタム条件式`として`compareClassNN("classNNの値")`を指定します。
classNNはWindowsSpyから確認できます。

## まとめ

`MouseGestureL`は`AutoHotkey`と同様に"玄人向け"ではありますが、ここまで設定してしまえば快適に使えます。