2013-03-26 21 views
6

Zostałem poproszony o przypisanie podpowiedzi do każdego elementu w menu konfiguracyjnym. Skończyłem "dodawać" etykietkę narzędzi do każdej kontrolki na stronie, ale wydaje się, że czasami pojawia się etykietka narzędzia, a czasami nie, w zależności od pozycji kontrolki na ekranie.Etykiety MFC pojawiają się tylko przy specjalnych okazjach.

Aby tooltip-erize strony po raz pierwszy

EnableToolTips(TRUE); 

W metodzie każdy CPropertyPage za OnInitDialog. Następnie dodać mapie powiadomieniem

ON_NOTIFY_EX(TTN_NEEDTEXT, 0, OnToolTipText) 

z funkcją OnToolTipText patrząc jak taki

BOOL CCfgPrefPage::OnToolTipText(UINT id, NMHDR * pNMHDR, LRESULT * pResult) 
{ 
    TOOLTIPTEXT *pTTT = (TOOLTIPTEXT *)pNMHDR; 
    UINT nID = pNMHDR->idFrom; 

    if (pTTT->uFlags & TTF_IDISHWND) 
    { 
     nID = ::GetDlgCtrlID((HWND)nID); 
     if(nID) 
     { 
      if(nID == GetDlgItem(IDC_PICKDIST_EDIT)->GetDlgCtrlID()) 
       _tcsncpy_s(pTTT->szText, _T("Tool Tip Text"), _TRUNCATE); 
      else if(nID == GetDlgItem(IDC_ENDPTTOL_EDIT)->GetDlgCtrlID()) 
       _tcsncpy_s(pTTT->szText, _T("Tool Tip Text"), _TRUNCATE); 

      pTTT->lpszText = pTTT->szText; // Sanity Check 
      pTTT->hinst = AfxGetResourceHandle(); // Don't think this is needed at all 
      return TRUE; 
     } 
    } 
    return FALSE; 
} 

Wydaje się dla niektórych z moich kontroli podpowiedzi nie będą wyświetlane. W większości pól kontrolnych wyświetla się wskazówka narzędzia, ale dla niektórych po prostu się nie wyświetla. Nie ma żadnych innych kontrolek, które je zakrywają, nie są wyłączone.

Inną rzeczą, jeśli korzystam z niestandardowych okien kursora, wielokrotnie mruga końcówka narzędzia, tak że w niektórych przypadkach jest nieczytelna. Jak mogę to naprawić? To nie jest problem w sterowaniu CEdit, więc dlaczego jest to problem gdzie indziej?

EDYCJA: Zaktualizuj, formanty, które były na stronach od lat wydają się pokazywać wskazówki narzędzi. Jakakolwiek kontrola, którą próbuję dodać teraz/dziś, nie będzie pokazywać wskazówek dotyczących narzędzi. Bez względu na pozycję, typ kontroli, ustawienia, nie mogę uzyskać pojedynczej wskazówki narzędzia, aby pokazać na nowo wstawionym sterowaniu.

+0

Napotkałem podobny problem w systemie Windows XP (i tylko na XP, bez problemów w Vista, 7 i 8). Mam przycisk z końcówką narzędzia w modalnym oknie dialogowym.Gdy mysz zatrzyma się nad przyciskiem, etykietka pojawi się po bardzo krótkim czasie. Jak na razie dobrze. Teraz podpowiedź odchodzi, gdy jeden z następujących dwóch coditions spełniony jest: 1) użytkownik przesuwa kursor myszy na przycisku, 2) użytkownik nie porusza się mysz dla 4 lub 5 sekund. Jeśli końcówka narzędzia zniknie z powodu drugiego warunku, nigdy nie powróci do tego okna dialogowego, chyba że okno dialogowe zostanie zamknięte i ponownie otwarte. –

+0

Również używam komputera z systemem Windows XP. Nie masz problemy nr 2, jak liście, mogę pozwolić podpowiedź zniknie i będzie wrócić po usunę + przesunąć kursor nad nim ponownie. Mój problem polega na tym, że tooltip nie ma i nie pojawia się w przypadku unikalnych kontrolek, a nie konkretnych. Wydaje się, że dla niektórych CCheckBox i niektórych nie, pojawi się dla niektórych CEdit, a niektóre nie. Etykietka również miga co każde 50ms, dzięki czemu jest częściowo nieczytelna; ale jest to tylko z nietypowymi myszami, takimi jak "krzyż", którego często używam na ekranie z dokładnością. –

+3

podpowiedzi Okna są jednym z najważniejszych cech Pita (wdrożenie) wszechczasów. –

Odpowiedz

6

Jeśli nie chcesz używać klasy pomocniczej, zaproponowałem, a następnie napraw problemy w kodzie. pierwsze, użycie ON_NOTIFY_EX_RANGE makro gdy mapowanie nawet obsługi, jak to (ten obejmie wszystkie identyfikatory):

