Вокруг ZX Spectrum 1991 г.

Программирование игр: реализация Тетриса на Си


Суть игры "Тетрис" состоит в следующем. В плоский стакан сверху падают фигуры, построенные из четырех квадратов. Играющий может перемещать их по горизонтали и вращать в плоскости "картинки". В каждый момент времени падает ровно одна фигура. Как только дальнейшее падение становится невозможным, фигура останавливается, и сверху начинает падать следующая. Если некоторый горизонтальней ряд между стенками "стакана" оказывается заполненным, он "схлопывается» в результате чего находящиеся выше ряды опускаются вниз. Цель игры - собрать в "стакан" как можно больше фигур. Рассмотрим структуры данных, необходимые для эффективной реализации игры. Начнем со "стакана”. В качестве его модели само-собой напрашивается двумерный массив. Обозначим его stakan [stakw,stakd], где stakw - щирина, a stakd - глубина "стакана". Мы считаем, что "стакан" состоит из stakw*stakd квадратов такого-же размера, как и квадраты, из которых состоят фигуры. Значение stakan [х,у]=0 означает, что квадрат с координатами х;у незаполнен. В противном случае stakan [х,у] интерпретируется как цвет фигуры, покрывающей квадрат с координатами x,y Мы будем использовать 19 фигур, показанных ниже. Внутри каждой фигуры точкой помечен квадрат, который будет называться точкой привязки. Для того, чтобы задать фигуру достаточно описать местоположение каждого из трех оставшихся квадратов по отношению к точке привязки. Обозначим хх[19,3], уу[19,3] – массивы, содержащие координаты квадратов по отношению к точке привязки, т.е. xx[f,i] – это смещение по оси X квадрата i фигуры f относительно точки привязки этой фигуры (уу[f,i] определяется аналогично). Например, для фигуры 0 хх[0,0]=-1, уу[0,0]=-1, хх[0,1]=-1, уу[0,1]=0, хх[0,2]=1, уу[0,2]=0 (ось X расположена как обычно, слева направо, а ось Y - сверху вниз). Некоторые фигуры при поворотах трансформируются друг в друга. Например, поворачивая по часовой стрелке фигуру О мы получим последовательно фигуры 2, 1, 3, а затем снова фигуру 0. Это означает, что нам нет необходимости заниматься разработкой какого-то специального алгоритма поворота фигур. Пово¬рот можно реализовать в виде замены одной фигуры на другую. Для хранения информации о порядке смены фигур при повороте будем использовать массив nextfig[19]. Значение nextfig[i] интерпретируется как номер фигуры, которой заменяется фигура i после ее поворота по часовой стрелке на 90 градусов. Массивы хх, уу, nextfig должны быть проинициализированы в начале программы, поскольку в них содержатся исходные данные. define xscr 3 /* координаты левого верхнего*/ define yscr 0 /* угла "стакана" */ define stakw 10 /* ширина и */ define stakd 20 /* глубина "стакана" */ define wait 30 define waitkey 60 define rotate «z» /* клавиша "поворот" */ define left «o» /* клавиша "влево" */ define right «p» /* клавиша "вправо" */ typedef char * charptr; /*---------------------------------------------------------*/ int nextfig[19]= {3,2,0,1,6,7,5,4,9,8,11,10,14,15,13,12,16,18,17}; int xx[19 ][3]={ {-1,-1,1},{-1,1,1},{0,0,1},{-1,0,0},{-1,-1,1}, {-1,1,1},{0,0,1},{-1,0,0},{-1,-1,0},{-1,0,1}, {-1,-1,0}, {-1,0,1},{-1,0,1},{-1,0,1},{0,-1,0}, {0,1,0},{1,0,1}, {-1,1,2},{0,0,0} }; Int yy[19][3]={ {-1,0,0},{0,0,1},{1,-1,-1},{1,1,-1},{1,0,0}, {0,0,-1},{-1,1,1},{-1,-1,1},{1,0,-1},{-1,-1,0}, {-1,0,1},{0,-1,-1},{0,-1,0}, {0,1,0}, {-1,0,1}, {-1,0,1},{0,1,1},{0,0,0},{-1,1,2} }; int figgen[7]={2,7,9,11,14,16,18}; /* номера "начальных" фигур */ int score,maxscore; int stakan[stakw ][stakd ]; int xfig,yfig,fig,colorfig; int new; /*---------------------------------------------------------*/ Main() {int k; maxscore=0; inline (0xCD,0xD6B); /* чистим экран */ while(1) {score=0; setpos(13,18); printf (« »); game(); /* начинаем игру */ if (score>maxscore) maxscore=score; setpos(13,3); printf(«max %6d»,maxscore); setpos(13,18); printf(«Play game? (Y/N)»); while((k-rawin()!=’y’)if (k=’n’)return; } } /*---------------------------------------------------------*/ setpos (x,y) int x,y; /* установка местоположения выводимого текста */ {printf(«%с%с%с",22,у,х); } /*---------------------------------------------------------*/ Game() {int time,k; Initgame(); /* инициализация */ colorfig=7; while(setfig(5,l,newfig())) /* цикл-пока для новой фигуры есть место */ { while(1) {time-wait; while(time-)if(k=key()) {if (k-left)setfig(xfig-1,yfig,fig); if (k-right)setfig(xfig+1,yfig,fig); if (k-rotate)setfig(xfig,yfig,nextfig[fig]); } if (setfig(xfig,yfig+l,fig)=0) /* если дошли до низа */ {figinst(); compress(); break; } } } } /*---------------------------------------------------------*/ newfig() /* возвращает номер новой фигуры и вычисляет счет */ {charptr р; new-1; score++; setpos (13,1); printf(«score %4d»,score); p=cast(charptr) 23672; /* указатель на псевдослучайное число */ colorfig=(*p)+score) % 7+1; return figgen[(*p)%7]; } /*---------------------------------------------------------*/ figinst() /* запись в stakan */ {int i; stakan[xfig][yfig]=colorfig; for(i=0;i<3;i++)stakan[xfig+xx[fig][i]][yfig+yy[fig][i]]=colorfig; } /*---------------------------------------------------------*/ compress() /* сжать заполненные ряды */ {int x,y,z,str,ax; for(y=stakd-l ;y;y--) {str=l; for(x=0;x=stakw) return 0; if ((b=y+yy[f][i]) <0) return 0; if (b>=stakd) return 0; if (stakan[a][b]) return 0; } if (stakan[x][y]) return 0; return 1; } /*---------------------------------------------------------*/ drawfig(c) int с; /* нарисовать фигуру fig цветом с */ {int i; setscr(xfig,yfig,c); for (i=0;i<3;i++)setscr(xfig+xx [fig][i],yfig+yy [fig][i],c); } /*---------------------------------------------------------*/


СОДЕРЖАНИЕ:


  Оставте Ваш отзыв:

  НИК/ИМЯ
  ПОЧТА (шифруется)
  КОД



Темы: Игры, Программное обеспечение, Пресса, Аппаратное обеспечение, Сеть, Демосцена, Люди, Программирование

Похожие статьи:
Эмуляторы - AY-3-8910, AY-3-8912, YM2149F.
Новости - Новости от FLASH на 22.06.97 года.
Юмор - Бестолковый словарь.
Две эротические историии - Мне почти тридцать лет, а моей подруге Юле девятнадцать...
Chocasutra - A Chocoholics Guide To Sex

В этот день...   23 ноября