トップ回答者
TextBox Multiline 時にコントロール移動しないのは何故。

質問
-
例えば、下記の様な何かキーを押されると次のコントロールに移動するコードがあるとします。
private void Form1_Load(object sender, EventArgs e)
{
this.KeyDown += new KeyEventHandler(Form1_KeyDown);
}private void Form1_KeyDown(object sender, System.Windows.Forms.KeyEventArgs e)
{
this.SelectNextControl(this.ActiveControl, true, true, true, true);
}このときに、TextBoxでMultilineがtrueの時に、
上下矢印キーと[PagePu][PageDown]キーでコントロールが移動しません。
左右矢印キーでは移動します。
TextBoxの派生では、いったんLostFocusが発生するので、
どこかに行こうとしているみたいなのですが。
・何故なのでしょうか。
・また、移動させるにはどの様にすれば可能でしょうか。
何か情報をお持ちの方がいましたら宜しくお願いします。
回答
-
taku2888 さん、こんにちは
ダッチです。まずフォームの KeyPreview に true が設定されているものとして話を進めさせていただきます。
taku2888 さんからの引用 ・何故なのでしょうか。
Form1_KeyDown の処理で e.Handled に true を設定していないためです。
これではフォームの KeyDown イベントの処理が行われた後に textbox の KeyDown イベントの処理も行われてしまいます。おそらく textbox が ↑ or ↓ キーを入力された場合に自身にフォーカスを設定していたりするのかもしれません。
taku2888 さんからの引用 ・また、移動させるにはどの様にすれば可能でしょうか。 Form1_KeyDown の処理で e.Handled = true とすることでフォームで KeyDown イベントを処理したことになり、 textbox の KeyDown イベントは発生しなくなります。これで textbox にフォーカスが戻るという現象は発生しなくなると思います。
taku2888 さんがやりたいことで一番気になるのが、本当に textbox でカーソルキーを入力したときにフォーカスを遷移させていいのかということです。なにか実験のためであればわかりますが、本当にフォーカスを遷移させたいのであれば、ユーザは使い図らいと思うかもしれません。
またフォームに配置されたボタンにフォーカスがある場合に、カーソルキーを入力してもフォームの KeyDown イベントは発生しません。これは問題ありませんか。
やりたいことの背景がわかれば、他の方法なども提案できると思います。
すべての返信
-
早い返信ありがとうございます。
> 上下キー等は行の移動になるので、Multilineの場合は無理です。
左右キーは文字の移動ですが、他コントロールに移るのはどうしてでしょうか。
> するのであれば、WndProc辺りをオーバーライドしてキャレット位置が1行目or末行なら
今、現在別処理にて回避してますが、
どうして Form の KeyDown 内からであると元に戻るのかと思い投稿しました。
オーバーライドでも、Formが先にKeyDownを受け、その後TextBoxに行き
LostFocusも発生するのに、どうして元のTextBoxに戻るのか、
戻る原因が不明です。
いったい、どこで戻されるのでしょうか。
ちなみに、
オーバーライドOnKeyDown内から、FormにSelectNextControlを送っても無理でした。
試しに、
OnGotFocus
OnLostFocus
OnKeyDown
OnEnter
を全てスルーしても移動できませんでした。
-
taku2888 さん、こんにちは
ダッチです。まずフォームの KeyPreview に true が設定されているものとして話を進めさせていただきます。
taku2888 さんからの引用 ・何故なのでしょうか。
Form1_KeyDown の処理で e.Handled に true を設定していないためです。
これではフォームの KeyDown イベントの処理が行われた後に textbox の KeyDown イベントの処理も行われてしまいます。おそらく textbox が ↑ or ↓ キーを入力された場合に自身にフォーカスを設定していたりするのかもしれません。
taku2888 さんからの引用 ・また、移動させるにはどの様にすれば可能でしょうか。 Form1_KeyDown の処理で e.Handled = true とすることでフォームで KeyDown イベントを処理したことになり、 textbox の KeyDown イベントは発生しなくなります。これで textbox にフォーカスが戻るという現象は発生しなくなると思います。
taku2888 さんがやりたいことで一番気になるのが、本当に textbox でカーソルキーを入力したときにフォーカスを遷移させていいのかということです。なにか実験のためであればわかりますが、本当にフォーカスを遷移させたいのであれば、ユーザは使い図らいと思うかもしれません。
またフォームに配置されたボタンにフォーカスがある場合に、カーソルキーを入力してもフォームの KeyDown イベントは発生しません。これは問題ありませんか。
やりたいことの背景がわかれば、他の方法なども提案できると思います。
-
一度、以下を読まれると参考になると思います。
Windowsアプリケーションで方向キーなどの特殊キーを処理するには?
http://www.atmarkit.co.jp/fdotnet/dotnettips/241windlgkey/windlgkey.html -
indigo-x さん
ダッチさん
trapemiyaさんありがとうございます。
Formで e.Handled = true ; にていけました。
オーバーライドした、OnKeyDownでFormにSelectNextControlを送った後に、
e.Handled = true ; しても変化がなかったので、
別の問題と思ってしまいました。
お手数をおかけました。
また、宜しくお願いします。
追記、
インターフェースの件ですが、MulitilineやsinglelineのTextBoxが複数あり、
何も、編集を加えない時は移動するようにするためです。
Mulitiline部分は、たまにしか編集がないため。
既存のシステムVC++ -> C# 移植で同様のインターフェース仕様要望のため・・・