Removed C++-style "//" comments to allow C sources to be built with C compilers.
[dyninst.git] / visiClients / terrain / src / action.c
1 /*
2  * Copyright (c) 1989, 1990 Barton P. Miller, Morgan Clark, Timothy Torzewski
3  *     Jeff Hollingsworth, and Bruce Irvin. All rights reserved.
4  *
5  * This software is furnished under the condition that it may not
6  * be provided or otherwise made available to, or used by, any
7  * other person.  No title to or ownership of the software is
8  * hereby transferred.  The name of the principals
9  * may not be used in any advertising or publicity related to this
10  * software without specific, written prior authorization.
11  * Any use of this software must include the above copyright notice.
12  *
13  */
14
15 /*
16  * This file contains the routines to display an action box.
17  *   An action box consists of several lines of text followed by a row
18  *   buttons defining the possible actions to take in responce to the
19  *   message.
20  *
21  * $Id: action.c,v 1.7 1998/03/30 01:22:18 wylie Exp $
22  */
23
24 #define max(x,y)        ((x > y) ? x : y);
25 #include <stdio.h>
26 #include <X11/Xlib.h>
27 #include <X11/Intrinsic.h>
28 #include <X11/StringDefs.h>
29 #include <X11/Shell.h>
30 #include <X11/Xaw/Command.h>
31 #include <X11/Xaw/Label.h>
32 #include <X11/Xaw/Box.h>
33 #include <X11/Xaw/Form.h>
34 #include <X11/Xaw/AsciiText.h>
35 #include <stdlib.h>
36
37 #include "FormatBox.h"
38 #include "Xbase.h"
39 #include "Xglobals.h"
40 #include "action.h"
41 #include "terrain.h"
42 #include "miscx.h"
43
44 static int Xorig, Yorig;
45
46 struct ActData {
47     int active;                 /* still waiting on a responce */
48     Widget shell;               /* top level holder */
49     Widget form;                /* form for items */
50     Widget banner;              /* banner string */
51     Widget Llogo;               /* left logo */
52     Widget Rlogo;               /* right logo */
53     Widget box;                 /* box to hold buttons */
54     Widget *buttons;            /* buttons */
55     Widget message;             /* message */
56     char *str;                  /* text of message */
57     void (*callBack)();         /* func to call when we are done */
58 };
59
60
61 #define EXPANSION       (5 * fontWidth)
62 #define DEF_DIST        15
63
64 Pixmap icon_pixmap = (Pixmap)NULL;
65
66 static int width, height;
67 static struct ActData act;
68 static int start_x, start_y;
69 static Arg get_stuff[] = {
70     {    XtNwidth,      (XtArgVal) &width },
71 };
72
73 static void EndActFunc(Widget w, int id, int cdata)
74 {
75     XtRemoveGrab(act.shell);
76     XtUnmapWidget(act.shell);
77     if (act.callBack) (act.callBack)(id);
78     XtDestroyWidget(act.shell);
79     act.active = 0;
80     if (act.message) 
81        free(act.message);
82     return;
83 }
84
85 int RequestAction(int labelc, int buttonc, int justify, char *banner, char *labels[],
86                    char *buttons[], struct Logo *Llogo, struct Logo *Rlogo, 
87                    void (*callBack)())
88 {
89
90     int i;
91     int b_y;
92     int count;
93     int leng;
94     void IFeep();
95     XEvent event;
96     Arg args[200];
97     WindowInfo info;
98     XSizeHints hints;
99     Widget last = NULL;
100
101     act.active = 1;
102     act.callBack = callBack;
103
104     count = 0;
105     XtSetArg(args[count], XtNx, start_x); count++;
106     XtSetArg(args[count], XtNy, start_y); count++;
107     XtSetArg(args[count], XtNiconName, "Terrain Message"); count++;
108     XtSetArg(args[count], XtNmappedWhenManaged, False); count++;
109     act.shell = XtCreatePopupShell("Message" , topLevelShellWidgetClass,
110         w_top, args, (unsigned) count);
111
112     /* form to hold items */
113     count = 0;
114     XtSetArg(args[count], XtNdefaultDistance, DEF_DIST); count++;
115     act.form = XtCreateManagedWidget("form", formWidgetClass,
116         act.shell, args, (unsigned) count);
117     XtAddEventHandler(act.form, ButtonPressMask, (int)NULL, IFeep, NULL);
118
119     /* left logo if it exists */
120     if (Llogo) {
121         count = 0;
122         XtSetArg(args[count], XtNborderWidth, 0); count++;
123         XtSetArg(args[count], XtNbitmap, Llogo->icon); count++;
124         last = act.Llogo = XtCreateManagedWidget("Llogo", labelWidgetClass,
125             act.form, args, (unsigned) count);
126     }
127
128     /* banner title */
129     b_y = Llogo ? Llogo->h : 0;
130     b_y = (Rlogo && (Rlogo->h > b_y)) ? Rlogo->h : b_y;
131     count = 0;
132     if (Llogo) XtSetArg(args[count], XtNhorizDistance, 0), count++;
133     if (b_y) XtSetArg(args[count], XtNheight, b_y); count++;
134     XtSetArg(args[count], XtNresizable, True); count++;
135     XtSetArg(args[count], XtNresize, True); count++;
136     XtSetArg(args[count], XtNfromHoriz, last); count++;
137     XtSetArg(args[count], XtNborderWidth, 0); count++;
138     XtSetArg(args[count], XtNlabel, banner); count++;
139     last = act.banner = XtCreateManagedWidget("bannerString", labelWidgetClass,
140         act.form, args, (unsigned) count);
141
142     /* right logo if it exists */
143     if (Rlogo) {
144         count = 0;
145         XtSetArg(args[count], XtNbitmap, Rlogo->icon); count++;
146         XtSetArg(args[count], XtNborderWidth, 0); count++;
147         XtSetArg(args[count], XtNfromHoriz, act.banner); count++;
148         XtSetArg(args[count], XtNhorizDistance, 5), count++;
149         last = act.Rlogo = XtCreateManagedWidget("Rlogo", labelWidgetClass,
150             act.form, args, (unsigned) count);
151     }
152
153     if (labelc) {
154         leng = 0;
155         width = 0;
156         for (i=0; i < labelc; i++) {
157             leng += strlen(labels[i]);
158             width = max(width,XTextWidth(fontStruct, labels[i], 
159                                          (signed) strlen(labels[i])));
160         }
161         act.str = (char *) malloc((unsigned) leng + labelc);
162         act.str[0] = '\0';
163         for (i=0; i < labelc; i++) {
164             if (i) strcat(act.str, "\n");
165             strcat(act.str, labels[i]);
166         }
167
168         count = 0;
169         XtSetArg(args[count], XtNborderWidth, 0); count++;
170         XtSetArg(args[count], XtNtopMargin, 0); count++;
171         XtSetArg(args[count], XtNbottomMargin, 0); count++;
172         XtSetArg(args[count], XtNwidth, width+10); count++;
173         height = fontHeight * labelc;
174         XtSetArg(args[count], XtNheight, height+5); count++;
175         XtSetArg(args[count], XtNjustify, justify); count++;
176         XtSetArg(args[count], XtNfromVert, last); count++;
177         XtSetArg(args[count], XtNresizable, True); count++;
178         XtSetArg(args[count], XtNdisplayCaret, False); count++;
179         XtSetArg(args[count], XtNresize, XawtextResizeWidth); count++;
180         XtSetArg(args[count], XtNstring, act.str); count++;
181         last = act.message = XtCreateManagedWidget("message", 
182             asciiTextWidgetClass, act.form, args, (unsigned) count);
183     }
184         
185     count = 0;
186     XtSetArg(args[count], XtNfromVert, last); count++;
187     XtSetArg(args[count], XtNfromHoriz, NULL); count++;
188     XtSetArg(args[count], XtNborderWidth, 0); count++;
189     XtSetArg(args[count], XtNvSpace, 5); count++;
190     XtSetArg(args[count], XtNhSpace, 15); count++;
191     XtSetArg(args[count], XtNorientation, XtorientHorizontal); count++;
192     XtSetArg(args[count], XtNtop, XtChainBottom); count++;
193     XtSetArg(args[count], XtNbottom, XtChainBottom); count++;
194     XtSetArg(args[count], XtNresizable, True); count++;
195     XtSetArg(args[count], XtNresize, True); count++;
196     XtSetArg(args[count], XtNformat, XtNcenter); count++;
197     act.box = XtCreateManagedWidget("box", formatBoxWidgetClass, 
198         act.form, args, (unsigned) count);
199
200     act.buttons = (Widget *) calloc((unsigned) buttonc, sizeof(Widget));
201     for (i=0; i < buttonc; i++) {
202         last = act.buttons[i] = XtCreateManagedWidget(buttons[i], 
203             commandWidgetClass, act.box, NULL, 0);
204         XtAddCallback(act.buttons[i], XtNcallback, (XtCallbackProc)EndActFunc,
205                      (XtPointer)i);
206     }
207
208     XtRealizeWidget(act.shell);
209     IGetGeometry(XtWindow(act.form), &info);
210     width = info.width - 2 * DEF_DIST;
211     width -= Rlogo ? (Rlogo->w + DEF_DIST): 0;
212     width -= Llogo ? (Llogo->w + DEF_DIST): 0;
213     XtSetValue(act.banner, XtNwidth, (XtPointer)width);
214
215     width = info.width - 2 * DEF_DIST;
216     if (labelc) XtSetValue(act.message, XtNwidth, (XtPointer)width);
217     XtSetValue(act.box, XtNwidth, (XtPointer)width);
218
219     hints.flags = USPosition;
220     hints.x = start_x;
221     hints.y = start_y;
222     XSetNormalHints(XtDisplay(act.shell), XtWindow(act.shell), &hints);
223     XtAddGrab(act.shell, TRUE, FALSE);
224     XtMapWidget(act.shell);
225
226     /* We need to process events until the action is done, then we can let
227        the function return.  This prevents multiple error windows from becomming
228        active at once. */
229     while (act.active) {
230         XNextEvent(dpy, &event);
231         XtDispatchEvent(&event);
232     }
233     return(0);
234 }
235
236 void InitAction(int x, int y)
237 {
238     start_x = x;
239     start_y = y;
240 }
241
242
243
244