Как мне симулировать качающийся маятник?

9

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

JQuery обладает легкостью "свинга", аналогичной тому, что я ищу. Как это работает?

Я думал о вращении с одного угла на другой Math.easeOutExpo, но настоящие маятники облегчаются по-другому ...

mjanisz1
источник
2
Сделайте так, чтобы синусоида подала угловую скорость маятника так, чтобы нулевая точка находилась на пиках, а самое высокое значение скорости находилось внизу.
Дробовик ниндзя

Ответы:

10

Ну, вам придется использовать немного физики, но вам не нужно имитировать физику. Есть формулы для движения маятника, которые вы можете легко использовать для установки вращения вашего маятника. Для небольших колебаний движение может быть аппроксимировано простым гармоническим движением .

Угловое смещение в определенное время может быть аппроксимировано с помощью:

введите описание изображения здесь

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

MichaelHouse
источник
4

Вот расчет без триггеров, полученный из простых тригеров и физики 11-го класса. Предполагается, что начало координат - это самая низкая точка подвеса маятникового боба, что L - длина маятника, и что принято обычное графическое соглашение: y увеличивается вниз, а x увеличивается вправо:

Обновление: я испортил yAcceleration изначально; это проще
Обновление № 2 : Добавлен явный контроль времени и добавлены единицы измерения.

const float gravity = 9.8;     // units of metres/sec/sec
const float deltaT  = 0.001;   // equals 0.001 sec or 1 millisecond

var xVelocity = 0.010;         // units metres/sec equals 10 cm/sec 
var x = 0.0;                   // units metres
var y = 0.0;                   // units metres

while (true) {
  var xAcceleration = -gravity * (x/L) * (L-y)/L;

  x += (xVelocity + (xAcceleration/2 * deltaT)) * deltaT;
  y  = Math.SQRT(L*L - x*x) - L; 

  xVelocity += xAcceleration * deltaT;
}
Питер Гиркенс
источник
2
Время отсутствует в уравнении.
Майк Земдер
@MaikSemder: единица времени определяется как цикл анимации, что бы это ни было. Зачем делать это по-другому?
Питер Гиркенс
Прямо сейчас ваша интеграция ускорения использует неявное время 1 единица. Если ваша игровая единица времени равна секундам, у вас может быть только 1 кадр симуляции в секунду, просто подключите время явно, и вы избавитесь от этой проблемы. Время уже там, просто сделайте это явным. Например, время кадра меняется, но вам нужна стабильная постоянная скорость анимации, не зависящая от времени кадра, а также между различными платформами, или вы хотите эффект слима, по многим причинам.
Майк Земдер
1
Это была моя точка зрения, г приходит извне или «игра». Теперь у вас есть единица времени. Дельта Т сейчас составляет 1 единицу времени. Для симуляции в реальном времени это не очень удобно, поскольку в вашей игре есть своя «идея» прошедшего времени. Если вы сделаете это явным параметром, а не неявной константой, это может сделать ваш ответ полезным для игры.
Майк Земдер
2
Хорошая :) скорость также должна быть умножена на «deltaT», чтобы вывести «смещение» из скорости, чтобы ее можно было добавить к «x», голосование вверх
Maik Semder