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

Leis de movimento de Newton

No exemplo final da ultima seção, nós vimos como poderíamos calcular a aceleração dinâmica tendo como base um vetor apontando de um círculo na tela para a posição do mouse. O movimento resultante assemelhava-se a uma atração magnética entre círculo e mouse, como se uma força estivesse puxando o círculo em direção ao mouse. Nesta seção, vamos formalizar nossa compreensão do conceito de uma força e sua relação com a aceleração. O nosso objetivo é entender como fazer vários objetos se moverem pela tela e responderem a uma variedade de forças do meio.
Antes de começarmos a examinar a prática da simulação de forças no código, vamos dar uma olhada conceitual no que significa ser uma força no mundo real. Assim como a palavra "vetor", "força" é muitas vezes usada para significar uma variedade de coisas. Pode indicar uma intensidade vigorosa, como em "Ela empurrou a rocha com grande força" ou "Ele falou com força". A definição de força que nos interessa é muito mais formal e vem das leis de movimento de Isaac Newton:
A força é um vetor que faz um objeto com massa acelerar.
A boa notícia é que reconhecemos a primeira parte da definição: uma força é um vetor. Ainda bem que acabamos de passar uma seção inteira aprendendo o que é um vetor e como programar com PVector!
Vamos olhar para as três leis de Newton em relação ao conceito de força.

Primeira Lei de Newton

A primeira lei de Newton é comumente enunciada como:
Um objeto em repouso permanece em repouso e um objeto em movimento permanece em movimento.
Contudo, falta um elemento importante relacionado às forças. Poderíamos expandir a definição assim:
Um objeto em repouso permanece em repouso e um objeto em movimento permanece em movimento com velocidade e direção constantes, a não ser que seja submetido a uma força desequilibrada.
Até o aparecimento de Newton, a teoria dominante do movimento — formulada por Aristóteles — tinha quase dois mil anos. Ela afirmava que, se um objeto se move, algum tipo de força é necessária para mantê-lo em movimento. A menos que essa coisa se movendo esteja sendo empurrada ou puxada, ela irá simplesmente perder velocidade ou parar. Certo?
Isto, claro, não é verdade. Na ausência de quaisquer forças, nenhuma força é necessária para manter um objeto em movimento. Um objeto (como uma bola) jogado na atmosfera da Terra perde velocidade por causa da resistência do ar (uma força). A velocidade de um objeto apenas permanecerá constante na ausência de quaisquer forças ou se as forças que atuam sobre ele se cancelarem uma à outra, ou seja, a força resultante for igual a zero. Isto é muitas vezes chamado de equilíbrio . A bola caindo alcançará uma velocidade terminal (que permanece constante), uma vez que a força de resistência do ar seja igual à força da gravidade.
O pêndulo não se move porque todas as forças se anulam (a força resultante é zero)
Em nosso mundo de ProcessingJS, podemos reescrever a primeira lei de Newton assim:
A velocidade de um objeto PVector permanecerá constante se ele estiver em um estado de equilíbrio.
Deixando de lado por alguns instantes a segunda lei de Newton (indiscutivelmente a lei mais importante para os propósitos de nossos estudos), vamos para a terceira lei.

Terceira Lei de Newton

Essa lei geralmente é enunciada como:
Para toda ação há uma reação igual e oposta.
Esta lei frequentemente causa um pouco de confusão pela forma que é apresentada. Por um lado, parece que uma força causa a outra. Sim, se você empurrar alguém, este alguém pode decidir ativamente empurrá-lo de volta. Mas isto não é a ação e reação de que estamos falando na terceira lei de Newton.
Digamos que você se empurre contra a parede. A parede não decide ativamente empurrar você de volta. Não há nenhuma força de "origem". Seu impulso simplesmente inclui ambas as forças, referidas como um "par ação/reação."
Uma maneira melhor de enunciar a lei seria:
Forças sempre ocorrem em pares. As duas forças são de igual intensidade, mas em sentidos opostos.
Agora, isso ainda causa confusão porque parece que estas forças sempre se anulariam mutuamente. Este não é o caso. Lembre-se, as forças atuam em objetos diferentes. E só porque as duas forças são iguais, não significa que os movimentos são iguais (ou que os objetos vão parar de se mover).
Tente empurrar um caminhão parado. Embora o caminhão seja muito mais poderoso que você, ao contrário de um em movimento, um caminhão parado nunca vai dominar você e enviar-lhe voando para trás. A força que você exerce sobre ele é igual e contrária à força exercida sobre as suas mãos. O resultado depende de uma variedade de outros fatores. Se o caminhão é um caminhão pequeno em uma descida congelada, você provavelmente será capaz de fazê-lo se mover. Por outro lado, se for um caminhão grande em uma estrada de terra e você empurrar com força suficiente (mesmo talvez estando em movimento), você poderia machucar sua mão.
E se você empurrasse um caminhão usando patins?
Vamos re-escrever a terceira lei de Newton para o nosso mundo de ProcessingJS:
Se calcularmos um PVector f que é a força do objeto A sobre o objeto B, também devemos aplicar a força—PVector.mult(f,-1);—que B exerce sobre o objeto A.
Veremos que no mundo da programação de ProcessingJS, nem sempre teremos que permanecer fieis à afirmação acima. Às vezes, como no caso da atração gravitacional entre corpos, vamos querer modelar forças iguais e contrárias. Outras vezes, como quando estamos simplesmente dizendo, "Ei, existe um pouco de vento no ambiente," não vamos considerar modelar a força que um corpo exerce no ar. Na verdade, não modelaremos o ar de maneira alguma! Lembre-se, nós simplesmente estamos nos inspirando na física do mundo natural, não simulando tudo com perfeita precisão.

