読者です 読者をやめる 読者になる 読者になる

blechmusikの日記

キー・カスタマイズ・ソフトウェア "DvorakJ" の覚え書きをはじめとして様々なことを書いています。

右Ctrl と [Back Space] で [Ctrl] + [Back Space] を発行する際の問題点と改善策

AutoHotkey DvorakJ

はじめに

DvorakJ の使用中にATOKで確定アンドゥを実行すると変換中の文字列が正しく表示されなくなる、との報告を受けた*1。これは2010年末にも受けた不具合の症状であって*2、それには当時対処した覚えがあるのだが、現行の DvorakJ において再び問題が現れたので、また取り組まねばならなくなった。DvorakJ では、順に打鍵する配列に対応する都合上、[Ctrl] + [Back Space] を入力したら [Ctrl] + [Back Space] を発行し、それからいくつかの処理を行っている。これらの一連の処理のどれかと、ATOKの確定アンドゥの処理が整合的ではないようなのだ。
調べた結果、ATOKの確定アンドゥのキーバインド [Ctrl] + [Back Space] が正しく動かない恐れがあるのは、DvorakJ のみならず AutoHotkey のスクリプト全般であることが分かった。なお、ここでいう AutoHotkey とは AutoHotkey_L の最新版のことである。
このエントリーでは、 [Ctrl] + [Back Space] を AutoHotkey で発行する際の問題点を検証し改善策を提示する。その際、使用方法 - AutoHotkeyJpのKey history and script infoの表記にならって、キーの発行処理を説明しよう。

検証

^sc00Eのとき

まずは ^sc00E で [Ctrl] + [Back Space] を発行する、すなわち Ctrl を押しながら sc00E にあたるキー、つまり Back Space を押せば [Ctrl] + [Back Space] を発行するという処理を作成してみよう。

^sc00E::
	send,^{bs}
	return

これを実行したうえで [左 Ctrl] + [Back Space] を入力するとこうなる。

VK  SC	Type	Up/Dn	Elapsed	Key
--------------------------------------------
A2  01D	 	d	0.92	LControl       	
08  00E	h	d	0.14	Backspace      	
08  00E	i	d	0.00	Backspace      	
08  00E	i	u	0.00	Backspace      	
08  00E	s	u	0.11	Backspace      	
A2  01D	 	u	0.09	LControl    

問題はなさそうだ。
他方、[右 Ctrl] + [Back Space] を入力すると問題が生じる。

VK  SC	Type	Up/Dn	Elapsed	Key
--------------------------------------------
A3  11D	 	d	0.86	RControl       	
08  00E	h	d	0.16	Backspace      	
A2  01D	i	d	0.05	LControl       	
A3  11D	i	u	0.00	RControl       	
08  00E	i	d	0.00	Backspace      	
08  00E	i	u	0.00	Backspace      	
A2  01D	i	u	0.00	LControl       	
A3  11D	i	d	0.00	RControl       	
08  00E	s	u	0.08	Backspace      	
A3  11D	 	u	0.00	RControl   

[左 Ctrl] を仮想的に押し下げてから [右Ctrl] を仮想的に押し上げて、[Back Space] を入力し、[左 Ctrl] を仮想的に押し上げてから [右Ctrl] を仮想的に押し下げる。[Back Space] のキーを発行するときには、[右 Ctrl] ではなくて [左 Ctrl] を一緒に発行しているのだ。言い換えると、修飾キーを不要にも押し下げたり押し上げたりしているということである。
キーフックを左右の Ctrl ではなくてどちらか一方に限定すると、キーの発行処理はどうなるだろうか。つぎにこの点を検証してみる。

<^sc00Eのとき

ホットキー - AutoHotkeyJpの「右のモディファイアキーを使用(NT系専用)」「左のモディファイアキーを使用(NT系専用)」を使用することで、[Ctrl] + [Back Space] の挙動を確認してみよう。

<^sc00E::
	send,^{bs}
	return

これを実行したうえで [左 Ctrl] + [Back Space] を入力するとこうなる。

