no real changes, just use HandleWindowEvent() instead of GetEventHandler()->SafelyPro...
[wxWidgets.git] / src / common / menucmn.cpp
1 ///////////////////////////////////////////////////////////////////////////////
2 // Name: src/common/menucmn.cpp
3 // Purpose: wxMenu and wxMenuBar methods common to all ports
4 // Author: Vadim Zeitlin
5 // Modified by:
6 // Created: 26.10.99
7 // RCS-ID: $Id$
8 // Copyright: (c) wxWidgets team
9 // Licence: wxWindows licence
10 ///////////////////////////////////////////////////////////////////////////////
11
12 // ============================================================================
13 // declarations
14 // ============================================================================
15
16 // ----------------------------------------------------------------------------
17 // headers
18 // ----------------------------------------------------------------------------
19
20 // For compilers that support precompilation, includes "wx.h".
21 #include "wx/wxprec.h"
22
23 #ifdef __BORLANDC__
24 #pragma hdrstop
25 #endif
26
27 #if wxUSE_MENUS
28
29 #ifndef WX_PRECOMP
30 #include "wx/intl.h"
31 #include "wx/log.h"
32 #include "wx/menu.h"
33 #endif
34
35 #include "wx/stockitem.h"
36
37 // ----------------------------------------------------------------------------
38 // template lists
39 // ----------------------------------------------------------------------------
40
41 #include "wx/listimpl.cpp"
42
43 WX_DEFINE_LIST(wxMenuList)
44 WX_DEFINE_LIST(wxMenuItemList)
45
46 // ============================================================================
47 // implementation
48 // ============================================================================
49
50 // ----------------------------------------------------------------------------
51 // wxMenuItemBase
52 // ----------------------------------------------------------------------------
53
54 wxMenuItemBase::wxMenuItemBase(wxMenu *parentMenu,
55 int id,
56 const wxString& text,
57 const wxString& help,
58 wxItemKind kind,
59 wxMenu *subMenu)
60 {
61 wxASSERT_MSG( parentMenu != NULL, wxT("menuitem should have a menu") );
62
63 m_parentMenu = parentMenu;
64 m_subMenu = subMenu;
65 m_isEnabled = true;
66 m_isChecked = false;
67 m_id = id;
68 m_kind = kind;
69 if (m_id == wxID_ANY)
70 m_id = wxWindow::NewControlId();
71 if (m_id == wxID_SEPARATOR)
72 m_kind = wxITEM_SEPARATOR;
73
74 SetItemLabel(text);
75 SetHelp(help);
76 }
77
78 wxMenuItemBase::~wxMenuItemBase()
79 {
80 delete m_subMenu;
81 }
82
83 #if wxUSE_ACCEL
84
85 wxAcceleratorEntry *wxMenuItemBase::GetAccel() const
86 {
87 return wxAcceleratorEntry::Create(GetItemLabel());
88 }
89
90 void wxMenuItemBase::SetAccel(wxAcceleratorEntry *accel)
91 {
92 wxString text = m_text.BeforeFirst(wxT('\t'));
93 if ( accel )
94 {
95 text += wxT('\t');
96 text += accel->ToString();
97 }
98
99 SetItemLabel(text);
100 }
101
102 #endif // wxUSE_ACCEL
103
104 void wxMenuItemBase::SetItemLabel(const wxString& str)
105 {
106 m_text = str;
107
108 if ( m_text.empty() && !IsSeparator() )
109 {
110 wxASSERT_MSG( wxIsStockID(GetId()),
111 wxT("A non-stock menu item with an empty label?") );
112 m_text = wxGetStockLabel(GetId(), wxSTOCK_WITH_ACCELERATOR |
113 wxSTOCK_WITH_MNEMONIC);
114 }
115 }
116
117 void wxMenuItemBase::SetHelp(const wxString& str)
118 {
119 m_help = str;
120
121 if ( m_help.empty() && !IsSeparator() && wxIsStockID(GetId()) )
122 {
123 // get a stock help string
124 m_help = wxGetStockHelpString(GetId());
125 }
126 }
127
128 #if WXWIN_COMPATIBILITY_2_8
129 wxString wxMenuItemBase::GetLabelFromText(const wxString& text)
130 {
131 return GetLabelText(text);
132 }
133 #endif
134
135 bool wxMenuBase::ms_locked = true;
136
137 // ----------------------------------------------------------------------------
138 // wxMenu ctor and dtor
139 // ----------------------------------------------------------------------------
140
141 void wxMenuBase::Init(long style)
142 {
143 m_menuBar = (wxMenuBar *)NULL;
144 m_menuParent = (wxMenu *)NULL;
145
146 m_invokingWindow = (wxWindow *)NULL;
147 m_style = style;
148 m_clientData = (void *)NULL;
149 m_eventHandler = this;
150 }
151
152 wxMenuBase::~wxMenuBase()
153 {
154 WX_CLEAR_LIST(wxMenuItemList, m_items);
155
156 // Actually, in GTK, the submenus have to get deleted first.
157 }
158
159 // ----------------------------------------------------------------------------
160 // wxMenu item adding/removing
161 // ----------------------------------------------------------------------------
162
163 void wxMenuBase::AddSubMenu(wxMenu *submenu)
164 {
165 wxCHECK_RET( submenu, _T("can't add a NULL submenu") );
166
167 submenu->SetParent((wxMenu *)this);
168 }
169
170 wxMenuItem* wxMenuBase::DoAppend(wxMenuItem *item)
171 {
172 wxCHECK_MSG( item, NULL, wxT("invalid item in wxMenu::Append()") );
173
174 m_items.Append(item);
175 item->SetMenu((wxMenu*)this);
176 if ( item->IsSubMenu() )
177 {
178 AddSubMenu(item->GetSubMenu());
179 }
180
181 return item;
182 }
183
184 wxMenuItem* wxMenuBase::Insert(size_t pos, wxMenuItem *item)
185 {
186 wxCHECK_MSG( item, NULL, wxT("invalid item in wxMenu::Insert") );
187
188 if ( pos == GetMenuItemCount() )
189 {
190 return DoAppend(item);
191 }
192 else
193 {
194 wxCHECK_MSG( pos < GetMenuItemCount(), NULL,
195 wxT("invalid index in wxMenu::Insert") );
196
197 return DoInsert(pos, item);
198 }
199 }
200
201 wxMenuItem* wxMenuBase::DoInsert(size_t pos, wxMenuItem *item)
202 {
203 wxCHECK_MSG( item, NULL, wxT("invalid item in wxMenu::Insert()") );
204
205 wxMenuItemList::compatibility_iterator node = m_items.Item(pos);
206 wxCHECK_MSG( node, NULL, wxT("invalid index in wxMenu::Insert()") );
207
208 m_items.Insert(node, item);
209 item->SetMenu((wxMenu*)this);
210 if ( item->IsSubMenu() )
211 {
212 AddSubMenu(item->GetSubMenu());
213 }
214
215 return item;
216 }
217
218 wxMenuItem *wxMenuBase::Remove(wxMenuItem *item)
219 {
220 wxCHECK_MSG( item, NULL, wxT("invalid item in wxMenu::Remove") );
221
222 return DoRemove(item);
223 }
224
225 wxMenuItem *wxMenuBase::DoRemove(wxMenuItem *item)
226 {
227 wxMenuItemList::compatibility_iterator node = m_items.Find(item);
228
229 // if we get here, the item is valid or one of Remove() functions is broken
230 wxCHECK_MSG( node, NULL, wxT("bug in wxMenu::Remove logic") );
231
232 // we detach the item, but we do delete the list node (i.e. don't call
233 // DetachNode() here!)
234 m_items.Erase(node);
235
236 // item isn't attached to anything any more
237 item->SetMenu((wxMenu *)NULL);
238 wxMenu *submenu = item->GetSubMenu();
239 if ( submenu )
240 {
241 submenu->SetParent((wxMenu *)NULL);
242 if ( submenu->IsAttached() )
243 submenu->Detach();
244 }
245
246 return item;
247 }
248
249 bool wxMenuBase::Delete(wxMenuItem *item)
250 {
251 wxCHECK_MSG( item, false, wxT("invalid item in wxMenu::Delete") );
252
253 return DoDelete(item);
254 }
255
256 bool wxMenuBase::DoDelete(wxMenuItem *item)
257 {
258 wxMenuItem *item2 = DoRemove(item);
259 wxCHECK_MSG( item2, false, wxT("failed to delete menu item") );
260
261 // don't delete the submenu
262 item2->SetSubMenu((wxMenu *)NULL);
263
264 delete item2;
265
266 return true;
267 }
268
269 bool wxMenuBase::Destroy(wxMenuItem *item)
270 {
271 wxCHECK_MSG( item, false, wxT("invalid item in wxMenu::Destroy") );
272
273 return DoDestroy(item);
274 }
275
276 bool wxMenuBase::DoDestroy(wxMenuItem *item)
277 {
278 wxMenuItem *item2 = DoRemove(item);
279 wxCHECK_MSG( item2, false, wxT("failed to delete menu item") );
280
281 delete item2;
282
283 return true;
284 }
285
286 // ----------------------------------------------------------------------------
287 // wxMenu searching for items
288 // ----------------------------------------------------------------------------
289
290 // Finds the item id matching the given string, wxNOT_FOUND if not found.
291 int wxMenuBase::FindItem(const wxString& text) const
292 {
293 wxString label = wxMenuItem::GetLabelText(text);
294 for ( wxMenuItemList::compatibility_iterator node = m_items.GetFirst();
295 node;
296 node = node->GetNext() )
297 {
298 wxMenuItem *item = node->GetData();
299 if ( item->IsSubMenu() )
300 {
301 int rc = item->GetSubMenu()->FindItem(label);
302 if ( rc != wxNOT_FOUND )
303 return rc;
304 }
305
306 // we execute this code for submenus as well to alllow finding them by
307 // name just like the ordinary items
308 if ( !item->IsSeparator() )
309 {
310 if ( item->GetItemLabelText() == label )
311 return item->GetId();
312 }
313 }
314
315 return wxNOT_FOUND;
316 }
317
318 // recursive search for item by id
319 wxMenuItem *wxMenuBase::FindItem(int itemId, wxMenu **itemMenu) const
320 {
321 if ( itemMenu )
322 *itemMenu = NULL;
323
324 wxMenuItem *item = NULL;
325 for ( wxMenuItemList::compatibility_iterator node = m_items.GetFirst();
326 node && !item;
327 node = node->GetNext() )
328 {
329 item = node->GetData();
330
331 if ( item->GetId() == itemId )
332 {
333 if ( itemMenu )
334 *itemMenu = (wxMenu *)this;
335 }
336 else if ( item->IsSubMenu() )
337 {
338 item = item->GetSubMenu()->FindItem(itemId, itemMenu);
339 }
340 else
341 {
342 // don't exit the loop
343 item = NULL;
344 }
345 }
346
347 return item;
348 }
349
350 // non recursive search
351 wxMenuItem *wxMenuBase::FindChildItem(int id, size_t *ppos) const
352 {
353 wxMenuItem *item = (wxMenuItem *)NULL;
354 wxMenuItemList::compatibility_iterator node = GetMenuItems().GetFirst();
355
356 size_t pos;
357 for ( pos = 0; node; pos++ )
358 {
359 if ( node->GetData()->GetId() == id )
360 {
361 item = node->GetData();
362
363 break;
364 }
365
366 node = node->GetNext();
367 }
368
369 if ( ppos )
370 {
371 *ppos = item ? pos : (size_t)wxNOT_FOUND;
372 }
373
374 return item;
375 }
376
377 // find by position
378 wxMenuItem* wxMenuBase::FindItemByPosition(size_t position) const
379 {
380 wxCHECK_MSG( position < m_items.GetCount(), NULL,
381 _T("wxMenu::FindItemByPosition(): invalid menu index") );
382
383 return m_items.Item( position )->GetData();
384 }
385
386 // ----------------------------------------------------------------------------
387 // wxMenu helpers used by derived classes
388 // ----------------------------------------------------------------------------
389
390 // Update a menu and all submenus recursively. source is the object that has
391 // the update event handlers defined for it. If NULL, the menu or associated
392 // window will be used.
393 void wxMenuBase::UpdateUI(wxEvtHandler* source)
394 {
395 if (GetInvokingWindow())
396 {
397 // Don't update menus if the parent
398 // frame is about to get deleted
399 wxWindow *tlw = wxGetTopLevelParent( GetInvokingWindow() );
400 if (tlw && wxPendingDelete.Member(tlw))
401 return;
402 }
403
404 if ( !source && GetInvokingWindow() )
405 source = GetInvokingWindow()->GetEventHandler();
406 if ( !source )
407 source = GetEventHandler();
408 if ( !source )
409 source = this;
410
411 wxMenuItemList::compatibility_iterator node = GetMenuItems().GetFirst();
412 while ( node )
413 {
414 wxMenuItem* item = node->GetData();
415 if ( !item->IsSeparator() )
416 {
417 wxWindowID id = item->GetId();
418 wxUpdateUIEvent event(id);
419 event.SetEventObject( source );
420
421 if ( source->ProcessEvent(event) )
422 {
423 // if anything changed, update the changed attribute
424 if (event.GetSetText())
425 SetLabel(id, event.GetText());
426 if (event.GetSetChecked())
427 Check(id, event.GetChecked());
428 if (event.GetSetEnabled())
429 Enable(id, event.GetEnabled());
430 }
431
432 // recurse to the submenus
433 if ( item->GetSubMenu() )
434 item->GetSubMenu()->UpdateUI(source);
435 }
436 //else: item is a separator (which doesn't process update UI events)
437
438 node = node->GetNext();
439 }
440 }
441
442 bool wxMenuBase::SendEvent(int id, int checked)
443 {
444 wxCommandEvent event(wxEVT_COMMAND_MENU_SELECTED, id);
445 event.SetEventObject(this);
446 event.SetInt(checked);
447
448 bool processed = false;
449
450 // Try the menu's event handler
451 // if ( !processed )
452 {
453 wxEvtHandler *handler = GetEventHandler();
454 if ( handler )
455 processed = handler->SafelyProcessEvent(event);
456 }
457
458 // Try the window the menu was popped up from (and up through the
459 // hierarchy)
460 if ( !processed )
461 {
462 const wxMenuBase *menu = this;
463 while ( menu )
464 {
465 wxWindow *win = menu->GetInvokingWindow();
466 if ( win )
467 {
468 processed = win->HandleWindowEvent(event);
469 break;
470 }
471
472 menu = menu->GetParent();
473 }
474 }
475
476 return processed;
477 }
478
479 // ----------------------------------------------------------------------------
480 // wxMenu attaching/detaching to/from menu bar
481 // ----------------------------------------------------------------------------
482
483 wxMenuBar* wxMenuBase::GetMenuBar() const
484 {
485 if(GetParent())
486 return GetParent()->GetMenuBar();
487 return m_menuBar;
488 }
489
490 void wxMenuBase::Attach(wxMenuBarBase *menubar)
491 {
492 // use Detach() instead!
493 wxASSERT_MSG( menubar, _T("menu can't be attached to NULL menubar") );
494
495 // use IsAttached() to prevent this from happening
496 wxASSERT_MSG( !m_menuBar, _T("attaching menu twice?") );
497
498 m_menuBar = (wxMenuBar *)menubar;
499 }
500
501 void wxMenuBase::Detach()
502 {
503 // use IsAttached() to prevent this from happening
504 wxASSERT_MSG( m_menuBar, _T("detaching unattached menu?") );
505
506 m_menuBar = NULL;
507 }
508
509 // ----------------------------------------------------------------------------
510 // wxMenu functions forwarded to wxMenuItem
511 // ----------------------------------------------------------------------------
512
513 void wxMenuBase::Enable( int id, bool enable )
514 {
515 wxMenuItem *item = FindItem(id);
516
517 wxCHECK_RET( item, wxT("wxMenu::Enable: no such item") );
518
519 item->Enable(enable);
520 }
521
522 bool wxMenuBase::IsEnabled( int id ) const
523 {
524 wxMenuItem *item = FindItem(id);
525
526 wxCHECK_MSG( item, false, wxT("wxMenu::IsEnabled: no such item") );
527
528 return item->IsEnabled();
529 }
530
531 void wxMenuBase::Check( int id, bool enable )
532 {
533 wxMenuItem *item = FindItem(id);
534
535 wxCHECK_RET( item, wxT("wxMenu::Check: no such item") );
536
537 item->Check(enable);
538 }
539
540 bool wxMenuBase::IsChecked( int id ) const
541 {
542 wxMenuItem *item = FindItem(id);
543
544 wxCHECK_MSG( item, false, wxT("wxMenu::IsChecked: no such item") );
545
546 return item->IsChecked();
547 }
548
549 void wxMenuBase::SetLabel( int id, const wxString &label )
550 {
551 wxMenuItem *item = FindItem(id);
552
553 wxCHECK_RET( item, wxT("wxMenu::SetLabel: no such item") );
554
555 item->SetItemLabel(label);
556 }
557
558 wxString wxMenuBase::GetLabel( int id ) const
559 {
560 wxMenuItem *item = FindItem(id);
561
562 wxCHECK_MSG( item, wxEmptyString, wxT("wxMenu::GetLabel: no such item") );
563
564 return item->GetItemLabel();
565 }
566
567 void wxMenuBase::SetHelpString( int id, const wxString& helpString )
568 {
569 wxMenuItem *item = FindItem(id);
570
571 wxCHECK_RET( item, wxT("wxMenu::SetHelpString: no such item") );
572
573 item->SetHelp( helpString );
574 }
575
576 wxString wxMenuBase::GetHelpString( int id ) const
577 {
578 wxMenuItem *item = FindItem(id);
579
580 wxCHECK_MSG( item, wxEmptyString, wxT("wxMenu::GetHelpString: no such item") );
581
582 return item->GetHelp();
583 }
584
585 // ----------------------------------------------------------------------------
586 // wxMenuBarBase ctor and dtor
587 // ----------------------------------------------------------------------------
588
589 wxMenuBarBase::wxMenuBarBase()
590 {
591 // not attached yet
592 m_menuBarFrame = NULL;
593 }
594
595 wxMenuBarBase::~wxMenuBarBase()
596 {
597 WX_CLEAR_LIST(wxMenuList, m_menus);
598 }
599
600 // ----------------------------------------------------------------------------
601 // wxMenuBar item access: the base class versions manage m_menus list, the
602 // derived class should reflect the changes in the real menubar
603 // ----------------------------------------------------------------------------
604
605 wxMenu *wxMenuBarBase::GetMenu(size_t pos) const
606 {
607 wxMenuList::compatibility_iterator node = m_menus.Item(pos);
608 wxCHECK_MSG( node, NULL, wxT("bad index in wxMenuBar::GetMenu()") );
609
610 return node->GetData();
611 }
612
613 bool wxMenuBarBase::Append(wxMenu *menu, const wxString& WXUNUSED(title))
614 {
615 wxCHECK_MSG( menu, false, wxT("can't append NULL menu") );
616
617 m_menus.Append(menu);
618 menu->Attach(this);
619
620 return true;
621 }
622
623 bool wxMenuBarBase::Insert(size_t pos, wxMenu *menu,
624 const wxString& title)
625 {
626 if ( pos == m_menus.GetCount() )
627 {
628 return wxMenuBarBase::Append(menu, title);
629 }
630 else // not at the end
631 {
632 wxCHECK_MSG( menu, false, wxT("can't insert NULL menu") );
633
634 wxMenuList::compatibility_iterator node = m_menus.Item(pos);
635 wxCHECK_MSG( node, false, wxT("bad index in wxMenuBar::Insert()") );
636
637 m_menus.Insert(node, menu);
638 menu->Attach(this);
639
640 return true;
641 }
642 }
643
644 wxMenu *wxMenuBarBase::Replace(size_t pos, wxMenu *menu,
645 const wxString& WXUNUSED(title))
646 {
647 wxCHECK_MSG( menu, NULL, wxT("can't insert NULL menu") );
648
649 wxMenuList::compatibility_iterator node = m_menus.Item(pos);
650 wxCHECK_MSG( node, NULL, wxT("bad index in wxMenuBar::Replace()") );
651
652 wxMenu *menuOld = node->GetData();
653 node->SetData(menu);
654
655 menu->Attach(this);
656 menuOld->Detach();
657
658 return menuOld;
659 }
660
661 wxMenu *wxMenuBarBase::Remove(size_t pos)
662 {
663 wxMenuList::compatibility_iterator node = m_menus.Item(pos);
664 wxCHECK_MSG( node, NULL, wxT("bad index in wxMenuBar::Remove()") );
665
666 wxMenu *menu = node->GetData();
667 m_menus.Erase(node);
668 menu->Detach();
669
670 return menu;
671 }
672
673 int wxMenuBarBase::FindMenu(const wxString& title) const
674 {
675 wxString label = wxMenuItem::GetLabelText(title);
676
677 size_t count = GetMenuCount();
678 for ( size_t i = 0; i < count; i++ )
679 {
680 wxString title2 = GetMenuLabel(i);
681 if ( (title2 == title) ||
682 (wxMenuItem::GetLabelText(title2) == label) )
683 {
684 // found
685 return (int)i;
686 }
687 }
688
689 return wxNOT_FOUND;
690
691 }
692
693 // ----------------------------------------------------------------------------
694 // wxMenuBar attaching/detaching to/from the frame
695 // ----------------------------------------------------------------------------
696
697 void wxMenuBarBase::Attach(wxFrame *frame)
698 {
699 wxASSERT_MSG( !IsAttached(), wxT("menubar already attached!") );
700
701 m_menuBarFrame = frame;
702 }
703
704 void wxMenuBarBase::Detach()
705 {
706 wxASSERT_MSG( IsAttached(), wxT("detaching unattached menubar") );
707
708 m_menuBarFrame = NULL;
709 }
710
711 // ----------------------------------------------------------------------------
712 // wxMenuBar searching for items
713 // ----------------------------------------------------------------------------
714
715 wxMenuItem *wxMenuBarBase::FindItem(int id, wxMenu **menu) const
716 {
717 if ( menu )
718 *menu = NULL;
719
720 wxMenuItem *item = NULL;
721 size_t count = GetMenuCount(), i;
722 wxMenuList::const_iterator it;
723 for ( i = 0, it = m_menus.begin(); !item && (i < count); i++, it++ )
724 {
725 item = (*it)->FindItem(id, menu);
726 }
727
728 return item;
729 }
730
731 int wxMenuBarBase::FindMenuItem(const wxString& menu, const wxString& item) const
732 {
733 wxString label = wxMenuItem::GetLabelText(menu);
734
735 int i = 0;
736 wxMenuList::compatibility_iterator node;
737 for ( node = m_menus.GetFirst(); node; node = node->GetNext(), i++ )
738 {
739 if ( label == wxMenuItem::GetLabelText(GetMenuLabel(i)) )
740 return node->GetData()->FindItem(item);
741 }
742
743 return wxNOT_FOUND;
744 }
745
746 // ---------------------------------------------------------------------------
747 // wxMenuBar functions forwarded to wxMenuItem
748 // ---------------------------------------------------------------------------
749
750 void wxMenuBarBase::Enable(int id, bool enable)
751 {
752 wxMenuItem *item = FindItem(id);
753
754 wxCHECK_RET( item, wxT("attempt to enable an item which doesn't exist") );
755
756 item->Enable(enable);
757 }
758
759 void wxMenuBarBase::Check(int id, bool check)
760 {
761 wxMenuItem *item = FindItem(id);
762
763 wxCHECK_RET( item, wxT("attempt to check an item which doesn't exist") );
764 wxCHECK_RET( item->IsCheckable(), wxT("attempt to check an uncheckable item") );
765
766 item->Check(check);
767 }
768
769 bool wxMenuBarBase::IsChecked(int id) const
770 {
771 wxMenuItem *item = FindItem(id);
772
773 wxCHECK_MSG( item, false, wxT("wxMenuBar::IsChecked(): no such item") );
774
775 return item->IsChecked();
776 }
777
778 bool wxMenuBarBase::IsEnabled(int id) const
779 {
780 wxMenuItem *item = FindItem(id);
781
782 wxCHECK_MSG( item, false, wxT("wxMenuBar::IsEnabled(): no such item") );
783
784 return item->IsEnabled();
785 }
786
787 void wxMenuBarBase::SetLabel(int id, const wxString& label)
788 {
789 wxMenuItem *item = FindItem(id);
790
791 wxCHECK_RET( item, wxT("wxMenuBar::SetLabel(): no such item") );
792
793 item->SetItemLabel(label);
794 }
795
796 wxString wxMenuBarBase::GetLabel(int id) const
797 {
798 wxMenuItem *item = FindItem(id);
799
800 wxCHECK_MSG( item, wxEmptyString,
801 wxT("wxMenuBar::GetLabel(): no such item") );
802
803 return item->GetItemLabel();
804 }
805
806 void wxMenuBarBase::SetHelpString(int id, const wxString& helpString)
807 {
808 wxMenuItem *item = FindItem(id);
809
810 wxCHECK_RET( item, wxT("wxMenuBar::SetHelpString(): no such item") );
811
812 item->SetHelp(helpString);
813 }
814
815 wxString wxMenuBarBase::GetHelpString(int id) const
816 {
817 wxMenuItem *item = FindItem(id);
818
819 wxCHECK_MSG( item, wxEmptyString,
820 wxT("wxMenuBar::GetHelpString(): no such item") );
821
822 return item->GetHelp();
823 }
824
825 void wxMenuBarBase::UpdateMenus( void )
826 {
827 wxEvtHandler* source;
828 wxMenu* menu;
829 int nCount = GetMenuCount();
830 for (int n = 0; n < nCount; n++)
831 {
832 menu = GetMenu( n );
833 if (menu != NULL)
834 {
835 source = menu->GetEventHandler();
836 if (source != NULL)
837 menu->UpdateUI( source );
838 }
839 }
840 }
841
842 #if WXWIN_COMPATIBILITY_2_8
843 // get or change the label of the menu at given position
844 void wxMenuBarBase::SetLabelTop(size_t pos, const wxString& label)
845 {
846 SetMenuLabel(pos, label);
847 }
848
849 wxString wxMenuBarBase::GetLabelTop(size_t pos) const
850 {
851 return GetMenuLabelText(pos);
852 }
853 #endif
854
855 #endif // wxUSE_MENUS