Subversion Repositories Kolibri OS

Rev

Rev 4481 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
1805 yogev_ezra 1
//
2
 
3
#include "kosSyst.h"
4
#include "KosFile.h"
5
#include "gfxdef.h"
6
#include "gameWnd.h"
7
#include "mcarray.h"
8
#include "lang.h"
9
 
10
//
11
#define EMPTY_PLACE				0
12
 
13
#define LEVEL_PROGRESS_LEFT		(132+1)
14
#define LEVEL_PROGRESS_TOP		(388+21)
15
#define LEVEL_PROGRESS_HEIGHT	4
16
#define LEVEL_PROGRESS_WIDTH	329
17
#define LEVEL_PROGRESS_COLOUR	0xDF2933
18
 
19
#define BONUS_SOMEBLOCK_TOP		(120+21)
20
#define BONUS_SOMEBLOCK_LEFT	(46+1)
21
#define BONUS_FREEBLOCK_TOP		(163+21)
22
#define BONUS_FREEBLOCK_LEFT	(9+1)
23
#define BONUS_DIAGBLOCK_TOP		(213+21)
24
#define BONUS_DIAGBLOCK_LEFT	(48+1)
25
#define BONUS_PROGRESS_HEIGHT	37
26
#define BONUS_PROGRESS_WIDTH	4
27
 
28
#define LEVEL_SCORE_BASE		50
29
 
30
//
31
CKosBitmap gameFace;
32
CKosBitmap gameBlocks;
33
CKosBitmap gameNumbers;
34
CKosBitmap gameBlocksZ[4];
35
//
36
CFishka *fishki[blocksNum];
37
 
38
//
39
char *gameWndTitle;
40
#if LANG == RUS
4481 hidnplayr 41
char gameWndTitle1[] = "” а ®­ ¦¤св ⥡п :)\0";
42
char gameWndTitle2[] = "Ќг ў®в...\0";
1805 yogev_ezra 43
char gameOverText[] = "„ «миҐ ¤®а®ЈЁ ­Ґв!";
44
#else
4481 hidnplayr 45
char gameWndTitle1[] = "Pharaoh waits for you :)\0";
46
char gameWndTitle2[] = "Well...\0";
1805 yogev_ezra 47
char gameOverText[] = "No further way!";
48
#endif
49
//
50
Word gcx, gcy;
51
//
52
#define mapSize			8
53
//
54
//
55
#define blocksLeft		(134+2)
56
#define blocksTop		(43+22)
57
//
58
#define blockTypesNum	10
59
//
60
Byte gameMap[mapSize * mapSize];
61
// уровень
62
int gameLevel;
63
//
64
int maxGameLevel;
65
int startGameLevel;
66
// счёт
67
Dword playerScore;
68
// счётчик добавленных блоков
69
int insertedBlocksCount;
70
// количество блоков для перехода на следующий уровень
71
int levelBlocksLimit;
72
// номер выделенного блока
73
int selectedBlock;
74
// прибавление шага для индикатора прохождения уровня * 1024
75
int levelProgressStep;
76
// занчение индикатора прохождения уровня
77
int levelProgressCount;
78
// блоки для удаления
79
struct sRemoveBlock
80
{
81
	short int ndx;
82
	short int value;
83
	sRemoveBlock()
84
	{
85
		this->ndx = 0;
86
		this->value = 0;
87
	};
88
	sRemoveBlock( int pNdx, int pValue )
89
	{
90
		this->ndx = pNdx;
91
		this->value = pValue;
92
	};
93
};
94
bool operator == ( const sRemoveBlock &b1, const sRemoveBlock &b2 )
95
{
96
	return b1.ndx == b2.ndx;
97
};
98
MCArray toRemoveList;
99
// падающие блоки
100
MCArray toFallList;
101
//
102
bool mouseButtonDisabled;
103
//
104
bool freezeBonuses = false;
105
//
106
int bonusSomeBlockProgressStep;
107
int bonusSomeBlockProgressCount;
108
//
109
int bonusFreeBlockProgressStep;
110
int bonusFreeBlockProgressCount;
111
//
112
int bonusDiagBlockProgressStep;
113
int bonusDiagBlockProgressCount;
114
 
115
 
116
 
117
#define SELECTED_BLOCK_NONE			-1
118
 
119
// бонус включен
120
int bonusSomeBlock;
121
// счётчик блоков для бонуса
122
int bonusSomeBlockCount;
123
// количество блоков, которое надо убрать, чтобы получить бонус
124
int bonusSomeBlockEdge;
125
#define BONUS_SOMEBLOCK_SELECTED	-2
126
//
127
bool bonusFreeBlock;
128
int bonusFreeBlockCount;
129
int bonusFreeBlockEdge;
130
#define BONUS_FREEBLOCK_SELECTED	-3
131
//
132
int bonusDiagBlock;
133
int bonusDiagBlockCount;
134
int bonusDiagBlockEdge;
135
#define BONUS_DIAGBLOCK_SELECTED	-4
136
//
137
void drawScore();
138
// отобразить блоки бонусов
139
void drawBonuses();
140
//
141
void drawLevelNum();
142
//
143
void fadeOutBlocks();
144
//
145
void fallDownBlocks();
146
 
147
 
148
void ClearGameMeters()
149
{
150
	// индикатор прохождение уровня
151
	kos_DrawBar(
152
		LEVEL_PROGRESS_LEFT,
153
		LEVEL_PROGRESS_TOP,
154
		LEVEL_PROGRESS_WIDTH,
155
		LEVEL_PROGRESS_HEIGHT,
156
 
157
		);
158
	// индикаторы бонусов
159
	// some
160
	kos_DrawBar(
161
		33+1,
162
		118+21,
163
		BONUS_PROGRESS_WIDTH,
164
		BONUS_PROGRESS_HEIGHT,
165
 
166
		);
167
	// free
168
	kos_DrawBar(
169
		58+1,
170
		166+21,
171
		BONUS_PROGRESS_WIDTH,
172
		BONUS_PROGRESS_HEIGHT,
173
 
174
		);
175
	// diag
176
	kos_DrawBar(
177
		37+1,
178
		213+21,
179
		BONUS_PROGRESS_WIDTH,
180
		BONUS_PROGRESS_HEIGHT,
181
 
182
		);
183
}
184
 
185
 
