1 /*
2 // Xtruco
3 // Card Game
4 */
5
6 #include "xbook.h"
7 #include <stdlib.h>
8 #include <time.h>
9 #include <sys/types.h>
10 #include <sys/ipc.h>
11 #include <sys/shm.h>
12
13 #include "truco.xb"
14 #include "cards.xbm"
15
16 #define MAX_PIX 30
17 #define TOTAL 42
18 #define BACK 40
19 #define MAXIMO 12
20 #define YES 88
21 #define NO 89
22 #define NEW 99
23 #define WAITING 91
24 #define ERR_TRUCO 666
25
26 typedef struct
27 {
28 Pixmap bitmap;
29 int x, y;
30 int width, height;
31 } BIT_STRUCT;
32
33 typedef struct
34 {
35 int x, y;
36 int val_score;
37 } TYPE_SCORE;
38
39 struct {
40 int what;
41 int card_state;
42 int val_score;
43 int X;
44 int Y;
45 } Table[9];
46
47 struct {
48 int number_of_trucos; /* alguns ainda nao utilizados */
49 int first_truco;
50 int second_truco;
51 int third_truco;
52 int lying;
53 int time_seconds;
54 int analisys;
55 } info={ 0, 0, 0, 0, 0, 8, 1};
56
57 BIT_STRUCT the_bitmaps[ MAX_PIX ];
58 TYPE_SCORE score[ 2 ]={{0,0,0},{0,0,0}};
59
60 int horiz, vert;
61 int State=0, Message=0, Cards[40];
62 char Messa[80];
63 static unsigned char *CarBit[TOTAL];
64 static unsigned long black, white, green, blue, red, navy;
65 Pixmap bitmap1;
66 int pc, you, Who_Play, You_Play, first, MyScore, YouScore;
67 int alert, Sum_Val, ValGame, danger, Begining;
68 int Play, Beginer, Who_Say_Truco,score1, score2;
69 int SHOW=1;
70 void Refresh(Display *, Window, GC, Pixmap, int, int, int, int);
71
main(argc,argv)72 main( argc, argv )
73 int argc;
74 char *argv[];
75 {
76 Display *display;
77 int screen;
78 Window rootwindow, window;
79 int x, y, width, height;
80 XFontStruct *font;
81 Pixmap icon, pixmap;
82 GC pixgc, gc;
83 int num_bitmaps, font_height, position, fator;
84 Colormap colormap;
85 int shmid, size, shmflg;
86 key_t key;
87 char * shmaddr;
88
89 #ifdef IPC_OK
90 size= 3600*sizeof( unsigned char *);
91 key= IPC_PRIVATE;
92 shmflg= IPC_CREAT;
93 shmid= shmget( key, size, shmflg );
94 shmflg |= 0x1ff;
95 shmat( shmid, shmaddr, shmflg );
96 #endif
97 CarBit[0]= card1_bits;CarBit[1]= card2_bits;CarBit[2]= card3_bits;
98 CarBit[3]= card4_bits;CarBit[4]= card5_bits;CarBit[5]= card6_bits;
99 CarBit[6]= card7_bits;CarBit[7]= card8_bits;CarBit[8]= card9_bits;
100 CarBit[9]= card10_bits;CarBit[10]= card11_bits;CarBit[11]= card12_bits;
101 CarBit[12]= card13_bits;CarBit[13]= card14_bits;CarBit[14]= card15_bits;
102 CarBit[15]= card16_bits;CarBit[16]= card17_bits;CarBit[17]= card18_bits;
103 CarBit[18]= card19_bits;CarBit[19]= card20_bits;CarBit[20]= card21_bits;
104 CarBit[21]= card22_bits;CarBit[22]= card23_bits;CarBit[23]= card24_bits;
105 CarBit[24]= card25_bits;CarBit[25]= card26_bits;CarBit[26]= card27_bits;
106 CarBit[27]= card28_bits;CarBit[28]= card29_bits;CarBit[29]= card30_bits;
107 CarBit[30]= card31_bits;CarBit[31]= card32_bits;CarBit[32]= card33_bits;
108 CarBit[33]= card34_bits;CarBit[34]= card35_bits;CarBit[35]= card36_bits;
109 CarBit[36]= card37_bits;CarBit[37]= card38_bits;CarBit[38]= card39_bits;
110 CarBit[39]= card40_bits;CarBit[40]= card41_bits;CarBit[41]= card42_bits;
111 for(x=0;x<40;x++) Cards[x]=x+1;
112 x = 10;
113 y = 10;
114 width=640;
115 height= 480;
116 display = SetUpDisplay( argc, argv, &screen );
117 rootwindow= RootWindow( display, screen );
118 black = BlackPixel( display, screen );
119 white = WhitePixel( display, screen );
120 colormap = DefaultColormap( display, screen );
121 blue = GetColor( display, "gray", colormap, white );
122 green = GetColor( display, "darkgreen", colormap, 2L );
123 red = GetColor( display, "red", colormap, white );
124 navy = GetColor( display, "darkblue", colormap, black );
125 horiz = width;
126 vert = height;
127 fator = horiz/6;
128 for(position=0;position<3;position++)
129 {
130 Table[position].X= Table[position+3].X= fator*(position+1);
131 Table[position].Y= 25;
132 Table[position+3].Y= vert - 160;
133 }
134 Table[6].X= fator*5;
135 Table[6].Y= (Table[0].Y+Table[3].Y)/2;
136 Table[7].X= Table[0].X+36;
137 Table[7].Y= (Table[0].Y+Table[3].Y)/2;
138 Table[8].X= Table[2].X-36;
139 Table[8].Y= (Table[2].Y+Table[3].Y)/2;
140 num_bitmaps = 0;
141 pixmap = CreatePixmap( display, rootwindow, width,
142 height, DefaultDepth( display, screen ),
143 black, green, &pixgc );
144 XFreeGC( display, pixgc );
145 CheckGeometry( argc, argv, DisplayWidth( display, screen ),
146 DisplayHeight( display, screen ),
147 &x, &y, &width, &height );
148 window = TopWindow( display, x, y, width, height,
149 super_bits, super_width, super_height,
150 &icon, &gc );
151 font = LoadFont( display, gc, argc, argv, "variable" );
152 font_height = (font->ascent + font->descent);
153 SetNormalHints( display, window, x, y, width, height );
154 SetWMHints( display, window, icon );
155 NameWindow( display, window, "Super Truco", "Super Truco", "Super Truco" );
156 MakeButtons( display, window, gc, white, navy, font->fid );
157 MapWindow( display, window );
158 while( EventLoop( display, window, pixmap, gc,
159 &width, &height ) == True );
160 XFreePixmap( display, pixmap );
161 XFreePixmap( display, icon );
162 CloseDisplay( display, window, gc );
163 #ifdef IPC_OK
164 shmdt( shmaddr );
165 #endif
166 exit( 0 );
167 }
168
Draw_Cards(display,rootwindow,pixmap,pixgc,card,posx,posy)169 Draw_Cards(display, rootwindow, pixmap, pixgc, card, posx, posy )
170 Display *display;
171 Window rootwindow;
172 Pixmap pixmap;
173 GC pixgc;
174 int card, posx, posy;
175 {
176 bitmap1 = XCreateBitmapFromData( display, rootwindow,
177 CarBit[card], CARD_WIDTH, CARD_HEIGHT );
178 if((card%2)==0)
179 XSetForeground( display, pixgc, red );
180 else
181 XSetForeground( display, pixgc, black );
182 XSetBackground( display, pixgc, white );
183 XCopyPlane( display, bitmap1,
184 pixmap, pixgc, 0, 0,
185 CARD_WIDTH,
186 CARD_HEIGHT,
187 posx,
188 posy,
189 0x01 );
190 XFreePixmap( display, bitmap1 );
191 }
192
First_Openning(display,rootwindow,pixmap,pixgc,type)193 First_Openning(display, rootwindow, pixmap, pixgc, type )
194 Display *display;
195 Window rootwindow;
196 Pixmap pixmap;
197 GC pixgc;
198 int type;
199 {
200 Pixmap bitmap1;
201
202 bitmap1 = XCreateBitmapFromData( display, rootwindow,
203 super_bits, super_width, super_height );
204 if(type!=0)
205 XSetBackground( display, pixgc, green );
206 else
207 XSetBackground( display, pixgc, red );
208 XSetForeground( display, pixgc, green );
209 XCopyPlane( display, bitmap1,
210 pixmap, pixgc, 0, 0,
211 super_width,
212 super_height,
213 (horiz/2)-(super_width/2),
214 (vert/2)-(super_height/2),
215 0x01 );
216 XFreePixmap( display, bitmap1 );
217 Refresh( display, rootwindow, pixgc, pixmap, (horiz/2)-(super_width/2),
218 (vert/2)-(super_height/2), super_width, super_height );
219 }
220
DrawPartCards(display,rootwindow,pixmap,pixgc,card,posx,posy,width)221 DrawPartCards(display, rootwindow, pixmap, pixgc, card, posx, posy, width )
222 Display *display;
223 Window rootwindow;
224 Pixmap pixmap;
225 GC pixgc;
226 int card, posx, posy, width;
227 {
228 bitmap1 = XCreateBitmapFromData( display, rootwindow,
229 CarBit[card], CARD_WIDTH, CARD_HEIGHT );
230 if((card%2)==0)
231 XSetForeground( display, pixgc, red );
232 else
233 XSetForeground( display, pixgc, black );
234 XSetBackground( display, pixgc, white );
235 XCopyPlane( display, bitmap1,
236 pixmap, pixgc, 0, 0,
237 width,
238 CARD_HEIGHT,
239 posx,
240 posy,
241 0x01 );
242 XFreePixmap( display, bitmap1 );
243 }
244
ClearCard(display,rootwindow,pixmap,pixgc,posx,posy,width)245 ClearCard(display, rootwindow, pixmap, pixgc, posx, posy, width )
246 Display *display;
247 Window rootwindow;
248 Pixmap pixmap;
249 GC pixgc;
250 int width;
251 {
252 bitmap1 = XCreateBitmapFromData( display, rootwindow,
253 CarBit[0], CARD_WIDTH, CARD_HEIGHT );
254
255 XSetForeground( display, pixgc, green );
256 XSetBackground( display, pixgc, green );
257 XCopyPlane( display, bitmap1,
258 pixmap, pixgc, 0, 0,
259 width,
260 CARD_HEIGHT,
261 posx,
262 posy,
263 0x01 );
264 XFreePixmap( display, bitmap1 );
265 }
266
EventLoop(display,window,pixmap,gc,width,height)267 EventLoop( display, window, pixmap, gc, width, height )
268 Display *display;
269 Window window;
270 Pixmap pixmap;
271 GC gc;
272 int *width, *height;
273 {
274 XEvent event;
275 KeySym keysym;
276 static int what=0;
277 int status=False;
278 int Last_State=0, position, resulters;
279 struct timeval timer1, timer2;
280 struct timezone zone;
281
282 if((status= CheckEvent( display, True, *width, *height,
283 &event, &keysym ))==True)
284 {
285 Last_State= State;
286 if( ButtonEvent( display, &event ) == True )
287 {
288 if( State==200)
289 return( False );
290 }
291 else if( InvEvent( display, &event ) == True )
292 {
293 if( State==200)
294 return( False );
295 }
296 }
297 switch(State)
298 {
299 case 0:
300 First_Openning(display, window, pixmap, gc, 0 );
301 State=WAITING;
302 break;
303 case NEW:
304 sprintf(Messa, "Starting a new game...");
305 TalkMachine( display, window, gc, Messa, 0 );
306 if(Last_State==2)
307 Cuting(display, window, pixmap, gc, BACK, 480 );
308 First_Openning(display, window, pixmap, gc, 1 );
309 score[0].val_score=0; score[1].val_score=0;
310 DrawScore( display, window, pixmap, gc, blue,
311 white, white, 10 , horiz, vert, score );
312 case 1:
313 TalkMachine( display, window, gc, Messa, 1 );
314 for(what=0;what<9;what++) Table[what].card_state=0;
315 TableCards( display, window, pixmap, gc, BACK );
316 strcpy(Messa, "Please, CUT...");
317 TalkMachine( display, window, gc, Messa, 0 );
318 ShowCards(display, window, pixmap, gc, BACK );
319 Message=Last_State=0;
320 State=2;
321 break;
322 case 2:
323 if((Message==4) || (Message==40))
324 {
325 TalkMachine( display, window, gc, Messa, 1 );
326 what=event.xbutton.x;
327 Cuting(display, window, pixmap, gc, BACK, what );
328 TableCards( display, window, pixmap, gc, BACK );
329 strcpy(Messa, "Let's go...");
330 if(Beginer==1) State=3; else State=4;
331 if((MyScore==MAXIMO-1) && (YouScore<11))
332 State=6;
333 else if((YouScore==MAXIMO-1) && (MyScore<11))
334 {
335 Sum_Val=2; State=5;
336 strcpy(Messa, "Will Yoy go play?...");
337 }
338 TalkMachine( display, window, gc, Messa, 0 );
339 Message=0;
340 }
341 break;
342 case 3:
343 if((Message==5) && (Who_Say_Truco!=2))
344 {
345 State=6;
346 Who_Say_Truco=2;
347 ValGame+= Sum_Val;
348 Sum_Val=0;
349 }
350 else if((Message==1) || (Message==2) || (Message==3)
351 || (Message==10) || (Message==20) || (Message==30))
352 {
353 ValGame+= Sum_Val;
354 Sum_Val=0;
355 if(Message<10)
356 {
357 you=Table[6+Play].val_score
358 =Table[Message+2].val_score;
359 Table[6+Play].what= Table[Message+2].what;
360 Table[6+Play].card_state=2;
361 Table[Message+2].card_state=0;
362 }
363 else
364 {
365 Table[Message/10+2].card_state=0;
366 you=Table[6+Play].val_score =0;
367 Table[6+Play].card_state=1;
368 }
369 TableCards( display, window, pixmap, gc, BACK );
370 if((++Beginer)>2) Beginer=1;
371 if(Beginer==1) State=3 ; else State=4;
372 if((++Play)>2){ Play=1; State=13; }
373 }
374 else if(Message==ERR_TRUCO)
375 {
376 ValGame += Sum_Val;
377 Sum_Val = 0;
378 pc=you+1;
379 score1=0; score2=2;
380 State=13;
381 }
382
383 Message=0;
384 break;
385 case 4:
386 if(You_Play==100)
387 switch(Who_Play)
388 {
389 case 1:
390 You_Play= FirstGame();
391 break;
392 case 2:
393 You_Play= SecondGame();
394 break;
395 case 3:
396 You_Play= ThirdGame();
397 break;
398 }
399 position= You_Play;
400 if(position<0) position*=(-1);
401 position--;
402 resulters=0;
403 if((Who_Play>1) && (Who_Say_Truco!=1) &&
404 (ValGame<12) && !((Who_Play==2) && (You_Play<0))
405 && (YouScore!=MAXIMO-1) && (MyScore!=MAXIMO-1) )
406 resulters=CanSayTruco(position, you);
407 if(resulters>=1)
408 {
409 Who_Say_Truco=1;
410 if(ValGame==1) Sum_Val=2; else Sum_Val=3;
411 sprintf(Messa, "Truco (%2d). Do you accept?...",
412 Sum_Val+ValGame );
413 TalkMachine( display, window, gc, Messa, 0 );
414 }
415 if(Sum_Val==0)
416 {
417 if(You_Play>0)
418 {
419 You_Play--;
420 Table[6+Play].what= Table[You_Play].what;
421 pc=Table[6+Play].val_score=Table[You_Play].val_score;
422 Table[6+Play].card_state= 2;
423 Table[You_Play].card_state=0;
424 }
425 else
426 {
427 You_Play*=(-1);You_Play--;
428 Table[6+Play].what = 0;
429 pc=Table[6+Play].val_score = 0;
430 Table[6+Play].card_state= 1;
431 Table[You_Play].card_state=0;
432 }
433 TableCards( display, window, pixmap, gc, BACK );
434 if((++Beginer)>2) Beginer=1;
435 if(Beginer==1) State=3; else State=4;
436 if((++Play)>2) { Play=1; State=13; }
437 }
438 else State=5;
439 break;
440 case 5:
441 if((Message==5) && (Who_Say_Truco!=2))
442 {
443 State=6;
444 Who_Say_Truco=2;
445 TalkMachine( display, window, gc, Messa, 1 );
446 ValGame+= Sum_Val;
447 Sum_Val=0;
448 }
449 else if(Message==YES)
450 {
451 Message=0;
452 TalkMachine( display, window, gc, Messa, 1 );
453 if(Beginer==1) State=3; else State=4;
454 }
455 else if(Message==NO)
456 {
457 strcpy(Messa, "You run away again...");
458 TalkMachine( display, window, gc, Messa, 0 );
459 Message=0;
460 State=13;
461 Sum_Val=score1=0;
462 score2=10;
463 you=0;
464 pc=1;
465 }
466 else if(Message==ERR_TRUCO)
467 {
468 ValGame += Sum_Val;
469 Sum_Val = 0;
470 pc=you+1;
471 score1=0; score2=2;
472 State=13;
473 Message=0;
474 }
475 break;
476 case 6:
477 if(Beginer==1) State=3; else State=4;
478 resulters=AcceptTruco(pc);
479 if(ValGame==1) info.number_of_trucos++;
480 if(resulters>=1)
481 {
482 if(ValGame==1) ValGame+=2; else ValGame+=3;
483 if(( resulters>1) && (ValGame<12) &&
484 ((ValGame+MyScore)<MAXIMO))
485 {
486 Sum_Val+=3;
487 Who_Say_Truco=1;
488 sprintf(Messa, "I Want %2d. Do you accept?...",
489 ValGame+Sum_Val );
490 State=5;
491 }
492 else
493 sprintf(Messa, "I accept, let's go !!!");
494 TalkMachine( display, window, gc, Messa, 0 );
495 }
496 else
497 {
498 sprintf(Messa, "Sorry!!! I don't accept...");
499 TalkMachine( display, window, gc, Messa, 0 );
500 State=13;score1=10; pc= score2=0; you=1;
501 }
502 break;
503 case 13:
504 You_Play=100;
505 if(you>pc)
506 {
507 score1++;
508 Beginer=1;
509 if(Who_Play==1) first=2;
510 }
511 else if(you<pc)
512 {
513 if(Who_Play==1) first=1;
514 score2++;
515 Beginer=2;
516 }
517 else if(you==pc)
518 {
519 if(Who_Play==1) first=3;
520 if(!((score2==1) && (score1==1) && (Who_Play==2)))
521 { score2++;score1++;}
522 }
523 if(you>11)
524 for(position=0;position<6;position++)
525 if(Table[position].val_score<you)
526 Table[position].val_score++;
527 if(pc>11)
528 for(position=0;position<6;position++)
529 if(Table[position].val_score<pc)
530 Table[position].val_score++;
531 pc=you=-1;
532 TableCards( display, window, pixmap, gc, BACK );
533 gettimeofday(&timer1, &zone);
534 while(1) {
535 gettimeofday(&timer2, &zone );
536 if(timer2.tv_sec>(timer1.tv_sec+1L)) break; }
537 if(Beginer==1) State=3; else State=4;
538 Table[7].card_state=0; Table[8].card_state=0;
539 if((score1>1) || (score2>1))
540 {
541 for(position=0;position<7;position++)
542 Table[position].card_state=0;
543 if((score1>1) && (score2>1))
544 { if(first==1)score1--;
545 else if(first==2) score2--; }
546 if(score1>1)
547 YouScore+=ValGame;
548 if(score2>1) MyScore+=ValGame;
549 State=1;
550 if(YouScore>=MAXIMO)
551 sprintf(Messa, "You Win !!!");
552 else if(MyScore>=MAXIMO)
553 sprintf(Messa, "OOHHH! I Win!!! Try again...");
554 if((YouScore>=MAXIMO) || (MyScore>=MAXIMO))
555 {
556 TalkMachine( display, window, gc, Messa, 0 );
557 if(YouScore>MAXIMO) YouScore=MAXIMO;
558 if(MyScore>MAXIMO) MyScore=MAXIMO;
559 State=0;
560 }
561 alert=score1=score2=0;
562 Play=1;
563 Who_Play=1;
564 }
565 else
566 Who_Play++;
567 score[0].val_score=MyScore; score[1].val_score= YouScore;
568 TableCards( display, window, pixmap, gc, BACK );
569 DrawScore( display, window, pixmap, gc, blue,
570 white, white, 10 , horiz, vert, score );
571 break;
572 }
573 if(status==True)
574 switch( event.type )
575 {
576 case Expose:
577 Refresh( display, window, gc, pixmap,
578 event.xexpose.x,
579 event.xexpose.y,
580 event.xexpose.width,
581 event.xexpose.height );
582 DrawScore( display, window, pixmap, gc, blue,
583 white, white, 10 , horiz, vert, score );
584 if(State==WAITING)
585 strcpy(Messa,
586 "This is the first version of the Xtruco...");
587 TalkMachine( display, window, gc, Messa, 0 );
588 XFlush( display );
589 break;
590 case KeyPress:
591 if( ( keysym == XK_Q ) || ( keysym == XK_q ) )
592 {
593 return( False );
594 }
595 else if( ( keysym == XK_A ) || ( keysym == XK_a ) )
596 {
597 if((++SHOW)>2) SHOW=1;
598 }
599 case ConfigureNotify:
600 *width = event.xconfigure.width;
601 *height = event.xconfigure.height;
602 break;
603 }
604 return( True );
605 }
606
607 void
Refresh(display,window,gc,pixmap,x,y,width,height)608 Refresh( display, window, gc, pixmap, x, y, width, height )
609 Display *display;
610 Window window;
611 GC gc;
612 Pixmap pixmap;
613 int x, y, width, height;
614 {
615 if( ( x > horiz ) || ( y > vert ) )
616 {
617 return;
618 }
619 if( ( x + width ) > horiz )
620 {
621 width = horiz - x;
622 if( width < 0 )
623 {
624 return;
625 }
626 }
627 if( ( y + height ) > vert )
628 {
629 height = vert - y;
630 if( height < 0 )
631 {
632 return;
633 }
634 }
635 XCopyArea( display, pixmap, window, gc, x, y, width,
636 height, x, y );
637 return;
638 }
639
MakeButtons(display,window,gc,fore,back,font_id,h,v)640 MakeButtons( display, window, gc, fore, back, font_id, h, v )
641 Display *display;
642 Window window;
643 GC gc;
644 unsigned long fore, back;
645 Font font_id;
646 {
647 int QuitApplication();
648 int Button_Truco();
649 int Button_No();
650 int Button_Yes();
651 int Button_New();
652 int card1();
653 int card2();
654 int card3();
655 int Button_Cut();
656 int x, y, pos1, pos2;
657
658 pos1 = horiz/2 -36- 20*10;
659 pos2 = vert/2 - 48;
660 x = 390+CARD_WIDTH;
661 InvButton( display, window, pos1, pos2, x, CARD_HEIGHT, Button_Cut );
662 x = horiz- (BUTTON_WIDTH + 5);
663 y = vert-BUTTON_HEIGHT-5;
664 CreateButton( display, window, x, y, fore, back,
665 font_id, "QUIT",QuitApplication );
666 y -= BUTTON_HEIGHT + 5;
667 CreateButton( display, window, x, y, fore, back,
668 font_id, "NEW",Button_New );
669 y -= BUTTON_HEIGHT + 5;
670 CreateButton( display, window, x, y, fore, back,
671 font_id, "NO", Button_No );
672 y -= BUTTON_HEIGHT + 5;
673 CreateButton( display, window, x, y, fore, back,
674 font_id, "YES", Button_Yes );
675 y -= BUTTON_HEIGHT + 5;
676 CreateButton( display, window, x, y, fore, back,
677 font_id, "TRUCO", Button_Truco );
678 InvButton( display, window, Table[3].X, Table[3].Y, CARD_WIDTH,
679 CARD_HEIGHT, card1 );
680 InvButton( display, window, Table[4].X, Table[4].Y, CARD_WIDTH,
681 CARD_HEIGHT, card2 );
682 InvButton( display, window, Table[5].X, Table[5].Y, CARD_WIDTH,
683 CARD_HEIGHT, card3 );
684 }
685
Button_Truco(display,window)686 Button_Truco(display, window)
687 Display *display;
688 Window window;
689 {
690 if((YouScore==MAXIMO-1) || (MyScore==MAXIMO-1))
691 Message=ERR_TRUCO;
692 else
693 Message=5;
694 }
695
Button_Yes(display,window)696 Button_Yes(display, window)
697 Display *display;
698 Window window;
699 {
700 ValGame+= Sum_Val;
701 Sum_Val=0;
702 Message=YES;
703 }
704
Button_No(display,window)705 Button_No(display, window)
706 Display *display;
707 Window window;
708 {
709 if(State>2)
710 {
711 State=5;
712 Message=NO;
713 }
714 }
715
Button_New(display,window)716 Button_New( display, window )
717 Display *display;
718 Window window;
719 {
720 State=NEW;
721 Begining= RANDOM(2)+1;
722 Beginer=Begining;
723 alert=YouScore=MyScore=0;
724 Play=1; Who_Play=1; You_Play=100;
725 info.number_of_trucos=info.first_truco=0;
726 }
727
QuitApplication(display,window)728 QuitApplication( display, window )
729 Display *display;
730 Window window;
731 {
732 State=200;
733 fprintf(stderr,"\nSuper Truco (XTruco)\n"\
734 "By Marcos Martins Duma\n\n"\
735 "Address:\n"\
736 "Rua Manoel Jose da Cunha, n.65\n"\
737 "Jaguare - Sao Paulo - SP\nBrazil\n"\
738 "CEP 05338-040\n\n" );
739 }
740
card1(display,window,type)741 card1( display, window, type )
742 Display *display;
743 Window window;
744 int type;
745 {
746 if(Table[3].card_state!=0)
747 Message=1*type;
748 }
749
card2(display,window,type)750 card2( display, window, type )
751 Display *display;
752 Window window;
753 int type;
754 {
755 if(Table[4].card_state!=0)
756 Message=2*type;
757 }
758
card3(display,window,type)759 card3( display, window, type )
760 Display *display;
761 Window window;
762 int type;
763 {
764 if(Table[5].card_state!=0)
765 Message=3*type;
766 }
767
Button_Cut(display,window,type)768 Button_Cut( display, window, type )
769 Display *display;
770 Window window;
771 int type;
772 {
773 Message=4*type;
774 ValGame=1;
775 You_Play=100;
776 Who_Say_Truco=Sum_Val=danger=0;
777 pc=you=-1;
778 if((++Begining)>2) Begining=1;
779 Beginer=Begining;
780 score1=score2=first=0;
781 }
782
ShowCards(display,window,pixmap,gc,card)783 ShowCards(display, window, pixmap, gc, card )
784 Display *display;
785 Window window;
786 Pixmap pixmap;
787 GC gc;
788 int card;
789 {
790 int what;
791 int a=0;
792 int pos1, pos2;
793
794 if(card>39) what=card; else what=40;
795 pos1 = horiz/2 -36- 20*10;
796 pos2 = vert/2 - 48;
797 Draw_Cards( display, window, pixmap, gc, what,
798 pos1, pos2 );
799 Refresh( display, window, gc, pixmap, pos1, pos2,
800 CARD_WIDTH, CARD_HEIGHT );
801 XFlush( display );
802 Shuffle();
803 pos1= horiz/2 -36- 20*10;
804 pos2= vert/2 - 48;
805 for(a=1; a<41; a++)
806 {
807 Draw_Cards( display, window, pixmap, gc, what,
808 pos1, pos2 );
809 Refresh( display, window, gc, pixmap, pos1, pos2,
810 CARD_WIDTH, CARD_HEIGHT );
811 pos1+= 10;
812 }
813 }
814
Shuffle()815 Shuffle()
816 {
817 int auxs[40];
818 int count=40,v;
819
820 for(v=0;v<40;v++) auxs[v]=Cards[v];
821 while(count)
822 {
823 v= RANDOM(40);
824 if(auxs[v]>=0)
825 {
826 Cards[--count]= auxs[v];
827 auxs[v]= -1;
828 }
829 }
830 }
831
Cuting(display,window,pixmap,gc,card,pos)832 Cuting(display, window, pixmap, gc, card, pos)
833 Display *display;
834 Window window;
835 Pixmap pixmap;
836 GC gc;
837 int card, pos;
838 {
839 int a=0, b, corta, corta2;
840 int pos1, pos2, x;
841 int c[40], what;
842
843 if(card>39) what=card; else what=40;
844 for(a=0;a<40;a++) c[a]=Cards[a];
845 pos1= horiz/2 -36- 20*10;
846 pos2= vert/2 - 48;
847 if(pos>480) pos=480;
848 corta=pos-pos1+10;
849 if(corta<0) corta=0;
850 corta=corta/10;
851 corta2=corta; pos=pos1+10*corta;
852 if(corta<40)
853 {
854 x=0; b=10;
855 while(x<CARD_WIDTH)
856 {
857 x+=b;
858 if(x>CARD_WIDTH) { b-=(x-CARD_WIDTH);x=CARD_WIDTH; }
859 pos-=b;
860 DrawPartCards( display, window, pixmap, gc, what,
861 pos, pos2, x );
862 Refresh( display, window, gc, pixmap, pos, pos2,
863 x, CARD_HEIGHT );
864 }
865 pos1-=b;
866 for(a=pos-10; a>=pos1; a-=10)
867 {
868 DrawPartCards( display, window, pixmap, gc, what,
869 a, pos2, CARD_WIDTH );
870 ClearCard( display, window, pixmap, gc,
871 a+CARD_WIDTH, pos2, 10 );
872 Refresh( display, window, gc, pixmap, a, pos2,
873 CARD_WIDTH+10, CARD_HEIGHT );
874 }
875 pos=a;
876 }
877 else
878 corta2=0;
879 for(a=400; a>=(10*corta2); a-=10)
880 {
881 DrawPartCards( display, window, pixmap, gc, what,
882 pos1+a, pos2, CARD_WIDTH );
883 ClearCard( display, window, pixmap, gc,
884 pos1+a+CARD_WIDTH, pos2, 10 );
885 Refresh( display, window, gc, pixmap, pos1+a, pos2,
886 CARD_WIDTH+10, CARD_HEIGHT );
887 }
888 corta2=pos1+a+10;
889 for(a=pos;a<corta2; a+=10)
890 {
891 ClearCard( display, window, pixmap, gc,
892 a, pos2, 10 );
893 DrawPartCards( display, window, pixmap, gc, what,
894 a+10, pos2, CARD_WIDTH );
895 Refresh( display, window, gc, pixmap, a, pos2,
896 CARD_WIDTH+10, CARD_HEIGHT );
897 }
898 ClearCard( display, window, pixmap, gc,
899 corta2, pos2, CARD_WIDTH );
900 Refresh( display, window, gc, pixmap, corta2, pos2,
901 CARD_WIDTH, CARD_HEIGHT );
902 b=0;
903 for(a=corta; a<40; a++) Cards[(b++)]=c[a];
904 for(a=0; a<corta; a++) Cards[(b++)]= c[a];
905 b=0;
906 for(a=0; a<9; a++)
907 {
908 Table[b].what= Cards[a];
909 if(b<3) Table[b].card_state=SHOW;
910 else if(b<7) Table[b].card_state=2;
911 else Table[b].card_state=0;
912 b++;
913 }
914 for(a=6; a>=0; a--)
915 {
916 b=(Table[a].what-1)/4+1;
917 if((a<6) && (( b==Table[6].val_score+1)
918 || ((b==1) && (Table[6].val_score==10))))
919 Table[a].val_score=11 + (Table[a].what-1)%4;
920 else Table[a].val_score=b;
921 }
922 }
923
TableCards(display,window,pixmap,gc,card)924 TableCards (display, window, pixmap, gc, card )
925 Display *display;
926 Window window;
927 Pixmap pixmap;
928 GC gc;
929 int card;
930 {
931 int a, what;
932
933 if(card<40) card=BACK;
934 for(a=0; a<9; a++)
935 {
936 if(Table[a].card_state!=0)
937 {
938 if(Table[a].card_state==1) what=card;
939 else what=Table[a].what-1;
940 Draw_Cards( display, window, pixmap, gc, what,
941 Table[a].X, Table[a].Y);
942 Refresh( display, window, gc, pixmap, Table[a].X,
943 Table[a].Y, CARD_WIDTH, CARD_HEIGHT );
944 }
945 else
946 {
947 ClearCard( display, window, pixmap, gc,
948 Table[a].X, Table[a].Y, CARD_WIDTH);
949 Refresh( display, window, gc, pixmap, Table[a].X,
950 Table[a].Y, CARD_WIDTH, CARD_HEIGHT );
951 }
952 }
953 }
954
955 #define SC_WIDTH 150
956
957
DrawScore(display,window,pixmap,gc,c1,c2,c3,f,h,v,draw_score)958 DrawScore( display, window, pixmap, gc, c1, c2, c3, f, h, v, draw_score )
959 Display *display;
960 Window window;
961 Pixmap pixmap;
962 GC gc;
963 unsigned long c1, c2, c3; /* colors */
964 int f, h, v; /* width_fonte, horiz, vert */
965 TYPE_SCORE *draw_score; /* Struct for Score (val_scores) */
966 {
967 int p1, p2, l, a, m, n, SC_HEIGHT;
968 char Scores[10];
969
970 SC_HEIGHT=8*f;
971 m= p1= horiz- SC_WIDTH;
972 n= p2= 0;
973 l= SC_WIDTH-1;
974 a= SC_HEIGHT-1;
975 Scores[9]='\0';
976 XSetForeground( display, gc, c1 );
977 XSetBackground( display, gc, c1 );
978 XFillRectangle( display, window, gc, p1, p2, l, a );
979 XSetForeground( display, gc, c3 );
980 XDrawRectangle( display, window, gc, p1, p2, l, a );
981 XDrawLine(display, window, gc, p1+l/2, p2, p1+l/2, p2+a );
982 p2 += 3*f;
983 a -= (3*f);
984 XDrawLine(display, window, gc, p1, p2, p1+l, p2 );
985 XSetForeground( display, gc, c2 );
986 ShowText( display, window, gc, "Machine", p1+5, n+2*f );
987 ShowText( display, window, gc, "You", p1+5+l/2, n+2*f );
988 sprintf(Scores," %2d", score[0].val_score );
989 ShowText( display, window, gc, Scores, p1+5, p2+3*f );
990 sprintf(Scores," %2d", score[1].val_score );
991 ShowText( display, window, gc, Scores, p1+5+l/2, p2+3*f );
992 }
993
ShowText(display,window,gc,text,pos1,pos2)994 ShowText( display, window, gc, text, pos1, pos2 )
995 Display *display;
996 Window window;
997 GC gc;
998 char text[];
999 int pos1, pos2;
1000 {
1001 int tamanho;
1002
1003 tamanho= strlen( text );
1004 XDrawImageString( display, window, gc,
1005 pos1, pos2,
1006 text, tamanho );
1007 }
1008
TalkMachine(display,window,gc,text,type)1009 TalkMachine( display, window, gc, text, type )
1010 Display *display;
1011 Window window;
1012 GC gc;
1013 char *text;
1014 int type;
1015 {
1016 int tam, pos1, pos2, a, b;
1017 char buffer[80];
1018
1019 if(type==1) strcpy(text," " );
1020 b= 30;
1021 a= 400;
1022 pos1=10;
1023 pos2=vert - b; /* -b/3; */
1024 XSetForeground( display, gc, green );
1025 XSetBackground( display, gc, green );
1026 XFillRectangle( display, window, gc, pos1, pos2, a, b );
1027 XSetForeground( display, gc, black );
1028 XSetForeground( display, gc, white );
1029 strcpy( buffer, "Machine -> ");
1030 strcat( buffer, text );
1031 tam= strlen( buffer );
1032 pos1+= 10;
1033 pos2+= (b/2);
1034 XDrawImageString( display, window, gc, pos1, pos2,
1035 buffer, tam );
1036 XFlush( display );
1037 }
1038
1039
FirstGame()1040 FirstGame()
1041 {
1042 struct {
1043 int v;
1044 int q;
1045 } c[3], t;
1046 int a,b,c1,c2,c3,ret, aleat;
1047
1048 for(a=0;a<3;a++)
1049 {
1050 c[a].v=Table[a].val_score;
1051 c[a].q=a+1;
1052 }
1053 for(a=0;a<3;a++)
1054 for(b=a;b<3;b++)
1055 {
1056 if(c[a].v>c[b].v){
1057 t=c[a]; c[a]=c[b]; c[b]=t; }
1058 }
1059 c1=c[0].v; c2=c[1].v; c3=c[2].v;
1060 switch(Play)
1061 {
1062 case 1:
1063 if((c3==14) && (c2==13)) ret=c[0].q;
1064 else
1065 {
1066 aleat= RANDOM(10);
1067 ret=-1*(c[0].q);
1068 switch(aleat)
1069 {
1070 case 0:
1071 for(a=2;a>=0;a--)
1072 if(c[a].v<13) {ret=c[a].q; break; }
1073 break;
1074 case 1:
1075 ret=c[0].q;
1076 break;
1077 default:
1078 for(a=2;a>=0;a--)
1079 if(c[a].v<11) {ret=c[a].q; break; }
1080 if(ret>0)
1081 break;
1082 for(a=0;a<=2;a++)
1083 if(c[a].v<13) {ret=c[a].q; break; }
1084 break;
1085 }
1086 }
1087 break;
1088 case 2:
1089 if((RANDOM(3))==1) aleat=-1; else aleat=1;
1090 ret=aleat*c[0].q;
1091 if((c3==14) && (c2==13) && (c1<you)) ret=c[0].q*aleat;
1092 else if((c3==14) && (c2==13)) ret=c[0].q*(-1);
1093 else
1094 {
1095 for(a=0;a<=2;a++)
1096 {
1097 if(c[a].v==you) ret=c[a].q;
1098 if((c[a].v>you) && (c[a].v<12))
1099 { ret=c[a].q; break; }
1100 }
1101 for(a=2;a>=1;a--)
1102 if((c[a].v==you) && (c3>8))
1103 ret=c[a].q;
1104 }
1105 break;
1106 }
1107 return (ret);
1108 }
1109
SecondGame()1110 SecondGame()
1111 {
1112 struct {
1113 int v;
1114 int q;
1115 } c[2], t;
1116 int a,b,c1,c2,ret,aleat;
1117
1118 b=0;
1119 for(a=0;a<3;a++)
1120 {
1121 if(!Table[a].card_state) continue;
1122 c[b].v=Table[a].val_score;
1123 c[b].q=a+1;
1124 b++;
1125 }
1126 if(c[0].v>c[1].v) { t=c[0]; c[0]=c[1]; c[1]=t; }
1127 c1=c[0].v; c2=c[1].v;
1128
1129 aleat=RANDOM(4);
1130 switch(Play)
1131 {
1132 case 1:
1133 ret=c[1].q;
1134 if(c2==14)
1135 {
1136 if(RANDOM(3)==0) aleat=-1; else aleat=1;
1137 if(c1<6) ret=c[0].q*aleat;
1138 else if(c1>5) ret=-1*c[0].q;
1139 }
1140 else if(c2==13)
1141 {
1142 if(RANDOM(2)==1)
1143 {
1144 if((RANDOM(3))==1) aleat=-1; else aleat=1;
1145 if((c1>7) && (YouScore<MyScore+2)) ret=-1*c[0].q;
1146 else if(c1<=6) ret=c[0].q*aleat;
1147 }
1148 else
1149 ret=c[1].q;
1150 }
1151 else if((c2>11) && (aleat==1) && (YouScore<MyScore+2))
1152 {
1153 if(RANDOM(4)==3) aleat=-1; else aleat=1;
1154 if(c1<6) ret=c[0].q*aleat;
1155 if(c1>6) ret=-1*c[0].q;
1156 }
1157 else if(c2>9)
1158 {
1159 if((RANDOM(10)==6) && (YouScore<MyScore+2))
1160 ret=c[0].q;
1161 else
1162 ret=c[1].q;
1163 }
1164 else if((c2>=4) && (c1<4)) ret=c[1].q;
1165 else if((c1<4) && (aleat==2)) ret=-1*c[0].q;
1166 else
1167 {
1168 ret=c[RANDOM(2)].q;
1169 }
1170 break;
1171 case 2:
1172 ret=-1*c[0].q;
1173 for(a=0;a<2;a++) if(c[a].v>you) {ret=c[a].q; break; }
1174 if((first==1) || ((ret<0) && (first==3)))
1175 for(a=0;a<2;a++) if(c[a].v>=you) {ret=c[a].q; break; }
1176 break;
1177 }
1178 return (ret);
1179 }
1180
ThirdGame()1181 ThirdGame()
1182 {
1183 int a;
1184 int ret;
1185
1186 for(a=0;a<3;a++)
1187 {
1188 if(Table[a].card_state==0) continue;
1189 ret=a+1;
1190 }
1191 if((Play==2) && (Table[ret-1].val_score<you)) ret*=(-1);
1192 return (ret);
1193 }
1194
CanSayTruco(val1,val2)1195 CanSayTruco(val1, val2)
1196 int val1, val2;
1197 {
1198 int a,c1,c2,ret,aleat;
1199
1200 ret=0;
1201 if(MyScore+ValGame>=MAXIMO) return( ret );
1202 for(a=0;a<3;a++)
1203 {
1204 if(!Table[a].card_state) continue;
1205 if(Table[val1].val_score==Table[a].val_score)
1206 c1=Table[a].val_score;
1207 else
1208 c2=Table[a].val_score;
1209 }
1210 switch(Who_Play)
1211 {
1212 case 2:
1213 ret=0;
1214 if((first==1) && (ValGame==1) && (You_Play>0))
1215 {
1216 if(c1>9) ret=1;
1217 else if((c1>8) && (c2>5)) ret=1;
1218 else if((c1>8) && (YouScore<MyScore+2)) ret=1;
1219 else if((c1>=6) && (info.number_of_trucos>3)
1220 && (RANDOM(2)==0)) { danger=1; ret=1; }
1221 else if((c1>=6) && (Begining==1) && (YouScore<=MyScore))
1222 { danger=1; ret=1; }
1223 else if((RANDOM(3)==0) && ((YouScore<=MyScore)
1224 || (YouScore>=(MyScore/2)))) { danger=1; ret=1; }
1225 }
1226 else if(first==2)
1227 {
1228 if((ValGame+YouScore)>=MAXIMO) return(ret=1);
1229 if(val2==0) alert++;
1230 if((ValGame==1) && (c1>val2) &&
1231 (c2>11) && (val2!=0)) ret=1;
1232 }
1233 else if((first==3) && (val2<0))
1234 {
1235 if((ValGame+YouScore)>=MAXIMO) return(ret=1);
1236 else if((c1>9) && (ValGame==1)) ret=1;
1237 else if(c1>13) ret=1;
1238 }
1239 else if((first==3) && (val2>0) && (c1>val2)) ret=1;
1240 else if((first==3) && ((ValGame+YouScore)>=MAXIMO)) ret=1;
1241 break;
1242 case 3:
1243 if((ValGame+YouScore)>=MAXIMO) return(ret=1);
1244 ret=0;
1245 aleat=RANDOM(3);
1246 if(val2>=0)
1247 {
1248
1249 if(c1>val2) ret=1;
1250 if((first==1) && (c1==val2)) ret=1;
1251 else if((val2<7)&& (aleat<=1)) { ret=1; danger=1; }
1252 else if(val2<=3) { ret=1; danger=1; }
1253 else if((RANDOM(4)==2) && (ValGame==1)
1254 && (val2<11) && (YouScore<MyScore+4)) {ret=1; danger=1;}
1255 }
1256 else if(val2<0)
1257 {
1258 if((ValGame+YouScore)>=MAXIMO) return(ret=1);
1259 else if(c1==14) ret=1;
1260 else if((c1>10) && (ValGame==1)) ret=1;
1261 else if((c1>8) && !(alert) && (ValGame==1))
1262 ret=1;
1263 }
1264 break;
1265 }
1266 return(ret);
1267 }
1268
AcceptTruco(val1)1269 AcceptTruco(val1)
1270 int val1;
1271 {
1272 int a,b,c1,c2,c3,ret,t;
1273 int c[3];
1274
1275 c1=c2=c3=ret=0;
1276 if(val1>=0) c[ret++]=val1;
1277 for(a=0;a<3;a++)
1278 {
1279 if(!Table[a].card_state) continue;
1280 c[ret]=Table[a].val_score;
1281 ret++;
1282 }
1283 for(a=ret;a<3;a++) c[a]=0;
1284 for(a=0;a<3;a++)
1285 for(b=a+1;b<3;b++)
1286 if((c[a]>c[b]) && (c[b]!=0)) {t=c[a];c[a]=c[b];c[b]=t;}
1287 c1=c[0];
1288 ret=0; while((ret<3) && (Table[ret].card_state>0)) ret++;
1289 if(c[1]!=0) c2= c[1]; else {c2= Table[ret].val_score; ret++; }
1290 while((ret<3) && (Table[ret].card_state>0)) ret++;
1291 if(c[2]!=0) c3= c[2]; else {c3= Table[ret].val_score; ret++; }
1292 ret=0;
1293 switch(Who_Play)
1294 {
1295 case 1:
1296 info.first_truco++;
1297 if((ValGame+YouScore)>=MAXIMO) return (ret=2);
1298 else if((c3>9) && (c2>8)) ret=1;
1299 else if((c3>10) && (c1>5) && (c2>6)) ret=1;
1300 else if((info.first_truco>1)
1301 && (c3>7) && (c2>6)) {ret=1;danger=1;}
1302 break;
1303 case 2:
1304 if((ValGame+YouScore)>=MAXIMO) return(ret=2);
1305 if(first==1)
1306 {
1307 if(c2==14) ret=2;
1308 else if((c1>7) && (c2>6)) ret=1;
1309 else if((c2>8) && !(alert)) ret=1;
1310 else if(c2>10) ret=1;
1311 }
1312 else if(first==2)
1313 {
1314 if((c1>5) && (c2>8) && (c3>6)) ret=1;
1315 else if((c1>9) && (c2>10)) ret=1;
1316 }
1317 else if((first==3) && (val1>0))
1318 {
1319 if(val1==14) ret=2;
1320 else if(val1>9) ret=1;
1321 else if((ValGame==1) && (val1>8)
1322 && (RANDOM(2)==0)) ret=1;
1323 }
1324 else if(first==3)
1325 {
1326 if(c2==14) ret=2;
1327 else if(c2>11) ret=1;
1328 else if((ValGame==1) && (c2>8)) ret=1;
1329 else if((ValGame==1) &&
1330 (c2>6) && (RANDOM(4)==1)) {ret=1;danger=1;}
1331 }
1332 break;
1333 case 3:
1334 if((ValGame+YouScore)>=MAXIMO) return (ret=2);
1335 ret=0;
1336 if(val1>0)
1337 {
1338 if(c1==14) ret=2;
1339 else if(c1>10) ret=1;
1340 else if((c1>6) && (first==3)) ret=1;
1341 else if((c1>7) && (ValGame==1)) ret=1;
1342 else if((c1>6) && (!alert) && (RANDOM(2)==1))
1343 { ret=1; danger=1; }
1344 }
1345 else if(val1<0)
1346 {
1347 if(c1>11) ret=1;
1348 else if((c1>7) && !(alert)) ret=1;
1349 else if((first==1) && (Begining==1) && (c1>6)
1350 && (c2>6) && (c3>6)) ret=1;
1351 }
1352 break;
1353 }
1354 return(ret);
1355 }
1356
RANDOM(val_score)1357 RANDOM( val_score )
1358 int val_score;
1359 {
1360 int ret;
1361
1362 #ifndef RAND_MAX
1363 ret=(int) rand()%val_score;
1364 #else
1365 ret=((int) (50.0*rand()/(RAND_MAX+1.0)))%val_score;
1366 #endif
1367 return( ret );
1368 }
1369