충돌 엔진과 물리 엔진 사이에는 큰 차이가 있습니다. 물리 엔진은 일반적으로 충돌 엔진을 사용하지만 동일한 작업을 수행하지는 않습니다.
충돌 엔진은 충돌 감지와 충돌 응답의 두 부분으로 나뉩니다. 후자는 일반적으로 물리 엔진의 일부입니다. 이것이 충돌 엔진과 물리 엔진이 일반적으로 동일한 라이브러리에 롤링되는 이유입니다.
충돌 감지는 이산 형과 연속 형의 두 가지 형태로 제공됩니다. 고급 엔진은 서로 다른 속성을 갖기 때문에 두 가지를 모두 지원합니다. 일반적으로 연속 충돌 감지는 비용이 많이 들고 실제로 필요한 경우에만 사용됩니다. 충돌과 물리의 대부분은 이산 방법을 사용하여 처리됩니다. 불연속적인 방법으로, 물체는 서로 관통하게되고 물리 엔진은 물체를 밀어 내려합니다. 따라서 엔진은 실제로 플레이어가 벽이나 바닥을 부분적으로 걷는 것을 막지 않으며 플레이어가 부분적으로 벽 / 바닥에 있음을 감지 한 후에 엔진을 수정합니다. 여기서는 불연속 충돌 감지에 중점을 두겠습니다. 처음부터 구현 한 경험이 가장 많기 때문입니다.
충돌 감지
충돌 감지는 비교적 쉽습니다. 모든 객체에는 변형과 모양이 있습니다 (여러 개의 모양이있을 수 있음). 순진한 접근법은 충돌 엔진이 모든 객체 쌍을 통해 O (n ^ 2) 루프를 수행하고 쌍 사이에 겹침이 있는지 테스트합니다. 더 스마트 한 접근법에서, 다수의 공간 데이터 구조 (예를 들어, 정적 대 동적 객체에 대한), 각각의 객체에 대한 경계 형상, 및 각 객체에 대한 다중 부분 볼록한 서브 셰이프가 존재한다.
공간 데이터 구조에는 KD-Trees, Dynamic AABB 트리, Octrees / Quadtrees, Binary Space Partitioning 트리 등이 포함됩니다. 각각의 장단점이 있기 때문에 일부 고급 엔진은 둘 이상의 엔진을 사용합니다. 예를 들어 다이내믹 AABB 트리는 실제로 움직이는 객체를 다룰 때 정말 빠르고 훌륭합니다. KD- 트리는 객체가 충돌하는 정적 레벨 형상에 더 적합 할 수 있습니다. 다른 옵션도 있습니다.
광범위한 단계는 공간 데이터 구조와 각 객체에 대한 추상 경계 볼륨을 사용합니다. 경계 체적은 전체 물체를 둘러싸는 단순한 모양으로, 일반적으로 충돌 테스트를 저렴하게 유지하면서 가능한 한 "밀하게"둘러싸는 것을 목표로합니다. 가장 일반적인 경계 모양은 축 정렬 경계 상자, 개체 정렬 경계 상자, 구 및 캡슐입니다. AABB는 일반적으로 가장 빠르고 가장 쉬운 것으로 간주됩니다 (구면이 더 쉽고 빠르지 만 이러한 공간 데이터 구조의 대부분은 구를 AABB로 변환해야 함). 그러나 많은 객체에 적합하지 않은 경향이 있습니다. 캡슐은 캐릭터 수준 충돌을 처리하기 위해 3D 엔진에서 널리 사용됩니다. 일부 엔진은 두 가지 경계 모양을 사용합니다.
충돌 감지의 마지막 단계는 형상이 교차하는 위치를 정확하게 감지하는 것입니다. 이것은 항상 메쉬 (또는 2D의 다각형)를 사용하는 것을 의미하지만 항상 그런 것은 아닙니다. 이 단계의 목적은 미세한 수준의 디테일이 필요한 경우 (예 : 간신히 놓친 샷을 무시할 수있는 사수의 총알 충돌) 객체가 실제로 충돌하는지 확인하는 것입니다. 또한 물체가 충돌하는 위치를 정확히 찾아서 물체의 반응에 영향을줍니다. 예를 들어 상자가 테이블의 가장자리에 있으면 엔진이 테이블이 상자를 밀고있는 지점을 알아야합니다. 상자가 얼마나 멀리 매달려 있는지에 따라 상자가 기울어지고 떨어질 수 있습니다.
매니 폴드 생성에 문의
여기에 사용 된 알고리즘에는 널리 사용되는 GJK 및 Minkowski Portal Refinement 알고리즘과 Separating Axis 테스트가 포함됩니다. 널리 사용되는 알고리즘은 일반적으로 볼록한 모양에만 작동하므로 많은 복잡한 객체를 볼록한 하위 객체로 나누고 각각에 대해 충돌 테스트를 수행해야합니다. 이것이 단순화 된 메쉬가 충돌에 자주 사용되는 이유 중 하나이며, 적은 수의 삼각형을 사용하는 처리 시간이 단축됩니다.
이러한 알고리즘 중 일부는 객체가 확실히 충돌 한 것이 아니라 충돌 한 위치, 즉 서로 얼마나 멀리 침투하고 있으며 "접촉점"이 무엇인지 알려줍니다. 일부 알고리즘에는이 정보를 얻기 위해 다각형 클리핑과 같은 추가 단계가 필요합니다.
신체적 반응
이 시점에서 접촉이 발견되었으며 물리 엔진이 접촉을 처리하기에 충분한 정보가 있습니다. 물리 처리는 매우 복잡 할 수 있습니다. 간단한 알고리즘은 일부 게임에서 작동하지만 상자 스택을 안정적으로 유지하는 것은 매우 어렵고 많은 작업과 명백하지 않은 해킹이 필요합니다.
가장 기본적인 수준에서 물리 엔진은 다음과 같은 작업을 수행합니다. 충돌하는 객체와 접촉 매니 폴드를 가져오고 충돌 된 객체를 분리하는 데 필요한 새로운 위치를 계산합니다. 객체를이 새로운 위치로 옮길 것입니다. 또한이 푸시로 인한 속도 변화와 복원 (튀김) 및 마찰 값을 결합하여 계산합니다. 물리 엔진은 중력과 같은 물체에 작용하는 다른 힘을 적용하여 물체의 새로운 속도를 계산 한 다음 새로운 위치를 (다음 프레임) 적용합니다.
고급 물리 반응이 빠르게 복잡해집니다. 위의 접근 방식은 하나의 개체가 다른 두 개체 위에있는 것을 포함하여 많은 상황에서 세분화됩니다. 각 쌍을 자체적으로 처리하면 "지터"가 발생하고 개체가 많이 튀어 오릅니다. 가장 기본적인 기술은 충돌하는 객체 쌍에 대해 여러 가지 속도 수정 반복을 수행하는 것입니다. 예를 들어 상자 "A"가 두 개의 다른 상자 "B"와 "C"위에 놓이면 충돌 AB가 먼저 처리되어 상자 A가 상자 C로 더 기울어지게됩니다. 그런 다음 저녁에 AC 충돌이 처리됩니다. 상자를 약간 빼내고 A를 아래로 잡아 당겨 B로 넣으십시오. 그런 다음 또 다른 반복이 수행되므로 AC 수정으로 인한 AB 오류가 약간 해결되어 AC 응답에 약간 더 많은 오류가 발생합니다. AC가 다시 처리 될 때 처리됩니다. 반복 횟수는 고정되어 있지 않으며 "완벽한"시점이 아니라 의미있는 결과를 제공하는 반복 횟수에 관계없이 반복됩니다. 10 번의 반복이 전형적인 첫 시도이지만 특정 엔진과 특정 게임의 요구에 가장 적합한 수를 파악하려면 조정이 필요합니다.
연락 캐싱
많은 유형의 게임을 다룰 때 실제로 유용한 것으로 밝혀지는 다른 트릭이 있습니다. 연락처 캐싱은 더 유용한 것 중 하나입니다. 연락처 캐시를 사용하면 충돌하는 각 개체 집합이 조회 테이블에 저장됩니다. 충돌이 감지되면 각 프레임에서이 캐시를 쿼리하여 객체가 이전에 접촉했는지 확인합니다. 객체가 이전에 접촉하지 않은 경우 "새로운 충돌"이벤트가 생성 될 수 있습니다. 개체가 이전에 접촉 한 경우이 정보를 사용하여보다 안정적인 응답을 제공 할 수 있습니다. 프레임에서 업데이트되지 않은 컨택 캐시의 항목은 분리 된 두 개의 오브젝트를 나타내며 "분리 오브젝트"이벤트가 생성 될 수 있습니다. 게임 로직은 종종 이러한 이벤트에 사용됩니다.
게임 로직이 새로운 충돌 이벤트에 응답하여 무시 된 것으로 플래그를 지정할 수도 있습니다. 이것은 뛰어 넘을 수는 있지만 플랫폼과 같이 플랫폼에서 공통적 인 일부 기능을 구현하는 데 실제로 유용합니다. 순진한 구현은 플랫폼-> 캐릭터 충돌 정상 (플레이어의 머리가 플랫폼의 바닥에 부딪쳤다는 것을 나타냄)이있는 충돌을 무시할 수 있지만 접촉 캐싱이 없으면 플레이어의 머리가 플랫폼을 통해 튀어 나와서 시작하면 중단됩니다. 넘어지다. 이 시점에서 접점 법선이 위로 향하게되어 플레이어가 플랫폼을 통해 팝업하지 않아야 할 수도 있습니다. 접촉 캐싱을 통해 엔진은 초기 충돌 법선을 안정적으로보고 플랫폼과 플레이어가 다시 분리 될 때까지 모든 추가 접촉 이벤트를 무시할 수 있습니다.
슬리핑
또 다른 유용한 기술은 객체가 상호 작용하지 않는 경우 "잠 들어있는"것으로 표시하는 것입니다. 수면 오브젝트는 물리 업데이트를받지 않고 다른 수면 오브젝트와 충돌하지 않으며 기본적으로 잠들지 않은 다른 오브젝트와 충돌 할 때까지 제자리에 고정되어 있습니다.
그 영향은 아무 것도하지 않고 거기에 앉아있는 모든 충돌 오브젝트 쌍이 처리 시간을 차지하지 않는다는 것입니다. 또한, 일정량의 작은 물리 보정이 없기 때문에 스택은 안정적입니다.
객체는 단일 프레임 이상의 속도가 거의 0 일 때 수면의 후보입니다. 이 0에 가까운 속도를 테스트하는 데 사용하는 엡실론은 아마도 스택 된 객체에 약간의 지터가 필요하고 객체의 전체 스택이 잠들기를 원하기 때문에 일반적인 부동 소수점 비교 엡실론보다 약간 높을 것입니다. "충분히 근접한"상태를 유지하십시오 임계 값은 물론 조정과 실험이 필요합니다.
제약
많은 물리 엔진의 마지막 주요 비트는 제약 솔버입니다. 이러한 시스템의 목적은 스프링, 모터, 휠 축, 시뮬레이션 된 소프트 바디, 천, 로프 및 체인, 때로는 유체 (유체가 완전히 다른 시스템으로 구현되는 경우도 있음)와 같은 것을 쉽게 구현하는 것입니다.
제약 조건 해결의 기본 사항조차도 수학을 매우 집중적으로 사용할 수 있으며이 주제에 대한 저의 전문 지식을 뛰어 넘습니다. 이 주제에 대한 자세한 설명은 랜디 갈 의 물리학 에 관한 훌륭한 기사 시리즈를 확인하는 것이 좋습니다 .