186
//
187
void drawGameMeters()
188
{
189
	//
190
	ClearGameMeters();
191
	// индикатор прохождение уровня
192
	kos_DrawBar(
193
		LEVEL_PROGRESS_LEFT,
194
		LEVEL_PROGRESS_TOP,
195
		levelProgressCount,
196
		LEVEL_PROGRESS_HEIGHT,
197
		LEVEL_PROGRESS_COLOUR
198
		);
199
	//
200
	if ( bonusSomeBlockProgressCount > 0 )
201
	// some
202
	kos_DrawBar(
203
		33+1,
204
		118+21+BONUS_PROGRESS_HEIGHT-bonusSomeBlockProgressCount,
205
		BONUS_PROGRESS_WIDTH,
206
		bonusSomeBlockProgressCount,
207
		LEVEL_PROGRESS_COLOUR
208
		);
209
	//
210
	if ( bonusFreeBlockProgressCount > 0 )
211
	// free
212
	kos_DrawBar(
213
		58+1,
214
		166+21+BONUS_PROGRESS_HEIGHT-bonusFreeBlockProgressCount,
215
		BONUS_PROGRESS_WIDTH,
216
		bonusFreeBlockProgressCount,
217
		LEVEL_PROGRESS_COLOUR
218
		);
219
	//
220
	if ( bonusDiagBlockProgressCount > 0 )
221
	// diag
222
	kos_DrawBar(
223
		37+1,
224
		213+21+BONUS_PROGRESS_HEIGHT-bonusDiagBlockProgressCount,
225
		BONUS_PROGRESS_WIDTH,
226
		bonusDiagBlockProgressCount,
227
		LEVEL_PROGRESS_COLOUR
228
		);
229
}
230
 
231
 
232
////////////////////////////////////////////////////////////////////////////////
233
void SetLevelVariables()
234
{
235
	selectedBlock = -1;
236
	levelBlocksLimit = ( gameLevel > 5 ) ? LEVEL_SCORE_BASE * ( gameLevel + 1 ) : LEVEL_SCORE_BASE * ( 11 - gameLevel );
237
	insertedBlocksCount = 0;
238
	//
239
	levelProgressCount = 0;
240
	levelProgressStep = ( LEVEL_PROGRESS_WIDTH * 1024 ) / levelBlocksLimit;
241
	//
242
	bonusSomeBlockEdge = levelBlocksLimit / 4;
243
	bonusFreeBlockEdge = levelBlocksLimit / 3;
244
	bonusDiagBlockEdge = levelBlocksLimit / 2;
245
	//
246
	bonusSomeBlockProgressStep = ( BONUS_PROGRESS_HEIGHT * 1024 ) / bonusSomeBlockEdge;
247
	bonusSomeBlockProgressCount = ( ( ( bonusSomeBlockCount > bonusSomeBlockEdge ) ? bonusSomeBlockEdge : bonusSomeBlockCount ) * bonusSomeBlockProgressStep ) / 1024;
248
	//
249
	bonusFreeBlockProgressStep = ( BONUS_PROGRESS_HEIGHT * 1024 ) / bonusFreeBlockEdge;
250
	bonusFreeBlockProgressCount = ( ( ( bonusFreeBlockCount > bonusFreeBlockEdge ) ? bonusFreeBlockEdge : bonusFreeBlockCount ) * bonusFreeBlockProgressStep ) / 1024;
251
	//
252
	bonusDiagBlockProgressStep = ( BONUS_PROGRESS_HEIGHT * 1024 ) / bonusDiagBlockEdge;
253
	bonusDiagBlockProgressCount = ( ( ( bonusDiagBlockCount > bonusDiagBlockEdge ) ? bonusDiagBlockEdge : bonusDiagBlockCount ) * bonusDiagBlockProgressStep ) / 1024;
254
}
255
 
256
 
257
//
258
int GetScoreByBlocks( int blocksCount )
259
{
260
	int limit, update, i, j, acc;
261
 
262
	//
263
	if ( blocksCount < 3 ) return 0;
264
	//
265
	limit = 20 * blocksNum * gameLevel;
266
	//
267
	update = gameLevel;
268
	acc = 1;
269
	//
270
	j = blocksCount - 3;
271
	//
272
	for ( i = 0; i < j; i++ )
273
	{
274
		//
275
		acc *= gameLevel + 1;
276
		//
277
		if ( ( update + acc ) > limit ) return limit;
278
	}
279
	//
280
	return update + acc;
281
}
282
 
283
 
284
 
285
//
286
int insertNewBlocks()
287
{
288
	int i, j, k, ndx, result, btn;
289
 
290
	//
291
	toFallList.Clear();
292
	//
293
	result = 0;
294
	//
295
	btn = gameLevel > 5 ? blockTypesNum : 5 + gameLevel;
296
	//
297
	ndx = ( mapSize * mapSize ) - mapSize;
298
	//
299
	for ( i = 0; i < mapSize; i++ )
300
	{
301
		for ( j = 0; j < mapSize; j++ )
302
		{
303
			//
304
			k = ndx + i - ( j * mapSize );
305
			//
306
			if ( gameMap[k] == EMPTY_PLACE )
307
			{
308
				//
309
				for ( ; j < (mapSize-1); j++ )
310
				{
311
					//
312
					gameMap[k] = gameMap[k-mapSize];
313
					toFallList.AddExclusive( k );
314
					k -= mapSize;
315
				}
316
				//
317
				gameMap[i] = ( rtlRand() % btn ) + 1;
318
				toFallList.AddExclusive( i );
319
				//
320
				result++;
321
				//
322
				break;
323
			}
324
		}
325
	}
326
	//
327
	insertedBlocksCount += result;
328
	//
329
	return result;
330
}
331
 
332
 
333
// поиск цепочек блоков для удаления, удаление блоков
334
// возвращает приращение счёта игрока
335
int findBlockLines()
336
{
337
	int x, y, ndx;
338
	int removeCount = 0;
339
 
340
	// очистим список для записи результатов
341
	toRemoveList.Clear();
342
	//
343
	for ( y = 0; y < mapSize; y++ )
344
	{
345
		//
346
		for ( x = 0; x < mapSize; x++ )
347
		{
348
			//
349
			ndx = x + ( y * mapSize );
350
			//
351
			if ( gameMap[ndx] == EMPTY_PLACE ) continue;
352
			// проверяем горизонтальную цепочку
353
			if ( x < (mapSize - 2) )
354
			{
355
				//
356
				if (
357
					( gameMap[ndx] == gameMap[ndx+1]  &&  gameMap[ndx] == gameMap[ndx+2] )
358
					|| ( BONUS_FREE_BLOCK == gameMap[ndx]  &&  gameMap[ndx+1] == gameMap[ndx+2] )
359
					|| ( gameMap[ndx] == gameMap[ndx+1]  &&  BONUS_FREE_BLOCK == gameMap[ndx+2] )
360
					|| ( gameMap[ndx] == gameMap[ndx+2]  &&  BONUS_FREE_BLOCK == gameMap[ndx+1] )
361
					)
362
				{
363
					// нашли цепочку, запомним
364
					toRemoveList.AddExclusive( sRemoveBlock( ndx, gameMap[ndx] ) );
365
					toRemoveList.AddExclusive( sRemoveBlock( ndx+1, gameMap[ndx+1] ) );
366
					toRemoveList.AddExclusive( sRemoveBlock( ndx+2, gameMap[ndx+2] ) );
367
				}
368
			}
369
			// проверяем вертикальную цепочку
370
			if ( y < (mapSize - 2) )
371
			{
372
				//
373
				if (
374
					( gameMap[ndx] == gameMap[ndx+mapSize]  &&  gameMap[ndx] == gameMap[ndx+mapSize+mapSize] )
375
					|| ( BONUS_FREE_BLOCK == gameMap[ndx]  &&  gameMap[ndx+mapSize] == gameMap[ndx+mapSize+mapSize] )
376
					|| ( gameMap[ndx] == gameMap[ndx+mapSize]  &&  BONUS_FREE_BLOCK == gameMap[ndx+mapSize+mapSize] )
377
					|| ( gameMap[ndx] == gameMap[ndx+mapSize+mapSize]  &&  BONUS_FREE_BLOCK == gameMap[ndx+mapSize] )
378
					)
379
				{
380
					// нашли цепочку, запомним
381
					toRemoveList.AddExclusive( sRemoveBlock( ndx, gameMap[ndx] ) );
382
					toRemoveList.AddExclusive( sRemoveBlock( ndx+mapSize, gameMap[ndx+mapSize] ) );
383
					toRemoveList.AddExclusive( sRemoveBlock( ndx+mapSize+mapSize, gameMap[ndx+mapSize+mapSize] ) );
384
				}
385
			}
386
		}
387
	}
388
	//
389
	return toRemoveList.GetCount();
390
}
391
 
