Quote:
Originally posted by gstercken
I didn't say it is the only way.
You do by implication. You insist that any other solution is unacceptable.
Quote:
Originally posted by gstercken
You can even do data validation in PreTranslateMessage(), for that matter.
You are being unrealistic, which is consistent with insisting that any other solution is unacceptable.
Quote:
Originally posted by gstercken
I just pointed out that DDV was the way MFC provides for data validation, and that DoDataExchange() is a virtual function designed specifically for that purpose - so why not use it? Validation in OnOK is what I often see beginners doing who haven't yet learnt about the DDX/DDV mechanism.
These are critical issues. Specifically, the question is whether DDV is "the" way or "a" way. Another question is whether validation in OnOK is always a bad choice.
Quote:
Originally posted by gstercken
However, the place to do this test is, by design, DoDataExchange(), and it will work regardless of whether the user clicks 'OK', 'Apply' or switches to another property page.
Again, you insist that DoDataExchange is the only acceptable solution.
Quote:
Originally posted by gstercken
Even if it was only one line of code (it is not, as you first have to find the offending control(s), set the focus, restore the selection etc.), that single line alone would still be one line too much. Let alone the several lines, message map entry etc. needed to implement OnOK. DoDataExchange(), in contrast, need not be added: It's already there in wizard-generated dialog code.
You are implying that it is not normal to process IDOK (override OnOK).
Quote:
Originally posted by gstercken
But one of the points in software design is to try to minimize the probability of those problems arising - not to create them artificially.
You are saying that a good programmer will overlook obvious changes when changing a program. I think it is matter of personal preference whether that is important.
Quote:
Originally posted by gstercken
You're right, there are none. As said above, you have to code them yourself (exactly the way you did in the code you posted). My point was only (and still is) that the most obvious place to do this, according to the design of MFC, is DoDataExchange, not OnOK.
Again, you insist that DoDataExchange is the only acceptable solution.
Quote:
Originally posted by gstercken
I thought I pointed out why OnOK() is not an acceptable alternative. Besides the problems mentioned regarding possible future extensions towards modeles dialogs or property pages, it also requires you to locate the offending control, set the focus, set the selection, and prevent the dialog from being closed. CDataExchange::Fail() already does all this for you. And IMO, any solution which requires rewriting code which is already there for you to be used is not an acceptable alternative.
Again, you insist that DoDataExchange is the only acceptable solution. The advantages of DoDataExchange that you describe here are a matter of personal preference.
The following are samples of doing validation in OnOk. Are these not examples of acceptable code? Are these things that a good MFC programmer would never do?
Code:
void CSpeakNDlg::OnOK() {
CString result;
InputEdit().GetWindowText(result);
if (result != m_targetWord) {
PlaySound(IDSOUND_INCORRECT);
AfxMessageBox(IDS_TRY_AGAIN);
return;
}
PlaySound(IDSOUND_CORRECT);
AdvanceLesson();
}
Code:
void CSpinEditDlg::OnOK() {
int values[NUM_EDIT];
UINT nID = 0;
BOOL bOk = TRUE;
for (int i = 0; bOk && i < NUM_EDIT; i++) {
nID = IDC_EDIT_MIN + i;
values[i] = GetDlgItemInt(nID, &bOk);
}
if (!bOk) {
// report illegal value
CString str;
str.LoadString(IDS_ILLEGAL_VALUE);
MessageBox(str);
CEdit& badEdit = *(CEdit*)GetDlgItem(nID);
badEdit.SetSel(0, -1);
badEdit.SetFocus();
return; // don't end dialog
}
EndDialog(IDOK);
}
Code:
void CCustListDlg::OnOK() {
int nIndex = m_colors.GetCurSel();
if (nIndex == -1) {
CString str;
str.LoadString(IDS_PLEASE_SELECT_COLOR);
MessageBox(str);
m_colors.SetFocus();
return;
}
DWORD color = m_colors.GetItemData(nIndex);
EndDialog(IDOK);
}