VK  SC	Type	Up/Dn	Elapsed	Key
--------------------------------------------
A2  01D	 	d	1.97	LControl       	
08  00E	h	d	0.16	Backspace      	
08  00E	i	d	0.00	Backspace      	
08  00E	i	u	0.00	Backspace      	
08  00E	s	u	0.11	Backspace      	
A2  01D	 	u	0.14	LControl

やはりこれは問題が生じない。
では [右Ctrl] + [Back Space] はどうだろうか。それらにはキーフックを適用しないので、問題は生じないのではないだろうか。

VK  SC	Type	Up/Dn	Elapsed	Key
--------------------------------------------
A3  11D	 	d	0.36	RControl       	
08  00E	#	d	0.13	Backspace      	
08  00E	 	u	0.14	Backspace      	
A3  11D	 	u	0.02	RControl   

思った通りの結果が出た。当然のことだが、[左Ctrl] + [Back Space] にキーフックを限定しているのだから、[右 Ctrl] + [Back Space] には何ら影響が及ばない。

>^sc00Eのとき

問題は [右 Ctrl] + [Back Space] にキーフックを適用するときだ。

>^sc00E::
	send,^{bs}
	return

まず[左Ctrl] + [Back Space] の挙動を見てみよう。

VK  SC	Type	Up/Dn	Elapsed	Key
--------------------------------------------
A2  01D	 	d	0.92	LControl       	
08  00E	#	d	0.16	Backspace      	
08  00E	 	u	0.09	Backspace      	
A2  01D	 	u	0.03	LControl  

このときは上記と同様に問題は生じない。
他方、[右Ctrl] + [Back Space] だとやはり問題が生じた。

VK  SC	Type	Up/Dn	Elapsed	Key
--------------------------------------------
A3  11D	 	d	0.98	RControl       	
08  00E	h	d	0.16	Backspace      	
A2  01D	i	d	0.00	LControl       	
A3  11D	i	u	0.00	RControl       	
08  00E	i	d	0.00	Backspace      	
08  00E	i	u	0.00	Backspace      	
A2  01D	i	u	0.00	LControl       	
A3  11D	i	d	0.00	RControl       	
08  00E	s	u	0.11	Backspace      	
A3  11D	 	u	0.03	RControl

修飾キーを自動的に復元する処理がうまくいっていないと言える。

対策

そこで、Send / SendRaw / SendEvent / SendInput / SendPlay - AutoHotkeyJpに書いてある {blind} という設定を用いて、修飾キーを自動的に復元しないようにする。
^sc00Eのときの処理はこう書くことが出来る。

^sc00E::
	send,{blind}{bs}
	return
VK  SC	Type	Up/Dn	Elapsed	Key
--------------------------------------------
A3  11D	 	d	4.01	RControl       	
08  00E	h	d	0.12	Backspace      	
08  00E	i	d	0.00	Backspace      	
08  00E	i	u	0.00	Backspace      	
08  00E	s	u	0.14	Backspace      	
A3  11D	 	u	0.01	RControl  

問題は生じないようだ。
では>^sc00Eのときはどうだろうか。

>^sc00E::
	send,{blind}{bs}
	return
VK  SC	Type	Up/Dn	Elapsed	Key
--------------------------------------------
A3  11D	 	d	4.85	RControl       	
08  00E	h	d	0.16	Backspace      	
08  00E	i	d	0.06	Backspace      	
08  00E	i	u	0.00	Backspace      	
08  00E	s	u	0.08	Backspace      	
A3  11D	 	u	0.05	RControl    

こちらでも問題は生じていない。

おわりに

このエントリーをまとめればつぎのように言える。すなわち、AutoHotkey で [右Ctrl] + [Back Space] を入力して [Ctrl] + [Back Space] を発行する際、必要が無いのに [右Ctrl] を仮想的に押し上げたり押し下げてしまうので、send の内容として{blind}を指定する必要がある。

後日追記

無変換キーの発行に関わる処理について、以下のエントリーを公開した。