392
 
393
// проверка на невозможность собрать какую-нибудь линию
394
bool checkGameOut()
395
{
396
	int x, y, ndx;
397
 
398
	//
399
	ndx = 0;
400
	//
401
	for ( y = 0; y < mapSize; y++ )
402
	{
403
		//
404
		for ( x = 0; x < mapSize; x++ )
405
		{
406
			// проверяем горизонтальные цепочки из двух символов
407
			if ( x < (mapSize - 1) )
408
			{
409
				//
410
				if ( gameMap[ndx] == gameMap[ndx+1] )
411
				{
412
					// нашли цепочку из двух блоков
413
					// проверка бонусов
414
					if ( bonusSomeBlock == gameMap[ndx] ) return false;
415
					if ( bonusFreeBlock ) return false;
416
					// проверка обычных перестановок
417
					if ( y > 0 )
418
					{
419
						//
420
						if ( x > 0 )
421
						{
422
							//
423
							if ( gameMap[ndx-mapSize-1] == gameMap[ndx] ) return false;
424
						}
425
						//
426
						if ( x < (mapSize - 2) )
427
						{
428
							//
429
							if ( gameMap[ndx-mapSize+2] == gameMap[ndx] ) return false;
430
						}
431
					}
432
					//
433
					if ( x > 1 )
434
					{
435
						//
436
						if ( gameMap[ndx-2] == gameMap[ndx] ) return false;
437
					}
438
					//
439
					if ( x < (mapSize - 3) )
440
					{
441
						//
442
						if ( gameMap[ndx+3] == gameMap[ndx] ) return false;
443
					}
444
					//
445
					if ( y < (mapSize - 1) )
446
					{
447
						//
448
						if ( x > 0 )
449
						{
450
							//
451
							if ( gameMap[ndx+mapSize-1] == gameMap[ndx] ) return false;
452
						}
453
						//
454
						if ( x < (mapSize - 2) )
455
						{
456
							//
457
							if ( gameMap[ndx+mapSize+2] == gameMap[ndx] ) return false;
458
						}
459
					}
460
					// проверка диагональных перестановок
461
					if ( bonusDiagBlock > 0 )
462
					{
463
						//
464
						if ( y > 0 )
465
						{
466
							//
467
							if ( x > 1 )
468
							{
469
								//
470
								if ( gameMap[ndx-mapSize-2] == gameMap[ndx] ) return false;
471
							}
472
							//
473
							if ( gameMap[ndx-mapSize] == gameMap[ndx] ) return false;
474
							//
475
							if ( x < (mapSize - 2) )
476
							{
477
								//
478
								if ( gameMap[ndx-mapSize+1] == gameMap[ndx] ) return false;
479
							}
480
							//
481
							if ( x < (mapSize - 3) )
482
							{
483
								//
484
								if ( gameMap[ndx-mapSize+3] == gameMap[ndx] ) return false;
485
							}
486
						}
487
						//
488
						if ( y < (mapSize - 1) )
489
						{
490
							//
491
							if ( x > 1 )
492
							{
493
								//
494
								if ( gameMap[ndx+mapSize-2] == gameMap[ndx] ) return false;
495
							}
496
							//
497
							if ( gameMap[ndx+mapSize] == gameMap[ndx] ) return false;
498
							//
499
							if ( x < (mapSize - 2) )
500
							{
501
								//
502
								if ( gameMap[ndx+mapSize+1] == gameMap[ndx] ) return false;
503
							}
504
							//
505
							if ( x < (mapSize - 3) )
506
							{
507
								//
508
								if ( gameMap[ndx+mapSize+3] == gameMap[ndx] ) return false;
509
							}
510
						}
511
					} // закончена проверка диагональных перестановок
512
				}
513
			}
514
			// проверяем горизонтальные цепочки из двух блоков с промежутком
515
			if ( x < (mapSize - 2) )
516
			{
517
				//
518
				if ( gameMap[ndx] == gameMap[ndx+2] )
519
				{
520
					// нашли два блока с промежутком
521
					// проверка бонусов
522
					if ( bonusSomeBlock == gameMap[ndx] ) return false;
523
					if ( bonusFreeBlock ) return false;
524
					//
525
					if ( y > 0 )
526
					{
527
						//
528
						if ( gameMap[ndx-mapSize+1] == gameMap[ndx] ) return false;
529
					}
530
					//
531
					if ( y < (mapSize-1) )
532
					{
533
						//
534
						if ( gameMap[ndx+mapSize+1] == gameMap[ndx] ) return false;
535
					}
536
					// проверка диагональных перестановок
537
					if ( bonusDiagBlock > 0 )
538
					{
539
						//
540
						if ( y > 0 )
541
						{
542
							//
543
							if ( gameMap[ndx-mapSize] == gameMap[ndx] ) return false;
544
							//
545
							if ( gameMap[ndx-mapSize+2] == gameMap[ndx] ) return false;
546
						}
547
						//
548
						if ( y < (mapSize-1) )
549
						{
550
							//
551
							if ( gameMap[ndx+mapSize] == gameMap[ndx] ) return false;
552
							//
553
							if ( gameMap[ndx+mapSize+2] == gameMap[ndx] ) return false;
554
						}
555
					}
556
				}
557
			}
558
			// проверяем вертикальные цепочки из двух символов
559
			if ( y < (mapSize - 1) )
560
			{
561
				//
562
				if ( gameMap[ndx] == gameMap[ndx+mapSize] )
563
				{
564
					// нашли цепочку из двух блоков
565
					// проверка бонусов
566
					if ( bonusSomeBlock == gameMap[ndx] ) return false;
567
					if ( bonusFreeBlock ) return false;
568
					//
569
					if ( x > 0 )
570
					{
571
						//
572
						if ( y > 0 )
573
						{
574
							//
575
							if ( gameMap[ndx-1-mapSize] == gameMap[ndx] ) return false;
576
						}
577
						//
578
						if ( y < (mapSize - 2) )
579
						{
580
							//
581
							if ( gameMap[ndx-1+(2*mapSize)] == gameMap[ndx] ) return false;
582
						}
583
					}
584
					//
585
					if ( y > 1 )
586
					{
587
						//
588
						if ( gameMap[ndx-(2*mapSize)] == gameMap[ndx] ) return false;
589
					}
590
					//
591
					if ( y < (mapSize - 3) )
592
					{
593
						//
594
						if ( gameMap[ndx+(3*mapSize)] == gameMap[ndx] ) return false;
595
					}
596
					//
597
					if ( x < (mapSize - 1) )
598
					{
599
						//
600
						if ( y > 0 )
601
						{
602
							//
603
							if ( gameMap[ndx+1-mapSize] == gameMap[ndx] ) return false;
604
						}
605
						//
606
						if ( y < (mapSize - 2) )
607
						{
608
							//
609
							if ( gameMap[ndx+1+(2*mapSize)] == gameMap[ndx] ) return false;
610
						}
611
					}
612
					// проверка диагональных перестановок
613
					if ( bonusDiagBlock > 0 )
614
					{
615
						//
616
						if ( x > 0 )
617
						{
618
							//
619
							if ( y > 1 )
620
							{
621
								//
622
								if ( gameMap[ndx-1-(2*mapSize)] == gameMap[ndx] ) return false;
623
							}
624
							//
625
							if ( gameMap[ndx-1] == gameMap[ndx] ) return false;
626
							//
627
							if ( y < (mapSize - 2) )
628
							{
629
								//
630
								if ( gameMap[ndx-1+mapSize] == gameMap[ndx] ) return false;
631
							}
632
							//
633
							if ( y < (mapSize - 3) )
634
							{
635
								//
636
								if ( gameMap[ndx-1+(3*mapSize)] == gameMap[ndx] ) return false;
637
							}
638
						}
639
						//
640
						if ( x < (mapSize - 1) )
641
						{
642
							//
643
							if ( y > 1 )
644
							{
645
								//
646
								if ( gameMap[ndx+1-(2*mapSize)] == gameMap[ndx] ) return false;
647
							}
648
							//
649
							if ( gameMap[ndx+1] == gameMap[ndx] ) return false;
650
							//
651
							if ( y < (mapSize - 2) )
652
							{
653
								//
654
								if ( gameMap[ndx+1+mapSize] == gameMap[ndx] ) return false;
655
							}
656
							//
657
							if ( y < (mapSize - 3) )
658
							{
659
								//
660
								if ( gameMap[ndx+1+(3*mapSize)] == gameMap[ndx] ) return false;
661
							}
662
						}
663
					} // закончена проверка диагональных перестановок
664
				}
665
			}
666
			// проверяем вертикальные цепочки из двух блоков с промежутком
667
			if ( y < (mapSize - 2) )
668
			{
669
				//
670
				if ( gameMap[ndx] == gameMap[ndx+(2*mapSize)] )
671
				{
672
					// нашли два блока с промежутком
673
					// проверка бонусов
674
					if ( bonusSomeBlock == gameMap[ndx] ) return false;
675
					if ( bonusFreeBlock ) return false;
676
					//
677
					if ( x > 0 )
678
					{
679
						//
680
						if ( gameMap[ndx-1+mapSize] == gameMap[ndx] ) return false;
681
					}
682
					//
683
					if ( x < (mapSize-1) )
684
					{
685
						//
686
						if ( gameMap[ndx+1+mapSize] == gameMap[ndx] ) return false;
687
					}
688
					// проверка диагональных перестановок
689
					if ( bonusDiagBlock > 0 )
690
					{
691
						//
692
						if ( x > 0 )
693
						{
694
							//
695
							if ( gameMap[ndx-1] == gameMap[ndx] ) return false;
696
							//
697
							if ( gameMap[ndx-1+(2*mapSize)] == gameMap[ndx] ) return false;
698
						}
699
						//
700
						if ( x < (mapSize-1) )
701
						{
702
							//
703
							if ( gameMap[ndx+1] == gameMap[ndx] ) return false;
704
							//
705
							if ( gameMap[ndx+1+(2*mapSize)] == gameMap[ndx] ) return false;
706
						}
707
					}
708
				}
709
			}
710
			//
711
			ndx++;
712
		}
713
	}
714
	//
715
	gameWndTitle = gameWndTitle2;
716
	//
717
	return true;
718
}
719
 
