comparison src/xmenu.c @ 8166:6fa3cd9b176d

(xmenu_show) [USE_X_TOOLKIT]: Keyboard input exits the menu. ButtonRelease does so if within Vdouble_click_time. Ignore mouse motion if button was already released. (menu_item_selection): Declare volatile, if __STDC__.
author Richard M. Stallman <rms@gnu.org>
date Thu, 07 Jul 1994 06:29:09 +0000
parents dda8e966edf5
children c3bc5fca374f
comparison
equal deleted inserted replaced
8165:02ee07034f11 8166:6fa3cd9b176d
1062 } 1062 }
1063 } 1063 }
1064 return Qnil; 1064 return Qnil;
1065 } 1065 }
1066 1066
1067 #ifdef __STDC__
1068 static Lisp_Object *volatile menu_item_selection;
1069 #else
1067 static Lisp_Object *menu_item_selection; 1070 static Lisp_Object *menu_item_selection;
1071 #endif
1068 1072
1069 static void 1073 static void
1070 popup_selection_callback (widget, id, client_data) 1074 popup_selection_callback (widget, id, client_data)
1071 Widget widget; 1075 Widget widget;
1072 LWLIB_ID id; 1076 LWLIB_ID id;
1364 TITLE is the specified menu title. 1368 TITLE is the specified menu title.
1365 ERROR is a place to store an error message string in case of failure. 1369 ERROR is a place to store an error message string in case of failure.
1366 (We return nil on failure, but the value doesn't actually matter.) */ 1370 (We return nil on failure, but the value doesn't actually matter.) */
1367 1371
1368 #ifdef USE_X_TOOLKIT 1372 #ifdef USE_X_TOOLKIT
1373
1374 extern unsigned last_event_timestamp;
1375 extern Lisp_Object Vdouble_click_time;
1369 1376
1370 extern unsigned int x_mouse_grabbed; 1377 extern unsigned int x_mouse_grabbed;
1371 extern Lisp_Object Vmouse_depressed; 1378 extern Lisp_Object Vmouse_depressed;
1372 1379
1373 static Lisp_Object 1380 static Lisp_Object
1609 pop_up_menu (mw, &dummy); 1616 pop_up_menu (mw, &dummy);
1610 } 1617 }
1611 1618
1612 /* No need to check a second time since this is done in the XEvent loop. 1619 /* No need to check a second time since this is done in the XEvent loop.
1613 This slows done the execution. */ 1620 This slows done the execution. */
1614 #if 0 1621 #ifdef XMENU_FOO
1615 /* Check again whether the mouse has moved to another menu bar item. */ 1622 /* Check again whether the mouse has moved to another menu bar item. */
1616 if (check_mouse_other_menu_bar (f)) 1623 if (check_mouse_other_menu_bar (f))
1617 { 1624 {
1618 /* The mouse moved into a different menu bar item. 1625 /* The mouse moved into a different menu bar item.
1619 We should bring up that item's menu instead. 1626 We should bring up that item's menu instead.
1629 1636
1630 /* Process events that apply to the menu. */ 1637 /* Process events that apply to the menu. */
1631 while (1) 1638 while (1)
1632 { 1639 {
1633 XEvent event; 1640 XEvent event;
1641 int queue_and_exit = 0;
1634 1642
1635 XtAppNextEvent (Xt_app_con, &event); 1643 XtAppNextEvent (Xt_app_con, &event);
1636 if (event.type == ButtonRelease) 1644 if (event.type == ButtonRelease)
1637 { 1645 {
1638 XtDispatchEvent (&event); 1646 XtDispatchEvent (&event);
1644 has been set to grabbed. Reset it now. */ 1652 has been set to grabbed. Reset it now. */
1645 x_mouse_grabbed &= ~(1 << event.xbutton.button); 1653 x_mouse_grabbed &= ~(1 << event.xbutton.button);
1646 if (!x_mouse_grabbed) 1654 if (!x_mouse_grabbed)
1647 Vmouse_depressed = Qnil; 1655 Vmouse_depressed = Qnil;
1648 } 1656 }
1649 break; 1657 if (! (menu_item_selection == 0
1658 && (((XButtonEvent *) (&event))->time - last_event_timestamp
1659 < XINT (Vdouble_click_time))))
1660 break;
1661 }
1662 else if (event.type == ButtonPress)
1663 {
1664 /* Any mouse button activity that doesn't select in the menu
1665 should unpost the menu. */
1666 if (menu_item_selection == 0)
1667 break;
1668 }
1669 else if (event.type == KeyPress)
1670 {
1671 /* Exit the loop, but first queue this event for reuse. */
1672 queue_and_exit = 1;
1650 } 1673 }
1651 else if (event.type == Expose) 1674 else if (event.type == Expose)
1652 process_expose_from_menu (event); 1675 process_expose_from_menu (event);
1653 else if (event.type == MotionNotify) 1676 /* If the mouse moves to a different menu bar item, switch to
1677 that item's menu. But only if the button is still held down. */
1678 else if (event.type == MotionNotify
1679 && x_mouse_grabbed)
1654 { 1680 {
1655 int event_x = (event.xmotion.x_root 1681 int event_x = (event.xmotion.x_root
1656 - (f->display.x->widget->core.x 1682 - (f->display.x->widget->core.x
1657 + f->display.x->widget->core.border_width)); 1683 + f->display.x->widget->core.border_width));
1658 int event_y = (event.xmotion.y_root 1684 int event_y = (event.xmotion.y_root
1677 break; 1703 break;
1678 } 1704 }
1679 } 1705 }
1680 1706
1681 XtDispatchEvent (&event); 1707 XtDispatchEvent (&event);
1682 if (XtWindowToWidget(XDISPLAY event.xany.window) != menu) 1708 if (queue_and_exit
1709 || XtWindowToWidget (XDISPLAY event.xany.window) != menu)
1683 { 1710 {
1684 queue_tmp 1711 queue_tmp
1685 = (struct event_queue *) malloc (sizeof (struct event_queue)); 1712 = (struct event_queue *) malloc (sizeof (struct event_queue));
1686 1713
1687 if (queue_tmp != NULL) 1714 if (queue_tmp != NULL)
1689 queue_tmp->event = event; 1716 queue_tmp->event = event;
1690 queue_tmp->next = queue; 1717 queue_tmp->next = queue;
1691 queue = queue_tmp; 1718 queue = queue_tmp;
1692 } 1719 }
1693 } 1720 }
1721 if (queue_and_exit)
1722 break;
1694 } 1723 }
1695 1724
1696 pop_down: 1725 pop_down:
1697 /* Unhighlight the menu bar item (if any) that led to this menu. */ 1726 /* Unhighlight the menu bar item (if any) that led to this menu. */
1698 if (menubarp) 1727 if (menubarp)