Segunda Lei de Newton

E aqui está a lei mais importante para o programador de ProcessingJS.
Essa lei é geralmente enunciada como:
Força é igual a massa vezes a aceleração.
Ou:
F=MA
Por que essa é a lei mais importante para nós? Bem, vamos escrevê-la de maneira diferente.
A=F/M
Aceleração é diretamente proporcional à força e inversamente proporcional à massa. Isto significa que se você for empurrado, quanto mais você for empurrado, mais rápido você se moverá (acelerar). Quanto maior você for, mais lento você se moverá.
Peso vs. Massa
A Massa de um objeto é a medida da quantidade de matéria no objeto (medido em kilogramas).
Peso, comumente confundido com o conceito de 'Massa', é tecnicamente a força da gravidade sobre um objeto. Oriunda da segunda lei de Newton, podemos calculá-lo como a massa vezes a aceleração da gravidade (F = m * g). Peso é medido em newtons (N).
Densidade é definida como a quantidade de massa por unidade de volume (gramas por centímetro cúbico, por exemplo).
Observe que um objeto que tem uma massa de um quilograma na terra teria uma massa de um quilograma na lua. Contudo, lá ele pesaria apenas um sexto do que pesa aqui.
Agora, no mundo de ProcessingJS, o que é massa? Não estamos lidando com pixels? Para iniciar de maneira mais simples, digamos que, em nosso mundo pixel simulado, todos os nossos objetos têm uma massa igual a 1. F/1 = F. E assim:
A=F
A aceleração de um objeto é igual à força. Isso é uma ótima notícia. Afinal, nós vimos na seção Vetores que aceleração era a chave para controlar o movimento de nossos objetos na tela. Localização é ajustada por velocidade e velocidade por aceleração. Aceleração foi onde tudo começou. Agora aprendemos que é na força onde realmente tudo começa.
Vamos usar o que aprendemos para aplicar em nosso objeto Mover, que atualmente tem localização, velocidade e aceleração. Agora nosso objetivo é ser capaz de adicionar forças para este objeto, talvez dizendo:
mover.applyForce(wind);
ou:
mover.applyForce(gravity);
onde vento e gravidade são PVectors. De acordo com a segunda lei de Newton, nós podemos implementar essa função como segue:
Mover.prototype.applyForce = function(force) {
    this.acceleration = force;
};

Acúmulo de força

