.NET 時代的 ComboBox 內建 AutoCompleteMode,但 VC6 需自行實作。利用 CBN_EDITCHANGE 訊息在使用者輸入時即時比對下拉清單,若找到相符項目則自動選取並高亮剩餘文字,提供類似自動完成的體驗。
IDC_COMBO_USER)加入 CBN_EDITCHANGE 訊息處理函式 OnEditchangeComboUser。
void CMyDlg::OnEditchangeComboUser()
{
CString strInput;
m_comboUser.GetWindowText(strInput); // 取得目前編輯框文字
int nLen = strInput.GetLength();
if (nLen == 0) return;
// 在下拉清單中尋找以 strInput 開頭的項目
int nIndex = m_comboUser.FindString(-1, strInput);
if (nIndex != CB_ERR) {
// 找到 → 選取該項目,編輯框會自動填入完整文字
m_comboUser.SelectString(-1, strInput);
// 高亮「補全」的部分,方便使用者繼續輸入或接受
m_comboUser.SetEditSel(nLen, -1);
}
// 未找到則不處理,保留使用者原始輸入
}
| 函式 | 用途 |
|---|---|
FindString(nStartAfter, lpszString) | 從索引 nStartAfter 之後尋找以 lpszString 開頭的項目,回傳索引或 CB_ERR。 |
SelectString(nStartAfter, lpszString) | 選取並將完整項目文字複製到編輯框。 |
SetEditSel(nStartChar, nEndChar) | 設定編輯框選取範圍;-1 表結尾。此處高亮補全部分。 |
GetLBText。FindString 可能造成輸入延遲,建議改用虛擬清單或預先建立 Trie 索引。
void CMyDlg::OnEditchangeComboUserEx()
{
CString strInput;
m_comboUser.GetWindowText(strInput);
if (strInput.IsEmpty()) return;
int nCount = m_comboUser.GetCount();
for (int i = 0; i < nCount; ++i) {
CString item;
m_comboUser.GetLBText(i, item);
if (item.Find(strInput) != -1) { // 包含關係
m_comboUser.SetCurSel(i);
m_comboUser.SetEditSel(strInput.GetLength(), -1);
break;
}
}
}