Attention: Here be dragons

This is the latest (unstable) version of this documentation, which may document features not available in or compatible with released stable versions of Godot.

Використання Jolt Physics

Вступ

Фізичний двигун Jolt було додано як альтернативу існуючому фізичному двигуну Godot Physics у версії 4.4. Jolt розроблено Jorrit Rouwe з акцентом на ігри та VR-додатки. Раніше він був доступний як розширення, але тепер вбудований у Godot. За замовчуванням нові проекти використовуватимуть його як фізичний двигун.

Існуюче розширення зараз розглядається як таке, що перебуває в режимі обслуговування. Це означає, що виправлення помилок будуть об'єднані, і воно буде сумісним з новими версіями Godot, доки вбудований модуль не матиме паритету функціональності з розширенням. Єдине, чого бракує на даний момент, це пов'язані з'єднання, про які ви можете прочитати на цій сторінці. Розширення можна знайти тут на GitHub та в бібліотеці ресурсів Godot.

Щоб змінити 3D-фізичний рушій на Jolt Physics, встановіть Project Settings > Physics > 3D > Physics Engine на Jolt Physics. Після цього натисніть кнопку Зберегти та перезапустити. Коли редактор знову відкриється, 3D-сцени тепер повинні використовувати Jolt для фізики.

Помітні відмінності від Godot Physics

Між існуючим фізичним двигуном Godot та Jolt існує багато відмінностей.

Спільні властивості

Поточні інтерфейси для вузлів 3D-суглобів не зовсім відповідають інтерфейсу власних суглобів Jolt. Таким чином, існує ряд властивостей суглобів, які не підтримуються, головним чином пов'язані з налаштуванням м'яких меж суглоба.

Непідтримувані властивості:

  • PinJoint3D: bias, damping, impulse_clamp

  • HingeJoint3D: bias, softness, relaxation

  • SliderJoint3D: angular_\*, \*_limit/softness, \*_limit/restitution, \*_limit/damping

  • ConeTwistJoint3D: bias, relaxation, softness

  • Generic6DOFJoint3D: *_limit_*/softness, *_limit_*/restitution, *_limit_*/damping, *_limit_*/erp

Наразі з'являється попередження, якщо ви встановите для цих властивостей значення, відмінні від значень за замовчуванням.

Монотільні суглоби

У методі Godot ви можете пропустити одне зі спільних тіл для двотілового суглоба та фактично зробити так, щоб "світ" був іншим тілом. Однак, шлях вузла, якому ви призначаєте своє тіло (node_a проти node_b), ігнорується. Фізика Godot завжди поводитиметься так, ніби ви призначили його node_a, і оскільки node_a також визначає систему відліку для спільних меж, ви отримаєте інвертовані межі та потенційно дивну форму межі, особливо якщо ваші межі дозволяють як лінійні, так і кутові ступені свободи.

Jolt поводитиметься так, ніби ви призначили тіло вузлу node_b, де node_a представлятиме "світ". Існує налаштування проекту під назвою Physics > Jolt Physics 3D > Joints > World Node, яке дозволяє перемикати цю поведінку, якщо вам потрібна сумісність для існуючого проекту.

Межі зіткнень

Jolt (та інші подібні фізичні двигуни) використовує те, що Jolt називає "опуклим радіусом", щоб покращити продуктивність та поведінку типів виявлення зіткнень, на які Jolt покладається для опуклих фігур. Інші фізичні двигуни (включно з Godot) можуть називати їх "полями зіткнень". Godot надає їх як властивість margin для кожного класу, похідного від Shape3D, але сама фізика Godot не використовує їх ні для чого.

Ці поля колізій іноді роблять в інших рушіях (як описано в документації Godot), фактично додаючи "оболонку" навколо фігури, трохи збільшуючи її розмір, а також заокруглюючи будь-які краї/кути. Однак у Jolt ці поля спочатку використовуються для стиснення фігури, а потім застосовується "оболонка", в результаті чого краї/кути аналогічно заокруглюються, але без збільшення розміру фігури.

Щоб уникнути необхідності налаштування цієї властивості поля вручну, оскільки її значення за замовчуванням може бути проблематичним для менших фігур, модуль Jolt надає налаштування проекту під назвою Physics > Jolt Physics 3D > Collisions > Collision Margin Fraction, яке множиться на найменшу вісь AABB фігури для обчислення фактичного поля. Властивість margin фігури потім використовується як верхня межа.

