1. small dnd compilation fixes (no attempt to make icon setting work though)

2. wxMenuItemBase appears
3. more key combinations handled by wxGTK for menu accels


git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@4184 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Vadim Zeitlin
1999-10-25 15:51:37 +00:00
parent 84a3fe2c9b
commit 974e8d946f
17 changed files with 621 additions and 506 deletions

View File

@@ -17,6 +17,7 @@
#if wxUSE_DRAG_AND_DROP #if wxUSE_DRAG_AND_DROP
#include "wx/dataobj.h" #include "wx/dataobj.h"
#include "wx/cursor.h"
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
// constants // constants

View File

@@ -29,12 +29,6 @@ class wxMenuBar;
class wxMenuItem; class wxMenuItem;
class wxMenu; class wxMenu;
//-----------------------------------------------------------------------------
// const
//-----------------------------------------------------------------------------
#define ID_SEPARATOR (-1)
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// wxMenuBar // wxMenuBar
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------

View File

@@ -14,62 +14,26 @@
#pragma interface #pragma interface
#endif #endif
#include "wx/defs.h"
#include "wx/string.h"
// ----------------------------------------------------------------------------
// constants
// ----------------------------------------------------------------------------
#define ID_SEPARATOR (-1)
//-----------------------------------------------------------------------------
// classes
//-----------------------------------------------------------------------------
class wxMenuItem;
class wxMenu;
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// wxMenuItem // wxMenuItem
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
class wxMenuItem : public wxObject class wxMenuItem : public wxMenuItemBase
{ {
DECLARE_DYNAMIC_CLASS(wxMenuItem)
public: public:
wxMenuItem(); wxMenuItem(wxMenu *parentMenu = (wxMenu *)NULL,
int id = wxID_SEPARATOR,
const wxString& text = wxEmptyString,
const wxString& help = wxEmptyString,
bool isCheckable = FALSE,
wxMenu *subMenu = (wxMenu *)NULL);
~wxMenuItem(); ~wxMenuItem();
// accessors // implement base class virtuals
// id virtual void SetText( const wxString& str ) { DoSetText(str); }
void SetId(int id) { m_id = id; } virtual void Enable( bool enable = TRUE );
int GetId() const { return m_id; } virtual void Check( bool check = TRUE );
bool IsSeparator() const { return m_id == ID_SEPARATOR; } virtual bool IsChecked() const;
// the item's text = name
void SetName(const wxString& str);
void SetText(const wxString& str) { SetName(str); } // compatibility
const wxString& GetName() const { return m_text; }
const wxString& GetText() const { return GetName(); }
// what kind of menu item we are
void SetCheckable(bool checkable) { m_isCheckMenu = checkable; }
bool IsCheckable() const { return m_isCheckMenu; }
void SetSubMenu(wxMenu *menu) { m_subMenu = menu; }
wxMenu *GetSubMenu() const { return m_subMenu; }
bool IsSubMenu() const { return m_subMenu != NULL; }
// state
void Enable( bool enable = TRUE );
bool IsEnabled() const { return m_isEnabled; }
void Check( bool check = TRUE );
bool IsChecked() const;
// help string (displayed in the status bar by default)
void SetHelp(const wxString& str) { m_helpStr = str; }
const wxString& GetHelp() const { return m_helpStr; }
// implementation // implementation
void SetMenuItem(GtkWidget *menuItem) { m_menuItem = menuItem; } void SetMenuItem(GtkWidget *menuItem) { m_menuItem = menuItem; }
@@ -77,20 +41,16 @@ public:
wxString GetHotKey() const { return m_hotKey; } wxString GetHotKey() const { return m_hotKey; }
void SetCheckedFlag(bool checked) { m_isChecked = checked; }
bool GetCheckedFlag() const { return m_isChecked; }
private: private:
int m_id; // DoSetText() transforms the accel mnemonics in our label from MSW/wxWin
wxString m_text; // style to GTK+ and is called from ctor and SetText()
void DoSetText(const wxString& text);
wxString m_hotKey; wxString m_hotKey;
bool m_isCheckMenu;
bool m_isChecked;
bool m_isEnabled;
wxMenu *m_subMenu;
wxString m_helpStr;
GtkWidget *m_menuItem; // GtkMenuItem GtkWidget *m_menuItem; // GtkMenuItem
DECLARE_DYNAMIC_CLASS(wxMenuItem)
}; };

View File

@@ -29,12 +29,6 @@ class wxMenuBar;
class wxMenuItem; class wxMenuItem;
class wxMenu; class wxMenu;
//-----------------------------------------------------------------------------
// const
//-----------------------------------------------------------------------------
#define ID_SEPARATOR (-1)
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// wxMenuBar // wxMenuBar
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------

View File

@@ -14,62 +14,26 @@
#pragma interface #pragma interface
#endif #endif
#include "wx/defs.h"
#include "wx/string.h"
// ----------------------------------------------------------------------------
// constants
// ----------------------------------------------------------------------------
#define ID_SEPARATOR (-1)
//-----------------------------------------------------------------------------
// classes
//-----------------------------------------------------------------------------
class wxMenuItem;
class wxMenu;
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// wxMenuItem // wxMenuItem
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
class wxMenuItem : public wxObject class wxMenuItem : public wxMenuItemBase
{ {
DECLARE_DYNAMIC_CLASS(wxMenuItem)
public: public:
wxMenuItem(); wxMenuItem(wxMenu *parentMenu = (wxMenu *)NULL,
int id = wxID_SEPARATOR,
const wxString& text = wxEmptyString,
const wxString& help = wxEmptyString,
bool isCheckable = FALSE,
wxMenu *subMenu = (wxMenu *)NULL);
~wxMenuItem(); ~wxMenuItem();
// accessors // implement base class virtuals
// id virtual void SetText( const wxString& str ) { DoSetText(str); }
void SetId(int id) { m_id = id; } virtual void Enable( bool enable = TRUE );
int GetId() const { return m_id; } virtual void Check( bool check = TRUE );
bool IsSeparator() const { return m_id == ID_SEPARATOR; } virtual bool IsChecked() const;
// the item's text = name
void SetName(const wxString& str);
void SetText(const wxString& str) { SetName(str); } // compatibility
const wxString& GetName() const { return m_text; }
const wxString& GetText() const { return GetName(); }
// what kind of menu item we are
void SetCheckable(bool checkable) { m_isCheckMenu = checkable; }
bool IsCheckable() const { return m_isCheckMenu; }
void SetSubMenu(wxMenu *menu) { m_subMenu = menu; }
wxMenu *GetSubMenu() const { return m_subMenu; }
bool IsSubMenu() const { return m_subMenu != NULL; }
// state
void Enable( bool enable = TRUE );
bool IsEnabled() const { return m_isEnabled; }
void Check( bool check = TRUE );
bool IsChecked() const;
// help string (displayed in the status bar by default)
void SetHelp(const wxString& str) { m_helpStr = str; }
const wxString& GetHelp() const { return m_helpStr; }
// implementation // implementation
void SetMenuItem(GtkWidget *menuItem) { m_menuItem = menuItem; } void SetMenuItem(GtkWidget *menuItem) { m_menuItem = menuItem; }
@@ -77,20 +41,16 @@ public:
wxString GetHotKey() const { return m_hotKey; } wxString GetHotKey() const { return m_hotKey; }
void SetCheckedFlag(bool checked) { m_isChecked = checked; }
bool GetCheckedFlag() const { return m_isChecked; }
private: private:
int m_id; // DoSetText() transforms the accel mnemonics in our label from MSW/wxWin
wxString m_text; // style to GTK+ and is called from ctor and SetText()
void DoSetText(const wxString& text);
wxString m_hotKey; wxString m_hotKey;
bool m_isCheckMenu;
bool m_isChecked;
bool m_isEnabled;
wxMenu *m_subMenu;
wxString m_helpStr;
GtkWidget *m_menuItem; // GtkMenuItem GtkWidget *m_menuItem; // GtkMenuItem
DECLARE_DYNAMIC_CLASS(wxMenuItem)
}; };

