Как правильно применить крутящий момент или угловой импульс к телу в PlayN?
Я пытался применить угловой импульс к объекту Body в PlayN, но безрезультатно. Какое бы значение (радиально) я ни вводил, угол тела никогда не меняется. Я пытался установить крутящий момент, но безрезультатно.
Пример кода, который не работает:
BodyDef def = new BodyDef();
def.type = BodyType.DYNAMIC;
Body body = world.createBody(def);
float degToRad = (float) (180 / Math.PI);
float radials = (float) (50 / degToRad);
// None of the following options work.
body.applyAngularImpulse(radials); // Immediate angular change.
body.applyTorque(radials); // Angular change over time.
Как я могу получить действительный объект тела, чтобы изменить его угол без ручной установки его угловой скорости (например, с помощью setAngularVelocity)?
Заранее спасибо!
Я заметил, что крутящий момент и угловая скорость сбрасываются путем вызова метода setWake, который я никогда не делаю вручную, но он вызывается классом Island:
public void setAwake(boolean flag) {
...
m_angularVelocity = 0.0f;
m_torque = 0.0f;
...
}
Примечание: установка угловой скорости не является опцией, потому что я полагаюсь на физическое моделирование. Я нашел статью о повороте угла Box2D, но это не изменило результат метода applyAngularImpulse.
3 ответа
Я отладил некоторые из них и пришел к выводу, что используемые мной значения были слишком низкими. При просмотре кода applyAngularImpulse я заметил несколько вещей:
public void applyAngularImpulse(float impulse) {
if (m_type != BodyType.DYNAMIC) {
return;
}
if (isAwake() == false) {
setAwake(true);
}
m_angularVelocity += m_invI * impulse;
}
m_invI - это действительно низкое значение, например, 2.44882598E-4, поэтому имеет смысл, если я использую слишком низкое значение, видимого эффекта просто нет. Если рассчитать импульс из примера вопроса, умноженного на поле m_invI:
m_invI = 0.00044882598 = 2.449E-4
impulse = 50 / 180 / PI = 0.08841941282 = 8.842E-2
m_invI * impulse = 2.449E-4 * 8.842E-2 = 0.00002165237 = 2.165E-5 <--
Это означает просто приращение угловой скорости 0,00002165237 за цикл обновления... Что слишком мало, чтобы быть заметным, как кажется.
Кроме того, просматривая форумы Box2D на предмет похожих ситуаций, я обнаружил, что лучше всего включать инерцию тела в расчет угловых импульсов. Как это:
body.applyAngularImpulse(speedValue * body.getInertia());
Инерция имеет тенденцию быть высоким значением (+4000) для меня.
Надеюсь, что это может помочь тем, у кого есть проблемы с подачей углового импульса или крутящего момента.
В моем случае я забыл позвонить
body.setFixedRotation(false);
Даже при том, что я устанавливал массу, сообщалось об инерции, равной 0, и все моменты и угловые импульсы игнорировались.
По-видимому, это исправлено по умолчанию.
У меня такая же проблема.
В моем случае я случайно поставил свои точки в CW порядке (что привело к отрицательной области и нулевой массе). Это был мой неверный код:
// incorrect version
triangleVertices.push(new B2Vec2(width / 2, 0.0)); // top
triangleVertices.push(new B2Vec2(0.0, height)); // left
triangleVertices.push(new B2Vec2(width, heightM)); // right
Это похоже на CCW, верно? Нет, не в моей системе координат (+Y не работает).
// corrected version
triangleVertices.push(new B2Vec2(width / 2, 0.0)); // top
triangleVertices.push(new B2Vec2(width, heightM)); // right
triangleVertices.push(new B2Vec2(0.0, height)); // left