If you're seeing this message, it means we're having trouble loading external resources on our website.

Se você está atrás de um filtro da Web, certifique-se que os domínios *.kastatic.org e *.kasandbox.org estão desbloqueados.

Conteúdo principal

Apontando na direção do movimento

Vamos voltar para um de nossos primeiros exemplos, aquele em que um objeto Mover acelera em direção ao mouse.
Você deve ter notado que quase todas as formas que desenhamos até agora são círculos. Isso é conveniente por várias razões, uma delas é que nós não precisamos considerar a questão da rotação. Se você rotacionar um círculo ele continua exatamente igual. No entanto, chega um momento na vida de todos os programadores de movimento em que eles querem desenhar alguma coisa na tela que aponte na direção do movimento. Talvez você esteja desenhando uma formiga, ou um carro, ou uma espaçonave. E quando dizemos "aponte na direção do movimento," o que estamos querendo realmente dizer é "rotacione de acordo com o vetor velocidade." Velocidade é um vetor, com um componente x e um y, mas para rotacionar um objeto em ProcessingJS nós precisamos de um ângulo. Vamos desenhar nosso diagrama trigonométrico mais uma vez, com um vetor velocidade do objeto:
OK. Sabemos que a definição da tangente é:
tangente(ângulo)=velocidadeyvelocidadex
O problema disso é que nós sabemos a velocidade, mas não sabemos o ângulo. Nós temos que calcular o ângulo. É aqui que uma função especial conhecida como a inversa da tangente entra em cena, às vezes chamada de arco tangente ou tg-1. (Existem também uma inversa do seno e uma inversa do cosseno.)
Se a tangente de um valor a for igual a um valor b, a tangente inversa de b será igual a a. Por exemplo:
setangente(a)=b
entãoa=arcotangente(b)
Viu como isso é o inverso? Com isso, podemos calcular o ângulo:
setangente(ângulo)=velocidadey/velocidadex
entãoângulo=arcotangente(velocidadey/velocidadex)
Agora que temos a fórmula, vamos ver em que parte da função display() do nosso mover ela deve entrar. Note que em ProcessingJS, a função para arco tangente é chamada atan(). O JavaScript também tem o Math.atan() de forma nativa (assim como todas as funções trigonométricas básicas), mas vamos continuar usando a funções fornecidas pelo ProcessingJS.
Mover.prototype.display = function () {
  var angle = atan(this.velocity.y / this.velocity.x);

  stroke(0, 0, 0);
  fill(127, 127, 127);
  pushMatrix();
  rectMode(CENTER);
  translate(this.position.x, this.position.y);
  rotate(angle);
  rect(0, 0, 30, 10);
  popMatrix();
};
Agora o código acima está praticamente terminado e quase funciona. Mas nós ainda temos um grande problema. Vamos considerar os dois vetores velocidade representados abaixo.
Ainda que sejam superficialmente similares, os dois vetores apontam em direções bem diferentes—direções opostas, na verdade! Contudo, se aplicarmos a nossa fórmula para encontrar o ângulo de cada vetor...
V1 ⇒ ângulo = atan(3/-4) = atan(-0,75) = -0,644 radianos = -57 graus
V2 ⇒ ângulo = atan(-3/4) = atan(-0,75) = -0,644 radianos = -57 graus
...vamos obter o mesmo ângulo para os dois vetores. Isso não pode estar certo para os dois; os vetores apontam em direções opostas! Na verdade, esse é um problema muito comum em computação gráfica. Ao invés de simplesmente usar atan()com um monte de instruções condicionais para solucionar cenários positivos/negativos ProcessingJS (junto com JavaScript e quase todos os ambientes de programação) tem uma função chamada atan2() que faz isso para você.
Mover.prototype.display = function () {
  var angle = atan2(this.velocity.y, this.velocity.x);

  stroke(0, 0, 0);
  fill(127, 127, 127);
  pushMatrix();
  rectMode(CENTER);
  translate(this.position.x, this.position.y);
  rotate(angle);
  rect(0, 0, 30, 10);
  popMatrix();
};
Para simplificar ainda mais, o próprio objeto PVector tem uma função chamada heading(), que se encarrega de chamar atan2() para você para que você possa obter o ângulo de direção 2D em radianos para qualquer PVector.
É assim que o programa ficará no final. Coloque seu mouse sobre ele e veja a rotação!

Este curso "Natural Simulations" é um derivado do "The Nature of Code" por Daniel Shiffman, usado sob a Creative Commons Attribution-NonCommercial 3.0 Unported License.

Quer participar da conversa?

  • Avatar piceratops seed style do usuário pignisfrow
    No Desafio: Virando o carro, ao apertar direita ou esquerda, o carro vira. O que não entendi foi, porque eu tenho que ficar segurando a tecla pra que ele efetivamente vire ao invés de apenas apertá-la e porque às vezes ele vira na diagonal, já que ele é programado para virar apenas 90º ou PI/2 rad?
    (1 voto)
    Avatar Default Khan Academy avatar do usuário
Você entende inglês? Clique aqui para ver mais debates na versão em inglês do site da Khan Academy.