Merge in from trunk r68684 - r69046
[wxWidgets.git] / src / osx / carbon / uma.cpp
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: src/osx/carbon/uma.cpp
3 // Purpose: UMA support
4 // Author: Stefan Csomor
5 // Modified by:
6 // Created: 04/01/98
7 // RCS-ID: $Id$
8 // Copyright: (c) Stefan Csomor
9 // Licence: The wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
11
12 #include "wx/wxprec.h"
13
14 #include "wx/osx/uma.h"
15
16 #if wxUSE_GUI
17
18 #include "wx/toplevel.h"
19 #include "wx/dc.h"
20
21 #include "wx/osx/uma.h"
22
23 // menu manager
24
25 #if wxOSX_USE_CARBON
26
27 MenuRef UMANewMenu( SInt16 id , const wxString& title , wxFontEncoding encoding )
28 {
29 wxString str = wxStripMenuCodes( title ) ;
30 MenuRef menu ;
31
32 CreateNewMenu( id , 0 , &menu ) ;
33 SetMenuTitleWithCFString( menu , wxCFStringRef(str , encoding ) ) ;
34
35 return menu ;
36 }
37
38 void UMASetMenuTitle( MenuRef menu , const wxString& title , wxFontEncoding encoding )
39 {
40 wxString str = wxStripMenuCodes( title ) ;
41
42 SetMenuTitleWithCFString( menu , wxCFStringRef(str , encoding) ) ;
43 }
44
45 void UMASetMenuItemText( MenuRef menu, MenuItemIndex item, const wxString& title, wxFontEncoding encoding )
46 {
47 // we don't strip the accels here anymore, must be done before
48 wxString str = title ;
49
50 SetMenuItemTextWithCFString( menu , item , wxCFStringRef(str , encoding) ) ;
51 }
52
53 void UMAEnableMenuItem( MenuRef inMenu , MenuItemIndex inItem , bool enable)
54 {
55 if ( enable )
56 EnableMenuItem( inMenu , inItem ) ;
57 else
58 DisableMenuItem( inMenu , inItem ) ;
59 }
60
61 void UMAAppendSubMenuItem( MenuRef menu , const wxString& title, wxFontEncoding encoding , MenuRef submenu )
62 {
63 AppendMenuItemTextWithCFString( menu,
64 CFSTR("A"), 0, 0,NULL);
65 UMASetMenuItemText( menu, (SInt16) ::CountMenuItems(menu), title , encoding );
66 SetMenuItemHierarchicalMenu( menu , CountMenuItems( menu ) , submenu ) ;
67 SetMenuTitleWithCFString(submenu , wxCFStringRef(title , encoding) );
68 }
69
70 void UMAInsertSubMenuItem( MenuRef menu , const wxString& title, wxFontEncoding encoding , MenuItemIndex item , SInt16 id )
71 {
72 InsertMenuItemTextWithCFString( menu,
73 CFSTR("A"), item, 0, 0);
74
75 UMASetMenuItemText( menu, item+1, title , encoding );
76 SetMenuItemHierarchicalID( menu , item+1 , id ) ;
77 }
78
79 void UMASetMenuItemShortcut( MenuRef menu , MenuItemIndex item , wxAcceleratorEntry *entry )
80 {
81 if ( !entry )
82 {
83 SetMenuItemCommandKey(menu, item, false, 0);
84 return ;
85 }
86
87 UInt8 modifiers = 0 ;
88 SInt16 key = entry->GetKeyCode() ;
89 if ( key )
90 {
91 bool explicitCommandKey = (entry->GetFlags() & wxACCEL_CTRL);
92
93 if (entry->GetFlags() & wxACCEL_ALT)
94 modifiers |= kMenuOptionModifier ;
95
96 if (entry->GetFlags() & wxACCEL_SHIFT)
97 modifiers |= kMenuShiftModifier ;
98
99 if (entry->GetFlags() & wxACCEL_RAW_CTRL)
100 modifiers |= kMenuControlModifier ;
101
102 SInt16 glyph = 0 ;
103 SInt16 macKey = key ;
104 if ( key >= WXK_F1 && key <= WXK_F15 )
105 {
106 if ( !explicitCommandKey )
107 modifiers |= kMenuNoCommandModifier ;
108
109 // for some reasons this must be 0 right now
110 // everything else leads to just the first function key item
111 // to be selected. Thanks to Ryan Wilcox for finding out.
112 macKey = 0 ;
113 glyph = kMenuF1Glyph + ( key - WXK_F1 ) ;
114 if ( key >= WXK_F13 )
115 glyph += 12 ;
116 }
117 else
118 {
119 switch ( key )
120 {
121 case WXK_BACK :
122 macKey = kBackspaceCharCode ;
123 glyph = kMenuDeleteLeftGlyph ;
124 break ;
125
126 case WXK_TAB :
127 macKey = kTabCharCode ;
128 glyph = kMenuTabRightGlyph ;
129 break ;
130
131 case kEnterCharCode :
132 macKey = kEnterCharCode ;
133 glyph = kMenuEnterGlyph ;
134 break ;
135
136 case WXK_RETURN :
137 macKey = kReturnCharCode ;
138 glyph = kMenuReturnGlyph ;
139 break ;
140
141 case WXK_ESCAPE :
142 macKey = kEscapeCharCode ;
143 glyph = kMenuEscapeGlyph ;
144 break ;
145
146 case WXK_SPACE :
147 macKey = ' ' ;
148 glyph = kMenuSpaceGlyph ;
149 break ;
150
151 case WXK_DELETE :
152 macKey = kDeleteCharCode ;
153 glyph = kMenuDeleteRightGlyph ;
154 break ;
155
156 case WXK_CLEAR :
157 macKey = kClearCharCode ;
158 glyph = kMenuClearGlyph ;
159 break ;
160
161 case WXK_PAGEUP :
162 macKey = kPageUpCharCode ;
163 glyph = kMenuPageUpGlyph ;
164 break ;
165
166 case WXK_PAGEDOWN :
167 macKey = kPageDownCharCode ;
168 glyph = kMenuPageDownGlyph ;
169 break ;
170
171 case WXK_LEFT :
172 macKey = kLeftArrowCharCode ;
173 glyph = kMenuLeftArrowGlyph ;
174 break ;
175
176 case WXK_UP :
177 macKey = kUpArrowCharCode ;
178 glyph = kMenuUpArrowGlyph ;
179 break ;
180
181 case WXK_RIGHT :
182 macKey = kRightArrowCharCode ;
183 glyph = kMenuRightArrowGlyph ;
184 break ;
185
186 case WXK_DOWN :
187 macKey = kDownArrowCharCode ;
188 glyph = kMenuDownArrowGlyph ;
189 break ;
190
191 case WXK_HOME :
192 macKey = kHomeCharCode ;
193 glyph = kMenuNorthwestArrowGlyph ;
194 break ;
195
196 case WXK_END :
197 macKey = kEndCharCode ;
198 glyph = kMenuSoutheastArrowGlyph ;
199 break ;
200 default :
201 macKey = toupper( key ) ;
202 break ;
203 }
204
205 // we now allow non command key shortcuts
206 // remove in case this gives problems
207 if ( !explicitCommandKey )
208 modifiers |= kMenuNoCommandModifier ;
209 }
210
211 // 1d and 1e have special meaning to SetItemCmd, so
212 // do not use for these character codes.
213 if (key != WXK_UP && key != WXK_RIGHT && key != WXK_DOWN && key != WXK_LEFT)
214 SetItemCmd( menu, item , macKey );
215
216 SetMenuItemModifiers( menu, item , modifiers ) ;
217
218 if ( glyph )
219 SetMenuItemKeyGlyph( menu, item , glyph ) ;
220 }
221 }
222
223 void UMAAppendMenuItem( MenuRef menu , const wxString& title, wxFontEncoding encoding , wxAcceleratorEntry *entry )
224 {
225 AppendMenuItemTextWithCFString( menu,
226 CFSTR("A"), 0, 0,NULL);
227 // don't attempt to interpret metacharacters like a '-' at the beginning (would become a separator otherwise)
228 ChangeMenuItemAttributes( menu , ::CountMenuItems(menu), kMenuItemAttrIgnoreMeta , 0 ) ;
229 UMASetMenuItemText(menu, (SInt16) ::CountMenuItems(menu), title , encoding );
230 UMASetMenuItemShortcut( menu , (SInt16) ::CountMenuItems(menu), entry ) ;
231 }
232
233 void UMAInsertMenuItem( MenuRef menu , const wxString& title, wxFontEncoding encoding , MenuItemIndex item , wxAcceleratorEntry *entry )
234 {
235 InsertMenuItemTextWithCFString( menu,
236 CFSTR("A"), item, 0, 0);
237
238 // don't attempt to interpret metacharacters like a '-' at the beginning (would become a separator otherwise)
239 ChangeMenuItemAttributes( menu , item+1, kMenuItemAttrIgnoreMeta , 0 ) ;
240 UMASetMenuItemText(menu, item+1 , title , encoding );
241 UMASetMenuItemShortcut( menu , item+1 , entry ) ;
242 }
243
244 static OSStatus UMAGetHelpMenu(
245 MenuRef * outHelpMenu,
246 MenuItemIndex * outFirstCustomItemIndex,
247 bool allowHelpMenuCreation);
248
249 static OSStatus UMAGetHelpMenu(
250 MenuRef * outHelpMenu,
251 MenuItemIndex * outFirstCustomItemIndex,
252 bool allowHelpMenuCreation)
253 {
254 static bool s_createdHelpMenu = false ;
255
256 if ( !s_createdHelpMenu && !allowHelpMenuCreation )
257 {
258 return paramErr ;
259 }
260
261 OSStatus status = HMGetHelpMenu( outHelpMenu , outFirstCustomItemIndex ) ;
262 s_createdHelpMenu = ( status == noErr ) ;
263 return status ;
264 }
265
266 OSStatus UMAGetHelpMenu(
267 MenuRef * outHelpMenu,
268 MenuItemIndex * outFirstCustomItemIndex)
269 {
270 return UMAGetHelpMenu( outHelpMenu , outFirstCustomItemIndex , true );
271 }
272
273 OSStatus UMAGetHelpMenuDontCreate(
274 MenuRef * outHelpMenu,
275 MenuItemIndex * outFirstCustomItemIndex)
276 {
277 return UMAGetHelpMenu( outHelpMenu , outFirstCustomItemIndex , false );
278 }
279
280 #endif
281
282 #endif // wxUSE_GUI