Е. Буткевич Пишем программы и игры



страница14/15
Дата22.06.2019
Размер2.79 Mb.
ТипКраткое содержание
1   ...   7   8   9   10   11   12   13   14   15
part=_part : dir=_diг;

}

// получить код части тела знеи

private int getPartO { return part; }

// получить код направления движения

private int getDirO { return dir; }

// получить координату х

private int getXO { return x; }

// получить координату у

private int getYO { return y; }

// установить тип части и направление

private void setPartDir(int _part, int jiir) {

// если второй аргумент -1.

// то направление остается неизменным

part=_part;

1f(_d1r!--l) dir=_ dir;

// класс змейки

private class Snake extends FullCanvas implements Runnable {

// константы, определяющие направление движения

private int UP = 0; // вверх

private int DOWN = 3; // вниз

private int LEFT • 1; // влево

private int RIGHT - 2; // вправо

private int HEAD = 0; // голова змеи

private int TAIL - 1; // хвост змеи

private int BODY = 2: // тело змеи

private int ACLOCKWISE_TURN = 3; // сгиб тела против часовой стрелки

private int CLOCKWISE_TURN = 4: U сгиб тела по часовой стрелке

private Vector snake: // хранилище элементов змейки

Полный листинг программы «Змейка» 179

private int width; // ширина экрана

private int height: // высота экрана

private int xHead; // координата х головы змейки

private int yHead; // координата у головы змейки

private Image heart; // картинка сердца

private int xHeart; // координата х сердца

private int yHeart; // координата у сердца

private Image[] images; // массив картинок элементов змейки

private int imageSize: // размер картинки элемента змейки

private int direction: II текущее направление змейки

private boolean eatFlag; // флаг удлинения змейки
private boolean gameOverFlag; // флаг конца игры

private RecordStore recordStore; // хранилище данных

private int recordID; // ID записи параметров

private byte level; // уровень сложности игры

private byte speed; // коэффициент вычисления задержки треда

private byte highScore; // текущий рекорд

// конструктор класса Snake public SnakeO {

// конструктор родительского класса

superO ; Г

// создать массив для картинок-частей змейки

images = new Image[20];

// создать объекты картинок для каждой части

try {

// голова во всех направлениях



images[0] = Image.createlmageC'/HeadUp.png"):

images[l] = Image.createlmageC'/HeadLeft.png");

images[2] = Image. createlmageC'/HeadRight.png"):

images[3] = Image.createlmageC'/HeadDown.png");

// хвост во всех направлениях

images[4] - Image.createlmageC'/TailUp.png"):

images[5] = Image.createlmageC'/TailLeft.png"):

images[6] - Image.createlmageCVTailRight.png");

images[7] = Image.createlmageC '/TailDown.png"):

// тело


images[8] = Image.createlmageC'/BodyUp.png");

images[9] = Image.createlmageC'/BodyLeft.png");

images[10] = images[9];

images[ll] = images[8];

// сгиб тела против часовой стрелки

180 Приложение 1. Полный листинг программы «Змейка»

images[12] • Image. createlmageC '/TurnDownLeft.png");

images[13] = Image.createlmageCVTurnUpLeft.png");

images[14] » Image. createlmageC'/TurnDownRight.png"):

images[15] = Image.createlmageC'/TurnllpRight.png"):

// сгиб тела по часовой стрелке

images[16] = images[14]:

images[17] • images[12]:

images[18] - 1mages[15]:

images[19] = images[13]:

// сердце

heart » Image. createlmageC '/heart.png");

}

catch (IOException ioe) {}



imageSize = images[O].getWidth();

// создать вектор, хранящий элементы змейки

snake = new VectorO ;:

// получить ширину экрана

width = getWidthO:

// получить высоту экрана

height - getHeightO;

II установить координаты головы в центре экрана

// для транспортабельности координаты кратны imageSize

xHead = ((width/2)/imageSize)*imageSize:

yHead = ((height/2)/imageSize)*imageSize;

// создать элемент головы змейки

SnakePart parts • new SnakePartUHead.yHead.HEAD.UP):



II добавить элемент в вектор

snake.addElement(partS):

// создать элемент тела змейки

parts - new SnakeParttxHead.yHead+imageSize.BODY.UP);