View File

@@ -1,6 +1,106 @@
///////////////////////////////////////////////////////////////////////////////
// Name: wx/menuitem.h
// Purpose: wxMenuItem class
// Author: Vadim Zeitlin
// Modified by:
// Created: 25.10.99
// RCS-ID: $Id$
// Copyright: (c) 1999 Vadim Zeitlin <zeitlin@dptmaths.ens-cachan.fr>
// Licence: wxWindows license
///////////////////////////////////////////////////////////////////////////////
#ifndef _WX_MENUITEM_H_BASE_ #ifndef _WX_MENUITEM_H_BASE_
#define _WX_MENUITEM_H_BASE_ #define _WX_MENUITEM_H_BASE_
// ----------------------------------------------------------------------------
// headers
// ----------------------------------------------------------------------------
#include "wx/object.h" // base class
// ----------------------------------------------------------------------------
// constants
// ----------------------------------------------------------------------------
// id for a separator line in the menu (invalid for normal item)
#define wxID_SEPARATOR (-1)
#ifndef ID_SEPARATOR // for compatibility only, don't use in new code
#define ID_SEPARATOR wxID_SEPARATOR
#endif
// ----------------------------------------------------------------------------
// forward declarations
// ----------------------------------------------------------------------------
class WXDLLEXPORT wxMenuItem;
class WXDLLEXPORT wxMenu;
// ----------------------------------------------------------------------------
// wxMenuItem is an item in the menu which may be either a normal item, a sub
// menu or a separator
// ----------------------------------------------------------------------------
class WXDLLEXPORT wxMenuItemBase : public wxObject
{
public:
// creation
static wxMenuItem *New(wxMenu *parentMenu = (wxMenu *)NULL,
int id = wxID_SEPARATOR,
const wxString& text = wxEmptyString,
const wxString& help = wxEmptyString,
bool isCheckable = FALSE,
wxMenu *subMenu = (wxMenu *)NULL);
// get/set id
void SetId(int id) { m_id = id; }
int GetId() const { return m_id; }
bool IsSeparator() const { return m_id == wxID_SEPARATOR; }
// the item's text (or name, or label...)
virtual void SetText(const wxString& str) { m_text = str; }
const wxString& GetText() const { return m_text; }
// what kind of menu item we are
virtual void SetCheckable(bool checkable) { m_isCheckable = checkable; }
bool IsCheckable() const { return m_isCheckable; }
bool IsSubMenu() const { return m_subMenu != NULL; }
void SetSubMenu(wxMenu *menu) { m_subMenu = menu; }
wxMenu *GetSubMenu() const { return m_subMenu; }
// state
virtual void Enable(bool enable = TRUE) { m_isEnabled = enable; }
virtual bool IsEnabled() const { return m_isEnabled; }
virtual void Check(bool check = TRUE) { m_isChecked = check; }
virtual bool IsChecked() const { return m_isChecked; }
// help string (displayed in the status bar by default)
void SetHelp(const wxString& str) { m_help = str; }
const wxString& GetHelp() const { return m_help; }
// compatibility only, use new functions in the new code
void SetName(const wxString& str) { SetText(str); }
const wxString& GetName() const { return GetText(); }
protected:
int m_id; // numeric id of the item >= 0 or -1
wxMenu *m_parentMenu, // the menu we belong to
*m_subMenu; // our sub menu or NULL
wxString m_text, // label of the item
m_help; // the help string for the item
bool m_isCheckable; // can be checked?
bool m_isChecked; // is checked?
bool m_isEnabled; // is enabled?
};
// ----------------------------------------------------------------------------
// include the real class declaration
// ----------------------------------------------------------------------------
#ifdef wxUSE_BASE_CLASSES_ONLY
#define wxMenuItem wxMenuItemBase
#else // !wxUSE_BASE_CLASSES_ONLY
#if defined(__WXMSW__) #if defined(__WXMSW__)
#include "wx/msw/menuitem.h" #include "wx/msw/menuitem.h"
#elif defined(__WXMOTIF__) #elif defined(__WXMOTIF__)
@@ -16,6 +116,7 @@
#elif defined(__WXSTUBS__) #elif defined(__WXSTUBS__)
#include "wx/stubs/menuitem.h" #include "wx/stubs/menuitem.h"
#endif #endif
#endif // wxUSE_BASE_CLASSES_ONLY/!wxUSE_BASE_CLASSES_ONLY
#endif #endif
// _WX_MENUITEM_H_BASE_ // _WX_MENUITEM_H_BASE_

View File

@@ -32,6 +32,8 @@ class WXDLLEXPORT wxFrame;
WXDLLEXPORT_DATA(extern const wxChar*) wxEmptyString; WXDLLEXPORT_DATA(extern const wxChar*) wxEmptyString;
WX_DEFINE_ARRAY(wxAcceleratorEntry *, wxAcceleratorArray);
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
// Menu // Menu
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
@@ -147,7 +149,7 @@ public:
void Detach(); void Detach();
#if wxUSE_ACCEL #if wxUSE_ACCEL
size_t GetAccelCount() const { return m_accelKeyCodes.GetCount(); } size_t GetAccelCount() const { return m_accels.GetCount(); }
size_t CopyAccels(wxAcceleratorEntry *accels) const; size_t CopyAccels(wxAcceleratorEntry *accels) const;
#endif // wxUSE_ACCEL #endif // wxUSE_ACCEL
@@ -186,8 +188,8 @@ private:
void* m_clientData; void* m_clientData;
#if wxUSE_ACCEL #if wxUSE_ACCEL
// the accelerators data // the accelerators for our menu items
wxArrayInt m_accelKeyCodes, m_accelFlags, m_accelIds; wxAcceleratorArray m_accels;
#endif // wxUSE_ACCEL #endif // wxUSE_ACCEL
}; };

View File

@@ -20,81 +20,50 @@
// headers // headers
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
#include "wx/setup.h"
// an exception to the general rule that a normal header doesn't include other
// headers - only because ownerdrw.h is not always included and I don't want
// to write #ifdef's everywhere...
#if wxUSE_OWNER_DRAWN #if wxUSE_OWNER_DRAWN
#include "wx/ownerdrw.h" #include "wx/ownerdrw.h" // base class
#endif #endif
// ----------------------------------------------------------------------------
// constants
// ----------------------------------------------------------------------------
// id for a separator line in the menu (invalid for normal item)
#define ID_SEPARATOR (-1)
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
// wxMenuItem: an item in the menu, optionally implements owner-drawn behaviour // wxMenuItem: an item in the menu, optionally implements owner-drawn behaviour
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
class WXDLLEXPORT wxMenuItem: public wxObject
class WXDLLEXPORT wxMenuItem : public wxMenuItemBase
#if wxUSE_OWNER_DRAWN #if wxUSE_OWNER_DRAWN
, public wxOwnerDrawn , public wxOwnerDrawn
#endif #endif
{ {
DECLARE_DYNAMIC_CLASS(wxMenuItem)
public: public:
// ctor & dtor // ctor & dtor
wxMenuItem(wxMenu *pParentMenu = NULL, int id = ID_SEPARATOR, wxMenuItem(wxMenu *parentMenu = (wxMenu *)NULL,
const wxString& strName = "", const wxString& wxHelp = "", int id = wxID_SEPARATOR,
bool bCheckable = FALSE, wxMenu *pSubMenu = NULL); const wxString& name = wxEmptyString,
const wxString& help = wxEmptyString,
bool isCheckable = FALSE,
wxMenu *subMenu = (wxMenu *)NULL);
virtual ~wxMenuItem(); virtual ~wxMenuItem();
// accessors (some more are inherited from wxOwnerDrawn or are below) // override base class virtuals
bool IsSeparator() const { return m_idItem == ID_SEPARATOR; } virtual void SetText(const wxString& strName);
bool IsEnabled() const { return m_bEnabled; } virtual void SetCheckable(bool checkable);
bool IsChecked() const { return m_bChecked; }
bool IsSubMenu() const { return GetSubMenu() != NULL; }
int GetId() const { return m_idItem; } virtual void Enable(bool bDoEnable = TRUE);
const wxString& GetHelp() const { return m_strHelp; } virtual void Check(bool bDoCheck = TRUE);
wxMenu *GetSubMenu() const { return m_pSubMenu; }
// unfortunately needed to resolve ambiguity between
// wxMenuItemBase::IsCheckable() and wxOwnerDrawn::IsCheckable()
bool IsCheckable() const { return wxMenuItemBase::IsCheckable(); }
// the id for a popup menu is really its menu handle (as required by // the id for a popup menu is really its menu handle (as required by
// ::AppendMenu() API) // ::AppendMenu() API), so this function will return either the id or the
// menu handle depending on what we're
int GetRealId() const; int GetRealId() const;
// operations // delete the submenu
void SetName(const wxString& strName);
void SetHelp(const wxString& strHelp) { m_strHelp = strHelp; }
void Enable(bool bDoEnable = TRUE);
void Check(bool bDoCheck = TRUE);
void DeleteSubMenu(); void DeleteSubMenu();
private: private:
int m_idItem; // numeric id of the item DECLARE_DYNAMIC_CLASS(wxMenuItem)
wxString m_strHelp; // associated help string
wxMenu *m_pSubMenu, // may be NULL
*m_pParentMenu; // menu this item is contained in
bool m_bEnabled, // enabled or greyed?
m_bChecked; // checked? (only if checkable)
#if wxUSE_OWNER_DRAWN
// wxOwnerDrawn base class already has these variables - nothing to do
#else //!owner drawn
bool m_bCheckable; // can be checked?
wxString m_strName; // name or label of the item
public:
const wxString& GetName() const { return m_strName; }
bool IsCheckable() const { return m_bCheckable; }
#endif //owner drawn
}; };
#endif //_MENUITEM_H #endif //_MENUITEM_H

