CComboBox DDX_CBString行为令人困惑 [英] CComboBox DDX_CBString behavior confusing
问题描述
我在对话框中使用ComboBox控件为用户提供一些有用的值(例如:10; 20; 100; 400; 800),但如果需要的话,让用户插入确切的值.
I use a ComboBox control in a Dialog to give the user some useful values (Ex: 10; 20; 100; 400; 800) but let the user insert the exact value if needed.
经过很长时间我发现了什么: 如果我在组合框中键入值 40 ,则组合框在UpdataData()总是 400 之后返回. :(( 更好的值为 39 或 41 ,没有问题.
What I have discovered after long time: If I type the value 40 in the Combobox, the Combobox returns after UpdataData() always 400. :(( Ohterwards with the values 39 or 41, there is no problem.
这不是我和用户所期望的行为.
当我键入一个值时,ComboBox应该使用此值,如果从下拉菜单中选择,请使用此值.
That's is not the behaviour what I and the user expected.
When I type a value, ComboBox should take this value, if select from the dropdown Menue, take this.
我现在看到这种行为是由DDX_CBString给出的.
I see now this behaviour is given by DDX_CBString.
我必须编写自己的DDX_CBString还是其他方法?
Do I have to write my own DDX_CBString or is there an another approach?
代码:
void CTestDialog::DoDataExchange(CDataExchange* pDX)
{
CDialogEx::DoDataExchange(pDX);
DDX_Control(pDX, IDC_IFBANDWIDTH, m_cIFBandWidth);
DDX_CBString(pDX, IDC_IFBANDWIDTH, m_sIFBandWidth); // Bahavior confusing
}
BOOL CTestDialog::OnInitDialog()
{
CDialogEx::OnInitDialog();
m_cIFBandWidth.ResetContent();
m_cIFBandWidth.AddString(_T("10"));
m_cIFBandWidth.AddString(_T("20"));
m_cIFBandWidth.AddString(_T("100"));
m_cIFBandWidth.AddString(_T("400"));
m_cIFBandWidth.AddString(_T("800"));
return TRUE; // return TRUE unless you set the focus to a control
// EXCEPTION: OCX Property Pages should return FALSE
}
void CTestDialog::OnBnClickedApply()
{
UpdateData(TRUE); // m_sIFBandWidth now 4 ok!
UpdateData(FALSE); // m_sIFBandWidth still 4, but control show 400, so the next OnOk() or Apply() take this value. Wrong!
}
推荐答案
我通过修改DDX_CBtring解决了这个问题.
I solved this with modify the DDX_CBtring.
void DDX_CBString_Normal(CDataExchange* pDX, int nIDC, CString& value)
{
..
if (pDX->m_bSaveAndValidate)
{
..
}
else
{
// Behaviour as we expect: Type a value and keep it
// Select it form dropwon, or take the value the user type it
AfxSetWindowText(hWndCtrl, value);
return;
/* Disable original MS behavior
// set current selection based on model string
if (::SendMessage(hWndCtrl, CB_SELECTSTRING, (WPARAM)-1,
(LPARAM)(LPCTSTR)value) == CB_ERR)
{
// just set the edit text (will be ignored if DROPDOWNLIST)
AfxSetWindowText(hWndCtrl, value);
}
*/
}
}
如果有人有其他方法,请告诉我.
If anyone has an another aproach let me know.
这篇关于CComboBox DDX_CBString行为令人困惑的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!