Неправильная инициализация мира — одна из самых
частых проблем. В Cannon.js физический мир создаётся через объект
CANNON.World. Часто встречается ситуация, когда забывают
настроить gravity или используют некорректные единицы
измерения. Например, world.gravity.set(0, -9.82, 0) задаёт
стандартное ускорение свободного падения в метрах в секунду.
Использование слишком больших или слишком маленьких значений ведёт к
странным эффектам: объекты могут «пролетать» сквозь пол или падать с
невероятной скоростью.
Диагностика: проверить значения
gravity, broadphase и
solver.iterations. Некорректные параметры
broadphase (например, NaiveBroadphase при
большом количестве объектов) сильно снижают производительность и могут
пропускать коллизии.
const world = new CANNON.World();
world.gravity.set(0, -9.82, 0);
world.broadphase = new CANNON.SAPBroadphase(world);
world.solver.iterations = 10;
Неправильные формы тел (shapes) — частая причина
неожиданных физических эффектов. Например, использование
CANNON.Box для сферического объекта создаёт некорректные
столкновения. Ещё одна ошибка — некорректное масштабирование форм:
const sphereShape = new CANNON.Sphere(1);
const body = new CANNON.Body({ mass: 1 });
body.addShape(sphereShape, new CANNON.Vec3(0, 0, 0));
Если объект визуально больше или меньше своей физической формы, появляется расхождение между визуальной моделью и физикой.
Диагностика: включение визуализации коллизий через
cannon-debugger помогает увидеть несоответствия между
формой тела и её физической коллизией.
Неправильные массы и центры масс приводят к
неестественной динамике: объекты могут вращаться слишком быстро или
зависать в воздухе. Для сложных тел важно правильно задавать
mass и смещать shape offset:
body.addShape(boxShape, new CANNON.Vec3(0, 0.5, 0));
body.mass = 2;
body.updateMassProperties();
Пропущенный шаг симуляции. В Cannon.js мир
обновляется вручную через world.step(dt). Часто забывают
вызывать этот метод или используют слишком большой dt, что
приводит к нестабильности:
const fixedTimeStep = 1.0 / 60.0;
const maxSubSteps = 3;
world.step(fixedTimeStep, deltaTime, maxSubSteps);
Диагностика: проверка частоты вызова
world.step и значения dt. При высоких
deltaTime объекты могут «телепортироваться» или застревать
в других телах.
Некорректная настройка контактов. В Cannon.js
используется CANNON.Material и ContactMaterial
для определения трения и упругости взаимодействия. Ошибки проявляются
как «липкие» или чрезмерно скользкие объекты:
const groundMaterial = new CANNON.Material("groundMaterial");
const sphereMaterial = new CANNON.Material("sphereMaterial");
const contactMaterial = new CANNON.ContactMaterial(
groundMaterial,
sphereMaterial,
{ friction: 0.4, restitution: 0.3 }
);
world.addContactMaterial(contactMaterial);
Диагностика: проверка всех материалов и контактных параметров. Если объекты ведут себя нестабильно, часто проблема в несоответствии трения или упругости.
Отставание или рассинхрон рендера и физики возникает, когда визуальные объекты обновляются не по координатам физического тела:
mesh.position.copy(body.position);
mesh.quaternion.copy(body.quaternion);
Диагностика: убедиться, что каждое тело визуально привязано к своей физической модели в каждом кадре. Любые изменения позиции или поворота вне физического мира приводят к рассинхрону.
mass для
динамических тел. Тело с массой 0 становится статическим, что ломает
динамику.solver.iterations) приводит к «проваливаниям»
объектов сквозь друг друга.addShape или applyForce может
привести к неожиданной мутации данных.console.log(body.position, body.velocity).cannon-debugger)
для проверки форм и коллизий.dt для поиска критических точек нестабильности.Эффективная диагностика ошибок в Cannon.js требует внимательного контроля параметров мира, тел, форм, материалов и синхронизации визуальной сцены. Большинство проблем сводится к несоответствию физических параметров и визуального представления, а также к неправильной частоте обновления симуляции.