View File

@@ -12,12 +12,14 @@
#ifndef _OWNERDRW_H #ifndef _OWNERDRW_H
#define _OWNERDRW_H #define _OWNERDRW_H
#include "wx/setup.h"
#if wxUSE_OWNER_DRAWN
#ifdef __GNUG__ #ifdef __GNUG__
#pragma interface "ownerdrw.h" #pragma interface "ownerdrw.h"
#endif #endif
#include <stddef.h>
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
// wxOwnerDrawn - a mix-in base class, derive from it to implement owner-drawn // wxOwnerDrawn - a mix-in base class, derive from it to implement owner-drawn
// behaviour // behaviour
@@ -26,11 +28,12 @@
// also supports 3 bitmaps: either a checked/unchecked bitmap for a checkable // also supports 3 bitmaps: either a checked/unchecked bitmap for a checkable
// element or one unchangeable bitmap otherwise. // element or one unchangeable bitmap otherwise.
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
class WXDLLEXPORT wxOwnerDrawn class WXDLLEXPORT wxOwnerDrawn
{ {
public: public:
// ctor & dtor // ctor & dtor
wxOwnerDrawn(const wxString& str = "", wxOwnerDrawn(const wxString& str = wxEmptyString,
bool bCheckable = FALSE, bool bCheckable = FALSE,
bool bMenuItem = FALSE); // FIXME kludge for colors bool bMenuItem = FALSE); // FIXME kludge for colors
virtual ~wxOwnerDrawn() { } virtual ~wxOwnerDrawn() { }
@@ -80,6 +83,7 @@ public:
// accessors // accessors
void SetName(const wxString& strName) { m_strName = strName; } void SetName(const wxString& strName) { m_strName = strName; }
const wxString& GetName() const { return m_strName; } const wxString& GetName() const { return m_strName; }
void SetCheckable(bool checkable) { m_bCheckable = checkable; }
bool IsCheckable() const { return m_bCheckable; } bool IsCheckable() const { return m_bCheckable; }
// this function might seem strange, but if it returns FALSE it means that // this function might seem strange, but if it returns FALSE it means that
@@ -134,5 +138,7 @@ private:
m_nMarginWidth; // space occupied by bitmap to the left of the item m_nMarginWidth; // space occupied by bitmap to the left of the item
}; };
#endif // wxUSE_OWNER_DRAWN
#endif #endif
// _OWNERDRW_H // _OWNERDRW_H

View File

@@ -221,12 +221,17 @@ WXDLLEXPORT wxChar* wxGetUserHome(const wxString& user = wxEmptyString);
#if wxUSE_GUI // GUI only things from now on #if wxUSE_GUI // GUI only things from now on
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
// Strip out any menu codes // Menu accelerators related things
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
WXDLLEXPORT wxChar* wxStripMenuCodes(wxChar *in, wxChar *out = (wxChar *) NULL); WXDLLEXPORT wxChar* wxStripMenuCodes(wxChar *in, wxChar *out = (wxChar *) NULL);
WXDLLEXPORT wxString wxStripMenuCodes(const wxString& str); WXDLLEXPORT wxString wxStripMenuCodes(const wxString& str);
#if wxUSE_ACCEL
class WXDLLEXPORT wxAcceleratorEntry;
WXDLLEXPORT wxAcceleratorEntry *wxGetAccelFromString(const wxString& label);
#endif // wxUSE_ACCEL
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
// Window search // Window search
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------

View File

@@ -32,6 +32,8 @@
#include "wx/defs.h" #include "wx/defs.h"
#include "wx/string.h" #include "wx/string.h"
#include "wx/utils.h" #include "wx/utils.h"
#include "wx/intl.h"
#include "wx/log.h"
#if wxUSE_GUI #if wxUSE_GUI
#include "wx/window.h" #include "wx/window.h"
@@ -39,6 +41,10 @@
#include "wx/frame.h" #include "wx/frame.h"
#include "wx/msgdlg.h" #include "wx/msgdlg.h"
#include "wx/textdlg.h" #include "wx/textdlg.h"
#if wxUSE_ACCEL
#include "wx/menuitem.h"
#include "wx/accel.h"
#endif // wxUSE_ACCEL
#endif // wxUSE_GUI #endif // wxUSE_GUI
#endif // WX_PRECOMP #endif // WX_PRECOMP
@@ -392,7 +398,7 @@ wxString wxNow()
#if wxUSE_GUI #if wxUSE_GUI
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
// Strip out any menu codes // Menu accelerators related functions
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
wxChar *wxStripMenuCodes (wxChar *in, wxChar *out) wxChar *wxStripMenuCodes (wxChar *in, wxChar *out)
@@ -439,6 +445,91 @@ wxString wxStripMenuCodes(const wxString& str)
return str1; return str1;
} }
#if wxUSE_ACCEL
// return wxAcceleratorEntry for the given menu string or NULL if none
// specified
wxAcceleratorEntry *wxGetAccelFromString(const wxString& label)
{
// check for accelerators: they are given after '\t'
int posTab = label.Find(wxT('\t'));
if ( posTab != wxNOT_FOUND ) {
// parse the accelerator string
int keyCode = 0;
int accelFlags = wxACCEL_NORMAL;
wxString current;
for ( size_t n = (size_t)posTab + 1; n < label.Len(); n++ ) {
if ( (label[n] == '+') || (label[n] == '-') ) {
if ( current == _("ctrl") )
accelFlags |= wxACCEL_CTRL;
else if ( current == _("alt") )
accelFlags |= wxACCEL_ALT;
else if ( current == _("shift") )
accelFlags |= wxACCEL_SHIFT;
else {
wxLogDebug(wxT("Unknown accel modifier: '%s'"),
current.c_str());
}
current.Empty();
}
else {
current += wxTolower(label[n]);
}
}
if ( current.IsEmpty() ) {
wxLogDebug(wxT("No accel key found, accel string ignored."));
}
else {
if ( current.Len() == 1 ) {
// it's a letter
keyCode = wxToupper(current[0U]);
}
else {
// is it a function key?
if ( current[0U] == 'f' && isdigit(current[1U]) &&
(current.Len() == 2 ||
(current.Len() == 3 && isdigit(current[2U]))) ) {
int n;
wxSscanf(current.c_str() + 1, wxT("%d"), &n);
keyCode = WXK_F1 + n - 1;
}
else {
#if 0 // this is not supported by GTK+, apparently
// several special cases
current.MakeUpper();
if ( current == wxT("DEL") ) {
keyCode = VK_DELETE;
}
else if ( current == wxT("PGUP") ) {
keyCode = VK_PRIOR;
}
else if ( current == wxT("PGDN") ) {
keyCode = VK_NEXT;
}
else
#endif // 0
{
wxLogDebug(wxT("Unrecognized accel key '%s', accel "
"string ignored."), current.c_str());
}
}
}
}
if ( keyCode ) {
// we do have something
return new wxAcceleratorEntry(accelFlags, keyCode);
}
}
return NULL;
}
#endif // wxUSE_ACCEL
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
// Window search functions // Window search functions
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------

