Mueve la bola

Este es el segundo paso de los 10 del tutorial de Canvas para el desarrollo de juegos. Puedes encontrar el c贸digo fuente como deber铆a quedar despu茅s de completar la lecci贸n en Gamedev-Canvas-workshop/lesson2.html.

Ya sabes c贸mo dibujar una pelota, lo has aprendido en el art铆culo anterior. Ahora vamos a hacer que se mueva. T茅cnicamente, estaremos pintando la pelota en la pantalla, borr谩ndola y luego pint谩ndola de nuevo en una posici贸n ligeramente diferente cada fotograma para dar la impresi贸n de movimiento, igual que se hace en las pel铆culas.

 

Definir un bucle de dibujo

 

Para actualizar el dibujo del lienzo en cada fotograma, necesitamos definir una funci贸n de dibujo que se ejecutar谩 una y otra vez, cambiando una serie de variables para modificar la posici贸n de cada personaje (sprite). Para que una misma funci贸n se ejecute una y otra vez puedes utilizar una funci贸n de sincronizaci贸n de JavaScript, como setInterval() or requestAnimationFrame().

Elimina todo el c贸digo JavaScript que tienes ahora mismo en de tu archivo HTML, excepto las dos primeras l铆neas, y a帽ade lo siguiente debajo de ellas. La funci贸n draw() se ejecutar谩 dentro de setInterval cada 10 milisegundos:

function draw() {
    // c贸digo para dibujar
}
setInterval(draw, 10);

Gracias a la naturaleza infinita de setInterval, la funci贸n draw () se llamar谩 cada 10 milisegundos por siempre, o hasta que lo detengamos. Ahora, vamos a dibujar la bola. Agrega lo siguiente dentro de tu funci贸n draw ():

ctx.beginPath();
ctx.arc(50, 50, 10, 0, Math.PI*2);
ctx.fillStyle = "#0095DD";
ctx.fill();
ctx.closePath();

Prueba tu c贸digo actualizado ahora 鈥 la bola deber铆a repintarse en cada fotograma (frame).

Hacer que se mueva

Aunque la bola se est谩 dibujando cada 10 milisegundos no se nota porque no hay movimiento, se dibuja una y otra vez en el mismo sitio.Vamos a cambiar eso. En primer lugar, en lugar de dibujar siempre en la posici贸n (50, 50) definiremos un punto de inicio en la parte central inferior del lienzo en las variables llamadas x e y, a continuaci贸n, las utilizaremos para definir la posici贸n en la que se dibuja el c铆rculo.

Primero, agrega las dos l铆neas siguientes a la funci贸n draw (), para definir x e y:

 

var x = canvas.width/2;
var y = canvas.height-30;

 

A continuaci贸n actualiza la funci贸n draw() para usar las variables x e y en el m茅todo arc(), como se muestra en la siguiente l铆nea resaltada:

function draw() {
    ctx.beginPath();
    ctx.arc(x, y, 10, 0, Math.PI*2);
    ctx.fillStyle = "#0095DD";
    ctx.fill();
    ctx.closePath();
}

Ahora viene la parte importante: queremos a帽adir un valor peque帽o a x e y despu茅s de que cada fotograma se haya dibujado para que parezca que la pelota se est谩 moviendo. Definamos estos valores peque帽os como dx y dy, y establezcamos sus valores en 2 y -2 respectivamente. Agrega lo siguiente debajo de sus definiciones de variables x e y:

var dx = 2;
var dy = -2;

Lo 煤ltimo que hay que hacer es actualizar x e y con nuestras variables dx y dy en cada fotograma, de modo que la bola ser谩 pintada en la nueva posici贸n en cada actualizaci贸n. Agrega las dos nuevas l铆neas siguientes indicadas a continuaci贸n a la funci贸n draw ():

function draw() {
    ctx.beginPath();
    ctx.arc(x, y, 10, 0, Math.PI*2);
    ctx.fillStyle = "#0095DD";
    ctx.fill();
    ctx.closePath();
    x += dx;
    y += dy;
}

Guarda el c贸digo de nuevo y pru茅balo en tu navegador. Esto funciona bien, aunque parece que la bola est谩 dejando un rastro detr谩s de ella:

Borrar el  lienzo antes de cada fotograma

La bola est谩 dejando un rastro porque estamos pintando un nuevo c铆rculo en cada fotograma sin borrar el anterior. No te preocupes, porque hay un m茅todo para borrar todo el contenido de lienzo: clearRect (). Este m茅todo tiene cuatro par谩metros: las coordenadas x e y de la esquina superior izquierda de un rect谩ngulo y las coordenadas x e y de la esquina inferior derecha de un rect谩ngulo. En todo el 谩rea definida por ese rect谩ngulo se borrar谩 cualquier cosa que se haya pintado antes.
 

A帽ade la siguiente nueva l铆nea resaltada a la funci贸n draw():

function draw() {
    ctx.clearRect(0, 0, canvas.width, canvas.height);
    ctx.beginPath();
    ctx.arc(x, y, 10, 0, Math.PI*2);
    ctx.fillStyle = "#0095DD";
    ctx.fill();
    ctx.closePath();
    x += dx;
    y += dy;
}

Guarda tu c贸digo y vuelve a probarlo. Esta vez ver谩s el movimiento de la bola sin dejar rastro. Cada 10 milisegundos se borra todo el lienzo, se dibuja el c铆rculo azul (nuestra pelota) en una posici贸n determinada y los valores x e y se actualizan para el siguiente fotograma.

Limpiar el c贸digo

Vamos a a帽adir m谩s y m谩s comandos a la funci贸n draw () en los pr贸ximos art铆culos, por lo que es bueno mantenerlo lo m谩s simple y limpio posible. Comencemos moviendo el c贸digo de dibujo de la bola a una funci贸n separada.

Reemplaza la funci贸n draw() con las dos funciones siguientes:

function drawBall() {
    ctx.beginPath();
    ctx.arc(x, y, 10, 0, Math.PI*2);
    ctx.fillStyle = "#0095DD";
    ctx.fill();
    ctx.closePath();
}

function draw() {
    ctx.clearRect(0, 0, canvas.width, canvas.height);
    drawBall();
    x += dx;
    y += dy;
}

Compara tu c贸digo

Puedes comprobar el c贸digo terminado de este art铆culo en la demostraci贸n en vivo a continuaci贸n, y jugar con ella para entender mejor c贸mo funciona:

Ejercicio: intenta cambiar la velocidad de la bola en movimiento o la direcci贸n hacia la que se mueve.

Siguientes pasos

Hemos dibujado nuestra bola y hemos hecho que se mueva, pero cuando supera el borde del canvas, desaparece. En el tercer cap铆tulo exploraremos como hacer que rebote en las paredes.