Движение космического корабля - PullRequest
0 голосов
/ 15 февраля 2012

Я создаю мини-игру космического корабля с ощущением, похожим на скорость побега. Я не могу заставить инерцию работать правильно. У меня также есть проблемы с функциями поворота. Если я коснусь клавиш со стрелками влево или вправо, то это не будет похоже на движение кругового типа, которое должно происходить.

$(function() {
var canvas = Raphael('game', 1000, 800);
var background = canvas.rect(0, 0, 1000, 800);
background.attr("fill", "black");

var ship = canvas.rect(200, 200, 10, 35);
ship.attr("fill", "red");
ship.angle = 0;
ship.turnrate = 4;
ship.maxSpeed = 2;
ship.acc = 0;
ship.accSpeed = 0.25;
ship.vel = [0,0];

var up = 0;
var left = 0;
var right = 0;
var speedx = 0;
var speedy = 0;

function moveShip() {
    if (left == 1) {
        ship.angle = (ship.angle - ship.turnrate) % 360;
    }

    if (right == 1) {
        ship.angle = (ship.angle + ship.turnrate) % 360;
    }

    if (up == 1) {
        if (ship.acc < ship.maxSpeed) {
            ship.acc += ship.accSpeed;
        }

        if (ship.acc > ship.maxSpeed) {
            ship.acc = ship.speed;
        }
    }

    if (up == 0) {
        if (ship.acc > 0) {
            ship.acc -= ship.accSpeed;
        }

        if (ship.acc < 0) {
            ship.acc = 0;
        }
    }

    speedx = ship.vel[0] + ship.acc * Math.sin(ship.angle);
    speedy = ship.vel[1] + ship.acc * Math.cos(ship.angle);

    ship.vel = [speedx, speedy];

    ship.transform("");
    ship.rotate(ship.angle);
    ship.attr({x: ship.vel[0], y: ship.vel[1]});

    $("#stats").text("ship.angle: " + ship.angle
            + " vel[0]: " + ship.vel[0] + " vel[1]: " + ship.vel[1]
    + " ship.speed: " + ship.maxSpeed + " speedx: " + speedx + " speedy: " + speedy);
}

function keyPressed(evt) {
    if (evt.keyCode == 38) {
        up = 1;
    }

    if (evt.keyCode == 37) {
        left = 1;
    }

    if (evt.keyCode == 39) {
        right = 1;
    }
}

function keyReleased(evt) {
    if (evt.keyCode == 38) {
        up = 0;
    }

    if (evt.keyCode == 37) {
        left = 0;
    }

    if (evt.keyCode == 39) {
        right = 0;
    }
}

function gameloop() {
    moveShip();
}

$(document).keydown(keyPressed);
$(document).keyup(keyReleased);
setInterval(gameloop, 30);
});

Я искал переполнение стека и Интернет, но большинство вопросов касаются классической игры типа Space Invaders, которая не включает в себя поворот или инерцию.

Буду признателен за любую помощь, я действительно хочу иметь хорошее понимание того, что мне не хватает.

1 Ответ

1 голос
/ 15 февраля 2012

Вы уверены, что хотите изменить ускорение корабля с помощью клавиш со стрелками?Помните, ускорение - это скорость изменения скорости.Это означает, что если у вас есть постоянное ускорение, тогда ваша скорость начнет расти, расти и расти.Довольно скоро у вас будет корабль, который идет слишком быстро.

Результаты чата, здесь для потомков:

$(function() {
    var canvas = Raphael('game', 1000, 800);
    var background = canvas.rect(0, 0, 1000, 800);
    background.attr("fill", "black");

    var ship = canvas.rect(200, 200, 10, 35);
    ship.attr("fill", "red");
    ship.angle = 0;
    ship.turnrate = 4;
    ship.maxSpeed = 0.25;
    ship.acc = 0.25;
    ship.vel = [0,0];
    ship.pos = [500,400];

    var up = 0;
    var left = 0;
    var right = 0;
    var speedx = 0;
    var speedy = 0;

    function moveShip() {
        if (left == 1) {
            ship.angle = (ship.angle - ship.turnrate) % 360;
        }

        if (right == 1) {
            ship.angle = (ship.angle + ship.turnrate) % 360;
        }

        if (up == 1) {
            speedx = ship.vel[0] + ship.acc * Math.sin(ship.angle * Math.PI / 180);
            speedy = ship.vel[1] - ship.acc * Math.cos(ship.angle * Math.PI / 180);

            ship.vel = [speedx, speedy];
        }
        ship.pos = [ship.pos[0] + speedx, ship.pos[1] + speedy];

        ship.transform("");
        ship.rotate(ship.angle);
        ship.attr({x: ship.pos[0], y: ship.pos[1]});

        $("#stats").text("ship.angle: " + ship.angle
                + " vel[0]: " + ship.vel[0] + " vel[1]: " + ship.vel[1]
        + " ship.speed: " + ship.maxSpeed + " speedx: " + speedx + " speedy: " + speedy);
    }

    function keyPressed(evt) {
        if (evt.keyCode == 38) {
            up = 1;
        }

        if (evt.keyCode == 37) {
            left = 1;
        }

        if (evt.keyCode == 39) {
            right = 1;
        }
    }

    function keyReleased(evt) {
        if (evt.keyCode == 38) {
            up = 0;
        }

        if (evt.keyCode == 37) {
            left = 0;
        }

        if (evt.keyCode == 39) {
            right = 0;
        }
    }

    function gameloop() {
        moveShip();
    }

    $(document).keydown(keyPressed);
    $(document).keyup(keyReleased);
    setInterval(gameloop, 30);
});​

Исправлены две ошибки.Был добавлен атрибут pos, так что скорость и положение могут обновляться отдельно.Кроме того, Math.sin и Math.cos принимают углы в радианах, поэтому мы преобразовали угол для этих функций.

Вы можете поиграть с результатами: http://jsfiddle.net/mJcN7/8/

...