aboutsummaryrefslogtreecommitdiffstats
path: root/src/macmenu.c
diff options
context:
space:
mode:
authorYAMAMOTO Mitsuharu2006-02-19 07:33:13 +0000
committerYAMAMOTO Mitsuharu2006-02-19 07:33:13 +0000
commit0f745bcf7946d55239cf6a06d64853af034c267e (patch)
tree65fc339274925f4e6fd1ec9c4c2f88a1988abf14 /src/macmenu.c
parente5538a995cb0e696ac3389ec09e0197a398b90eb (diff)
downloademacs-0f745bcf7946d55239cf6a06d64853af034c267e.tar.gz
emacs-0f745bcf7946d55239cf6a06d64853af034c267e.zip
(popup_activated_flag, submenu_id)
(next_menubar_widget_id): Remove variables. (initialize_frame_menubar): Remove function. (pop_down_menu, mac_menu_show): Simplify save value. (dispose_menus): New function. (pop_down_menu, fill_menubar): Use it. (fill_submenu): Remove function. All uses changed to fill_menu. (add_menu_item): Remove args SUBMENU and FORCE_DISABLE. New arg POS. Don't call SetMenuItemHierarchicalID here. (fill_menu): Add arg SUBMENU_ID. Return submenu_id that is to be used next. Call SetMenuItemHierarchicalID here. (fill_menubar): Add arg DEEP_P. All uses changed. Clean up menu objects if needed. Reuse existing menu bar titles if possible. (set_frame_menubar): Don't clean up menu objects here.
Diffstat (limited to 'src/macmenu.c')
-rw-r--r--src/macmenu.c243
1 files changed, 116 insertions, 127 deletions
diff --git a/src/macmenu.c b/src/macmenu.c
index bd4ad6291cf..fccbbe6402c 100644
--- a/src/macmenu.c
+++ b/src/macmenu.c
@@ -189,8 +189,9 @@ static void single_keymap_panes P_ ((Lisp_Object, Lisp_Object, Lisp_Object,
189static void list_of_panes P_ ((Lisp_Object)); 189static void list_of_panes P_ ((Lisp_Object));
190static void list_of_items P_ ((Lisp_Object)); 190static void list_of_items P_ ((Lisp_Object));
191 191
192static void fill_submenu (MenuHandle, widget_value *); 192static int fill_menu P_ ((MenuHandle, widget_value *, int));
193static void fill_menubar (widget_value *); 193static void fill_menubar P_ ((widget_value *, int));
194static void dispose_menus P_ ((int));
194 195
195 196
196/* This holds a Lisp vector that holds the results of decoding 197/* This holds a Lisp vector that holds the results of decoding
@@ -247,15 +248,6 @@ static int menu_items_n_panes;
247/* Current depth within submenus. */ 248/* Current depth within submenus. */
248static int menu_items_submenu_depth; 249static int menu_items_submenu_depth;
249 250
250/* Flag which when set indicates a dialog or menu has been posted by
251 Xt on behalf of one of the widget sets. */
252static int popup_activated_flag;
253
254/* Index of the next submenu */
255static int submenu_id;
256
257static int next_menubar_widget_id;
258
259/* This is set nonzero after the user activates the menu bar, and set 251/* This is set nonzero after the user activates the menu bar, and set
260 to zero again after the menu bars are redisplayed by prepare_menu_bar. 252 to zero again after the menu bars are redisplayed by prepare_menu_bar.
261 While it is nonzero, all calls to set_frame_menubar go deep. 253 While it is nonzero, all calls to set_frame_menubar go deep.
@@ -1440,7 +1432,7 @@ install_menu_quit_handler (MenuHandle menu_handle)
1440 menu = GetMenuHandle (++i); 1432 menu = GetMenuHandle (++i);
1441 } 1433 }
1442 1434
1443 i = menu_handle ? MIN_POPUP_SUBMENU_ID : MIN_SUBMENU_ID; 1435 i = menu_handle ? MIN_POPUP_SUBMENU_ID : MIN_SUBMENU_ID;
1444 menu = GetMenuHandle (i); 1436 menu = GetMenuHandle (i);
1445 while (menu != NULL) 1437 while (menu != NULL)
1446 { 1438 {
@@ -1679,27 +1671,7 @@ set_frame_menubar (f, first_time, deep_p)
1679 /* Non-null value to indicate menubar has already been "created". */ 1671 /* Non-null value to indicate menubar has already been "created". */
1680 f->output_data.mac->menubar_widget = 1; 1672 f->output_data.mac->menubar_widget = 1;
1681 1673
1682 { 1674 fill_menubar (first_wv->contents, deep_p);
1683 int i = MIN_MENU_ID;
1684 MenuHandle menu = GetMenuHandle (i);
1685 while (menu != NULL)
1686 {
1687 DeleteMenu (i);
1688 DisposeMenu (menu);
1689 menu = GetMenuHandle (++i);
1690 }
1691
1692 i = MIN_SUBMENU_ID;
1693 menu = GetMenuHandle (i);
1694 while (menu != NULL)
1695 {
1696 DeleteMenu (i);
1697 DisposeMenu (menu);
1698 menu = GetMenuHandle (++i);
1699 }
1700 }
1701
1702 fill_menubar (first_wv->contents);
1703 1675
1704 /* Add event handler so we can detect C-g. */ 1676 /* Add event handler so we can detect C-g. */
1705 install_menu_quit_handler (NULL); 1677 install_menu_quit_handler (NULL);
@@ -1708,22 +1680,6 @@ set_frame_menubar (f, first_time, deep_p)
1708 UNBLOCK_INPUT; 1680 UNBLOCK_INPUT;
1709} 1681}
1710 1682
1711/* Called from Fx_create_frame to create the initial menubar of a frame
1712 before it is mapped, so that the window is mapped with the menubar already
1713 there instead of us tacking it on later and thrashing the window after it
1714 is visible. */
1715
1716void
1717initialize_frame_menubar (f)
1718 FRAME_PTR f;
1719{
1720 /* This function is called before the first chance to redisplay
1721 the frame. It has to be, so the frame will have the right size. */
1722 FRAME_MENU_BAR_ITEMS (f) = menu_bar_items (FRAME_MENU_BAR_ITEMS (f));
1723 set_frame_menubar (f, 1, 1);
1724}
1725
1726
1727/* Get rid of the menu bar of frame F, and free its storage. 1683/* Get rid of the menu bar of frame F, and free its storage.
1728 This is used when deleting a frame, and when turning off the menu bar. */ 1684 This is used when deleting a frame, and when turning off the menu bar. */
1729 1685
@@ -1739,11 +1695,9 @@ static Lisp_Object
1739pop_down_menu (arg) 1695pop_down_menu (arg)
1740 Lisp_Object arg; 1696 Lisp_Object arg;
1741{ 1697{
1742 struct Lisp_Save_Value *p1 = XSAVE_VALUE (Fcar (arg)); 1698 struct Lisp_Save_Value *p = XSAVE_VALUE (arg);
1743 struct Lisp_Save_Value *p2 = XSAVE_VALUE (Fcdr (arg)); 1699 FRAME_PTR f = p->pointer;
1744 1700 MenuHandle menu = GetMenuHandle (POPUP_SUBMENU_ID);
1745 FRAME_PTR f = p1->pointer;
1746 MenuHandle *menu = p2->pointer;
1747 1701
1748 BLOCK_INPUT; 1702 BLOCK_INPUT;
1749 1703
@@ -1752,19 +1706,9 @@ pop_down_menu (arg)
1752 FRAME_MAC_DISPLAY_INFO (f)->grabbed = 0; 1706 FRAME_MAC_DISPLAY_INFO (f)->grabbed = 0;
1753 1707
1754 /* delete all menus */ 1708 /* delete all menus */
1755 { 1709 dispose_menus (MIN_POPUP_SUBMENU_ID);
1756 int i = MIN_POPUP_SUBMENU_ID;
1757 MenuHandle submenu = GetMenuHandle (i);
1758 while (submenu != NULL)
1759 {
1760 DeleteMenu (i);
1761 DisposeMenu (submenu);
1762 submenu = GetMenuHandle (++i);
1763 }
1764 }
1765
1766 DeleteMenu (POPUP_SUBMENU_ID); 1710 DeleteMenu (POPUP_SUBMENU_ID);
1767 DisposeMenu (*menu); 1711 DisposeMenu (menu);
1768 1712
1769 UNBLOCK_INPUT; 1713 UNBLOCK_INPUT;
1770 1714
@@ -1998,8 +1942,8 @@ mac_menu_show (f, x, y, for_click, keymaps, title, error)
1998 1942
1999 /* Actually create the menu. */ 1943 /* Actually create the menu. */
2000 menu = NewMenu (POPUP_SUBMENU_ID, "\p"); 1944 menu = NewMenu (POPUP_SUBMENU_ID, "\p");
2001 submenu_id = MIN_POPUP_SUBMENU_ID; 1945 InsertMenu (menu, -1);
2002 fill_submenu (menu, first_wv->contents); 1946 fill_menu (menu, first_wv->contents, MIN_POPUP_SUBMENU_ID);
2003 1947
2004 /* Free the widget_value objects we used to specify the 1948 /* Free the widget_value objects we used to specify the
2005 contents. */ 1949 contents. */
@@ -2016,11 +1960,7 @@ mac_menu_show (f, x, y, for_click, keymaps, title, error)
2016 menu_item_choice = 0; 1960 menu_item_choice = 0;
2017 menu_item_selection = 0; 1961 menu_item_selection = 0;
2018 1962
2019 InsertMenu (menu, -1); 1963 record_unwind_protect (pop_down_menu, make_save_value (f, 0));
2020
2021 record_unwind_protect (pop_down_menu,
2022 Fcons (make_save_value (f, 0),
2023 make_save_value (&menu, 0)));
2024 1964
2025 /* Add event handler so we can detect C-g. */ 1965 /* Add event handler so we can detect C-g. */
2026 install_menu_quit_handler (menu); 1966 install_menu_quit_handler (menu);
@@ -2421,15 +2361,16 @@ name_is_separator (name)
2421} 2361}
2422 2362
2423static void 2363static void
2424add_menu_item (MenuHandle menu, widget_value *wv, int submenu, 2364add_menu_item (menu, pos, wv)
2425 int force_disable) 2365 MenuHandle menu;
2366 int pos;
2367 widget_value *wv;
2426{ 2368{
2427#if TARGET_API_MAC_CARBON 2369#if TARGET_API_MAC_CARBON
2428 CFStringRef item_name; 2370 CFStringRef item_name;
2429#else 2371#else
2430 Str255 item_name; 2372 Str255 item_name;
2431#endif 2373#endif
2432 int pos;
2433 2374
2434 if (name_is_separator (wv->name)) 2375 if (name_is_separator (wv->name))
2435 AppendMenu (menu, "\p-"); 2376 AppendMenu (menu, "\p-");
@@ -2438,8 +2379,6 @@ add_menu_item (MenuHandle menu, widget_value *wv, int submenu,
2438 AppendMenu (menu, "\pX"); 2379 AppendMenu (menu, "\pX");
2439 2380
2440#if TARGET_API_MAC_CARBON 2381#if TARGET_API_MAC_CARBON
2441 pos = CountMenuItems (menu);
2442
2443 item_name = cfstring_create_with_utf8_cstring (wv->name); 2382 item_name = cfstring_create_with_utf8_cstring (wv->name);
2444 2383
2445 if (wv->key != NULL) 2384 if (wv->key != NULL)
@@ -2457,13 +2396,11 @@ add_menu_item (MenuHandle menu, widget_value *wv, int submenu,
2457 SetMenuItemTextWithCFString (menu, pos, item_name); 2396 SetMenuItemTextWithCFString (menu, pos, item_name);
2458 CFRelease (item_name); 2397 CFRelease (item_name);
2459 2398
2460 if (wv->enabled && !force_disable) 2399 if (wv->enabled)
2461 EnableMenuItem (menu, pos); 2400 EnableMenuItem (menu, pos);
2462 else 2401 else
2463 DisableMenuItem (menu, pos); 2402 DisableMenuItem (menu, pos);
2464#else /* ! TARGET_API_MAC_CARBON */ 2403#else /* ! TARGET_API_MAC_CARBON */
2465 pos = CountMItems (menu);
2466
2467 item_name[sizeof (item_name) - 1] = '\0'; 2404 item_name[sizeof (item_name) - 1] = '\0';
2468 strncpy (item_name, wv->name, sizeof (item_name) - 1); 2405 strncpy (item_name, wv->name, sizeof (item_name) - 1);
2469 if (wv->key != NULL) 2406 if (wv->key != NULL)
@@ -2477,88 +2414,140 @@ add_menu_item (MenuHandle menu, widget_value *wv, int submenu,
2477 c2pstr (item_name); 2414 c2pstr (item_name);
2478 SetMenuItemText (menu, pos, item_name); 2415 SetMenuItemText (menu, pos, item_name);
2479 2416
2480 if (wv->enabled && !force_disable) 2417 if (wv->enabled)
2481 EnableItem (menu, pos); 2418 EnableItem (menu, pos);
2482 else 2419 else
2483 DisableItem (menu, pos); 2420 DisableItem (menu, pos);
2484#endif /* ! TARGET_API_MAC_CARBON */ 2421#endif /* ! TARGET_API_MAC_CARBON */
2485 2422
2486 /* Draw radio buttons and tickboxes. */ 2423 /* Draw radio buttons and tickboxes. */
2487 {
2488 if (wv->selected && (wv->button_type == BUTTON_TYPE_TOGGLE || 2424 if (wv->selected && (wv->button_type == BUTTON_TYPE_TOGGLE ||
2489 wv->button_type == BUTTON_TYPE_RADIO)) 2425 wv->button_type == BUTTON_TYPE_RADIO))
2490 SetItemMark (menu, pos, checkMark); 2426 SetItemMark (menu, pos, checkMark);
2491 else 2427 else
2492 SetItemMark (menu, pos, noMark); 2428 SetItemMark (menu, pos, noMark);
2493 }
2494 2429
2495 SetMenuItemRefCon (menu, pos, (UInt32) wv->call_data); 2430 SetMenuItemRefCon (menu, pos, (UInt32) wv->call_data);
2496 } 2431 }
2497
2498 if (submenu != 0)
2499 SetMenuItemHierarchicalID (menu, pos, submenu);
2500} 2432}
2501 2433
2502/* Construct native Mac OS menubar based on widget_value tree. */ 2434/* Construct native Mac OS menu based on widget_value tree. */
2503 2435
2504static void 2436static int
2505fill_submenu (MenuHandle menu, widget_value *wv) 2437fill_menu (menu, wv, submenu_id)
2438 MenuHandle menu;
2439 widget_value *wv;
2440 int submenu_id;
2506{ 2441{
2507 for ( ; wv != NULL; wv = wv->next) 2442 int pos;
2508 if (wv->contents)
2509 {
2510 int cur_submenu = submenu_id++;
2511 MenuHandle submenu = NewMenu (cur_submenu, "\pX");
2512 fill_submenu (submenu, wv->contents);
2513 InsertMenu (submenu, -1);
2514 add_menu_item (menu, wv, cur_submenu, 0);
2515 }
2516 else
2517 add_menu_item (menu, wv, 0, 0);
2518}
2519 2443
2444 for (pos = 1; wv != NULL; wv = wv->next, pos++)
2445 {
2446 add_menu_item (menu, pos, wv);
2447 if (wv->contents)
2448 {
2449 MenuHandle submenu = NewMenu (submenu_id, "\pX");
2520 2450
2521/* Construct native Mac OS menu based on widget_value tree. */ 2451 InsertMenu (submenu, -1);
2452 SetMenuItemHierarchicalID (menu, pos, submenu_id);
2453 submenu_id = fill_menu (submenu, wv->contents, submenu_id + 1);
2454 }
2455 }
2522 2456
2523static void 2457 return submenu_id;
2524fill_menu (MenuHandle menu, widget_value *wv)
2525{
2526 for ( ; wv != NULL; wv = wv->next)
2527 if (wv->contents)
2528 {
2529 int cur_submenu = submenu_id++;
2530 MenuHandle submenu = NewMenu (cur_submenu, "\pX");
2531 fill_submenu (submenu, wv->contents);
2532 InsertMenu (submenu, -1);
2533 add_menu_item (menu, wv, cur_submenu, 0);
2534 }
2535 else
2536 add_menu_item (menu, wv, 0, 0);
2537} 2458}
2538 2459
2539/* Construct native Mac OS menubar based on widget_value tree. */ 2460/* Construct native Mac OS menubar based on widget_value tree. */
2540 2461
2541static void 2462static void
2542fill_menubar (widget_value *wv) 2463fill_menubar (wv, deep_p)
2464 widget_value *wv;
2465 int deep_p;
2543{ 2466{
2544 int id; 2467 int id, submenu_id;
2468 MenuHandle menu;
2469 Str255 title;
2470#if !TARGET_API_MAC_CARBON
2471 int title_changed_p = 0;
2472#endif
2545 2473
2546 submenu_id = MIN_SUBMENU_ID; 2474 /* Clean up the menu bar when filled by the entire menu trees. */
2475 if (deep_p)
2476 {
2477 dispose_menus (MIN_MENU_ID);
2478 dispose_menus (MIN_SUBMENU_ID);
2479#if !TARGET_API_MAC_CARBON
2480 title_changed_p = 1;
2481#endif
2482 }
2547 2483
2484 /* Fill menu bar titles and submenus. Reuse the existing menu bar
2485 titles as much as possible to minimize redraw (if !deep_p). */
2486 submenu_id = MIN_SUBMENU_ID;
2548 for (id = MIN_MENU_ID; wv != NULL; wv = wv->next, id++) 2487 for (id = MIN_MENU_ID; wv != NULL; wv = wv->next, id++)
2549 { 2488 {
2550 MenuHandle menu;
2551 Str255 title;
2552
2553 strncpy (title, wv->name, 255); 2489 strncpy (title, wv->name, 255);
2554 title[255] = 0; 2490 title[255] = '\0';
2555 c2pstr (title); 2491 c2pstr (title);
2556 menu = NewMenu (id, title); 2492
2493 menu = GetMenuHandle (id);
2494 if (menu)
2495 {
2496#if TARGET_API_MAC_CARBON
2497 Str255 old_title;
2498
2499 GetMenuTitle (menu, old_title);
2500 if (!EqualString (title, old_title, false, false))
2501 SetMenuTitle (menu, title);
2502#else /* !TARGET_API_MAC_CARBON */
2503 if (!EqualString (title, (*menu)->menuData, false, false))
2504 {
2505 DeleteMenu (id);
2506 DisposeMenu (menu);
2507 menu = NewMenu (id, title);
2508 InsertMenu (menu, GetMenuHandle (id + 1) ? id + 1 : 0);
2509 title_changed_p = 1;
2510 }
2511#endif /* !TARGET_API_MAC_CARBON */
2512 }
2513 else
2514 {
2515 menu = NewMenu (id, title);
2516 InsertMenu (menu, 0);
2517#if !TARGET_API_MAC_CARBON
2518 title_changed_p = 1;
2519#endif
2520 }
2557 2521
2558 if (wv->contents) 2522 if (wv->contents)
2559 fill_menu (menu, wv->contents); 2523 submenu_id = fill_menu (menu, wv->contents, submenu_id);
2524 }
2560 2525
2561 InsertMenu (menu, 0); 2526 if (GetMenuHandle (id))
2527 {
2528 dispose_menus (id);
2529#if !TARGET_API_MAC_CARBON
2530 title_changed_p = 1;
2531#endif
2532 }
2533
2534#if !TARGET_API_MAC_CARBON
2535 if (title_changed_p)
2536 InvalMenuBar ();
2537#endif
2538}
2539
2540static void
2541dispose_menus (id)
2542 int id;
2543{
2544 MenuHandle menu;
2545
2546 while ((menu = GetMenuHandle (id)) != NULL)
2547 {
2548 DeleteMenu (id);
2549 DisposeMenu (menu);
2550 id++;
2562 } 2551 }
2563} 2552}
2564 2553