Undo my previous commit, as per Stefan.
[bpt/emacs.git] / lwlib / lwlib-Xlw.c
CommitLineData
07bf635f
RS
1/* The lwlib interface to "xlwmenu" menus.
2 Copyright (C) 1992 Lucid, Inc.
73b0cd50 3 Copyright (C) 1994, 2000-2011 Free Software Foundation, Inc.
07bf635f
RS
4
5This file is part of the Lucid Widget Library.
6
177c0ea7 7The Lucid Widget Library is free software; you can redistribute it and/or
07bf635f
RS
8modify it under the terms of the GNU General Public License as published by
9the Free Software Foundation; either version 1, or (at your option)
10any later version.
11
12The Lucid Widget Library is distributed in the hope that it will be useful,
177c0ea7 13but WITHOUT ANY WARRANTY; without even the implied warranty of
07bf635f
RS
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
18along with GNU Emacs; see the file COPYING. If not, write to
364c38d3
LK
19the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
20Boston, MA 02110-1301, USA. */
07bf635f 21
0f0912e6
PE
22#ifdef HAVE_CONFIG_H
23#include <config.h>
24#endif
25
d7306fe6 26#include <setjmp.h>
e226063c 27#include "lisp.h"
2f96293d 28
07bf635f
RS
29#include "lwlib-Xlw.h"
30#include <X11/StringDefs.h>
31#include <X11/IntrinsicP.h>
32#include <X11/ObjectP.h>
33#include <X11/CompositeP.h>
34#include <X11/Shell.h>
35#include "xlwmenu.h"
36
d3a785ff
GM
37#if 0
38
39#include <stdio.h>
40
41/* Print the complete X resource name of widget WIDGET to stderr.
42 This is sometimes handy to have available. */
43
44void
c825c0b6 45x_print_complete_resource_name (Widget widget)
d3a785ff
GM
46{
47 int i;
48 String names[100];
49
50 for (i = 0; i < 100 && widget != NULL; ++i)
51 {
52 names[i] = XtName (widget);
53 widget = XtParent (widget);
54 }
55
56 for (--i; i >= 1; --i)
57 fprintf (stderr, "%s.", names[i]);
58 fprintf (stderr, "%s\n", names[0]);
59}
60
61#endif /* 0 */
62
63
07bf635f 64\f/* Menu callbacks */
fa616ec4
GM
65
66/* Callback XtNhighlightCallback for Lucid menus. W is the menu
67 widget, CLIENT_DATA contains a pointer to the widget_instance
68 for the menu, CALL_DATA contains a pointer to the widget_value
69 structure for the highlighted menu item. The latter may be null
70 if there isn't any highlighted menu item. */
71
72static void
c3174d16 73highlight_hook (Widget w, XtPointer client_data, XtPointer call_data)
fa616ec4
GM
74{
75 widget_instance *instance = (widget_instance *) client_data;
76
77 if (instance->info->highlight_cb
78 && !w->core.being_destroyed)
79 instance->info->highlight_cb (w, instance->info->id, call_data);
80}
81
3fcd0186 82static void
c3174d16 83enter_hook (Widget w, XtPointer client_data, XtPointer call_data)
3fcd0186
JD
84{
85 highlight_hook (w, client_data, call_data);
86}
87
88static void
c3174d16 89leave_hook (Widget w, XtPointer client_data, XtPointer call_data)
3fcd0186
JD
90{
91 highlight_hook (w, client_data, NULL);
92}
93
94
07bf635f 95static void
c3174d16 96pre_hook (Widget w, XtPointer client_data, XtPointer call_data)
07bf635f
RS
97{
98 widget_instance* instance = (widget_instance*)client_data;
99 widget_value* val;
100
101 if (w->core.being_destroyed)
102 return;
103
104 val = lw_get_widget_value_for_widget (instance, w);
105 if (instance->info->pre_activate_cb)
106 instance->info->pre_activate_cb (w, instance->info->id,
107 val ? val->call_data : NULL);
108}
109
110static void
c3174d16 111pick_hook (Widget w, XtPointer client_data, XtPointer call_data)
07bf635f
RS
112{
113 widget_instance* instance = (widget_instance*)client_data;
114 widget_value* contents_val = (widget_value*)call_data;
115 widget_value* widget_val;
116 XtPointer widget_arg;
117
118 if (w->core.being_destroyed)
119 return;
120
121 if (instance->info->selection_cb && contents_val && contents_val->enabled
122 && !contents_val->contents)
123 instance->info->selection_cb (w, instance->info->id,
124 contents_val->call_data);
125
126 widget_val = lw_get_widget_value_for_widget (instance, w);
127 widget_arg = widget_val ? widget_val->call_data : NULL;
128 if (instance->info->post_activate_cb)
129 instance->info->post_activate_cb (w, instance->info->id, widget_arg);
130
131}
132
133\f/* creation functions */
0b96f00b 134
07bf635f 135static Widget
c3174d16 136xlw_create_menubar (widget_instance *instance)
07bf635f 137{
9acc68b1 138 Widget widget;
5acc1a62 139 Arg al[5];
c52de5eb 140 int ac = 0;
9acc68b1 141
c52de5eb 142 XtSetArg (al[ac], XtNmenu, instance->info->val); ac++;
5acc1a62
PR
143#ifdef emacs
144 XtSetArg (al[ac], XtNshowGrip, 0); ac++;
145 XtSetArg (al[ac], XtNresizeToPreferred, 1); ac++;
146 XtSetArg (al[ac], XtNallowResize, 1); ac++;
147#endif
9acc68b1 148
c52de5eb
RS
149 /* This used to use XtVaCreateWidget, but an old Xt version
150 has a bug in XtVaCreateWidget that frees instance->info->name. */
364e6904 151 widget
c52de5eb
RS
152 = XtCreateWidget (instance->info->name, xlwMenuWidgetClass,
153 instance->parent, al, ac);
19240c20 154
07bf635f
RS
155 XtAddCallback (widget, XtNopen, pre_hook, (XtPointer)instance);
156 XtAddCallback (widget, XtNselect, pick_hook, (XtPointer)instance);
3fcd0186
JD
157 XtAddCallback (widget, XtNleaveCallback, leave_hook, (XtPointer)instance);
158 XtAddCallback (widget, XtNenterCallback, enter_hook, (XtPointer)instance);
07bf635f
RS
159 return widget;
160}
161
162static Widget
c3174d16 163xlw_create_popup_menu (widget_instance *instance)
07bf635f 164{
364e6904
RS
165 Widget popup_shell
166 = XtCreatePopupShell (instance->info->name, overrideShellWidgetClass,
167 instance->parent, NULL, 0);
177c0ea7 168
19240c20 169 Widget widget;
c52de5eb
RS
170 Arg al[2];
171 int ac = 0;
19240c20 172
c52de5eb
RS
173 XtSetArg (al[ac], XtNmenu, instance->info->val); ac++;
174 XtSetArg (al[ac], XtNhorizontal, False); ac++;
19240c20 175
c52de5eb
RS
176 /* This used to use XtVaManagedCreateWidget, but an old Xt version
177 has a bug in XtVaManagedCreateWidget that frees instance->info->name. */
364e6904 178 widget
c52de5eb
RS
179 = XtCreateManagedWidget ("popup", xlwMenuWidgetClass,
180 popup_shell, al, ac);
19240c20 181
07bf635f 182 XtAddCallback (widget, XtNselect, pick_hook, (XtPointer)instance);
3fcd0186
JD
183 XtAddCallback (widget, XtNleaveCallback, leave_hook, (XtPointer)instance);
184 XtAddCallback (widget, XtNenterCallback, enter_hook, (XtPointer)instance);
244c93fe 185
07bf635f
RS
186 return popup_shell;
187}
188
177c0ea7 189widget_creation_entry
07bf635f
RS
190xlw_creation_table [] =
191{
192 {"menubar", xlw_create_menubar},
193 {"popup", xlw_create_popup_menu},
194 {NULL, NULL}
195};
196
197Boolean
c3174d16 198lw_lucid_widget_p (Widget widget)
07bf635f
RS
199{
200 WidgetClass the_class = XtClass (widget);
364e6904 201
07bf635f
RS
202 if (the_class == xlwMenuWidgetClass)
203 return True;
204 if (the_class == overrideShellWidgetClass)
364e6904
RS
205 return (XtClass (((CompositeWidget)widget)->composite.children [0])
206 == xlwMenuWidgetClass);
07bf635f
RS
207 return False;
208}
209
210void
e226063c
DL
211xlw_update_one_widget (widget_instance* instance, Widget widget,
212 widget_value* val, Boolean deep_p)
07bf635f 213{
c52de5eb 214 Arg al[1];
07bf635f 215
c52de5eb
RS
216 /* This used to use XtVaSetValues, but some old Xt versions
217 that have a bug in XtVaCreateWidget might have it here too. */
218 XtSetArg (al[0], XtNmenu, instance->info->val);
219
220 XtSetValues (widget, al, 1);
07bf635f
RS
221}
222
223void
c825c0b6
J
224xlw_update_one_value (widget_instance *instance,
225 Widget widget,
226 widget_value *val)
07bf635f
RS
227{
228 return;
229}
230
231void
e226063c 232xlw_pop_instance (widget_instance* instance, Boolean up)
07bf635f
RS
233{
234}
235
236void
c3174d16 237xlw_popup_menu (Widget widget, XEvent *event)
07bf635f 238{
07bf635f
RS
239 XlwMenuWidget mw;
240
241 if (!XtIsShell (widget))
242 return;
243
244 mw = (XlwMenuWidget)((CompositeWidget)widget)->composite.children [0];
245
0c7c510c 246 if (event)
244c93fe 247 XtCallActionProc ((Widget) mw, "start", event, NULL, 0);
0c7c510c
RS
248 else
249 {
244c93fe
JD
250 XEvent dummy;
251 XButtonPressedEvent *bd = &dummy.xbutton;
252
253 bd->type = ButtonPress;
254 bd->serial = 0;
255 bd->send_event = 0;
256 bd->display = XtDisplay (widget);
257 bd->window = XtWindow (XtParent (widget));
258 bd->time = CurrentTime;
259 bd->button = 0;
260 XQueryPointer (bd->display, bd->window, &bd->root,
261 &bd->subwindow, &bd->x_root, &bd->y_root,
262 &bd->x, &bd->y, &bd->state);
263
264 XtCallActionProc ((Widget) mw, "start", &dummy, NULL, 0);
0c7c510c 265 }
07bf635f
RS
266}
267
268\f/* Destruction of instances */
269void
c3174d16 270xlw_destroy_instance (widget_instance *instance)
07bf635f
RS
271{
272 if (instance->widget)
273 XtDestroyWidget (instance->widget);
274}
275