720
 
721
//
722
bool exterminateLines()
723
{
724
	int deletedBlocks, btn, i, j;
725
	bool needRedrawBonus = false;
726
 
727
	//
728
	btn = gameLevel > 5 ? blockTypesNum : 5 + gameLevel;
729
	//
730
	playerScore += GetScoreByBlocks( deletedBlocks = findBlockLines() );
731
	//
732
	if ( ! freezeBonuses )
733
	{
734
		//
735
		if ( gameLevel >= 2 && bonusSomeBlock <= 0 ) bonusSomeBlockCount += deletedBlocks;
736
		if ( gameLevel >= 3 && !bonusFreeBlock ) bonusFreeBlockCount += deletedBlocks;
737
		if ( gameLevel >= 4 && bonusDiagBlock <= 0 ) bonusDiagBlockCount += deletedBlocks;
738
		// первый бонус
739
		if (
740
			( bonusSomeBlockCount >= bonusSomeBlockEdge || ( gameLevel >= 2 && deletedBlocks >= 4 ) )
741
			&& bonusSomeBlock <= 0
742
			)
743
		{
744
			bonusSomeBlock = ( rtlRand() % btn ) + 1;
745
			needRedrawBonus = true;
746
			if ( bonusSomeBlockCount >= bonusSomeBlockEdge ) bonusSomeBlockCount = 0;
747
		}
748
		if ( bonusSomeBlockCount >= bonusSomeBlockEdge ) bonusSomeBlockCount = 0;
749
		// второй бонус
750
		if ( bonusFreeBlockCount >= bonusFreeBlockEdge || ( gameLevel >=3 && deletedBlocks >= 5 ) )
751
		{
752
			bonusFreeBlock = true;
753
			needRedrawBonus = true;
754
			if ( bonusFreeBlockCount >= bonusFreeBlockEdge ) bonusFreeBlockCount = 0;
755
		}
756
		if ( bonusFreeBlockCount >= bonusFreeBlockEdge ) bonusFreeBlockCount = 0;
757
		// третий бонус
758
		if ( bonusDiagBlockCount >= bonusDiagBlockEdge || ( gameLevel >= 4 && deletedBlocks >= 6 ) )
759
		{
760
			bonusDiagBlock = 3;
761
			needRedrawBonus = true;
762
			if ( bonusDiagBlockCount >= bonusDiagBlockEdge ) bonusDiagBlockCount = 0;
763
		}
764
		if ( bonusDiagBlockCount >= bonusDiagBlockEdge ) bonusDiagBlockCount = 0;
765
		//
766
		bonusSomeBlockProgressCount = ( ( ( bonusSomeBlockCount > bonusSomeBlockEdge ) ? bonusSomeBlockEdge : bonusSomeBlockCount ) * bonusSomeBlockProgressStep ) / 1024;
767
		//
768
		bonusFreeBlockProgressCount = ( ( ( bonusFreeBlockCount > bonusFreeBlockEdge ) ? bonusFreeBlockEdge : bonusFreeBlockCount ) * bonusFreeBlockProgressStep ) / 1024;
769
		//
770
		bonusDiagBlockProgressCount = ( ( ( bonusDiagBlockCount > bonusDiagBlockEdge ) ? bonusDiagBlockEdge : bonusDiagBlockCount ) * bonusDiagBlockProgressStep ) / 1024;
771
		//
772
		if ( needRedrawBonus ) drawBonuses();
773
	}
774
	//
775
	j = toRemoveList.GetCount();
776
	//
777
	for ( i = 0; i < j; i++ )
778
	{
779
		gameMap[toRemoveList[i].ndx] = EMPTY_PLACE;
780
	}
781
	//
782
	return toRemoveList.GetCount() > 0;
783
}
784
 