snake.addElement(partS):

il создать элемент хвоста змейки

parts - new SnakePart(xHead,yHead+2*imageSize.TAIL.UP):

snake.addElement(partS):

// установить текущее направление движения

direction • UP;

// получить новые координаты для сердца

setNewHeartO:

II сбросить флаг окончания игры

gameOverFlag = false:

// параметры для долговременного хранения

// первый байт - текущий рекорд

// второй байт - уровень сложности игры

Полный листинг программы «Змейка» 181



byte buff[] - {0,5}; try {

// открыть хранилище записей с именем "SNAKE"

recordStore • RecordStore.openRecordStore("SNAKE", true);

// получить список записей хранилища

RecordEnumeration re - recordStore.enumerateRecords(null, null.

false);

// если хранилище пусто if (re.numRecords()==0)

// добавить новую запись параметров игры

recordID - recordStore.addRecord(buff, 0. 2); else

// получить id записи параметров игры

recordID = re.nextRecordldO: // считать запись параметров игры buff = recordStore. getRecord(recordID); // первый байт: текущий рекорд highScore - buff[0]: // второй байт: уровень сложности игры level • buff[l];

// установить коэффициент вычисления задержки speed = 100; 1 catchCRecordStoreException rse) {

// метод перерисовки экрана public void paint(Graphics g) {

// очистить экран g.setColor(OxFFFFFF): g.fillRect(0.0, width. height); g.setColor(OxOOOOOO); // нарисовать рамку g.drawRect(O.O.width-l.height-l); // получить длину змейки int snakeLen = snake.size(): // если поднят флаг конца игры if ( gameOverFlag ) {

// включить вибрацию на 100 мс

DeviceControl.startVibra(lOO.lOO):

// вывести сообщение конца игры

g.drawStringCGAME OVER", width/2,height/2-10.g.HCENTER|g.TOP);

// строка сообщения счета игры

182 Приложение 1. Полный листинг программы «Змейка»

String scoreStr;

// массив долговремен ных данных

byte buffО = new byte[2];

// если установлен новый рекорд

if(highScore < snakeLen) {

highScore • (byte)snakeLen;

// инициализировать массив новыми параметрами

buff[0] - mgnScore;

buff['l] - level:

try {

// записать новый рекорд в хранилище recordStore,setRecоrd(recordID.buff.0.2):



) catch(RecordStoreException rse) {

}

// установить цвет текста красным g.setColor(OxffOOOO); // сформировать строку с новым рекордом scoreStr - new String("HIGH SCORE: "+snakelen): // если рекорд не установлен } else



// сформировать строку со счетом scoreStr * new StringCVOUR SCORE: "+snakeLen): // вывести счет

g. drawString( scoreStr. width/2. height/2+10.g.HCENTER|g. TOP): // если флаг конца игры не поднят ) else {

// для каждого элемента змейки for ( int 1=0: i){

П вывести картинку, индекс которой вычисляется // с помощь» комбинации кода части тела и кода направления g.drawImage(images[4*C(Snai<:ePart)snake.elenientAt(i)) . get Part O+ ((SnakePart)snake.elementAt(i)).getDir()]. ((SnakePart)snake.elementAt(i)).getX(). ((SnakePart)snake.elementAt(i)).getY(). g.HCENTER | g.VCENTER);

)

// вывести картинку сердца



g.drawImage(heart.xHeart.yHeart.g.HCENTER | g.VCENTER): J

// метод setNewHeart; получает новые координаты для сердца public void setNewHeart0 { (

// получить количество возможных позиций по координате х

Полный листинг программы «Змейка» 183

int xPartMaxNum = (width-5)/imageSize;

// получить количество возможных позиций по координате у

int yPartMaxNum = (height-5)/imageSize ;

// получить длину змеи



int len = snake.sizeO;

// создать объект генератора случайных чисел

Random rnd • new Random();

// флаг корректной генерации

boolean setFlag - false;

// повторяем, пока не сгенерируем корректные координаты сердца

while ( !setFlag ) {

// поднять флаг корректной генерации

setFlag - true;

// сгенерировать случайную координату х

xHeart « imageSize*(Math.abs(rnd.nextInt( m xPartMaxNum+l) ;

// сгенерировать случайную координату у

yHeart = imageSize*(Math.abs(rnd.nextInt())£yPartMaxNum+l);

// проверить совпадение координат сердца

// с координатами элементов змеи

for ( int i-0; i

if ( xHeart — ((SnakePartKsnake.elementAt(i))).getXO SS yHeart — ((SnakePart)(snake.elementAtd))).getYO)

// опустить флаг корректной генерации



setFlag = false;

// метод keyPressed обработки нажатий клавиш public synchronized void keyPressed(int keyCode) { // если флаг конца игры не поднят if ( IgameOverFlag ) { switch (keyCode) {

// проверить, можно ли передвигаться в заданном направлении // и вызвать соответствующую функцию передвижения case KEYJUM2:

checkMove(xHead. yHead-imageSize) : moveUpt); break: case KEY_NUM4:

checkMove(xHead-imageSize. yHead): moveLeftO; break; case KEY_NUM6:

184 Приложение 1. Полный листинг программы «Змейка»

moveRightO): break; case KEYJUM8:

checkMove(xHead, yHead+imageSize); moveDownO); break;

// вызвать перерисовку экрана repaintO: } else {

// GameOver! отобразить стартовое меню display setCurrent(menu):

// метод автоматического продвижения змейки public void run() {

// пока не поднят флаг конца игры while (IgameOverFlag) {

// синхронизировать с управлением synchronized (this) {

// продвинуть змейку в текущем направлении ifCdirection—UP) {checkMove(xHead, yHead-7): moveUpO;} if(direction==LEFT) {checkMove(xHead-7. yHead): moveLeftO:} if(direction==RIGHT) {checkMove(xHead+7, yHead); moveRightO: if(direction=—DOWN) {checkMove(xHead, yHead+7): moveDownO;}

)

// вызвать перерисовку экрана



repaintO: try {

// приостановить тред на sleep*level миллисекунд

Thread.sieep(1evel*speed); } catch (InterruptedException e) {

// проверить возможность передвижения // в точку с координатами (хН.уН) public void checkMoveOnt xH, int yH) // для каждого элемента змеи for ( int 1-3: i

Полный листинг программы «Змейка» 185

// если проверяемая точка совпадает с координатами элемента if ( хН — USnakePartHsnake.elementAtdm.getXO && уН - ((SnakePart)(snake.elementAt(i))).getYO)

// поднять флаг конца игры gameOverFlag=true;

// проверить совпадение координат передвижения // с координатами сердца if ( j« — xHeart && уН — yHeart ) { // поднять флаг удлинения змейки eatFlag - true;



!1 пройти в цикле частоты от 100 до 1000 герц с шагом 50 for(int 1=100: i<=1000; i+=50) { П создать звуковой объект Sound beep = new Sound(i.50); // воспроизвести звуковой объект beep.play(l);

\

II увеличить скорость

speed--;


) else

// опустить флаг удлинения змейки

eatFlag - false;

// передвижение влево private void moveLeftO {

// если текущее направление направо, то возврат

if ( direction==RIGHT ) return;



// сдвинуть координату головы влево

xHead-=imageS ize;

// проверить выход за левую границу экрана

if ( xHead <=• imageSize/2+1) { gameOverFlag=true; return; }

// получить первый элемент змеи

SnakePart head = (SnakePartKsnake.firstElementO);

// если текущее направление вверх

if ( direction==UP )

// заменить голову на сгиб против часовой стрелки

head. setPartDir(ACLOCKWISE_TURN. LEFT); else {

// если текущее направление вниз

if ( direction—=DOWN )



186 Приложение 1. Полный листинг программы «Змейка»

// заменить голову на сгиб по часовой стрелке head. setPartDi r(CLOCKWISE _TURN, LEFT); else // если текущее направление влево // заменить голову на тело head.setPartDirCBODY,LEFT);



II создать новый элемент для головы

SnakePart sPart • new SnakePart(xHead,yHead, HEAD, LEFT);

// добавить голову первым элементом вектора

snake.insertElementAt(sPart,0);

// если флаг удлинения змеи поднят if (eatFlag) {

II получить новые координаты для сердца

setNewHeartC);

else {

It продвинуть хвост, // удалить последний элемент snake.removeEletnent(snake.lastElernent()}; It назначить хвостом предпоследний элемент - ((SnakePart JsnakeJastElerent О). setPartDi r (TAIL.-1):

// установить текущее направление direction = LEFT; }



t! передвижение вправо private void moveRightO {

// если текущее направление налево, то возврат

if ( direction==LEFT ) return:

// сдвинуть координату головы вправо

xHead+=imageSize;

// проверить выход за правую границу экрана

if ( xHead >- width-imageSize/2) { gameOverFlag=true; return; )

It если текущее направление змейки вверх.

// заменить голову на сгиб по часовой стрелке

if ( direction — UP) ( (SnakePartK snake.firstElementO))>. setPartDi r(CLOCKWISEJ"URN, RIGHT);

else {


It если текущее направление змейки вниз,

// заменить голову на сгиб против часовой стрелки

if ( direction — DOWN) ((SnakePartKsnake.firstElementO)).

Полный листинг программы «Змейка» 187

setPa rtDi r(ACLOCKWISE_TURN.RIGHT); // продвижение по лрямой, заменить голову на тело else ((SnakePart)(snake.firstElement())).setPartDir(BODY. RIGHT):

// добавить новый элемент головы змейки

SnakePart sPart - new SnakePart(xHead.yHead.HEAD.RIGHT);

snake. insertElementAt(sPart.O);

// если поднят флаг удлинения

if (eatFlag)

// получить новые координаты для сердца

setNewHeartO; else {

// продвинуть хвост

snake. removeElement(snake. lastElementO);

((SnakePartJsnake.lastElementO).setPartDir(TAIL.-l):

// установить текущее направление движения direction - RIGHT: )

// передвижение вверх private void movellpO {

// если текущее направление вниз, то возврат

if ( direction ~ DOWN ) return:

// сдвинуть координату головы вверх yHead-=imageSize;

// проверить выход за верхнюю границу экрана

if ( yHead <= imageSize/2+1) { gameOverFlag=true; return: }

// если текущее направление змейки влево.

// заменить голову на сгиб по часовой стрелке

if ( direction==LEFT) ((SnakePartKsnake.firstElementO)). setPartDi r(CLOCKWI SE_TURN.UP);

else {



II если текущее направление змейки направо,

// заменить голову на сгиб против часовой стрелки

if ( di rection—RIGHT) ((SnakePartMsnake.firstElementO)).

setPartDir(ACLOCKWISEJURN.UP); // продвижение по прямой, заменить голову на тело else ((SnakePart)(snake.firstElementO)).setPartDir(B0DY.UP);



Н добавить новый элемент головы змейки

188 Приложение 1. Полный листинг программы «Змейка»

SnakePart sPart - new SnakePart(xHead.yHead.HEAD.UP); snake.insertEl ementAt(sPart.O);

// если поднят флаг удлинения if (eatFlag)

// получить новые координаты для сердца

setNewHeartO; else {

// продвинуть хвост

snake. removeElement(snake.lastElementO);

((SnakePa rt)snakeЛ astElementO)).setPartDi r(TAIL.-l);

// установить текущее направление движения direction = UP; }

// передвижение вниз private void moveDownO {

// если текущее направление вверх, то возврат

if ( direct1on=4JP ) return;

// сдвинуть координату головы вниз

yHead+=imageSize;

// проверить выход за нижнюю границу экрана

if ( yHead >= height-imageSize/2) { gameOverFlag-true,- return; }

// если текущее направление змейки влево.

// заменить голову на сгиб против часовой стрелки

if ( direction-LEFT) ((SnakePartKsnake. first El ementO)). setPartDir(ACLOCKWISE_TURN.DOWN):

else {

// если текущее направление змейки направо,

// заменить голову на сгиб по часовой стрелке

if ( direction==RIGHT) ((SnakePartXsnake.firstElementO)).

setPartOi r(CLOCKWISE_TURN.DOWN): // продвижение по прямой, заменить голову на тело else ((SnakePart)(snake.firstElement())).setPartDir(BODY.DOWN):

// добавить новый элемент головы змейки

SnakePart sPart = new SnakeParUxHead.yHead.HEAD.DOWN);

snake.1nsertElementAt(sPart.O):

// если поднят флаг удлинения if (eatFlag)

Полный листинг программы «Змейка» 189

// получить новые координаты для сердца setltewHeartO: else {

// продвинуть хвост

snake.removeEIement(snake. 1 astElement ()):

(CSnakePart)snake.1astE1ement()).setPartDir(TAlL.-l):

}

// установить текущее направление движения

direction - DOWN:

}

} II class Snake ] // class SnakeGame

Приложение 2

Полный листинг программы «BookReader»

// Пример программы "BookReader"

//

// Реализован в рамках книги



// "Программируем игры для мобильных телефонов"

//

// (с) Voolkan



import javax.microedition.midlet.MIDlet; import javax.microedition.lcdui .*; import Java.util.Stack;

import java.io.InputStream: import java.io.EOFException: import java.io.IOException;

public class BookReader extends MIDlet {

private Display display: // менеджер дисплея private BookCanvas fCanvas: // экранный фрагмент книги

,public void destroyApp(boolean flag) {

1

public void pauseAppO {



// стартовый метод мидлета

public void startAppO {

// получить ссылку на менеджер дисплея display = Display.getDisplay(this):

Полный листинг программы «BookReader» 191

// создать новую форму с именем основного класса

Form form = new Form(getClass().getNameO);

// создать объект экранного фрагмента книги

fCanvas • new BookCanvasO;

// отобразить экранный фрагмент книги

di splay.setCurrenttfCanvas);

// класс экранного фрагмента книги public class BookCanvas extends Canvas {

private Stack Pagelndex; // стек смещений страниц от начала текста public BookCanvasO {

// создать новый объект стека номеров страниц

Pagelndex - new StackO:

// метод перерисовки объекта экранного фрагмента protected void paint(Graphics g) {

// получить ширину и высоту рабочей области экрана

int gw = g.getClipWidthO;

int gh - g.getClipHeightO:



It создать шрифт

Font font = Font.getFont(Font.FACE_M0N0SPACE. Font.STYLE_PLAIN.

Font.SIZE_SMALL): // установить шрифт g.setFont(font):

// инициализировать поток

InputStream is - getClass0 .getResourceAsStreamC7story.txt"

MyData lnputStream mdis = new MyDatalnputStream(is);

int x=0,y=0: // текущее положение вывода на экране int offset-0; // смещение по исходному тексту

// очистка экрана

g.setColor(255,255.255);

g.fillRect(O,O.gw.gh):

g.setColor(O.O.O);

// получить смещение для очередной страницы if (! Pagelndex.emptyO)



192 Приложение 2. Полный листинг программы «BookReader»

offset-C(Integer)PageIndex.peek()).intValuet):

try{

tl сместиться по тексту до необходимой страницы

mdi s.sk i pBytes(offset); } catchUOException ioe) {}

String sWord: do {

// прочитать очередное слово из потока

sWord - mdis.readWordO:

// продвинуть смещение по файлу на одно слово

offset+=sWord.1ength( );

II если текущая позиция и пиксельная ширина слова

// не выходят за экран

if(x+font.stringWidth(sWord)<=gw) {

// отобразить слово, начиная с текущей позиции

g.drawStringtsWord. x.y. g.TOPjg.LEFT) :

II сместить текущую позицию на пиксельную ширину слова

x+=font. stri ngWidth( sWord);

// если слово последнее в строке, перевести текущую позицию

// в начало новой строки на дисплее

if (mdis.b_endline) { y+=font.getHeight(); x-0: }

I

// слово не входит по ширине с текущей позиции else {



!) перейти на новую строку

y+-font.getHe1ghtO:

// если на экране есть место для новой строки.

// отобразить слово с начала строки

if(y+font,getHeightO

g.drawStringCsWord. o.y. g.TOPjg.LEFT):

// перевести теку|цую позицию на ширину слова

к-font.stri ngW1dth(sWord)\

}

// повторять до тех пор, пока есть место // для новой строки или не кончится файл } while(y+font.getHeight()!mdis.b_endFile):



int index; // смещение начала страницы

II если цикл закончился чтением слова, которое не было

// отображено на экране, сместить начало новой страницы

// назад на одно слово

if(mdis.b_endLine) index-offset; else index=offset-sWord.length():

Полный листинг программы «BookReader» 193

// поместить в стек начало следующей страницы if(!mdis.b_endFile) Pagelndex.push(new Integer(index)): // закрыть поток try{

mdis.closet); ) catch(IOException ioe) {}

// метод обработки нажатий клавиш public void keyPressedCint keyCode){ // обработка нажатий клавиш switch( keyCode) { case KEYJUM1:

// удалить из стека начала // следующей и текущей страницы Pagelndex.popO;

ifdPagelndex.emptyO) Pagelndex.popO; repaint O: break: case KEYJUM2:

// перерисовать экран // (начало следующей страницы уже в стеке) repaintO: break: case KEY_NUM0:

// очистить стек и перерисовать экран Pagelndex.removeAl1Elements (); repaintO; break;

} // class BookCanvas } // class BookReader

import java.io.InputStream; import java.io.DatalnputStream; import java.io.EOFException: import java.io.IOException:

public class MyDatalnputStream extends OatalnputStream {

// кодовая строка преобразования символов private String WIN1251 _TO_UNICODE -



194 Приложение 2. Полный листинг программы «BookReader»

" \u0402\ u0403\u201a\u0453\u201e\u2026\u2020\u2021\u20ac\u2030\u0409\u2039\u040a\u040c\ u040b\ U040f\u0452\u2018\u2019\u201c\u201d\u2022\u2013\u2014\ufffd\u2122\u0459\u203a\u045a\u045c\

U045b\u045f\u00a0\u040e\u045e\u0408\u00a4\u0490\u00a6\u00a7\u0401\u00a9\u0404\u00ab\u00ac\ U00ad\u00ae\u0407\u00b0\u00bl\u0406\u0456\u0491\u00b5\u00b6\u00b7\u0451\u2116\u0454\u00bb\ U0458\u0405\u0455\u0457\u0410\u0411\u0412\u0413\u0414\u0415\u0416\u0417\u0418\u0419\u041a\ U041b\u041c\u041d\u041e\u041f\u0420\u0421\u0422\u0423\u0424\u0425\u0426\u0427\u0428\u0429\

U0439\u043a\u043b\u043c\u043d\u043e\u043f\u0440\u0441\u0442\u0443\u0444\u0445\u0446\u0447\ U0448\u0449\u044a\u044b\u044c\u044d\u044e\u044f";

public boolean b_endLine » false; // флаг конца строки public boolean b_endFile = false; // флаг конца файла

public MyDatalnputStreamdnputStream is) {

super(is);

// метод чтения слова из потока public String readWordO {

int i=0; // счетчик символов в текущем слове b_endFile = false;

char[] word = new char[100]: // массив для чтения слова try {

// читать слово посимвольно до пробела или перевода строки

do word[i++]=(char)convert(readl)nsignedByte()):

while (word[i-l]!=32 && word[i-l]!=10): ) catch(EOFException ioe) {

// конец файла

i--: b_endFile - true;

)

catchdOException ioe) {}



// если слово заканчивается переводом строки, поднять флаг if(word[i-l]==10) b_endl_ine=true: else b_endLine=false: // возвратить строку с прочитанным словом return (new String(word.O.i));

// метод конвертации симолов в Unicode char convert(int ch) {

return (ch < 128) ? (char)ch : WIN1251_T0_UNIC0DE.charAt(ch-128):


Каталог: Техника -> Информационные%20технологии
Информационные%20технологии -> Методические рекомендации по построению систем защиты узлов интернет 1 требования к системе защиты узла интернет 2
Техника -> Учебная программа для специальности: 1-23 01 73 Средства массовой информации
Техника -> Ремонт китайских телефонов
Техника -> Для профилактики и лечения насморка Зачем промывать нос во время насморка?
Техника -> Учебная программа для специальности: 1-23 01 73 Средства массовой информации


Поделитесь с Вашими друзьями:
1   ...   7   8   9   10   11   12   13   14   15


База данных защищена авторским правом ©vossta.ru 2019
обратиться к администрации

    Главная страница