ON_NOTIFY_EX_RANGE(TTN_NEEDTEXTA, 0, 0xFFFF, OnToolTipText) 

Następnie trzeba naprawić swoją funkcję. Widzę tutaj kilka problemów. Po pierwsze, podczas testowania flagi TTF_IDISHWND wystarczy ponownie zainicjalizować nID. Nie musisz stosować tego do całej funkcji. Po drugie, po wszystkich manipulacjach, twój nID będzie faktycznym identyfikatorem okna dialogowego. Nie ma potrzeby, aby GetDlgItem function()

BOOL CCfgPrefPage::OnToolTipText(UINT id, NMHDR * pNMHDR, LRESULT * pResult) 
{ 
    TOOLTIPTEXT *pTTT = (TOOLTIPTEXT *)pNMHDR; 
    UINT nID = pNMHDR->idFrom; 

    if (pTTT->uFlags & TTF_IDISHWND) 
    { 
     nID = ::GetDlgCtrlID((HWND)nID); 
    } 
    if(nID) 
    { 
     if(nID == IDC_PICKDIST_EDIT) 
      _tcsncpy_s(pTTT->szText, _T("Tool Tip Text"), _TRUNCATE); 
     else if(nID == IDC_ENDPTTOL_EDIT) 
      _tcsncpy_s(pTTT->szText, _T("Tool Tip Text"), _TRUNCATE); 

     //pTTT->lpszText = pTTT->szText; // Sanity Check 
     *pResult = 0; 
     return TRUE; 
    } 
    return FALSE; 
} 
+0

Że za wysiłek , ale to nie rozwiązuje moich problemów. Zgadzam się, że jest to właściwy sposób napisania funkcji. Ale jak to jest, nadal istnieją 4-5 kontroli na każdej CPropertyPage, która nie będzie wyświetlać etykietki narzędzi. Jak mogę to debugować, aby zobaczyć, dokąd zmierza wiadomość? –

+0

@BumSkeeter - Odpowiedź od cha powinna zadziałać. Ale "EnableToolTips" działa tylko na ** elementach podrzędnych ** obiektu *** CWnd ***, w którym jest wywoływany. Czy możesz potwierdzić, że nowe kontrolki, które dodałeś, są tworzone jako ** dziecko ** kontroli tego obiektu CWnd? – mfc

0

Praca z paska narzędzi, który powtarza niektóre elementy menu z menu starszego aplikacji MFC, pracuję w tej kwestii podpowiedzi, jak (1) modyfikowanie Mapa bitowa paska narzędzi zawierająca dodatkowe ikony i (2) zapewniająca informację zwrotną od użytkownika na temat bieżącego stanu aplikacji. Mój problem polega na tym, że muszę to robić ręcznie, zamiast korzystać z różnych kreatorów i narzędzi.

To, co zrobiłem, to (1) dodać nowych członków do klasy pochodnej CView do obsługi dodatkowych wiadomości, (2) zmodyfikować mapę bitową paska narzędzi, aby dodać dodatkowe ikony przy użyciu zarówno MS Paint, jak i edytora zasobów, oraz (3) dodał nowe identyfikatory zdarzeń i programy obsługi zdarzeń do mapy komunikatów dla klasy pochodnej CView.

Jednym z problemów, które napotkałem podczas zmiany paska mapy, było to, że od kiedy wstawiałem ikonę, musiałem przesunąć istniejącą ikonę w bitmapie w prawo. Moja pierwsza próba spowodowała przesunięcie ikony pokazanej jako puste na pasku narzędzi aplikacji. Wtedy zdałem sobie sprawę, że muszę dodać trochę więcej do długości mapy bitowej paska narzędzi. Po dodaniu kilku dodatkowych kolumn do ostatniej ikony w mapie bitowej paska narzędzi, aby stała się ona standardową szerokością w pikselach, ikona wyświetli się prawidłowo.

Dla podpowiedzi I dodaje następujące do mapy wiadomość:

ON_NOTIFY_EX(TTN_NEEDTEXT, 0, OnToolTipText) 

I dodaje następujące metody do mojej klasy do obsługi powiadomień dla mojego menu. Na marginesie okazuje się, że OnToolTipText() jest standardową metodą używaną w klasie CFrameWnd i CMDIChildWnd, jednak CView wywodzi się z CWnd, podobnie jak CFrameWnd, więc wątpię, czy ma to wpływ na nazwę metody.

inline BOOL CPCSampleView::OnToolTipText(UINT id, NMHDR * pNMHDR, LRESULT * pResult) 
{ 
    static wchar_t toolTextToggleExportSylk [64] = L"Toggle SYLK export."; 
    static wchar_t toolTextClearWindow [64] = L"Clear the log displayed."; 
    static wchar_t toolTextConnectLan [64] = L"Log on the POS terminal through the LAN."; 

    TOOLTIPTEXT *pTTT = (TOOLTIPTEXT *)pNMHDR; 

    switch (pNMHDR->idFrom) { 
     case ID_TOGGLE_SYLK_EXPORT: 
      pTTT->lpszText = toolTextToggleExportSylk; 
      return TRUE; 
     case ID_WINDOW_CLEAR: 
      pTTT->lpszText = toolTextClearWindow; 
      return TRUE; 
     case ID_CONNECT_LAN_ON: 
      pTTT->lpszText = toolTextConnectLan; 
      return TRUE; 
    } 
    // if we do not handle the message then return FALSE to let someone else do it. 
    return FALSE; 
} 

