2

OnCharとOnKeydownを上書きして、特定の種類の文字が編集コントロールに挿入されないようにブロックしようとしています。複数のポイントをブロックしようとしています'。' そして数ではないものは何でも。

まず、すでに「。」があるかどうかを確認します。ダイアログクラスで定義された変数をfalseに設定することにより、フォーカスがある編集コントロールで:

void MyMainDialog::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags)
{
  CWnd * eb1 = GetDlgItem(IDC_EDIT1); //Reference dimension 1 box;
  CWnd * eb2 = GetDlgItem(IDC_EDIT2); //Reference dimension 2 box
  CWnd * eb3 = GetDlgItem(IDC_EDIT3); //Reference dimension 3 box
  CString temp;

  CWnd * focusedHand = MyMainDialog::GetFocus(); //Reference edit box being focused

  if(focusedHand == eb1)
  {
    eb1->GetWindowTextA(temp);
    if(temp.Find('.') != -1)
      checkPoint = true;
    else
      checkPoint = false;
  }
  else if(focusedHand == eb2)
  {
    eb2->GetWindowTextA(temp);
    if(temp.Find('.') != -1)
      checkPoint = true;
    else
      checkPoint = false;
  }
  else if(focusedHand == eb3)
  {
    eb3->GetWindowTextA(temp);
    if(temp.Find('.') != -1)
      checkPoint = true;
    else
      checkPoint = false;
  }

  CDialogEx::OnKeyDown(nChar, nRepCnt, nFlags);
}

OnCharで、入力されている文字をチェックしています。それがポイントであるかどうかの数ではないが、すでにポイントがあった場合、私はCDialogからOnCharを呼び出さない:

void MyMainDialog::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags)
{
   if(nChar == '.' && checkPoint == false) //Is a point and there is no other point
  {
     CDialogEx::OnChar(nChar, nRepCnt, nFlags);   
  }

  if((nChar < '0' || nChar > '9')) //Is not a number
  {
     //Show message to user
  }
  else //Is a number
  {
    CDialogEx::OnChar(nChar, nRepCnt, nFlags);
  }
}

さて、私のコードは機能していません。コンパイルされ、エディットコントロールに入力してもクラッシュしませんが、何もしません。それを上書きする正しい方法は、CDialogEx :: OnChar()の呼び出しを防ぐことなのか、それとも表示される文字がnullになるようにnChar=0にする必要があるのか​​疑問に思っています。しかし、それに加えて、OnCharで表示しようとしているメッセージも表示されていません。つまり、MyMainDialog :: OnChar()が呼び出されていません。代わりにCDialogEx::OnChar()を上書きする必要がありますか?

ご清聴ありがとうございました

4

3 に答える 3

2

私は解決策を見つけました。コードが私のアプリケーションで効果を発揮していないように見える理由は、MyMainDialogにのみ効果を発揮しているためです。Edit Controlに入力すると、OnChar()がCEditから呼び出されるため、インターセプトする必要があります。CEdit :: OnChar()を上書きすることはできません。解決策は、CEditから派生するクラスを作成し、そのクラスからOnChar()をインターセプトすることです。また、編集コントロールを操作するには、CEditの代わりにクラスを使用する必要があります。

その後、私のコードは次のように再定式化されました。

OnChar():

void CustomEdit::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags)
{
  if(nChar == '.' && checkPoint == true) //Is a point and there is already a point
  {
     //Show message  
  }
  else if(nChar == '.' && checkPoint == false) //Is a point but there is no point
  {
    CEdit::OnChar(nChar, nRepCnt, nFlags);
  }

  if((nChar < '0' || nChar > '9') && nChar != 8) //Is not a number or backspace
  {
     //Show message
  }
  else //Valid
  {
     CEdit::OnChar(nChar, nRepCnt, nFlags);
  }
}

OnKeyDown():

void CustomEdit::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags)
{
  CString temp;

  this->GetWindowTextA(temp);
  if(temp.Find('.') == -1)
    checkPoint = false; //There is no point
  else
    checkPoint = true; //There is a point

  CEdit::OnKeyDown(nChar, nRepCnt, nFlags);
}

これが同様の質問を持つ人に役立つことを願っています。ちなみに、インターネットにはたくさんのクラスや自動化されたソリューションがありますが、私はこれを学習目的で手動で行いました。

于 2012-05-11T06:24:39.223 に答える
2

はるかに簡単な方法は、OnChange イベントで入力を処理することです。

// do not add numbers; ascci numbers is 48 - 57
if ((m_strYOURCONTROL[m_strYOURCONTROL.GetLength() - 1]) > 47 && 
         m_strYOURCONTROL[m_strYOURCONTROL.GetLength() - 1]) < 58)
{
    m_strYOURCONTROL = m_strYOURCONTROL.Mid(0, m_strYOURCONTROL.GetLength() - 1);
}

これは数字を許可しません。この実装により、編集ボックスへの入力をより簡単に処理できます

于 2011-12-09T10:05:51.427 に答える
1

別の解決策は、 PreTranslateMessageWM_CHARで以前に処理することです。

于 2011-12-08T13:02:20.937 に答える