Rev 4652 | Go to most recent revision | Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
1805 | yogev_ezra | 1 | #define BUILD_RUS |
2 | #ifndef __MENUET__ |
||
3 | #include |
||
4 | #include |
||
5 | #include |
||
6 | #include |
||
7 | #include |
||
8 | #else |
||
9 | #include |
||
10 | #include |
||
11 | using namespace Menuet; |
||
12 | #define strlen StrLen |
||
13 | #define strcpy StrCopy |
||
14 | #define memcpy MemCopy |
||
15 | #include |
||
16 | const unsigned dectab[] = { 1000000000, 100000000, 10000000, 1000000, 100000, |
||
17 | 10000, 1000, 100, 10, 0 }; |
||
18 | int sprintf( char *Str, char* Format, ... ) |
||
19 | { |
||
20 | int i, fmtlinesize, j, k, flag; |
||
21 | unsigned head, tail; |
||
22 | char c; |
||
23 | va_list arglist; |
||
24 | // |
||
25 | va_start(arglist, Format); |
||
26 | |||
27 | // |
||
28 | fmtlinesize = strlen( Format ); |
||
29 | // |
||
30 | if( fmtlinesize == 0 ) return 0; |
||
31 | |||
32 | // |
||
33 | for( i = 0, j = 0; i < fmtlinesize; i++ ) |
||
34 | { |
||
35 | // |
||
36 | c = Format[i]; |
||
37 | // |
||
38 | if( c != '%' ) |
||
39 | { |
||
40 | Str[j++] = c; |
||
41 | continue; |
||
42 | } |
||
43 | // |
||
44 | i++; |
||
45 | // |
||
46 | if( i >= fmtlinesize ) break; |
||
47 | |||
48 | // |
||
49 | flag = 0; |
||
50 | // |
||
51 | c = Format[i]; |
||
52 | if (c == 'l') c = Format[++i]; |
||
53 | // |
||
54 | switch( c ) |
||
55 | { |
||
56 | // |
||
57 | case '%': |
||
58 | Str[j++] = c; |
||
59 | break; |
||
60 | // |
||
61 | case 's': |
||
62 | char* str; |
||
63 | str = va_arg(arglist, char*); |
||
64 | for( k = 0; ( c = str[k] ) != 0; k++ ) |
||
65 | { |
||
66 | Str[j++] = c; |
||
67 | } |
||
68 | break; |
||
69 | // |
||
70 | case 'c': |
||
71 | Str[j++] = va_arg(arglist, int) & 0xFF; |
||
72 | break; |
||
73 | // |
||
74 | case 'u': |
||
75 | case 'd': |
||
76 | head = va_arg(arglist, unsigned); |
||
77 | for( k = 0; dectab[k] != 0; k++ ) |
||
78 | { |
||
79 | tail = head % dectab[k]; |
||
80 | head /= dectab[k]; |
||
81 | c = head + '0'; |
||
82 | if( c == '0' ) |
||
83 | { |
||
84 | if( flag ) Str[j++] = c; |
||
85 | } |
||
86 | else |
||
87 | { |
||
88 | flag++; |
||
89 | Str[j++] = c; |
||
90 | } |
||
91 | // |
||
92 | head = tail; |
||
93 | } |
||
94 | // |
||
95 | c = head + '0'; |
||
96 | Str[j++] = c; |
||
97 | break; |
||
98 | default: |
||
99 | break; |
||
100 | } |
||
101 | } |
||
102 | // |
||
103 | Str[j] = 0; |
||
104 | return j; |
||
105 | } |
||
106 | int isdigit(int c) |
||
107 | { |
||
108 | return (c>='0' && c<='9'); |
||
109 | } |
||
110 | int atoi(const char* string) |
||
111 | { |
||
112 | int res=0; |
||
113 | int sign=0; |
||
114 | const char* ptr; |
||
115 | for (ptr=string; *ptr && *ptr<=' ';ptr++); |
||
116 | if (*ptr=='-') {sign=1;++ptr;} |
||
117 | while (*ptr >= '0' && *ptr <= '9') |
||
118 | { |
||
119 | res = res*10 + *ptr++ - '0'; |
||
120 | } |
||
121 | if (sign) res = -res; |
||
122 | return res; |
||
123 | } |
||
124 | int islower(int c) |
||
125 | { |
||
126 | return (c>='a' && c<='z'); |
||
127 | } |
||
128 | int abs(int n) |
||
129 | { |
||
130 | return (n<0)?-n:n; |
||
131 | } |
||
132 | int memcmp(const void* buf1, const void* buf2, unsigned count) |
||
133 | { |
||
134 | const char* ptr1 = (const char*)buf1; |
||
135 | const char* ptr2 = (const char*)buf2; |
||
136 | unsigned i=0; |
||
137 | while (i |
||
138 | if (i==count) |
||
139 | return 0; |
||
140 | else if (*ptr1<*ptr2) |
||
141 | return -1; |
||
142 | else |
||
143 | return 1; |
||
144 | } |
||
145 | void strncpy(char* dest, const char* source, unsigned len) |
||
146 | { |
||
147 | char* ptr1 = dest; |
||
148 | const char *ptr2 = source; |
||
149 | for (;len-- && *ptr2; *ptr1++=*ptr2++) ; |
||
150 | } |
||
151 | unsigned int rand_data[4]; |
||
152 | |||
153 | void randomize() |
||
154 | { |
||
155 | rand_data[0] = (unsigned int)Clock(); |
||
156 | rand_data[1] = (unsigned int)GetPackedTime(); |
||
157 | rand_data[2] = (unsigned int)GetPackedDate(); |
||
158 | rand_data[3] = (unsigned int)0xA3901BD2 ^ GetPid(); |
||
159 | } |
||
160 | |||
161 | unsigned int rand() |
||
162 | { |
||
163 | rand_data[0] ^= _HashDword(rand_data[3] + 0x2835C013U); |
||
164 | rand_data[1] += _HashDword(rand_data[0]); |
||
165 | rand_data[2] -= _HashDword(rand_data[1]); |
||
166 | rand_data[3] ^= _HashDword(rand_data[2]); |
||
167 | return rand_data[3]; |
||
168 | } |
||
169 | |||
170 | #define random(k) (rand() % (k)) |
||
171 | #define floor Floor |
||
172 | double fabs(double x) |
||
173 | { |
||
174 | __asm fld x |
||
175 | __asm fabs |
||
176 | } |
||
177 | #define M_PI 3.14159265358979323846 |
||
178 | double cos(double x) |
||
179 | { |
||
180 | __asm fld x |
||
181 | __asm fcos |
||
182 | } |
||
183 | double sin(double x) |
||
184 | { |
||
185 | __asm fld x |
||
186 | __asm fsin |
||
187 | } |
||
188 | /*inline void printf(const char* format, ...) |
||
189 | {}*/ |
||
190 | #define printf /* nothing */ |
||
191 | inline void strcat(char* str1, const char* str2) |
||
192 | {strcpy(str1+strlen(str1),str2);} |
||
193 | int strncmp(const char* str1, const char* str2, unsigned len) |
||
194 | { |
||
195 | for (;len--;) |
||
196 | { |
||
197 | if (*str1 != *str2) break; |
||
198 | if (*str1 == 0) |
||
199 | return 0; |
||
200 | ++str1;++str2; |
||
201 | } |
||
202 | if (len==(unsigned)-1) |
||
203 | return 0; |
||
204 | if (*str1 < *str2) |
||
205 | return -1; |
||
206 | return 1; |
||
207 | } |
||
208 | #define clock Clock |
||
209 | typedef unsigned int clock_t; |
||
210 | #define CLOCKS_PER_SEC 100 |
||
211 | #define XK_Left 0xB0 |
||
212 | #define XK_Right 0xB3 |
||
213 | #define XK_Up 0xB2 |
||
214 | #define XK_Down 0xB1 |
||
215 | #define XK_Return 0x0D |
||
216 | #define XK_space 0x20 |
||
217 | #define XK_Escape 0x1B |
||
218 | #define XK_less '<' |
||
219 | #define XK_comma ',' |
||
220 | #define XK_period '.' |
||
221 | #define XK_greater '>' |
||
222 | #define XK_minus '-' |
||
223 | #define XK_equal '=' |
||
224 | #define XK_underscore '_' |
||
225 | #define XK_plus '+' |
||
226 | #define XK_Delete 0xB6 |
||
227 | #define XK_F8 0x39 |
||
228 | #define XK_l 'l' |
||
229 | #define XK_L 'L' |
||
230 | #define XK_F2 0x33 |
||
231 | #define XK_s 's' |
||
232 | #define XK_S 'S' |
||
233 | #define XK_slash '/' |
||
234 | #define XK_question '?' |
||
235 | #define XK_n 'n' |
||
236 | #define XK_N 'N' |
||
237 | #define XK_t 't' |
||
238 | #define XK_T 'T' |
||
239 | #define XK_r 'r' |
||
240 | #define XK_R 'R' |
||
241 | #define XK_b 'b' |
||
242 | #define XK_B 'B' |
||
243 | #define XK_f 'f' |
||
244 | #define XK_F 'F' |
||
245 | #define assert(a) /* nothing */ |
||
246 | #include "qsort.c" |
||
247 | #endif |
||
248 | #include "gr-draw.h" |
||
249 | #include "board.h" |
||
250 | #include "player.h" |
||
251 | #include "buttons.h" |
||
252 | #include "sysproc.h" |
||
253 | |||
254 | char *strskipref(char *s1, char *s2) |
||
255 | { |
||
256 | int L = strlen(s2); |
||
257 | if (strncmp(s1, s2, L) == 0) return s1 + L; |
||
258 | else return 0; |
||
259 | } |
||
260 | |||
261 | class TPlayArray |
||
262 | { |
||
263 | public: |
||
264 | TPlayArray(int d = 10) : play(0), nplay(0), mplay(0) {} |
||
265 | ~TPlayArray() {Clear();} |
||
266 | |||
267 | void Clear(); |
||
268 | void Add(const PlayWrite &pl); |
||
269 | PlayWrite &operator[](int i) {return play[i];} |
||
270 | int GetNPlay() const {return nplay;} |
||
271 | #ifndef __MENUET__ |
||
272 | int OpenFile(const char *name, int kind); |
||
273 | int MsgOpenFile(const char *name, int kind); |
||
274 | int SaveFile(const char *name, int num, int kind); |
||
275 | int MsgSaveFile(const char *name, int num, int kind); |
||
276 | #endif |
||
277 | void Del(int n); |
||
278 | protected: |
||
279 | void Extend(int n = -1); |
||
280 | |||
281 | PlayWrite *play; |
||
282 | int nplay, mplay; |
||
283 | protected: |
||
284 | #ifndef __MENUET__ |
||
285 | static const char *const search[]; |
||
286 | static int AnalizeKind(FILE *f, const int w[], const char *smb = 0); |
||
287 | static int ReadFileTo(FILE *f, char c); |
||
288 | static int ReadFileTo(FILE *f, const char *c); |
||
289 | static int ReadTheText(FILE *f, const char *s); |
||
290 | #endif |
||
291 | }; |
||
292 | |||
293 | #ifndef __MENUET__ |
||
294 | const char *const TPlayArray::search[] = |
||
295 | {"checkers-", "play:", "text", "bin_1.0\n", "history_", "1.0", "1.1"}; |
||
296 | #endif |
||
297 | |||
298 | void TPlayArray::Clear() |
||
299 | { |
||
300 | if (play) delete[] play; |
||
301 | play = 0; nplay = 0; mplay = 0; |
||
302 | } |
||
303 | |||
304 | void TPlayArray::Extend(int n) |
||
305 | { |
||
306 | if (n < 0) n = nplay + 1; |
||
307 | if (mplay < n) |
||
308 | { |
||
309 | PlayWrite *p_old = play; |
||
310 | int m_old = mplay; |
||
311 | mplay = n * 2; |
||
312 | play = new PlayWrite[mplay]; |
||
313 | if (p_old) |
||
314 | { |
||
315 | for (int i = 0; i < m_old; i++) play[i] = p_old[i]; |
||
316 | delete[] p_old; |
||
317 | } |
||
318 | } |
||
319 | } |
||
320 | |||
321 | void TPlayArray::Add(const PlayWrite &pl) |
||
322 | { |
||
323 | Extend(); |
||
324 | play[nplay] = pl; |
||
325 | nplay++; |
||
326 | } |
||
327 | |||
328 | #ifndef __MENUET__ |
||
329 | int TPlayArray::AnalizeKind(FILE *f, const int w[], const char *smb) |
||
330 | { |
||
331 | int i, L, was1 = 1; |
||
332 | unsigned char ch; |
||
333 | int fnd[NELEM(search)]; |
||
334 | for (i = 0; i < NELEM(search); i++) fnd[i] = 1; |
||
335 | for (L = 0; was1; L++) |
||
336 | { |
||
337 | was1 = 0; |
||
338 | if (fread(&ch, 1, 1, f) != 1) return (L == 0) ? -2 : -1; |
||
339 | for (i = 0; w[i] >= 0; i++) if (fnd[i]) |
||
340 | { |
||
341 | if (tolower(ch) != tolower(search[w[i]][L])) fnd[i] = 0; |
||
342 | else |
||
343 | { |
||
344 | was1 = 1; |
||
345 | if (search[w[i]][L+1] == 0) |
||
346 | { |
||
347 | if (smb && smb[0] && fread(&ch, 1, 1, f) == 1) |
||
348 | { |
||
349 | ungetc(ch, f); |
||
350 | if (strchr(smb, tolower(ch)) || isalpha(ch) && strchr(smb, toupper(ch))) |
||
351 | { |
||
352 | break; |
||
353 | } |
||
354 | } |
||
355 | return i; |
||
356 | } |
||
357 | } |
||
358 | } |
||
359 | } |
||
360 | return -10 - L; |
||
361 | } |
||
362 | |||
363 | int TPlayArray::ReadFileTo(FILE *f, char c) |
||
364 | { |
||
365 | char ch; |
||
366 | do |
||
367 | { |
||
368 | if (fread(&ch, 1, 1, f) != 1) return 0; |
||
369 | } |
||
370 | while(ch != c); |
||
371 | return 1; |
||
372 | } |
||
373 | |||
374 | int TPlayArray::ReadFileTo(FILE *f, const char *c) |
||
375 | { |
||
376 | char ch; |
||
377 | do |
||
378 | { |
||
379 | if (fread(&ch, 1, 1, f) != 1) return 0; |
||
380 | } |
||
381 | while(!strchr(c, ch)); |
||
382 | return 1; |
||
383 | } |
||
384 | |||
385 | int TPlayArray::ReadTheText(FILE *f, const char *s) |
||
386 | { |
||
387 | char ch; |
||
388 | while (*s) |
||
389 | { |
||
390 | if (fread(&ch, 1, 1, f) != 1 || ch != *s) return 0; |
||
391 | s++; |
||
392 | } |
||
393 | return 1; |
||
394 | } |
||
395 | |||
396 | int TPlayArray::OpenFile(const char *name, int kind) |
||
397 | { |
||
398 | int k_fnd = 0; |
||
399 | FILE *f = fopen(name, "rb"); |
||
400 | if (!f) return -1; |
||
401 | if (kind == -1) |
||
402 | { |
||
403 | const int w[] = {0, -1}; |
||
404 | int r = AnalizeKind(f, w); |
||
405 | if (r >= 0) {kind = w[r]; k_fnd = 1;} |
||
406 | else if (r == -11) {kind = 3; k_fnd = 3;} |
||
407 | else {fclose(f); return (kind == -2) ? -2 : -10;} |
||
408 | } |
||
409 | if (kind == 0) |
||
410 | { |
||
411 | if (k_fnd < 1 && !ReadFileTo(f, '-')) {fclose(f); return -10;} |
||
412 | k_fnd = 1; |
||
413 | const int w[] = {1, 4, -1}; |
||
414 | int r = AnalizeKind(f, w); |
||
415 | if (r >= 0) {kind = w[r]; k_fnd = 2;} |
||
416 | else {fclose(f); return -10;} |
||
417 | } |
||
418 | if (kind == 1) |
||
419 | { |
||
420 | if (k_fnd < 2 && !ReadFileTo(f, ':')) {fclose(f); return -10;} |
||
421 | k_fnd = 2; |
||
422 | const int w[] = {2, 3, -1}; |
||
423 | int r = AnalizeKind(f, w); |
||
424 | if (r >= 0) {kind = w[r]; k_fnd = 3;} |
||
425 | else {fclose(f); return -10;} |
||
426 | } |
||
427 | if (kind == 4) |
||
428 | { |
||
429 | if (k_fnd < 2 && !ReadFileTo(f, '_')) {fclose(f); return -10;} |
||
430 | k_fnd = 2; |
||
431 | const int w[] = {5, 6, -1}; |
||
432 | int r = AnalizeKind(f, w, ".1234567890"); |
||
433 | if (r >= 0) {kind = w[r]; k_fnd = 3;} |
||
434 | else {fclose(f); return -10;} |
||
435 | } |
||
436 | if (kind == 5) {kind = 3; k_fnd = 0;} |
||
437 | if (kind == 6) |
||
438 | { |
||
439 | if (!ReadFileTo(f, "\n\r")) {fclose(f); return -4;} |
||
440 | k_fnd = 3; |
||
441 | PlayWrite *pl = 0; |
||
442 | int np = THistory::HRead(f, pl); |
||
443 | if (np > 0 && pl) |
||
444 | { |
||
445 | int i; |
||
446 | Extend(nplay + np); |
||
447 | for (i = 0; i < np; i++) |
||
448 | { |
||
449 | if (pl[i].GetN() >= 3) play[nplay++] = pl[i]; |
||
450 | } |
||
451 | } |
||
452 | if (pl) delete[] pl; |
||
453 | fclose(f); |
||
454 | return 1; |
||
455 | } |
||
456 | if (kind == 2) |
||
457 | { |
||
458 | printf("kind = 2\n"); |
||
459 | unsigned char ch; |
||
460 | do |
||
461 | { |
||
462 | if (fread(&ch, 1, 1, f) != 1) {fclose(f); return -10;} |
||
463 | } |
||
464 | while(!isspace(ch)); |
||
465 | PlayWrite pl; |
||
466 | char word[101]; |
||
467 | int i, kind = 0; |
||
468 | for (;;) |
||
469 | { |
||
470 | do |
||
471 | { |
||
472 | if (fread(&ch, 1, 1, f) != 1) break; |
||
473 | } |
||
474 | while(ch == 0 || isspace(ch)); |
||
475 | if (feof(f)) strcpy(word, "[end]"); |
||
476 | else |
||
477 | { |
||
478 | i = 0; |
||
479 | while(ch != 0 && !isspace(ch)) |
||
480 | { |
||
481 | if (i < 100) word[i++] = ch; |
||
482 | if (fread(&ch, 1, 1, f) != 1) break; |
||
483 | } |
||
484 | word[i] = 0; |
||
485 | } |
||
486 | if (word[0] != '[') |
||
487 | { |
||
488 | if (kind == 1) |
||
489 | { |
||
490 | if (word[0] != '#' && word[0] != '$' && word[0] != '%') |
||
491 | { |
||
492 | Position pos; |
||
493 | pos.Read(word, 1); |
||
494 | pl.Clear(); |
||
495 | pl.Add(0, pos); |
||
496 | kind = 2; |
||
497 | } |
||
498 | } |
||
499 | else if (kind == 2) |
||
500 | { |
||
501 | if (word[0] != '#' && word[0] != '$' && word[0] != '%') |
||
502 | { |
||
503 | for (i = 0; word[i] && word[i] != '.' && word[i] != ','; i++) |
||
504 | { |
||
505 | if (!isdigit((unsigned char)word[i])) {i = -1; break;} |
||
506 | } |
||
507 | if (i == -1) |
||
508 | { |
||
509 | PlayWrite::PMv pmv; |
||
510 | if (pl.GetPosL(pmv.pos) < 0) kind = 3; |
||
511 | else if (!pmv.pos.ReadMv(pmv.mv, word, 1)) kind = 3; |
||
512 | else if (pl.Add(pmv.mv) != 0) kind = 3; |
||
513 | } |
||
514 | } |
||
515 | } |
||
516 | } |
||
517 | else |
||
518 | { |
||
519 | if (kind == 2 || kind == 3) |
||
520 | { |
||
521 | if (pl.GetN() > 0) Add(pl); |
||
522 | pl.Clear(); |
||
523 | } |
||
524 | kind = 0; |
||
525 | for (i = 0; word[i]; i++) |
||
526 | { |
||
527 | word[i] = (char)tolower((unsigned char)word[i]); |
||
528 | } |
||
529 | if (strskipref(word, "[end]")) break; |
||
530 | else if (strskipref(word, "[play_v1.1]")) kind = 1; |
||
531 | } |
||
532 | } |
||
533 | fclose(f); |
||
534 | return 1; |
||
535 | } |
||
536 | if (kind == 3) |
||
537 | { |
||
538 | char ch[LEN_WPOS]; |
||
539 | if (k_fnd < 3 && !ReadFileTo(f, '\n')) {fclose(f); return -10;} |
||
540 | k_fnd = 3; |
||
541 | do |
||
542 | { |
||
543 | PlayWrite pl; |
||
544 | for (;;) |
||
545 | { |
||
546 | int i; |
||
547 | for (i = 0; i < LEN_WPOS; i++) |
||
548 | { |
||
549 | if (fread(ch + i, 1, 1, f) != 1 || ch[i] < 0) break; |
||
550 | } |
||
551 | if (i < LEN_WPOS) break; |
||
552 | PlayWrite::PMv pmv0, pmv1; |
||
553 | pmv1.pos.Read(ch); |
||
554 | pmv1.pos.Reverse(); |
||
555 | if (pl.GetPMvL(pmv0) >= 0) |
||
556 | { |
||
557 | TComputerPlayer::Z z; |
||
558 | z.FindAllMoves(pmv0); |
||
559 | int r; |
||
560 | for (r = 0; r < z.narr; r++) |
||
561 | { |
||
562 | if (memcmp(z.array[r].pos.SH, pmv1.pos.SH, sizeof(pmv1.pos.SH)) == 0) |
||
563 | { |
||
564 | pmv1 = z.array[r]; |
||
565 | break; |
||
566 | } |
||
567 | } |
||
568 | if (r < z.narr) pl.Add(pmv1); |
||
569 | else {fclose(f); return -3;} |
||
570 | } |
||
571 | else pl.Add(0, pmv1.pos); |
||
572 | } |
||
573 | if (pl.GetN() > 0) Add(pl); |
||
574 | } |
||
575 | while(!feof(f)); |
||
576 | fclose(f); |
||
577 | return 1; |
||
578 | } |
||
579 | fclose(f); |
||
580 | return -10; |
||
581 | } |
||
582 | |||
583 | int TPlayArray::MsgOpenFile(const char *name, int kind) |
||
584 | { |
||
585 | int n0 = nplay, no_games = 0; |
||
586 | int r = OpenFile(name, kind); |
||
587 | if (r <= 0) |
||
588 | { |
||
589 | if (r == -1) |
||
590 | { |
||
591 | #ifdef BUILD_RUS |
||
592 | printf("\n誨: 䠩 \"%s\".\n", name); |
||
593 | #else |
||
594 | printf("\nCheckers: Can't open the file \"%s\".\n", name); |
||
595 | #endif |
||
596 | return 0; |
||
597 | } |
||
598 | else if (r == -2) |
||
599 | { |
||
600 | #ifdef BUILD_RUS |
||
601 | printf("\n誨: \"%s\" .\n", name); |
||
602 | #else |
||
603 | printf("\nCheckers: The file \"%s\" is empty.\n", name); |
||
604 | #endif |
||
605 | return 0; |
||
606 | } |
||
607 | else if (r == -3) |
||
608 | { |
||
609 | #ifdef BUILD_RUS |
||
610 | printf("\n誨: \"%s\" 訡.\n", name); |
||
611 | #else |
||
612 | printf("\nCheckers: Invalid file \"%s\".\n", name); |
||
613 | #endif |
||
614 | return 0; |
||
615 | } |
||
616 | else if (r == -4) no_games = 1; |
||
617 | else if (r == -10) |
||
618 | { |
||
619 | #ifdef BUILD_RUS |
||
620 | printf("\n誨: \"%s\" ⨯.\n", name); |
||
621 | #else |
||
622 | printf("\nCheckers: The file \"%s\" has wrong type.\n", name); |
||
623 | #endif |
||
624 | return 0; |
||
625 | } |
||
626 | else |
||
627 | { |
||
628 | #ifdef BUILD_RUS |
||
629 | printf("\n誨: 訡 䠩 \"%s\".\n", name); |
||
630 | #else |
||
631 | printf("\nCheckers: Error openning the file \"%s\".\n", name); |
||
632 | #endif |
||
633 | return 0; |
||
634 | } |
||
635 | } |
||
636 | if (!no_games && nplay > n0) return 1; |
||
637 | else |
||
638 | { |
||
639 | #ifdef BUILD_RUS |
||
640 | printf("\n誨: \"%s\" ᮤন .\n", name); |
||
641 | #else |
||
642 | printf("\nCheckers: File \"%s\" don't contains games.\n", name); |
||
643 | #endif |
||
644 | return 0; |
||
645 | } |
||
646 | } |
||
647 | |||
648 | int TPlayArray::SaveFile(const char *name, int num, int kind) |
||
649 | { |
||
650 | FILE *f = 0; |
||
651 | if (kind == 0 || kind == 1 || kind == 2) |
||
652 | { |
||
653 | f = fopen(name, "wt"); |
||
654 | if (!f) return -1; |
||
655 | fprintf(f, "checkers-play:text\n"); |
||
656 | int i0 = num, i; |
||
657 | if (num < 0) {i0 = 0; num = nplay-1;} |
||
658 | for (i = i0; i <= num; i++) if (play[i].GetN() > 0) |
||
659 | { |
||
660 | PlayWrite::PMv pmv; |
||
661 | if (play[i].GetPos(pmv.pos, 0) < 0) return -9; |
||
662 | char *str = new char[10 + NUM_CELL]; |
||
663 | if (!str) return -5; |
||
664 | pmv.pos.Write(str, 1); |
||
665 | fprintf(f, "\n[Play_v1.1]#%d %s\n", i - i0 + 1, str); |
||
666 | delete[] str; |
||
667 | int j; |
||
668 | for (j = 1; j < play[i].GetN(); j++) |
||
669 | { |
||
670 | if (play[i].GetPos(pmv.pos, j - 1) < 0) return -9; |
||
671 | if (play[i].GetMove(pmv.mv, j) < 0) return -9; |
||
672 | str = new char[pmv.pos.GetLenMvEx(pmv.mv, 11)]; |
||
673 | if (!str) return -5; |
||
674 | pmv.pos.WriteMvEx(pmv.mv, str, 11); |
||
675 | if (j % 2 == 1) |
||
676 | { |
||
677 | int nbytes = fprintf(f, "%d. ", (j + 1) / 2); |
||
678 | while(nbytes++ < 5) fprintf(f, " "); |
||
679 | } |
||
680 | fprintf(f, "%s", str); |
||
681 | if (j % 2 == 0 || j == play[i].GetN() - 1) fprintf(f, "\n"); |
||
682 | else fprintf(f, " ,\t"); |
||
683 | delete[] str; |
||
684 | } |
||
685 | } |
||
686 | fclose(f); |
||
687 | return 1; |
||
688 | } |
||
689 | else if (kind == -1 || kind == 3) |
||
690 | { |
||
691 | f = fopen(name, "wb"); |
||
692 | if (!f) return -1; |
||
693 | if (kind == 3) fprintf(f, "checkers-play:bin_1.0\n"); |
||
694 | int i = num; |
||
695 | if (num < 0) {i = 0; num = nplay-1;} |
||
696 | for (; i <= num; i++) |
||
697 | { |
||
698 | char ch[LEN_WPOS]; |
||
699 | Position pos; |
||
700 | play[i].GetPosL(pos); |
||
701 | if (!pos.AllCanEat() && !pos.AllCanMove()) |
||
702 | { |
||
703 | ch[0] = (pos.wmove == 0) ? char(-3) : char(-1); |
||
704 | } |
||
705 | else ch[0] = char(-2); |
||
706 | fwrite(ch, 1, 1, f); |
||
707 | int j; |
||
708 | for (j = 0; j < play[i].GetN(); j++) |
||
709 | { |
||
710 | Position pos; |
||
711 | play[i].GetPos(pos, j); |
||
712 | pos.Reverse(); |
||
713 | pos.Write(ch); |
||
714 | fwrite(ch, LEN_WPOS, 1, f); |
||
715 | } |
||
716 | } |
||
717 | fclose(f); |
||
718 | return 1; |
||
719 | } |
||
720 | if (f) fclose(f); |
||
721 | return -10; |
||
722 | } |
||
723 | |||
724 | int TPlayArray::MsgSaveFile(const char *name, int num, int kind) |
||
725 | { |
||
726 | int r = SaveFile(name, num, kind); |
||
727 | if (r <= 0) |
||
728 | { |
||
729 | if (r == -1) |
||
730 | { |
||
731 | #ifdef BUILD_RUS |
||
732 | printf("\n誨: 䠩 \"%s\" .\n", name); |
||
733 | #else |
||
734 | printf("\nCheckers: Can't open the file \"%s\" to write.\n", name); |
||
735 | #endif |
||
736 | } |
||
737 | else if (r == -5) |
||
738 | { |
||
739 | #ifdef BUILD_RUS |
||
740 | printf("\n誨: 筮 ࠭ 䠩 \"%s\".\n", name); |
||
741 | #else |
||
742 | printf("\nCheckers: Not enough memory to save the file \"%s\".\n", name); |
||
743 | #endif |
||
744 | } |
||
745 | else if (r == -10) |
||
746 | { |
||
747 | #ifdef BUILD_RUS |
||
748 | printf("\n誨: \"%s\" ⨯.\n", name); |
||
749 | #else |
||
750 | printf("\nCheckers: The file \"%s\" has wrong type.\n", name); |
||
751 | #endif |
||
752 | } |
||
753 | else |
||
754 | { |
||
755 | #ifdef BUILD_RUS |
||
756 | printf("\n誨: 訡 ࠭ 䠩 \"%s\".\n", name); |
||
757 | #else |
||
758 | printf("\nCheckers: Error saving the file \"%s\".\n", name); |
||
759 | #endif |
||
760 | } |
||
761 | return 0; |
||
762 | } |
||
763 | else |
||
764 | { |
||
765 | #ifdef BUILD_RUS |
||
766 | printf("\n誨: \"%s\" ࠭.\n", name); |
||
767 | #else |
||
768 | printf("\nCheckers: File \"%s\" saved.\n", name); |
||
769 | #endif |
||
770 | return 1; |
||
771 | } |
||
772 | } |
||
773 | #endif |
||
774 | |||
775 | void TPlayArray::Del(int n) |
||
776 | { |
||
777 | if (!play || n < 0 || n >= nplay) return; |
||
778 | else if (nplay <= 1) {Clear(); return;} |
||
779 | int i; |
||
780 | for (i = n; i < nplay - 1; i++) play[i] = play[i+1]; |
||
781 | play[nplay - 1].Clear(); |
||
782 | nplay--; |
||
783 | } |
||
784 | |||
785 | |||
786 | void SetPlayerString(char *str, int c, TChPlayer *p) |
||
787 | { |
||
788 | strcpy(str, c ? "blue: " : "red: "); |
||
789 | if (!p) strcat(str, "input"); |
||
790 | else strcat(str, "computer"); |
||
791 | } |
||
792 | |||
793 | class TMainDraw : public TSomeDraw |
||
794 | { |
||
795 | public: |
||
796 | TMainDraw() : undo_redo(0), ur_type(-1), cur_play(0), |
||
797 | def_savefile("save.che"), def_savekind(2) {InitButton();} |
||
798 | |||
799 | virtual void Draw(TGraphDraw *drw, int w, int h) |
||
800 | { |
||
801 | int d = button.GetDelt(); |
||
802 | int hh = button.GetHeight(w - 2*d); |
||
803 | if (hh != 0) hh += d; |
||
804 | drw->SetColor(drw->GetBlackColor()); |
||
805 | button.Draw(drw, d, h - hh, w - 2*d); |
||
806 | } |
||
807 | |||
808 | virtual void DrawB(TGraphDraw *drw, TChBoard &board) |
||
809 | { |
||
810 | int urt = (board.GetCurMoveN() <= 0) + |
||
811 | 2*(board.GetCurMoveN() >= board.GetNumMove()); |
||
812 | if (ur_type != urt) SetButtonKind(board); |
||
813 | Draw(drw, board.GetW(), board.GetH()); |
||
814 | } |
||
815 | |||
816 | virtual TIntPoint GetDSize(int w, int h) |
||
817 | { |
||
818 | int d = button.GetDelt(); |
||
819 | int hh = button.GetHeight(w - 2*d); |
||
820 | if (hh != 0) hh += d; |
||
821 | return TIntPoint(0, hh); |
||
822 | } |
||
823 | |||
824 | virtual int ButtonPnt(int xp, int yp, int w, int h, int &n, int k = 0) |
||
825 | { |
||
826 | int d = button.GetDelt(); |
||
827 | int hh = button.GetHeight(w - 2*d); |
||
828 | if (hh != 0) hh += d; |
||
829 | return button.ButtonPnt(xp - d, yp - (h - hh), w - 2*d, n, k); |
||
830 | } |
||
831 | |||
832 | void InitButton(); |
||
833 | void SetButtonKind(const TChBoard &board); |
||
834 | void PressUR(int n, TChBoard &board, TGraphDraw *drw); |
||
835 | void PressLS(int n, TChBoard &board, TGraphDraw *drw); |
||
836 | void CurPlayNorm() |
||
837 | { |
||
838 | if (cur_play < 0 || cur_play >= play.GetNPlay()) cur_play = 0; |
||
839 | } |
||
840 | |||
841 | TXButtonArray button; |
||
842 | TMultiButton *undo_redo, *play_list; |
||
843 | char player_str[2][50], play_num[2][10]; |
||
844 | TPlayArray play; |
||
845 | int cur_play; |
||
846 | char *def_savefile; |
||
847 | int def_savekind; |
||
848 | protected: |
||
849 | int ur_type; |
||
850 | }; |
||
851 | |||
852 | void TMainDraw::InitButton() |
||
853 | { |
||
854 | button.Add(1, 80, 22, "new game"); |
||
855 | button.Add(6, 60, 22, "list"); |
||
856 | button.Add(7, 60, 22, "delete"); |
||
857 | play_list = new TMultiButton(20); |
||
858 | play_list->a.Add(26, 20, 22, "1"); |
||
859 | play_list->a.Add(21, 20, 22, "-"); |
||
860 | play_list->a.Add(23, 37, 22, play_num[0], -2); |
||
861 | play_list->a.Add(22, 20, 22, "+"); |
||
862 | play_list->a.Add(27, 37, 22, play_num[1]); |
||
863 | play_list->SetDefW(); |
||
864 | button.Add(play_list); |
||
865 | button.Add(24, 50, 22, "clear"); |
||
866 | #ifndef __MENUET__ |
||
867 | button.Add(25, 50, 22, "save"); |
||
868 | #endif |
||
869 | button.Add(2, 120, 22, player_str[0]); |
||
870 | button.Add(3, 120, 22, player_str[1]); |
||
871 | button.Add(4, 110, 22, "rotate board"); |
||
872 | undo_redo = new TMultiButton(10); |
||
873 | undo_redo->a.Add(11, 27, 22, "<<"); |
||
874 | undo_redo->a.Add(12, 20, 22, "<"); |
||
875 | undo_redo->a.Add(15, 20, 22, "^"); |
||
876 | undo_redo->a.Add(13, 20, 22, ">"); |
||
877 | undo_redo->a.Add(14, 27, 22, ">>"); |
||
878 | undo_redo->SetDefW(); |
||
879 | button.Add(undo_redo); |
||
880 | button.Add(5, 60, 22, "exit"); |
||
881 | } |
||
882 | |||
883 | void TMainDraw::SetButtonKind(const TChBoard &board) |
||
884 | { |
||
885 | int thick; |
||
886 | TextButton *txb; |
||
887 | TXButton *bt1; |
||
888 | ur_type = 0; |
||
889 | SetPlayerString(player_str[0], 0, board.GetPlayer(0)); |
||
890 | SetPlayerString(player_str[1], 1, board.GetPlayer(1)); |
||
891 | int is_drw = !board.GetPViewStatus(); |
||
892 | bt1 = button.GetButton(2); |
||
893 | if (bt1) bt1->drw = is_drw; |
||
894 | bt1 = button.GetButton(3); |
||
895 | if (bt1) bt1->drw = is_drw; |
||
896 | if (board.GetCurMoveN() <= 0) {ur_type++; thick = 0;} |
||
897 | else thick = 3; |
||
898 | // txb = dynamic_cast |
||
899 | // if (txb) txb->thick = thick; |
||
900 | // txb = dynamic_cast |
||
901 | // if (txb) txb->thick = thick; |
||
902 | // we can use simple static cast |
||
903 | ((TextButton*)(undo_redo->a.GetButton(11)))->thick = thick; |
||
904 | ((TextButton*)(undo_redo->a.GetButton(12)))->thick = thick; |
||
905 | if (board.GetCurMoveN() >= board.GetNumMove()) {ur_type += 2; thick = 0;} |
||
906 | else thick = 3; |
||
907 | // txb = dynamic_cast |
||
908 | // if (txb) txb->thick = thick; |
||
909 | // txb = dynamic_cast |
||
910 | // if (txb) txb->thick = thick; |
||
911 | ((TextButton*)(undo_redo->a.GetButton(13)))->thick = thick; |
||
912 | ((TextButton*)(undo_redo->a.GetButton(14)))->thick = thick; |
||
913 | if (board.GetCurMoveN() < board.GetNumMove() || |
||
914 | (board.GetPViewStatus() && board.GetGameEnd() <= 0)) |
||
915 | { |
||
916 | thick = 3; |
||
917 | } |
||
918 | else thick = 0; |
||
919 | // txb = dynamic_cast |
||
920 | // if (txb) txb->thick = thick; |
||
921 | ((TextButton*)(undo_redo->a.GetButton(15)))->thick = thick; |
||
922 | if (play.GetNPlay() == 0) is_drw = 1; |
||
923 | bt1 = button.GetButton(6); |
||
924 | if (bt1) bt1->drw = is_drw; |
||
925 | bt1 = button.GetButton(7); |
||
926 | if (bt1) bt1->drw = !is_drw; |
||
927 | #ifndef __MENUET__ |
||
928 | bt1 = button.GetButton(25); |
||
929 | if (bt1) bt1->drw = !is_drw; |
||
930 | #endif |
||
931 | is_drw = board.GetPViewStatus() && play.GetNPlay() > 1; |
||
932 | bt1 = button.GetButton(20); |
||
933 | if (bt1) bt1->drw = is_drw; |
||
934 | bt1 = button.GetButton(24); |
||
935 | if (bt1) bt1->drw = is_drw; |
||
936 | if (is_drw) |
||
937 | { |
||
938 | play_num[0][0] = 0; play_num[1][0] = 0; |
||
939 | if (cur_play >= 0) sprintf(play_num[0], "%d", cur_play + 1); |
||
940 | sprintf(play_num[1], "%d", play.GetNPlay()); |
||
941 | thick = (cur_play <= 0) ? 0 : 3; |
||
942 | #define dynamic_cast static_cast |
||
943 | txb = dynamic_cast |
||
944 | if (txb) txb->thick = thick; |
||
945 | txb = dynamic_cast |
||
946 | if (txb) txb->thick = thick; |
||
947 | thick = (cur_play >= play.GetNPlay() - 1) ? 0 : 3; |
||
948 | txb = dynamic_cast |
||
949 | if (txb) txb->thick = thick; |
||
950 | txb = dynamic_cast |
||
951 | if (txb) txb->thick = thick; |
||
952 | #undef dynamic_cast |
||
953 | } |
||
954 | } |
||
955 | |||
956 | void TMainDraw::PressUR(int n, TChBoard &board, TGraphDraw *drw) |
||
957 | { |
||
958 | int mv; |
||
959 | if (n == 11) mv = 0; |
||
960 | else if (n == 12) mv = board.GetCurMoveN() - 1; |
||
961 | else if (n == 13) mv = board.GetCurMoveN() + 1; |
||
962 | else mv = board.GetNumMove(); |
||
963 | if (board.SetCurMoveN(mv)) |
||
964 | { |
||
965 | SetButtonKind(board); |
||
966 | if (drw && drw->IsDraw()) |
||
967 | { |
||
968 | drw->DrawClear(); |
||
969 | board.Draw(drw); |
||
970 | } |
||
971 | } |
||
972 | else Draw(drw, board.GetW(), board.GetH()); |
||
973 | } |
||
974 | |||
975 | void TMainDraw::PressLS(int n, TChBoard &board, TGraphDraw *drw) |
||
976 | { |
||
977 | int need_redraw = 0; |
||
978 | if (n == 6) |
||
979 | { |
||
980 | if (!board.GetPViewStatus() || play.GetNPlay() == 0) |
||
981 | { |
||
982 | PlayWrite cur_pw = board.GetPlay(); |
||
983 | if (cur_pw.GetN() > 2 || play.GetNPlay() == 0) play.Add(board.GetPlay()); |
||
984 | cur_play = play.GetNPlay() - 1; |
||
985 | board.SetPlay(play[cur_play]); |
||
986 | need_redraw = 1; |
||
987 | } |
||
988 | } |
||
989 | else if (n == 7) |
||
990 | { |
||
991 | if (board.GetPViewStatus() && play.GetNPlay() != 0) |
||
992 | { |
||
993 | play.Del(cur_play); |
||
994 | if (play.GetNPlay() >= 1) |
||
995 | { |
||
996 | if (cur_play >= play.GetNPlay()) cur_play--; |
||
997 | board.SetPlay(play[cur_play]); |
||
998 | } |
||
999 | need_redraw = 1; |
||
1000 | } |
||
1001 | } |
||
1002 | else if (n == 21) |
||
1003 | { |
||
1004 | if (cur_play > 0) {board.SetPlay(play[--cur_play]); need_redraw = 1;} |
||
1005 | } |
||
1006 | else if (n == 22) |
||
1007 | { |
||
1008 | if (cur_play < play.GetNPlay() - 1) |
||
1009 | { |
||
1010 | board.SetPlay(play[++cur_play]); need_redraw = 1; |
||
1011 | } |
||
1012 | } |
||
1013 | else if (n == 26) |
||
1014 | { |
||
1015 | if (cur_play > 0) |
||
1016 | { |
||
1017 | cur_play = 0; |
||
1018 | board.SetPlay(play[cur_play]); need_redraw = 1; |
||
1019 | } |
||
1020 | } |
||
1021 | else if (n == 27) |
||
1022 | { |
||
1023 | if (cur_play < play.GetNPlay() - 1) |
||
1024 | { |
||
1025 | cur_play = play.GetNPlay() - 1; |
||
1026 | board.SetPlay(play[cur_play]); need_redraw = 1; |
||
1027 | } |
||
1028 | } |
||
1029 | else if (n == 24) {play.Clear(); cur_play = 0; need_redraw = 1;} |
||
1030 | #ifndef __MENUET__ |
||
1031 | else if (n == 25) |
||
1032 | { |
||
1033 | if (play.GetNPlay() > 0) play.MsgSaveFile(def_savefile, -1, def_savekind); |
||
1034 | } |
||
1035 | else if (n == 28) |
||
1036 | { |
||
1037 | if (play.GetNPlay() > 0) play.MsgSaveFile(def_savefile, cur_play, def_savekind); |
||
1038 | } |
||
1039 | #endif |
||
1040 | if (need_redraw) |
||
1041 | { |
||
1042 | SetButtonKind(board); |
||
1043 | if (drw && drw->IsDraw()) |
||
1044 | { |
||
1045 | drw->DrawClear(); |
||
1046 | board.Draw(drw); |
||
1047 | } |
||
1048 | } |
||
1049 | else Draw(drw, board.GetW(), board.GetH()); |
||
1050 | } |
||
1051 | |||
1052 | struct TTimerDraw |
||
1053 | { |
||
1054 | TTimerDraw(TChBoard *brd, TGraphDraw *drw) : brd(brd), drw(drw) {} |
||
1055 | |||
1056 | TChBoard *brd; |
||
1057 | clock_t st, ut, dt; |
||
1058 | double x0; |
||
1059 | TGraphDraw *drw; |
||
1060 | |||
1061 | static void draw(void *v, int k = 0); |
||
1062 | }; |
||
1063 | |||
1064 | void TTimerDraw::draw(void *v, int k) |
||
1065 | { |
||
1066 | TTimerDraw &d = *(TTimerDraw*)v; |
||
1067 | clock_t t = clock(); |
||
1068 | if (k == 0 && t - d.ut < CLOCKS_PER_SEC * 0.01) return; |
||
1069 | if (k > 0) |
||
1070 | { |
||
1071 | d.st = t; |
||
1072 | if (!d.drw || !d.drw->IsDraw()) return; |
||
1073 | d.drw->DrawClear(); |
||
1074 | d.brd->Draw(d.drw); |
||
1075 | d.dt = t; |
||
1076 | } |
||
1077 | else if (!d.drw || !d.drw->IsDraw()) return; |
||
1078 | double xold = d.x0; |
||
1079 | if (k >= 0) |
||
1080 | { |
||
1081 | d.x0 = (1 - cos(2.0 * (t - d.st) / CLOCKS_PER_SEC)) / 2; |
||
1082 | d.brd->DrawTimer(d.drw, d.x0, 0); |
||
1083 | d.ut = t; |
||
1084 | if (k == 0 && t - d.dt > CLOCKS_PER_SEC * 0.5) |
||
1085 | { |
||
1086 | d.brd->Draw(d.drw); |
||
1087 | d.dt = t; |
||
1088 | } |
||
1089 | } |
||
1090 | if (k <= 0) d.brd->DrawTimer(d.drw, xold, 1); |
||
1091 | } |
||
1092 | |||
1093 | |||
1094 | struct TMainData |
||
1095 | { |
||
1096 | TChBoard board; |
||
1097 | TComputerPlayer player; |
||
1098 | TMainDraw main_draw; |
||
1099 | |||
1100 | TMainData(int id = 0); |
||
1101 | void InitDef(); |
||
1102 | static int EventFunction(const TGraphDraw::event &ev); |
||
1103 | void NewGame(TGraphDraw *drw); |
||
1104 | void RotateBoard(TGraphDraw *drw); |
||
1105 | void PlayerPress(int np, TGraphDraw *drw); |
||
1106 | void GoToCurMove(TGraphDraw *drw); |
||
1107 | }; |
||
1108 | |||
1109 | TMainData::TMainData(int id) : board(id) |
||
1110 | { |
||
1111 | board.SetCheckResize(1); |
||
1112 | board.SetPlayer(1, &player); |
||
1113 | board.SetBottomColor(0); |
||
1114 | board.SetSomeDraw(&main_draw); |
||
1115 | board.SetMinWSize(90, 140); |
||
1116 | } |
||
1117 | |||
1118 | void TMainData::InitDef() |
||
1119 | { |
||
1120 | if (main_draw.play.GetNPlay() > 0) |
||
1121 | { |
||
1122 | main_draw.CurPlayNorm(); |
||
1123 | board.SetPlay(main_draw.play[main_draw.cur_play]); |
||
1124 | } |
||
1125 | main_draw.SetButtonKind(board); |
||
1126 | } |
||
1127 | |||
1128 | void TMainData::NewGame(TGraphDraw *drw) |
||
1129 | { |
||
1130 | board.NewGame(); |
||
1131 | main_draw.SetButtonKind(board); |
||
1132 | if (drw && drw->IsDraw()) {drw->DrawClear(); board.Draw(drw);} |
||
1133 | } |
||
1134 | |||
1135 | void TMainData::RotateBoard(TGraphDraw *drw) |
||
1136 | { |
||
1137 | board.SetBottomColor(3 - board.GetBottomColor()); |
||
1138 | if (drw && drw->IsDraw()) {drw->DrawClear(); board.Draw(drw);} |
||
1139 | } |
||
1140 | |||
1141 | void TMainData::PlayerPress(int np, TGraphDraw *drw) |
||
1142 | { |
||
1143 | if (np != 0 && np != 1) return; |
||
1144 | if (board.GetPlayer(np)) board.SetPlayer(np, 0); |
||
1145 | else board.SetPlayer(np, &player); |
||
1146 | if (board.GetPlayer(0) && !board.GetPlayer(1)) |
||
1147 | { |
||
1148 | board.SetBottomColor(1); |
||
1149 | } |
||
1150 | if (board.GetPlayer(1) && !board.GetPlayer(0)) |
||
1151 | { |
||
1152 | board.SetBottomColor(0); |
||
1153 | } |
||
1154 | main_draw.SetButtonKind(board); |
||
1155 | if (drw && drw->IsDraw()) {drw->DrawClear(); board.Draw(drw);} |
||
1156 | } |
||
1157 | |||
1158 | void TMainData::GoToCurMove(TGraphDraw *drw) |
||
1159 | { |
||
1160 | board.GoToCurMove(); |
||
1161 | main_draw.SetButtonKind(board); |
||
1162 | if (drw && drw->IsDraw()) {drw->DrawClear(); board.Draw(drw);} |
||
1163 | } |
||
1164 | |||
1165 | int TMainData::EventFunction(const TGraphDraw::event &ev) |
||
1166 | { |
||
1167 | if (!ev.any.drw->data) return -100; |
||
1168 | TMainData &data = *(TMainData*)ev.any.drw->data; |
||
1169 | int nbutton, ret = 0; |
||
1170 | switch(ev.type) |
||
1171 | { |
||
1172 | case TGraphDraw::event::button_down: |
||
1173 | if (ev.button.n != 1) break; |
||
1174 | ev.button.drw->OpenDraw(); |
||
1175 | if (data.main_draw.ButtonPnt(ev.button.x, ev.button.y, |
||
1176 | data.board.GetW(), data.board.GetH(), nbutton, 1) > 0) |
||
1177 | { |
||
1178 | data.main_draw.Draw(ev.button.drw, data.board.GetW(), data.board.GetH()); |
||
1179 | ret |= TGraphDraw::ret_setcapture; |
||
1180 | } |
||
1181 | else data.board.MouseClick(ev.button.drw, ev.button.x, ev.button.y); |
||
1182 | ev.button.drw->CloseDraw(); |
||
1183 | break; |
||
1184 | case TGraphDraw::event::mouse_move: |
||
1185 | if (ev.button.n >= 0 && ev.button.n != 1) break; |
||
1186 | ev.button.drw->OpenDraw(); |
||
1187 | if (data.main_draw.ButtonPnt(ev.button.x, ev.button.y, |
||
1188 | data.board.GetW(), data.board.GetH(), nbutton, 2) >= 1000) |
||
1189 | { |
||
1190 | data.main_draw.Draw(ev.button.drw, data.board.GetW(), data.board.GetH()); |
||
1191 | } |
||
1192 | ev.button.drw->CloseDraw(); |
||
1193 | break; |
||
1194 | case TGraphDraw::event::button_up: |
||
1195 | if (ev.button.n != 1) break; |
||
1196 | ev.button.drw->OpenDraw(); |
||
1197 | if (data.main_draw.ButtonPnt(ev.button.x, ev.button.y, |
||
1198 | data.board.GetW(), data.board.GetH(), nbutton, 3) > 0) |
||
1199 | { |
||
1200 | switch(nbutton) |
||
1201 | { |
||
1202 | case 1: |
||
1203 | data.NewGame(ev.button.drw); |
||
1204 | break; |
||
1205 | case 2: |
||
1206 | case 3: |
||
1207 | data.PlayerPress(nbutton - 2, ev.button.drw); |
||
1208 | break; |
||
1209 | case 4: |
||
1210 | data.RotateBoard(ev.button.drw); |
||
1211 | break; |
||
1212 | case 5: |
||
1213 | data.main_draw.Draw(ev.button.drw, data.board.GetW(), data.board.GetH()); |
||
1214 | ev.button.drw->Quit(); |
||
1215 | break; |
||
1216 | case 11: |
||
1217 | case 12: |
||
1218 | case 13: |
||
1219 | case 14: |
||
1220 | data.main_draw.PressUR(nbutton, data.board, ev.button.drw); |
||
1221 | break; |
||
1222 | case 15: |
||
1223 | data.GoToCurMove(ev.button.drw); |
||
1224 | break; |
||
1225 | case 6: |
||
1226 | case 7: |
||
1227 | case 21: |
||
1228 | case 22: |
||
1229 | case 23: |
||
1230 | case 24: |
||
1231 | case 25: |
||
1232 | case 26: |
||
1233 | case 27: |
||
1234 | data.main_draw.PressLS(nbutton, data.board, ev.button.drw); |
||
1235 | break; |
||
1236 | default: |
||
1237 | data.main_draw.Draw(ev.button.drw, data.board.GetW(), data.board.GetH()); |
||
1238 | break; |
||
1239 | } |
||
1240 | } |
||
1241 | ev.button.drw->CloseDraw(); |
||
1242 | break; |
||
1243 | case TGraphDraw::event::draw: |
||
1244 | ev.button.drw->OpenDraw(); |
||
1245 | data.board.Draw(ev.button.drw); |
||
1246 | ev.button.drw->CloseDraw(); |
||
1247 | break; |
||
1248 | case TGraphDraw::event::key_down: |
||
1249 | ev.button.drw->OpenDraw(); |
||
1250 | if (ev.key.k == XK_Left) data.board.PKeyEvent(ev.button.drw, TChBoard::PLeft); |
||
1251 | else if (ev.key.k == XK_Right) data.board.PKeyEvent(ev.button.drw, TChBoard::PRight); |
||
1252 | else if (ev.key.k == XK_Up) data.board.PKeyEvent(ev.button.drw, TChBoard::PUp); |
||
1253 | else if (ev.key.k == XK_Down) data.board.PKeyEvent(ev.button.drw, TChBoard::PDown); |
||
1254 | else if (ev.key.k == XK_Return || ev.key.k == XK_space) |
||
1255 | { |
||
1256 | data.board.PKeyEvent(ev.button.drw, TChBoard::PEnter); |
||
1257 | } |
||
1258 | else if (ev.key.k == XK_Escape) ev.button.drw->Quit(); |
||
1259 | else if (ev.key.k == XK_less) data.main_draw.PressUR(11, data.board, ev.button.drw); |
||
1260 | else if (ev.key.k == XK_comma) data.main_draw.PressUR(12, data.board, ev.button.drw); |
||
1261 | else if (ev.key.k == XK_period) data.main_draw.PressUR(13, data.board, ev.button.drw); |
||
1262 | else if (ev.key.k == XK_greater) data.main_draw.PressUR(14, data.board, ev.button.drw); |
||
1263 | else if (ev.key.k == XK_minus) data.main_draw.PressLS(21, data.board, ev.button.drw); |
||
1264 | else if (ev.key.k == XK_equal) data.main_draw.PressLS(22, data.board, ev.button.drw); |
||
1265 | else if (ev.key.k == XK_underscore) data.main_draw.PressLS(26, data.board, ev.button.drw); |
||
1266 | else if (ev.key.k == XK_plus) data.main_draw.PressLS(27, data.board, ev.button.drw); |
||
1267 | else if (ev.key.k == XK_Delete) data.main_draw.PressLS(7, data.board, ev.button.drw); |
||
1268 | else if (ev.key.k == XK_F8) data.main_draw.PressLS(24, data.board, ev.button.drw); |
||
1269 | else if (ev.key.k == XK_l || ev.key.k == XK_L) data.main_draw.PressLS(6, data.board, ev.button.drw); |
||
1270 | #ifndef __MENUET__ |
||
1271 | else if (ev.key.k == XK_F2) data.main_draw.PressLS(25, data.board, ev.button.drw); |
||
1272 | #endif |
||
1273 | else if (ev.key.k == XK_s || ev.key.k == XK_S) data.main_draw.PressLS(28, data.board, ev.button.drw); |
||
1274 | else if (ev.key.k == XK_slash || ev.key.k == XK_question) data.GoToCurMove(ev.button.drw); |
||
1275 | else if (ev.key.k == XK_n || ev.key.k == XK_N) data.NewGame(ev.button.drw); |
||
1276 | else if (ev.key.k == XK_t || ev.key.k == XK_T) data.RotateBoard(ev.button.drw); |
||
1277 | else if (ev.key.k == XK_r || ev.key.k == XK_R) data.PlayerPress(0, ev.button.drw); |
||
1278 | else if (ev.key.k == XK_b || ev.key.k == XK_B) data.PlayerPress(1, ev.button.drw); |
||
1279 | else if (ev.key.k == XK_f || ev.key.k == XK_F) |
||
1280 | { |
||
1281 | int w, h; |
||
1282 | ev.button.drw->GetSize(w, h); |
||
1283 | ev.button.drw->CloseDraw(); |
||
1284 | if (DuplicateProcess() == 0) |
||
1285 | { |
||
1286 | ev.button.drw->ResReinit(w, h); |
||
1287 | data.board.EraseHistory(); |
||
1288 | } |
||
1289 | } |
||
1290 | ev.button.drw->CloseDraw(); |
||
1291 | break; |
||
1292 | case TGraphDraw::event::close: |
||
1293 | ret = 1; |
||
1294 | break; |
||
1295 | } |
||
1296 | return ret; |
||
1297 | } |
||
1298 | |||
1299 | #ifndef __MENUET__ |
||
1300 | int main(int argc, char **argv) |
||
1301 | { |
||
1302 | randomize(); |
||
1303 | THistory::InitHFile(argv[0]); |
||
1304 | TMainData data(-1); |
||
1305 | if (argv && argc >= 2) |
||
1306 | { |
||
1307 | int i, kx = 1; |
||
1308 | for (i = 1; i < argc; i++) |
||
1309 | { |
||
1310 | if (kx == 1 && argv[i][0] == '-') |
||
1311 | { |
||
1312 | if (strcmp(argv[i], "--") == 0) kx = 0; |
||
1313 | else if (strcmp(argv[i], "-ssf") == 0) ssf = 1; |
||
1314 | else if (strncmp(argv[i], "-save", 5) == 0) |
||
1315 | { |
||
1316 | int j = 5; |
||
1317 | if (argv[i][j]) |
||
1318 | { |
||
1319 | if (argv[i][j] != '=' || !argv[i][j+1]) |
||
1320 | { |
||
1321 | data.main_draw.def_savekind = atoi(argv[i] + j); |
||
1322 | while (argv[i][j] && argv[i][j] != '=') j++; |
||
1323 | if (argv[i][j] != '=' || !argv[i][j+1]) continue; |
||
1324 | } |
||
1325 | data.main_draw.def_savefile = argv[i] + j + 1; |
||
1326 | } |
||
1327 | } |
||
1328 | else printf("Checkers: Invalid key %s\n", argv[i]); |
||
1329 | } |
||
1330 | else if (kx == 0 || kx == 1) |
||
1331 | { |
||
1332 | data.main_draw.play.MsgOpenFile(argv[i], -1); |
||
1333 | } |
||
1334 | } |
||
1335 | } |
||
1336 | data.InitDef(); |
||
1337 | TMainGraphDraw graph( |
||
1338 | #ifdef BUILD_RUS |
||
1339 | "誨" |
||
1340 | #else |
||
1341 | "Checkers" |
||
1342 | #endif |
||
1343 | ); |
||
1344 | TTimerDraw timer_draw(&data.board, &graph); |
||
1345 | data.player.draw = TTimerDraw::draw; data.player.data = &timer_draw; |
||
1346 | graph.evfunc = TMainData::EventFunction; graph.data = &data; |
||
1347 | graph.SetAboutInfo(1); |
||
1348 | graph.Run(TGraphDraw::button_down_mask | TGraphDraw::button_up_mask | |
||
1349 | TGraphDraw::key_down_mask | TGraphDraw::mouse_drag_mask, |
||
1350 | 450 + 100 * ssf, 528); |
||
1351 | return 0; |
||
1352 | } |
||
1353 | #else |
||
1354 | |||
1355 | TMainData* mdata; |
||
1356 | TMainGraphDraw* graph; |
||
1357 | |||
1358 | bool MenuetOnStart(TStartData &me_start, TThreadData) |
||
1359 | { |
||
1360 | mdata = new TMainData(-1); |
||
1361 | graph = new TMainGraphDraw; |
||
1362 | randomize(); |
||
1363 | mdata->InitDef(); |
||
1364 | static TTimerDraw timer_draw(&mdata->board, graph); |
||
1365 | mdata->player.draw = TTimerDraw::draw; mdata->player.data = &timer_draw; |
||
1366 | graph->data = mdata; |
||
1367 | me_start.WinData.Title = |
||
1368 | #ifdef BUILD_RUS |
||
1369 | "誨" |
||
1370 | #else |
||
1371 | "Checkers" |
||
1372 | #endif |
||
1373 | ; |
||
1374 | me_start.Width = 450 + 100*ssf; |
||
1375 | me_start.Height = 528; |
||
1376 | return true; |
||
1377 | } |
||
1378 | bool MenuetOnClose(TThreadData) |
||
1379 | { |
||
1380 | delete mdata; |
||
1381 | delete graph; |
||
1382 | return true; |
||
1383 | } |
||
1384 | int MenuetOnIdle(TThreadData) |
||
1385 | {return -1;} |
||
1386 | void MenuetOnSize(int window_rect[], TThreadData) |
||
1387 | {mdata->board.Resize(window_rect[2]-window_rect[0], window_rect[3]-window_rect[1]);} |
||
1388 | void MenuetOnKeyPress(TThreadData) |
||
1389 | { |
||
1390 | TGraphDraw::event ev; |
||
1391 | ev.type = TGraphDraw::event::key_down; |
||
1392 | ev.any.drw = graph; |
||
1393 | ev.key.k = GetKey(); |
||
1394 | mdata->EventFunction(ev); |
||
1395 | } |
||
1396 | void MenuetOnDraw(void) |
||
1397 | { |
||
1398 | TGraphDraw::event ev; |
||
1399 | ev.type = TGraphDraw::event::draw; |
||
1400 | ev.any.drw = graph; |
||
1401 | mdata->EventFunction(ev); |
||
1402 | } |
||
1403 | void MenuetOnMouse(TThreadData) |
||
1404 | { |
||
1405 | short x,y; |
||
1406 | GetMousePosition(x,y); |
||
1407 | int m = GetMouseButton() & 1; |
||
1408 | static int mprev = 0; |
||
1409 | if (m == mprev) |
||
1410 | return; |
||
1411 | mprev = m; |
||
1412 | TGraphDraw::event ev; |
||
1413 | ev.type = m ? TGraphDraw::event::button_down : TGraphDraw::event::button_up; |
||
1414 | ev.any.drw = graph; |
||
1415 | ev.button.n = 1; |
||
1416 | ev.button.x = x; |
||
1417 | ev.button.y = y; |
||
1418 | mdata->EventFunction(ev); |
||
1419 | } |
||
1420 | #endif>=>>>>=>=>>=>"); |