785
 
786
// заполнение игрового поля случайной комбинацией блоков
787
void initGameMap()
788
{
789
	int i, localScore, localInserted, btn;
790
 
791
	//
792
	btn = gameLevel > 5 ? blockTypesNum : 5 + gameLevel;
793
	//
794
	for ( i = 0; i < (mapSize * mapSize); i++ )
795
	{
796
		gameMap[i] = ( rtlRand() % btn ) + 1;
797
	}
798
	//
799
	localScore = playerScore;
800
	localInserted = insertedBlocksCount;
801
	//
802
	freezeBonuses = true;
803
	//
804
	while ( exterminateLines() )
805
	{
806
		while ( insertNewBlocks() > 0 );
807
	}
808
	//
809
	freezeBonuses = false;
810
	//
811
	playerScore = localScore;
812
	insertedBlocksCount = localInserted;
813
}
814
 
815
 
816
// отобразить блоки бонусов
817
void drawBonuses()
818
{
819
	//
820
	kos_PutImage(
821
		selectedBlock != BONUS_SOMEBLOCK_SELECTED ?
822
			fishki[bonusSomeBlock]->GetBits() :
823
			fishki[bonusSomeBlock]->GetHighlightedBits(),
824
		blockSize, blockSize,
825
		BONUS_SOMEBLOCK_LEFT, BONUS_SOMEBLOCK_TOP
826
		);
827
	//
828
	kos_PutImage(
829
		bonusFreeBlock ?
830
		(
831
			selectedBlock != BONUS_FREEBLOCK_SELECTED ?
832
			fishki[BONUS_FREE_BLOCK]->GetBits() :
833
			fishki[BONUS_FREE_BLOCK]->GetHighlightedBits()
834
		) :
835
		fishki[0]->GetBits(),
836
		blockSize, blockSize,
837
		BONUS_FREEBLOCK_LEFT, BONUS_FREEBLOCK_TOP
838
		);
839
	//
840
	kos_PutImage(
841
		bonusDiagBlock > 0 ?
842
			fishki[bonusDiagBlock+BONUS_DIAG_BLOCK-1]->GetBits() :
843
			fishki[0]->GetBits(),
844
		blockSize, blockSize,
845
		BONUS_DIAGBLOCK_LEFT, BONUS_DIAGBLOCK_TOP
846
		);
847
}
848
 
849
 
850
// отобразить игровое поле
851
void drawGameMap()
852
{
853
	int i, j, ndx;
854
 
855
	//
856
	for ( i = 0; i < mapSize; i++ )
857
	{
858
		//
859
		for ( j = 0; j < mapSize; j++ )
860
		{
861
			//
862
			ndx = (i*mapSize) + j;
863
			//
864
			kos_PutImage(
865
				ndx != selectedBlock ?
866
					fishki[gameMap[ndx]]->GetBits() :
867
					fishki[gameMap[ndx]]->GetHighlightedBits(),
868
				blockSize, blockSize,
869
				(j * blockSize) + blocksLeft,
870
				(i * blockSize) + blocksTop
871
				);
872
		}
873
	}
874
}
875
 
876
 
877
// координаты курсора "мыши"
878
int mX, mY;
879
 
880
// проверка на нажатие левой кнопки "мыши"
881
bool mouseLButtonDown()
882
{
883
	static bool isDown = false;
884
	Dword buttons;
885
 
886
	//
887
	kos_GetMouseState( buttons, mX, mY );
888
	//
889
	if ( mouseButtonDisabled ) return false;
890
	//
891
	if ( ( buttons & 1 ) )
892
	{
893
		if ( isDown )
894
			return false;
895
		else
896
		{
897
			isDown = true;
898
			return true;
899
		}
900
	}
901
	else
902
	{
903
		if ( isDown )
904
		{
905
			isDown = false;
906
		}
907
		return false;
908
	}
909
}
910
 
911
//
912
void flipTwoBlocks( int ndx1, int ndx2 )
913
{
914
	Word blX, blY, selX, selY;
915
	Byte fishCode;
916
 
917
	//
918
	blX = ( ndx1 % mapSize ) * blockSize + blocksLeft;
919
	blY = ( ndx1 / mapSize ) * blockSize + blocksTop;
920
	selX = ( ndx2 % mapSize ) * blockSize + blocksLeft;
921
	selY = ( ndx2 / mapSize ) * blockSize + blocksTop;
922
	// переставим блоки местами
923
	fishCode = gameMap[ndx1];
924
	gameMap[ndx1] = gameMap[ndx2];
925
	gameMap[ndx2] = fishCode;
926
	// изображение блока
927
	kos_PutImage(
928
		fishki[gameMap[ndx1]]->GetBits(),
929
		blockSize, blockSize,
930
		blX,
931
		blY
932
		);
933
	// изображение блока
934
	kos_PutImage(
935
		fishki[gameMap[ndx2]]->GetBits(),
936
		blockSize, blockSize,
937
		selX,
938
		selY
939
		);
940
}
941
 
942
 