Ці поля, для більшості випадків використання, повинні бути більш-менш прозорими, але іноді можуть призводити до дивних колізійних нормалей під час виконання запитів фігури. Ви можете зменшити вищезгадане налаштування проекту, щоб зменшити це, зокрема встановити його на 0.0, але занадто мале поле також може призвести до дивних колізійних результатів, тому зазвичай не рекомендується.

Стабілізація Баумгарта

Стабілізація Баумгарта — це метод вирішення проблеми проникнення тіл та приведення їх до стану, коли вони лише торкаються одне одного. У фізиці Godot це працює як пружина. Це означає, що тіла можуть прискорюватися, що може призвести до їх перестрибування та повного роз'єднання. За допомогою поштовху стабілізація застосовується лише до положення, а не до швидкості тіла. Це означає, що перестрибування неможливе, але для вирішення проблеми проникнення може знадобитися більше часу.

Силу цієї стабілізації можна налаштувати за допомогою налаштувань проекту Physics > Jolt Physics 3D > Simulation > Baumgarte Stabilization Factor. Встановлення цього налаштування проекту на 0.0 вимкне стабілізацію Баумгарта. Встановлення на 1.0 вирішить проблему проникнення за 1 крок симуляції. Це швидко, але часто також нестабільно.

Зіткнення привидів

Jolt використовує два методи для зменшення зіткнень типу "привид", тобто зіткнень з внутрішніми краями фігур/тіл, що призводять до утворення нормалей зіткнень, що протистоять напрямку руху.

Перший метод, який називається «активне виявлення ребер», позначає ребра трикутників у ConcavePolygonShape3D або HeightMapShape3D як «активні» або «неактивні» на основі кута до сусіднього трикутника. Коли відбувається зіткнення з неактивним ребром, нормаль зіткнення буде замінена нормаллю трикутника, щоб зменшити ефект фантомних зіткнень.

Поріг кута для цього активного виявлення країв налаштовується через налаштування проекту Physics >Jolt Physics 3D > Collisions > Active Edge Threshold.

Другий метод, який називається «покращене внутрішнє видалення ребер», натомість додає перевірки під час виконання для визначення активності ребра на основі точок контакту двох тіл. Це має перевагу в тому, що застосовується не лише до зіткнень з ConcavePolygonShape3D та HeightMapShape3D, але й до ребер між будь-якими фігурами в межах одного тіла.

Покращене видалення внутрішніх країв можна вмикати та вимикати для різних контекстів, до яких воно застосовується, використовуючи Physics >Jolt Physics 3D > Simulation > Use Enhanced Internal Edge Removal, налаштування проекту та аналогічні налаштування для queries та motion queries.

Зверніть увагу, що ні активне виявлення країв, ні покращене видалення внутрішніх країв не застосовуються під час роботи з колізіями-привидами між двома різними тілами.

Використання пам'яті

Jolt використовує розподільник стеку для тимчасових розподілів пам'яті на етапі моделювання. Цей розподільник стеку вимагає виділення певного обсягу пам'яті заздалегідь, який можна налаштувати за допомогою параметрів проекту Physics > Jolt Physics 3D > Limits > Temporary Memory Buffer Size.

Індекс грані, відбитий променем

Властивість face_index, що повертається в результатах intersect_ray() та RayCast3D, за замовчуванням завжди матиме значення -1 з Jolt. Налаштування проекту Physics > Jolt Physics 3D > Queries > Enable Ray Cast Face Index увімкне їх.

Зверніть увагу, що ввімкнення цього параметра збільшить вимоги до пам'яті для ConcavePolygonShape3D приблизно на 25%.

Кінематичні контакти RigidBody3D

Під час використання Jolt, class_RigidBody3D, заморожений за допомогою FREEZE_MODE_KINEMATIC, за замовчуванням не повідомлятиме про контакти від зіткнень з іншими статичними/кінематичними тілами з міркувань продуктивності, навіть якщо встановлено ненульове значення max_contacts_reported. Якщо у вас є багато/великі кінематичні тіла, що перекриваються зі складною статичною геометрією, такою як ConcavePolygonShape3D або HeightMapShape3D, ви можете зрештою витрачати значну кількість продуктивності процесора та пам'яті, не усвідомлюючи цього.

З цієї причини ця поведінка вмикається через налаштування проекту Physics > Jolt Physics 3D > Simulation > Generate All Kinematic Contacts.

Контактні імпульси

Через внутрішні обмеження Jolt, контактні імпульси, що надаються PhysicsDirectBodyState3D.get_contact_impulse(), оцінюються заздалегідь на основі таких речей, як контактний різноманіття та швидкості тіл, що стикаються. Це означає, що повідомлені імпульси будуть точними лише у випадках, коли два тіла, що розглядаються, не стикаються з жодними іншими тілами.