View File

@@ -628,7 +628,7 @@ gtk_dnd_window_configure_callback( GtkWidget *WXUNUSED(widget), GdkEventConfigur
if (source->m_dragContext->action == GDK_ACTION_COPY) action = wxDragCopy; if (source->m_dragContext->action == GDK_ACTION_COPY) action = wxDragCopy;
if (source->m_dragContext->action == GDK_ACTION_MOVE) action = wxDragMove; if (source->m_dragContext->action == GDK_ACTION_MOVE) action = wxDragMove;
source->GiveFeedback( action, FALSE ); source->GiveFeedback( action );
return 0; return 0;
} }

View File

@@ -17,6 +17,10 @@
#include "wx/intl.h" #include "wx/intl.h"
#include "wx/app.h" #include "wx/app.h"
#if wxUSE_ACCEL
#include "wx/accel.h"
#endif // wxUSE_ACCEL
#include "gdk/gdk.h" #include "gdk/gdk.h"
#include "gtk/gtk.h" #include "gtk/gtk.h"
@@ -488,15 +492,17 @@ static void gtk_menu_clicked_callback( GtkWidget *widget, wxMenu *menu )
if (item->IsCheckable()) if (item->IsCheckable())
{ {
if (item->GetCheckedFlag() == item->IsChecked()) bool isReallyChecked = item->IsChecked();
if ( item->wxMenuItemBase::IsChecked() == isReallyChecked )
{ {
/* the menu item has been checked by calling wxMenuItem->Check() */ /* the menu item has been checked by calling wxMenuItem->Check() */
return; return;
} }
else else
{ {
/* the user pressed on the menu item -> report */ /* the user pressed on the menu item -> report and make consistent
item->SetCheckedFlag(item->IsChecked()); /* make consistent again */ * again */
item->wxMenuItemBase::Check(isReallyChecked);
} }
} }
@@ -573,16 +579,37 @@ static void gtk_menu_nolight_callback( GtkWidget *widget, wxMenu *menu )
// wxMenuItem // wxMenuItem
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
IMPLEMENT_DYNAMIC_CLASS(wxMenuItem,wxObject) IMPLEMENT_DYNAMIC_CLASS(wxMenuItem, wxMenuItemBase)
wxMenuItem::wxMenuItem() wxMenuItem *wxMenuItemBase::New(wxMenu *parentMenu,
int id,
const wxString& name,
const wxString& help,
bool isCheckable,
wxMenu *subMenu)
{ {
m_id = ID_SEPARATOR; return new wxMenuItem(parentMenu, id, name, help, isCheckable, subMenu);
m_isCheckMenu = FALSE; }
wxMenuItem::wxMenuItem(wxMenu *parentMenu,
int id,
const wxString& text,
const wxString& help,
bool isCheckable,
wxMenu *subMenu)
{
m_id = id;
m_isCheckable = isCheckable;
m_isChecked = FALSE; m_isChecked = FALSE;
m_isEnabled = TRUE; m_isEnabled = TRUE;
m_subMenu = (wxMenu *) NULL; m_subMenu = subMenu;
m_parentMenu = parentMenu;
m_help = help;
m_menuItem = (GtkWidget *) NULL; m_menuItem = (GtkWidget *) NULL;
// call it after initializing m_menuItem to NULL
DoSetText(text);
} }
wxMenuItem::~wxMenuItem() wxMenuItem::~wxMenuItem()
@@ -591,10 +618,10 @@ wxMenuItem::~wxMenuItem()
} }
// it's valid for this function to be called even if m_menuItem == NULL // it's valid for this function to be called even if m_menuItem == NULL
void wxMenuItem::SetName( const wxString& str ) void wxMenuItem::DoSetText( const wxString& str )
{ {
/* '\t' is the deliminator indicating a hot key */ /* '\t' is the deliminator indicating a hot key */
m_text = wxT(""); m_text.Empty();
const wxChar *pc = str; const wxChar *pc = str;
for (; (*pc != wxT('\0')) && (*pc != wxT('\t')); pc++ ) for (; (*pc != wxT('\0')) && (*pc != wxT('\t')); pc++ )
{ {
@@ -639,9 +666,10 @@ void wxMenuItem::Check( bool check )
wxCHECK_RET( IsCheckable(), wxT("Can't check uncheckable item!") ) wxCHECK_RET( IsCheckable(), wxT("Can't check uncheckable item!") )
if (check == m_isChecked) return; if (check == m_isChecked)
return;
m_isChecked = check; wxMenuItemBase::Check( check );
gtk_check_menu_item_set_state( (GtkCheckMenuItem*)m_menuItem, (gint)check ); gtk_check_menu_item_set_state( (GtkCheckMenuItem*)m_menuItem, (gint)check );
} }
@@ -650,18 +678,17 @@ void wxMenuItem::Enable( bool enable )
wxCHECK_RET( m_menuItem, wxT("invalid menu item") ); wxCHECK_RET( m_menuItem, wxT("invalid menu item") );
gtk_widget_set_sensitive( m_menuItem, enable ); gtk_widget_set_sensitive( m_menuItem, enable );
m_isEnabled = enable; wxMenuItemBase::Enable( enable );
} }
bool wxMenuItem::IsChecked() const bool wxMenuItem::IsChecked() const
{ {
wxCHECK_MSG( m_menuItem, FALSE, wxT("invalid menu item") ); wxCHECK_MSG( m_menuItem, FALSE, wxT("invalid menu item") );
wxCHECK( IsCheckable(), FALSE ); // can't get state of uncheckable item! wxCHECK_MSG( IsCheckable(), FALSE,
wxT("can't get state of uncheckable item!") );
bool bIsChecked = ((GtkCheckMenuItem*)m_menuItem)->active != 0; return ((GtkCheckMenuItem*)m_menuItem)->active != 0;
return bIsChecked;
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@@ -751,8 +778,7 @@ const wxString wxMenu::GetTitle() const
void wxMenu::AppendSeparator() void wxMenu::AppendSeparator()
{ {
wxMenuItem *mitem = new wxMenuItem(); wxMenuItem *mitem = new wxMenuItem(this, wxID_SEPARATOR);
mitem->SetId(ID_SEPARATOR);
#if (GTK_MINOR_VERSION > 0) #if (GTK_MINOR_VERSION > 0)
GtkItemFactoryEntry entry; GtkItemFactoryEntry entry;
@@ -776,53 +802,65 @@ void wxMenu::AppendSeparator()
m_items.Append( mitem ); m_items.Append( mitem );
} }
#if (GTK_MINOR_VERSION > 0) #if (GTK_MINOR_VERSION > 0) && wxUSE_ACCEL
static char* GetHotKey( const wxString &hotkey, char *hotbuf ) static wxString GetHotKey( const wxMenuItem& item )
{ {
if (hotkey.IsEmpty()) return (char*) NULL; wxString hotkey;
switch (hotkey[0]) // as wxGetAccelFromString() looks for TAB, insert a dummy one here
wxString label;
label << wxT('\t') << item.GetHotKey();
wxAcceleratorEntry *accel = wxGetAccelFromString(label);
if ( accel )
{ {
case wxT('a'): /* Alt */ int flags = accel->GetFlags();
case wxT('A'): if ( flags & wxACCEL_ALT )
case wxT('m'): /* Meta */ hotkey += wxT("<alt>");
case wxT('M'): if ( flags & wxACCEL_CTRL )
hotkey += wxT("<control>");
if ( flags & wxACCEL_SHIFT )
hotkey += wxT("<shift>");
int code = accel->GetKeyCode();
switch ( code )
{ {
strcpy( hotbuf, "<alt>" ); case WXK_F1:
wxString last = hotkey.Right(1); case WXK_F2:
strcat( hotbuf, last.mb_str() ); case WXK_F3:
return hotbuf; case WXK_F4:
} case WXK_F5:
case wxT('c'): /* Ctrl */ case WXK_F6:
case wxT('C'): case WXK_F7:
case wxT('s'): /* Strg, yeah man, I'm German */ case WXK_F8:
case wxT('S'): case WXK_F9:
{ case WXK_F10:
strcpy( hotbuf, "<control>" ); case WXK_F11:
wxString last = hotkey.Right(1); case WXK_F12:
strcat( hotbuf, last.mb_str() ); hotkey << wxT('F') << code = WXK_F1 + 1;
return hotbuf; break;
}
case wxT('F'): /* function keys */ // if there are any other keys wxGetAccelFromString() may return,
{ // we should process them here
strcpy( hotbuf, hotkey.mb_str() );
return hotbuf;
}
default: default:
if ( wxIsalnum(code) )
{ {
hotkey << (wxChar)code;
break;
}
wxFAIL_MSG( wxT("unknown keyboard accel") );
} }
} }
return (char*) NULL;
return hotkey;
} }
#endif #endif // wxUSE_ACCEL
void wxMenu::Append( int id, const wxString &item, const wxString &helpStr, bool checkable ) void wxMenu::Append( int id, const wxString &item, const wxString &helpStr, bool checkable )
{ {
wxMenuItem *mitem = new wxMenuItem(); wxMenuItem *mitem = new wxMenuItem(this, id, item, helpStr, checkable);
mitem->SetId(id);
mitem->SetText(item);
mitem->SetHelp(helpStr);
mitem->SetCheckable(checkable);
#if (GTK_MINOR_VERSION > 0) #if (GTK_MINOR_VERSION > 0)
/* text has "_" instead of "&" after mitem->SetText() */ /* text has "_" instead of "&" after mitem->SetText() */
@@ -842,8 +880,16 @@ void wxMenu::Append( int id, const wxString &item, const wxString &helpStr, bool
else else
entry.item_type = "<Item>"; entry.item_type = "<Item>";
char hotbuf[50]; #if wxUSE_ACCEL
entry.accelerator = GetHotKey( mitem->GetHotKey(), hotbuf ); // due to an apparent bug in GTK+, we have to use a static buffer here -
// otherwise GTK+ 1.2.2 manages to override the memory we pass to it
// somehow! (VZ)
static char s_accel[32]; // must be big enough for <control><alt><shift>F12
strncpy(s_accel, GetHotKey(*mitem).mb_str(), WXSIZEOF(s_accel));
entry.accelerator = s_accel;
#else
entry.accelerator = NULL;
#endif
gtk_item_factory_create_item( m_factory, &entry, (gpointer) this, 2 ); /* what is 2 ? */ gtk_item_factory_create_item( m_factory, &entry, (gpointer) this, 2 ); /* what is 2 ? */
@@ -886,10 +932,7 @@ void wxMenu::Append( int id, const wxString &item, const wxString &helpStr, bool
void wxMenu::Append( int id, const wxString &item, wxMenu *subMenu, const wxString &helpStr ) void wxMenu::Append( int id, const wxString &item, wxMenu *subMenu, const wxString &helpStr )
{ {
wxMenuItem *mitem = new wxMenuItem(); wxMenuItem *mitem = new wxMenuItem(this, id, item, helpStr, FALSE, subMenu);
mitem->SetId(id);
mitem->SetText(item);
mitem->SetHelp(helpStr);
#if (GTK_MINOR_VERSION > 0) #if (GTK_MINOR_VERSION > 0)
/* text has "_" instead of "&" after mitem->SetText() */ /* text has "_" instead of "&" after mitem->SetText() */
@@ -938,7 +981,6 @@ void wxMenu::Append( int id, const wxString &item, wxMenu *subMenu, const wxStri
gtk_menu_item_set_submenu( GTK_MENU_ITEM(menuItem), subMenu->m_menu ); gtk_menu_item_set_submenu( GTK_MENU_ITEM(menuItem), subMenu->m_menu );
mitem->SetMenuItem(menuItem); mitem->SetMenuItem(menuItem);
mitem->SetSubMenu(subMenu);
m_items.Append( mitem ); m_items.Append( mitem );
} }

View File

@@ -628,7 +628,7 @@ gtk_dnd_window_configure_callback( GtkWidget *WXUNUSED(widget), GdkEventConfigur
if (source->m_dragContext->action == GDK_ACTION_COPY) action = wxDragCopy; if (source->m_dragContext->action == GDK_ACTION_COPY) action = wxDragCopy;
if (source->m_dragContext->action == GDK_ACTION_MOVE) action = wxDragMove; if (source->m_dragContext->action == GDK_ACTION_MOVE) action = wxDragMove;
source->GiveFeedback( action, FALSE ); source->GiveFeedback( action );
return 0; return 0;
} }

View File

@@ -17,6 +17,10 @@
#include "wx/intl.h" #include "wx/intl.h"
#include "wx/app.h" #include "wx/app.h"
#if wxUSE_ACCEL
#include "wx/accel.h"
#endif // wxUSE_ACCEL
#include "gdk/gdk.h" #include "gdk/gdk.h"
#include "gtk/gtk.h" #include "gtk/gtk.h"
@@ -488,15 +492,17 @@ static void gtk_menu_clicked_callback( GtkWidget *widget, wxMenu *menu )
if (item->IsCheckable()) if (item->IsCheckable())
{ {
if (item->GetCheckedFlag() == item->IsChecked()) bool isReallyChecked = item->IsChecked();
if ( item->wxMenuItemBase::IsChecked() == isReallyChecked )
{ {
/* the menu item has been checked by calling wxMenuItem->Check() */ /* the menu item has been checked by calling wxMenuItem->Check() */
return; return;
} }
else else
{ {
/* the user pressed on the menu item -> report */ /* the user pressed on the menu item -> report and make consistent
item->SetCheckedFlag(item->IsChecked()); /* make consistent again */ * again */
item->wxMenuItemBase::Check(isReallyChecked);
} }
} }
@@ -573,16 +579,37 @@ static void gtk_menu_nolight_callback( GtkWidget *widget, wxMenu *menu )
// wxMenuItem // wxMenuItem
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
IMPLEMENT_DYNAMIC_CLASS(wxMenuItem,wxObject) IMPLEMENT_DYNAMIC_CLASS(wxMenuItem, wxMenuItemBase)
wxMenuItem::wxMenuItem() wxMenuItem *wxMenuItemBase::New(wxMenu *parentMenu,
int id,
const wxString& name,
const wxString& help,
bool isCheckable,
wxMenu *subMenu)
{ {
m_id = ID_SEPARATOR; return new wxMenuItem(parentMenu, id, name, help, isCheckable, subMenu);
m_isCheckMenu = FALSE; }
wxMenuItem::wxMenuItem(wxMenu *parentMenu,
int id,
const wxString& text,
const wxString& help,
bool isCheckable,
wxMenu *subMenu)
{
m_id = id;
m_isCheckable = isCheckable;
m_isChecked = FALSE; m_isChecked = FALSE;
m_isEnabled = TRUE; m_isEnabled = TRUE;
m_subMenu = (wxMenu *) NULL; m_subMenu = subMenu;
m_parentMenu = parentMenu;
m_help = help;
m_menuItem = (GtkWidget *) NULL; m_menuItem = (GtkWidget *) NULL;
// call it after initializing m_menuItem to NULL
DoSetText(text);
} }
wxMenuItem::~wxMenuItem() wxMenuItem::~wxMenuItem()
@@ -591,10 +618,10 @@ wxMenuItem::~wxMenuItem()
} }
// it's valid for this function to be called even if m_menuItem == NULL // it's valid for this function to be called even if m_menuItem == NULL
void wxMenuItem::SetName( const wxString& str ) void wxMenuItem::DoSetText( const wxString& str )
{ {
/* '\t' is the deliminator indicating a hot key */ /* '\t' is the deliminator indicating a hot key */
m_text = wxT(""); m_text.Empty();
const wxChar *pc = str; const wxChar *pc = str;
for (; (*pc != wxT('\0')) && (*pc != wxT('\t')); pc++ ) for (; (*pc != wxT('\0')) && (*pc != wxT('\t')); pc++ )
{ {
@@ -639,9 +666,10 @@ void wxMenuItem::Check( bool check )
wxCHECK_RET( IsCheckable(), wxT("Can't check uncheckable item!") ) wxCHECK_RET( IsCheckable(), wxT("Can't check uncheckable item!") )
if (check == m_isChecked) return; if (check == m_isChecked)
return;
m_isChecked = check; wxMenuItemBase::Check( check );
gtk_check_menu_item_set_state( (GtkCheckMenuItem*)m_menuItem, (gint)check ); gtk_check_menu_item_set_state( (GtkCheckMenuItem*)m_menuItem, (gint)check );
} }
@@ -650,18 +678,17 @@ void wxMenuItem::Enable( bool enable )
wxCHECK_RET( m_menuItem, wxT("invalid menu item") ); wxCHECK_RET( m_menuItem, wxT("invalid menu item") );
gtk_widget_set_sensitive( m_menuItem, enable ); gtk_widget_set_sensitive( m_menuItem, enable );
m_isEnabled = enable; wxMenuItemBase::Enable( enable );
} }
bool wxMenuItem::IsChecked() const bool wxMenuItem::IsChecked() const
{ {
wxCHECK_MSG( m_menuItem, FALSE, wxT("invalid menu item") ); wxCHECK_MSG( m_menuItem, FALSE, wxT("invalid menu item") );
wxCHECK( IsCheckable(), FALSE ); // can't get state of uncheckable item! wxCHECK_MSG( IsCheckable(), FALSE,
wxT("can't get state of uncheckable item!") );
bool bIsChecked = ((GtkCheckMenuItem*)m_menuItem)->active != 0; return ((GtkCheckMenuItem*)m_menuItem)->active != 0;
return bIsChecked;
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@@ -751,8 +778,7 @@ const wxString wxMenu::GetTitle() const
void wxMenu::AppendSeparator() void wxMenu::AppendSeparator()
{ {
wxMenuItem *mitem = new wxMenuItem(); wxMenuItem *mitem = new wxMenuItem(this, wxID_SEPARATOR);
mitem->SetId(ID_SEPARATOR);
#if (GTK_MINOR_VERSION > 0) #if (GTK_MINOR_VERSION > 0)
GtkItemFactoryEntry entry; GtkItemFactoryEntry entry;
@@ -776,53 +802,65 @@ void wxMenu::AppendSeparator()
m_items.Append( mitem ); m_items.Append( mitem );
} }
#if (GTK_MINOR_VERSION > 0) #if (GTK_MINOR_VERSION > 0) && wxUSE_ACCEL
static char* GetHotKey( const wxString &hotkey, char *hotbuf ) static wxString GetHotKey( const wxMenuItem& item )
{ {
if (hotkey.IsEmpty()) return (char*) NULL; wxString hotkey;
switch (hotkey[0]) // as wxGetAccelFromString() looks for TAB, insert a dummy one here
wxString label;
label << wxT('\t') << item.GetHotKey();
wxAcceleratorEntry *accel = wxGetAccelFromString(label);
if ( accel )
{ {
case wxT('a'): /* Alt */ int flags = accel->GetFlags();
case wxT('A'): if ( flags & wxACCEL_ALT )
case wxT('m'): /* Meta */ hotkey += wxT("<alt>");
case wxT('M'): if ( flags & wxACCEL_CTRL )
hotkey += wxT("<control>");
if ( flags & wxACCEL_SHIFT )
hotkey += wxT("<shift>");
int code = accel->GetKeyCode();
switch ( code )
{ {
strcpy( hotbuf, "<alt>" ); case WXK_F1:
wxString last = hotkey.Right(1); case WXK_F2:
strcat( hotbuf, last.mb_str() ); case WXK_F3:
return hotbuf; case WXK_F4:
} case WXK_F5:
case wxT('c'): /* Ctrl */ case WXK_F6:
case wxT('C'): case WXK_F7:
case wxT('s'): /* Strg, yeah man, I'm German */ case WXK_F8:
case wxT('S'): case WXK_F9:
{ case WXK_F10:
strcpy( hotbuf, "<control>" ); case WXK_F11:
wxString last = hotkey.Right(1); case WXK_F12:
strcat( hotbuf, last.mb_str() ); hotkey << wxT('F') << code = WXK_F1 + 1;
return hotbuf; break;
}
case wxT('F'): /* function keys */ // if there are any other keys wxGetAccelFromString() may return,
{ // we should process them here
strcpy( hotbuf, hotkey.mb_str() );
return hotbuf;
}
default: default:
if ( wxIsalnum(code) )
{ {
hotkey << (wxChar)code;
break;
}
wxFAIL_MSG( wxT("unknown keyboard accel") );
} }
} }
return (char*) NULL;
return hotkey;
} }
#endif #endif // wxUSE_ACCEL
void wxMenu::Append( int id, const wxString &item, const wxString &helpStr, bool checkable ) void wxMenu::Append( int id, const wxString &item, const wxString &helpStr, bool checkable )
{ {
wxMenuItem *mitem = new wxMenuItem(); wxMenuItem *mitem = new wxMenuItem(this, id, item, helpStr, checkable);
mitem->SetId(id);
mitem->SetText(item);
mitem->SetHelp(helpStr);
mitem->SetCheckable(checkable);
#if (GTK_MINOR_VERSION > 0) #if (GTK_MINOR_VERSION > 0)
/* text has "_" instead of "&" after mitem->SetText() */ /* text has "_" instead of "&" after mitem->SetText() */
@@ -842,8 +880,16 @@ void wxMenu::Append( int id, const wxString &item, const wxString &helpStr, bool
else else
entry.item_type = "<Item>"; entry.item_type = "<Item>";
char hotbuf[50]; #if wxUSE_ACCEL
entry.accelerator = GetHotKey( mitem->GetHotKey(), hotbuf ); // due to an apparent bug in GTK+, we have to use a static buffer here -
// otherwise GTK+ 1.2.2 manages to override the memory we pass to it
// somehow! (VZ)
static char s_accel[32]; // must be big enough for <control><alt><shift>F12
strncpy(s_accel, GetHotKey(*mitem).mb_str(), WXSIZEOF(s_accel));
entry.accelerator = s_accel;
#else
entry.accelerator = NULL;
#endif
gtk_item_factory_create_item( m_factory, &entry, (gpointer) this, 2 ); /* what is 2 ? */ gtk_item_factory_create_item( m_factory, &entry, (gpointer) this, 2 ); /* what is 2 ? */
@@ -886,10 +932,7 @@ void wxMenu::Append( int id, const wxString &item, const wxString &helpStr, bool
void wxMenu::Append( int id, const wxString &item, wxMenu *subMenu, const wxString &helpStr ) void wxMenu::Append( int id, const wxString &item, wxMenu *subMenu, const wxString &helpStr )
{ {
wxMenuItem *mitem = new wxMenuItem(); wxMenuItem *mitem = new wxMenuItem(this, id, item, helpStr, FALSE, subMenu);
mitem->SetId(id);
mitem->SetText(item);
mitem->SetHelp(helpStr);
#if (GTK_MINOR_VERSION > 0) #if (GTK_MINOR_VERSION > 0)
/* text has "_" instead of "&" after mitem->SetText() */ /* text has "_" instead of "&" after mitem->SetText() */
@@ -938,7 +981,6 @@ void wxMenu::Append( int id, const wxString &item, wxMenu *subMenu, const wxStri
gtk_menu_item_set_submenu( GTK_MENU_ITEM(menuItem), subMenu->m_menu ); gtk_menu_item_set_submenu( GTK_MENU_ITEM(menuItem), subMenu->m_menu );
mitem->SetMenuItem(menuItem); mitem->SetMenuItem(menuItem);
mitem->SetSubMenu(subMenu);
m_items.Append( mitem ); m_items.Append( mitem );
} }

View File

@@ -141,78 +141,9 @@ void wxMenu::Append(wxMenuItem *pItem)
wxCHECK_RET( pItem != NULL, wxT("can't append NULL item to the menu") ); wxCHECK_RET( pItem != NULL, wxT("can't append NULL item to the menu") );
#if wxUSE_ACCEL #if wxUSE_ACCEL
// check for accelerators: they are given after '\t' wxAcceleratorEntry *accel = wxGetAccelFromMenuLabel(pItem->GetText());
wxString label = pItem->GetName(); if ( accel ) {
int posTab = label.Find(wxT('\t')); m_accels.Add(accel);
if ( posTab != wxNOT_FOUND ) {
// parse the accelerator string
int keyCode = 0;
int accelFlags = wxACCEL_NORMAL;
wxString current;
for ( size_t n = (size_t)posTab + 1; n < label.Len(); n++ ) {
if ( (label[n] == '+') || (label[n] == '-') ) {
if ( current == _("ctrl") )
accelFlags |= wxACCEL_CTRL;
else if ( current == _("alt") )
accelFlags |= wxACCEL_ALT;
else if ( current == _("shift") )
accelFlags |= wxACCEL_SHIFT;
else {
wxLogDebug(wxT("Unknown accel modifier: '%s'"),
current.c_str());
}
current.Empty();
}
else {
current += wxTolower(label[n]);
}
}
if ( current.IsEmpty() ) {
wxLogDebug(wxT("No accel key found, accel string ignored."));
}
else {
if ( current.Len() == 1 ) {
// it's a letter
keyCode = wxToupper(current[0U]);
}
else {
// is it a function key?
if ( current[0U] == 'f' && isdigit(current[1U]) &&
(current.Len() == 2 ||
(current.Len() == 3 && isdigit(current[2U]))) ) {
int n;
wxSscanf(current.c_str() + 1, wxT("%d"), &n);
keyCode = VK_F1 + n - 1;
}
else {
// several special cases
current.MakeUpper();
if ( current == wxT("DEL") ) {
keyCode = VK_DELETE;
}
else if ( current == wxT("PGUP") ) {
keyCode = VK_PRIOR;
}
else if ( current == wxT("PGDN") ) {
keyCode = VK_NEXT;
}
else {
wxLogDebug(wxT("Unrecognized accel key '%s', accel "
"string ignored."), current.c_str());
}
}
}
}
if ( keyCode ) {
// do add an entry
m_accelKeyCodes.Add(keyCode);
m_accelFlags.Add(accelFlags);
m_accelIds.Add(pItem->GetId());
}
} }
#endif // wxUSE_ACCEL #endif // wxUSE_ACCEL
@@ -262,13 +193,7 @@ void wxMenu::Append(wxMenuItem *pItem)
// menu is just a normal string (passed in data parameter) // menu is just a normal string (passed in data parameter)
flags |= MF_STRING; flags |= MF_STRING;
// Don't know what the correct cast should be, but it doesn't pData = (char*)pItem->GetText().c_str();
// compile in BC++/16-bit without this cast.
#if !defined(__WIN32__)
pData = (char*) (const char*) label;
#else
pData = label;
#endif
} }
if ( !::AppendMenu(GetHmenu(), flags, id, pData) ) if ( !::AppendMenu(GetHmenu(), flags, id, pData) )
@@ -373,7 +298,7 @@ size_t wxMenu::CopyAccels(wxAcceleratorEntry *accels) const
size_t count = GetAccelCount(); size_t count = GetAccelCount();
for ( size_t n = 0; n < count; n++ ) for ( size_t n = 0; n < count; n++ )
{ {
(*accels++).Set(m_accelFlags[n], m_accelKeyCodes[n], m_accelIds[n]); *accels++ = *m_accels[n];
} }
return count; return count;
@@ -422,7 +347,7 @@ void wxMenu::SetLabel(int id, const wxString& label)
wxMenuItem *item = FindItemForId(id) ; wxMenuItem *item = FindItemForId(id) ;
wxCHECK_RET( item, wxT("wxMenu::SetLabel: no such item") ); wxCHECK_RET( item, wxT("wxMenu::SetLabel: no such item") );
item->SetName(label); item->SetText(label);
} }
wxString wxMenu::GetLabel(int id) const wxString wxMenu::GetLabel(int id) const
@@ -430,7 +355,7 @@ wxString wxMenu::GetLabel(int id) const
wxString label; wxString label;
wxMenuItem *pItem = FindItemForId(id) ; wxMenuItem *pItem = FindItemForId(id) ;
if (pItem) if (pItem)
label = pItem->GetName() ; label = pItem->GetText() ;
else else
wxFAIL_MSG(wxT("wxMenu::GetLabel: item doesn't exist")); wxFAIL_MSG(wxT("wxMenu::GetLabel: item doesn't exist"));
@@ -592,7 +517,7 @@ int wxMenu::FindItem (const wxString& itemString) const
} }
else if ( !item->IsSeparator() ) else if ( !item->IsSeparator() )
{ {
wxString label = wxStripMenuCodes(item->GetName()); wxString label = wxStripMenuCodes(item->GetText());
if ( itemLabel == label ) if ( itemLabel == label )
return item->GetId(); return item->GetId();
} }
@@ -812,7 +737,7 @@ void wxMenuBar::SetLabel(int id, const wxString& label)
wxCHECK_RET( item, wxT("wxMenuBar::SetLabel(): no such item") ); wxCHECK_RET( item, wxT("wxMenuBar::SetLabel(): no such item") );
item->SetName(label); item->SetText(label);
} }
wxString wxMenuBar::GetLabel(int id) const wxString wxMenuBar::GetLabel(int id) const
@@ -820,9 +745,10 @@ wxString wxMenuBar::GetLabel(int id) const
wxMenu *itemMenu = NULL; wxMenu *itemMenu = NULL;
wxMenuItem *item = FindItemForId(id, &itemMenu) ; wxMenuItem *item = FindItemForId(id, &itemMenu) ;
wxCHECK_MSG( item, wxT(""), wxT("wxMenuBar::GetLabel(): no such item") ); wxCHECK_MSG( item, wxEmptyString,
wxT("wxMenuBar::GetLabel(): no such item") );
return item->GetName(); return item->GetText();
} }
void wxMenuBar::SetHelpString (int id, const wxString& helpString) void wxMenuBar::SetHelpString (int id, const wxString& helpString)