943
// игровой процесс
944
int GameLoop()
945
{
946
	int result, ndx, blX, blY, selX, selY, ddX, ddY, nSel;
947
	Byte keyCode, mCode;
948
	bool needDecBonus;
949
	Dword buttonID;
950
 
951
	//
952
	gameWndTitle = gameWndTitle1;
953
	gameFace.GetSize( gcx, gcy );
954
	gameLevel = startGameLevel;
955
	playerScore = 0;
956
	bonusSomeBlock = 0;
957
	bonusFreeBlock = false;
958
	bonusDiagBlock = 0;
959
	bonusSomeBlockCount = 0;
960
	bonusFreeBlockCount = 0;
961
	bonusDiagBlockCount = 0;
962
	bonusSomeBlockProgressCount = 0;
963
	bonusFreeBlockProgressCount = 0;
964
	bonusDiagBlockProgressCount = 0;
965
	SetLevelVariables();
966
	mouseButtonDisabled = false;
967
	initGameMap();
968
	//
969
	kos_ChangeWindow( -1, -1, gcx + 1, gcy + 21 );
970
	//
971
	for ( result = GM_NONE; result == GM_NONE; )
972
	{
973
		switch( kos_WaitForEvent() )
974
		{
975
		// надо полностью перерисовать окно
976
		case 1:
977
			DrawGameWindow();
978
			break;
979
 
980
		// клавиатура
981
		case 2:
982
			if ( kos_GetKey( keyCode ) )
983
			{
984
				//
985
				switch ( keyCode )
986
				{
987
				case 0x1B:
988
					result = GM_ABORT;
989
					break;
990
 
991
				default:
992
					break;
993
				}
994
			}
995
			break;
996
 
997
		// кнопки
998
		case 3:
999
			if ( kos_GetButtonID( buttonID ) )
1000
			{
1001
				switch ( buttonID )
1002
				{
4484 hidnplayr 1003
				case 1:
1004
					kos_ExitApp();
1005
 
1805 yogev_ezra 1006
				case 0xA:
1007
					result = GM_ABORT;
1008
					break;
1009
 
1010
				default:
1011
					break;
1012
				}
1013
			}
1014
 
1015
		// событие от мыши
1016
		case 6:
1017
			// нажатие левой кнопки?
1018
			if ( mouseLButtonDown() )
1019
			{
1020
				// считаем координаты относително игрового поля
1021
				blX = mX - blocksLeft;
1022
				blY = mY - blocksTop;
1023
				// попало в игровое поле?
1024
				if ( blX >= 0 && blX < (mapSize * blockSize)
1025
					&& blY >= 0 && blY < (mapSize * blockSize) )
1026
				{
1027
					// получаем координаты в блоках
1028
					blX /= blockSize;
1029
					blY /= blockSize;
1030
					// получаем номер блока на карте
1031
					ndx = blX + ( blY * mapSize );
1032
					// ещё одна проверка, чтобы не вылезти за пределы карты
1033
					if ( ndx >= 0 && ndx < (mapSize * mapSize) )
1034
					{
1035
						// начинаем перерисовку
1036
						kos_WindowRedrawStatus( WRS_BEGIN );
1037
						// если не было выбранного блока
1038
						if ( selectedBlock == SELECTED_BLOCK_NONE )
1039
						{
1040
							// запомним выделенный блок
1041
							selectedBlock = ndx;
1042
							// отметим блок на игровом поле
1043
							kos_PutImage(
1044
								fishki[gameMap[selectedBlock]]->GetHighlightedBits(),
1045
								blockSize, blockSize,
1046
								( selectedBlock % mapSize ) * blockSize + blocksLeft,
1047
								( selectedBlock / mapSize ) * blockSize + blocksTop
1048
								);
1049
						}
1050
						else // помеченный блок уже есть
1051
						{
1052
							if ( selectedBlock >= 0 )
1053
							{
1054
								// координаты помеченного блока
1055
								selX = selectedBlock % mapSize;
1056
								selY = selectedBlock / mapSize;
1057
								// был выбран другой блок?
1058
								if ( ndx != selectedBlock )
1059
								{
1060
									// считаем разность координат двух блоков
1061
									ddX = selX - blX;
1062
									ddY = selY - blY;
1063
									needDecBonus = ( bonusDiagBlock > 0 && abs(ddX) == 1 && abs(ddY) == 1 );
1064
									// если это соседний блок
1065
									if (
1066
										( abs(ddX) == 1 && ddY == 0 )
1067
										|| ( abs(ddY) == 1 && ddX == 0 )
1068
										|| needDecBonus
1069
										)
1070
									{
1071
										// переставим блоки местами
1072
										flipTwoBlocks( ndx, selectedBlock );
1073
										//
1074
										kos_Pause( 16 );
1075
										//
1076
										if ( findBlockLines() > 0 )
1077
										{
1078
											//
1079
											if ( needDecBonus )
1080
											{
1081
												//
1082
												--bonusDiagBlock;
1083
												//
1084
												drawBonuses();
1085
											}
1086
											// снимаем пометку с блока
1087
											selectedBlock = SELECTED_BLOCK_NONE;
1088
											//
1089
											while ( exterminateLines() )
1090
											{
1091
												//
1092
												fadeOutBlocks();
1093
												//
1094
												//drawGameMap();
1095
												//drawScore();
1096
												//
1097
												//kos_Pause( 25 );
1098
												//
1099
												while ( insertNewBlocks() > 0 )
1100
												{
1101
													//
1102
													fallDownBlocks();
1103
													//
1104
													//drawGameMap();
1105
													//kos_Pause( 30 );
1106
												}
1107
											}
1108
											//
1109
											drawScore();
1110
											//
1111
											levelProgressCount = ( ( ( insertedBlocksCount > levelBlocksLimit ) ? levelBlocksLimit : insertedBlocksCount ) * levelProgressStep ) / 1024;
1112
											//
1113
											drawGameMeters();
1114
											//
1115
											if ( insertedBlocksCount > levelBlocksLimit )
1116
											{
1117
												kos_Pause( 50 );
1118
												gameLevel++;
1119
												SetLevelVariables();
1120
												//
1121
												//initGameMap();
1122
												//
1123
												//DrawGameWindow();
1124
												//
1125
												drawGameMeters();
1126
												drawLevelNum();
1127
											}
1128
											else
1129
												//
1130
												if ( mouseButtonDisabled = checkGameOut() )
1131
												{
1132
													//
1133
													DrawGameWindow();
1134
												}
1135
										}
1136
										else
1137
										{
1138
											// не получается линии, блоки ставим на место
1139
											flipTwoBlocks( ndx, selectedBlock );
1140
											// снимаем пометку с блока
1141
											selectedBlock = SELECTED_BLOCK_NONE;
1142
										}
1143
									}
1144
									else // выбран несоседний блок
1145
									{
1146
										// перестим маркер
1147
										kos_PutImage(
1148
											fishki[gameMap[selectedBlock]]->GetBits(),
1149
											blockSize, blockSize,
1150
											selX * blockSize + blocksLeft,
1151
											selY * blockSize + blocksTop
1152
											);
1153
										// пометим выбранный блок
1154
										selectedBlock = ndx;
1155
										// на игровом поле
1156
										kos_PutImage(
1157
											fishki[gameMap[selectedBlock]]->GetHighlightedBits(),
1158
											blockSize, blockSize,
1159
											blX * blockSize + blocksLeft,
1160
											blY * blockSize + blocksTop
1161
											);
1162
									}
1163
								}
1164
								else // выбран тот же блок
1165
								{
1166
									// снимаем пометку
1167
									kos_PutImage(
1168
										fishki[gameMap[selectedBlock]]->GetBits(),
1169
										blockSize, blockSize,
1170
										selX * blockSize + blocksLeft,
1171
										selY * blockSize + blocksTop
1172
										);
1173
									//
1174
									selectedBlock = SELECTED_BLOCK_NONE;
1175
								}
1176
							}
1177
							else
1178
							// ткнули в блок при выбранном бонусе
1179
							{
1180
								//
1181
								mCode = gameMap[ndx];
1182
								//
1183
								switch ( selectedBlock )
1184
								{
1185
								case BONUS_SOMEBLOCK_SELECTED:
1186
									gameMap[ndx] = bonusSomeBlock;
1187
									break;
1188
 
1189
								case BONUS_FREEBLOCK_SELECTED:
1190
									gameMap[ndx] = BONUS_FREE_BLOCK;
1191
									break;
1192
 
1193
								default:
1194
									break;
1195
								}
1196
								//
1197
								if ( findBlockLines() > 0 )
1198
								{
1199
									// убираем использованный бонус
1200
									switch ( selectedBlock )
1201
									{
1202
									case BONUS_SOMEBLOCK_SELECTED:
1203
										bonusSomeBlock = 0;
1204
										break;
1205
 
1206
									case BONUS_FREEBLOCK_SELECTED:
1207
										bonusFreeBlock = false;
1208
										break;
1209
 
1210
									default:
1211
										break;
1212
									}
1213
									// на экране тоже
1214
									drawBonuses();
1215
									drawGameMap();
1216
									kos_Pause( 16 );
1217
									// убираем блоки
1218
									// снимаем пометку с блока
1219
									selectedBlock = SELECTED_BLOCK_NONE;
1220
									//
1221
									while ( exterminateLines() )
1222
									{
1223
										//
1224
										fadeOutBlocks();
1225
										//
1226
										//drawGameMap();
1227
										//drawScore();
1228
										//
1229
										//kos_Pause( 25 );
1230
										//
1231
										while ( insertNewBlocks() > 0 )
1232
										{
1233
											//
1234
											fallDownBlocks();
1235
											//
1236
											//drawGameMap();
1237
											//kos_Pause( 30 );
1238
										}
1239
									}
1240
									//
1241
									drawScore();
1242
									//
1243
									levelProgressCount = ( ( ( insertedBlocksCount > levelBlocksLimit ) ? levelBlocksLimit : insertedBlocksCount ) * levelProgressStep ) / 1024;
1244
									//
1245
									drawGameMeters();
1246
									//
1247
									if ( insertedBlocksCount > levelBlocksLimit )
1248
									{
1249
										kos_Pause( 50 );
1250
										gameLevel++;
1251
										SetLevelVariables();
1252
										//
1253
										//initGameMap();
1254
										//
1255
										//DrawGameWindow();
1256
										//
1257
										drawGameMeters();
1258
										drawLevelNum();
1259
									}
1260
									else
1261
										//
1262
										mouseButtonDisabled = checkGameOut();
1263
								}
1264
								else
1265
								// бонус здесь неприменим
1266
								{
1267
									// вернём взад
1268
									gameMap[ndx] = mCode;
1269
									// пометим блок
1270
									selectedBlock = ndx;
1271
									// на игровом поле
1272
									kos_PutImage(
1273
										fishki[gameMap[selectedBlock]]->GetHighlightedBits(),
1274
										blockSize, blockSize,
1275
										blX * blockSize + blocksLeft,
1276
										blY * blockSize + blocksTop
1277
										);
1278
									// уберём пометку с бонуса
1279
									drawBonuses();
1280
								}
1281
							}
1282
						}
1283
						// определим кнопку
1284
						kos_DefineButton(
1285
							444+1, 2+21,
1286
							54, 20,
1287
							0x6000000A,
1288
 
1289
							);
1290
						// завершаем перерисовку
1291
						kos_WindowRedrawStatus( WRS_END );
1292
					}
1293
				}
1294
				else
1295
				// проверим попадание в бонусы
1296
				{
1297
					nSel = 0;
1298
					//
1299
					if ( mX >= BONUS_SOMEBLOCK_LEFT && (mX - BONUS_SOMEBLOCK_LEFT) <= blockSize
1300
						&& mY >= BONUS_SOMEBLOCK_TOP && (mY - BONUS_SOMEBLOCK_TOP ) <= blockSize )
1301
					{
1302
						//
1303
						nSel = BONUS_SOMEBLOCK_SELECTED;
1304
					}
1305
					//
1306
					if ( mX >= BONUS_FREEBLOCK_LEFT && (mX - BONUS_FREEBLOCK_LEFT) <= blockSize
1307
						&& mY >= BONUS_FREEBLOCK_TOP && (mY - BONUS_FREEBLOCK_TOP ) <= blockSize )
1308
					{
1309
						//
1310
						nSel = BONUS_FREEBLOCK_SELECTED;
1311
					}
1312
					//
1313
					if ( mX >= BONUS_DIAGBLOCK_LEFT && (mX - BONUS_DIAGBLOCK_LEFT) <= blockSize
1314
						&& mY >= BONUS_DIAGBLOCK_TOP && (mY - BONUS_DIAGBLOCK_TOP ) <= blockSize )
1315
					{
1316
						//
1317
						nSel = BONUS_DIAGBLOCK_SELECTED;
1318
					}
1319
					//
1320
					if ( nSel != 0 )
1321
					{
1322
						//
1323
						if ( selectedBlock > 0 )
1324
						{
1325
							// снимаем пометку
1326
							kos_PutImage(
1327
								fishki[gameMap[selectedBlock]]->GetBits(),
1328
								blockSize, blockSize,
1329
								(selectedBlock % mapSize) * blockSize + blocksLeft,
1330
								(selectedBlock / mapSize) * blockSize + blocksTop
1331
								);
1332
						}
1333
						//
1334
						if ( selectedBlock != nSel )
1335
							selectedBlock = nSel;
1336
						else
1337
							selectedBlock = SELECTED_BLOCK_NONE;
1338
						//
1339
						drawBonuses();
1340
					}
1341
				}
1342
 
1343
			}
1344
			//
1345
			break;
1346
 
1347
		default:
1348
			break;
1349
		}
1350
	}
1351
	// отменим кнопку
1352
	kos_DefineButton(
1353
		0, 0,
1354
		0, 0,
1355
		0x8000000A,
1356
 
1357
		);
1358
	//
1359
	if ( gameLevel > maxGameLevel ) maxGameLevel = gameLevel;
1360
	//
1361
	return result;
1362
}
1363
 