Area3D та SoftBody3D

Jolt supports the same type of interactions between class_SoftBody3D and Area3D as Godot Physics, such as the wind and gravity properties found on Area3D. Unlike Godot Physics however, Jolt also supports the various overlap signals and methods found on Area3D, for when a class_SoftBody3D enters or exits an overlap with it, such as body_entered.

To revert back to the behavior of Godot Physics, where no overlap signals are emitted, you need to configure the area's collision_mask such that there's no overlap with the soft body's collision_layer. You can also filter out any class_SoftBody3D in the signal connection yourself.

WorldBoundaryShape3D

class_WorldBoundaryShape3D, який призначений для представлення нескінченної площини, реалізовано в Jolt дещо інакше порівняно з Godot Physics. Обидва рушії мають верхню межу ефективного розміру цієї площини, але цей розмір набагато менший при використанні Jolt, щоб уникнути проблем з точністю.

Ви можете налаштувати цей розмір за допомогою параметрів проєкту Physics > Jolt Physics 3D > Limits > World Boundary Shape Size.

Помітні відмінності від розширення Godot Jolt

Хоча вбудований модуль Jolt значною мірою є прямим портом розширення Godot Jolt, є кілька відмінностей.

Параметри проекту

Усі налаштування проєкту перенесено з категорії physics/jolt_3d до physics/jolt_physics_3d.

Крім того, було також здійснено деякі перейменування та рефакторинг окремих налаштувань проекту. До них належать:

  • sleep/enabled зараз simulation/allow_sleep.

  • sleep/velocity_threshold зараз simulation/sleep_velocity_threshold.

  • sleep/time_threshold зараз simulation/sleep_time_threshold.

  • collisions/use_shape_margins зараз collisions/collision_margin_fraction, де значення 0 еквівалентне його вимкненню.

  • collisions/use_enhanced_internal_edge_removal зараз simulation/use_enhanced_internal_edge_removal.

  • collisions/areas_detect_static_bodies зараз simulation/areas_detect_static_bodies.

  • collisions/report_all_kinematic_contacts зараз simulation/generate_all_kinematic_contacts.

  • collisions/soft_body_point_margin зараз simulation/soft_body_point_radius.

  • collisions/body_pair_cache_enabled is now simulation/body_pair_contact_cache_enabled.

  • collisions/body_pair_cache_distance_threshold є now simulation/body_pair_contact_cache_distance_threshold.

  • collisions/body_pair_cache_angle_threshold is now simulation/body_pair_contact_cache_angle_threshold.

  • continuous_cd/movement_threshold зараз simulation/continuous_cd_movement_threshold, але виражений у вигляді дробу, а не відсотків.

  • continuous_cd/max_penetration зараз simulation/continuous_cd_max_penetration, але виражений у вигляді дробу, а не відсотків.

  • kinematics/use_enhanced_internal_edge_removal зараз motion_queries/use_enhanced_internal_edge_removal.

  • kinematics/recovery_iterations зараз motion_queries/recovery_iterations, але виражений у вигляді дробу, а не відсотків.

  • kinematics/recovery_amount зараз motion_queries/recovery_amount.

  • queries/use_legacy_ray_casting було видалено.

  • solver/position_iterations зараз simulation/position_steps.

  • solver/velocity_iterations зараз simulation/velocity_steps.

  • solver/position_correction зараз simulation/baumgarte_stabilization_factor, але виражений у вигляді дробу, а не відсотків.

  • solver/active_edge_threshold зараз collisions/active_edge_threshold.

  • solver/bounce_velocity_threshold зараз simulation/bounce_velocity_threshold.

  • solver/contact_speculative_distance зараз simulation/speculative_contact_distance.

  • solver/contact_allowed_penetration зараз simulation/penetration_slop.

  • limits/max_angular_velocity тепер зберігається у вигляді радіанів.

  • limits/max_temporary_memory зараз limits/temporary_memory_buffer_size.

Суглобові вузли

Вузли з'єднань, що відображаються в розширенні Godot Jolt (JoltPinJoint3D, JoltHingeJoint3D, JoltSliderJoint3D, JoltConeTwistJoint3D та JoltGeneric6DOFJoint), не були включені до модуля Jolt.

Безпека потоків

На відміну від розширення Godot Jolt, модуль Jolt має потокобезпечність, зокрема підтримку налаштування проекту Physics > 3D > Run On Separate Thread. Однак це не було ретельно протестовано, тому його слід вважати експериментальним.