merge with latest sources
git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@7985 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
339
src/mac/menu.cpp
339
src/mac/menu.cpp
@@ -33,8 +33,10 @@
|
||||
// ----------------------
|
||||
#include <string.h>
|
||||
|
||||
#if !USE_SHARED_LIBRARY
|
||||
IMPLEMENT_DYNAMIC_CLASS(wxMenu, wxEvtHandler)
|
||||
IMPLEMENT_DYNAMIC_CLASS(wxMenuBar, wxEvtHandler)
|
||||
#endif
|
||||
|
||||
// the (popup) menu title has this special id
|
||||
static const int idMenuTitle = -2;
|
||||
@@ -47,145 +49,6 @@ const short kwxMacAppleMenuId = 1 ;
|
||||
// implementation
|
||||
// ============================================================================
|
||||
|
||||
//
|
||||
// Helper Functions to get Mac Menus the way they should be ;-)
|
||||
//
|
||||
|
||||
void wxMacCtoPString(const char* theCString, Str255 thePString);
|
||||
|
||||
// remove inappropriate characters, if useShortcuts is false, the ampersand will not auto-generate a mac menu-shortcut
|
||||
|
||||
void wxMacBuildMenuString(StringPtr outMacItemText, char *outMacShortcutChar , short *outMacModifiers , const char *inItemText , bool useShortcuts )
|
||||
{
|
||||
char *p = (char *) &outMacItemText[1] ;
|
||||
short macModifiers = 0 ;
|
||||
char macShortCut = 0 ;
|
||||
const char *inItemName ;
|
||||
wxString inItemTextMac ;
|
||||
|
||||
if (wxApp::s_macDefaultEncodingIsPC)
|
||||
{
|
||||
inItemTextMac = wxMacMakeMacStringFromPC( inItemText ) ;
|
||||
inItemName = inItemTextMac ;
|
||||
}
|
||||
else
|
||||
{
|
||||
inItemName = inItemText ;
|
||||
}
|
||||
|
||||
if ( useShortcuts && !wxApp::s_macSupportPCMenuShortcuts )
|
||||
useShortcuts = false ;
|
||||
|
||||
// we have problems with a leading hypen - it will be taken as a separator
|
||||
|
||||
while ( *inItemName == '-' )
|
||||
inItemName++ ;
|
||||
|
||||
while( *inItemName )
|
||||
{
|
||||
switch ( *inItemName )
|
||||
{
|
||||
// special characters for macintosh menus -> use some replacement
|
||||
case ';' :
|
||||
*p++ = ',' ;
|
||||
break ;
|
||||
case '^' :
|
||||
*p++ = ' ' ;
|
||||
break ;
|
||||
case '!' :
|
||||
*p++ = ' ' ;
|
||||
break ;
|
||||
case '<' :
|
||||
*p++ = ' ' ;
|
||||
break ;
|
||||
case '/' :
|
||||
*p++ = '|' ;
|
||||
break ;
|
||||
case '(' :
|
||||
*p++ = '[' ;
|
||||
break ;
|
||||
case ')' :
|
||||
*p++ = ']' ;
|
||||
break ;
|
||||
// shortcuts
|
||||
case '&' :
|
||||
{
|
||||
++inItemName ;
|
||||
if ( *inItemName )
|
||||
{
|
||||
*p++ = *inItemName ;
|
||||
if ( useShortcuts )
|
||||
macShortCut = *inItemName ;
|
||||
}
|
||||
else
|
||||
--inItemName ;
|
||||
}
|
||||
break ;
|
||||
// win-like accelerators
|
||||
case '\t' :
|
||||
{
|
||||
++inItemName ;
|
||||
while( *inItemName )
|
||||
{
|
||||
if (strncmp("Ctrl", inItemName, 4) == 0)
|
||||
{
|
||||
inItemName = inItemName + 5;
|
||||
macShortCut = *inItemName;
|
||||
}
|
||||
else if (strncmp("Cntrl", inItemName, 5) == 0)
|
||||
{
|
||||
inItemName = inItemName + 6;
|
||||
macShortCut = *inItemName;
|
||||
}
|
||||
else if (strncmp("Alt", inItemName, 3) == 0)
|
||||
{
|
||||
inItemName = inItemName + 4;
|
||||
macModifiers |= kMenuOptionModifier ;
|
||||
macShortCut = *inItemName ;
|
||||
}
|
||||
else if (strncmp("Shift", inItemName, 5) == 0)
|
||||
{
|
||||
inItemName = inItemName + 6;
|
||||
macModifiers |= kMenuShiftModifier ;
|
||||
macShortCut = *inItemName ;
|
||||
}
|
||||
else if (strncmp("F", inItemName, 1) == 0)
|
||||
{
|
||||
inItemName += strlen( inItemName ) ;
|
||||
// no function keys at the moment
|
||||
// macModifiers |= kMenuShiftModifier ;
|
||||
// macShortCut = *inItemName ;
|
||||
}
|
||||
else
|
||||
{
|
||||
break ;
|
||||
}
|
||||
}
|
||||
|
||||
if ( *inItemName == 0 )
|
||||
--inItemName ;
|
||||
|
||||
}
|
||||
break ;
|
||||
default :
|
||||
*p++ = *inItemName ;
|
||||
}
|
||||
++inItemName ;
|
||||
}
|
||||
|
||||
outMacItemText[0] = (p - (char *)outMacItemText) - 1;
|
||||
if ( outMacShortcutChar )
|
||||
*outMacShortcutChar = macShortCut ;
|
||||
if ( outMacModifiers )
|
||||
*outMacModifiers = macModifiers ;
|
||||
if ( macShortCut )
|
||||
{
|
||||
int pos = outMacItemText[0] ;
|
||||
outMacItemText[++pos] = '/';
|
||||
outMacItemText[++pos] = toupper( macShortCut );
|
||||
outMacItemText[0] = pos ;
|
||||
}
|
||||
}
|
||||
|
||||
// Menus
|
||||
|
||||
@@ -199,10 +62,10 @@ void wxMenu::Init()
|
||||
|
||||
// create the menu
|
||||
Str255 label;
|
||||
wxMacBuildMenuString( label, NULL , NULL , m_title , false );
|
||||
wxMenuItem::MacBuildMenuString( label, NULL , NULL , m_title , false );
|
||||
m_macMenuId = s_macNextMenuId++;
|
||||
wxCHECK_RET( s_macNextMenuId < 236 , "menu ids > 235 cannot be used for submenus on mac" );
|
||||
m_hMenu = ::NewMenu(m_macMenuId, label);
|
||||
m_hMenu = UMANewMenu(m_macMenuId, label);
|
||||
|
||||
if ( !m_hMenu )
|
||||
{
|
||||
@@ -220,7 +83,7 @@ void wxMenu::Init()
|
||||
wxMenu::~wxMenu()
|
||||
{
|
||||
if (m_hMenu)
|
||||
::DisposeMenu(m_hMenu);
|
||||
UMADisposeMenu(m_hMenu);
|
||||
|
||||
#if wxUSE_ACCEL
|
||||
// delete accels
|
||||
@@ -310,38 +173,28 @@ bool wxMenu::DoInsertOrAppend(wxMenuItem *pItem, size_t pos)
|
||||
Str255 label;
|
||||
wxASSERT_MSG( pSubMenu->m_hMenu != NULL , "invalid submenu added");
|
||||
pSubMenu->m_menuParent = this ;
|
||||
wxMacBuildMenuString( label , NULL , NULL , pItem->GetText() ,false);
|
||||
wxMenuItem::MacBuildMenuString( label , NULL , NULL , pItem->GetText() ,false);
|
||||
|
||||
// hardcoded adding of the submenu combination for mac
|
||||
|
||||
int theEnd = label[0] + 1;
|
||||
if (theEnd > 251)
|
||||
theEnd = 251; // mac allows only 255 characters
|
||||
label[theEnd++] = '/';
|
||||
label[theEnd++] = hMenuCmd;
|
||||
label[theEnd++] = '!';
|
||||
label[theEnd++] = pSubMenu->m_macMenuId;
|
||||
label[theEnd] = 0x00;
|
||||
label[0] = theEnd;
|
||||
|
||||
if (wxMenuBar::MacGetInstalledMenuBar() == m_menuBar)
|
||||
{
|
||||
::InsertMenu( pSubMenu->m_hMenu , -1 ) ;
|
||||
UMAInsertMenu( pSubMenu->m_hMenu , -1 ) ;
|
||||
}
|
||||
|
||||
if ( pos == (size_t)-1 )
|
||||
{
|
||||
MacAppendMenu(m_hMenu, label);
|
||||
UMAAppendSubMenuItem(m_hMenu, label, pSubMenu->m_macMenuId);
|
||||
}
|
||||
else
|
||||
{
|
||||
MacInsertMenuItem(m_hMenu, label , pos);
|
||||
UMAInsertSubMenuItem(m_hMenu, label , pos, pSubMenu->m_macMenuId);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Str255 label ;
|
||||
wxMacBuildMenuString( label , NULL , NULL , pItem->GetText(), pItem->GetId() == wxApp::s_macAboutMenuItemId);
|
||||
UInt8 modifiers ;
|
||||
SInt16 key ;
|
||||
wxMenuItem::MacBuildMenuString( label, &key , &modifiers , pItem->GetText(), pItem->GetId() == wxApp::s_macAboutMenuItemId);
|
||||
if ( label[0] == 0 )
|
||||
{
|
||||
// we cannot add empty menus on mac
|
||||
@@ -350,17 +203,17 @@ bool wxMenu::DoInsertOrAppend(wxMenuItem *pItem, size_t pos)
|
||||
}
|
||||
if ( pos == (size_t)-1 )
|
||||
{
|
||||
MacAppendMenu(m_hMenu, label);
|
||||
UMAAppendMenuItem(m_hMenu, label,key,modifiers);
|
||||
}
|
||||
else
|
||||
{
|
||||
MacInsertMenuItem(m_hMenu, label , pos);
|
||||
UMAInsertMenuItem(m_hMenu, label , pos,key,modifiers);
|
||||
}
|
||||
if ( pItem->GetId() == idMenuTitle )
|
||||
{
|
||||
if ( pos == (size_t)-1 )
|
||||
{
|
||||
UMADisableMenuItem( m_hMenu , CountMItems( m_hMenu ) ) ;
|
||||
UMADisableMenuItem( m_hMenu , CountMenuItems( m_hMenu ) ) ;
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -452,113 +305,9 @@ void wxMenu::SetTitle(const wxString& label)
|
||||
{
|
||||
Str255 title ;
|
||||
m_title = label ;
|
||||
wxMacBuildMenuString( title, NULL , NULL , label , false );
|
||||
wxMenuItem::MacBuildMenuString( title, NULL , NULL , label , false );
|
||||
UMASetMenuTitle( m_hMenu , title ) ;
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
void wxMenu::SetLabel(int id, const wxString& label)
|
||||
{
|
||||
Str255 maclabel ;
|
||||
int index ;
|
||||
wxMenuItem *item = FindItemForId(id) ;
|
||||
if (item==NULL)
|
||||
return;
|
||||
|
||||
index = MacGetIndexFromItem( item ) ;
|
||||
if (index < 1)
|
||||
return;
|
||||
|
||||
if (item->GetSubMenu()==NULL)
|
||||
{
|
||||
wxMacBuildMenuString( maclabel , NULL , NULL , label , false );
|
||||
::SetMenuItemText( m_hMenu , index , maclabel ) ;
|
||||
}
|
||||
else
|
||||
{
|
||||
wxMacBuildMenuString( maclabel , NULL , NULL , label , false );
|
||||
::SetMenuItemText( m_hMenu , index , maclabel ) ;
|
||||
}
|
||||
item->SetName(label);
|
||||
}
|
||||
|
||||
wxString wxMenu::GetLabel(int Id) const
|
||||
{
|
||||
wxMenuItem *pItem = FindItemForId(Id) ;
|
||||
return pItem->GetName() ;
|
||||
}
|
||||
|
||||
// Finds the item id matching the given string, -1 if not found.
|
||||
int wxMenu::FindItem (const wxString& itemString) const
|
||||
{
|
||||
char buf1[200];
|
||||
char buf2[200];
|
||||
wxStripMenuCodes ((char *)(const char *)itemString, buf1);
|
||||
|
||||
for (wxNode * node = m_menuItems.First (); node; node = node->Next ())
|
||||
{
|
||||
wxMenuItem *item = (wxMenuItem *) node->Data ();
|
||||
if (item->GetSubMenu())
|
||||
{
|
||||
int ans = item->GetSubMenu()->FindItem(itemString);
|
||||
if (ans > -1)
|
||||
return ans;
|
||||
}
|
||||
if ( !item->IsSeparator() )
|
||||
{
|
||||
wxStripMenuCodes((char *)item->GetName().c_str(), buf2);
|
||||
if (strcmp(buf1, buf2) == 0)
|
||||
return item->GetId();
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
wxMenuItem *wxMenu::FindItemForId(int itemId, wxMenu ** itemMenu) const
|
||||
{
|
||||
if (itemMenu)
|
||||
*itemMenu = NULL;
|
||||
for (wxNode * node = m_menuItems.First (); node; node = node->Next ())
|
||||
{
|
||||
wxMenuItem *item = (wxMenuItem *) node->Data ();
|
||||
|
||||
if (item->GetId() == itemId)
|
||||
{
|
||||
if (itemMenu)
|
||||
*itemMenu = (wxMenu *) this;
|
||||
return item;
|
||||
}
|
||||
|
||||
if (item->GetSubMenu())
|
||||
{
|
||||
wxMenuItem *ans = item->GetSubMenu()->FindItemForId (itemId, itemMenu);
|
||||
if (ans)
|
||||
return ans;
|
||||
}
|
||||
}
|
||||
|
||||
if (itemMenu)
|
||||
*itemMenu = NULL;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void wxMenu::SetHelpString(int itemId, const wxString& helpString)
|
||||
{
|
||||
wxMenuItem *item = FindItemForId (itemId);
|
||||
if (item)
|
||||
item->SetHelp(helpString);
|
||||
}
|
||||
|
||||
wxString wxMenu::GetHelpString (int itemId) const
|
||||
{
|
||||
wxMenuItem *item = FindItemForId (itemId);
|
||||
wxString str("");
|
||||
return (item == NULL) ? str : item->GetHelp();
|
||||
}
|
||||
*/
|
||||
|
||||
bool wxMenu::ProcessCommand(wxCommandEvent & event)
|
||||
{
|
||||
bool processed = FALSE;
|
||||
@@ -678,7 +427,10 @@ bool wxMenu::MacMenuSelect( wxEvtHandler* handler, long when , int macMenuId, in
|
||||
if (node)
|
||||
{
|
||||
wxMenuItem *pItem = (wxMenuItem*)node->Data();
|
||||
|
||||
|
||||
if (pItem->IsCheckable())
|
||||
pItem->Check(! pItem->IsChecked());
|
||||
|
||||
wxCommandEvent event(wxEVT_COMMAND_MENU_SELECTED, pItem->GetId());
|
||||
event.m_timeStamp = when;
|
||||
event.SetEventObject(handler);
|
||||
@@ -892,7 +644,8 @@ void wxMenuBar::MacInstallMenuBar()
|
||||
int pos ;
|
||||
wxMenu* menu = m_menus[i] , *subMenu = NULL ;
|
||||
|
||||
|
||||
#if !TARGET_CARBON
|
||||
/* the help menu does not exist in CARBON anymore */
|
||||
if( m_titles[i] == "?" || m_titles[i] == "&?" || m_titles[i] == wxApp::s_macHelpMenuTitleName )
|
||||
{
|
||||
MenuHandle mh = NULL ;
|
||||
@@ -906,8 +659,8 @@ void wxMenuBar::MacInstallMenuBar()
|
||||
formerHelpMenuItems = CountMenuItems( mh ) ;
|
||||
}
|
||||
|
||||
for (pos = 0 , node = menu->GetMenuItems().First(); node; node = node->Next(), pos++)
|
||||
{
|
||||
for (pos = 0 , node = menu->GetMenuItems().First(); node; node = node->Next(), pos++)
|
||||
{
|
||||
item = (wxMenuItem *)node->Data();
|
||||
subMenu = item->GetSubMenu() ;
|
||||
if (subMenu)
|
||||
@@ -919,12 +672,14 @@ void wxMenuBar::MacInstallMenuBar()
|
||||
if ( item->IsSeparator() )
|
||||
{
|
||||
if ( mh )
|
||||
::AppendMenu(mh, "\p-" );
|
||||
UMAAppendMenuItem(mh, "\p-" );
|
||||
}
|
||||
else
|
||||
{
|
||||
Str255 label ;
|
||||
wxMacBuildMenuString( label , NULL , NULL , item->GetText(), item->GetId() != wxApp::s_macAboutMenuItemId); // no shortcut in about menu
|
||||
UInt8 modifiers ;
|
||||
SInt16 key ;
|
||||
wxMenuItem::MacBuildMenuString( label, &key , &modifiers , item->GetText(), item->GetId() != wxApp::s_macAboutMenuItemId); // no shortcut in about menu
|
||||
if ( label[0] == 0 )
|
||||
{
|
||||
// we cannot add empty menus on mac
|
||||
@@ -933,36 +688,36 @@ void wxMenuBar::MacInstallMenuBar()
|
||||
}
|
||||
if ( item->GetId() == wxApp::s_macAboutMenuItemId )
|
||||
{
|
||||
::SetMenuItemText( GetMenuHandle( kwxMacAppleMenuId ) , 1 , label );
|
||||
// ::EnableMenuItem( GetMenuHandle( kwxMacAppleMenuId ) , 1 );
|
||||
::EnableItem( GetMenuHandle( kwxMacAppleMenuId ) , 1 );
|
||||
UMASetMenuItemText( GetMenuHandle( kwxMacAppleMenuId ) , 1 , label );
|
||||
UMAEnableMenuItem( GetMenuHandle( kwxMacAppleMenuId ) , 1 );
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( mh )
|
||||
::AppendMenu(mh, label );
|
||||
UMAAppendMenuItem(mh, label , key , modifiers );
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
wxMacBuildMenuString( label, NULL , NULL , m_titles[i] , false );
|
||||
wxMenuItem::MacBuildMenuString( label, NULL , NULL , m_titles[i] , false );
|
||||
UMASetMenuTitle( menu->GetHMenu() , label ) ;
|
||||
for (pos = 0, node = menu->GetMenuItems().First(); node; node = node->Next(), pos++)
|
||||
{
|
||||
for (pos = 0, node = menu->GetMenuItems().First(); node; node = node->Next(), pos++)
|
||||
{
|
||||
item = (wxMenuItem *)node->Data();
|
||||
subMenu = item->GetSubMenu() ;
|
||||
if (subMenu)
|
||||
{
|
||||
::InsertMenu( subMenu->GetHMenu() , -1 ) ;
|
||||
UMAInsertMenu( subMenu->GetHMenu() , -1 ) ;
|
||||
}
|
||||
}
|
||||
::InsertMenu(m_menus[i]->GetHMenu(), 0);
|
||||
UMAInsertMenu(m_menus[i]->GetHMenu(), 0);
|
||||
}
|
||||
}
|
||||
::DrawMenuBar() ;
|
||||
UMADrawMenuBar() ;
|
||||
|
||||
s_macInstalledMenuBar = this;
|
||||
}
|
||||
@@ -1037,18 +792,18 @@ wxMenu *wxMenuBar::Replace(size_t pos, wxMenu *menu, const wxString& title)
|
||||
{
|
||||
if (s_macInstalledMenuBar == this)
|
||||
{
|
||||
::DeleteMenu( menuOld->MacGetMenuId() /* m_menus[pos]->MacGetMenuId() */ ) ;
|
||||
UMADeleteMenu( menuOld->MacGetMenuId() /* m_menus[pos]->MacGetMenuId() */ ) ;
|
||||
{
|
||||
Str255 label;
|
||||
wxMacBuildMenuString( label, NULL , NULL , title , false );
|
||||
wxMenuItem::MacBuildMenuString( label, NULL , NULL , title , false );
|
||||
UMASetMenuTitle( menu->GetHMenu() , label ) ;
|
||||
if ( pos == m_menus.GetCount() - 1)
|
||||
{
|
||||
::InsertMenu( menu->GetHMenu() , 0 ) ;
|
||||
UMAInsertMenu( menu->GetHMenu() , 0 ) ;
|
||||
}
|
||||
else
|
||||
{
|
||||
::InsertMenu( menu->GetHMenu() , m_menus[pos+1]->MacGetMenuId() ) ;
|
||||
UMAInsertMenu( menu->GetHMenu() , m_menus[pos+1]->MacGetMenuId() ) ;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1206,6 +961,16 @@ bool wxMenuBar::Append(wxMenu *menu, const wxString& title)
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void wxMenuBar::Attach(wxFrame *frame)
|
||||
{
|
||||
// wxASSERT_MSG( !IsAttached(), wxT("menubar already attached!") );
|
||||
|
||||
m_menuBarFrame = frame;
|
||||
|
||||
#if wxUSE_ACCEL
|
||||
RebuildAccelTable();
|
||||
#endif // wxUSE_ACCEL
|
||||
}
|
||||
// ---------------------------------------------------------------------------
|
||||
// wxMenuBar searching for menu items
|
||||
// ---------------------------------------------------------------------------
|
||||
|
Reference in New Issue
Block a user