za opinie użytkowników na menu, które przełącza się eksport plików podczas wykonywania raportów ja przewidziane następujące zmiany w mapie wiadomość, a następnie wdrożyć odpowiednie metody. Istnieją dwa rodzaje komunikatów zaangażowanych więc musiałem dodać dwie metody i dwa nowe wpisy wiadomość mapy:

// New message map entries to handle the menu item selection event 
// and to update the menu item and the toolbar icon with state changes 
ON_COMMAND(ID_TOGGLE_SYLK_EXPORT, OnToggleExportSylk) 
ON_UPDATE_COMMAND_UI(ID_TOGGLE_SYLK_EXPORT, OnUpdateToggleExportSylk) 


// New methods added to the CView derived class 

// handle the menu selection event generated by either selecting the menu item 
// from the menu or by clicking on the icon in the toolbar. 
void CPCSampleView::OnToggleExportSylk() 
{ 
    // Exclusive Or to toggle the indicator bit from 0 to 1 and 1 to 0. 
    GetDocument()->ulReportOptionsMap ^= CPCSampleDoc::ulReportOptionsExportSylk; 
} 

// handle the request from the MFC framework to update the displayed state this 
// not only does a check mark against the menu item it also causes the toolbar 
// icon to appear depressed if click is set or non-depressed if click is not set 
inline void CPCSampleView::OnUpdateToggleExportSylk (CCmdUI* pCmdUI) 
{ 
    if (GetDocument()->ulReportOptionsMap & CPCSampleDoc::ulReportOptionsExportSylk) 
    { 
     // SYLK export is turned on so indicate status to the user. This will 
     // put a check mark beside the menu item and show the toolbar button depressed 
     pCmdUI->SetCheck (1); 
    } 
    else 
    { 
     // SYLK export is turned off so indicate status to the user. This will 
     // remove the check mark beside the menu item and show the toolbar button as raised. 
     pCmdUI->SetCheck (0); 
    } 
} 

Zasób potrzebne zmiany pliku zostały dostarczenie nowego przycisku na działanie przerzutnika jak dodać nowy element menu dla akcji przełączania. Używam tego samego identyfikatora zasobu dla kilku różnych rzeczy, ponieważ wszystkie są oddzielne. Tak więc id łańcucha zasobów jest taki sam jak dla pozycji menu i jest taki sam dla przycisku paska narzędzi, aby uprościć moje życie i ułatwić znalezienie wszystkich poszczególnych bitów.

Definicja pliku zasobów Pasek wygląda następująco:

IDR_MAINFRAME TOOLBAR 16, 15 
BEGIN 
    BUTTON  ID_CONNECT_LAN_ON 
    SEPARATOR 
    BUTTON  ID_WINDOW_CLEAR 
    SEPARATOR 
    BUTTON  ID_TOGGLE_SYLK_EXPORT 
    SEPARATOR 
    BUTTON  ID_APP_ABOUT 
END 

A specyficzna część menu, która wykorzystuje ten sam identyfikator zasobu dla identyfikatora zdarzenia przełącznik wygląda następująco:

MENUITEM "Export to SYLK file",   ID_TOGGLE_SYLK_EXPORT 

Następnie do podać tekst paska stanu, który pojawia się za pomocą myszy, tam jest dodawanie tablicy ciągów:

ID_TOGGLE_SYLK_EXPORT "Toggle export of SYLK format report files for spreadsheets." 

Członek struct lpszText jest opisać w dokumentacji MSDN dla struct TOOLINFO jak:

wskaźnik do bufora zawierającego tekst narzędzia lub identyfikatorem zasobu znaków, który zawiera tekst. Ten element członkowski jest czasami używany do zwracania wartości. Jeśli chcesz sprawdzić zwróconą wartość, musisz wskazać prawidłowy bufor o odpowiednim rozmiarze. W przeciwnym razie można ustawić wartość NULL. Jeśli lpszText jest ustawiony na LPSTR_TEXTCALLBACK, kontrolka wysyła kod powiadomienia TTN_GETDISPINFO do okna właściciela, aby pobrać tekst.

przeglądu istniejącego odpowiedź na to pytanie, zastanawiałem się o czeku if Oświadczenie dla flagi TTF_IDISHWND. Dokumentacja MSDN dla struktury TOOLINFO ma następujące znaczenie:

Wskazuje, że członem uId jest uchwyt okna narzędzia. Jeśli ta flaga nie jest ustawiona, uID jest identyfikatorem narzędzia.