1 /* $Id: win.c,v 1.9 2002/03/02 21:02:21 sverrehu Exp $ */
2 /**************************************************************************
3 *
4 * FILE win.c
5 * MODULE OF Card game.
6 *
7 * WRITTEN BY Sverre H. Huseby <shh@thathost.com>
8 *
9 **************************************************************************/
10
11 #include <stdlib.h>
12 #include <time.h>
13
14 #include <X11/Xlib.h>
15 #include <X11/Intrinsic.h>
16 #include <X11/StringDefs.h>
17 #include <X11/Core.h>
18 #include <X11/Xaw/Command.h>
19 #include <X11/Xaw/Label.h>
20 #include <X11/Xaw/Form.h>
21
22 #include <shhmsg.h>
23 #include <shhcards.h>
24
25 #include "game.h"
26 #include "score.h"
27 #include "board.h"
28 #include "options.h"
29 #include "about.h"
30 #include "highscores.h"
31 #include "readme.h"
32 #include "win.h"
33
34 /* undo capabilities are not yet written. */
35 #undef UNDO
36
37 /* put menu buttons at bottom instead of at top? */
38 #define BUTTONS_AT_BOTTOM
39
40 /**************************************************************************
41 * *
42 * P R I V A T E D A T A *
43 * *
44 **************************************************************************/
45
46 #define SCORE_STAT_DELAY 30000
47
48 #ifdef UNDO
49 static Widget undoWidget;
50 #endif
51 static XtIntervalId timerId;
52 static XtIntervalId scoreTimerId;
53 static int timerRunning = 0;
54
55
56
57 /**************************************************************************
58 * *
59 * P U B L I C D A T A *
60 * *
61 **************************************************************************/
62
63 Display *winDisplay;
64
65 XtAppContext winAppContext;
66 Widget winTopLevel;
67 Widget winMainWindow;
68 Widget boardWidget;
69 Widget timeWidget;
70 Widget aboutButton;
71 Widget highscoresButton;
72 Widget readmeButton;
73
74
75
76 /**************************************************************************
77 * *
78 * P R I V A T E F U N C T I O N S *
79 * *
80 **************************************************************************/
81
82 static void
winGetAndHandleEvent(void)83 winGetAndHandleEvent(void)
84 {
85 XEvent e;
86
87 XtAppNextEvent(winAppContext, &e);
88 if (e.xany.window == boardWin)
89 boardHandleEvent(&e);
90 else if (e.xany.window == boardPopup)
91 boardHandlePopupEvent(&e);
92 else
93 XtDispatchEvent(&e);
94 }
95
96 static void
callbackQuit(Widget w,XtPointer clientData,XtPointer callData)97 callbackQuit(Widget w, XtPointer clientData, XtPointer callData)
98 {
99 gameExit = 1;
100 }
101
102 static void
callbackNewGame(Widget w,XtPointer clientData,XtPointer callData)103 callbackNewGame(Widget w, XtPointer clientData, XtPointer callData)
104 {
105 gameFinishGame();
106 gameInitGame();
107 }
108
109 static void
callbackOptions(Widget w,XtPointer clientData,XtPointer callData)110 callbackOptions(Widget w, XtPointer clientData, XtPointer callData)
111 {
112 optionsPopup();
113 }
114
115 #ifdef UNDO
116 static void
callbackUndo(Widget w,XtPointer clientData,XtPointer callData)117 callbackUndo(Widget w, XtPointer clientData, XtPointer callData)
118 {
119 }
120 #endif
121
122 static void
timerProc(XtPointer foo,XtIntervalId * bar)123 timerProc(XtPointer foo, XtIntervalId *bar)
124 {
125 if (gameRunning && timerRunning)
126 timerId = XtAppAddTimeOut(winAppContext, 1000, timerProc, 0);
127 gameUpdateTime();
128 }
129
130 static void
scoreTimerProc(XtPointer foo,XtIntervalId * bar)131 scoreTimerProc(XtPointer foo, XtIntervalId *bar)
132 {
133 scoreTimerId = XtAppAddTimeOut(winAppContext, SCORE_STAT_DELAY,
134 scoreTimerProc, 0);
135 scoreStatHighscoreFile();
136 }
137
138 static void
callbackAbout(Widget w,XtPointer clientData,XtPointer callData)139 callbackAbout(Widget w, XtPointer clientData, XtPointer callData)
140 {
141 aboutPopup();
142 }
143
144 static void
callbackHighscores(Widget w,XtPointer clientData,XtPointer callData)145 callbackHighscores(Widget w, XtPointer clientData, XtPointer callData)
146 {
147 highscoresPopup();
148 }
149
150 static void
callbackReadme(Widget w,XtPointer clientData,XtPointer callData)151 callbackReadme(Widget w, XtPointer clientData, XtPointer callData)
152 {
153 readmePopup();
154 }
155
156
157
158 /**************************************************************************
159 * *
160 * P U B L I C F U N C T I O N S *
161 * *
162 **************************************************************************/
163
164 void
winParseOptions(int * argc,char * argv[])165 winParseOptions(int *argc, char *argv[])
166 {
167 static String resources[] = {
168 "*board.background: " BOARD_BACKGROUND_COLOR,
169 "*board.foreground: magenta",
170 "*font: 9x15bold",
171 "*copyright*font: 6x10",
172 "*status*font: 6x10",
173 "*highscores*font: 6x10",
174 "*readme*font: 6x10",
175 NULL
176 };
177
178 winTopLevel = XtVaAppInitialize(&winAppContext, "Sol",
179 NULL, 0, argc, argv, resources, NULL);
180 winDisplay = XtDisplay(winTopLevel);
181 }
182
183 void
winInit(void)184 winInit(void)
185 {
186 Widget quitWidget, newWidget, optWidget;
187
188 optionsInit(winTopLevel);
189 aboutInit(winTopLevel);
190 highscoresInit(winTopLevel);
191 readmeInit(winTopLevel);
192 winMainWindow
193 = XtVaCreateManagedWidget("mainWindow",
194 formWidgetClass, winTopLevel,
195 NULL);
196 #ifdef BUTTONS_AT_BOTTOM
197 /* otherwise, board is set up last. see below. */
198 boardWidget
199 = XtVaCreateManagedWidget("board",
200 coreWidgetClass, winMainWindow,
201 XtNwidth, boardWidth,
202 XtNheight, boardHeight,
203 XtNborderWidth, 1,
204 NULL);
205 #endif
206 quitWidget
207 = XtVaCreateManagedWidget("quit",
208 commandWidgetClass, winMainWindow,
209 XtNlabel, "Quit",
210 #ifdef BUTTONS_AT_BOTTOM
211 XtNfromVert, boardWidget,
212 #endif
213 NULL);
214 newWidget
215 = XtVaCreateManagedWidget("new",
216 commandWidgetClass, winMainWindow,
217 XtNlabel, "New game",
218 XtNfromHoriz, quitWidget,
219 #ifdef BUTTONS_AT_BOTTOM
220 XtNfromVert, boardWidget,
221 #endif
222 NULL);
223 optWidget
224 = XtVaCreateManagedWidget("options",
225 commandWidgetClass, winMainWindow,
226 XtNlabel, "Options",
227 XtNfromHoriz, newWidget,
228 #ifdef BUTTONS_AT_BOTTOM
229 XtNfromVert, boardWidget,
230 #endif
231 NULL);
232 #ifdef UNDO
233 undoWidget
234 = XtVaCreateManagedWidget("undo",
235 commandWidgetClass, winMainWindow,
236 XtNlabel, "Undo",
237 XtNsensitive, 0,
238 XtNfromHoriz, optWidget,
239 #ifdef BUTTONS_AT_BOTTOM
240 XtNfromVert, boardWidget,
241 #endif
242 NULL);
243 #endif
244 highscoresButton
245 = XtVaCreateManagedWidget("highscoresButton",
246 commandWidgetClass, winMainWindow,
247 XtNlabel, "Highscores",
248 #ifdef UNDO
249 XtNfromHoriz, undoWidget,
250 #else
251 XtNfromHoriz, optWidget,
252 #endif
253 #ifdef BUTTONS_AT_BOTTOM
254 XtNfromVert, boardWidget,
255 #endif
256 NULL);
257 aboutButton
258 = XtVaCreateManagedWidget("aboutButton",
259 commandWidgetClass, winMainWindow,
260 XtNlabel, "About",
261 XtNfromHoriz, highscoresButton,
262 #ifdef BUTTONS_AT_BOTTOM
263 XtNfromVert, boardWidget,
264 #endif
265 NULL);
266 readmeButton
267 = XtVaCreateManagedWidget("readmeButton",
268 commandWidgetClass, winMainWindow,
269 XtNlabel, "Help",
270 XtNfromHoriz, aboutButton,
271 #ifdef BUTTONS_AT_BOTTOM
272 XtNfromVert, boardWidget,
273 #endif
274 NULL);
275 timeWidget
276 = XtVaCreateManagedWidget("time",
277 labelWidgetClass, winMainWindow,
278 XtNlabel, "Time: 0:00",
279 XtNfromHoriz, readmeButton,
280 XtNsensitive, 0,
281 #ifdef BUTTONS_AT_BOTTOM
282 XtNfromVert, boardWidget,
283 #endif
284 NULL);
285 #ifndef BUTTONS_AT_BOTTOM
286 /* otherwise, board is set up first. see above. */
287 boardWidget
288 = XtVaCreateManagedWidget("board",
289 coreWidgetClass, winMainWindow,
290 XtNwidth, boardWidth,
291 XtNheight, boardHeight,
292 XtNfromVert, quitWidget,
293 XtNborderWidth, 1,
294 NULL);
295 #endif
296
297 XtAddCallback(quitWidget, XtNcallback, callbackQuit, 0);
298 XtAddCallback(newWidget, XtNcallback, callbackNewGame, 0);
299 XtAddCallback(optWidget, XtNcallback, callbackOptions, 0);
300 #ifdef UNDO
301 XtAddCallback(undoWidget, XtNcallback, callbackUndo, 0);
302 #endif
303 XtAddCallback(aboutButton, XtNcallback, callbackAbout, 0);
304 XtAddCallback(highscoresButton, XtNcallback, callbackHighscores, 0);
305 XtAddCallback(readmeButton, XtNcallback, callbackReadme, 0);
306
307 XtRealizeWidget(winTopLevel);
308
309 boardWin = XtWindowOfObject(boardWidget);
310 scoreTimerId = XtAppAddTimeOut(winAppContext, SCORE_STAT_DELAY,
311 scoreTimerProc, 0);
312 }
313
314 void
winFinish(void)315 winFinish(void)
316 {
317 readmeFinish();
318 highscoresFinish();
319 aboutFinish();
320 optionsFinish();
321 }
322
323 void
winInitGame(void)324 winInitGame(void)
325 {
326 if (gameDoTiming)
327 XtSetSensitive(timeWidget, 1);
328 winShowTime();
329 XtRemoveTimeOut(scoreTimerId);
330 scoreTimerId = XtAppAddTimeOut(winAppContext, SCORE_STAT_DELAY,
331 scoreTimerProc, 0);
332 }
333
334 void
winFinishGame(void)335 winFinishGame(void)
336 {
337 if (timerRunning) {
338 XtRemoveTimeOut(timerId);
339 timerRunning = 0;
340 }
341 #ifdef UNDO
342 XtSetSensitive(undoWidget, 0);
343 #endif
344 XtSetSensitive(timeWidget, 0);
345 }
346
347 void
winMainLoop(void)348 winMainLoop(void)
349 {
350 while (!gameExit)
351 winGetAndHandleEvent();
352 }
353
354 void
winFlush(void)355 winFlush(void)
356 {
357 XFlush(winDisplay);
358 }
359
360 void
winShowTime(void)361 winShowTime(void)
362 {
363 char text[40];
364
365 if (!gameDoTiming)
366 return;
367 sprintf(text, "Time: %6.6s", gameTimeToStr(gameTime));
368 XtVaSetValues(timeWidget, XtNlabel, text, NULL);
369 winFlush();
370 }
371
372 void
winStartTiming(void)373 winStartTiming(void)
374 {
375 if (timerRunning)
376 return;
377 timerId = XtAppAddTimeOut(winAppContext, 1000, timerProc, 0);
378 timerRunning = 1;
379 }
380