factoring common code, applying patch 1825183

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/branches/WX_2_8_BRANCH@49618 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Stefan Csomor
2007-11-04 10:32:30 +00:00
parent 8a4529c6a6
commit 639db60ccb

View File

@@ -139,109 +139,89 @@ pascal OSStatus wxDockEventHandler( EventHandlerCallRef inHandlerCallRef,
wxDockTaskBarIcon* pTB = (wxDockTaskBarIcon*) pData; wxDockTaskBarIcon* pTB = (wxDockTaskBarIcon*) pData;
const UInt32 eventClass = GetEventClass(inEvent); const UInt32 eventClass = GetEventClass(inEvent);
const UInt32 eventKind = GetEventKind(inEvent); const UInt32 eventKind = GetEventKind(inEvent);
OSStatus err = eventNotHandledErr;
// Handle wxTaskBar menu events (note that this is a global event handler // Handle wxTaskBar menu events (note that this is a global event handler
// so it will actually get called by all commands/menus) // so it will actually get called by all commands/menus)
if ((eventClass == kEventClassCommand) && (eventKind == kEventCommandProcess)) if ((eventClass == kEventClassCommand) && (eventKind == kEventCommandProcess || eventKind == kEventCommandUpdateStatus ))
{ {
// if we have no taskbar menu quickly pass it back to wxApp // if we have no taskbar menu quickly pass it back to wxApp
if (pTB->m_pMenu == NULL) if (pTB->m_pMenu != NULL)
return eventNotHandledErr;
// This is the real reason why we need this. Normally menus
// get handled in wxMacAppEventHandler
//
// pascal OSStatus wxMacAppEventHandler(EventHandlerCallRef handler,
// EventRef event, void *data)
//
// However, in the case of a taskbar menu call
// command.menu.menuRef IS NULL!
// Which causes the wxApp handler just to skip it.
MenuRef taskbarMenuRef = MAC_WXHMENU(pTB->m_pMenu->GetHMenu());
OSStatus err;
// get the HICommand from the event
HICommand command;
err = GetEventParameter(
inEvent, kEventParamDirectObject,
typeHICommand, NULL,
sizeof(HICommand), NULL, &command );
if (err == noErr)
{ {
// Obtain the REAL menuRef and the menuItemIndex in the real menuRef // This is the real reason why we need this. Normally menus
// // get handled in wxMacAppEventHandler
// NOTE: menuRef is generally used here for submenus, as // However, in the case of a taskbar menu call
// GetMenuItemRefCon could give an incorrect wxMenuItem if we pass // command.menu.menuRef IS NULL!
// just the top level wxTaskBar menu // Which causes the wxApp handler just to skip it.
MenuItemIndex menuItemIndex;
MenuRef menuRef;
err = GetIndMenuItemWithCommandID( // get the HICommand from the event
taskbarMenuRef, HICommand command;
command.commandID, if (GetEventParameter(inEvent, kEventParamDirectObject,
1, &menuRef, &menuItemIndex ); typeHICommand, NULL,sizeof(HICommand), NULL, &command ) == noErr)
if (err == noErr)
{ {
MenuCommand id = command.commandID; // Obtain the REAL menuRef and the menuItemIndex in the real menuRef
wxMenuItem *item = NULL; //
// NOTE: menuRef is generally used here for submenus, as
// GetMenuItemRefCon could give an incorrect wxMenuItem if we pass
// just the top level wxTaskBar menu
MenuItemIndex menuItemIndex;
MenuRef menuRef;
MenuRef taskbarMenuRef = MAC_WXHMENU(pTB->m_pMenu->GetHMenu());
if (id != 0) // get the wxMenuItem reference from the MenuRef // the next command is only successful if it was a command from the taskbar menu
GetMenuItemRefCon( menuRef, menuItemIndex, (URefCon*) &item ); // otherwise we pass it on
if (GetIndMenuItemWithCommandID(taskbarMenuRef,command.commandID,
if (item) 1, &menuRef, &menuItemIndex ) == noErr)
{ {
// Handle items that are checkable wxMenu* itemMenu = wxFindMenuFromMacMenu( menuRef ) ;
// FIXME: Doesn't work (at least on 10.2)! int id = wxMacCommandToId( command.commandID ) ;
if (item->IsCheckable()) wxMenuItem *item = NULL;
item->Check( !item->IsChecked() );
// send the wxEvent to the wxMenu if (id != 0) // get the wxMenuItem reference from the MenuRef
item->GetMenu()->SendEvent( id, item->IsCheckable() ? item->IsChecked() : -1 ); GetMenuItemRefCon( menuRef, menuItemIndex, (URefCon*) &item );
// successfully handled the event if (item && itemMenu )
err = noErr; {
if ( eventKind == kEventCommandProcess )
err = itemMenu->MacHandleCommandProcess( item, id );
else if ( eventKind == kEventCommandUpdateStatus )
err = itemMenu->MacHandleCommandUpdateStatus( item, id );
}
} }
} }
} //end if noErr on getting HICommand from event } //end if noErr on getting HICommand from event
// return whether we handled the event or not
return err;
} }
else if ((eventClass == kEventClassApplication) && (eventKind == kEventAppGetDockTileMenu ))
// We better have a kEventClassApplication/kEventAppGetDockTileMenu combo here,
// otherwise something is truly funky
wxASSERT(eventClass == kEventClassApplication &&
eventKind == kEventAppGetDockTileMenu);
// process the right click events
// NB: This may result in double or even triple-creation of the menus
// We need to do this for 2.4 compat, however
wxTaskBarIconEvent downevt(wxEVT_TASKBAR_RIGHT_DOWN, NULL);
pTB->m_parent->ProcessEvent(downevt);
wxTaskBarIconEvent upevt(wxEVT_TASKBAR_RIGHT_UP, NULL);
pTB->m_parent->ProcessEvent(upevt);
// create popup menu
wxMenu* menu = pTB->DoCreatePopupMenu();
OSStatus err = eventNotHandledErr;
if (menu != NULL)
{ {
// note to self - a MenuRef *is* a MenuHandle // process the right click events
MenuRef hMenu = MAC_WXHMENU(menu->GetHMenu()); // NB: This may result in double or even triple-creation of the menus
// We need to do this for 2.4 compat, however
wxTaskBarIconEvent downevt(wxEVT_TASKBAR_RIGHT_DOWN, NULL);
pTB->m_parent->ProcessEvent(downevt);
// When SetEventParameter is called it will decrement wxTaskBarIconEvent upevt(wxEVT_TASKBAR_RIGHT_UP, NULL);
// the reference count of the menu - we need to make pTB->m_parent->ProcessEvent(upevt);
// sure it stays around in the wxMenu class here
CFRetain(hMenu);
// set the actual dock menu // create popup menu
err = SetEventParameter( wxMenu* menu = pTB->DoCreatePopupMenu();
inEvent, kEventParamMenuRef,
typeMenuRef, sizeof(MenuRef), &hMenu ); if (menu != NULL)
verify_noerr( err ); {
// note to self - a MenuRef *is* a MenuHandle
MenuRef hMenu = MAC_WXHMENU(menu->GetHMenu());
// When SetEventParameter is called it will decrement
// the reference count of the menu - we need to make
// sure it stays around in the wxMenu class here
CFRetain(hMenu);
// set the actual dock menu
err = SetEventParameter(
inEvent, kEventParamMenuRef,
typeMenuRef, sizeof(MenuRef), &hMenu );
verify_noerr( err );
}
} }
return err; return err;
@@ -317,6 +297,7 @@ wxDockTaskBarIcon::wxDockTaskBarIcon(wxTaskBarIcon* parent)
EventTypeSpec tbEventList[] = EventTypeSpec tbEventList[] =
{ {
{ kEventClassCommand, kEventProcessCommand }, { kEventClassCommand, kEventProcessCommand },
{ kEventClassCommand, kEventCommandUpdateStatus },
{ kEventClassApplication, kEventAppGetDockTileMenu } { kEventClassApplication, kEventAppGetDockTileMenu }
}; };