フォーカスの移動を禁止するには?

解決


エステ丸  2008-10-07 19:42:47  No: 69094

エステ丸と申します。初めて質問させていただきます。

環境:VisualStdio.net2005 VC++ MFC

内容:
仕事で作成していますダイアログですが、少し特殊で入力値の
エラーチェックを各コントロールのロストフォーカス時に行い、
NGであればメッセージを出して再度そのコントロールにフォーカスを
セットする仕様です。

現状、TABもしくはマウスで他のコントロールにフォーカスを移動すると、
一旦次のコントロールに移動してしまい、そこのエラーチェックを行って
最初のコントロールに戻ります。(メッセージが2回でます)
フォーカスを次のコントロールに移動させたくないのですが
良い方法はありませんでしょうか?

※エディット1でエラーがでた場合一旦エディット2に移ってエディット1に戻ってしまう。
    ┏━━━━┓①エラーチェック
    ┃ エディット1┃④セットフォーカス
    ┗━━━━┛
    ┏━━━━┓②セットフォーカス
    ┃ エディット2┃③エラーチェック
    ┗━━━━┛

処理は、各コントロールのOnEnKillfocus***イベントハンドラ内にて
エラーチェックを行うようにし、NGならセットフォーカスしています。

void CDlg::OnEnKillfocus***()
{
    // Error Check
    if( エラーならば )
    {
        AfxMessageBox("Error");
        // 今のコントロールにフォーカスセット
        m_Edit.SetFoucus()
    }
  // 正しい値ならOK
}

TABのみであればいろんな方法がありますが、マウスも使用しますので
頭を悩ませています。ご教授の方宜しくお願い致します。


rin  2008-10-07 21:04:13  No: 69095

まだ入力の必要の無いエディットボックスを
「EnableWindow」で封じておく

入力の必要がでたときに、封印をとき、そこにむかってSetFocusする


エステ丸  2008-10-07 23:59:20  No: 69096

rin様

ありがとうございます。

void CDlg::OnEnSetfocus***()
{
    // まだ入力の必要の無いエディットボックスを「EnableWindow」で封じておく
}

void CDlg::OnEnKillfocus***()
{
    // Error Check
    if( エラーならば )
    {
        AfxMessageBox("Error");
        // 今のコントロールにフォーカスセット
        m_Edit.SetFoucus()
    }
// 正しい値ならOK
// すべてのエディットボックスをEnableWindow(TRUE)で解除する
}

パッと思いついたのがこんなやりかたでしょうか。
ただ、他の項目が無効表示(グレーアウト)されてしまうので客先に
「移動できないように見えるからNG!」と言われないか心配です。

交渉はしてみますが、もし他の方法をご存知でしたら教えていただけませんでしょうか?

宜しくお願いします。


gak  2008-10-08 01:15:46  No: 69097

>> もし他の方法をご存知でしたら教えていただけませんでしょうか?
単純にフラグで管理とか。

----------------
class CDlg {
    bool ignore_;
    CDlg() : ignore_(false) {}
}

void CDlg::OnEnKillfocus***()
{
    // Error Check
    if (!ignore_) {
        if( エラーならば ) {
            ignore_ = true;
            AfxMessageBox("Error");
            // 今のコントロールにフォーカスセット
//          m_Edit.SetFoucus()
            GotoDlgCtrl(&m_Edit);
            ignore_ = false;
        }
    }
}
----------------


2リットル  2008-10-08 04:10:18  No: 69098

Vista、VC2008で試したところ、上記②のセットフォーカスは呼ばれないようでした。
つまり、エディットボックス2はSETFOCUSなしでKILLFOCUSが呼ばれてました。

VC2005では異なるのかもしれませんが、次のようなコードを試してみたらどうでしょう?

void CDlg::OnEnKillfocus***()
{
    // フォーカスが自身にない場合はスルー
    // CWnd::GetFocus()の戻り値チェックはGetSafeHwnd()に関しては不要
    if (CWnd::GetFocus()->GetSafeHwnd() != m_edit.GetSafeHwnd()) {
        return;
    }

    // Error Check
    if( エラーならば )
    {
        AfxMessageBox("Error");
        // 今のコントロールにフォーカスセット
         m_Edit.SetFoucus()
    }
  // 正しい値ならOK
}


エステ丸  2008-10-09 00:06:14  No: 69099

2リットル様

サンプルありがとうございました。

>> Vista、VC2008で試したところ、上記②のセットフォーカスは呼ばれな
>> いようでした。
>> つまり、エディットボックス2はSETFOCUSなしでKILLFOCUSが呼ばれてました。
テストプロジェクトを作成しまして試しましたがエディットボックス2
はSETFOCUSがよばれました。教えていただきました、サンプルコードも
試しましたが、フォーカスはエディット2にあるのに入力するとエディット
ボックス1に値が入るというよくわからない結果となりました。
MFCはやはり環境によって差異があるようです。

gak様

APIやMFCに頼らずフラグ管理となっているサンプルコードですが試させて
いただきました所、思うような結果が得られました。
感謝いたします。

皆様、親切に対応していただきありがとうございました。
今後とも宜しくお願いします。


エステ丸  2008-10-09 00:07:26  No: 69100

解決致しました。


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

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






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