Adobe Flash. Создание аркад, головоломок и других игр с помощью ActionScript
Шрифт:
// Бита следует за курсором.
function movePaddle {
paddle._x = _xmouse;
}Следующая функция покажется вам знакомой, так как она очень похожа на функцию moveBall, которая используется в других играх этой главы. Однако есть и некоторые отличия. Для того чтобы узнать, ударился ли мяч о биту, код проверяет, полностью ли они перекрываются (13) . Затем, если все-таки столкновение произошло, скорость мяча по горизонтали определяется тем, где именно мяч ударился о биту (14) . К тому же код для определения, пропущен ли мяч, проще, так как он просто проверяет, пролетел ли мяч сквозь нижнюю стену или нет (15) .
function moveBall {
// Изменяем горизонтальное и вертикальное положение мяча.
x += dx;
y += dy;
// Проверяем, находится ли мяч у правой стены.
if (x+ballRadius > rightWall) {
overshoot = (x+ballRadius) – rightWall;
x -= overshoot*2;
dx *= -1;
}
//
if (x-ballRadius < leftWall) {
overshott = leftWall – (x-ballRadius);
x += overshoot*2;
dx *= -1;
}
// Проверяем, находится ли мяч у верхней стены.
if (y-ballRadius < topWall) {
overshoot = topWall – (y-ballRadius);
y += overshoot*2;
dy *= -1;
}
(13) → // Находится ли мяч там, где должен удариться о биту?
if ((y+ballRadius > paddleTop) and (y-ballRadius < paddleBottom)) {
// Находится ли там бита?
paddleLeft = paddle._x-(paddle._width/2);
paddleRight = paddle._x+(paddle._width/2);
if ((x+ballRadius > paddleLeft) and (x-ballRadius < paddleRight)) {
// Удар о биту.
overshoot = paddleTop – (y+ballRadius);
y += overshoot*2;
dy *= -1;
(14) → // Указываем горизонтальную скорость мяча
// в зависимости от места соприкосновения мяча и биты.
dx = (ball._x – paddle._x)/4;
} else {
// Мяч пролетел мимо биты
passedPaddle = true;
}
}
// Проверяем, пролетел ли мяч мимо биты.
(15) → if (y > bottomWall) {
Mouse.show;
if (numBalls == 0) {
// Больше мячей нет, конец игры.
gotoAndPlay("game over");
} else {
// Еще остался мяч.
numBalls–;
gotoAndPlay("start ball");
}
}
// Определяем расположение мяча.
ball._x = x;
ball._y = y;
}Для того чтобы узнать, ударил ли мяч по блоку, код проверяет все 55 блоков. Блок с горизонтальным положением равным -1000 пикселов уже был сбит, такие блоки игнорируются. В противном случае вызывается функция brickHit, чтобы определить, перекрываются ли мяч и блок. Если да, то блок удаляется, а мяч отталкивается от него. Обратите внимание на переменную leveldone. Изначально ее значение равно true, но оно изменяется на false, как только встречается блок, который не был сбит. Если значение переменной leveldone все еще остается истинным после того, как были использованы все мячи, игроку удалось удалить все блоки. Игра переходит к кадру «start level», но прежде увеличивается скорость мяча по вертикали, то есть переменная dy.
Совет
Необходимо проверить, превышает ли скорость мяча по вертикали значение 7, если да, то нужно снова присвоить ей значение 7. Это вызвано тем, что блоки имеют 8 пикселов в высоту. Если скорость мяча будет равна 8 пикселам или более, тогда мяч будет перелетать через блоки, не выбивая их. К счастью, скорость, равная 7, и так слишком велика – даже хороший игрок долго не продержится.
function checkCollisions {
// Определяем границы мяча.
ballTop = ball._y – ball._height/2;
ballBottom = ball._y + ball._height/2;
ballLeft = ball._x – ball._width/2;
ballRight = ball._x + ball._width/2;
// Допускаем, что уровень пройден.
leveldone = true;
// Выясняем, ударил ли мяч по блоку.
for (i=1; i<=55; i++) {
brick = _root[“a”+i];
// Проверяем, есть ли еще блоки вокруг.
if (brick._x <> -1000) {
if (brickHit(brick)) {
// Если по блоку ударили,
// его нужно удалить с экрана.
brick._x = -1000;
// Изменяем направление движения мяча.
dy *= -1;
} else {
// Блоки еще остались, так что уровень
// не закончен.
leveldone = false;
}
}
}
// Все ли блоки уже выбиты?
if (leveldone) {
// Начать новый уровень.
Mouse.show;
gotoAndPlay("start level");
// Увеличиваем скорость движения мяча по вертикали.
dy += 1;
if (dy > 7) dy=7;
}
}Совет
Обратите внимание, что в функции hitBrick находятся четыре вложенных оператора if. Возможно, вам будет интересно, почему не написать четыре условия в линию, соединив их оператором AND. Дело в скорости. С вложенными операторами if, если одно из условий оказалось ложным, программа не будет проверять остальные. Таким образом, значительно сократится объем работы, которую выполняет программа, и скорость игры увеличится. С операторами AND программе Flash придется проверять все четыре условия,
даже если первое из них ложное.Функция hitBrick проверяет все четыре стороны мяча по отношению ко всем четырем сторонам блока, чтобы узнать, перекрывает ли мяч один из них. Функция возвращает значение либо true, либо false.
function brickHit(brick) {
// Проверяем, попал ли мяч по блоку.
if (ballTop <= brick._y + brick._height/2) {
if (ballBottom >= brick._y – brick._height/2) {
if (ballRight >= brick._x – brick._width/2) {
if (ballLeft <= brick._x + brick._width/2) {
// Все условия верны, то есть мяч
// столкнулся с блоком.
return(true);
}
}
}
}
// Мяч не столкнулся с блоком.
return(false);
}
К сведению
Для работы кода необходимо точно указать множество элементов. Запустите ролик Paddlebricks.fla, чтобы посмотреть готовый вариант программы в действии. Для создания своей собственной версии необходимо запомнить имена всех клипов и в каждый кадр вставить команду stop. Также нужно вставить небольшие фрагменты кода в кнопки и первый кадр.
Ряды блоков были раскрашены с помощью эффекта Tint (Окраска), благодаря чему игра стала визуально более интересной. Вы можете выбрать другое графическое решение, ничего не меняя в функциональной части игры.
Другие возможности
Игра станет интереснее, если в ней будет подсчет очков. Здесь это не сделано для того, чтобы не усложнять код. Просто добавьте текстовое поле «score» и свяжите его с переменной score. Затем прибавляйте единицу каждый раз, когда игрок выбивает блок.
Возможно, вам также захочется добавить текстовые поля, чтобы сообщать пользователю, на каком он уровне и сколько осталось мячей. Можно добавить и звуковые эффекты.Бита и блоки: три измерения
Исходный файл: 3Dpaddlebricks.fla
Итак, в этой главе вы видели, как шар движется по плоскости. А что если шар должен будет двигаться в третьем измерении: в глубину?
На рис. 11.5 показано, как это может выглядеть. Бита – это полупрозрачный квадрат на переднем плане игры. Четыре боковые стены ведут к задней стене, находящейся на некотором расстоянии в глубине экрана. Шар уменьшается по мере того, как становится все дальше от биты. Цель состоит в том, чтобы выбить все кирпичи (блоки) из задней стены.
Рисунок 11.5. Цель этой игры такая же, как и у предыдущей, но перспектива создает некоторую специфичность
Задача проекта
Задача этой игры – создание иллюзии трехмерности. Экраны компьютеров безнадежно завязли в двух измерениях. Но изменяя размер шара и используя линии перспективы, чтобы заставить шар двигаться по мере удаления по направлению к центру экрана, вы можете создать иллюзию, что шарик движется прямо вглубь экрана.
Цель состоит в том, чтобы выбить все 16 блоков из задней стены. Как только шар касается кирпича, он выпадает. Когда шар достигает уровня с битой, она должны занимать такое положение, чтобы коснуться мяча. Место, где шар коснулся биты, определяет новое направление шара.
Когда все 16 кирпичей выбиты, уровень пройден. На следующем уровне шар движется несколько быстрее.
Подход
Чтобы следить за положением мяча, необходима новая переменная. Можно использовать х для горизонтальной и у для вертикальной характеристики положения шара. Третья переменная, z, следит за глубиной – как глубоко внутри экрана находится шар.
Эти три переменные определяют положение мяча внутри воображаемого параллелепипеда, в котором происходит игра. Этот параллелепипед имеет горизонтальные и вертикальные размеры по 400 единиц и 140 единиц в глубину. Чтобы перевести это в координаты экрана, нужна некоторая ловкость. Если вы еще раз посмотрите на рис. 11.5, то заметите, что границы шахты видимы. Наружный квадрат (грань), ближний к игроку, находится на том же уровне, что и бита. Он имеет размер 400x400. Внутренняя грань, представляющая заднюю стену, имеет размер 120x120.
На рисунке 11.6 еще раз изображены обе грани, но на этот раз с обозначенными x, y и z координатами. Верхний левый угол обеих граней имеет значения х и у равные 0. Однако наружный угол имеет значение z равное 0, а внутренний – значение z, равное 140. Остальные углы обозначаются аналогично.
Если мяч находится на позиции (х, у) = (0,0) и движется от 0 к 140 вдоль оси Oz, то он движется вдоль ребра параллелепипеда (рис. 11.6). Если мяч в центре экрана, в положении (200,200), и движется от 0 до 140 вдоль Oz, ему вообще не нужно смещаться вправо или влево. Если мяч в какой-нибудь промежуточной позиции, например (50,65), и движется от 0 до 140 вдоль Oz, то он должен двигаться вдоль своей линии перспективы так, чтобы сохранить свое положение относительно передней и задней граней.