1 /*
2 **
3 **	X11 Jewel By David Cooper and Jose Guterman 05/92
4 **
5 */
6 
7 #ifdef VMS
8 #include <decw$include/Xlib.h>
9 #include <decw$include/Xutil.h>
10 #include <decw$include/Xos.h>
11 #else
12 #include <X11/Xlib.h>
13 #include <X11/Xutil.h>
14 #include <X11/Xos.h>
15 #endif
16 
17 #include "general.h"
18 #include "logic.h"
19 #include "hscore.h"
20 #include "xhscore.h"
21 #include "jewel.h"
22 #include "game.h"
23 #include "panel.h"
24 #include "xw.h"
25 
26 
27 /* util functions */
Key_Bell()28 void Key_Bell()
29 	{
30 	if (Sound())
31 		{ XBell(xw_display,100); }
32 	}
33 #define STRBUFSIZE 128
34 
35 
36 #include <stdlib.h>
37 #define RANDY(range) (random()%(range))
38 
Melt_Down()39 void Melt_Down()
40 	{
41 	int cycle;
42 	int offx,offy;
43 	int srcx,srcy, destx,desty;
44 	unsigned int width,height;
45 	unsigned int GWIDTH=NUM_COLS*SIZE_PIECE, GHEIGHT=NUM_ROWS*SIZE_PIECE;
46 
47 	struct timeval curtime;
48 	gettimeofday(&curtime,NULL);
49 	srandom((unsigned int)(curtime.tv_usec>>8));
50 
51 #define NUM_CYCLES 12
52 	for(cycle=0;cycle<NUM_CYCLES;cycle++)
53 	  for(srcy=1+cycle ;srcy<(GHEIGHT-10);srcy+=(SIZE_PIECE/2))
54 		{
55 		int count;
56 		for (count=0;count<((NUM_COLS*SIZE_PIECE)/40);count++)
57 			{
58 			offx=RANDY(5)-2;
59 			offy=RANDY(4)+1;
60 
61 			width=RANDY(GWIDTH/2);
62 			height=RANDY(GHEIGHT-srcy-offy);
63 
64 			/* MAXwidth+MAXoffx must be << GWIDTH */
65 			srcx=RANDY(GWIDTH-width-(abs(offx)));
66 			if (offx<0) { srcx-=offx; }
67 
68 			destx=srcx+offx;
69 			desty=srcy+offy;
70 			if (desty>(GHEIGHT-1)) break;
71 
72 			XCopyArea(xw_display,xw_window,xw_window,xw_gc,
73 				srcx+(BRD_LOC_X+SIZE_PIECE), srcy+BRD_LOC_Y,
74 				width,height,
75 				destx+(BRD_LOC_X+SIZE_PIECE),desty+BRD_LOC_Y);
76 			}
77 		}
78 	xw_sync_sleep(150L);
79 
80 	/* erase area */
81 #	define NUM_SCAT 10 /* SIZE_PIECE should be an integral mult of this */
82 	offx=RANDY(NUM_SCAT);
83 	offy=RANDY(NUM_SCAT);
84 	for (srcx=0; srcx < NUM_SCAT; srcx++)
85 		{
86 		static int xscat[NUM_SCAT]={ 1, 9, 3, 6, 2, 4, 0, 7, 5, 8 };
87 		static int yscat[NUM_SCAT]={ 2, 1, 0, 8, 6, 4, 9, 3, 7, 5 };
88 		for (srcy=0; srcy < NUM_SCAT; srcy++)
89 			{
90 			for (destx=0;destx<NUM_COLS;destx++)
91 			  for (desty=0;desty<NUM_ROWS;desty++)
92 				{
93 				/*XClearArea(xw_display,xw_window,*/
94 				XFillRectangle(xw_display,xw_window,PiecesGC[FLASH1],
95 					((destx+1)*SIZE_PIECE)+BRD_LOC_X+
96 						xscat[(srcx+srcy+offx)%NUM_SCAT]*(SIZE_PIECE/NUM_SCAT),
97 					((desty)*SIZE_PIECE)+BRD_LOC_Y+
98 						yscat[(srcy+offy)%NUM_SCAT]*(SIZE_PIECE/NUM_SCAT),
99 					(SIZE_PIECE/NUM_SCAT), (SIZE_PIECE/NUM_SCAT)/*,False*/);
100 				}
101 			}
102 		}
103 	xw_sync_sleep(150L);
104 	}
105 
106 
Draw_Piece(piece,x,y)107 void Draw_Piece(piece,x,y)
108 int piece, x, y;
109 	{
110 	/* draw piece at loc x,y */
111 	/* locations here are not raw board, but the active board */
112 	if (x<0)
113 		{
114 		XCopyPlane(xw_display, PiecesPM[piece], xw_window, PiecesGC[piece],
115 			0, 0, SIZE_PIECE, SIZE_PIECE,
116 			PREV_LOC_X+(SIZE_PIECE*1), PREV_LOC_Y+(SIZE_PIECE*(y+1)), 1L);
117 		}
118 	else
119 		{
120 		XCopyPlane(xw_display, PiecesPM[piece], xw_window, PiecesGC[piece],
121 			0, 0, SIZE_PIECE, SIZE_PIECE,
122 			BRD_LOC_X+(SIZE_PIECE*(x+1)), BRD_LOC_Y+(SIZE_PIECE*y), 1L);
123 		}
124 	}
125 
126 
Flash_Pieces(p_remove,numflash,background)127 void Flash_Pieces(p_remove, numflash, background)
128 struct rem_piece p_remove[];
129 int numflash,background;
130 	{
131 #ifndef SLOW_DRAW
132 #  define SLOW_DRAW 0
133 #endif
134 	int reps;
135 	int findex;
136 
137 	for (reps=0;reps<NUM_FLASH;reps++)
138 		{
139 		for (findex=0;findex < numflash;findex++)
140 			{
141 			Draw_Piece(FLASH1+reps, p_remove[findex].x, p_remove[findex].y);
142 			}
143 		xw_sync_sleep(70L+SLOW_DRAW);
144 		for (findex=0;findex < numflash;findex++)
145 			{
146 			Draw_Piece(p_remove[findex].piece,
147 				p_remove[findex].x, p_remove[findex].y);
148 			}
149 		xw_sync_sleep(160L+SLOW_DRAW);
150 		}
151 	for (findex=0;findex < numflash;findex++)
152 		{
153 		Draw_Piece(background, p_remove[findex].x, p_remove[findex].y);
154 		}
155 	xw_sync_sleep(100L+SLOW_DRAW);
156 	}
157 
Redraw_Add_Score(pts,mult)158 void Redraw_Add_Score(pts,mult)
159 int pts, mult;
160 	{
161 #ifndef SLOW_FONTS
162 #   define SLOW_FONTS 0
163 #endif
164 	char buf[80];
165 	int y=SCORE_LOC_Y;
166 	XCharStruct Sizes;
167 	int dir, asc, dsc;
168 	/* write points */
169 	sprintf(buf,"POINTS");
170 	XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
171 		buf, strlen(buf));
172 	sprintf(buf,"%d",pts);
173 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
174 	XDrawImageString(xw_display, xw_window, ScoreGC,
175 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
176 	y+=Score_Char_MHeight;
177 
178 	/* write multiple */
179 	sprintf(buf,"X");
180 	XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
181 		buf, strlen(buf));
182 	sprintf(buf,"%d",mult);
183 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
184 	XDrawImageString(xw_display, xw_window, ScoreGC,
185 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
186 	y+=Score_Char_MHeight;
187 
188 	/* wait a while */
189 	xw_sync_sleep(160L+SLOW_FONTS);
190 
191 	/* put total points up */
192 	y=SCORE_LOC_Y;
193 	sprintf(buf,"%6d",(pts * mult));
194 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
195 	XDrawImageString(xw_display, xw_window, ScoreGC,
196 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
197 
198 	for (y=SCORE_LOC_Y+1; y<(SCORE_LOC_Y + (Score_Char_MHeight*2)) ; y++)
199 			/* location of SCORE */
200 		{
201 		char *buf2="POINTS ";
202 		XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
203 			buf2, strlen(buf2));
204 		XDrawImageString(xw_display, xw_window, ScoreGC,
205 			(Score_x_right - Sizes.width), y, buf, strlen(buf));
206 		if (SLOW_FONTS > 0)
207 		    {
208 		    xw_sync_sleep(10L+SLOW_FONTS);
209 		    /* IF THE X-SERVER IS FAST WITH FONTS */
210 		    }
211 		}
212 	xw_sync_sleep(110L+SLOW_FONTS);
213 	}
214 
215 
Redraw_Score(Score)216 void Redraw_Score(Score)
217 int Score;
218 	{
219 	char buf[80];
220 	XCharStruct Sizes;
221 	int dir, asc, dsc;
222 	int y=SCORE_LOC_Y + (Score_Char_MHeight*2);
223 	/* write Score */
224 	sprintf(buf,"SCORE  ");
225 	XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
226 		buf, strlen(buf));
227 	sprintf(buf,"%d",Score);
228 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
229 	XDrawImageString(xw_display, xw_window, ScoreGC,
230 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
231 	y+=Score_Char_MHeight;
232 	}
233 
Redraw_Lives(Lives)234 void Redraw_Lives(Lives)
235 int Lives;
236 	{
237 	char buf[80];
238 	XCharStruct Sizes;
239 	int dir, asc, dsc;
240 	int y=SCORE_LOC_Y + (Score_Char_MHeight*3);
241 	/* write Lives */
242 	sprintf(buf,"LIVES  ");
243 	XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
244 		buf, strlen(buf));
245 	sprintf(buf,"%d",Lives);
246 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
247 	XDrawImageString(xw_display, xw_window, ScoreGC,
248 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
249 	y+=Score_Char_MHeight;
250 	}
251 
Redraw_Speed(Speed)252 void Redraw_Speed(Speed)
253 float Speed;
254 	{
255 	char buf[80];
256 	XCharStruct Sizes;
257 	int dir, asc, dsc;
258 	int y=SCORE_LOC_Y + (Score_Char_MHeight*4);
259 	/* write Speed */
260 	sprintf(buf,"SPEED  ");
261 	XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
262 		buf, strlen(buf));
263 	sprintf(buf,"%.5f",Speed);
264 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
265 	XDrawImageString(xw_display, xw_window, ScoreGC,
266 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
267 	y+=Score_Char_MHeight;
268 	}
269 
270 
Redraw_Stage(Stage)271 void Redraw_Stage(Stage)
272 int Stage;
273 	{
274 	char buf[80];
275 	XCharStruct Sizes;
276 	int dir, asc, dsc;
277 	int y=SCORE_LOC_Y + (Score_Char_MHeight*5);
278 	/* write Stage */
279 	sprintf(buf,"STAGE  ");
280 	XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
281 		buf, strlen(buf));
282 	sprintf(buf," %d",Stage);
283 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
284 	XDrawImageString(xw_display, xw_window, ScoreGC,
285 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
286 	y+=Score_Char_MHeight;
287 	}
288 
289 
Redraw_Rest(Rest)290 void Redraw_Rest(Rest)
291 int Rest;
292 	{
293 	char buf[80];
294 	XCharStruct Sizes;
295 	int dir, asc, dsc;
296 	int y=SCORE_LOC_Y + (Score_Char_MHeight*6);
297 	/* write Rest */
298 	sprintf(buf,"REST  ");
299 	XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
300 		buf, strlen(buf));
301 	sprintf(buf,"  %d",Rest);
302 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
303 	XDrawImageString(xw_display, xw_window, ScoreGC,
304 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
305 	y+=Score_Char_MHeight;
306 	}
307 
Redraw_Sound()308 void Redraw_Sound()
309 	{
310 	char buf[80];
311 	XCharStruct Sizes;
312 	int dir, asc, dsc;
313 	int y=SCORE_LOC_Y + (Score_Char_MHeight*7);
314 	/* write Sound */
315 	sprintf(buf,"SOUND ");
316 	XDrawImageString(xw_display, xw_window, ScoreGC, SCORE_LOC_X, y,
317 		buf, strlen(buf));
318 	sprintf(buf,"%s",((Sound()) ? "  ON" : "OFF"));
319 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
320 	XDrawImageString(xw_display, xw_window, ScoreGC,
321 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
322 	y+=Score_Char_MHeight;
323 	}
324 
Redraw_Pause()325 void Redraw_Pause()
326 	{
327 	char buf[80];
328 	XCharStruct Sizes;
329 	int dir, asc, dsc;
330 	int y=SCORE_LOC_Y + (Score_Char_MHeight*8);
331 	/* write Pause */
332 	if (Paused())
333 		{ sprintf(buf,"PAUSED"); }
334 	else
335 		{ sprintf(buf,"            "); }
336 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
337 	XDrawImageString(xw_display, xw_window, ScoreGC,
338 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
339 	}
340 
Redraw_Game_Board()341 void Redraw_Game_Board()
342 	{
343 	int x,y;
344 	/* build border */
345 	for (y=0;y<BOARD_HEIGHT;y++)
346 		{
347 		XCopyPlane(xw_display, BorderPM, xw_window, BorderGC, 0, 0,
348 			Border_Width, Border_Height,
349 			BRD_LOC_X, BRD_LOC_Y+(SIZE_PIECE*y),1L);
350 		XCopyPlane(xw_display, BorderPM, xw_window, BorderGC, 0, 0,
351 			Border_Width, Border_Height,
352 			BRD_LOC_X+(SIZE_PIECE*(BOARD_WIDTH-1)), BRD_LOC_Y+(SIZE_PIECE*y),1L);
353 		}
354 	for (x=1;x<(BOARD_WIDTH-1);x++)
355 		{
356 		XCopyPlane(xw_display, BorderPM, xw_window, BorderGC, 0, 0,
357 			Border_Width, Border_Height,
358 			BRD_LOC_X+(SIZE_PIECE*x),BRD_LOC_Y+(SIZE_PIECE*(BOARD_HEIGHT-1)),1L);
359 		}
360 	for (x=0;x<(PREVIEW_WIDTH);x++)
361 	  for (y=0;y<(PREVIEW_HEIGHT);y++)
362 		{
363 		XCopyPlane(xw_display, BorderPM, xw_window, BorderGC, 0, 0,
364 			Border_Width, Border_Height,
365 			PREV_LOC_X+(SIZE_PIECE*x),PREV_LOC_Y+(SIZE_PIECE*y),1L);
366 		}
367 	/* put pieces on it */
368 	Redraw_Board();
369 	}
370 
Start_New_Game()371 void Start_New_Game()
372 	{
373 	extern void Expose_Game();
374 	XClearWindow(xw_display,xw_window);
375 	xw_set_timer(Get_Speed_ms());
376 	JewelState=GAME;
377 	New_Game();
378 	Init_Logic();
379 	Expose_Game();
380 	}
381 
End_Game()382 void End_Game()
383 	{
384 	char *buf;
385 	XCharStruct Sizes;
386 	int dir, asc, dsc;
387 	int y=SCORE_LOC_Y + (Score_Char_MHeight*8);
388 
389 	buf="GAME OVER";
390 	XTextExtents(ScoreFont,buf,strlen(buf),&dir,&asc,&dsc,&Sizes);
391 	XDrawImageString(xw_display, xw_window, ScoreGC,
392 		(Score_x_right - Sizes.width), y, buf, strlen(buf));
393 
394 	xw_sync_sleep(500L);
395 	Set_State_High_Score();
396 	Update_High_Scores(Get_Stage(), Get_Score());
397 	}
398 
399 
Expose_Game()400 void Expose_Game()
401 	{
402 	XCopyPlane(xw_display, Logo2PM, xw_window, Logo2GC, 0, 0,
403 		Jewellogo2_Width, Jewellogo2_Height,
404 		LOGO_LOC_X, LOGO_LOC_Y, 1L);
405 
406 	XSetClipOrigin(xw_display, LogoGC, LOGO_LOC_X, LOGO_LOC_Y );
407 	XCopyPlane(xw_display, LogoPM, xw_window, LogoGC, 0, 0,
408 		Jewellogo_Width, Jewellogo_Height,
409 		LOGO_LOC_X, LOGO_LOC_Y, 1L);
410 
411 	XDrawImageString(xw_display, xw_window, VerGC, VER_LOC_X,
412 		VER_LOC_Y+((VerFont->ascent)*3/2),
413 		VerString, strlen(VerString));
414 
415 	Redraw_Text();
416 	Redraw_Game_Board();
417 	XFlush(xw_display);
418 	}
419 
Game_Timeout()420 void Game_Timeout()
421 	{
422 	if (!Paused())
423 		{
424 		Logic_Timeout();
425 		XFlush(xw_display);
426 		}
427 	if (JewelState==GAME)
428 		{ xw_set_timer(Get_Speed_ms()); }
429 	}
430