1364
//
1365
void drawLevelNum()
1366
{
1367
	Word startX;
1368
 
1369
	//
1370
	if ( gameLevel > 9 )
1371
	{
1372
		//
1373
		startX = LEVEL_LEFT;
1374
		//
1375
		kos_PutImage(
1376
			gameNumbers.GetBits() + ( ( gameLevel / 10 ) * NUM_WIDTH * NUM_HEIGHT ),
1377
			NUM_WIDTH, NUM_HEIGHT,
1378
			startX, LEVEL_TOP
1379
			);
1380
		//
1381
		startX += NUM_WIDTH;
1382
	}
1383
	else
1384
	{
1385
		//
1386
		startX = LEVEL_LEFT + ( (LEVEL_WIDTH - NUM_WIDTH) / 2 );
1387
	}
1388
	//
1389
	kos_PutImage(
1390
		gameNumbers.GetBits() + ( ( gameLevel % 10 ) * NUM_WIDTH * NUM_HEIGHT ),
1391
		NUM_WIDTH, NUM_HEIGHT,
1392
		startX, LEVEL_TOP
1393
		);
1394
}
1395
 
1396
//
1397
void drawScore()
1398
{
1399
	Word startX;
1400
	int i, j;
1401
	char strNum[8];
1402
 
1403
	// число в текстовом виде
1404
	sprintf( strNum, "%U", playerScore );
1405
	//
1406
	j = strlen( strNum );
1407
	//
1408
	startX = SCORE_LEFT + ( ( SCORE_WIDTH - ( NUM_WIDTH * j ) ) / 2 );
1409
	//
1410
	for ( i = 0; i < j; i++ )
1411
	{
1412
		//
1413
		kos_PutImage(
1414
			gameNumbers.GetBits() + ( ( strNum[i] - '0' ) * NUM_WIDTH * NUM_HEIGHT ),
1415
			NUM_WIDTH, NUM_HEIGHT,
1416
			startX, SCORE_TOP
1417
			);
1418
		//
1419
		startX += NUM_WIDTH;
1420
	}
1421
}
1422
 
