1 /* Copyright (C) 1993, 1992 Nathan Sidwell */ 2 /* RCS $Id: makemris.c,v 4.20 1995/12/21 15:55:04 nathan Exp $ */ 3 /*{{{ includes*/ 4 #include "xmris.h" 5 #include "defmris.h" 6 #include <X11/Xaw/Form.h> 7 #include <X11/Xaw/Paned.h> 8 #include <X11/Xaw/Simple.h> 9 #include "makecom.c" 10 /*}}}*/ 11 /*{{{ tables*/ 12 /*{{{ static color*/ 13 static struct 14 { 15 unsigned backgrounds; /* normal background */ 16 unsigned current[2][3]; /* current colors */ 17 int state; /* type of colors */ 18 unsigned busy; /* not arrived at target */ 19 unsigned whizz; /* whizz value */ 20 unsigned count; /* delay count */ 21 } color; /* color information */ 22 /*}}}*/ 23 /*{{{ static Arg toplevel_args[] =*/ 24 static Arg toplevel_args[] = 25 { 26 {XtNinput, True}, 27 }; 28 /*}}}*/ 29 /*}}}*/ 30 /*{{{ prototypes*/ 31 static Boolean convert_string2keysym PROTOARG((Display *, XrmValue *, 32 Cardinal *, XrmValue *, XrmValue *, XtPointer *)); 33 /*}}}*/ 34 /*{{{ Boolean convert_string2keysym(display, args, num_args, from, to, data)*/ 35 static Boolean convert_string2keysym 36 /* ARGSUSED */ 37 FUNCARG((display, args, num_args, from, to, data), 38 Display *display 39 ARGSEP XrmValue *args 40 ARGSEP Cardinal *num_args 41 ARGSEP XrmValue *from 42 ARGSEP XrmValue *to 43 ARGSEP XtPointer *data 44 ) 45 /* 46 * converts a key name string to a key code 47 */ 48 { 49 static KeySym keysym; 50 51 if(to->size < sizeof(KeySym)) 52 { 53 to->size = sizeof(KeySym); 54 return False; 55 } 56 keysym = XStringToKeysym((char CONST *)from->addr); 57 if(keysym != NoSymbol) 58 { 59 to->size = sizeof(KeySym); 60 if(to->addr) 61 *(KeySym *)to->addr = keysym; 62 else 63 to->addr = (XtPointer)&keysym; 64 return True; 65 } 66 else 67 { 68 XtDisplayStringConversionWarning(display, from->addr, XtRKeySym); 69 return False; 70 } 71 } 72 /*}}}*/ 73 /*{{{ void create_widget()*/ 74 extern VOIDFUNC create_widget FUNCARGVOID 75 /* 76 * Create the graphics contexts, sprites and colours and stuff. 77 * sets visual and stuff for the toplevel widget 78 */ 79 { 80 display.form = XtVaCreateManagedWidget("form", formWidgetClass, 81 display.toplevel, XtNdefaultDistance, (XtArgVal)0, (String)NULL); 82 display.garden = XtVaCreateManagedWidget(&names[data.gender != False][1], 83 simpleWidgetClass, display.form, XtNwidth, (XtArgVal)WINDOW_WIDTH, 84 XtNheight, (XtArgVal)WINDOW_HEIGHT, (String)NULL); 85 create_resources(display.garden); 86 assert(!(VEL_X_FAST * FAST_STEPS * 2 % VEL_X)); 87 assert(!(VEL_Y_FAST * FAST_STEPS * 2 % VEL_Y)); 88 return; 89 } 90 /*}}}*/ 91 /*{{{ void color_cycle()*/ 92 extern VOIDFUNC color_cycle FUNCARGVOID 93 /* 94 * Moves the background colors towards their targets. Called during 95 * each animation cycle, and programmed by color_set. 96 */ 97 { 98 if(color.busy) 99 { 100 assert(display.dynamic); 101 if(!color.count--) 102 { 103 unsigned target[3]; 104 unsigned ix; 105 106 color.count = WHIZZ_CYCLES - 1; 107 color.busy = 0; 108 for(ix = 2; ix--;) 109 { 110 /*{{{ set target*/ 111 if(color.state == BACKGROUND_WHIZZ) 112 /*{{{ set whizz target*/ 113 { 114 unsigned cycle, offset; 115 unsigned a, b, c; 116 117 color.busy = 1; 118 offset = color.whizz % WHIZZ_STEPS * WHIZZ_SIZE; 119 cycle = color.whizz / WHIZZ_STEPS; 120 if(cycle & 1) 121 a = 0xFFFF - offset, b = 0xFFFF, c = 0; 122 else 123 a = 0xFFFF, b = offset, c = 0; 124 if(cycle / 2 == 1) 125 c = b, b = a, a = 0; 126 else if(cycle / 2 == 2) 127 c = a, a = b, b = 0; 128 target[0] = a; 129 target[1] = b; 130 target[2] = c; 131 if(ix) 132 for(cycle = 3; cycle--;) 133 target[cycle] ^= 0xFFFF; 134 } 135 /*}}}*/ 136 else 137 /*{{{ set drone or normal target*/ 138 { 139 XColor *sptr; 140 141 sptr = &colors[backgrounds[color.state == 142 BACKGROUND_DRONES ? BACKGROUNDS : 143 color.backgrounds][ix]]; 144 target[0] = sptr->red; 145 target[1] = sptr->green; 146 target[2] = sptr->blue; 147 } 148 /*}}}*/ 149 /*}}}*/ 150 /*{{{ move*/ 151 { 152 unsigned gun; 153 unsigned *tptr, *cptr; 154 155 for(tptr = target, cptr = color.current[ix], gun = 3; 156 gun--; tptr++, cptr++) 157 if(*tptr > *cptr) 158 { 159 if(*tptr - *cptr <= WHIZZ_SIZE) 160 *cptr = *tptr; 161 else 162 { 163 *cptr += WHIZZ_SIZE; 164 color.busy = 1; 165 } 166 } 167 else if(*tptr < *cptr) 168 { 169 if(*cptr - *tptr <= WHIZZ_SIZE) 170 *cptr = *tptr; 171 else 172 { 173 *cptr -= WHIZZ_SIZE; 174 color.busy = 1; 175 } 176 } 177 } 178 /*}}}*/ 179 /*{{{ store*/ 180 { 181 XColor *cptr; 182 unsigned *sptr; 183 184 sptr = color.current[ix]; 185 cptr = &colors[COLOR_DYNAMIC + ix]; 186 cptr->red = sptr[0]; 187 cptr->green = sptr[1]; 188 cptr->blue = sptr[2]; 189 cptr->flags = DoRed | DoGreen | DoBlue; 190 XStoreColor(display.display, display.colormap, cptr); 191 } 192 /*}}}*/ 193 } 194 color.whizz = (color.whizz + 1) % (6 * WHIZZ_STEPS); 195 } 196 } 197 return; 198 } 199 /*}}}*/ 200 /*{{{ void color_set(type)*/ 201 extern VOIDFUNC color_set 202 FUNCARG((type), 203 int type 204 ) 205 /* 206 * Set the board background colours to be what they ought. 207 * either one of the BACKGROUND_ specials, or a background index. 208 * color_cycle actually sets the color for us. 209 */ 210 { 211 if(display.dynamic) 212 { 213 color.count = 0; 214 if(type < 0 || type >= BACKGROUNDS) 215 color.state = type; 216 else 217 { 218 color.state = BACKGROUND_NORMAL; 219 color.backgrounds = type; 220 } 221 color.busy = 1; 222 } 223 return; 224 } 225 /*}}}*/ 226 /*{{{ void open_toolkit(arc, argv)*/ 227 extern VOIDFUNC open_toolkit 228 FUNCARG((argc, argv), 229 int argc 230 ARGSEP String *argv 231 ) 232 { 233 #if !__STDC__ 234 /*{{{ K&R string fixups*/ 235 { 236 char *ptr; 237 238 ptr = XtMalloc(strlen(XMRISVERSION) + strlen(DATE) + 239 strlen(title_text[0].text)); 240 sprintf(ptr, title_text[0].text, XMRISVERSION, DATE); 241 title_text[0].text = ptr; 242 } 243 /*}}}*/ 244 #endif /* __STDC__ */ 245 extract_options(&argc, argv, command_options); 246 default_gender = GAME_GENDER; 247 /*{{{ determine gender of the game*/ 248 if(*argv) 249 { 250 size_t length; 251 unsigned ix; 252 char CONST *ptr; 253 254 for(ptr = *argv + strlen(*argv); ptr != *argv && *ptr != '/'; ptr--) 255 /* EMPTY */; 256 if(*ptr == '/') 257 ptr++; 258 for(length = 0; ptr[length] && ptr[length] != '.'; length++) 259 /* EMPTY */; 260 for(ix = 2; ix--;) 261 { 262 size_t other; 263 264 other = strlen(&names[ix][1]); 265 if(length >= other && 266 !strncmp(&ptr[length - other], &names[ix][1], other)) 267 default_gender = ix; 268 } 269 } 270 /*}}}*/ 271 if(data.help == False) 272 /*{{{ more setup*/ 273 { 274 if(data.nodisplay == False) 275 { 276 XrmOptionDescRec CONST *ptr; 277 278 /* as options is an extern of unknown size, I can't use 279 * XtNumber() to get its size, so I've done it this way 280 */ 281 for(ptr = options; *(char CONST **)ptr; ptr++) 282 /* EMPTY */; 283 display.toplevel = XtAppInitialize(&display.context, "Xmris", 284 options, (Cardinal)(ptr - options), 285 (Cardinal *)&argc, (String *)argv, 286 (String *)NULL, toplevel_args, XtNumber(toplevel_args)); 287 } 288 if(argc > 1) 289 /*{{{ error*/ 290 { 291 unsigned ix; 292 293 data.help = True; 294 data.colors = False; 295 fprintf(stderr, "%s: Unknown option%s:", argv[0], 296 argc > 2 ? "s" : ""); 297 for(ix = 1; ix != argc; ix++) 298 fprintf(stderr, "%s %s", ix == 1 ? "" : ",", argv[ix]); 299 fputc('\n', stderr); 300 } 301 /*}}}*/ 302 else if(data.nodisplay != False) 303 { 304 if(data.scores == False && !data.expire && 305 !data.remove && !data.format) 306 fatal_error("-nodisplay must be accompanied by -scores, -expire, -remove or -format"); 307 } 308 else 309 /*{{{ some more setup*/ 310 { 311 XtResource CONST *ptr; 312 char CONST *dir; 313 314 XtAppSetTypeConverter(display.context, XtRString, XtRKeySym, 315 convert_string2keysym, (XtConvertArgRec *)NULL, 0, XtCacheNone, 316 (void (*)PROTOARG((XtAppContext, XrmValue *, XtPointer, 317 XrmValue *, Cardinal *)))NULL); 318 XtAppSetTypeConverter(display.context, XtRString, XtRGender, 319 convert_string2gender, (XtConvertArgRec *)NULL, 0, XtCacheNone, 320 (void (*)PROTOARG((XtAppContext, XrmValue *, XtPointer, 321 XrmValue *, Cardinal *)))NULL); 322 display.display = XtDisplay(display.toplevel); 323 dir = data.dir; 324 for(ptr = resources; *(char CONST **)ptr; ptr++) 325 /* EMPTY */; 326 XtGetApplicationResources(display.toplevel, (XtPointer)&data, 327 resources, (Cardinal)(ptr - resources), (Arg *)NULL, 0); 328 if(dir) 329 data.dir = dir; 330 gettoplevelresources(); 331 XtVaSetValues(display.toplevel, 332 XtNtitle, (XtArgVal)names[data.gender != False], 333 XtNiconName, (XtArgVal)names[data.gender != False], 334 NULL); 335 { 336 XKeyboardState keyboard; 337 338 XGetKeyboardControl(display.display, &keyboard); 339 display.repeat = keyboard.global_auto_repeat; 340 } 341 } 342 /*}}}*/ 343 if(!data.dir) 344 data.dir = (char *)resources[0].default_addr; 345 } 346 /*}}}*/ 347 return; 348 } 349 /*}}}*/ 350