Isto parece muito bom. Afinal, aceleração = força é uma tradução literal da segunda Lei de Newton (sem massa). Entretanto, há um grande problema aqui. Vamos voltar para o que estamos tentando realizar: criar um objeto em movimento na tela que responda ao vento e à gravidade.
mover.applyForce(wind);
mover.applyForce(gravity);
mover.update();
mover.display();
Ok, vamos ser o computador por um momento. Primeiro, nós chamamos applyForced() com o vento. E então a aceleração do objeto Mover é associada com o PVetor do vento. Depois, chamamos applyForce() com a gravidade. Agora, a aceleração do objeto mover é definida como o PVetor da gravidade. Em terceiro lugar, chamamos update(). O que acontece em update()? A aceleração é adicionada à velocidade.
velocity.add(acceleration);
Nós não vamos ver nenhum erro no nosso programa, mas nossa! Temos um grande problema. Qual é o valor da aceleração quando ela é adicionada à velocidade? Ela é igual à força da gravidade. O vento foi deixado de fora! Se chamarmos applyForce() mais do que uma vez, ela sobrescreve a última chamada. Como vamos lidar com mais de uma força?
A verdade é que começamos com uma versão simplificada da segunda Lei de Newton. Aqui é uma maneira mais precisa para colocá-la:
Força resultante é igual à massa vezes aceleração.
Ou, aceleração é igual à soma de todas as forças dividida pela massa. Isso faz todo sentido. Afinal, como vimos na primeira Lei de Newton, se a soma de todas as forças é igual a zero, um objeto experimenta o estado de equilíbrio (ou seja, sem aceleração). A nossa implementação disso é através do processo conhecido como acumulação de força. Ele é na verdade bastate simples; tudo que precisamos fazer é adicionar todas as forças juntas. A qualquer momento, podem existir 1, 2, 6, 12, ou 303 forças. Enquanto nosso objeto souber como acumulá-las, não importa quantas forças agem sobre ele.
Vamos modificar o método applyForce() para adicionar cada nova força à aceleração, acumulando-as:
Mover.prototype.applyForce = function(force) {
    this.acceleration.add(force);
};
Mas não terminamos ainda. Acumulação de forças tem mais uma parte. Já que estamos somando todas as forças juntas num dado momento, nós temos de ter certeza de limpar a aceleração (ou seja, defini-la como zero) antes de cada vez que update() é chamada. Vamos pensar sobre o vento por um momento. Às vezes o vento é muito forte, às vezes é fraco, e às vezes não há nenhum vento. A qualquer momento, pode existir uma enorme rajada de vento, digamos, quando o usuário segurar o mouse pressionado
if (mousePressed) {
  var wind = new PVector(0.5, 0);
  mover.applyForce(wind);
}
Quando o usuário soltar o mouse, o vento irá parar, e de acordo com a primeira lei de Newton, o objeto vai continuar a se mover a uma velocidade constante. Porém, se nós esquecermos de redefinir a aceleração para zero, a rajada de vento ainda estaria em vigor. Pior ainda, ela se somaria a ela mesma no quadro anterior, já que estamos acumulando forças! A aceleração, na nossa simulação, não tem memória; ela é simplesmente calculada baseada nas forças do ambiente presentes em um momento no tempo. Isso é diferente de, digamos, localização, que deve lembrar onde o objeto estava no quadro anterior para mover adequadamente para o próximo.
A maneira mais fácil de implementar a limpeza da aceleração para cada quadro é multiplicar o PVector por 0 ao final de update().
Mover.prototype.update = function() {
    this.velocity.add(this.acceleration);
    this.location.add(this.velocity);
    this.acceleration.mult(0);
};

Lidando com a massa

Certo. Nós temos uma pequena adição a fazer antes de acabar de integrar forças em nossa classe Mover e estarmos prontos para ver os exemplos. Afinal de contas, a Segunda Lei de Newton é, na verdade, F=MA e não A=F. Incorporar a massa é tão fácil quanto adicionar uma propriedade ao nosso objeto, mas nós precisamos gastar um pouco mais de tempo aqui porque uma pequena complicação irá surgir.
Unidades de Medida
Agora que estamos introduzindo a massa, é importante fazer uma pequena observação sobre unidades de medida. No mundo real, as coisas são medidas em unidades específicas. Nós dizemos que dois objetos estão a 3 metros de distância, a bola de beisebol se move a uma taxa de 90 quilômetros por hora ou esta bola de boliche tem a massa de 6 quilogramas. Como nós veremos posteriormente neste curso, algumas vezes nós iremos levar as unidades do mundo real em consideração. Entretanto, nesta seção, nós iremos ignorá-las na maior parte do tempo. Nossas unidades de medida são em pixels ("Estes dois círculos estão a 100 pixels de distância") e os quadros de animação ("Este círculo está se movendo a uma taxa de 2 pixels por quadro"). No caso da massa, não existe nenhuma unidade de medida para nós usarmos. Nós iremos simplesmente criar algo. Nesse exemplo, nós aleatoriamente escolhemos o número 10. Não há uma unidade de media, embora você possa gostar de inventar a sua, como "1 moog" ou "1 yurkle". Também deve ser observado que, para fins de demonstração, nós vamos associar a massa a pixels (desenhando, por exemplo, um círculo com um raio de 10). Isso nos permite visualizar a massa de um objeto. No mundo real, contudo, o tamanho não indica definitivamente a massa. Uma pequena bola de metal pode ser ter uma massa bem maior que um grande balão por causa de sua densidade.
A massa é um escalar (ponto flutuante), não um vetor, sendo apenas um número descrevendo a quantidade de matéria de um objeto. Nós podemos fantasiar sobre as coisas e calcular a área de uma forma como sua massa, mas é mais simples começar dizendo "Ei, a massa desse objeto é...hmm, não sei...que tal 1?"
var Mover = function() {
    this.mass = 1;
    this.position = new PVector(random(width), random(height));
    this.velocity = new PVector(0, 0);
    this.acceleration = new PVector(0, 0);
};
Isto não é tão legal, já que as coisas só começam a ficar interessantes quando temos objetos com massas diferentes, mas é um começo. Onde a massa entra? Nós a usamos quando aplicamos a Segunda Lei de Newton ao nosso objeto.
Mover.prototype.applyForce = function(force) {
  force.div(this.mass);
  this.acceleration.add(force);
};
E mais uma vez, embora nosso código pareça bem razoável, nós temos um problema significativo aqui. Considere o seguinte cenário, com dois objetos Mover, os dois sendo levados pela força do vento.
var m1 = new Mover();
var m2 = new Mover();