1423
 
1424
//
1425
void DrawGameWindow()
1426
{
1427
	//
1428
	kos_WindowRedrawStatus( WRS_BEGIN );
1429
	// окно
1430
	kos_DefineAndDrawWindow(
1431
		WNDLEFT, WNDTOP,
1432
		gcx + 1, gcy + 21,
4484 hidnplayr 1433
		0x54, 0x0,				// Skinned fixed size window, dont fill working area, window has caption
1805 yogev_ezra 1434
		0, WNDHEADCOLOUR,
4481 hidnplayr 1435
		gameWndTitle
1805 yogev_ezra 1436
		);
1437
	// заголовок окна
4481 hidnplayr 1438
	  kos_ChangeWindowCaption(gameWndTitle);
1805 yogev_ezra 1439
	gameFace.Draw( 1, 21 );
1440
	drawGameMap();
1441
	drawGameMeters();
1442
	drawBonuses();
1443
	// номер уровня
1444
	drawLevelNum();
1445
	drawScore();
1446
	//
1447
	if ( mouseButtonDisabled )
1448
	{
1449
		//
1450
		kos_DrawBar(
1451
			( gcx + 1 - 160 ) / 2, ( gcy + 21 - 32 ) / 2,
1452
			160, 32,
1453
			0x2383B3
1454
			);
1455
		//
1456
		kos_WriteTextToWindow(
1457
			( gcx + 1 - sizeof( gameOverText ) * 6 ) / 2, ( gcy + 21 - 9 ) / 2,
1458
			0x0, 0xF7F7F7,
1459
			gameOverText,
1460
			sizeof( gameOverText )
1461
			);
1462
	}
1463
	// определим кнопку
1464
	kos_DefineButton(
1465
		444+1, 2+21,
1466
		54, 20,
1467
		0x6000000A,
1468
 
1469
		);
1470
	//
1471
	kos_WindowRedrawStatus( WRS_END );
1472
}
1473
 
1474
 
1475
//
1476
void fadeOutBlocks()
1477
{
1478
	int i, j, k, ndx, x, y;
1479
 
1480
	//
1481
	j = toRemoveList.GetCount();
1482
	//
1483
	for ( k = 0; k < 4; k++ )
1484
	{
1485
		//
1486
		__asm{
1487
				push	eax
1488
				push	ebx
1489
				mov		eax, 18
1490
				mov		ebx, 14
1491
				int		0x40
1492
				pop		eax
1493
				pop		ebx
1494
		}
1495
		//
1496
		for ( i = 0; i < j; i++ )
1497
		{
1498
			//
1499
			ndx = toRemoveList[i].ndx;
1500
			y = ndx / mapSize;
1501
			x = ndx % mapSize;
1502
			//
1503
			kos_PutImage(
1504
				gameBlocksZ[k].GetBits() + ( (toRemoveList[i].value - 1) * blockSize * blockSize ),
1505
				blockSize, blockSize,
1506
				(x * blockSize) + blocksLeft,
1507
				(y * blockSize) + blocksTop
1508
				);
1509
		}
1510
		//
1511
		kos_Pause( 3 );
1512
	}
1513
	//clear
1514
	for ( i = 0; i < j; i++ )
1515
	{
1516
		//
1517
		ndx = toRemoveList[i].ndx;
1518
		y = ndx / mapSize;
1519
		x = ndx % mapSize;
1520
		//
1521
		kos_DrawBar(
1522
			(x * blockSize) + blocksLeft,
1523
			(y * blockSize) + blocksTop,
1524
			blockSize, blockSize, 0
1525
			);
1526
	}
1527
	//
1528
	kos_Pause( 16 );
1529
}
1530
 
1531
 
1532
//
1533
void fallDownBlocks()
1534
{
1535
	int i, j, k, ndx, x, y, height, offset;
1536
 
1537
	//
1538
	j = toFallList.GetCount();
1539
	//
1540
	for ( k = 1; k <= blockSize; k += 2 )
1541
	{
1542
		//
1543
		__asm{
1544
				push	eax
1545
				push	ebx
1546
				mov		eax, 18
1547
				mov		ebx, 14
1548
				int		0x40
1549
				pop		eax
1550
				pop		ebx
1551
		}
1552
		//
1553
		for ( i = 0; i < j; i++ )
1554
		{
1555
			//
1556
			ndx = toFallList[i];
1557
			//
1558
			y = ( ( ( ndx / mapSize ) - 1 ) * blockSize ) + k;
1559
			if ( y < 0 )
1560
			{
1561
				y = 0;
1562
				height = k;
1563
				offset = blockSize - k;
1564
			}
1565
			else
1566
			{
1567
				offset = 0;
1568
				height = blockSize;
1569
			}
1570
			//
1571
			x = ( ndx % mapSize ) * blockSize;
1572
			//
1573
			kos_PutImage(
1574
				fishki[gameMap[ndx]]->GetBits() + ( offset * blockSize ),
1575
				blockSize, height,
1576
				x + blocksLeft,
1577
				y + blocksTop
1578
				);
1579
		}
1580
		//
1581
		kos_Pause( 1 );
1582
	}
1583
}