changes from H.G. Muller; version 4.3.15
[xboard.git] / xboard.c
1 /*\r
2  * xboard.c -- X front end for XBoard\r
3  * $Id: xboard.c,v 2.2 2003/11/06 07:22:14 mann Exp $\r
4  *\r
5  * Copyright 1991 by Digital Equipment Corporation, Maynard, Massachusetts.\r
6  * Enhancements Copyright 1992-2001 Free Software Foundation, Inc.\r
7  *\r
8  * The following terms apply to Digital Equipment Corporation's copyright\r
9  * interest in XBoard:\r
10  * ------------------------------------------------------------------------\r
11  * All Rights Reserved\r
12  *\r
13  * Permission to use, copy, modify, and distribute this software and its\r
14  * documentation for any purpose and without fee is hereby granted,\r
15  * provided that the above copyright notice appear in all copies and that\r
16  * both that copyright notice and this permission notice appear in\r
17  * supporting documentation, and that the name of Digital not be\r
18  * used in advertising or publicity pertaining to distribution of the\r
19  * software without specific, written prior permission.\r
20  *\r
21  * DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING\r
22  * ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL\r
23  * DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR\r
24  * ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,\r
25  * WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,\r
26  * ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS\r
27  * SOFTWARE.\r
28  * ------------------------------------------------------------------------\r
29  *\r
30  * The following terms apply to the enhanced version of XBoard distributed\r
31  * by the Free Software Foundation:\r
32  * ------------------------------------------------------------------------\r
33  * This program is free software; you can redistribute it and/or modify\r
34  * it under the terms of the GNU General Public License as published by\r
35  * the Free Software Foundation; either version 2 of the License, or\r
36  * (at your option) any later version.\r
37  *\r
38  * This program is distributed in the hope that it will be useful,\r
39  * but WITHOUT ANY WARRANTY; without even the implied warranty of\r
40  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r
41  * GNU General Public License for more details.\r
42  *\r
43  * You should have received a copy of the GNU General Public License\r
44  * along with this program; if not, write to the Free Software\r
45  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.\r
46  * ------------------------------------------------------------------------\r
47  *\r
48  * See the file ChangeLog for a revision history.\r
49  */\r
50 \r
51 #include "config.h"\r
52 \r
53 #include <stdio.h>\r
54 #include <ctype.h>\r
55 #include <signal.h>\r
56 #include <errno.h>\r
57 #include <sys/types.h>\r
58 #include <sys/stat.h>\r
59 #include <pwd.h>\r
60 \r
61 #if !OMIT_SOCKETS\r
62 # if HAVE_SYS_SOCKET_H\r
63 #  include <sys/socket.h>\r
64 #  include <netinet/in.h>\r
65 #  include <netdb.h>\r
66 # else /* not HAVE_SYS_SOCKET_H */\r
67 #  if HAVE_LAN_SOCKET_H\r
68 #   include <lan/socket.h>\r
69 #   include <lan/in.h>\r
70 #   include <lan/netdb.h>\r
71 #  else /* not HAVE_LAN_SOCKET_H */\r
72 #   define OMIT_SOCKETS 1\r
73 #  endif /* not HAVE_LAN_SOCKET_H */\r
74 # endif /* not HAVE_SYS_SOCKET_H */\r
75 #endif /* !OMIT_SOCKETS */\r
76 \r
77 #if STDC_HEADERS\r
78 # include <stdlib.h>\r
79 # include <string.h>\r
80 #else /* not STDC_HEADERS */\r
81 extern char *getenv();\r
82 # if HAVE_STRING_H\r
83 #  include <string.h>\r
84 # else /* not HAVE_STRING_H */\r
85 #  include <strings.h>\r
86 # endif /* not HAVE_STRING_H */\r
87 #endif /* not STDC_HEADERS */\r
88 \r
89 #if HAVE_SYS_FCNTL_H\r
90 # include <sys/fcntl.h>\r
91 #else /* not HAVE_SYS_FCNTL_H */\r
92 # if HAVE_FCNTL_H\r
93 #  include <fcntl.h>\r
94 # endif /* HAVE_FCNTL_H */\r
95 #endif /* not HAVE_SYS_FCNTL_H */\r
96 \r
97 #if HAVE_SYS_SYSTEMINFO_H\r
98 # include <sys/systeminfo.h>\r
99 #endif /* HAVE_SYS_SYSTEMINFO_H */\r
100 \r
101 #if TIME_WITH_SYS_TIME\r
102 # include <sys/time.h>\r
103 # include <time.h>\r
104 #else\r
105 # if HAVE_SYS_TIME_H\r
106 #  include <sys/time.h>\r
107 # else\r
108 #  include <time.h>\r
109 # endif\r
110 #endif\r
111 \r
112 #if HAVE_UNISTD_H\r
113 # include <unistd.h>\r
114 #endif\r
115 \r
116 #if HAVE_SYS_WAIT_H\r
117 # include <sys/wait.h>\r
118 #endif\r
119 \r
120 #if HAVE_DIRENT_H\r
121 # include <dirent.h>\r
122 # define NAMLEN(dirent) strlen((dirent)->d_name)\r
123 # define HAVE_DIR_STRUCT\r
124 #else\r
125 # define dirent direct\r
126 # define NAMLEN(dirent) (dirent)->d_namlen\r
127 # if HAVE_SYS_NDIR_H\r
128 #  include <sys/ndir.h>\r
129 #  define HAVE_DIR_STRUCT\r
130 # endif\r
131 # if HAVE_SYS_DIR_H\r
132 #  include <sys/dir.h>\r
133 #  define HAVE_DIR_STRUCT\r
134 # endif\r
135 # if HAVE_NDIR_H\r
136 #  include <ndir.h>\r
137 #  define HAVE_DIR_STRUCT\r
138 # endif\r
139 #endif\r
140 \r
141 #include <X11/Intrinsic.h>\r
142 #include <X11/StringDefs.h>\r
143 #include <X11/Shell.h>\r
144 #include <X11/cursorfont.h>\r
145 #include <X11/Xatom.h>\r
146 #if USE_XAW3D\r
147 #include <X11/Xaw3d/Dialog.h>\r
148 #include <X11/Xaw3d/Form.h>\r
149 #include <X11/Xaw3d/List.h>\r
150 #include <X11/Xaw3d/Label.h>\r
151 #include <X11/Xaw3d/SimpleMenu.h>\r
152 #include <X11/Xaw3d/SmeBSB.h>\r
153 #include <X11/Xaw3d/SmeLine.h>\r
154 #include <X11/Xaw3d/Box.h>\r
155 #include <X11/Xaw3d/MenuButton.h>\r
156 #include <X11/Xaw3d/Text.h>\r
157 #include <X11/Xaw3d/AsciiText.h>\r
158 #else\r
159 #include <X11/Xaw/Dialog.h>\r
160 #include <X11/Xaw/Form.h>\r
161 #include <X11/Xaw/List.h>\r
162 #include <X11/Xaw/Label.h>\r
163 #include <X11/Xaw/SimpleMenu.h>\r
164 #include <X11/Xaw/SmeBSB.h>\r
165 #include <X11/Xaw/SmeLine.h>\r
166 #include <X11/Xaw/Box.h>\r
167 #include <X11/Xaw/MenuButton.h>\r
168 #include <X11/Xaw/Text.h>\r
169 #include <X11/Xaw/AsciiText.h>\r
170 #endif\r
171 \r
172 // [HGM] bitmaps: put before incuding the bitmaps / pixmaps, to know how many piece types there are.\r
173 #include "common.h"\r
174 \r
175 #if HAVE_LIBXPM\r
176 #include <X11/xpm.h>\r
177 #include "pixmaps/pixmaps.h"\r
178 #define IMAGE_EXT "xpm"\r
179 #else\r
180 #define IMAGE_EXT "xim"\r
181 #include "bitmaps/bitmaps.h"\r
182 #endif\r
183 \r
184 #include "bitmaps/icon_white.bm"\r
185 #include "bitmaps/icon_black.bm"\r
186 #include "bitmaps/checkmark.bm"\r
187 \r
188 #include "frontend.h"\r
189 #include "backend.h"\r
190 #include "moves.h"\r
191 #include "xboard.h"\r
192 #include "childio.h"\r
193 #include "xgamelist.h"\r
194 #include "xhistory.h"\r
195 #include "xedittags.h"
196
197 // must be moved to xengineoutput.h
198 void EngineOutputProc P((Widget w, XEvent *event,
199                         String *prms, Cardinal *nprms));
200 void EngineOutputPopDown();\r
201 \r
202 \r
203 #ifdef __EMX__\r
204 #ifndef HAVE_USLEEP\r
205 #define HAVE_USLEEP\r
206 #endif\r
207 #define usleep(t)   _sleep2(((t)+500)/1000)\r
208 #endif\r
209 \r
210 typedef struct {\r
211     String string;\r
212     XtActionProc proc;\r
213 } MenuItem;\r
214 \r
215 typedef struct {\r
216     String name;\r
217     MenuItem *mi;\r
218 } Menu;\r
219 \r
220 int main P((int argc, char **argv));\r
221 RETSIGTYPE CmailSigHandler P((int sig));\r
222 RETSIGTYPE IntSigHandler P((int sig));\r
223 void CreateGCs P((void));\r
224 void CreateXIMPieces P((void));\r
225 void CreateXPMPieces P((void));\r
226 void CreatePieces P((void));\r
227 void CreatePieceMenus P((void));\r
228 Widget CreateMenuBar P((Menu *mb));\r
229 Widget CreateButtonBar P ((MenuItem *mi));\r
230 char *FindFont P((char *pattern, int targetPxlSize));\r
231 void PieceMenuPopup P((Widget w, XEvent *event,\r
232                        String *params, Cardinal *num_params));\r
233 static void PieceMenuSelect P((Widget w, ChessSquare piece, caddr_t junk));\r
234 static void DropMenuSelect P((Widget w, ChessSquare piece, caddr_t junk));\r
235 void ReadBitmap P((Pixmap *pm, String name, unsigned char bits[],\r
236                    u_int wreq, u_int hreq));\r
237 void CreateGrid P((void));\r
238 int EventToSquare P((int x, int limit));\r
239 void DrawSquare P((int row, int column, ChessSquare piece, int do_flash));\r
240 void EventProc P((Widget widget, caddr_t unused, XEvent *event));\r
241 void HandleUserMove P((Widget w, XEvent *event,\r
242                      String *prms, Cardinal *nprms));\r
243 void AnimateUserMove P((Widget w, XEvent * event,\r
244                      String * params, Cardinal * nParams));\r
245 void WhiteClock P((Widget w, XEvent *event,\r
246                    String *prms, Cardinal *nprms));\r
247 void BlackClock P((Widget w, XEvent *event,\r
248                    String *prms, Cardinal *nprms));\r
249 void DrawPositionProc P((Widget w, XEvent *event,\r
250                      String *prms, Cardinal *nprms));\r
251 void XDrawPosition P((Widget w, /*Boolean*/int repaint, \r
252                      Board board));\r
253 void CommentPopUp P((char *title, char *label));\r
254 void CommentPopDown P((void));\r
255 void CommentCallback P((Widget w, XtPointer client_data,\r
256                         XtPointer call_data));\r
257 void ICSInputBoxPopUp P((void));\r
258 void ICSInputBoxPopDown P((void));\r
259 void FileNamePopUp P((char *label, char *def,\r
260                       FileProc proc, char *openMode));\r
261 void FileNamePopDown P((void));\r
262 void FileNameCallback P((Widget w, XtPointer client_data,\r
263                          XtPointer call_data));\r
264 void FileNameAction P((Widget w, XEvent *event,\r
265                        String *prms, Cardinal *nprms));\r
266 void AskQuestionReplyAction P((Widget w, XEvent *event,\r
267                           String *prms, Cardinal *nprms));\r
268 void AskQuestionProc P((Widget w, XEvent *event,\r
269                           String *prms, Cardinal *nprms));\r
270 void AskQuestionPopDown P((void));\r
271 void PromotionPopUp P((void));\r
272 void PromotionPopDown P((void));\r
273 void PromotionCallback P((Widget w, XtPointer client_data,\r
274                           XtPointer call_data));\r
275 void EditCommentPopDown P((void));\r
276 void EditCommentCallback P((Widget w, XtPointer client_data,\r
277                             XtPointer call_data));\r
278 void SelectCommand P((Widget w, XtPointer client_data, XtPointer call_data));\r
279 void ResetProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
280 void LoadGameProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
281 void LoadNextGameProc P((Widget w, XEvent *event, String *prms,\r
282                          Cardinal *nprms));\r
283 void LoadPrevGameProc P((Widget w, XEvent *event, String *prms,\r
284                          Cardinal *nprms));\r
285 void ReloadGameProc P((Widget w, XEvent *event, String *prms,\r
286                        Cardinal *nprms));\r
287 void LoadPositionProc P((Widget w, XEvent *event,\r
288                          String *prms, Cardinal *nprms));\r
289 void LoadNextPositionProc P((Widget w, XEvent *event, String *prms,\r
290                          Cardinal *nprms));\r
291 void LoadPrevPositionProc P((Widget w, XEvent *event, String *prms,\r
292                          Cardinal *nprms));\r
293 void ReloadPositionProc P((Widget w, XEvent *event, String *prms,\r
294                        Cardinal *nprms));\r
295 void CopyPositionProc P((Widget w, XEvent *event, String *prms,\r
296                          Cardinal *nprms));\r
297 void PastePositionProc P((Widget w, XEvent *event, String *prms,\r
298                           Cardinal *nprms));\r
299 void CopyGameProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
300 void PasteGameProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
301 void SaveGameProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
302 void SavePositionProc P((Widget w, XEvent *event,\r
303                          String *prms, Cardinal *nprms));\r
304 void MailMoveProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
305 void ReloadCmailMsgProc P((Widget w, XEvent *event, String *prms,\r
306                             Cardinal *nprms));\r
307 void QuitProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
308 void PauseProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
309 void MachineBlackProc P((Widget w, XEvent *event, String *prms,\r
310                          Cardinal *nprms));\r
311 void MachineWhiteProc P((Widget w, XEvent *event,\r
312                          String *prms, Cardinal *nprms));\r
313 void AnalyzeModeProc P((Widget w, XEvent *event,\r
314                          String *prms, Cardinal *nprms));\r
315 void AnalyzeFileProc P((Widget w, XEvent *event,\r
316                          String *prms, Cardinal *nprms));\r
317 void TwoMachinesProc P((Widget w, XEvent *event, String *prms,\r
318                         Cardinal *nprms));\r
319 void IcsClientProc P((Widget w, XEvent *event, String *prms,\r
320                       Cardinal *nprms));\r
321 void EditGameProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
322 void EditPositionProc P((Widget w, XEvent *event,\r
323                          String *prms, Cardinal *nprms));\r
324 void TrainingProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
325 void EditCommentProc P((Widget w, XEvent *event,\r
326                         String *prms, Cardinal *nprms));\r
327 void IcsInputBoxProc P((Widget w, XEvent *event,\r
328                         String *prms, Cardinal *nprms));\r
329 void AcceptProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
330 void DeclineProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
331 void RematchProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
332 void CallFlagProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
333 void DrawProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
334 void AbortProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
335 void AdjournProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
336 void ResignProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
337 void EnterKeyProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
338 void StopObservingProc P((Widget w, XEvent *event, String *prms,\r
339                           Cardinal *nprms));\r
340 void StopExaminingProc P((Widget w, XEvent *event, String *prms,\r
341                           Cardinal *nprms));\r
342 void BackwardProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
343 void ForwardProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
344 void ToStartProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
345 void ToEndProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
346 void RevertProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
347 void TruncateGameProc P((Widget w, XEvent *event, String *prms,\r
348                          Cardinal *nprms));\r
349 void RetractMoveProc P((Widget w, XEvent *event, String *prms,\r
350                         Cardinal *nprms));\r
351 void MoveNowProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
352 void AlwaysQueenProc P((Widget w, XEvent *event, String *prms,\r
353                         Cardinal *nprms));\r
354 void AnimateDraggingProc P((Widget w, XEvent *event, String *prms,\r
355                          Cardinal *nprms));\r
356 void AnimateMovingProc P((Widget w, XEvent *event, String *prms,\r
357                          Cardinal *nprms));\r
358 void AutocommProc P((Widget w, XEvent *event, String *prms,\r
359                      Cardinal *nprms));\r
360 void AutoflagProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
361 void AutoflipProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
362 void AutobsProc P((Widget w, XEvent *event, String *prms,\r
363                         Cardinal *nprms));\r
364 void AutoraiseProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
365 void AutosaveProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
366 void BlindfoldProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
367 void FlashMovesProc P((Widget w, XEvent *event, String *prms,\r
368                        Cardinal *nprms));\r
369 void FlipViewProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
370 void GetMoveListProc P((Widget w, XEvent *event, String *prms,\r
371                         Cardinal *nprms));\r
372 void HighlightDraggingProc P((Widget w, XEvent *event, String *prms,\r
373                               Cardinal *nprms));\r
374 void HighlightLastMoveProc P((Widget w, XEvent *event, String *prms,\r
375                               Cardinal *nprms));\r
376 void MoveSoundProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
377 void IcsAlarmProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
378 void OldSaveStyleProc P((Widget w, XEvent *event, String *prms,\r
379                          Cardinal *nprms));\r
380 void PeriodicUpdatesProc P((Widget w, XEvent *event, String *prms,\r
381                          Cardinal *nprms));\r
382 void PonderNextMoveProc P((Widget w, XEvent *event, String *prms,\r
383                            Cardinal *nprms));\r
384 void PopupMoveErrorsProc P((Widget w, XEvent *event, String *prms,\r
385                         Cardinal *nprms));\r
386 void PopupExitMessageProc P((Widget w, XEvent *event, String *prms,\r
387                              Cardinal *nprms));\r
388 void PremoveProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
389 void QuietPlayProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
390 void ShowCoordsProc P((Widget w, XEvent *event, String *prms,\r
391                        Cardinal *nprms));\r
392 void ShowThinkingProc P((Widget w, XEvent *event, String *prms,\r
393                          Cardinal *nprms));\r
394 void HideThinkingProc P((Widget w, XEvent *event, String *prms,\r
395                          Cardinal *nprms));\r
396 void TestLegalityProc P((Widget w, XEvent *event, String *prms,\r
397                           Cardinal *nprms));\r
398 void InfoProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
399 void ManProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
400 void HintProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
401 void BookProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
402 void AboutGameProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
403 void AboutProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
404 void DebugProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
405 void NothingProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
406 void Iconify P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
407 void DisplayMove P((int moveNumber));\r
408 void DisplayTitle P((char *title));\r
409 void ICSInitScript P((void));\r
410 int LoadGamePopUp P((FILE *f, int gameNumber, char *title));\r
411 void ErrorPopUp P((char *title, char *text, int modal));\r
412 void ErrorPopDown P((void));\r
413 static char *ExpandPathName P((char *path));\r
414 static void CreateAnimVars P((void));\r
415 static void DragPieceBegin P((int x, int y));\r
416 static void DragPieceMove P((int x, int y));\r
417 static void DragPieceEnd P((int x, int y));\r
418 static void DrawDragPiece P((void));\r
419 char *ModeToWidgetName P((GameMode mode));\r
420 void EngineOutputUpdate( FrontEndProgramStats * stats );\r
421 void ShuffleMenuProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
422 void EngineMenuProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
423 void UciMenuProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
424 void TimeControlProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
425 void NewVariantProc P((Widget w, XEvent *event, String *prms, Cardinal *nprms));\r
426 void ShufflePopDown P(());\r
427 void EnginePopDown P(());\r
428 void UciPopDown P(());\r
429 void TimeControlPopDown P(());\r
430 void NewVariantPopDown P(());\r
431 /*\r
432 * XBoard depends on Xt R4 or higher\r
433 */\r
434 int xtVersion = XtSpecificationRelease;\r
435 \r
436 int xScreen;\r
437 Display *xDisplay;\r
438 Window xBoardWindow;\r
439 Pixel lightSquareColor, darkSquareColor, whitePieceColor, blackPieceColor,\r
440   jailSquareColor, highlightSquareColor, premoveHighlightColor;\r
441 GC lightSquareGC, darkSquareGC, jailSquareGC, lineGC, wdPieceGC, wlPieceGC,\r
442   bdPieceGC, blPieceGC, wbPieceGC, bwPieceGC, coordGC, highlineGC,\r
443   wjPieceGC, bjPieceGC, prelineGC, countGC;\r
444 Pixmap iconPixmap, wIconPixmap, bIconPixmap, xMarkPixmap;\r
445 Widget shellWidget, layoutWidget, formWidget, boardWidget, messageWidget, \r
446   whiteTimerWidget, blackTimerWidget, titleWidget, widgetList[16], \r
447   commentShell, promotionShell, whitePieceMenu, blackPieceMenu, dropMenu,\r
448   menuBarWidget, buttonBarWidget, editShell, errorShell, analysisShell,\r
449   ICSInputShell, fileNameShell, askQuestionShell;\r
450 XSegment gridSegments[(BOARD_SIZE + 1) * 2];\r
451 XSegment jailGridSegments[(BOARD_SIZE + 3) * 2];\r
452 Font clockFontID, coordFontID, countFontID;\r
453 XFontStruct *clockFontStruct, *coordFontStruct, *countFontStruct;\r
454 XtAppContext appContext;\r
455 char *layoutName;\r
456 char *oldICSInteractionTitle;\r
457 \r
458 FileProc fileProc;\r
459 char *fileOpenMode;
460 char installDir[] = "."; // [HGM] UCI: needed for UCI; probably needs run-time initializtion\r
461 \r
462 Position commentX = -1, commentY = -1;\r
463 Dimension commentW, commentH;\r
464 \r
465 int squareSize, smallLayout = 0, tinyLayout = 0,
466   marginW, marginH, // [HGM] for run-time resizing\r
467   fromX = -1, fromY = -1, toX, toY, commentUp = False, analysisUp = False,\r
468   ICSInputBoxUp = False, askQuestionUp = False,\r
469   filenameUp = False, promotionUp = False, pmFromX = -1, pmFromY = -1,\r
470   editUp = False, errorUp = False, errorExitStatus = -1, lineGap;\r
471 Pixel timerForegroundPixel, timerBackgroundPixel;\r
472 Pixel buttonForegroundPixel, buttonBackgroundPixel;\r
473 char *chessDir, *programName, *programVersion,\r
474   *gameCopyFilename, *gamePasteFilename;\r
475 \r
476 #define SOLID 0\r
477 #define OUTLINE 1\r
478 Pixmap pieceBitmap[2][(int)BlackPawn];\r
479 Pixmap xpmPieceBitmap[4][(int)BlackPawn];       /* LL, LD, DL, DD */\r
480 Pixmap xpmLightSquare, xpmDarkSquare, xpmJailSquare;\r
481 int useImages, useImageSqs;\r
482 XImage *ximPieceBitmap[4][(int)BlackPawn];      /* LL, LD, DL, DD */\r
483 Pixmap ximMaskPm[(int)BlackPawn];            /* clipmasks, used for XIM pieces */\r
484 XImage *ximLightSquare, *ximDarkSquare;\r
485 XImage *xim_Cross;\r
486 \r
487 #define pieceToSolid(piece) &pieceBitmap[SOLID][((int)(piece)) % (int)BlackPawn]\r
488 #define pieceToOutline(piece) &pieceBitmap[OUTLINE][((int)(piece)) % (int)BlackPawn]\r
489 \r
490 #define White(piece) ((int)(piece) < (int)BlackPawn)\r
491 \r
492 /* Variables for doing smooth animation. This whole thing\r
493    would be much easier if the board was double-buffered,\r
494    but that would require a fairly major rewrite.       */\r
495 \r
496 typedef struct {\r
497         Pixmap  saveBuf;\r
498         Pixmap  newBuf;\r
499         GC      blitGC, pieceGC, outlineGC;\r
500         XPoint  startSquare, prevFrame, mouseDelta;\r
501         int     startColor;\r
502         int     dragPiece;\r
503         Boolean dragActive;\r
504         int     startBoardX, startBoardY;\r
505     } AnimState;\r
506 \r
507 /* There can be two pieces being animated at once: a player\r
508    can begin dragging a piece before the remote opponent has moved. */\r
509 \r
510 static AnimState game, player;\r
511 \r
512 /* Bitmaps for use as masks when drawing XPM pieces.\r
513    Need one for each black and white piece.             */\r
514 static Pixmap xpmMask[BlackKing + 1];\r
515 \r
516 /* This magic number is the number of intermediate frames used\r
517    in each half of the animation. For short moves it's reduced\r
518    by 1. The total number of frames will be factor * 2 + 1.  */\r
519 #define kFactor    4\r
520 \r
521 SizeDefaults sizeDefaults[] = SIZE_DEFAULTS;\r
522 \r
523 MenuItem fileMenu[] = {\r
524     {"New Game", ResetProc},\r
525     {"New Shuffle Game ...", ShuffleMenuProc},\r
526     {"New Variant ...", NewVariantProc},      // [HGM] variant: not functional yet\r
527     {"----", NothingProc},\r
528     {"Load Game", LoadGameProc},\r
529     {"Load Next Game", LoadNextGameProc},\r
530     {"Load Previous Game", LoadPrevGameProc},\r
531     {"Reload Same Game", ReloadGameProc},\r
532     {"Save Game", SaveGameProc},\r
533     {"----", NothingProc},\r
534     {"Copy Game", CopyGameProc},\r
535     {"Paste Game", PasteGameProc},\r
536     {"----", NothingProc},\r
537     {"Load Position", LoadPositionProc},\r
538     {"Load Next Position", LoadNextPositionProc},\r
539     {"Load Previous Position", LoadPrevPositionProc},\r
540     {"Reload Same Position", ReloadPositionProc},\r
541     {"Save Position", SavePositionProc},\r
542     {"----", NothingProc},\r
543     {"Copy Position", CopyPositionProc},\r
544     {"Paste Position", PastePositionProc},\r
545     {"----", NothingProc},\r
546     {"Mail Move", MailMoveProc},\r
547     {"Reload CMail Message", ReloadCmailMsgProc},\r
548     {"----", NothingProc},\r
549     {"Exit", QuitProc},\r
550     {NULL, NULL}\r
551 };\r
552 \r
553 MenuItem modeMenu[] = {\r
554     {"Machine White", MachineWhiteProc},\r
555     {"Machine Black", MachineBlackProc},\r
556     {"Two Machines", TwoMachinesProc},\r
557     {"Analysis Mode", AnalyzeModeProc},\r
558     {"Analyze File", AnalyzeFileProc },\r
559     {"ICS Client", IcsClientProc},\r
560     {"Edit Game", EditGameProc},\r
561     {"Edit Position", EditPositionProc},\r
562     {"Training", TrainingProc},\r
563     {"----", NothingProc},\r
564     {"Show Engine Output", EngineOutputProc},\r
565     {"Show Evaluation Graph", NothingProc}, // [HGM] evalgr: not functional yet\r
566     {"Show Game List", ShowGameListProc},\r
567     {"Show Move History", HistoryShowProc}, // [HGM] hist: activate 4.2.7 code\r
568     {"----", NothingProc},\r
569     {"Edit Tags", EditTagsProc},\r
570     {"Edit Comment", EditCommentProc},\r
571     {"ICS Input Box", IcsInputBoxProc},\r
572     {"Pause", PauseProc},\r
573     {NULL, NULL}\r
574 };\r
575 \r
576 MenuItem actionMenu[] = {\r
577     {"Accept", AcceptProc},\r
578     {"Decline", DeclineProc},\r
579     {"Rematch", RematchProc},\r
580     {"----", NothingProc},    \r
581     {"Call Flag", CallFlagProc},\r
582     {"Draw", DrawProc},\r
583     {"Adjourn", AdjournProc},\r
584     {"Abort", AbortProc},\r
585     {"Resign", ResignProc},\r
586     {"----", NothingProc},    \r
587     {"Stop Observing", StopObservingProc},\r
588     {"Stop Examining", StopExaminingProc},\r
589     {NULL, NULL}\r
590 };\r
591 \r
592 MenuItem stepMenu[] = {\r
593     {"Backward", BackwardProc},\r
594     {"Forward", ForwardProc},\r
595     {"Back to Start", ToStartProc},\r
596     {"Forward to End", ToEndProc},\r
597     {"Revert", RevertProc},\r
598     {"Truncate Game", TruncateGameProc},\r
599     {"----", NothingProc},    \r
600     {"Move Now", MoveNowProc},\r
601     {"Retract Move", RetractMoveProc},\r
602     {NULL, NULL}\r
603 };    \r
604 \r
605 MenuItem optionsMenu[] = {
606     {"Flip View", FlipViewProc},\r
607     {"----", NothingProc},    \r
608     {"Adjudications ...", EngineMenuProc},    \r
609     {"Engine Settings ...", UciMenuProc},    \r
610     {"Time Control ...", TimeControlProc},    \r
611     {"----", NothingProc},    \r
612     {"Always Queen", AlwaysQueenProc},\r
613     {"Animate Dragging", AnimateDraggingProc},\r
614     {"Animate Moving", AnimateMovingProc},\r
615     {"Auto Comment", AutocommProc},\r
616     {"Auto Flag", AutoflagProc},\r
617     {"Auto Flip View", AutoflipProc},\r
618     {"Auto Observe", AutobsProc},\r
619     {"Auto Raise Board", AutoraiseProc},\r
620     {"Auto Save", AutosaveProc},\r
621     {"Blindfold", BlindfoldProc},\r
622     {"Flash Moves", FlashMovesProc},\r
623     {"Get Move List", GetMoveListProc},\r
624 #if HIGHDRAG\r
625     {"Highlight Dragging", HighlightDraggingProc},\r
626 #endif\r
627     {"Highlight Last Move", HighlightLastMoveProc},\r
628     {"Move Sound", MoveSoundProc},\r
629     {"ICS Alarm", IcsAlarmProc},\r
630     {"Old Save Style", OldSaveStyleProc},\r
631     {"Periodic Updates", PeriodicUpdatesProc},  \r
632     {"Ponder Next Move", PonderNextMoveProc},\r
633     {"Popup Exit Message", PopupExitMessageProc},       \r
634     {"Popup Move Errors", PopupMoveErrorsProc}, \r
635     {"Premove", PremoveProc},\r
636     {"Quiet Play", QuietPlayProc},\r
637     {"Show Coords", ShowCoordsProc},\r
638     {"Hide Thinking", HideThinkingProc},\r
639     {"Test Legality", TestLegalityProc},\r
640     {NULL, NULL}\r
641 };\r
642 \r
643 MenuItem helpMenu[] = {\r
644     {"Info XBoard", InfoProc},\r
645     {"Man XBoard", ManProc},\r
646     {"----", NothingProc},\r
647     {"Hint", HintProc},\r
648     {"Book", BookProc},\r
649     {"----", NothingProc},\r
650     {"About XBoard", AboutProc},\r
651     {NULL, NULL}\r
652 };\r
653 \r
654 Menu menuBar[] = {\r
655     {"File", fileMenu},\r
656     {"Mode", modeMenu},\r
657     {"Action", actionMenu},\r
658     {"Step", stepMenu},\r
659     {"Options", optionsMenu},\r
660     {"Help", helpMenu},\r
661     {NULL, NULL}\r
662 };\r
663 \r
664 #define PAUSE_BUTTON "P"\r
665 MenuItem buttonBar[] = {\r
666     {"<<", ToStartProc},\r
667     {"<", BackwardProc},\r
668     {PAUSE_BUTTON, PauseProc},\r
669     {">", ForwardProc},\r
670     {">>", ToEndProc},\r
671     {NULL, NULL}\r
672 };\r
673 \r
674 #define PIECE_MENU_SIZE 11\r
675 String pieceMenuStrings[2][PIECE_MENU_SIZE] = {\r
676     { "White", "----", "Pawn", "Knight", "Bishop", "Rook", "Queen", "King",\r
677       "----", "Empty square", "Clear board" },\r
678     { "Black", "----", "Pawn", "Knight", "Bishop", "Rook", "Queen", "King",\r
679       "----", "Empty square", "Clear board" },\r
680   };\r
681 /* must be in same order as PieceMenuStrings! */\r
682 ChessSquare pieceMenuTranslation[2][PIECE_MENU_SIZE] = {\r
683     { WhitePlay, (ChessSquare) 0, WhitePawn, WhiteKnight, WhiteBishop,\r
684         WhiteRook, WhiteQueen, WhiteKing,\r
685         (ChessSquare) 0, EmptySquare, ClearBoard },\r
686     { BlackPlay, (ChessSquare) 0, BlackPawn, BlackKnight, BlackBishop,\r
687         BlackRook, BlackQueen, BlackKing,\r
688         (ChessSquare) 0, EmptySquare, ClearBoard },\r
689 };\r
690 \r
691 #define DROP_MENU_SIZE 6\r
692 String dropMenuStrings[DROP_MENU_SIZE] = {\r
693     "----", "Pawn", "Knight", "Bishop", "Rook", "Queen"\r
694   };\r
695 /* must be in same order as PieceMenuStrings! */\r
696 ChessSquare dropMenuTranslation[DROP_MENU_SIZE] = {\r
697     (ChessSquare) 0, WhitePawn, WhiteKnight, WhiteBishop,\r
698     WhiteRook, WhiteQueen\r
699 };\r
700 \r
701 typedef struct {\r
702     char piece;\r
703     char* widget;\r
704 } DropMenuEnables;\r
705 \r
706 DropMenuEnables dmEnables[] = {\r
707     { 'P', "Pawn" },\r
708     { 'N', "Knight" },\r
709     { 'B', "Bishop" },\r
710     { 'R', "Rook" },\r
711     { 'Q', "Queen" }\r
712 };\r
713 \r
714 Arg shellArgs[] = {\r
715     { XtNwidth, 0 },\r
716     { XtNheight, 0 },\r
717     { XtNminWidth, 0 },\r
718     { XtNminHeight, 0 },\r
719     { XtNmaxWidth, 0 },\r
720     { XtNmaxHeight, 0 }\r
721 };\r
722 \r
723 Arg layoutArgs[] = {\r
724     { XtNborderWidth, 0 },\r
725     { XtNdefaultDistance, 0 },\r
726 };\r
727 \r
728 Arg formArgs[] = {\r
729     { XtNborderWidth, 0 },\r
730     { XtNresizable, (XtArgVal) True },\r
731 };\r
732 \r
733 Arg boardArgs[] = {\r
734     { XtNborderWidth, 0 },\r
735     { XtNwidth, 0 },\r
736     { XtNheight, 0 }\r
737 };\r
738 \r
739 Arg titleArgs[] = {\r
740     { XtNjustify, (XtArgVal) XtJustifyRight },\r
741     { XtNlabel, (XtArgVal) "..." },\r
742     { XtNresizable, (XtArgVal) True },\r
743     { XtNresize, (XtArgVal) False }\r
744 };\r
745 \r
746 Arg messageArgs[] = {\r
747     { XtNjustify, (XtArgVal) XtJustifyLeft },\r
748     { XtNlabel, (XtArgVal) "..." },\r
749     { XtNresizable, (XtArgVal) True },\r
750     { XtNresize, (XtArgVal) False }\r
751 };\r
752 \r
753 Arg timerArgs[] = {\r
754     { XtNborderWidth, 0 },\r
755     { XtNjustify, (XtArgVal) XtJustifyLeft }\r
756 };\r
757 \r
758 XtResource clientResources[] = {\r
759     { "whitePieceColor", "whitePieceColor", XtRString, sizeof(String),\r
760         XtOffset(AppDataPtr, whitePieceColor), XtRString,\r
761         WHITE_PIECE_COLOR },\r
762     { "blackPieceColor", "blackPieceColor", XtRString, sizeof(String),\r
763         XtOffset(AppDataPtr, blackPieceColor), XtRString,\r
764         BLACK_PIECE_COLOR },\r
765     { "lightSquareColor", "lightSquareColor", XtRString,\r
766         sizeof(String), XtOffset(AppDataPtr, lightSquareColor),\r
767         XtRString, LIGHT_SQUARE_COLOR }, \r
768     { "darkSquareColor", "darkSquareColor", XtRString, sizeof(String),\r
769         XtOffset(AppDataPtr, darkSquareColor), XtRString,\r
770         DARK_SQUARE_COLOR },\r
771     { "highlightSquareColor", "highlightSquareColor", XtRString,\r
772         sizeof(String), XtOffset(AppDataPtr, highlightSquareColor),\r
773         XtRString, HIGHLIGHT_SQUARE_COLOR },\r
774     { "premoveHighlightColor", "premoveHighlightColor", XtRString,\r
775         sizeof(String), XtOffset(AppDataPtr, premoveHighlightColor),\r
776         XtRString, PREMOVE_HIGHLIGHT_COLOR },\r
777     { "movesPerSession", "movesPerSession", XtRInt, sizeof(int),\r
778         XtOffset(AppDataPtr, movesPerSession), XtRImmediate,\r
779         (XtPointer) MOVES_PER_SESSION },\r
780     { "timeIncrement", "timeIncrement", XtRInt, sizeof(int),\r
781         XtOffset(AppDataPtr, timeIncrement), XtRImmediate,\r
782         (XtPointer) TIME_INCREMENT },\r
783     { "initString", "initString", XtRString, sizeof(String),\r
784         XtOffset(AppDataPtr, initString), XtRString, INIT_STRING },\r
785     { "secondInitString", "secondInitString", XtRString, sizeof(String),\r
786         XtOffset(AppDataPtr, secondInitString), XtRString, INIT_STRING },\r
787     { "firstComputerString", "firstComputerString", XtRString,\r
788         sizeof(String), XtOffset(AppDataPtr, firstComputerString), XtRString,\r
789       COMPUTER_STRING },\r
790     { "secondComputerString", "secondComputerString", XtRString,\r
791         sizeof(String), XtOffset(AppDataPtr, secondComputerString), XtRString,\r
792       COMPUTER_STRING },\r
793     { "firstChessProgram", "firstChessProgram", XtRString,\r
794         sizeof(String), XtOffset(AppDataPtr, firstChessProgram),\r
795         XtRString, FIRST_CHESS_PROGRAM },\r
796     { "secondChessProgram", "secondChessProgram", XtRString,\r
797         sizeof(String), XtOffset(AppDataPtr, secondChessProgram),\r
798         XtRString, SECOND_CHESS_PROGRAM },\r
799     { "firstPlaysBlack", "firstPlaysBlack", XtRBoolean,\r
800         sizeof(Boolean), XtOffset(AppDataPtr, firstPlaysBlack),\r
801         XtRImmediate, (XtPointer) False },\r
802     { "noChessProgram", "noChessProgram", XtRBoolean,\r
803         sizeof(Boolean), XtOffset(AppDataPtr, noChessProgram),\r
804         XtRImmediate, (XtPointer) False },\r
805     { "firstHost", "firstHost", XtRString, sizeof(String),\r
806         XtOffset(AppDataPtr, firstHost), XtRString, FIRST_HOST },\r
807     { "secondHost", "secondHost", XtRString, sizeof(String),\r
808         XtOffset(AppDataPtr, secondHost), XtRString, SECOND_HOST },\r
809     { "firstDirectory", "firstDirectory", XtRString, sizeof(String),\r
810         XtOffset(AppDataPtr, firstDirectory), XtRString, "." },\r
811     { "secondDirectory", "secondDirectory", XtRString, sizeof(String),\r
812         XtOffset(AppDataPtr, secondDirectory), XtRString, "." },\r
813     { "bitmapDirectory", "bitmapDirectory", XtRString,\r
814         sizeof(String), XtOffset(AppDataPtr, bitmapDirectory),\r
815         XtRString, "" },\r
816     { "remoteShell", "remoteShell", XtRString, sizeof(String),\r
817         XtOffset(AppDataPtr, remoteShell), XtRString, REMOTE_SHELL },\r
818     { "remoteUser", "remoteUser", XtRString, sizeof(String),\r
819         XtOffset(AppDataPtr, remoteUser), XtRString, "" },\r
820     { "timeDelay", "timeDelay", XtRFloat, sizeof(float),\r
821         XtOffset(AppDataPtr, timeDelay), XtRString,\r
822         (XtPointer) TIME_DELAY_QUOTE },\r
823     { "timeControl", "timeControl", XtRString, sizeof(String),\r
824         XtOffset(AppDataPtr, timeControl), XtRString,\r
825         (XtPointer) TIME_CONTROL },\r
826     { "internetChessServerMode", "internetChessServerMode",\r
827         XtRBoolean, sizeof(Boolean),\r
828         XtOffset(AppDataPtr, icsActive), XtRImmediate,\r
829         (XtPointer) False },\r
830     { "internetChessServerHost", "internetChessServerHost",\r
831         XtRString, sizeof(String),\r
832         XtOffset(AppDataPtr, icsHost),\r
833         XtRString, (XtPointer) ICS_HOST },\r
834     { "internetChessServerPort", "internetChessServerPort",\r
835         XtRString, sizeof(String),\r
836         XtOffset(AppDataPtr, icsPort), XtRString,\r
837         (XtPointer) ICS_PORT },\r
838     { "internetChessServerCommPort", "internetChessServerCommPort",\r
839         XtRString, sizeof(String),\r
840         XtOffset(AppDataPtr, icsCommPort), XtRString,\r
841         ICS_COMM_PORT },\r
842     { "internetChessServerLogonScript", "internetChessServerLogonScript",\r
843         XtRString, sizeof(String),\r
844         XtOffset(AppDataPtr, icsLogon), XtRString,\r
845         ICS_LOGON },\r
846     { "internetChessServerHelper", "internetChessServerHelper",\r
847         XtRString, sizeof(String),\r
848         XtOffset(AppDataPtr, icsHelper), XtRString, "" },\r
849     { "internetChessServerInputBox", "internetChessServerInputBox",\r
850         XtRBoolean, sizeof(Boolean),\r
851         XtOffset(AppDataPtr, icsInputBox), XtRImmediate,\r
852         (XtPointer) False },\r
853     { "icsAlarm", "icsAlarm",\r
854         XtRBoolean, sizeof(Boolean),\r
855         XtOffset(AppDataPtr, icsAlarm), XtRImmediate,\r
856         (XtPointer) True },\r
857     { "icsAlarmTime", "icsAlarmTime",\r
858         XtRInt, sizeof(int),\r
859         XtOffset(AppDataPtr, icsAlarmTime), XtRImmediate,\r
860         (XtPointer) 5000 },\r
861     { "useTelnet", "useTelnet", XtRBoolean, sizeof(Boolean),\r
862         XtOffset(AppDataPtr, useTelnet), XtRImmediate,\r
863         (XtPointer) False },\r
864     { "telnetProgram", "telnetProgram", XtRString, sizeof(String),\r
865         XtOffset(AppDataPtr, telnetProgram), XtRString, TELNET_PROGRAM },\r
866     { "gateway", "gateway", XtRString, sizeof(String),\r
867         XtOffset(AppDataPtr, gateway), XtRString, "" },\r
868     { "loadGameFile", "loadGameFile", XtRString, sizeof(String),\r
869         XtOffset(AppDataPtr, loadGameFile), XtRString, "" },\r
870     { "loadGameIndex", "loadGameIndex",\r
871         XtRInt, sizeof(int),\r
872         XtOffset(AppDataPtr, loadGameIndex), XtRImmediate,\r
873         (XtPointer) 0 },\r
874     { "saveGameFile", "saveGameFile", XtRString, sizeof(String),\r
875         XtOffset(AppDataPtr, saveGameFile), XtRString, "" },\r
876     { "autoRaiseBoard", "autoRaiseBoard", XtRBoolean,\r
877         sizeof(Boolean), XtOffset(AppDataPtr, autoRaiseBoard),\r
878         XtRImmediate, (XtPointer) True },\r
879     { "autoSaveGames", "autoSaveGames", XtRBoolean,\r
880         sizeof(Boolean), XtOffset(AppDataPtr, autoSaveGames),\r
881         XtRImmediate, (XtPointer) False },\r
882     { "blindfold", "blindfold", XtRBoolean,\r
883         sizeof(Boolean), XtOffset(AppDataPtr, blindfold),\r
884         XtRImmediate, (XtPointer) False },\r
885     { "loadPositionFile", "loadPositionFile", XtRString,\r
886         sizeof(String), XtOffset(AppDataPtr, loadPositionFile),\r
887         XtRString, "" },\r
888     { "loadPositionIndex", "loadPositionIndex",\r
889         XtRInt, sizeof(int),\r
890         XtOffset(AppDataPtr, loadPositionIndex), XtRImmediate,\r
891         (XtPointer) 1 },\r
892     { "savePositionFile", "savePositionFile", XtRString,\r
893         sizeof(String), XtOffset(AppDataPtr, savePositionFile),\r
894         XtRString, "" },\r
895     { "matchMode", "matchMode", XtRBoolean, sizeof(Boolean),\r
896         XtOffset(AppDataPtr, matchMode), XtRImmediate, (XtPointer) False },\r
897     { "matchGames", "matchGames", XtRInt, sizeof(int),\r
898         XtOffset(AppDataPtr, matchGames), XtRImmediate,\r
899         (XtPointer) 0 },\r
900     { "monoMode", "monoMode", XtRBoolean, sizeof(Boolean),\r
901         XtOffset(AppDataPtr, monoMode), XtRImmediate,\r
902         (XtPointer) False },\r
903     { "debugMode", "debugMode", XtRBoolean, sizeof(Boolean),\r
904         XtOffset(AppDataPtr, debugMode), XtRImmediate,\r
905         (XtPointer) False },\r
906     { "clockMode", "clockMode", XtRBoolean, sizeof(Boolean),\r
907         XtOffset(AppDataPtr, clockMode), XtRImmediate,\r
908         (XtPointer) True },\r
909     { "boardSize", "boardSize", XtRString, sizeof(String),\r
910         XtOffset(AppDataPtr, boardSize), XtRString, "" },\r
911     { "searchTime", "searchTime", XtRString, sizeof(String),\r
912         XtOffset(AppDataPtr, searchTime), XtRString,\r
913         (XtPointer) "" },\r
914     { "searchDepth", "searchDepth", XtRInt, sizeof(int),\r
915         XtOffset(AppDataPtr, searchDepth), XtRImmediate, \r
916         (XtPointer) 0 },\r
917     { "showCoords", "showCoords", XtRBoolean, sizeof(Boolean),\r
918         XtOffset(AppDataPtr, showCoords), XtRImmediate,\r
919         (XtPointer) False },\r
920     { "showJail", "showJail", XtRInt, sizeof(int),\r
921         XtOffset(AppDataPtr, showJail), XtRImmediate,\r
922         (XtPointer) 0 },\r
923     { "showThinking", "showThinking", XtRBoolean, sizeof(Boolean),\r
924         XtOffset(AppDataPtr, showThinking), XtRImmediate,\r
925         (XtPointer) True },\r
926     { "ponderNextMove", "ponderNextMove", XtRBoolean, sizeof(Boolean),\r
927         XtOffset(AppDataPtr, ponderNextMove), XtRImmediate,\r
928         (XtPointer) True },\r
929     { "periodicUpdates", "periodicUpdates", XtRBoolean, sizeof(Boolean),\r
930         XtOffset(AppDataPtr, periodicUpdates), XtRImmediate,\r
931         (XtPointer) True },\r
932     { "clockFont", "clockFont", XtRString, sizeof(String),\r
933         XtOffset(AppDataPtr, clockFont), XtRString, CLOCK_FONT },\r
934     { "coordFont", "coordFont", XtRString, sizeof(String),\r
935         XtOffset(AppDataPtr, coordFont), XtRString, COORD_FONT },\r
936     { "font", "font", XtRString, sizeof(String),\r
937         XtOffset(AppDataPtr, font), XtRString, DEFAULT_FONT },\r
938     { "ringBellAfterMoves", "ringBellAfterMoves",\r
939         XtRBoolean, sizeof(Boolean),\r
940         XtOffset(AppDataPtr, ringBellAfterMoves),\r
941         XtRImmediate, (XtPointer) False },\r
942     { "autoCallFlag", "autoCallFlag", XtRBoolean,\r
943         sizeof(Boolean), XtOffset(AppDataPtr, autoCallFlag),\r
944         XtRImmediate, (XtPointer) False },\r
945     { "autoFlipView", "autoFlipView", XtRBoolean,\r
946         sizeof(Boolean), XtOffset(AppDataPtr, autoFlipView),\r
947         XtRImmediate, (XtPointer) True },\r
948     { "autoObserve", "autoObserve", XtRBoolean,\r
949         sizeof(Boolean), XtOffset(AppDataPtr, autoObserve),\r
950         XtRImmediate, (XtPointer) False },\r
951     { "autoComment", "autoComment", XtRBoolean,\r
952         sizeof(Boolean), XtOffset(AppDataPtr, autoComment),\r
953         XtRImmediate, (XtPointer) False },\r
954     { "getMoveList", "getMoveList", XtRBoolean,\r
955         sizeof(Boolean), XtOffset(AppDataPtr, getMoveList),\r
956         XtRImmediate, (XtPointer) True },\r
957 #if HIGHDRAG\r
958     { "highlightDragging", "highlightDragging", XtRBoolean,\r
959         sizeof(Boolean), XtOffset(AppDataPtr, highlightDragging),\r
960         XtRImmediate, (XtPointer) False },\r
961 #endif\r
962     { "highlightLastMove", "highlightLastMove", XtRBoolean,\r
963         sizeof(Boolean), XtOffset(AppDataPtr, highlightLastMove),\r
964         XtRImmediate, (XtPointer) False },\r
965     { "premove", "premove", XtRBoolean,\r
966         sizeof(Boolean), XtOffset(AppDataPtr, premove),\r
967         XtRImmediate, (XtPointer) True },\r
968     { "testLegality", "testLegality", XtRBoolean,\r
969         sizeof(Boolean), XtOffset(AppDataPtr, testLegality),\r
970         XtRImmediate, (XtPointer) True },\r
971     { "flipView", "flipView", XtRBoolean,\r
972         sizeof(Boolean), XtOffset(AppDataPtr, flipView),\r
973         XtRImmediate, (XtPointer) False },\r
974     { "cmail", "cmailGameName", XtRString, sizeof(String),\r
975         XtOffset(AppDataPtr, cmailGameName), XtRString, "" },\r
976     { "alwaysPromoteToQueen", "alwaysPromoteToQueen", XtRBoolean,\r
977         sizeof(Boolean), XtOffset(AppDataPtr, alwaysPromoteToQueen),\r
978         XtRImmediate, (XtPointer) False },\r
979     { "oldSaveStyle", "oldSaveStyle", XtRBoolean,\r
980         sizeof(Boolean), XtOffset(AppDataPtr, oldSaveStyle),\r
981         XtRImmediate, (XtPointer) False },\r
982     { "quietPlay", "quietPlay", XtRBoolean,\r
983         sizeof(Boolean), XtOffset(AppDataPtr, quietPlay),\r
984         XtRImmediate, (XtPointer) False },\r
985     { "titleInWindow", "titleInWindow", XtRBoolean,\r
986         sizeof(Boolean), XtOffset(AppDataPtr, titleInWindow),\r
987         XtRImmediate, (XtPointer) False },\r
988     { "localLineEditing", "localLineEditing", XtRBoolean,\r
989         sizeof(Boolean), XtOffset(AppDataPtr, localLineEditing),\r
990         XtRImmediate, (XtPointer) True }, /* not implemented, must be True */\r
991 #ifdef ZIPPY\r
992     { "zippyTalk", "zippyTalk", XtRBoolean,\r
993         sizeof(Boolean), XtOffset(AppDataPtr, zippyTalk),\r
994         XtRImmediate, (XtPointer) ZIPPY_TALK },\r
995     { "zippyPlay", "zippyPlay", XtRBoolean,\r
996         sizeof(Boolean), XtOffset(AppDataPtr, zippyPlay),\r
997         XtRImmediate, (XtPointer) ZIPPY_PLAY },\r
998     { "zippyLines", "zippyLines", XtRString, sizeof(String),\r
999         XtOffset(AppDataPtr, zippyLines), XtRString, ZIPPY_LINES },\r
1000     { "zippyPinhead", "zippyPinhead", XtRString, sizeof(String),\r
1001         XtOffset(AppDataPtr, zippyPinhead), XtRString, ZIPPY_PINHEAD },\r
1002     { "zippyPassword", "zippyPassword", XtRString, sizeof(String),\r
1003         XtOffset(AppDataPtr, zippyPassword), XtRString, ZIPPY_PASSWORD },\r
1004     { "zippyPassword2", "zippyPassword2", XtRString, sizeof(String),\r
1005         XtOffset(AppDataPtr, zippyPassword2), XtRString, ZIPPY_PASSWORD2 },\r
1006     { "zippyWrongPassword", "zippyWrongPassword", XtRString, sizeof(String),\r
1007         XtOffset(AppDataPtr, zippyWrongPassword), XtRString,\r
1008         ZIPPY_WRONG_PASSWORD },\r
1009     { "zippyAcceptOnly", "zippyAcceptOnly", XtRString, sizeof(String),\r
1010         XtOffset(AppDataPtr, zippyAcceptOnly), XtRString, ZIPPY_ACCEPT_ONLY },\r
1011     { "zippyUseI", "zippyUseI", XtRBoolean,\r
1012         sizeof(Boolean), XtOffset(AppDataPtr, zippyUseI),\r
1013         XtRImmediate, (XtPointer) ZIPPY_USE_I },\r
1014     { "zippyBughouse", "zippyBughouse", XtRInt,\r
1015         sizeof(int), XtOffset(AppDataPtr, zippyBughouse),\r
1016         XtRImmediate, (XtPointer) ZIPPY_BUGHOUSE },\r
1017     { "zippyNoplayCrafty", "zippyNoplayCrafty", XtRBoolean,\r
1018         sizeof(Boolean), XtOffset(AppDataPtr, zippyNoplayCrafty),\r
1019         XtRImmediate, (XtPointer) ZIPPY_NOPLAY_CRAFTY },\r
1020     { "zippyGameEnd", "zippyGameEnd", XtRString, sizeof(String),\r
1021         XtOffset(AppDataPtr, zippyGameEnd), XtRString, ZIPPY_GAME_END },\r
1022     { "zippyGameStart", "zippyGameStart", XtRString, sizeof(String),\r
1023         XtOffset(AppDataPtr, zippyGameStart), XtRString, ZIPPY_GAME_START },\r
1024     { "zippyAdjourn", "zippyAdjourn", XtRBoolean,\r
1025         sizeof(Boolean), XtOffset(AppDataPtr, zippyAdjourn),\r
1026         XtRImmediate, (XtPointer) ZIPPY_ADJOURN },\r
1027     { "zippyAbort", "zippyAbort", XtRBoolean,\r
1028         sizeof(Boolean), XtOffset(AppDataPtr, zippyAbort),\r
1029         XtRImmediate, (XtPointer) ZIPPY_ABORT },\r
1030     { "zippyVariants", "zippyVariants", XtRString, sizeof(String),\r
1031         XtOffset(AppDataPtr, zippyVariants), XtRString, ZIPPY_VARIANTS },\r
1032     { "zippyMaxGames", "zippyMaxGames", XtRInt, sizeof(int),\r
1033         XtOffset(AppDataPtr, zippyMaxGames), XtRImmediate,\r
1034         (XtPointer) ZIPPY_MAX_GAMES },\r
1035     { "zippyReplayTimeout", "zippyReplayTimeout", XtRInt, sizeof(int),\r
1036         XtOffset(AppDataPtr, zippyReplayTimeout), XtRImmediate,\r
1037         (XtPointer) ZIPPY_REPLAY_TIMEOUT },\r
1038 #endif\r
1039     { "flashCount", "flashCount", XtRInt, sizeof(int),\r
1040         XtOffset(AppDataPtr, flashCount), XtRImmediate,\r
1041         (XtPointer) FLASH_COUNT  },\r
1042     { "flashRate", "flashRate", XtRInt, sizeof(int),\r
1043         XtOffset(AppDataPtr, flashRate), XtRImmediate,\r
1044         (XtPointer) FLASH_RATE },\r
1045     { "pixmapDirectory", "pixmapDirectory", XtRString,\r
1046         sizeof(String), XtOffset(AppDataPtr, pixmapDirectory),\r
1047         XtRString, "" },\r
1048     { "msLoginDelay", "msLoginDelay", XtRInt, sizeof(int),\r
1049         XtOffset(AppDataPtr, msLoginDelay), XtRImmediate,\r
1050         (XtPointer) MS_LOGIN_DELAY },\r
1051     { "colorizeMessages", "colorizeMessages", XtRBoolean,\r
1052         sizeof(Boolean), XtOffset(AppDataPtr, colorize),\r
1053         XtRImmediate, (XtPointer) False },      \r
1054     { "colorShout", "colorShout", XtRString,\r
1055         sizeof(String), XtOffset(AppDataPtr, colorShout),\r
1056         XtRString, COLOR_SHOUT },\r
1057     { "colorSShout", "colorSShout", XtRString,\r
1058         sizeof(String), XtOffset(AppDataPtr, colorSShout),\r
1059         XtRString, COLOR_SSHOUT },\r
1060     { "colorChannel1", "colorChannel1", XtRString,\r
1061         sizeof(String), XtOffset(AppDataPtr, colorChannel1),\r
1062         XtRString, COLOR_CHANNEL1 },\r
1063     { "colorChannel", "colorChannel", XtRString,\r
1064         sizeof(String), XtOffset(AppDataPtr, colorChannel),\r
1065         XtRString, COLOR_CHANNEL },\r
1066     { "colorKibitz", "colorKibitz", XtRString,\r
1067         sizeof(String), XtOffset(AppDataPtr, colorKibitz),\r
1068         XtRString, COLOR_KIBITZ },\r
1069     { "colorTell", "colorTell", XtRString,\r
1070         sizeof(String), XtOffset(AppDataPtr, colorTell),\r
1071         XtRString, COLOR_TELL },\r
1072     { "colorChallenge", "colorChallenge", XtRString,\r
1073         sizeof(String), XtOffset(AppDataPtr, colorChallenge),\r
1074         XtRString, COLOR_CHALLENGE },\r
1075     { "colorRequest", "colorRequest", XtRString,\r
1076         sizeof(String), XtOffset(AppDataPtr, colorRequest),\r
1077         XtRString, COLOR_REQUEST },\r
1078     { "colorSeek", "colorSeek", XtRString,\r
1079         sizeof(String), XtOffset(AppDataPtr, colorSeek),\r
1080         XtRString, COLOR_SEEK },\r
1081     { "colorNormal", "colorNormal", XtRString,\r
1082         sizeof(String), XtOffset(AppDataPtr, colorNormal),\r
1083         XtRString, COLOR_NORMAL },      \r
1084     { "soundProgram", "soundProgram", XtRString,\r
1085       sizeof(String), XtOffset(AppDataPtr, soundProgram),\r
1086       XtRString, "play" },\r
1087     { "soundShout", "soundShout", XtRString,\r
1088       sizeof(String), XtOffset(AppDataPtr, soundShout),\r
1089       XtRString, "" },\r
1090     { "soundSShout", "soundSShout", XtRString,\r
1091       sizeof(String), XtOffset(AppDataPtr, soundSShout),\r
1092       XtRString, "" },\r
1093     { "soundChannel1", "soundChannel1", XtRString,\r
1094       sizeof(String), XtOffset(AppDataPtr, soundChannel1),\r
1095       XtRString, "" },\r
1096     { "soundChannel", "soundChannel", XtRString,\r
1097       sizeof(String), XtOffset(AppDataPtr, soundChannel),\r
1098       XtRString, "" },\r
1099     { "soundKibitz", "soundKibitz", XtRString,\r
1100       sizeof(String), XtOffset(AppDataPtr, soundKibitz),\r
1101       XtRString, "" },\r
1102     { "soundTell", "soundTell", XtRString,\r
1103       sizeof(String), XtOffset(AppDataPtr, soundTell),\r
1104       XtRString, "" },\r
1105     { "soundChallenge", "soundChallenge", XtRString,\r
1106       sizeof(String), XtOffset(AppDataPtr, soundChallenge),\r
1107       XtRString, "" },\r
1108     { "soundRequest", "soundRequest", XtRString,\r
1109       sizeof(String), XtOffset(AppDataPtr, soundRequest),\r
1110       XtRString, "" },\r
1111     { "soundSeek", "soundSeek", XtRString,\r
1112       sizeof(String), XtOffset(AppDataPtr, soundSeek),\r
1113       XtRString, "" },\r
1114     { "soundMove", "soundMove", XtRString,\r
1115       sizeof(String), XtOffset(AppDataPtr, soundMove),\r
1116       XtRString, "$" },\r
1117     { "soundIcsWin", "soundIcsWin", XtRString,\r
1118       sizeof(String), XtOffset(AppDataPtr, soundIcsWin),\r
1119       XtRString, "" },\r
1120     { "soundIcsLoss", "soundIcsLoss", XtRString,\r
1121       sizeof(String), XtOffset(AppDataPtr, soundIcsLoss),\r
1122       XtRString, "" },\r
1123     { "soundIcsDraw", "soundIcsDraw", XtRString,\r
1124       sizeof(String), XtOffset(AppDataPtr, soundIcsDraw),\r
1125       XtRString, "" },\r
1126     { "soundIcsUnfinished", "soundIcsUnfinished", XtRString,\r
1127       sizeof(String), XtOffset(AppDataPtr, soundIcsUnfinished),\r
1128       XtRString, "" },\r
1129     { "soundIcsAlarm", "soundIcsAlarm", XtRString,\r
1130       sizeof(String), XtOffset(AppDataPtr, soundIcsAlarm),\r
1131       XtRString, "$" },\r
1132     { "reuseFirst", "reuseFirst", XtRBoolean,\r
1133         sizeof(Boolean), XtOffset(AppDataPtr, reuseFirst),\r
1134         XtRImmediate, (XtPointer) True },\r
1135     { "reuseSecond", "reuseSecond", XtRBoolean,\r
1136         sizeof(Boolean), XtOffset(AppDataPtr, reuseSecond),\r
1137         XtRImmediate, (XtPointer) True },\r
1138     { "animateDragging", "animateDragging", XtRBoolean,\r
1139         sizeof(Boolean), XtOffset(AppDataPtr, animateDragging),\r
1140         XtRImmediate, (XtPointer) True },\r
1141     { "animateMoving", "animateMoving", XtRBoolean,\r
1142         sizeof(Boolean), XtOffset(AppDataPtr, animate),\r
1143         XtRImmediate, (XtPointer) True },\r
1144     { "animateSpeed", "animateSpeed", XtRInt,\r
1145         sizeof(int), XtOffset(AppDataPtr, animSpeed),\r
1146         XtRImmediate, (XtPointer)10 },\r
1147     { "popupExitMessage", "popupExitMessage", XtRBoolean,\r
1148         sizeof(Boolean), XtOffset(AppDataPtr, popupExitMessage),\r
1149         XtRImmediate, (XtPointer) True },\r
1150     { "popupMoveErrors", "popupMoveErrors", XtRBoolean,\r
1151         sizeof(Boolean), XtOffset(AppDataPtr, popupMoveErrors),\r
1152         XtRImmediate, (XtPointer) False },\r
1153     { "fontSizeTolerance", "fontSizeTolerance", XtRInt,\r
1154         sizeof(int), XtOffset(AppDataPtr, fontSizeTolerance),\r
1155         XtRImmediate, (XtPointer)4 },\r
1156     { "initialMode", "initialMode", XtRString,\r
1157         sizeof(String), XtOffset(AppDataPtr, initialMode),\r
1158         XtRImmediate, (XtPointer) "" },\r
1159     { "variant", "variant", XtRString,\r
1160         sizeof(String), XtOffset(AppDataPtr, variant),\r
1161         XtRImmediate, (XtPointer) "normal" },\r
1162     { "firstProtocolVersion", "firstProtocolVersion", XtRInt,\r
1163         sizeof(int), XtOffset(AppDataPtr, firstProtocolVersion),\r
1164         XtRImmediate, (XtPointer)PROTOVER },\r
1165     { "secondProtocolVersion", "secondProtocolVersion", XtRInt,\r
1166         sizeof(int), XtOffset(AppDataPtr, secondProtocolVersion),\r
1167         XtRImmediate, (XtPointer)PROTOVER },\r
1168     { "showButtonBar", "showButtonBar", XtRBoolean,\r
1169         sizeof(Boolean), XtOffset(AppDataPtr, showButtonBar),\r
1170         XtRImmediate, (XtPointer) True },\r
1171     { "firstScoreAbs", "firstScoreAbs", XtRBoolean,\r
1172         sizeof(Boolean), XtOffset(AppDataPtr, firstScoreIsAbsolute),\r
1173         XtRImmediate, (XtPointer) False },\r
1174     { "secondScoreAbs", "secondScoreAbs", XtRBoolean,\r
1175         sizeof(Boolean), XtOffset(AppDataPtr, secondScoreIsAbsolute),\r
1176         XtRImmediate, (XtPointer) False },\r
1177     { "pgnExtendedInfo", "pgnExtendedInfo", XtRBoolean,\r
1178         sizeof(Boolean), XtOffset(AppDataPtr, saveExtendedInfoInPGN),\r
1179         XtRImmediate, (XtPointer) False },\r
1180     { "hideThinkingFromHuman", "hideThinkingFromHuman", XtRBoolean,\r
1181         sizeof(Boolean), XtOffset(AppDataPtr, hideThinkingFromHuman),\r
1182         XtRImmediate, (XtPointer) True },\r
1183     { "adjudicateLossThreshold", "adjudicateLossThreshold", XtRInt,\r
1184         sizeof(int), XtOffset(AppDataPtr, adjudicateLossThreshold),\r
1185         XtRImmediate, (XtPointer) 0},\r
1186     { "pgnEventHeader", "pgnEventHeader", XtRString,\r
1187         sizeof(String), XtOffset(AppDataPtr, pgnEventHeader),\r
1188         XtRImmediate, (XtPointer) "Computer Chess Game" },    \r
1189     { "defaultFrcPosition", "defaultFrcPositon", XtRInt,\r
1190         sizeof(int), XtOffset(AppDataPtr, defaultFrcPosition),\r
1191         XtRImmediate, (XtPointer) -1},\r
1192 \r
1193     // [HGM] 4.3.xx options\r
1194     { "boardWidth", "boardWidth", XtRInt,\r
1195         sizeof(int), XtOffset(AppDataPtr, NrFiles),\r
1196         XtRImmediate, (XtPointer) -1},\r
1197     { "boardHeight", "boardHeight", XtRInt,\r
1198         sizeof(int), XtOffset(AppDataPtr, NrRanks),\r
1199         XtRImmediate, (XtPointer) -1},\r
1200     { "matchPause", "matchPause", XtRInt,\r
1201         sizeof(int), XtOffset(AppDataPtr, matchPause),\r
1202         XtRImmediate, (XtPointer) 10000},\r
1203     { "holdingsSize", "holdingsSize", XtRInt,\r
1204         sizeof(int), XtOffset(AppDataPtr, holdingsSize),\r
1205         XtRImmediate, (XtPointer) -1},\r
1206     { "flipBlack", "flipBlack", XtRBoolean,\r
1207         sizeof(Boolean), XtOffset(AppDataPtr, upsideDown),\r
1208         XtRImmediate, (XtPointer) False},\r
1209     { "allWhite", "allWhite", XtRBoolean,\r
1210         sizeof(Boolean), XtOffset(AppDataPtr, allWhite),\r
1211         XtRImmediate, (XtPointer) False},\r
1212     { "pieceToCharTable", "pieceToCharTable", XtRString,\r
1213         sizeof(String), XtOffset(AppDataPtr, pieceToCharTable),\r
1214         XtRImmediate, (XtPointer) 0},\r
1215     { "alphaRank", "alphaRank", XtRBoolean,\r
1216         sizeof(Boolean), XtOffset(AppDataPtr, alphaRank),\r
1217         XtRImmediate, (XtPointer) False},\r
1218     { "testClaims", "testClaims", XtRBoolean,\r
1219         sizeof(Boolean), XtOffset(AppDataPtr, testClaims),\r
1220         XtRImmediate, (XtPointer) True},\r
1221     { "checkMates", "checkMates", XtRBoolean,\r
1222         sizeof(Boolean), XtOffset(AppDataPtr, checkMates),\r
1223         XtRImmediate, (XtPointer) True},\r
1224     { "materialDraws", "materialDraws", XtRBoolean,\r
1225         sizeof(Boolean), XtOffset(AppDataPtr, materialDraws),\r
1226         XtRImmediate, (XtPointer) True},\r
1227     { "trivialDraws", "trivialDraws", XtRBoolean,\r
1228         sizeof(Boolean), XtOffset(AppDataPtr, trivialDraws),\r
1229         XtRImmediate, (XtPointer) False},\r
1230     { "ruleMoves", "ruleMoves", XtRInt,\r
1231         sizeof(int), XtOffset(AppDataPtr, ruleMoves),\r
1232         XtRImmediate, (XtPointer) 51},\r
1233     { "repeatsToDraw", "repeatsToDraw", XtRInt,\r
1234         sizeof(int), XtOffset(AppDataPtr, drawRepeats),\r
1235         XtRImmediate, (XtPointer) 6},\r
1236     { "engineDebugOutput", "engineDebugOutput", XtRInt,\r
1237         sizeof(int), XtOffset(AppDataPtr, engineComments),\r
1238         XtRImmediate, (XtPointer) 1},\r
1239     { "userName", "userName", XtRString,\r
1240         sizeof(int), XtOffset(AppDataPtr, userName),\r
1241         XtRImmediate, (XtPointer) 0},\r
1242     { "autoKibitz", "autoKibitz", XtRBoolean,\r
1243         sizeof(Boolean), XtOffset(AppDataPtr, autoKibitz),\r
1244         XtRImmediate, (XtPointer) False},\r
1245     { "firstTimeOdds", "firstTimeOdds", XtRInt,\r
1246         sizeof(int), XtOffset(AppDataPtr, firstTimeOdds),\r
1247         XtRImmediate, (XtPointer) 1},\r
1248     { "secondTimeOdds", "secondTimeOdds", XtRInt,\r
1249         sizeof(int), XtOffset(AppDataPtr, secondTimeOdds),\r
1250         XtRImmediate, (XtPointer) 1},\r
1251     { "timeOddsMode", "timeOddsMode", XtRInt,\r
1252         sizeof(int), XtOffset(AppDataPtr, timeOddsMode),\r
1253         XtRImmediate, (XtPointer) 0},\r
1254     { "firstAccumulateTC", "firstAccumulateTC", XtRInt,\r
1255         sizeof(int), XtOffset(AppDataPtr, firstAccumulateTC),\r
1256         XtRImmediate, (XtPointer) 1},\r
1257     { "secondAccumulateTC", "secondAccumulateTC", XtRInt,\r
1258         sizeof(int), XtOffset(AppDataPtr, secondAccumulateTC),\r
1259         XtRImmediate, (XtPointer) 1},\r
1260     { "firstNPS", "firstNPS", XtRInt,\r
1261         sizeof(int), XtOffset(AppDataPtr, firstNPS),\r
1262         XtRImmediate, (XtPointer) -1},\r
1263     { "secondNPS", "secondNPS", XtRInt,\r
1264         sizeof(int), XtOffset(AppDataPtr, secondNPS),\r
1265         XtRImmediate, (XtPointer) -1},\r
1266     { "serverMoves", "serverMoves", XtRString,\r
1267         sizeof(String), XtOffset(AppDataPtr, serverMovesName),\r
1268         XtRImmediate, (XtPointer) 0},\r
1269     { "serverPause", "serverPause", XtRInt,\r
1270         sizeof(int), XtOffset(AppDataPtr, serverPause),\r
1271         XtRImmediate, (XtPointer) 0},\r
1272     { "suppressLoadMoves", "suppressLoadMoves", XtRBoolean,\r
1273         sizeof(Boolean), XtOffset(AppDataPtr, suppressLoadMoves),\r
1274         XtRImmediate, (XtPointer) False},
1275     { "userName", "userName", XtRString,\r
1276         sizeof(String), XtOffset(AppDataPtr, userName),\r
1277         XtRImmediate, (XtPointer) 0},\r
1278     { "egtFormats", "egtFormats", XtRString,\r
1279         sizeof(String), XtOffset(AppDataPtr, egtFormats),\r
1280         XtRImmediate, (XtPointer) 0},\r
1281     { "rewindIndex", "rewindIndex", XtRInt,\r
1282         sizeof(int), XtOffset(AppDataPtr, rewindIndex),\r
1283         XtRImmediate, (XtPointer) 0},\r
1284     { "sameColorGames", "sameColorGames", XtRInt,\r
1285         sizeof(int), XtOffset(AppDataPtr, sameColorGames),\r
1286         XtRImmediate, (XtPointer) 0},\r
1287     { "smpCores", "smpCores", XtRInt,\r
1288         sizeof(int), XtOffset(AppDataPtr, smpCores),\r
1289         XtRImmediate, (XtPointer) 1},\r
1290
1291     // [HGM] Winboard_x UCI options\r
1292     { "firstIsUCI", "firstIsUCI", XtRBoolean,\r
1293         sizeof(Boolean), XtOffset(AppDataPtr, firstIsUCI),\r
1294         XtRImmediate, (XtPointer) False},\r
1295     { "secondIsUCI", "secondIsUCI", XtRBoolean,\r
1296         sizeof(Boolean), XtOffset(AppDataPtr, secondIsUCI),\r
1297         XtRImmediate, (XtPointer) False},\r
1298     { "firstHasOwnBookUCI", "firstHasOwnBookUCI", XtRBoolean,\r
1299         sizeof(Boolean), XtOffset(AppDataPtr, firstHasOwnBookUCI),\r
1300         XtRImmediate, (XtPointer) True},\r
1301     { "secondHasOwnBookUCI", "secondHasOwnBookUCI", XtRBoolean,\r
1302         sizeof(Boolean), XtOffset(AppDataPtr, secondHasOwnBookUCI),\r
1303         XtRImmediate, (XtPointer) True},\r
1304     { "usePolyglotBook", "usePolyglotBook", XtRBoolean,\r
1305         sizeof(Boolean), XtOffset(AppDataPtr, usePolyglotBook),\r
1306         XtRImmediate, (XtPointer) False},\r
1307     { "defaultHashSize", "defaultHashSize", XtRInt,\r
1308         sizeof(int), XtOffset(AppDataPtr, defaultHashSize),\r
1309         XtRImmediate, (XtPointer) 64},\r
1310     { "defaultCacheSizeEGTB", "defaultCacheSizeEGTB", XtRInt,\r
1311         sizeof(int), XtOffset(AppDataPtr, defaultCacheSizeEGTB),\r
1312         XtRImmediate, (XtPointer) 4},\r
1313     { "polyglotDir", "polyglotDir", XtRString,\r
1314         sizeof(String), XtOffset(AppDataPtr, polyglotDir),\r
1315         XtRImmediate, (XtPointer) "." },\r
1316     { "polyglotBook", "polyglotBook", XtRString,\r
1317         sizeof(String), XtOffset(AppDataPtr, polyglotBook),\r
1318         XtRImmediate, (XtPointer) "" },    \r
1319     { "defaultPathEGTB", "defaultPathEGTB", XtRString,\r
1320         sizeof(String), XtOffset(AppDataPtr, defaultPathEGTB),\r
1321         XtRImmediate, (XtPointer) "/usr/local/share/egtb"},\r
1322 };\r
1323 \r
1324 XrmOptionDescRec shellOptions[] = {\r
1325     { "-whitePieceColor", "whitePieceColor", XrmoptionSepArg, NULL },\r
1326     { "-blackPieceColor", "blackPieceColor", XrmoptionSepArg, NULL },\r
1327     { "-lightSquareColor", "lightSquareColor", XrmoptionSepArg, NULL },\r
1328     { "-darkSquareColor", "darkSquareColor", XrmoptionSepArg, NULL },\r
1329     { "-highlightSquareColor", "highlightSquareColor", XrmoptionSepArg, NULL },\r
1330     { "-premoveHighlightColor", "premoveHighlightColor", XrmoptionSepArg,NULL},\r
1331     { "-movesPerSession", "movesPerSession", XrmoptionSepArg, NULL },\r
1332     { "-mps", "movesPerSession", XrmoptionSepArg, NULL },\r
1333     { "-timeIncrement", "timeIncrement", XrmoptionSepArg, NULL },\r
1334     { "-inc", "timeIncrement", XrmoptionSepArg, NULL },\r
1335     { "-initString", "initString", XrmoptionSepArg, NULL },\r
1336     { "-firstInitString", "initString", XrmoptionSepArg, NULL },\r
1337     { "-secondInitString", "secondInitString", XrmoptionSepArg, NULL },\r
1338     { "-firstComputerString", "firstComputerString", XrmoptionSepArg, NULL },\r
1339     { "-secondComputerString", "secondComputerString", XrmoptionSepArg, NULL },\r
1340     { "-firstChessProgram", "firstChessProgram", XrmoptionSepArg, NULL },\r
1341     { "-fcp", "firstChessProgram", XrmoptionSepArg, NULL },\r
1342     { "-secondChessProgram", "secondChessProgram", XrmoptionSepArg, NULL },\r
1343     { "-scp", "secondChessProgram", XrmoptionSepArg, NULL },\r
1344     { "-firstPlaysBlack", "firstPlaysBlack", XrmoptionSepArg, NULL },\r
1345     { "-fb", "firstPlaysBlack", XrmoptionNoArg, "True" },\r
1346     { "-xfb", "firstPlaysBlack", XrmoptionNoArg, "False" },\r
1347     { "-noChessProgram", "noChessProgram", XrmoptionSepArg, NULL },\r
1348     { "-ncp", "noChessProgram", XrmoptionNoArg, "True" },\r
1349     { "-xncp", "noChessProgram", XrmoptionNoArg, "False" },\r
1350     { "-firstHost", "firstHost", XrmoptionSepArg, NULL },\r
1351     { "-fh", "firstHost", XrmoptionSepArg, NULL },\r
1352     { "-secondHost", "secondHost", XrmoptionSepArg, NULL },\r
1353     { "-sh", "secondHost", XrmoptionSepArg, NULL },\r
1354     { "-firstDirectory", "firstDirectory", XrmoptionSepArg, NULL },\r
1355     { "-fd", "firstDirectory", XrmoptionSepArg, NULL },\r
1356     { "-secondDirectory", "secondDirectory", XrmoptionSepArg, NULL },\r
1357     { "-sd", "secondDirectory", XrmoptionSepArg, NULL },\r
1358     { "-bitmapDirectory", "bitmapDirectory", XrmoptionSepArg, NULL },\r
1359     { "-bm", "bitmapDirectory", XrmoptionSepArg, NULL },\r
1360     { "-remoteShell", "remoteShell", XrmoptionSepArg, NULL },\r
1361     { "-rsh", "remoteShell", XrmoptionSepArg, NULL },\r
1362     { "-remoteUser", "remoteUser", XrmoptionSepArg, NULL },\r
1363     { "-ruser", "remoteUser", XrmoptionSepArg, NULL },\r
1364     { "-timeDelay", "timeDelay", XrmoptionSepArg, NULL },\r
1365     { "-td", "timeDelay", XrmoptionSepArg, NULL },\r
1366     { "-timeControl", "timeControl", XrmoptionSepArg, NULL },\r
1367     { "-tc", "timeControl", XrmoptionSepArg, NULL },\r
1368     { "-internetChessServerMode", "internetChessServerMode",\r
1369         XrmoptionSepArg, NULL },\r
1370     { "-ics", "internetChessServerMode", XrmoptionNoArg, "True" },\r
1371     { "-xics", "internetChessServerMode", XrmoptionNoArg, "False" },\r
1372     { "-internetChessServerHost", "internetChessServerHost",\r
1373         XrmoptionSepArg, NULL },\r
1374     { "-icshost", "internetChessServerHost", XrmoptionSepArg, NULL },\r
1375     { "-internetChessServerPort", "internetChessServerPort",\r
1376         XrmoptionSepArg, NULL },\r
1377     { "-icsport", "internetChessServerPort", XrmoptionSepArg, NULL },\r
1378     { "-internetChessServerCommPort", "internetChessServerCommPort",\r
1379         XrmoptionSepArg, NULL },\r
1380     { "-icscomm", "internetChessServerCommPort", XrmoptionSepArg, NULL },\r
1381     { "-internetChessServerLogonScript", "internetChessServerLogonScript",\r
1382         XrmoptionSepArg, NULL },\r
1383     { "-icslogon", "internetChessServerLogonScript", XrmoptionSepArg, NULL },\r
1384     { "-internetChessServerHelper", "internetChessServerHelper",\r
1385         XrmoptionSepArg, NULL },\r
1386     { "-icshelper", "internetChessServerHelper", XrmoptionSepArg, NULL },\r
1387     { "-internetChessServerInputBox", "internetChessServerInputBox",\r
1388         XrmoptionSepArg, NULL },\r
1389     { "-icsinput", "internetChessServerInputBox", XrmoptionNoArg, "True" },\r
1390     { "-xicsinput", "internetChessServerInputBox", XrmoptionNoArg, "False" },\r
1391     { "-icsAlarm", "icsAlarm", XrmoptionSepArg, NULL },\r
1392     { "-alarm", "icsAlarm", XrmoptionNoArg, "True" },\r
1393     { "-xalarm", "icsAlarm", XrmoptionNoArg, "False" },\r
1394     { "-icsAlarmTime", "icsAlarmTime", XrmoptionSepArg, NULL },\r
1395     { "-useTelnet", "useTelnet", XrmoptionSepArg, NULL },\r
1396     { "-telnet", "useTelnet", XrmoptionNoArg, "True" },\r
1397     { "-xtelnet", "useTelnet", XrmoptionNoArg, "False" },\r
1398     { "-telnetProgram", "telnetProgram", XrmoptionSepArg, NULL },\r
1399     { "-gateway", "gateway", XrmoptionSepArg, NULL },\r
1400     { "-loadGameFile", "loadGameFile", XrmoptionSepArg, NULL },\r
1401     { "-lgf", "loadGameFile", XrmoptionSepArg, NULL },\r
1402     { "-loadGameIndex", "loadGameIndex", XrmoptionSepArg, NULL },\r
1403     { "-lgi", "loadGameIndex", XrmoptionSepArg, NULL },\r
1404     { "-saveGameFile", "saveGameFile", XrmoptionSepArg, NULL },\r
1405     { "-sgf", "saveGameFile", XrmoptionSepArg, NULL },\r
1406     { "-autoSaveGames", "autoSaveGames", XrmoptionSepArg, NULL },\r
1407     { "-autosave", "autoSaveGames", XrmoptionNoArg, "True" },\r
1408     { "-xautosave", "autoSaveGames", XrmoptionNoArg, "False" },\r
1409     { "-autoRaiseBoard", "autoRaiseBoard", XrmoptionSepArg, NULL },\r
1410     { "-autoraise", "autoRaiseBoard", XrmoptionNoArg, "True" },\r
1411     { "-xautoraise", "autoRaiseBoard", XrmoptionNoArg, "False" },\r
1412     { "-blindfold", "blindfold", XrmoptionSepArg, NULL },\r
1413     { "-blind", "blindfold", XrmoptionNoArg, "True" },\r
1414     { "-xblind", "blindfold", XrmoptionNoArg, "False" },\r
1415     { "-loadPositionFile", "loadPositionFile", XrmoptionSepArg, NULL },\r
1416     { "-lpf", "loadPositionFile", XrmoptionSepArg, NULL },\r
1417     { "-loadPositionIndex", "loadPositionIndex", XrmoptionSepArg, NULL },\r
1418     { "-lpi", "loadPositionIndex", XrmoptionSepArg, NULL },\r
1419     { "-savePositionFile", "savePositionFile", XrmoptionSepArg, NULL },\r
1420     { "-spf", "savePositionFile", XrmoptionSepArg, NULL },\r
1421     { "-matchMode", "matchMode", XrmoptionSepArg, NULL },\r
1422     { "-mm", "matchMode", XrmoptionNoArg, "True" },\r
1423     { "-xmm", "matchMode", XrmoptionNoArg, "False" },\r
1424     { "-matchGames", "matchGames", XrmoptionSepArg, NULL },\r
1425     { "-mg", "matchGames", XrmoptionSepArg, NULL },\r
1426     { "-monoMode", "monoMode", XrmoptionSepArg, NULL },\r
1427     { "-mono", "monoMode", XrmoptionNoArg, "True" },\r
1428     { "-xmono", "monoMode", XrmoptionNoArg, "False" },\r
1429     { "-debugMode", "debugMode", XrmoptionSepArg, NULL },\r
1430     { "-debug", "debugMode", XrmoptionNoArg, "True" },\r
1431     { "-xdebug", "debugMode", XrmoptionNoArg, "False" },\r
1432     { "-clockMode", "clockMode", XrmoptionSepArg, NULL },\r
1433     { "-clock", "clockMode", XrmoptionNoArg, "True" },\r
1434     { "-xclock", "clockMode", XrmoptionNoArg, "False" },\r
1435     { "-boardSize", "boardSize", XrmoptionSepArg, NULL },\r
1436     { "-size", "boardSize", XrmoptionSepArg, NULL },\r
1437     { "-searchTime", "searchTime", XrmoptionSepArg, NULL },\r
1438     { "-st", "searchTime", XrmoptionSepArg, NULL },\r
1439     { "-searchDepth", "searchDepth", XrmoptionSepArg, NULL },\r
1440     { "-depth", "searchDepth", XrmoptionSepArg, NULL },\r
1441     { "-showCoords", "showCoords", XrmoptionSepArg, NULL },\r
1442     { "-coords", "showCoords", XrmoptionNoArg, "True" },\r
1443     { "-xcoords", "showCoords", XrmoptionNoArg, "False" },\r
1444 #if JAIL\r
1445     { "-showJail", "showJail", XrmoptionSepArg, NULL },\r
1446     { "-jail", "showJail", XrmoptionNoArg, "1" },\r
1447     { "-sidejail", "showJail", XrmoptionNoArg, "2" },\r
1448     { "-xjail", "showJail", XrmoptionNoArg, "0" },\r
1449 #endif\r
1450     { "-showThinking", "showThinking", XrmoptionSepArg, NULL },\r
1451     { "-thinking", "showThinking", XrmoptionNoArg, "True" },\r
1452     { "-xthinking", "showThinking", XrmoptionNoArg, "False" },\r
1453     { "-ponderNextMove", "ponderNextMove", XrmoptionSepArg, NULL },\r
1454     { "-ponder", "ponderNextMove", XrmoptionNoArg, "True" },\r
1455     { "-xponder", "ponderNextMove", XrmoptionNoArg, "False" },\r
1456     { "-periodicUpdates", "periodicUpdates", XrmoptionSepArg, NULL },\r
1457     { "-periodic", "periodicUpdates", XrmoptionNoArg, "True" },\r
1458     { "-xperiodic", "periodicUpdates", XrmoptionNoArg, "False" },\r
1459     { "-clockFont", "clockFont", XrmoptionSepArg, NULL },\r
1460     { "-coordFont", "coordFont", XrmoptionSepArg, NULL },\r
1461     { "-font", "font", XrmoptionSepArg, NULL },\r
1462     { "-ringBellAfterMoves", "ringBellAfterMoves", XrmoptionSepArg, NULL },\r
1463     { "-bell", "ringBellAfterMoves", XrmoptionNoArg, "True" },\r
1464     { "-xbell", "ringBellAfterMoves", XrmoptionNoArg, "False" },\r
1465     { "-movesound", "ringBellAfterMoves", XrmoptionNoArg, "True" },\r
1466     { "-xmovesound", "ringBellAfterMoves", XrmoptionNoArg, "False" },\r
1467     { "-autoCallFlag", "autoCallFlag", XrmoptionSepArg, NULL },\r
1468     { "-autoflag", "autoCallFlag", XrmoptionNoArg, "True" },\r
1469     { "-xautoflag", "autoCallFlag", XrmoptionNoArg, "False" },\r
1470     { "-autoFlipView", "autoFlipView", XrmoptionSepArg, NULL },\r
1471     { "-autoflip", "autoFlipView", XrmoptionNoArg, "True" },\r
1472     { "-xautoflip", "autoFlipView", XrmoptionNoArg, "False" },\r
1473     { "-autoObserve", "autoObserve", XrmoptionSepArg, NULL },\r
1474     { "-autobs", "autoObserve", XrmoptionNoArg, "True" },\r
1475     { "-xautobs", "autoObserve", XrmoptionNoArg, "False" },\r
1476     { "-autoComment", "autoComment", XrmoptionSepArg, NULL },\r
1477     { "-autocomm", "autoComment", XrmoptionNoArg, "True" },\r
1478     { "-xautocomm", "autoComment", XrmoptionNoArg, "False" },\r
1479     { "-getMoveList", "getMoveList", XrmoptionSepArg, NULL },\r
1480     { "-moves", "getMoveList", XrmoptionNoArg, "True" },\r
1481     { "-xmoves", "getMoveList", XrmoptionNoArg, "False" },\r
1482 #if HIGHDRAG\r
1483     { "-highlightDragging", "highlightDragging", XrmoptionSepArg, NULL },\r
1484     { "-highdrag", "highlightDragging", XrmoptionNoArg, "True" },\r
1485     { "-xhighdrag", "highlightDragging", XrmoptionNoArg, "False" },\r
1486 #endif\r
1487     { "-highlightLastMove", "highlightLastMove", XrmoptionSepArg, NULL },\r
1488     { "-highlight", "highlightLastMove", XrmoptionNoArg, "True" },\r
1489     { "-xhighlight", "highlightLastMove", XrmoptionNoArg, "False" },\r
1490     { "-premove", "premove", XrmoptionSepArg, NULL },\r
1491     { "-pre", "premove", XrmoptionNoArg, "True" },\r
1492     { "-xpre", "premove", XrmoptionNoArg, "False" },\r
1493     { "-testLegality", "testLegality", XrmoptionSepArg, NULL },\r
1494     { "-legal", "testLegality", XrmoptionNoArg, "True" },\r
1495     { "-xlegal", "testLegality", XrmoptionNoArg, "False" },\r
1496     { "-flipView", "flipView", XrmoptionSepArg, NULL },\r
1497     { "-flip", "flipView", XrmoptionNoArg, "True" },\r
1498     { "-xflip", "flipView", XrmoptionNoArg, "False" },\r
1499     { "-cmail", "cmailGameName", XrmoptionSepArg, NULL },\r
1500     { "-alwaysPromoteToQueen", "alwaysPromoteToQueen",\r
1501         XrmoptionSepArg, NULL },\r
1502     { "-queen", "alwaysPromoteToQueen", XrmoptionNoArg, "True" },\r
1503     { "-xqueen", "alwaysPromoteToQueen", XrmoptionNoArg, "False" },\r
1504     { "-oldSaveStyle", "oldSaveStyle", XrmoptionSepArg, NULL },\r
1505     { "-oldsave", "oldSaveStyle", XrmoptionNoArg, "True" },\r
1506     { "-xoldsave", "oldSaveStyle", XrmoptionNoArg, "False" },\r
1507     { "-quietPlay", "quietPlay", XrmoptionSepArg, NULL },\r
1508     { "-quiet", "quietPlay", XrmoptionNoArg, "True" },\r
1509     { "-xquiet", "quietPlay", XrmoptionNoArg, "False" },\r
1510     { "-titleInWindow", "titleInWindow", XrmoptionSepArg, NULL },\r
1511     { "-title", "titleInWindow", XrmoptionNoArg, "True" },\r
1512     { "-xtitle", "titleInWindow", XrmoptionNoArg, "False" },\r
1513 #ifdef ZIPPY\r
1514     { "-zippyTalk", "zippyTalk", XrmoptionSepArg, NULL },\r
1515     { "-zt", "zippyTalk", XrmoptionNoArg, "True" },\r
1516     { "-xzt", "zippyTalk", XrmoptionNoArg, "False" },\r
1517     { "-zippyPlay", "zippyPlay", XrmoptionSepArg, NULL },\r
1518     { "-zp", "zippyPlay", XrmoptionNoArg, "True" },\r
1519     { "-xzp", "zippyPlay", XrmoptionNoArg, "False" },\r
1520     { "-zippyLines", "zippyLines", XrmoptionSepArg, NULL },\r
1521     { "-zippyPinhead", "zippyPinhead", XrmoptionSepArg, NULL },\r
1522     { "-zippyPassword", "zippyPassword", XrmoptionSepArg, NULL },\r
1523     { "-zippyPassword2", "zippyPassword2", XrmoptionSepArg, NULL },\r
1524     { "-zippyWrongPassword", "zippyWrongPassword", XrmoptionSepArg, NULL },\r
1525     { "-zippyAcceptOnly", "zippyAcceptOnly", XrmoptionSepArg, NULL },\r
1526     { "-zippyUseI", "zippyUseI", XrmoptionSepArg, NULL },\r
1527     { "-zui", "zippyUseI", XrmoptionNoArg, "True" },\r
1528     { "-xzui", "zippyUseI", XrmoptionNoArg, "False" },\r
1529     { "-zippyBughouse", "zippyBughouse", XrmoptionSepArg, NULL },\r
1530     { "-zippyNoplayCrafty", "zippyNoplayCrafty", XrmoptionSepArg, NULL },\r
1531     { "-znc", "zippyNoplayCrafty", XrmoptionNoArg, "True" },\r
1532     { "-xznc", "zippyNoplayCrafty", XrmoptionNoArg, "False" },\r
1533     { "-zippyGameEnd", "zippyGameEnd", XrmoptionSepArg, NULL },\r
1534     { "-zippyGameStart", "zippyGameStart", XrmoptionSepArg, NULL },\r
1535     { "-zippyAdjourn", "zippyAdjourn", XrmoptionSepArg, NULL },\r
1536     { "-zadj", "zippyAdjourn", XrmoptionNoArg, "True" },\r
1537     { "-xzadj", "zippyAdjourn", XrmoptionNoArg, "False" },\r
1538     { "-zippyAbort", "zippyAbort", XrmoptionSepArg, NULL },\r
1539     { "-zab", "zippyAbort", XrmoptionNoArg, "True" },\r
1540     { "-xzab", "zippyAbort", XrmoptionNoArg, "False" },\r
1541     { "-zippyVariants", "zippyVariants", XrmoptionSepArg, NULL },\r
1542     { "-zippyMaxGames", "zippyMaxGames", XrmoptionSepArg, NULL },\r
1543     { "-zippyReplayTimeout", "zippyReplayTimeout", XrmoptionSepArg, NULL },\r
1544 #endif\r
1545     { "-flashCount", "flashCount", XrmoptionSepArg, NULL },\r
1546     { "-flash", "flashCount", XrmoptionNoArg, "3" },\r
1547     { "-xflash", "flashCount", XrmoptionNoArg, "0" },\r
1548     { "-flashRate", "flashRate", XrmoptionSepArg, NULL },\r
1549     { "-pixmapDirectory", "pixmapDirectory", XrmoptionSepArg, NULL },\r
1550     { "-msLoginDelay", "msLoginDelay", XrmoptionSepArg, NULL },\r
1551     { "-pixmap", "pixmapDirectory", XrmoptionSepArg, NULL },\r
1552     { "-colorizeMessages", "colorizeMessages", XrmoptionSepArg, NULL },\r
1553     { "-colorize", "colorizeMessages", XrmoptionNoArg, "True" },\r
1554     { "-xcolorize", "colorizeMessages", XrmoptionNoArg, "False" },\r
1555     { "-colorShout", "colorShout", XrmoptionSepArg, NULL },\r
1556     { "-colorSShout", "colorSShout", XrmoptionSepArg, NULL },\r
1557     { "-colorCShout", "colorSShout", XrmoptionSepArg, NULL }, /*FICS name*/\r
1558     { "-colorChannel1", "colorChannel1", XrmoptionSepArg, NULL },\r
1559     { "-colorChannel", "colorChannel", XrmoptionSepArg, NULL },\r
1560     { "-colorKibitz", "colorKibitz", XrmoptionSepArg, NULL },\r
1561     { "-colorTell", "colorTell", XrmoptionSepArg, NULL },\r
1562     { "-colorChallenge", "colorChallenge", XrmoptionSepArg, NULL },\r
1563     { "-colorRequest", "colorRequest", XrmoptionSepArg, NULL },\r
1564     { "-colorSeek", "colorSeek", XrmoptionSepArg, NULL },\r
1565     { "-colorNormal", "colorNormal", XrmoptionSepArg, NULL },\r
1566     { "-soundProgram", "soundProgram", XrmoptionSepArg, NULL },\r
1567     { "-soundShout", "soundShout", XrmoptionSepArg, NULL },\r
1568     { "-soundSShout", "soundSShout", XrmoptionSepArg, NULL },\r
1569     { "-soundCShout", "soundSShout", XrmoptionSepArg, NULL }, /*FICS name*/\r
1570     { "-soundChannel1", "soundChannel1", XrmoptionSepArg, NULL },\r
1571     { "-soundChannel", "soundChannel", XrmoptionSepArg, NULL },\r
1572     { "-soundKibitz", "soundKibitz", XrmoptionSepArg, NULL },\r
1573     { "-soundTell", "soundTell", XrmoptionSepArg, NULL },\r
1574     { "-soundChallenge", "soundChallenge", XrmoptionSepArg, NULL },\r
1575     { "-soundRequest", "soundRequest", XrmoptionSepArg, NULL },\r
1576     { "-soundSeek", "soundSeek", XrmoptionSepArg, NULL },\r
1577     { "-soundMove", "soundMove", XrmoptionSepArg, NULL },\r
1578     { "-soundIcsWin", "soundIcsWin", XrmoptionSepArg, NULL },\r
1579     { "-soundIcsLoss", "soundIcsLoss", XrmoptionSepArg, NULL },\r
1580     { "-soundIcsDraw", "soundIcsDraw", XrmoptionSepArg, NULL },\r
1581     { "-soundIcsUnfinished", "soundIcsUnfinished", XrmoptionSepArg, NULL },\r
1582     { "-soundIcsAlarm", "soundIcsAlarm", XrmoptionSepArg, NULL },\r
1583     { "-reuseFirst", "reuseFirst", XrmoptionSepArg, NULL },\r
1584     { "-reuseChessPrograms", "reuseFirst", XrmoptionSepArg, NULL }, /*compat*/\r
1585     { "-reuse", "reuseFirst", XrmoptionNoArg, "True" },\r
1586     { "-xreuse", "reuseFirst", XrmoptionNoArg, "False" },\r
1587     { "-reuseSecond", "reuseSecond", XrmoptionSepArg, NULL },\r
1588     { "-reuse2", "reuseSecond", XrmoptionNoArg, "True" },\r
1589     { "-xreuse2", "reuseSecond", XrmoptionNoArg, "False" },\r
1590     { "-animateMoving", "animateMoving", XrmoptionSepArg, NULL },\r
1591     { "-animate", "animateMoving", XrmoptionNoArg, "True" },\r
1592     { "-xanimate", "animateMoving", XrmoptionNoArg, "False" },\r
1593     { "-animateDragging", "animateDragging", XrmoptionSepArg, NULL },\r
1594     { "-drag", "animateDragging", XrmoptionNoArg, "True" },\r
1595     { "-xdrag", "animateDragging", XrmoptionNoArg, "False" },\r
1596     { "-animateSpeed", "animateSpeed", XrmoptionSepArg, NULL },\r
1597     { "-popupExitMessage", "popupExitMessage", XrmoptionSepArg, NULL },\r
1598     { "-exit", "popupExitMessage", XrmoptionNoArg, "True" },\r
1599     { "-xexit", "popupExitMessage", XrmoptionNoArg, "False" },\r
1600     { "-popupMoveErrors", "popupMoveErrors", XrmoptionSepArg, NULL },\r
1601     { "-popup", "popupMoveErrors", XrmoptionNoArg, "True" },\r
1602     { "-xpopup", "popupMoveErrors", XrmoptionNoArg, "False" },\r
1603     { "-fontSizeTolerance", "fontSizeTolerance", XrmoptionSepArg, NULL },\r
1604     { "-initialMode", "initialMode", XrmoptionSepArg, NULL },\r
1605     { "-mode", "initialMode", XrmoptionSepArg, NULL },\r
1606     { "-variant", "variant", XrmoptionSepArg, NULL },\r
1607     { "-firstProtocolVersion", "firstProtocolVersion", XrmoptionSepArg, NULL },\r
1608     { "-secondProtocolVersion","secondProtocolVersion",XrmoptionSepArg, NULL },\r
1609     { "-showButtonBar", "showButtonBar", XrmoptionSepArg, NULL },\r
1610     { "-buttons", "showButtonBar", XrmoptionNoArg, "True" },\r
1611     { "-xbuttons", "showButtonBar", XrmoptionNoArg, "False" },\r
1612     /* [AS,HR] New features */\r
1613     { "-firstScoreAbs", "firstScoreAbs", XrmoptionSepArg, NULL },\r
1614     { "-secondScoreAbs", "secondScoreAbs", XrmoptionSepArg, NULL },\r
1615     { "-pgnExtendedInfo", "pgnExtendedInfo", XrmoptionSepArg, NULL },\r
1616     { "-hideThinkingFromHuman", "hideThinkingFromHuman", XrmoptionSepArg, NULL },\r
1617     { "-adjudicateLossThreshold", "adjudicateLossThreshold", XrmoptionSepArg, NULL },\r
1618     { "-pgnEventHeader", "pgnEventHeader", XrmoptionSepArg, NULL },\r
1619     { "-firstIsUCI", "firstIsUCI", XrmoptionSepArg, NULL },\r
1620     { "-secondIsUCI", "secondIsUCI", XrmoptionSepArg, NULL },\r
1621     { "-fUCI", "firstIsUCI", XrmoptionNoArg, "True" },\r
1622     { "-sUCI", "secondIsUCI", XrmoptionNoArg, "True" },\r
1623     { "-firstHasOwnBookUCI", "firstHasOwnBookUCI", XrmoptionSepArg, NULL },\r
1624     { "-secondHasOwnBookUCI", "secondHasOwnBookUCI", XrmoptionSepArg, NULL },\r
1625     { "-fNoOwnBookUCI", "firstHasOwnBookUCI", XrmoptionNoArg, "False" },\r
1626     { "-sNoOwnBookUCI", "secondHasOwnBookUCI", XrmoptionNoArg, "False" },\r
1627     { "-polyglotDir", "polyglotDir", XrmoptionSepArg, NULL },\r
1628     { "-usePolyglotBook", "usePolyglotBook", XrmoptionSepArg, NULL },\r
1629     { "-polyglotBook", "polyglotBook", XrmoptionSepArg, NULL },\r
1630     { "-defaultHashSize", "defaultHashSize", XrmoptionSepArg, NULL },\r
1631     { "-defaultCacheSizeEGTB", "defaultCacheSizeEGTB", XrmoptionSepArg, NULL },\r
1632     { "-defaultPathEGTB", "defaultPathEGTB", XrmoptionSepArg, NULL },\r
1633     { "-defaultFrcPosition", "defaultFrcPosition", XrmoptionSepArg, NULL },\r
1634     // [HGM] I am sure AS added many more options, but we have to fish them out, from the list in winboard.c\r
1635 \r
1636     /* [HGM,HR] User-selectable board size */\r
1637     { "-boardWidth", "boardWidth", XrmoptionSepArg, NULL }, \r
1638     { "-boardHeight", "boardHeight", XrmoptionSepArg, NULL }, \r
1639     { "-matchPause", "matchPause", XrmoptionSepArg, NULL }, \r
1640 \r
1641     /* [HGM] new arguments of 4.3.xx. All except first three are back-end options, which should work immediately */\r
1642     { "-holdingsSize", "holdingsSize", XrmoptionSepArg, NULL }, // requires extensive front-end changes to work\r
1643     { "-flipBlack", "flipBlack", XrmoptionSepArg, NULL },       // requires front-end changes to work\r
1644     { "-allWhite", "allWhite", XrmoptionSepArg, NULL },         // requires front-end changes to work\r
1645     { "-pieceToCharTable", "pieceToCharTable", XrmoptionSepArg, NULL }, \r
1646     { "-alphaRank", "alphaRank", XrmoptionSepArg, NULL }, \r
1647     { "-testClaims", "testClaims", XrmoptionSepArg, NULL }, \r
1648     { "-checkMates", "checkMates", XrmoptionSepArg, NULL }, \r
1649     { "-materialDraws", "materialDraws", XrmoptionSepArg, NULL }, \r
1650     { "-trivialDraws", "trivialDraws", XrmoptionSepArg, NULL }, \r
1651     { "-ruleMoves", "ruleMoves", XrmoptionSepArg, NULL }, \r
1652     { "-repeatsToDraw", "repeatsToDraw", XrmoptionSepArg, NULL },\r
1653     { "-engineDebugOutput", "engineDebugOutput", XrmoptionSepArg, NULL }, \r
1654     { "-userName", "userName", XrmoptionSepArg, NULL }, \r
1655     { "-autoKibitz", "autoKibitz", XrmoptionNoArg, "True" }, \r
1656     { "-firstTimeOdds", "firstTimeOdds", XrmoptionSepArg, NULL }, \r
1657     { "-secondTimeOdds", "secondTimeOdds", XrmoptionSepArg, NULL }, \r
1658     { "-timeOddsMode", "timeOddsMode", XrmoptionSepArg, NULL }, \r
1659     { "-firstAccumulateTC", "firstAccumulateTC", XrmoptionSepArg, NULL }, \r
1660     { "-secondAccumulateTC", "secondAccumulateTC", XrmoptionSepArg, NULL }, \r
1661     { "-firstNPS", "firstNPS", XrmoptionSepArg, NULL }, \r
1662     { "-secondNPS", "secondNPS", XrmoptionSepArg, NULL }, \r
1663     { "-serverMoves", "serverMoves", XrmoptionSepArg, NULL }, \r
1664     { "-serverPause", "serverPause", XrmoptionSepArg, NULL }, \r
1665     { "-suppressLoadMoves", "suppressLoadMoves", XrmoptionSepArg, NULL }, \r
1666     { "-egtFormats", "egtFormats", XrmoptionSepArg, NULL }, \r
1667     { "-userName", "userName", XrmoptionSepArg, NULL }, \r
1668     { "-smpCores", "smpCores", XrmoptionSepArg, NULL }, \r
1669     { "-sameColorGames", "sameColorGames", XrmoptionSepArg, NULL }, \r
1670     { "-rewindIndex", "rewindIndex", XrmoptionSepArg, NULL }, \r
1671 };\r
1672 \r
1673 \r
1674 XtActionsRec boardActions[] = {\r
1675     { "DrawPosition", DrawPositionProc },\r
1676     { "HandleUserMove", HandleUserMove },\r
1677     { "AnimateUserMove", AnimateUserMove },\r
1678     { "FileNameAction", FileNameAction },\r
1679     { "AskQuestionProc", AskQuestionProc },\r
1680     { "AskQuestionReplyAction", AskQuestionReplyAction },\r
1681     { "PieceMenuPopup", PieceMenuPopup },\r
1682     { "WhiteClock", WhiteClock },\r
1683     { "BlackClock", BlackClock },\r
1684     { "Iconify", Iconify },\r
1685     { "ResetProc", ResetProc },\r
1686     { "LoadGameProc", LoadGameProc },\r
1687     { "LoadNextGameProc", LoadNextGameProc },\r
1688     { "LoadPrevGameProc", LoadPrevGameProc },\r
1689     { "LoadSelectedProc", LoadSelectedProc },\r
1690     { "ReloadGameProc", ReloadGameProc },\r
1691     { "LoadPositionProc", LoadPositionProc },\r
1692     { "LoadNextPositionProc", LoadNextPositionProc },\r
1693     { "LoadPrevPositionProc", LoadPrevPositionProc },\r
1694     { "ReloadPositionProc", ReloadPositionProc },\r
1695     { "CopyPositionProc", CopyPositionProc },\r
1696     { "PastePositionProc", PastePositionProc },\r
1697     { "CopyGameProc", CopyGameProc },\r
1698     { "PasteGameProc", PasteGameProc },\r
1699     { "SaveGameProc", SaveGameProc },\r
1700     { "SavePositionProc", SavePositionProc },\r
1701     { "MailMoveProc", MailMoveProc },\r
1702     { "ReloadCmailMsgProc", ReloadCmailMsgProc },\r
1703     { "QuitProc", QuitProc },\r
1704     { "MachineWhiteProc", MachineWhiteProc },\r
1705     { "MachineBlackProc", MachineBlackProc },\r
1706     { "AnalysisModeProc", AnalyzeModeProc },\r
1707     { "AnalyzeFileProc", AnalyzeFileProc },\r
1708     { "TwoMachinesProc", TwoMachinesProc },\r
1709     { "IcsClientProc", IcsClientProc },\r
1710     { "EditGameProc", EditGameProc },\r
1711     { "EditPositionProc", EditPositionProc },\r
1712     { "TrainingProc", EditPositionProc },\r
1713     { "EngineOutputProc", EngineOutputProc}, // [HGM] Winboard_x engine-output window\r
1714     { "ShowGameListProc", ShowGameListProc },\r
1715     { "ShowMoveListProc", HistoryShowProc},\r
1716     { "EditTagsProc", EditCommentProc },\r
1717     { "EditCommentProc", EditCommentProc },\r
1718     { "IcsAlarmProc", IcsAlarmProc },\r
1719     { "IcsInputBoxProc", IcsInputBoxProc },\r
1720     { "PauseProc", PauseProc },\r
1721     { "AcceptProc", AcceptProc },\r
1722     { "DeclineProc", DeclineProc },\r
1723     { "RematchProc", RematchProc },\r
1724     { "CallFlagProc", CallFlagProc },\r
1725     { "DrawProc", DrawProc },\r
1726     { "AdjournProc", AdjournProc },\r
1727     { "AbortProc", AbortProc },\r
1728     { "ResignProc", ResignProc },\r
1729     { "EnterKeyProc", EnterKeyProc },\r
1730     { "StopObservingProc", StopObservingProc },\r
1731     { "StopExaminingProc", StopExaminingProc },\r
1732     { "BackwardProc", BackwardProc },\r
1733     { "ForwardProc", ForwardProc },\r
1734     { "ToStartProc", ToStartProc },\r
1735     { "ToEndProc", ToEndProc },\r
1736     { "RevertProc", RevertProc },\r
1737     { "TruncateGameProc", TruncateGameProc },\r
1738     { "MoveNowProc", MoveNowProc },\r
1739     { "RetractMoveProc", RetractMoveProc },\r
1740     { "AlwaysQueenProc", AlwaysQueenProc },\r
1741     { "AnimateDraggingProc", AnimateDraggingProc },\r
1742     { "AnimateMovingProc", AnimateMovingProc },\r
1743     { "AutoflagProc", AutoflagProc },\r
1744     { "AutoflipProc", AutoflipProc },\r
1745     { "AutobsProc", AutobsProc },\r
1746     { "AutoraiseProc", AutoraiseProc },\r
1747     { "AutosaveProc", AutosaveProc },\r
1748     { "BlindfoldProc", BlindfoldProc },\r
1749     { "FlashMovesProc", FlashMovesProc },\r
1750     { "FlipViewProc", FlipViewProc },\r
1751     { "GetMoveListProc", GetMoveListProc },\r
1752 #if HIGHDRAG\r
1753     { "HighlightDraggingProc", HighlightDraggingProc },\r
1754 #endif\r
1755     { "HighlightLastMoveProc", HighlightLastMoveProc },\r
1756     { "IcsAlarmProc", IcsAlarmProc },\r
1757     { "MoveSoundProc", MoveSoundProc },\r
1758     { "OldSaveStyleProc", OldSaveStyleProc },\r
1759     { "PeriodicUpdatesProc", PeriodicUpdatesProc },     \r
1760     { "PonderNextMoveProc", PonderNextMoveProc },\r
1761     { "PopupExitMessageProc", PopupExitMessageProc },   \r
1762     { "PopupMoveErrorsProc", PopupMoveErrorsProc },     \r
1763     { "PremoveProc", PremoveProc },\r
1764     { "QuietPlayProc", QuietPlayProc },\r
1765     { "ShowCoordsProc", ShowCoordsProc },\r
1766     { "ShowThinkingProc", ShowThinkingProc },\r
1767     { "HideThinkingProc", HideThinkingProc },\r
1768     { "TestLegalityProc", TestLegalityProc },\r
1769     { "InfoProc", InfoProc },\r
1770     { "ManProc", ManProc },\r
1771     { "HintProc", HintProc },\r
1772     { "BookProc", BookProc },\r
1773     { "AboutGameProc", AboutGameProc },\r
1774     { "AboutProc", AboutProc },\r
1775     { "DebugProc", DebugProc },\r
1776     { "NothingProc", NothingProc },\r
1777     { "CommentPopDown", (XtActionProc) CommentPopDown },\r
1778     { "EditCommentPopDown", (XtActionProc) EditCommentPopDown },\r
1779     { "TagsPopDown", (XtActionProc) TagsPopDown },\r
1780     { "ErrorPopDown", (XtActionProc) ErrorPopDown },\r
1781     { "ICSInputBoxPopDown", (XtActionProc) ICSInputBoxPopDown },\r
1782     { "AnalysisPopDown", (XtActionProc) AnalysisPopDown },\r
1783     { "FileNamePopDown", (XtActionProc) FileNamePopDown },\r
1784     { "AskQuestionPopDown", (XtActionProc) AskQuestionPopDown },\r
1785     { "GameListPopDown", (XtActionProc) GameListPopDown },\r
1786     { "PromotionPopDown", (XtActionProc) PromotionPopDown },\r
1787     { "HistoryPopDown", (XtActionProc) HistoryPopDown },\r
1788     { "EngineOutputPopDown", (XtActionProc) EngineOutputPopDown },\r
1789     { "ShufflePopDown", (XtActionProc) ShufflePopDown },\r
1790     { "EnginePopDown", (XtActionProc) EnginePopDown },\r
1791     { "UciPopDown", (XtActionProc) UciPopDown },\r
1792     { "TimeControlPopDown", (XtActionProc) TimeControlPopDown },\r
1793     { "NewVariantPopDown", (XtActionProc) NewVariantPopDown },\r
1794 };\r
1795      \r
1796 char globalTranslations[] =\r
1797   ":<Key>R: ResignProc() \n \\r
1798    :<Key>r: ResetProc() \n \\r
1799    :<Key>g: LoadGameProc() \n \\r
1800    :<Key>N: LoadNextGameProc() \n \\r
1801    :<Key>P: LoadPrevGameProc() \n \\r
1802    :<Key>Q: QuitProc() \n \\r
1803    :<Key>F: ToEndProc() \n \\r
1804    :<Key>f: ForwardProc() \n \\r
1805    :<Key>B: ToStartProc() \n \\r
1806    :<Key>b: BackwardProc() \n \\r
1807    :<Key>p: PauseProc() \n \\r
1808    :<Key>d: DrawProc() \n \\r
1809    :<Key>t: CallFlagProc() \n \\r
1810    :<Key>i: Iconify() \n \\r
1811    :<Key>c: Iconify() \n \\r
1812    :<Key>v: FlipViewProc() \n \\r
1813    <KeyDown>Control_L: BackwardProc() \n \\r
1814    <KeyUp>Control_L: ForwardProc() \n \\r
1815    <KeyDown>Control_R: BackwardProc() \n \\r
1816    <KeyUp>Control_R: ForwardProc() \n \\r
1817    Shift<Key>1: AskQuestionProc(\"Direct command\",\\r
1818                                 \"Send to chess program:\",,1) \n \\r
1819    Shift<Key>2: AskQuestionProc(\"Direct command\",\\r
1820                                 \"Send to second chess program:\",,2) \n";\r
1821 \r
1822 char boardTranslations[] =\r
1823    "<Btn1Down>: HandleUserMove() \n \\r
1824    <Btn1Up>: HandleUserMove() \n \\r
1825    <Btn1Motion>: AnimateUserMove() \n \\r
1826    Shift<Btn2Down>: XawPositionSimpleMenu(menuB) XawPositionSimpleMenu(menuD)\\r
1827                  PieceMenuPopup(menuB) \n \\r
1828    Any<Btn2Down>: XawPositionSimpleMenu(menuW) XawPositionSimpleMenu(menuD) \\r
1829                  PieceMenuPopup(menuW) \n \\r
1830    Shift<Btn3Down>: XawPositionSimpleMenu(menuW) XawPositionSimpleMenu(menuD)\\r
1831                  PieceMenuPopup(menuW) \n \\r
1832    Any<Btn3Down>: XawPositionSimpleMenu(menuB) XawPositionSimpleMenu(menuD) \\r
1833                  PieceMenuPopup(menuB) \n";\r
1834      \r
1835 char whiteTranslations[] = "<BtnDown>: WhiteClock()\n";\r
1836 char blackTranslations[] = "<BtnDown>: BlackClock()\n";\r
1837      \r
1838 char ICSInputTranslations[] =\r
1839     "<Key>Return: EnterKeyProc() \n";\r
1840 \r
1841 String xboardResources[] = {\r
1842     "*fileName*value.translations: #override\\n <Key>Return: FileNameAction()",\r
1843     "*question*value.translations: #override\\n <Key>Return: AskQuestionReplyAction()",\r
1844     "*errorpopup*translations: #override\\n <Key>Return: ErrorPopDown()",\r
1845     NULL\r
1846   };\r
1847      \r
1848 \r
1849 /* Max possible square size */\r
1850 #define MAXSQSIZE 256\r
1851 \r
1852 static int xpm_avail[MAXSQSIZE];\r
1853 \r
1854 #ifdef HAVE_DIR_STRUCT\r
1855 \r
1856 /* Extract piece size from filename */\r
1857 static int\r
1858 xpm_getsize(name, len, ext)\r
1859      char *name;\r
1860      int len;\r
1861      char *ext;\r
1862 {\r
1863     char *p, *d;\r
1864     char buf[10];\r
1865   \r
1866     if (len < 4)\r
1867       return 0;\r
1868 \r
1869     if ((p=strchr(name, '.')) == NULL ||\r
1870         StrCaseCmp(p+1, ext) != 0)\r
1871       return 0;\r
1872   \r
1873     p = name + 3;\r
1874     d = buf;\r
1875 \r
1876     while (*p && isdigit(*p))\r
1877       *(d++) = *(p++);\r
1878 \r
1879     *d = 0;\r
1880     return atoi(buf);\r
1881 }\r
1882 \r
1883 /* Setup xpm_avail */\r
1884 static int\r
1885 xpm_getavail(dirname, ext)\r
1886      char *dirname;\r
1887      char *ext;\r
1888 {\r
1889     DIR *dir;\r
1890     struct dirent *ent;\r
1891     int  i;\r
1892 \r
1893     for (i=0; i<MAXSQSIZE; ++i)\r
1894       xpm_avail[i] = 0;\r
1895 \r
1896     if (appData.debugMode)\r
1897       fprintf(stderr, "XPM dir:%s:ext:%s:\n", dirname, ext);\r
1898   \r
1899     dir = opendir(dirname);\r
1900     if (!dir)\r
1901       {\r
1902           fprintf(stderr, "%s: Can't access XPM directory %s\n", \r
1903                   programName, dirname);\r
1904           exit(1);\r
1905       }\r
1906   \r
1907     while ((ent=readdir(dir)) != NULL) {\r
1908         i = xpm_getsize(ent->d_name, NAMLEN(ent), ext);\r
1909         if (i > 0 && i < MAXSQSIZE)\r
1910           xpm_avail[i] = 1;\r
1911     }\r
1912 \r
1913     closedir(dir);\r
1914 \r
1915     return 0;\r
1916 }\r
1917 \r
1918 void\r
1919 xpm_print_avail(fp, ext)\r
1920      FILE *fp;\r
1921      char *ext;\r
1922 {\r
1923     int i;\r
1924 \r
1925     fprintf(fp, "Available `%s' sizes:\n", ext);\r
1926     for (i=1; i<MAXSQSIZE; ++i) {\r
1927         if (xpm_avail[i])\r
1928           printf("%d\n", i);\r
1929     }\r
1930 }\r
1931 \r
1932 /* Return XPM piecesize closest to size */\r
1933 int\r
1934 xpm_closest_to(dirname, size, ext)\r
1935      char *dirname;\r
1936      int size;\r
1937      char *ext;\r
1938 {\r
1939     int i;\r
1940     int sm_diff = MAXSQSIZE;\r
1941     int sm_index = 0;\r
1942     int diff;\r
1943   \r
1944     xpm_getavail(dirname, ext);\r
1945 \r
1946     if (appData.debugMode)\r
1947       xpm_print_avail(stderr, ext);\r
1948   \r
1949     for (i=1; i<MAXSQSIZE; ++i) {\r
1950         if (xpm_avail[i]) {\r
1951             diff = size - i;\r
1952             diff = (diff<0) ? -diff : diff;\r
1953             if (diff < sm_diff) {\r
1954                 sm_diff = diff;\r
1955                 sm_index = i;\r
1956             }\r
1957         }\r
1958     }\r
1959 \r
1960     if (!sm_index) {\r
1961         fprintf(stderr, "Error: No `%s' files!\n", ext);\r
1962         exit(1);\r
1963     }\r
1964 \r
1965     return sm_index;\r
1966 }\r
1967 #else   /* !HAVE_DIR_STRUCT */\r
1968 /* If we are on a system without a DIR struct, we can't\r
1969    read the directory, so we can't collect a list of\r
1970    filenames, etc., so we can't do any size-fitting. */\r
1971 int\r
1972 xpm_closest_to(dirname, size, ext)\r
1973      char *dirname;\r
1974      int size;\r
1975      char *ext;\r
1976 {\r
1977     fprintf(stderr, "Warning: No DIR structure found on this system --\n");\r
1978     fprintf(stderr, "         Unable to autosize for XPM/XIM pieces.\n");\r
1979     fprintf(stderr, "   Please report this error to frankm@hiwaay.net.\n");\r
1980     fprintf(stderr, "   Include system type & operating system in message.\n");\r
1981     return size;\r
1982 }\r
1983 #endif /* HAVE_DIR_STRUCT */\r
1984 \r
1985 static char *cnames[9] = { "black", "red", "green", "yellow", "blue",\r
1986                              "magenta", "cyan", "white" };\r
1987 typedef struct {\r
1988     int attr, bg, fg;\r
1989 } TextColors;\r
1990 TextColors textColors[(int)NColorClasses];\r
1991 \r
1992 /* String is: "fg, bg, attr". Which is 0, 1, 2 */\r
1993 static int\r
1994 parse_color(str, which)\r
1995      char *str;\r
1996      int which;\r
1997 {\r
1998     char *p, buf[100], *d;\r
1999     int i;\r
2000   \r
2001     if (strlen(str) > 99)       /* watch bounds on buf */\r
2002       return -1;\r
2003 \r
2004     p = str;\r
2005     d = buf;\r
2006     for (i=0; i<which; ++i) {\r
2007         p = strchr(p, ',');\r
2008         if (!p)\r
2009           return -1;\r
2010         ++p;\r
2011     }\r
2012 \r
2013     /* Could be looking at something like:\r
2014        black, , 1\r
2015        .. in which case we want to stop on a comma also */\r
2016     while (*p && *p != ',' && !isalpha(*p) && !isdigit(*p))\r
2017       ++p;\r
2018 \r
2019     if (*p == ',') {\r
2020         return -1;              /* Use default for empty field */\r
2021     }\r
2022     \r
2023     if (which == 2 || isdigit(*p))\r
2024       return atoi(p);\r
2025  \r
2026     while (*p && isalpha(*p))\r
2027       *(d++) = *(p++);\r
2028 \r
2029     *d = 0;\r
2030 \r
2031     for (i=0; i<8; ++i) {\r
2032         if (!StrCaseCmp(buf, cnames[i]))\r
2033           return which? (i+40) : (i+30);\r
2034     }\r
2035     if (!StrCaseCmp(buf, "default")) return -1;\r
2036 \r
2037     fprintf(stderr, "%s: unrecognized color %s\n", programName, buf);\r
2038     return -2;\r
2039 }\r
2040 \r
2041 static int\r
2042 parse_cpair(cc, str)\r
2043      ColorClass cc;\r
2044      char *str;\r
2045 {\r
2046     if ((textColors[(int)cc].fg=parse_color(str, 0)) == -2) {\r
2047         fprintf(stderr, "%s: can't parse foreground color in `%s'\n",\r
2048                 programName, str);\r
2049         return -1;\r
2050     }\r
2051 \r
2052     /* bg and attr are optional */\r
2053     textColors[(int)cc].bg = parse_color(str, 1);\r
2054     if ((textColors[(int)cc].attr = parse_color(str, 2)) < 0) {\r
2055         textColors[(int)cc].attr = 0;\r
2056     }\r
2057     return 0;\r
2058 }\r
2059 \r
2060 \r
2061 /* Arrange to catch delete-window events */\r
2062 Atom wm_delete_window;\r
2063 void\r
2064 CatchDeleteWindow(Widget w, String procname)\r
2065 {\r
2066   char buf[MSG_SIZ];\r
2067   XSetWMProtocols(xDisplay, XtWindow(w), &wm_delete_window, 1);\r
2068   sprintf(buf, "<Message>WM_PROTOCOLS: %s() \n", procname);\r
2069   XtAugmentTranslations(w, XtParseTranslationTable(buf));\r
2070 }\r
2071 \r
2072 void\r
2073 BoardToTop()\r
2074 {\r
2075   Arg args[16];\r
2076   XtSetArg(args[0], XtNiconic, False);\r
2077   XtSetValues(shellWidget, args, 1);\r
2078 \r
2079   XtPopup(shellWidget, XtGrabNone); /* Raise if lowered  */\r
2080 }\r
2081 \r
2082 #ifdef IDSIZES\r
2083   // eventually, all layout determining code should go into a subroutine, but until then IDSIZE remains undefined\r
2084 #else
2085 #define BoardSize int\r
2086 void InitDrawingSizes(BoardSize boardSize, int flags)\r
2087 {   // [HGM] resize is functional now, but for board format changes only (nr of ranks, files)\r
2088     Dimension timerWidth, boardWidth, boardHeight, w, h, sep, bor, wr, hr;
2089     Arg args[16];
2090     XtGeometryResult gres;\r
2091     int i;
2092
2093     if(!formWidget) return;\r
2094
2095     /*\r
2096      * Enable shell resizing.\r
2097      */\r
2098     shellArgs[0].value = (XtArgVal) &w;\r
2099     shellArgs[1].value = (XtArgVal) &h;\r
2100     XtGetValues(shellWidget, shellArgs, 2);\r
2101
2102     shellArgs[4].value = 2*w; shellArgs[2].value = 10;\r
2103     shellArgs[5].value = 2*h; shellArgs[3].value = 10;\r
2104     XtSetValues(shellWidget, &shellArgs[2], 4);
2105 \r
2106     XtSetArg(args[0], XtNdefaultDistance, &sep);\r    XtGetValues(formWidget, args, 1);
2107 \r
2108     boardWidth = lineGap + BOARD_WIDTH * (squareSize + lineGap);\r
2109     boardHeight = lineGap + BOARD_HEIGHT * (squareSize + lineGap);
2110     CreateGrid();\r
2111
2112     XtSetArg(args[0], XtNwidth, boardWidth);\r
2113     XtSetArg(args[1], XtNheight, boardHeight);\r
2114     XtSetValues(boardWidget, args, 2);\r
2115 \r
2116     timerWidth = (boardWidth - sep) / 2;\r
2117     XtSetArg(args[0], XtNwidth, timerWidth);\r
2118     XtSetValues(whiteTimerWidget, args, 1);\r
2119     XtSetValues(blackTimerWidget, args, 1);\r
2120 \r
2121     XawFormDoLayout(formWidget, False);\r
2122
2123     if (appData.titleInWindow) {\r
2124         i = 0;\r
2125         XtSetArg(args[i], XtNborderWidth, &bor); i++;\r
2126         XtSetArg(args[i], XtNheight, &h);  i++;\r
2127         XtGetValues(titleWidget, args, i);\r
2128         if (smallLayout) {\r
2129             w = boardWidth - 2*bor;\r
2130         } else {\r
2131             XtSetArg(args[0], XtNwidth, &w);\r
2132             XtGetValues(menuBarWidget, args, 1);\r
2133             w = boardWidth - w - sep - 2*bor - 2; // WIDTH_FUDGE\r
2134         }\r
2135 \r
2136         gres = XtMakeResizeRequest(titleWidget, w, h, &wr, &hr);\r
2137         if (gres != XtGeometryYes && appData.debugMode) {\r
2138             fprintf(stderr,\r
2139                     "%s: titleWidget geometry error %d %d %d %d %d\n",\r
2140                     programName, gres, w, h, wr, hr);\r
2141         }\r
2142     }\r
2143 \r
2144     XawFormDoLayout(formWidget, True);\r
2145
2146     /*\r
2147      * Inhibit shell resizing.\r
2148      */
2149     shellArgs[0].value = w = (XtArgVal) boardWidth + marginW;\r
2150     shellArgs[1].value = h = (XtArgVal) boardHeight + marginH;\r
2151     shellArgs[4].value = shellArgs[2].value = w;\r
2152     shellArgs[5].value = shellArgs[3].value = h;\r
2153     XtSetValues(shellWidget, &shellArgs[0], 6);\r
2154 }\r
2155 #endif\r
2156 \r
2157 int\r
2158 main(argc, argv)\r
2159      int argc;\r
2160      char **argv;\r
2161 {\r
2162     int i, j, clockFontPxlSize, coordFontPxlSize, fontPxlSize;\r
2163     XSetWindowAttributes window_attributes;\r
2164     Arg args[16];\r
2165     Dimension timerWidth, boardWidth, boardHeight, w, h, sep, bor, wr, hr;\r
2166     XrmValue vFrom, vTo;\r
2167     XtGeometryResult gres;\r
2168     char *p;\r
2169     XrmDatabase xdb;\r
2170     int forceMono = False;
2171 #define INDIRECTION\r
2172 #ifdef INDIRECTION
2173     // [HGM] before anything else, expand any indirection files amongst options
2174     char *argvCopy[1000]; // 1000 seems enough
2175     char newArgs[10000];  // holds actual characters
2176     int k = 0;
2177
2178     srandom(time(0)); // [HGM] book: make random truly random
2179
2180     j = 0;
2181     for(i=0; i<argc; i++) {
2182         if(j >= 1000-2) { printf("too many arguments\n"); exit(-1); }
2183 //fprintf(stderr, "arg %s\n", argv[i]);
2184         if(argv[i][0] != '@') argvCopy[j++] = argv[i]; else {
2185             char c;
2186             FILE *f = fopen(argv[i]+1, "rb");
2187             if(f == NULL) { fprintf(stderr, "ignore %s\n", argv[i]); continue; } // do not expand non-existing
2188             argvCopy[j++] = newArgs + k; // get ready for first argument from file
2189             while((c = fgetc(f)) != EOF) { // each line of file inserts 1 argument in the list
2190                 if(c == '\n') {
2191                     if(j >= 1000-2) { printf("too many arguments\n"); exit(-1); }
2192                     newArgs[k++] = 0;  // terminate current arg
2193                     if(k >= 10000-1) { printf("too long arguments\n"); exit(-1); }
2194                     argvCopy[j++] = newArgs + k; // get ready for next
2195                 } else {
2196                     if(k >= 10000-1) { printf("too long arguments\n"); exit(-1); }
2197                     newArgs[k++] = c;
2198                 }
2199             }
2200             newArgs[k] = 0;
2201             j--;
2202             fclose(f);
2203         }
2204     }
2205     argvCopy[j] = NULL;
2206     argv = argvCopy;
2207     argc = j;
2208 #if 0
2209     if(appData.debugMode,1) { // OK, appData is not initialized here yet...
2210         for(i=0; i<argc; i++) fprintf(stderr, "argv[%2d] = '%s'\n", i, argv[i]);
2211     }
2212 #endif
2213 #endif
2214
2215 \r
2216     setbuf(stdout, NULL);\r
2217     setbuf(stderr, NULL);\r
2218     debugFP = stderr;\r
2219     \r
2220     programName = strrchr(argv[0], '/');\r
2221     if (programName == NULL)\r
2222       programName = argv[0];\r
2223     else\r
2224       programName++;\r
2225 \r
2226     shellWidget =\r
2227       XtAppInitialize(&appContext, "XBoard", shellOptions,\r
2228                       XtNumber(shellOptions),\r
2229                       &argc, argv, xboardResources, NULL, 0);\r
2230     if (argc > 1) {\r
2231         fprintf(stderr, "%s: unrecognized argument %s\n",\r
2232                 programName, argv[1]);\r
2233         exit(2);\r
2234     }\r
2235     \r
2236     if ((chessDir = (char *) getenv("CHESSDIR")) == NULL) {\r
2237         chessDir = ".";\r
2238     } else {\r
2239         if (chdir(chessDir) != 0) {\r
2240             fprintf(stderr, "%s: can't cd to CHESSDIR: ", programName);\r
2241             perror(chessDir);\r
2242             exit(1);\r
2243         }\r
2244     }\r
2245     \r
2246     p = getenv("HOME");\r
2247     if (p == NULL) p = "/tmp";\r
2248     i = strlen(p) + strlen("/.xboardXXXXXx.pgn") + 1;\r
2249     gameCopyFilename = (char*) malloc(i);\r
2250     gamePasteFilename = (char*) malloc(i);\r
2251     sprintf(gameCopyFilename, "%s/.xboard%05uc.pgn", p, getpid());\r
2252     sprintf(gamePasteFilename, "%s/.xboard%05up.pgn", p, getpid());\r
2253 \r
2254     XtGetApplicationResources(shellWidget, (XtPointer) &appData,\r
2255                               clientResources, XtNumber(clientResources),\r
2256                               NULL, 0);\r
2257 \r
2258     /* [HGM,HR] make sure board size is acceptable */\r
2259     if(appData.NrFiles > BOARD_SIZE ||\r
2260        appData.NrRanks > BOARD_SIZE   )\r
2261          DisplayFatalError("Recompile with BOARD_SIZE > 12, to support this size", 0, 2);\r
2262 \r
2263 #if !HIGHDRAG\r
2264     /* This feature does not work; animation needs a rewrite */\r
2265     appData.highlightDragging = FALSE;\r
2266 #endif\r
2267     InitBackEnd1();\r
2268 \r
2269     xDisplay = XtDisplay(shellWidget);\r
2270     xScreen = DefaultScreen(xDisplay);\r
2271     wm_delete_window = XInternAtom(xDisplay, "WM_DELETE_WINDOW", True);\r
2272 \r
2273         gameInfo.variant = StringToVariant(appData.variant);\r
2274         InitPosition(FALSE);\r
2275 #if 0\r
2276     /*\r
2277      * Determine boardSize\r
2278      */\r
2279     gameInfo.boardWidth = gameInfo.boardHeight = 8; // [HGM] boardsize: make sure we start as 8x8\r
2280 \r
2281 //#ifndef IDSIZE\r
2282     // [HGM] as long as we have not created the possibility to change size while running, start with requested size\r
2283     gameInfo.boardWidth    = appData.NrFiles > 0 ? appData.NrFiles : 8; \r
2284     gameInfo.boardHeight   = appData.NrRanks > 0 ? appData.NrRanks : 8;\r
2285     gameInfo.holdingsWidth = appData.holdingsSize > 0 ? 2 : 0;\r
2286 #endif\r
2287 \r
2288 \r
2289 #ifdef IDSIZE\r
2290     InitDrawingSizes(-1, 0); // [HGM] initsize: make this into a subroutine\r
2291 #else\r
2292     if (isdigit(appData.boardSize[0])) {\r
2293         i = sscanf(appData.boardSize, "%d,%d,%d,%d,%d,%d,%d", &squareSize,\r
2294                    &lineGap, &clockFontPxlSize, &coordFontPxlSize,\r
2295                    &fontPxlSize, &smallLayout, &tinyLayout);\r
2296         if (i == 0) {\r
2297             fprintf(stderr, "%s: bad boardSize syntax %s\n",\r
2298                     programName, appData.boardSize);\r
2299             exit(2);\r
2300         }\r
2301         if (i < 7) {\r
2302             /* Find some defaults; use the nearest known size */\r
2303             SizeDefaults *szd, *nearest;\r
2304             int distance = 99999;\r
2305             nearest = szd = sizeDefaults;\r
2306             while (szd->name != NULL) {\r
2307                 if (abs(szd->squareSize - squareSize) < distance) {\r
2308                     nearest = szd;\r
2309                     distance = abs(szd->squareSize - squareSize);\r
2310                     if (distance == 0) break;\r
2311                 }\r
2312                 szd++;\r
2313             }\r
2314             if (i < 2) lineGap = nearest->lineGap;\r
2315             if (i < 3) clockFontPxlSize = nearest->clockFontPxlSize;\r
2316             if (i < 4) coordFontPxlSize = nearest->coordFontPxlSize;\r
2317             if (i < 5) fontPxlSize = nearest->fontPxlSize;\r
2318             if (i < 6) smallLayout = nearest->smallLayout;\r
2319             if (i < 7) tinyLayout = nearest->tinyLayout;\r
2320         }\r
2321     } else {\r
2322         SizeDefaults *szd = sizeDefaults;\r
2323         if (*appData.boardSize == NULLCHAR) {\r
2324             while (DisplayWidth(xDisplay, xScreen) < szd->minScreenSize ||\r
2325                    DisplayHeight(xDisplay, xScreen) < szd->minScreenSize) {\r
2326               szd++;\r
2327             }\r
2328             if (szd->name == NULL) szd--;\r
2329         } else {\r
2330             while (szd->name != NULL &&\r
2331                    StrCaseCmp(szd->name, appData.boardSize) != 0) szd++;\r
2332             if (szd->name == NULL) {\r
2333                 fprintf(stderr, "%s: unrecognized boardSize name %s\n",\r
2334                         programName, appData.boardSize);\r
2335                 exit(2);\r
2336             }\r
2337         }\r
2338         squareSize = szd->squareSize;\r
2339         lineGap = szd->lineGap;\r
2340         clockFontPxlSize = szd->clockFontPxlSize;\r
2341         coordFontPxlSize = szd->coordFontPxlSize;\r
2342         fontPxlSize = szd->fontPxlSize;\r
2343         smallLayout = szd->smallLayout;\r
2344         tinyLayout = szd->tinyLayout;\r
2345     }\r
2346 \r
2347     /* Now, using squareSize as a hint, find a good XPM/XIM set size */\r
2348     if (strlen(appData.pixmapDirectory) > 0) {\r
2349         p = ExpandPathName(appData.pixmapDirectory);\r
2350         if (!p) {\r
2351             fprintf(stderr, "Error expanding path name \"%s\"\n",\r
2352                    appData.pixmapDirectory);\r
2353             exit(1);\r
2354         }\r
2355         if (appData.debugMode) {\r
2356             fprintf(stderr, "XBoard square size (hint): %d\n", squareSize);\r
2357             fprintf(stderr, "%s fulldir:%s:\n", IMAGE_EXT, p);\r
2358         }\r
2359         squareSize = xpm_closest_to(p, squareSize, IMAGE_EXT);\r
2360         if (appData.debugMode) {\r
2361             fprintf(stderr, "Closest %s size: %d\n", IMAGE_EXT, squareSize);\r
2362         }\r
2363     }\r
2364                 \r
2365     /* [HR] height treated separately (hacked) */\r
2366     boardWidth = lineGap + BOARD_WIDTH * (squareSize + lineGap);\r
2367     boardHeight = lineGap + BOARD_HEIGHT * (squareSize + lineGap);\r
2368     if (appData.showJail == 1) {\r
2369         /* Jail on top and bottom */\r
2370         XtSetArg(boardArgs[1], XtNwidth, boardWidth);\r
2371         XtSetArg(boardArgs[2], XtNheight,\r
2372                  boardHeight + 2*(lineGap + squareSize));\r
2373     } else if (appData.showJail == 2) {\r
2374         /* Jail on sides */\r
2375         XtSetArg(boardArgs[1], XtNwidth,\r
2376                  boardWidth + 2*(lineGap + squareSize));\r
2377         XtSetArg(boardArgs[2], XtNheight, boardHeight);\r
2378     } else {\r
2379         /* No jail */\r
2380         XtSetArg(boardArgs[1], XtNwidth, boardWidth);\r
2381         XtSetArg(boardArgs[2], XtNheight, boardHeight);\r
2382     }\r
2383 \r
2384     /*\r
2385      * Determine what fonts to use.\r
2386      */\r
2387     appData.clockFont = FindFont(appData.clockFont, clockFontPxlSize);\r
2388     clockFontID = XLoadFont(xDisplay, appData.clockFont);\r
2389     clockFontStruct = XQueryFont(xDisplay, clockFontID);\r
2390     appData.coordFont = FindFont(appData.coordFont, coordFontPxlSize);\r
2391     coordFontID = XLoadFont(xDisplay, appData.coordFont);\r
2392     coordFontStruct = XQueryFont(xDisplay, coordFontID);\r
2393     appData.font = FindFont(appData.font, fontPxlSize);\r
2394     countFontID = XLoadFont(xDisplay, appData.coordFont); // [HGM] holdings\r
2395     countFontStruct = XQueryFont(xDisplay, countFontID);\r
2396 //    appData.font = FindFont(appData.font, fontPxlSize);\r
2397 \r
2398     xdb = XtDatabase(xDisplay);\r
2399     XrmPutStringResource(&xdb, "*font", appData.font);\r
2400 \r
2401     /*\r
2402      * Detect if there are not enough colors available and adapt.\r
2403      */\r
2404     if (DefaultDepth(xDisplay, xScreen) <= 2) {\r
2405       appData.monoMode = True;\r
2406     }\r
2407 \r
2408     if (!appData.monoMode) {\r
2409         vFrom.addr = (caddr_t) appData.lightSquareColor;\r
2410         vFrom.size = strlen(appData.lightSquareColor);\r
2411         XtConvert(shellWidget, XtRString, &vFrom, XtRPixel, &vTo);\r
2412         if (vTo.addr == NULL) {\r
2413           appData.monoMode = True;\r
2414           forceMono = True;\r
2415         } else {\r
2416           lightSquareColor = *(Pixel *) vTo.addr;\r
2417         }\r
2418     }\r
2419     if (!appData.monoMode) {\r
2420         vFrom.addr = (caddr_t) appData.darkSquareColor;\r
2421         vFrom.size = strlen(appData.darkSquareColor);\r
2422         XtConvert(shellWidget, XtRString, &vFrom, XtRPixel, &vTo);\r
2423         if (vTo.addr == NULL) {\r
2424           appData.monoMode = True;\r
2425           forceMono = True;\r
2426         } else {\r
2427           darkSquareColor = *(Pixel *) vTo.addr;\r
2428         }\r
2429     }\r
2430     if (!appData.monoMode) {\r
2431         vFrom.addr = (caddr_t) appData.whitePieceColor;\r
2432         vFrom.size = strlen(appData.whitePieceColor);\r
2433         XtConvert(shellWidget, XtRString, &vFrom, XtRPixel, &vTo);\r
2434         if (vTo.addr == NULL) {\r
2435           appData.monoMode = True;\r
2436           forceMono = True;\r
2437         } else {\r
2438           whitePieceColor = *(Pixel *) vTo.addr;\r
2439         }\r
2440     }\r
2441     if (!appData.monoMode) {\r
2442         vFrom.addr = (caddr_t) appData.blackPieceColor;\r
2443         vFrom.size = strlen(appData.blackPieceColor);\r
2444         XtConvert(shellWidget, XtRString, &vFrom, XtRPixel, &vTo);\r
2445         if (vTo.addr == NULL) {\r
2446           appData.monoMode = True;\r
2447           forceMono = True;\r
2448         } else {\r
2449           blackPieceColor = *(Pixel *) vTo.addr;\r
2450         }\r
2451     }\r
2452 \r
2453     if (!appData.monoMode) {\r
2454         vFrom.addr = (caddr_t) appData.highlightSquareColor;\r
2455         vFrom.size = strlen(appData.highlightSquareColor);\r
2456         XtConvert(shellWidget, XtRString, &vFrom, XtRPixel, &vTo);\r
2457         if (vTo.addr == NULL) {\r
2458           appData.monoMode = True;\r
2459           forceMono = True;\r
2460         } else {\r
2461           highlightSquareColor = *(Pixel *) vTo.addr;\r
2462         }\r
2463     }\r
2464 \r
2465     if (!appData.monoMode) {\r
2466         vFrom.addr = (caddr_t) appData.premoveHighlightColor;\r
2467         vFrom.size = strlen(appData.premoveHighlightColor);\r
2468         XtConvert(shellWidget, XtRString, &vFrom, XtRPixel, &vTo);\r
2469         if (vTo.addr == NULL) {\r
2470           appData.monoMode = True;\r
2471           forceMono = True;\r
2472         } else {\r
2473           premoveHighlightColor = *(Pixel *) vTo.addr;\r
2474         }\r
2475     }\r
2476 \r
2477     if (forceMono) {\r
2478       fprintf(stderr, "%s: too few colors available; trying monochrome mode\n",\r
2479               programName);\r
2480     }\r
2481 \r
2482     if (appData.monoMode && appData.debugMode) {\r
2483         fprintf(stderr, "white pixel = 0x%lx, black pixel = 0x%lx\n",\r
2484                 (unsigned long) XWhitePixel(xDisplay, xScreen),\r
2485                 (unsigned long) XBlackPixel(xDisplay, xScreen));\r
2486     }\r
2487     \r
2488     if (parse_cpair(ColorShout, appData.colorShout) < 0 ||\r
2489         parse_cpair(ColorSShout, appData.colorSShout) < 0 ||\r
2490         parse_cpair(ColorChannel1, appData.colorChannel1) < 0  ||\r
2491         parse_cpair(ColorChannel, appData.colorChannel) < 0  ||\r
2492         parse_cpair(ColorKibitz, appData.colorKibitz) < 0 ||\r
2493         parse_cpair(ColorTell, appData.colorTell) < 0 ||\r
2494         parse_cpair(ColorChallenge, appData.colorChallenge) < 0  ||\r
2495         parse_cpair(ColorRequest, appData.colorRequest) < 0  ||\r
2496         parse_cpair(ColorSeek, appData.colorSeek) < 0  ||\r
2497         parse_cpair(ColorNormal, appData.colorNormal) < 0)\r
2498       {\r
2499           if (appData.colorize) {\r
2500               fprintf(stderr,\r
2501                       "%s: can't parse color names; disabling colorization\n",\r
2502                       programName);\r
2503           }\r
2504           appData.colorize = FALSE;\r
2505       }\r
2506     textColors[ColorNone].fg = textColors[ColorNone].bg = -1;\r
2507     textColors[ColorNone].attr = 0;\r
2508     \r
2509     XtAppAddActions(appContext, boardActions, XtNumber(boardActions));\r
2510     \r
2511     /*\r
2512      * widget hierarchy\r
2513      */\r
2514     if (tinyLayout) {\r
2515         layoutName = "tinyLayout";\r
2516     } else if (smallLayout) {\r
2517         layoutName = "smallLayout";\r
2518     } else {\r
2519         layoutName = "normalLayout";\r
2520     }\r
2521     /* Outer layoutWidget is there only to provide a name for use in\r
2522        resources that depend on the layout style */\r
2523     layoutWidget =\r
2524       XtCreateManagedWidget(layoutName, formWidgetClass, shellWidget,\r
2525                             layoutArgs, XtNumber(layoutArgs));\r
2526     formWidget =\r
2527       XtCreateManagedWidget("form", formWidgetClass, layoutWidget,\r
2528                             formArgs, XtNumber(formArgs));\r
2529     XtSetArg(args[0], XtNdefaultDistance, &sep);\r
2530     XtGetValues(formWidget, args, 1);\r
2531 \r
2532     j = 0;\r
2533     widgetList[j++] = menuBarWidget = CreateMenuBar(menuBar);\r
2534     XtSetArg(args[0], XtNtop,    XtChainTop);\r
2535     XtSetArg(args[1], XtNbottom, XtChainTop);
2536     XtSetValues(menuBarWidget, args, 2);\r
2537 \r
2538     widgetList[j++] = whiteTimerWidget =\r
2539       XtCreateWidget("whiteTime", labelWidgetClass,\r
2540                      formWidget, timerArgs, XtNumber(timerArgs));\r
2541     XtSetArg(args[0], XtNfont, clockFontStruct);\r
2542     XtSetArg(args[1], XtNtop,    XtChainTop);\r
2543     XtSetArg(args[2], XtNbottom, XtChainTop);
2544     XtSetValues(whiteTimerWidget, args, 3);\r
2545     \r
2546     widgetList[j++] = blackTimerWidget =\r
2547       XtCreateWidget("blackTime", labelWidgetClass,\r
2548                      formWidget, timerArgs, XtNumber(timerArgs));\r
2549     XtSetArg(args[0], XtNfont, clockFontStruct);\r
2550     XtSetArg(args[1], XtNtop,    XtChainTop);\r
2551     XtSetArg(args[2], XtNbottom, XtChainTop);
2552     XtSetValues(blackTimerWidget, args, 3);\r
2553     \r
2554     if (appData.titleInWindow) {\r
2555         widgetList[j++] = titleWidget = \r
2556           XtCreateWidget("title", labelWidgetClass, formWidget,\r
2557                          titleArgs, XtNumber(titleArgs));\r
2558         XtSetArg(args[0], XtNtop,    XtChainTop);\r
2559         XtSetArg(args[1], XtNbottom, XtChainTop);
2560         XtSetValues(titleWidget, args, 2);\r
2561     }\r
2562 \r
2563     if (appData.showButtonBar) {\r
2564       widgetList[j++] = buttonBarWidget = CreateButtonBar(buttonBar);\r
2565       XtSetArg(args[0], XtNleft,  XtChainRight); // [HGM] glue to right window edge\r
2566       XtSetArg(args[1], XtNright, XtChainRight); //       for good run-time sizing
2567       XtSetArg(args[2], XtNtop,    XtChainTop);\r
2568       XtSetArg(args[3], XtNbottom, XtChainTop);
2569       XtSetValues(buttonBarWidget, args, 4);\r
2570     }\r
2571 \r
2572     widgetList[j++] = messageWidget =\r
2573       XtCreateWidget("message", labelWidgetClass, formWidget,\r
2574                      messageArgs, XtNumber(messageArgs));
2575     XtSetArg(args[0], XtNtop,    XtChainTop);\r
2576     XtSetArg(args[1], XtNbottom, XtChainTop);
2577     XtSetValues(messageWidget, args, 2);\r
2578 \r
2579     widgetList[j++] = boardWidget =\r
2580       XtCreateWidget("board", widgetClass, formWidget, boardArgs,\r
2581                      XtNumber(boardArgs));\r
2582 \r
2583     XtManageChildren(widgetList, j);\r
2584     \r
2585     timerWidth = (boardWidth - sep) / 2;\r
2586     XtSetArg(args[0], XtNwidth, timerWidth);\r
2587     XtSetValues(whiteTimerWidget, args, 1);\r
2588     XtSetValues(blackTimerWidget, args, 1);\r
2589     \r
2590     XtSetArg(args[0], XtNbackground, &timerBackgroundPixel);\r
2591     XtSetArg(args[1], XtNforeground, &timerForegroundPixel);\r
2592     XtGetValues(whiteTimerWidget, args, 2);\r
2593     \r
2594     if (appData.showButtonBar) {\r
2595       XtSetArg(args[0], XtNbackground, &buttonBackgroundPixel);\r
2596       XtSetArg(args[1], XtNforeground, &buttonForegroundPixel);\r
2597       XtGetValues(XtNameToWidget(buttonBarWidget, PAUSE_BUTTON), args, 2);\r
2598     }\r
2599 \r
2600     /*\r
2601      * formWidget uses these constraints but they are stored\r
2602      * in the children.\r
2603      */\r
2604     i = 0;\r
2605     XtSetArg(args[i], XtNfromHoriz, 0); i++;\r
2606     XtSetValues(menuBarWidget, args, i);\r
2607     if (appData.titleInWindow) {\r
2608         if (smallLayout) {\r
2609             i = 0;\r
2610             XtSetArg(args[i], XtNfromVert, menuBarWidget); i++;\r
2611             XtSetValues(whiteTimerWidget, args, i);\r
2612             i = 0;\r
2613             XtSetArg(args[i], XtNfromVert, menuBarWidget); i++;\r
2614             XtSetArg(args[i], XtNfromHoriz, whiteTimerWidget); i++;\r
2615             XtSetValues(blackTimerWidget, args, i);\r
2616             i = 0;\r
2617             XtSetArg(args[i], XtNfromVert, whiteTimerWidget); i++;\r
2618             XtSetArg(args[i], XtNjustify, XtJustifyLeft); i++;\r
2619             XtSetValues(titleWidget, args, i);\r
2620             i = 0;\r
2621             XtSetArg(args[i], XtNfromVert, titleWidget); i++;\r
2622             XtSetArg(args[i], XtNresizable, (XtArgVal) True); i++;\r
2623             XtSetValues(messageWidget, args, i);\r
2624             if (appData.showButtonBar) {\r
2625               i = 0;\r
2626               XtSetArg(args[i], XtNfromVert, titleWidget); i++;\r
2627               XtSetArg(args[i], XtNfromHoriz, messageWidget); i++;\r
2628               XtSetValues(buttonBarWidget, args, i);\r
2629             }\r
2630         } else {\r
2631             i = 0;\r
2632             XtSetArg(args[i], XtNfromVert, titleWidget); i++;\r
2633             XtSetValues(whiteTimerWidget, args, i);\r
2634             i = 0;\r
2635             XtSetArg(args[i], XtNfromVert, titleWidget); i++;\r
2636             XtSetArg(args[i], XtNfromHoriz, whiteTimerWidget); i++;\r
2637             XtSetValues(blackTimerWidget, args, i);\r
2638             i = 0;\r
2639             XtSetArg(args[i], XtNfromHoriz, menuBarWidget); i++;\r
2640             XtSetValues(titleWidget, args, i);\r
2641             i = 0;\r
2642             XtSetArg(args[i], XtNfromVert, whiteTimerWidget); i++;\r
2643             XtSetArg(args[i], XtNresizable, (XtArgVal) True); i++;\r
2644             XtSetValues(messageWidget, args, i);\r
2645             if (appData.showButtonBar) {\r
2646               i = 0;\r
2647               XtSetArg(args[i], XtNfromVert, whiteTimerWidget); i++;\r
2648               XtSetArg(args[i], XtNfromHoriz, messageWidget); i++;\r
2649               XtSetValues(buttonBarWidget, args, i);\r
2650             }\r
2651         }\r
2652     } else {\r
2653         i = 0;\r
2654         XtSetArg(args[i], XtNfromVert, menuBarWidget); i++;\r
2655         XtSetValues(whiteTimerWidget, args, i);\r
2656         i = 0;\r
2657         XtSetArg(args[i], XtNfromVert, menuBarWidget); i++;\r
2658         XtSetArg(args[i], XtNfromHoriz, whiteTimerWidget); i++;\r
2659         XtSetValues(blackTimerWidget, args, i);\r
2660         i = 0;\r
2661         XtSetArg(args[i], XtNfromVert, whiteTimerWidget); i++;\r
2662         XtSetArg(args[i], XtNresizable, (XtArgVal) True); i++;\r
2663         XtSetValues(messageWidget, args, i);\r
2664         if (appData.showButtonBar) {\r
2665           i = 0;\r
2666           XtSetArg(args[i], XtNfromVert, whiteTimerWidget); i++;\r
2667           XtSetArg(args[i], XtNfromHoriz, messageWidget); i++;\r
2668           XtSetValues(buttonBarWidget, args, i);\r
2669         }\r
2670     }\r
2671     i = 0;\r
2672     XtSetArg(args[0], XtNfromVert, messageWidget);\r
2673     XtSetArg(args[1], XtNtop,    XtChainTop);\r
2674     XtSetArg(args[2], XtNbottom, XtChainBottom);
2675     XtSetArg(args[3], XtNleft,   XtChainLeft);\r
2676     XtSetArg(args[4], XtNright,  XtChainRight);
2677     XtSetValues(boardWidget, args, 5);\r
2678 \r
2679     XtRealizeWidget(shellWidget);\r
2680 \r
2681     /*\r
2682      * Correct the width of the message and title widgets.\r
2683      * It is not known why some systems need the extra fudge term.\r
2684      * The value "2" is probably larger than needed.\r
2685      */\r
2686     XawFormDoLayout(formWidget, False);\r
2687
2688 #define WIDTH_FUDGE 2\r
2689     i = 0;\r
2690     XtSetArg(args[i], XtNborderWidth, &bor);  i++;\r
2691     XtSetArg(args[i], XtNheight, &h);  i++;\r
2692     XtGetValues(messageWidget, args, i);\r
2693     if (appData.showButtonBar) {\r
2694       i = 0;\r
2695       XtSetArg(args[i], XtNwidth, &w);  i++;\r
2696       XtGetValues(buttonBarWidget, args, i);\r
2697       w = boardWidth - w - sep - 2*bor - WIDTH_FUDGE;\r
2698     } else {\r
2699       w = boardWidth - 2*bor + 1; /*!! +1 compensates for kludge below */\r
2700     }\r
2701 \r
2702     gres = XtMakeResizeRequest(messageWidget, w, h, &wr, &hr);\r
2703     if (gres != XtGeometryYes && appData.debugMode) {\r
2704       fprintf(stderr, "%s: messageWidget geometry error %d %d %d %d %d\n",\r
2705               programName, gres, w, h, wr, hr);\r
2706     }\r
2707     \r
2708     /* !! Horrible hack to work around bug in XFree86 4.0.1 (X11R6.4.3) */\r
2709     /* The size used for the child widget in layout lags one resize behind\r
2710        its true size, so we resize a second time, 1 pixel smaller.  Yeech! */\r
2711     w--;\r
2712     gres = XtMakeResizeRequest(messageWidget, w, h, &wr, &hr);\r
2713     if (gres != XtGeometryYes && appData.debugMode) {\r
2714       fprintf(stderr, "%s: messageWidget geometry error %d %d %d %d %d\n",\r
2715               programName, gres, w, h, wr, hr);\r
2716     }\r
2717     /* !! end hack */\r
2718     XtSetArg(args[0], XtNleft,  XtChainLeft);  // [HGM] glue ends for good run-time sizing\r
2719     XtSetArg(args[1], XtNright, XtChainRight);
2720     XtSetValues(messageWidget, args, 2);\r
2721 \r
2722     if (appData.titleInWindow) {\r
2723         i = 0;\r
2724         XtSetArg(args[i], XtNborderWidth, &bor); i++;\r
2725         XtSetArg(args[i], XtNheight, &h);  i++;\r
2726         XtGetValues(titleWidget, args, i);\r
2727         if (smallLayout) {\r
2728             w = boardWidth - 2*bor;\r
2729         } else {\r
2730             XtSetArg(args[0], XtNwidth, &w);\r
2731             XtGetValues(menuBarWidget, args, 1);\r
2732             w = boardWidth - w - sep - 2*bor - WIDTH_FUDGE;\r
2733         }\r
2734 \r
2735         gres = XtMakeResizeRequest(titleWidget, w, h, &wr, &hr);\r
2736         if (gres != XtGeometryYes && appData.debugMode) {\r
2737             fprintf(stderr,\r
2738                     "%s: titleWidget geometry error %d %d %d %d %d\n",\r
2739                     programName, gres, w, h, wr, hr);\r
2740         }\r
2741     }\r
2742     XawFormDoLayout(formWidget, True);\r
2743 \r
2744     xBoardWindow = XtWindow(boardWidget);\r
2745 \r
2746     // [HGM] it seems the layout code ends here, but perhaps the color stuff is size independent and would\r
2747     //       not need to go into InitDrawingSizes().\r
2748 #endif    \r
2749 \r
2750     /* \r
2751      * Create X checkmark bitmap and initialize option menu checks.\r
2752      */\r
2753     ReadBitmap(&xMarkPixmap, "checkmark.bm",\r
2754                checkmark_bits, checkmark_width, checkmark_height);\r
2755     XtSetArg(args[0], XtNleftBitmap, xMarkPixmap);\r
2756     if (appData.alwaysPromoteToQueen) {\r
2757         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Always Queen"),\r
2758                     args, 1);\r
2759     }\r
2760     if (appData.animateDragging) {\r
2761         XtSetValues(XtNameToWidget(menuBarWidget,\r
2762                                    "menuOptions.Animate Dragging"),\r
2763                     args, 1);\r
2764     }\r
2765     if (appData.animate) {\r
2766         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Animate Moving"),\r
2767                     args, 1);\r
2768     }\r
2769     if (appData.autoComment) {\r
2770         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Auto Comment"),\r
2771                     args, 1);\r
2772     }\r
2773     if (appData.autoCallFlag) {\r
2774         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Auto Flag"),\r
2775                     args, 1);\r
2776     }\r
2777     if (appData.autoFlipView) {\r
2778         XtSetValues(XtNameToWidget(menuBarWidget,"menuOptions.Auto Flip View"),\r
2779                     args, 1);\r
2780     }\r
2781     if (appData.autoObserve) {\r
2782         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Auto Observe"),\r
2783                     args, 1);\r
2784     }\r
2785     if (appData.autoRaiseBoard) {\r
2786         XtSetValues(XtNameToWidget(menuBarWidget,\r
2787                                    "menuOptions.Auto Raise Board"), args, 1);\r
2788     }\r
2789     if (appData.autoSaveGames) {\r
2790         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Auto Save"),\r
2791                     args, 1);\r
2792     }\r
2793     if (appData.saveGameFile[0] != NULLCHAR) {\r
2794         /* Can't turn this off from menu */\r
2795         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Auto Save"),\r
2796                     args, 1);\r
2797         XtSetSensitive(XtNameToWidget(menuBarWidget, "menuOptions.Auto Save"),\r
2798                        False);\r
2799 \r
2800     }\r
2801     if (appData.blindfold) {\r
2802         XtSetValues(XtNameToWidget(menuBarWidget,\r
2803                                    "menuOptions.Blindfold"), args, 1);\r
2804     }\r
2805     if (appData.flashCount > 0) {\r
2806         XtSetValues(XtNameToWidget(menuBarWidget,\r
2807                                    "menuOptions.Flash Moves"),\r
2808                     args, 1);\r
2809     }\r
2810     if (appData.getMoveList) {\r
2811         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Get Move List"),\r
2812                     args, 1);\r
2813     }\r
2814 #if HIGHDRAG\r
2815     if (appData.highlightDragging) {\r
2816         XtSetValues(XtNameToWidget(menuBarWidget,\r
2817                                    "menuOptions.Highlight Dragging"),\r
2818                     args, 1);\r
2819     }\r
2820 #endif\r
2821     if (appData.highlightLastMove) {\r
2822         XtSetValues(XtNameToWidget(menuBarWidget,\r
2823                                    "menuOptions.Highlight Last Move"),\r
2824                     args, 1);\r
2825     }\r
2826     if (appData.icsAlarm) {\r
2827         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.ICS Alarm"),\r
2828                     args, 1);\r
2829     }\r
2830     if (appData.ringBellAfterMoves) {\r
2831         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Move Sound"),\r
2832                     args, 1);\r
2833     }\r
2834     if (appData.oldSaveStyle) {\r
2835         XtSetValues(XtNameToWidget(menuBarWidget,\r
2836                                    "menuOptions.Old Save Style"), args, 1);\r
2837     }\r
2838     if (appData.periodicUpdates) {\r
2839         XtSetValues(XtNameToWidget(menuBarWidget,\r
2840                                    "menuOptions.Periodic Updates"), args, 1);\r
2841     }   \r
2842     if (appData.ponderNextMove) {\r
2843         XtSetValues(XtNameToWidget(menuBarWidget,\r
2844                                    "menuOptions.Ponder Next Move"), args, 1);\r
2845     }   \r
2846     if (appData.popupExitMessage) {\r
2847         XtSetValues(XtNameToWidget(menuBarWidget,\r
2848                                    "menuOptions.Popup Exit Message"), args, 1);\r
2849     }   \r
2850     if (appData.popupMoveErrors) {\r
2851         XtSetValues(XtNameToWidget(menuBarWidget,\r
2852                                    "menuOptions.Popup Move Errors"), args, 1);\r
2853     }   \r
2854     if (appData.premove) {\r
2855         XtSetValues(XtNameToWidget(menuBarWidget,\r
2856                                    "menuOptions.Premove"), args, 1);\r
2857     }\r
2858     if (appData.quietPlay) {\r
2859         XtSetValues(XtNameToWidget(menuBarWidget,\r
2860                                    "menuOptions.Quiet Play"), args, 1);\r
2861     }\r
2862     if (appData.showCoords) {\r
2863         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Show Coords"),\r
2864                     args, 1);\r
2865     }\r
2866     if (appData.hideThinkingFromHuman) {\r
2867         XtSetValues(XtNameToWidget(menuBarWidget, "menuOptions.Hide Thinking"),\r
2868                     args, 1);\r
2869     }\r
2870     if (appData.testLegality) {\r
2871         XtSetValues(XtNameToWidget(menuBarWidget,"menuOptions.Test Legality"),\r
2872                     args, 1);\r
2873     }\r
2874 \r
2875     /*\r
2876      * Create an icon.\r
2877      */\r
2878     ReadBitmap(&wIconPixmap, "icon_white.bm",\r
2879                icon_white_bits, icon_white_width, icon_white_height);\r
2880     ReadBitmap(&bIconPixmap, "icon_black.bm",\r
2881                icon_black_bits, icon_black_width, icon_black_height);\r
2882     iconPixmap = wIconPixmap;\r
2883     i = 0;\r
2884     XtSetArg(args[i], XtNiconPixmap, iconPixmap);  i++;\r
2885     XtSetValues(shellWidget, args, i);\r
2886     \r
2887     /*\r
2888      * Create a cursor for the board widget.\r
2889      */\r
2890     window_attributes.cursor = XCreateFontCursor(xDisplay, XC_hand2);\r
2891     XChangeWindowAttributes(xDisplay, xBoardWindow,\r
2892                             CWCursor, &window_attributes);\r
2893     \r
2894     /*\r
2895      * Inhibit shell resizing.\r
2896      */\r
2897     shellArgs[0].value = (XtArgVal) &w;\r
2898     shellArgs[1].value = (XtArgVal) &h;\r
2899     XtGetValues(shellWidget, shellArgs, 2);\r
2900     shellArgs[4].value = shellArgs[2].value = w;\r
2901     shellArgs[5].value = shellArgs[3].value = h;\r
2902     XtSetValues(shellWidget, &shellArgs[2], 4);
2903     marginW =  w - boardWidth; // [HGM] needed to set new shellWidget size when we resize board\r
2904     marginH =  h - boardHeight;\r
2905 \r
2906     CatchDeleteWindow(shellWidget, "QuitProc");\r
2907 \r
2908     CreateGCs();\r
2909     CreateGrid();\r
2910 #if HAVE_LIBXPM\r
2911     if (appData.bitmapDirectory[0] != NULLCHAR) {\r
2912       CreatePieces();\r
2913     } else {\r
2914       CreateXPMPieces();\r
2915     }\r
2916 #else\r
2917     CreateXIMPieces();\r
2918     /* Create regular pieces */\r
2919     if (!useImages) CreatePieces();\r
2920 #endif  \r
2921 \r
2922     CreatePieceMenus();\r
2923 \r
2924     if (appData.animate || appData.animateDragging)\r
2925       CreateAnimVars();\r
2926     \r
2927     XtAugmentTranslations(formWidget,\r
2928                           XtParseTranslationTable(globalTranslations));\r
2929     XtAugmentTranslations(boardWidget,\r
2930                           XtParseTranslationTable(boardTranslations));\r
2931     XtAugmentTranslations(whiteTimerWidget,\r
2932                           XtParseTranslationTable(whiteTranslations));\r
2933     XtAugmentTranslations(blackTimerWidget,\r
2934                           XtParseTranslationTable(blackTranslations));\r
2935 \r
2936     /* Why is the following needed on some versions of X instead\r
2937      * of a translation? */\r
2938     XtAddEventHandler(boardWidget, ExposureMask, False,\r
2939                       (XtEventHandler) EventProc, NULL);\r
2940     /* end why */\r
2941 \r
2942     InitBackEnd2();\r
2943     \r
2944     if (errorExitStatus == -1) {\r
2945         if (appData.icsActive) {\r
2946             /* We now wait until we see "login:" from the ICS before\r
2947                sending the logon script (problems with timestamp otherwise) */\r
2948             /*ICSInitScript();*/\r
2949             if (appData.icsInputBox) ICSInputBoxPopUp();\r
2950         }\r
2951 \r
2952         signal(SIGINT, IntSigHandler);\r
2953         signal(SIGTERM, IntSigHandler);\r
2954         if (*appData.cmailGameName != NULLCHAR) {\r
2955             signal(SIGUSR1, CmailSigHandler);\r
2956         }\r
2957     }\r
2958         InitPosition(TRUE);\r
2959 \r
2960     XtAppMainLoop(appContext);\r
2961     return 0;\r
2962 }\r
2963 \r
2964 void\r
2965 ShutDownFrontEnd()\r
2966 {\r
2967     if (appData.icsActive && oldICSInteractionTitle != NULL) {\r
2968         DisplayIcsInteractionTitle(oldICSInteractionTitle);\r
2969     }\r
2970     unlink(gameCopyFilename);\r
2971     unlink(gamePasteFilename);\r
2972 }\r
2973 \r
2974 RETSIGTYPE\r
2975 IntSigHandler(sig)\r
2976      int sig;\r
2977 {\r
2978     ExitEvent(sig);\r
2979 }\r
2980 \r
2981 RETSIGTYPE\r
2982 CmailSigHandler(sig)\r
2983      int sig;\r
2984 {\r
2985     int dummy = 0;\r
2986     int error;\r
2987 \r
2988     signal(SIGUSR1, SIG_IGN);   /* suspend handler     */\r
2989 \r
2990     /* Activate call-back function CmailSigHandlerCallBack()             */\r
2991     OutputToProcess(cmailPR, (char *)(&dummy), sizeof(int), &error);\r
2992 \r
2993     signal(SIGUSR1, CmailSigHandler); /* re-activate handler */\r
2994 }\r
2995 \r
2996 void\r
2997 CmailSigHandlerCallBack(isr, closure, message, count, error)\r
2998      InputSourceRef isr;\r
2999      VOIDSTAR closure;\r
3000      char *message;\r
3001      int count;\r
3002      int error;\r
3003 {\r
3004     BoardToTop();\r
3005     ReloadCmailMsgEvent(TRUE);  /* Reload cmail msg  */\r
3006 }\r
3007 /**** end signal code ****/\r
3008 \r
3009 \r
3010 void\r
3011 ICSInitScript()\r
3012 {\r
3013     FILE *f;\r
3014     char buf[MSG_SIZ];\r
3015     char *p;\r
3016 \r
3017     f = fopen(appData.icsLogon, "r");\r
3018     if (f == NULL) {\r
3019         p = getenv("HOME");\r
3020         if (p != NULL) {\r
3021             strcpy(buf, p);\r
3022             strcat(buf, "/");\r
3023             strcat(buf, appData.icsLogon);\r
3024             f = fopen(buf, "r");\r
3025         }\r
3026     }\r
3027     if (f != NULL)\r
3028       ProcessICSInitScript(f);\r
3029 }\r
3030 \r
3031 void\r
3032 ResetFrontEnd()\r
3033 {\r
3034     CommentPopDown();\r
3035     EditCommentPopDown();\r
3036     TagsPopDown();\r
3037     return;\r
3038 }\r
3039 \r
3040 typedef struct {\r
3041     char *name;\r
3042     Boolean value;\r
3043 } Enables;\r
3044 \r
3045 void\r
3046 SetMenuEnables(enab)\r
3047      Enables *enab;\r
3048 {\r
3049   Widget w;\r
3050   if (!menuBarWidget) return;\r
3051   while (enab->name != NULL) {\r
3052     w = XtNameToWidget(menuBarWidget, enab->name);\r
3053     if (w == NULL) {\r
3054       DisplayError(enab->name, 0);\r
3055     } else {\r
3056       XtSetSensitive(w, enab->value);\r
3057     }\r
3058     enab++;\r
3059   }\r
3060 }\r
3061 \r
3062 Enables icsEnables[] = {\r
3063     { "menuFile.Mail Move", False },\r
3064     { "menuFile.Reload CMail Message", False },\r
3065     { "menuMode.Machine Black", False },\r
3066     { "menuMode.Machine White", False },\r
3067     { "menuMode.Analysis Mode", False },\r
3068     { "menuMode.Analyze File", False },\r
3069     { "menuMode.Two Machines", False },\r
3070 #ifndef ZIPPY\r
3071     { "menuHelp.Hint", False },\r
3072     { "menuHelp.Book", False },\r
3073     { "menuStep.Move Now", False },\r
3074     { "menuOptions.Periodic Updates", False },  \r
3075     { "menuOptions.Hide Thinking", False },\r
3076     { "menuOptions.Ponder Next Move", False },\r
3077 #endif\r
3078     { NULL, False }\r
3079 };\r
3080 \r
3081 Enables ncpEnables[] = {    \r
3082     { "menuFile.Mail Move", False },\r
3083     { "menuFile.Reload CMail Message", False },\r
3084     { "menuMode.Machine White", False },\r
3085     { "menuMode.Machine Black", False },\r
3086     { "menuMode.Analysis Mode", False },\r
3087     { "menuMode.Analyze File", False },\r
3088     { "menuMode.Two Machines", False },\r
3089     { "menuMode.ICS Client", False },\r
3090     { "menuMode.ICS Input Box", False },\r
3091     { "Action", False },\r
3092     { "menuStep.Revert", False },\r
3093     { "menuStep.Move Now", False },\r
3094     { "menuStep.Retract Move", False },\r
3095     { "menuOptions.Auto Comment", False },\r
3096     { "menuOptions.Auto Flag", False },\r
3097     { "menuOptions.Auto Flip View", False },\r
3098     { "menuOptions.Auto Observe", False },\r
3099     { "menuOptions.Auto Raise Board", False },\r
3100     { "menuOptions.Get Move List", False },\r
3101     { "menuOptions.ICS Alarm", False },\r
3102     { "menuOptions.Move Sound", False },\r
3103     { "menuOptions.Quiet Play", False },\r
3104     { "menuOptions.Hide Thinking", False },\r
3105     { "menuOptions.Periodic Updates", False },  \r
3106     { "menuOptions.Ponder Next Move", False },\r
3107     { "menuHelp.Hint", False },\r
3108     { "menuHelp.Book", False },\r
3109     { NULL, False }\r
3110 };\r
3111 \r
3112 Enables gnuEnables[] = {    \r
3113     { "menuMode.ICS Client", False },\r
3114     { "menuMode.ICS Input Box", False },\r
3115     { "menuAction.Accept", False },\r
3116     { "menuAction.Decline", False },\r
3117     { "menuAction.Rematch", False },\r
3118     { "menuAction.Adjourn", False },\r
3119     { "menuAction.Stop Examining", False },\r
3120     { "menuAction.Stop Observing", False },\r
3121     { "menuStep.Revert", False },\r
3122     { "menuOptions.Auto Comment", False },\r
3123     { "menuOptions.Auto Observe", False },\r
3124     { "menuOptions.Auto Raise Board", False },\r
3125     { "menuOptions.Get Move List", False },\r
3126     { "menuOptions.Premove", False },\r
3127     { "menuOptions.Quiet Play", False },\r
3128 \r
3129     /* The next two options rely on SetCmailMode being called *after*    */\r
3130     /* SetGNUMode so that when GNU is being used to give hints these     */\r
3131     /* menu options are still available                                  */\r
3132 \r
3133     { "menuFile.Mail Move", False },\r
3134     { "menuFile.Reload CMail Message", False },\r
3135     { NULL, False }\r
3136 };\r
3137 \r
3138 Enables cmailEnables[] = {    \r
3139     { "Action", True },\r
3140     { "menuAction.Call Flag", False },\r
3141     { "menuAction.Draw", True },\r
3142     { "menuAction.Adjourn", False },\r
3143     { "menuAction.Abort", False },\r
3144     { "menuAction.Stop Observing", False },\r
3145     { "menuAction.Stop Examining", False },\r
3146     { "menuFile.Mail Move", True },\r
3147     { "menuFile.Reload CMail Message", True },\r
3148     { NULL, False }\r
3149 };\r
3150 \r
3151 Enables trainingOnEnables[] = {    \r
3152   { "menuMode.Edit Comment", False },\r
3153   { "menuMode.Pause", False },\r
3154   { "menuStep.Forward", False },\r
3155   { "menuStep.Backward", False },\r
3156   { "menuStep.Forward to End", False },\r
3157   { "menuStep.Back to Start", False },\r
3158   { "menuStep.Move Now", False },\r
3159   { "menuStep.Truncate Game", False },\r
3160   { NULL, False }\r
3161 };\r
3162 \r
3163 Enables trainingOffEnables[] = {    \r
3164   { "menuMode.Edit Comment", True },\r
3165   { "menuMode.Pause", True },\r
3166   { "menuStep.Forward", True },\r
3167   { "menuStep.Backward", True },\r
3168   { "menuStep.Forward to End", True },\r
3169   { "menuStep.Back to Start", True },\r
3170   { "menuStep.Move Now", True },\r
3171   { "menuStep.Truncate Game", True },\r
3172   { NULL, False }\r
3173 };\r
3174 \r
3175 Enables machineThinkingEnables[] = {\r
3176   { "menuFile.Load Game", False },\r
3177   { "menuFile.Load Next Game", False },\r
3178   { "menuFile.Load Previous Game", False },\r
3179   { "menuFile.Reload Same Game", False },\r
3180   { "menuFile.Paste Game", False },\r
3181   { "menuFile.Load Position", False },\r
3182   { "menuFile.Load Next Position", False },\r
3183   { "menuFile.Load Previous Position", False },\r
3184   { "menuFile.Reload Same Position", False },\r
3185   { "menuFile.Paste Position", False },\r
3186   { "menuMode.Machine White", False },\r
3187   { "menuMode.Machine Black", False },\r
3188   { "menuMode.Two Machines", False },\r
3189   { "menuStep.Retract Move", False },\r
3190   { NULL, False }\r
3191 };\r
3192 \r
3193 Enables userThinkingEnables[] = {\r
3194   { "menuFile.Load Game", True },\r
3195   { "menuFile.Load Next Game", True },\r
3196   { "menuFile.Load Previous Game", True },\r
3197   { "menuFile.Reload Same Game", True },\r
3198   { "menuFile.Paste Game", True },\r
3199   { "menuFile.Load Position", True },\r
3200   { "menuFile.Load Next Position", True },\r
3201   { "menuFile.Load Previous Position", True },\r
3202   { "menuFile.Reload Same Position", True },\r
3203   { "menuFile.Paste Position", True },\r
3204   { "menuMode.Machine White", True },\r
3205   { "menuMode.Machine Black", True },\r
3206   { "menuMode.Two Machines", True },\r
3207   { "menuStep.Retract Move", True },\r
3208   { NULL, False }\r
3209 };\r
3210 \r
3211 void SetICSMode()\r
3212 {\r
3213   SetMenuEnables(icsEnables);\r
3214 }\r
3215 \r
3216 void\r
3217 SetNCPMode()\r
3218 {\r
3219   SetMenuEnables(ncpEnables);\r
3220 }\r
3221 \r
3222 void\r
3223 SetGNUMode()\r
3224 {\r
3225   SetMenuEnables(gnuEnables);\r
3226 }\r
3227 \r
3228 void\r
3229 SetCmailMode()\r
3230 {\r
3231   SetMenuEnables(cmailEnables);\r
3232 }\r
3233 \r
3234 void\r
3235 SetTrainingModeOn()\r
3236 {\r
3237   SetMenuEnables(trainingOnEnables);\r
3238   if (appData.showButtonBar) {\r
3239     XtSetSensitive(buttonBarWidget, False);\r
3240   }\r
3241   CommentPopDown();\r
3242 }\r
3243 \r
3244 void\r
3245 SetTrainingModeOff()\r
3246 {\r
3247   SetMenuEnables(trainingOffEnables);\r
3248   if (appData.showButtonBar) {\r
3249     XtSetSensitive(buttonBarWidget, True);\r
3250   }\r
3251 }\r
3252 \r
3253 void\r
3254 SetUserThinkingEnables()\r
3255 {\r
3256   if (appData.noChessProgram) return;\r
3257   SetMenuEnables(userThinkingEnables);\r
3258 }\r
3259 \r
3260 void\r
3261 SetMachineThinkingEnables()\r
3262 {\r
3263   if (appData.noChessProgram) return;\r
3264   SetMenuEnables(machineThinkingEnables);\r
3265   switch (gameMode) {\r
3266   case MachinePlaysBlack:\r
3267   case MachinePlaysWhite:\r
3268   case TwoMachinesPlay:\r
3269     XtSetSensitive(XtNameToWidget(menuBarWidget,\r
3270                                   ModeToWidgetName(gameMode)), True);\r
3271     break;\r
3272   default:\r
3273     break;\r
3274   }\r
3275 }\r
3276 \r
3277 #define Abs(n) ((n)<0 ? -(n) : (n))\r
3278 \r
3279 /*\r
3280  * Find a font that matches "pattern" that is as close as\r
3281  * possible to the targetPxlSize.  Prefer fonts that are k\r
3282  * pixels smaller to fonts that are k pixels larger.  The\r
3283  * pattern must be in the X Consortium standard format, \r
3284  * e.g. "-*-helvetica-bold-r-normal--*-*-*-*-*-*-*-*".\r
3285  * The return value should be freed with XtFree when no\r
3286  * longer needed.\r
3287  */\r
3288 char *FindFont(pattern, targetPxlSize)\r
3289      char *pattern;\r
3290      int targetPxlSize;\r
3291 {\r
3292     char **fonts, *p, *best, *scalable, *scalableTail;\r
3293     int i, j, nfonts, minerr, err, pxlSize;\r
3294 \r
3295     fonts = XListFonts(xDisplay, pattern, 999999, &nfonts);\r
3296     if (nfonts < 1) {\r
3297         fprintf(stderr, "%s: no fonts match pattern %s\n",\r
3298                 programName, pattern);\r
3299         exit(2);\r
3300     }\r
3301     best = fonts[0];\r
3302     scalable = NULL;\r
3303     minerr = 999999;\r
3304     for (i=0; i<nfonts; i++) {\r
3305         j = 0;\r
3306         p = fonts[i];\r
3307         if (*p != '-') continue;\r
3308         while (j < 7) {\r
3309             if (*p == NULLCHAR) break;\r
3310             if (*p++ == '-') j++;\r
3311         }\r
3312         if (j < 7) continue;\r
3313         pxlSize = atoi(p);\r
3314         if (pxlSize == 0) {\r
3315             scalable = fonts[i];\r
3316             scalableTail = p;\r
3317         } else {\r
3318             err = pxlSize - targetPxlSize;\r
3319             if (Abs(err) < Abs(minerr) ||\r
3320                 (minerr > 0 && err < 0 && -err == minerr)) {\r
3321                 best = fonts[i];\r
3322                 minerr = err;\r
3323             }\r
3324         }\r
3325     }\r
3326     if (scalable && Abs(minerr) > appData.fontSizeTolerance) {\r
3327         /* If the error is too big and there is a scalable font,\r
3328            use the scalable font. */\r
3329         int headlen = scalableTail - scalable;\r
3330         p = (char *) XtMalloc(strlen(scalable) + 10);\r
3331         while (isdigit(*scalableTail)) scalableTail++;\r
3332         sprintf(p, "%.*s%d%s", headlen, scalable, targetPxlSize, scalableTail);\r
3333     } else {\r
3334         p = (char *) XtMalloc(strlen(best) + 1);\r
3335         strcpy(p, best);\r
3336     }\r
3337     if (appData.debugMode) {\r
3338         fprintf(debugFP, "resolved %s at pixel size %d\n  to %s\n",\r
3339                 pattern, targetPxlSize, p);\r
3340     }\r
3341     XFreeFontNames(fonts);\r
3342     return p;\r
3343 }\r
3344 \r
3345 void CreateGCs()\r
3346 {\r
3347     XtGCMask value_mask = GCLineWidth | GCLineStyle | GCForeground\r
3348       | GCBackground | GCFunction | GCPlaneMask;\r
3349     XGCValues gc_values;\r
3350     GC copyInvertedGC;\r
3351     \r
3352     gc_values.plane_mask = AllPlanes;\r
3353     gc_values.line_width = lineGap;\r
3354     gc_values.line_style = LineSolid;\r
3355     gc_values.function = GXcopy;\r
3356     \r
3357     gc_values.foreground = XBlackPixel(xDisplay, xScreen);\r
3358     gc_values.background = XBlackPixel(xDisplay, xScreen);\r
3359     lineGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3360     \r
3361     gc_values.foreground = XBlackPixel(xDisplay, xScreen);\r
3362     gc_values.background = XWhitePixel(xDisplay, xScreen);\r
3363     coordGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3364     XSetFont(xDisplay, coordGC, coordFontID);\r
3365     \r
3366     // [HGM] make font for holdings counts (white on black0
3367     gc_values.foreground = XWhitePixel(xDisplay, xScreen);\r
3368     gc_values.background = XBlackPixel(xDisplay, xScreen);\r
3369     countGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3370     XSetFont(xDisplay, countGC, countFontID);\r
3371     \r
3372     if (appData.monoMode) {\r
3373         gc_values.foreground = XWhitePixel(xDisplay, xScreen);\r
3374         gc_values.background = XWhitePixel(xDisplay, xScreen);\r
3375         highlineGC = XtGetGC(shellWidget, value_mask, &gc_values);      \r
3376 \r
3377         gc_values.foreground = XWhitePixel(xDisplay, xScreen);\r
3378         gc_values.background = XBlackPixel(xDisplay, xScreen);\r
3379         lightSquareGC = wbPieceGC \r
3380           = XtGetGC(shellWidget, value_mask, &gc_values);\r
3381 \r
3382         gc_values.foreground = XBlackPixel(xDisplay, xScreen);\r
3383         gc_values.background = XWhitePixel(xDisplay, xScreen);\r
3384         darkSquareGC = bwPieceGC\r
3385           = XtGetGC(shellWidget, value_mask, &gc_values);\r
3386 \r
3387         if (DefaultDepth(xDisplay, xScreen) == 1) {\r
3388             /* Avoid XCopyPlane on 1-bit screens to work around Sun bug */\r
3389             gc_values.function = GXcopyInverted;\r
3390             copyInvertedGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3391             gc_values.function = GXcopy;\r
3392             if (XBlackPixel(xDisplay, xScreen) == 1) {\r
3393                 bwPieceGC = darkSquareGC;\r
3394                 wbPieceGC = copyInvertedGC;\r
3395             } else {\r
3396                 bwPieceGC = copyInvertedGC;\r
3397                 wbPieceGC = lightSquareGC;\r
3398             }\r
3399         }\r
3400     } else {\r
3401         gc_values.foreground = highlightSquareColor;\r
3402         gc_values.background = highlightSquareColor;\r
3403         highlineGC = XtGetGC(shellWidget, value_mask, &gc_values);      \r
3404 \r
3405         gc_values.foreground = premoveHighlightColor;\r
3406         gc_values.background = premoveHighlightColor;\r
3407         prelineGC = XtGetGC(shellWidget, value_mask, &gc_values);       \r
3408 \r
3409         gc_values.foreground = lightSquareColor;\r
3410         gc_values.background = darkSquareColor;\r
3411         lightSquareGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3412         \r
3413         gc_values.foreground = darkSquareColor;\r
3414         gc_values.background = lightSquareColor;\r
3415         darkSquareGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3416 \r
3417         gc_values.foreground = jailSquareColor;\r
3418         gc_values.background = jailSquareColor;\r
3419         jailSquareGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3420 \r
3421         gc_values.foreground = whitePieceColor;\r
3422         gc_values.background = darkSquareColor;\r
3423         wdPieceGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3424         \r
3425         gc_values.foreground = whitePieceColor;\r
3426         gc_values.background = lightSquareColor;\r
3427         wlPieceGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3428         \r
3429         gc_values.foreground = whitePieceColor;\r
3430         gc_values.background = jailSquareColor;\r
3431         wjPieceGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3432         \r
3433         gc_values.foreground = blackPieceColor;\r
3434         gc_values.background = darkSquareColor;\r
3435         bdPieceGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3436         \r
3437         gc_values.foreground = blackPieceColor;\r
3438         gc_values.background = lightSquareColor;\r
3439         blPieceGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3440 \r
3441         gc_values.foreground = blackPieceColor;\r
3442         gc_values.background = jailSquareColor;\r
3443         bjPieceGC = XtGetGC(shellWidget, value_mask, &gc_values);\r
3444     }\r
3445 }\r
3446 \r
3447 void loadXIM(xim, xmask, filename, dest, mask)\r
3448      XImage *xim;\r
3449      XImage *xmask;\r
3450      char *filename;\r
3451      Pixmap *dest;\r
3452      Pixmap *mask;\r
3453 {\r
3454     int x, y, w, h, p;\r
3455     FILE *fp;\r
3456     Pixmap temp;\r
3457     XGCValues   values;\r
3458     GC maskGC;\r
3459 \r
3460     fp = fopen(filename, "rb");\r
3461     if (!fp) {\r
3462         fprintf(stderr, "%s: error loading XIM!\n", programName);\r
3463         exit(1);\r
3464     }\r
3465           \r
3466     w = fgetc(fp);\r
3467     h = fgetc(fp);\r
3468   \r
3469     for (y=0; y<h; ++y) {\r
3470         for (x=0; x<h; ++x) {\r
3471             p = fgetc(fp);\r
3472 \r
3473             switch (p) {\r
3474               case 0:   \r
3475                 XPutPixel(xim, x, y, blackPieceColor); \r
3476                 if (xmask)\r
3477                   XPutPixel(xmask, x, y, WhitePixel(xDisplay,xScreen));\r
3478                 break;\r
3479               case 1:   \r
3480                 XPutPixel(xim, x, y, darkSquareColor); \r
3481                 if (xmask)\r
3482                   XPutPixel(xmask, x, y, BlackPixel(xDisplay,xScreen));\r
3483                 break;\r
3484               case 2:   \r
3485                 XPutPixel(xim, x, y, whitePieceColor); \r
3486                 if (xmask)\r
3487                   XPutPixel(xmask, x, y, WhitePixel(xDisplay,xScreen));\r
3488                 break;\r
3489               case 3:   \r
3490                 XPutPixel(xim, x, y, lightSquareColor);\r
3491                 if (xmask)\r
3492                   XPutPixel(xmask, x, y, BlackPixel(xDisplay,xScreen));\r
3493                 break;\r
3494             }\r
3495         }\r
3496     }\r
3497 \r
3498     /* create Pixmap of piece */\r
3499     *dest = XCreatePixmap(xDisplay, DefaultRootWindow(xDisplay),\r
3500                           w, h, xim->depth);\r
3501     XPutImage(xDisplay, *dest, lightSquareGC, xim,\r
3502               0, 0, 0, 0, w, h);  \r
3503 \r
3504     /* create Pixmap of clipmask \r
3505        Note: We assume the white/black pieces have the same\r
3506              outline, so we make only 6 masks. This is okay\r
3507              since the XPM clipmask routines do the same. */\r
3508     if (xmask) {\r
3509       temp = XCreatePixmap(xDisplay, DefaultRootWindow(xDisplay),\r
3510                             w, h, xim->depth);\r
3511       XPutImage(xDisplay, temp, lightSquareGC, xmask,\r
3512               0, 0, 0, 0, w, h);  \r
3513 \r
3514       /* now create the 1-bit version */\r
3515       *mask = XCreatePixmap(xDisplay, DefaultRootWindow(xDisplay),\r
3516                           w, h, 1);\r
3517 \r
3518       values.foreground = 1;\r
3519       values.background = 0;\r
3520 \r
3521       /* Don't use XtGetGC, not read only */\r
3522       maskGC = XCreateGC(xDisplay, *mask, \r
3523                     GCForeground | GCBackground, &values);\r
3524       XCopyPlane(xDisplay, temp, *mask, maskGC, \r
3525                   0, 0, squareSize, squareSize, 0, 0, 1);\r
3526       XFreePixmap(xDisplay, temp);\r
3527     }\r
3528 }\r
3529 \r
3530 void CreateXIMPieces()\r
3531 {\r
3532     int piece, kind;\r
3533     char buf[MSG_SIZ];\r
3534     u_int ss;\r
3535     static char *ximkind[] = { "ll", "ld", "dl", "dd" };\r
3536     XImage *ximtemp;\r
3537 \r
3538     ss = squareSize;\r
3539 \r
3540     /* The XSynchronize calls were copied from CreatePieces.\r
3541        Not sure if needed, but can't hurt */\r
3542     XSynchronize(xDisplay, True); /* Work-around for xlib/xt\r
3543                                      buffering bug */\r
3544   \r
3545     /* temp needed by loadXIM() */\r
3546     ximtemp = XGetImage(xDisplay, DefaultRootWindow(xDisplay),\r
3547                  0, 0, ss, ss, AllPlanes, XYPixmap);\r
3548 \r
3549     if (strlen(appData.pixmapDirectory) == 0) {\r
3550       useImages = 0;\r
3551     } else {\r
3552         useImages = 1;\r
3553         if (appData.monoMode) {\r
3554           DisplayFatalError("XIM pieces cannot be used in monochrome mode",\r
3555                             0, 2);\r
3556           ExitEvent(2);\r
3557         }\r
3558         fprintf(stderr, "\nLoading XIMs...\n");\r
3559         /* Load pieces */\r
3560         for (piece = (int) WhitePawn; piece <= (int) WhiteKing; piece++) {\r
3561             fprintf(stderr, "%d", piece+1);\r
3562             for (kind=0; kind<4; kind++) {\r
3563                 fprintf(stderr, ".");\r
3564                 sprintf(buf, "%s/%c%s%u.xim",\r
3565                         ExpandPathName(appData.pixmapDirectory),\r
3566                         ToLower(PieceToChar((ChessSquare)piece)),\r
3567                         ximkind[kind], ss);\r
3568                 ximPieceBitmap[kind][piece] =\r
3569                   XGetImage(xDisplay, DefaultRootWindow(xDisplay),\r
3570                             0, 0, ss, ss, AllPlanes, XYPixmap);\r
3571                 if (appData.debugMode)\r
3572                   fprintf(stderr, "(File:%s:) ", buf);\r
3573                 loadXIM(ximPieceBitmap[kind][piece], \r
3574                         ximtemp, buf,\r
3575                         &(xpmPieceBitmap[kind][piece]),\r
3576                         &(ximMaskPm[piece%(int)BlackPawn]));\r
3577             }\r
3578             fprintf(stderr," ");\r
3579         }\r
3580         /* Load light and dark squares */\r
3581         /* If the LSQ and DSQ pieces don't exist, we will \r
3582            draw them with solid squares. */\r
3583         sprintf(buf, "%s/lsq%u.xim", ExpandPathName(appData.pixmapDirectory), ss);\r
3584         if (access(buf, 0) != 0) {\r
3585             useImageSqs = 0;\r
3586         } else {\r
3587             useImageSqs = 1;\r
3588             fprintf(stderr, "light square ");\r
3589             ximLightSquare= \r
3590               XGetImage(xDisplay, DefaultRootWindow(xDisplay),\r
3591                         0, 0, ss, ss, AllPlanes, XYPixmap);\r
3592             if (appData.debugMode)\r
3593               fprintf(stderr, "(File:%s:) ", buf);\r
3594 \r
3595             loadXIM(ximLightSquare, NULL, buf, &xpmLightSquare, NULL);\r
3596             fprintf(stderr, "dark square ");\r
3597             sprintf(buf, "%s/dsq%u.xim",\r
3598                     ExpandPathName(appData.pixmapDirectory), ss);\r
3599             if (appData.debugMode)\r
3600               fprintf(stderr, "(File:%s:) ", buf);\r
3601             ximDarkSquare= \r
3602               XGetImage(xDisplay, DefaultRootWindow(xDisplay),\r
3603                         0, 0, ss, ss, AllPlanes, XYPixmap);\r
3604             loadXIM(ximDarkSquare, NULL, buf, &xpmDarkSquare, NULL);\r
3605             xpmJailSquare = xpmLightSquare;\r
3606         }\r
3607         fprintf(stderr, "Done.\n");\r
3608     }\r
3609     XSynchronize(xDisplay, False); /* Work-around for xlib/xt buffering bug */\r
3610 }\r
3611 \r
3612 #if HAVE_LIBXPM\r
3613 void CreateXPMPieces()\r
3614 {\r
3615     int piece, kind, r;\r
3616     char buf[MSG_SIZ];\r
3617     u_int ss = squareSize;\r
3618     XpmAttributes attr;\r
3619     static char *xpmkind[] = { "ll", "ld", "dl", "dd" };\r
3620     XpmColorSymbol symbols[4];\r
3621 \r
3622 #if 0\r
3623     /* Apparently some versions of Xpm don't define XpmFormat at all --tpm */\r
3624     if (appData.debugMode) {\r
3625         fprintf(stderr, "XPM Library Version: %d.%d%c\n", \r
3626                 XpmFormat, XpmVersion, (char)('a' + XpmRevision - 1));\r
3627     }\r
3628 #endif\r
3629   \r
3630     /* The XSynchronize calls were copied from CreatePieces.\r
3631        Not sure if needed, but can't hurt */\r
3632     XSynchronize(xDisplay, True); /* Work-around for xlib/xt buffering bug */\r
3633   \r
3634     /* Setup translations so piece colors match square colors */\r
3635     symbols[0].name = "light_piece";\r
3636     symbols[0].value = appData.whitePieceColor;\r
3637     symbols[1].name = "dark_piece";\r
3638     symbols[1].value = appData.blackPieceColor;\r
3639     symbols[2].name = "light_square";\r
3640     symbols[2].value = appData.lightSquareColor;\r
3641     symbols[3].name = "dark_square";\r
3642     symbols[3].value = appData.darkSquareColor;\r
3643 \r
3644     attr.valuemask = XpmColorSymbols;\r
3645     attr.colorsymbols = symbols;\r
3646     attr.numsymbols = 4;\r
3647 \r
3648     if (appData.monoMode) {\r
3649       DisplayFatalError("XPM pieces cannot be used in monochrome mode",\r
3650                         0, 2);\r
3651       ExitEvent(2);\r
3652     }\r
3653     if (strlen(appData.pixmapDirectory) == 0) {\r
3654         XpmPieces* pieces = builtInXpms;\r
3655         useImages = 1;\r
3656         /* Load pieces */\r
3657         while (pieces->size != squareSize && pieces->size) pieces++;\r
3658         if (!pieces->size) {\r
3659           fprintf(stderr, "No builtin XPM pieces of size %d\n", squareSize);\r
3660           exit(1);\r
3661         }\r
3662         for (piece = (int) WhitePawn; piece <= (int) WhiteKing; piece++) {\r
3663             for (kind=0; kind<4; kind++) {\r
3664 \r
3665                 if ((r=XpmCreatePixmapFromData(xDisplay, xBoardWindow,\r
3666                                                pieces->xpm[piece][kind],\r
3667                                                &(xpmPieceBitmap[kind][piece]),\r
3668                                                NULL, &attr)) != 0) {\r
3669                   fprintf(stderr, "Error %d loading XPM image \"%s\"\n",\r
3670                           r, buf);\r
3671                   exit(1); \r
3672                 }       \r
3673             }   \r
3674         }\r
3675         useImageSqs = 0;\r
3676         xpmJailSquare = xpmLightSquare;\r
3677     } else {\r
3678         useImages = 1;\r
3679         \r
3680         fprintf(stderr, "\nLoading XPMs...\n");\r
3681 \r
3682         /* Load pieces */\r
3683         for (piece = (int) WhitePawn; piece <= (int) WhiteKing; piece++) {\r
3684             fprintf(stderr, "%d ", piece+1);\r
3685             for (kind=0; kind<4; kind++) {\r
3686                 sprintf(buf, "%s/%c%s%u.xpm",\r
3687                         ExpandPathName(appData.pixmapDirectory),\r
3688                         ToLower(PieceToChar((ChessSquare)piece)),\r
3689                         xpmkind[kind], ss);\r
3690                 if (appData.debugMode) {\r
3691                     fprintf(stderr, "(File:%s:) ", buf);\r
3692                 }\r
3693                 if ((r=XpmReadFileToPixmap(xDisplay, xBoardWindow, buf,\r
3694                                            &(xpmPieceBitmap[kind][piece]),\r
3695                                  &