var wind = new PVector(1, 0);

m1.applyForce(wind);
m2.applyForce(wind);
De novo, vamos ser o computador. O objeto m1recebe a força do vento—(1,0)—a divide pela massa (10) e soma o resultado à aceleração.
| m1 igual à força do vento: | (1,0) | | Dividida pela massa de 10: | (0.1,0) |
Ok. Agora o objeto m2. Ele também recebe a força do vento—(1,0). Espera um segundo. Qual é o valor da força do vento? Observando com mais atenção, a força do vento agora, na verdade, é (0,1,0)!! Você se lembra desse pequeno detalhe quando se trabalha com objetos? Quando você passa um objeto (nesse caso um PVector) para uma função, você está passando uma referência para aquele objeto. Não é uma cópia! Então, se uma função faz uma alteração naquele objeto (que nesse caso ela faz ao dividi-lo pela massa) então o objeto está permanentemente alterado! Mas nós não queremos que m2 receba uma força dividida pela massa do objeto m1. Nós queremos que ele receba a força em seu estado original—(1,0). Então, nós devemos nos proteger e fazer uma cópia de PVector f antes de dividi-lo pela massa. Felizmente, o objeto PVector tem um método conveniente para fazer uma cópia—get(). get()retorna um novo objetoPVector com os mesmos dados. E, assim, nós podemos revisar applyForce() conforme abaixo:
Mover.prototype.applyForce = function(force) {
    var f = force.get();
    f.div(this.mass);
    this.acceleration.add(f);
};
Alternativamente, nós podemos reescrever o método usando a versão estática de div(), usando o que aprendemos sobre funções estáticas na seção anterior:
Mover.prototype.applyForce = function(force) {
  var f = PVector.div(force, this.mass);
  this.acceleration.add(f);
};
O mais importante é encontrar uma maneira de não afetar o vetor original da força, assim ele pode ser aplicado a vários objetos Mover.

Criando forças

Nós sabemos o que é uma força (um vetor) e sabemos como aplicar uma força a um objeto (dividindo-a pela massa e adicionando o resultado ao vetor aceleração do objeto). O que está faltando? Bem, temos agora que descobrir como conseguir uma força, em primeiro lugar. De onde as forças vêm?
Ao longo desta seção, vamos dar uma olhada em dois métodos para criar forças em nosso mundo ProcessingJS:
  • Crie uma força! Afinal, você é o programador, o criador do seu mundo. Não há nenhuma razão que impeça você de simplesmente criar uma força e aplicá-la.
  • Modele uma força! Sim, forças existem no mundo real. E os livros de física contêm equações que descrevem essas forças. Nós podemos pegar essas equações, traduzi-las em código fonte e modelar forças do mundo real no ProcessingJS.
A maneira mais fácil de criar uma força é simplesmente escolher um número. Vamos começar com a ideia de simular o vento. Que tal uma força de vento que aponta para a direita e é razoavelmente fraca? Assumindo um objeto Mover m, nosso código seria:
var wind = new PVector(0.01, 0);
  m.applyForce(wind);
O resultado não é algo terrivelmente interessante, mas é um bom começo. Nós criamos um objeto PVector, o inicializamos e o passamos para um objeto (que por sua vez irá aplicá-lo a sua própria aceleração). Se nós quisermos ter duas forças, talvez vento e gravidade (um pouco mais forte, apontando para baixo), nós podemos escrever o seguinte:
var wind = new PVector(0.01, 0);
var gravity = new PVector(0, 0.1);
m.applyForce(wind);
m.applyForce(gravity);
Agora nós temos duas forças, apontadas em direções diferentes com magnitudes diferentes, ambas aplicadas ao objeto m. Estamos começando a chegar em algum lugar. Agora nós construímos um mundo para nossos objetos em ProcessingJS, um ambiente ao qual eles podem realmente responder.
Aqui está como nosso programa ficou, quando colocamos tudo junto:
Uau! Nós vimos muitas coisas, mas agora você pode fazer muito. Continue em frente - aprenda a usar a força!
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?

Nenhuma postagem por enquanto.
Você entende inglês? Clique aqui para ver mais debates na versão em inglês do site da Khan Academy.