// declarations
// ============================================================================
-#if defined(__GNUG__) && !defined(NO_GCC_PRAGMA)
- #pragma implementation "cshelp.h"
-#endif
-
// ----------------------------------------------------------------------------
// headers
// ----------------------------------------------------------------------------
#if wxUSE_HELP
#ifndef WX_PRECOMP
+ #include "wx/app.h"
+ #include "wx/module.h"
#endif
#include "wx/tipwin.h"
-#include "wx/app.h"
-#include "wx/module.h"
#include "wx/cshelp.h"
+#if wxUSE_MS_HTML_HELP
+ #include "wx/msw/helpchm.h" // for ShowContextHelpPopup
+ #include "wx/utils.h" // for wxGetMousePosition()
+#endif
+
// ----------------------------------------------------------------------------
// wxContextHelpEvtHandler private class
// ----------------------------------------------------------------------------
wxCursor oldCursor = win->GetCursor();
win->SetCursor(cursor);
-#ifdef __WXMSW__
- // wxSetCursor(cursor);
+#ifdef __WXMAC__
+ wxSetCursor(cursor);
#endif
m_status = false;
win->SetCursor(oldCursor);
+#ifdef __WXMAC__
+ wxSetCursor(wxNullCursor);
+#endif
+
if (m_status)
{
wxPoint pt;
// Dispatch the help event to the relevant window
bool wxContextHelp::DispatchEvent(wxWindow* win, const wxPoint& pt)
{
- wxWindow* subjectOfHelp = win;
- bool eventProcessed = false;
- while (subjectOfHelp && !eventProcessed)
- {
- wxHelpEvent helpEvent(wxEVT_HELP, subjectOfHelp->GetId(), pt) ;
- helpEvent.SetEventObject(subjectOfHelp);
+ wxCHECK_MSG( win, false, _T("win parameter can't be NULL") );
- eventProcessed = win->GetEventHandler()->ProcessEvent(helpEvent);
+ wxHelpEvent helpEvent(wxEVT_HELP, win->GetId(), pt,
+ wxHelpEvent::Origin_HelpButton);
+ helpEvent.SetEventObject(win);
- // Go up the window hierarchy until the event is handled (or not).
- // I.e. keep submitting ancestor windows until one is recognised
- // by the app code that processes the ids and displays help.
- subjectOfHelp = subjectOfHelp->GetParent();
- }
- return eventProcessed;
+ return win->GetEventHandler()->ProcessEvent(helpEvent);
}
// ----------------------------------------------------------------------------
{
}
+wxString wxHelpProvider::GetHelpTextMaybeAtPoint(wxWindowBase *window)
+{
+ if ( m_helptextAtPoint != wxDefaultPosition ||
+ m_helptextOrigin != wxHelpEvent::Origin_Unknown )
+ {
+ wxCHECK_MSG( window, wxEmptyString, _T("window must not be NULL") );
+
+ wxPoint pt = m_helptextAtPoint;
+ wxHelpEvent::Origin origin = m_helptextOrigin;
+
+ m_helptextAtPoint = wxDefaultPosition;
+ m_helptextOrigin = wxHelpEvent::Origin_Unknown;
+
+ return window->GetHelpTextAtPoint(pt, origin);
+ }
+
+ return GetHelp(window);
+}
+
// ----------------------------------------------------------------------------
// wxSimpleHelpProvider
// ----------------------------------------------------------------------------
+#define WINHASH_KEY(w) wxPtrToUInt(w)
+
wxString wxSimpleHelpProvider::GetHelp(const wxWindowBase *window)
{
- wxLongToStringHashMap::iterator it = m_hashWindows.find((long)window);
+ wxSimpleHelpProviderHashMap::iterator it = m_hashWindows.find(WINHASH_KEY(window));
if ( it == m_hashWindows.end() )
{
void wxSimpleHelpProvider::AddHelp(wxWindowBase *window, const wxString& text)
{
- m_hashWindows.erase((long)window);
- m_hashWindows[(long)window] = text;
+ m_hashWindows.erase(WINHASH_KEY(window));
+ m_hashWindows[WINHASH_KEY(window)] = text;
}
void wxSimpleHelpProvider::AddHelp(wxWindowID id, const wxString& text)
{
- wxLongToStringHashMap::key_type key = (wxLongToStringHashMap::key_type)id;
+ wxSimpleHelpProviderHashMap::key_type key = (wxSimpleHelpProviderHashMap::key_type)id;
m_hashIds.erase(key);
m_hashIds[key] = text;
}
// removes the association
void wxSimpleHelpProvider::RemoveHelp(wxWindowBase* window)
{
- m_hashWindows.erase((long)window);
+ m_hashWindows.erase(WINHASH_KEY(window));
}
bool wxSimpleHelpProvider::ShowHelp(wxWindowBase *window)
{
-#if wxUSE_TIPWINDOW
- static wxTipWindow* s_tipWindow = NULL;
+#if wxUSE_MS_HTML_HELP || wxUSE_TIPWINDOW
+#if wxUSE_MS_HTML_HELP
+ // m_helptextAtPoint will be reset by GetHelpTextMaybeAtPoint(), stash it
+ const wxPoint posTooltip = m_helptextAtPoint;
+#endif // wxUSE_MS_HTML_HELP
- if (s_tipWindow)
- {
- // Prevent s_tipWindow being nulled in OnIdle,
- // thereby removing the chance for the window to be closed by ShowHelp
- s_tipWindow->SetTipWindowPtr(NULL);
- s_tipWindow->Close();
- }
- s_tipWindow = NULL;
+ const wxString text = GetHelpTextMaybeAtPoint(window);
- wxString text = GetHelp(window);
if ( !text.empty() )
{
- s_tipWindow = new wxTipWindow((wxWindow *)window, text, 100, & s_tipWindow);
+ // use the native help popup style if it's available
+#if wxUSE_MS_HTML_HELP
+ if ( !wxCHMHelpController::ShowContextHelpPopup
+ (
+ text,
+ posTooltip,
+ (wxWindow *)window
+ ) )
+#endif // wxUSE_MS_HTML_HELP
+ {
+#if wxUSE_TIPWINDOW
+ static wxTipWindow* s_tipWindow = NULL;
+
+ if ( s_tipWindow )
+ {
+ // Prevent s_tipWindow being nulled in OnIdle, thereby removing
+ // the chance for the window to be closed by ShowHelp
+ s_tipWindow->SetTipWindowPtr(NULL);
+ s_tipWindow->Close();
+ }
+
+ s_tipWindow = new wxTipWindow((wxWindow *)window, text,
+ 100, &s_tipWindow);
+#else // !wxUSE_TIPWINDOW
+ // we tried wxCHMHelpController but it failed and we don't have
+ // wxTipWindow to fall back on, so
+ return false;
+#endif // wxUSE_TIPWINDOW
+ }
return true;
}
-#else
+#else // !wxUSE_MS_HTML_HELP && !wxUSE_TIPWINDOW
wxUnusedVar(window);
-#endif // wxUSE_TIPWINDOW
+#endif // wxUSE_MS_HTML_HELP || wxUSE_TIPWINDOW
return false;
}
bool wxHelpControllerHelpProvider::ShowHelp(wxWindowBase *window)
{
- wxString text = GetHelp(window);
- if ( !text.empty() )
- {
- if (m_helpController)
- {
- if (text.IsNumber())
- return m_helpController->DisplayContextPopup(wxAtoi(text));
+ const wxString text = GetHelpTextMaybeAtPoint(window);
- // If the help controller is capable of popping up the text...
- else if (m_helpController->DisplayTextPopup(text, wxGetMousePosition()))
- {
- return true;
- }
- else
- // ...else use the default method.
- return wxSimpleHelpProvider::ShowHelp(window);
- }
- else
- return wxSimpleHelpProvider::ShowHelp(window);
+ if ( text.empty() )
+ return false;
+ if ( m_helpController )
+ {
+ // if it's a numeric topic, show it
+ long topic;
+ if ( text.ToLong(&topic) )
+ return m_helpController->DisplayContextPopup(topic);
+
+ // otherwise show the text directly
+ if ( m_helpController->DisplayTextPopup(text, wxGetMousePosition()) )
+ return true;
}
- return false;
+ // if there is no help controller or it's not capable of showing the help,
+ // fallback to the default method
+ return wxSimpleHelpProvider::ShowHelp(window);
}
// Convenience function for turning context id into wxString