Visual Studio MFC zmień tekst w kontrolce edycji podczas pisania / dynamicznie

Dec 04 2020

Próbuję skonfigurować aplikację MFC C ++ w programie Visual Studio 2019, która modyfikuje tekst użytkownika podczas pisania.

Obecny układ to 2 przyciski opcji,

ID = rdbOn(ustawione na Group = True, z wartością int zmienna m_isOn= 1)

ID = rdbOff, m_isOnwartość będzie =0

i 1 Kontrola edycji, ID = txtInputBox, ze CStringzmienną Wartośćm_inputString

Obecnie do testowania widzę, jak działałby przycisk po kliknięciu, wymagałoby czegoś takiego jak poniżej i tylko SetDlgItemTextwyniku. Ale stanie się to po wpisaniu, a nie w GDY piszą.

void Onsomebtnclick()
{
    //convert CString to String of m_inputString
    //do some string manipulation
    //convert back to CString
    //SetDlgItemText(txtInputBox, result)    
}

Aktualizacja: zabrałem się EN_CHANGEdo pracy Udało mi się rozpocząć EN_CHANGEpracę z sugestią flagi od użytkownika @GoGoWorx. Jednak teraz mam tylko mały problem, że kursor wraca na początek kontrolki edycji txtInput.
Czytam o używaniu a, CEdit::SetSelale nie wiem, jak używać tego bezpośrednio w moim kodzie. Próbowałem kontrolować MFC CEdit, umieszczając kursor na końcu ciągu po SetWindowText

someDlg::someFunction()
{
    //some logic stuff to get a result string
    SetDlgItemText(txtInputBox, result);
    //need it to set the cursor to the end
    //I tried these, but it didn't recognize (expression must have class type?)
    //txtInputBox.SetSel(0, -1);
    //txtInputBox.SetSel(-1);
}

Odpowiedzi

3 GoGoWorx Dec 04 2020 at 08:04

Wygląda na to, że musisz użyć ON_EN_CHANGEpowiadomienia mapy wiadomości (wywoływanego po zaktualizowaniu kontrolki na przykład z powodu wpisania lub wklejenia)

BEGIN_MESSAGE_MAP(CMyDialog, CDialog)   
    ON_EN_CHANGE(IDC_EDIT_CONTROL, &CMyDialog::OnEnChangeEditControl)
END_MESSAGE_MAP()

void CMyDialog::OnEnChangeEditControl()
{
   // Copy or call your Onsomebtnclick() here
}

Nie jestem pewien, czego używasz dla identyfikatora liczbowego dla kontrolki edycji, ponieważ są to zwykle definicje wielkimi literami - zamień IDC_EDIT_CONTROLpowyżej na swoją definicję (prawdopodobnie txtInputBox, ale znowu, zwykle są to duże litery , więc nie jestem pewien ).

Zmień także CMyDialognazwę swojej klasy dialogowej.

Zauważ, że używamy tutaj programu ON_EN_CHANGEobsługi mapy wiadomości zamiast ON_EN_UPDATE, ponieważ ON_EN_CHANGEwiadomość jest wysyłana po zaktualizowaniu kontrolki, podczas gdy ON_EN_UPDATEjest wywoływana tuż przed aktualizacją.

Programy obsługi mapy komunikatów są opisane w sekcji UwagiCEdit dokumentacji kontrolnej:https://docs.microsoft.com/en-us/cpp/mfc/reference/cedit-class?view=msvc-160

Jeśli chodzi o twoje obawy dotyczące modyfikowania rzeczy jako typów użytkowników - powinno to wystarczyć, ponieważ każda zmiana (naciśnięcie klawisza lub wklejanie ze schowka itp.) Powinna wywołać wywołanie tego programu obsługi, w którym możesz zmienić wszystko, czego potrzebujesz. Po prostu upewnij się, że podczas aktualizowania kontrolki nie wyzwalasz ON_EN_CHANGEponownie i kończysz w cyklicznej pętli „zmiany”.

Możesz to zrobić z jakąś flagą wskazującą, że to ty aktualizujesz kontrolkę, a nie użytkownik, jednak prawdopodobnie lepiej jest podklasować CEditkontrolkę, aby robić to, co chcesz. Istnieje kilka przykładów, jak to zrobić (nie jest to tak trudne, jak mogłoby się wydawać), na przykład:https://www.codeproject.com/Articles/27376/Avoiding-EN-CHANGE-notifications