View File

@@ -39,18 +39,25 @@
#include "wx/string.h" #include "wx/string.h"
#endif #endif
#include "wx/ownerdrw.h"
#include "wx/menuitem.h" #include "wx/menuitem.h"
#include "wx/log.h" #include "wx/log.h"
#include "wx/msw/private.h" #include "wx/msw/private.h"
// --------------------------------------------------------------------------- // ---------------------------------------------------------------------------
// convenience macro // macro
// --------------------------------------------------------------------------- // ---------------------------------------------------------------------------
// hide the ugly cast
#define GetHMenuOf(menu) ((HMENU)menu->GetHMenu()) #define GetHMenuOf(menu) ((HMENU)menu->GetHMenu())
// conditional compilation
#if wxUSE_OWNER_DRAWN
#define OWNER_DRAWN_ONLY( code ) if ( IsOwnerDrawn() ) code
#else // !wxUSE_OWNER_DRAWN
#define OWNER_DRAWN_ONLY( code )
#endif // wxUSE_OWNER_DRAWN/!wxUSE_OWNER_DRAWN
// ============================================================================ // ============================================================================
// implementation // implementation
// ============================================================================ // ============================================================================
@@ -61,11 +68,10 @@
#if !defined(USE_SHARED_LIBRARY) || !USE_SHARED_LIBRARY #if !defined(USE_SHARED_LIBRARY) || !USE_SHARED_LIBRARY
#if wxUSE_OWNER_DRAWN #if wxUSE_OWNER_DRAWN
IMPLEMENT_DYNAMIC_CLASS2(wxMenuItem, wxObject, wxOwnerDrawn) IMPLEMENT_DYNAMIC_CLASS2(wxMenuItem, wxMenuItemBase, wxOwnerDrawn)
#else //!USE_OWNER_DRAWN #else //!USE_OWNER_DRAWN
IMPLEMENT_DYNAMIC_CLASS(wxMenuItem, wxObject) IMPLEMENT_DYNAMIC_CLASS(wxMenuItem, wxMenuItemBase)
#endif //USE_OWNER_DRAWN #endif //USE_OWNER_DRAWN
#endif //USE_SHARED_LIBRARY #endif //USE_SHARED_LIBRARY
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
@@ -75,17 +81,15 @@
// ctor & dtor // ctor & dtor
// ----------- // -----------
wxMenuItem::wxMenuItem(wxMenu *pParentMenu, int id, wxMenuItem::wxMenuItem(wxMenu *pParentMenu,
const wxString& strName, const wxString& strHelp, int id,
const wxString& text,
const wxString& strHelp,
bool bCheckable, bool bCheckable,
wxMenu *pSubMenu) : wxMenu *pSubMenu) :
#if wxUSE_OWNER_DRAWN #if wxUSE_OWNER_DRAWN
wxOwnerDrawn(strName, bCheckable), wxOwnerDrawn(text, bCheckable)
#else //no owner drawn support
m_bCheckable(bCheckable),
m_strName(strName),
#endif // owner drawn #endif // owner drawn
m_strHelp(strHelp)
{ {
wxASSERT_MSG( pParentMenu != NULL, wxT("a menu item should have a parent") ); wxASSERT_MSG( pParentMenu != NULL, wxT("a menu item should have a parent") );
@@ -100,13 +104,16 @@ wxMenuItem::wxMenuItem(wxMenu *pParentMenu, int id,
ResetOwnerDrawn(); ResetOwnerDrawn();
#undef SYS_COLOR #undef SYS_COLOR
#endif #endif // wxUSE_OWNER_DRAWN
m_pParentMenu = pParentMenu; m_parentMenu = pParentMenu;
m_pSubMenu = pSubMenu; m_subMenu = pSubMenu;
m_bEnabled = TRUE; m_isEnabled = TRUE;
m_bChecked = FALSE; m_isChecked = FALSE;
m_idItem = id; m_id = id;
m_text = text;
m_isCheckable = bCheckable;
m_help = strHelp;
} }
wxMenuItem::~wxMenuItem() wxMenuItem::~wxMenuItem()
@@ -119,15 +126,15 @@ wxMenuItem::~wxMenuItem()
// return the id for calling Win32 API functions // return the id for calling Win32 API functions
int wxMenuItem::GetRealId() const int wxMenuItem::GetRealId() const
{ {
return m_pSubMenu ? (int)m_pSubMenu->GetHMenu() : GetId(); return m_subMenu ? (int)m_subMenu->GetHMenu() : GetId();
} }
// delete the sub menu // delete the sub menu
// ------------------- // -------------------
void wxMenuItem::DeleteSubMenu() void wxMenuItem::DeleteSubMenu()
{ {
delete m_pSubMenu; delete m_subMenu;
m_pSubMenu = NULL; m_subMenu = NULL;
} }
// change item state // change item state
@@ -135,8 +142,8 @@ void wxMenuItem::DeleteSubMenu()
void wxMenuItem::Enable(bool bDoEnable) void wxMenuItem::Enable(bool bDoEnable)
{ {
if ( m_bEnabled != bDoEnable ) { if ( m_isEnabled != bDoEnable ) {
long rc = EnableMenuItem(GetHMenuOf(m_pParentMenu), long rc = EnableMenuItem(GetHMenuOf(m_parentMenu),
GetRealId(), GetRealId(),
MF_BYCOMMAND | MF_BYCOMMAND |
(bDoEnable ? MF_ENABLED : MF_GRAYED)); (bDoEnable ? MF_ENABLED : MF_GRAYED));
@@ -145,16 +152,16 @@ void wxMenuItem::Enable(bool bDoEnable)
wxLogLastError("EnableMenuItem"); wxLogLastError("EnableMenuItem");
} }
m_bEnabled = bDoEnable; wxMenuItemBase::Enable(m_isEnabled);
} }
} }
void wxMenuItem::Check(bool bDoCheck) void wxMenuItem::Check(bool bDoCheck)
{ {
wxCHECK_RET( IsCheckable(), wxT("only checkable items may be checked") ); wxCHECK_RET( m_isCheckable, wxT("only checkable items may be checked") );
if ( m_bChecked != bDoCheck ) { if ( m_isChecked != bDoCheck ) {
long rc = CheckMenuItem(GetHMenuOf(m_pParentMenu), long rc = CheckMenuItem(GetHMenuOf(m_parentMenu),
GetId(), GetId(),
MF_BYCOMMAND | MF_BYCOMMAND |
(bDoCheck ? MF_CHECKED : MF_UNCHECKED)); (bDoCheck ? MF_CHECKED : MF_UNCHECKED));
@@ -163,19 +170,20 @@ void wxMenuItem::Check(bool bDoCheck)
wxLogLastError("CheckMenuItem"); wxLogLastError("CheckMenuItem");
} }
m_bChecked = bDoCheck; wxMenuItemBase::Check(m_isChecked);
} }
} }
void wxMenuItem::SetName(const wxString& strName) void wxMenuItem::SetText(const wxString& text)
{ {
// don't do anything if label didn't change // don't do anything if label didn't change
if ( m_strName == strName ) if ( m_text == text )
return; return;
m_strName = strName; wxMenuItemBase::SetText(text);
OWNER_DRAWN_ONLY( wxOwnerDrawn::SetName(text) );
HMENU hMenu = GetHMenuOf(m_pParentMenu); HMENU hMenu = GetHMenuOf(m_parentMenu);
UINT id = GetRealId(); UINT id = GetRealId();
UINT flagsOld = ::GetMenuState(hMenu, id, MF_BYCOMMAND); UINT flagsOld = ::GetMenuState(hMenu, id, MF_BYCOMMAND);
@@ -193,6 +201,7 @@ void wxMenuItem::SetName(const wxString& strName)
} }
LPCTSTR data; LPCTSTR data;
#if wxUSE_OWNER_DRAWN #if wxUSE_OWNER_DRAWN
if ( IsOwnerDrawn() ) if ( IsOwnerDrawn() )
{ {
@@ -203,13 +212,7 @@ void wxMenuItem::SetName(const wxString& strName)
#endif //owner drawn #endif //owner drawn
{ {
flagsOld |= MF_STRING; flagsOld |= MF_STRING;
// Don't know what the correct cast should be, but it doesn't data = (char*) text.c_str();
// compile in BC++/16-bit without this cast.
#if !defined(__WIN32__)
data = (char*) (const char*) strName;
#else
data = strName;
#endif
} }
if ( ::ModifyMenu(hMenu, id, if ( ::ModifyMenu(hMenu, id,
@@ -221,3 +224,22 @@ void wxMenuItem::SetName(const wxString& strName)
} }
} }
void wxMenuItem::SetCheckable(bool checkable)
{
wxMenuItemBase::SetCheckable(checkable);
OWNER_DRAWN_ONLY( wxOwnerDrawn::SetCheckable(checkable) );
}
// ----------------------------------------------------------------------------
// wxMenuItemBase
// ----------------------------------------------------------------------------
wxMenuItem *wxMenuItemBase::New(wxMenu *parentMenu,
int id,
const wxString& name,
const wxString& help,
bool isCheckable,
wxMenu *subMenu)
{
return new wxMenuItem(parentMenu, id, name, help, isCheckable, subMenu);
}