원 충돌 감지의 기본 원리
두 원이 서로 충돌했는지 확인하는 가장 직관적인 방법은 두 원의 중심 사이 거리를 계산한 뒤, 여기서 각 원의 반지름을 빼는 것입니다. 이 값이 0보다 작거나 같다면 두 원은 겹쳐 있는 상태, 즉 충돌한 상태라고 판단할 수 있습니다.
반대로 말하면, 두 중심 사이의 거리가 두 반지름의 합보다 크거나 같으면 두 원은 서로 닿아 있지 않다는 뜻입니다.
빠른 사전 검사로 연산 최적화하기
충돌 검사 대상인 원의 개수가 많아지면 모든 원 쌍에 대해 정밀한 거리 계산을 수행하는 것은 비효율적입니다. 예를 들어 원이 20개라면 최대 190개의 조합을 검사해야 하므로, 먼저 간단한 조건으로 충돌 가능성이 없는 경우를 미리 걸러내는 것이 좋습니다.
X축 또는 Y축 방향의 중심 좌표 차이가 두 반지름의 합보다 크다면, 두 원은 절대 충돌할 수 없습니다. 이를 코드로 표현하면 다음과 같습니다.
abs(x2 - x1) > (r2 + r1)
abs(y2 - y1) > (r2 + r1)
위 조건 중 하나라도 참이라면 해당 축 방향의 거리가 반지름의 합을 초과하는 것이므로, 두 원은 충돌하지 않습니다. 따라서 더 복잡한 거리 계산을 생략해도 됩니다.
정확한 충돌 판정하기
사전 검사를 통과한 원들에 대해서는 피타고라스 정리를 활용해 두 중심 사이의 실제 거리를 구합니다.
const dx = x2 - x1;
const dy = y2 - y1;
const dist = Math.sqrt(dx * dx + dy * dy);
if (dist < r1 + r2) {
// 두 원은 충돌 상태입니다.
}
제곱근(sqrt) 계산은 연산 비용이 크기 때문에, 성능이 중요한 실시간 게임 루프에서는 양변을 제곱하여 비교하는 방식을 사용하는 것이 좋습니다.
if (dx * dx + dy * dy < (r1 + r2) * (r1 + r2)) {
// 충돌 처리 로직
}
이처럼 간단한 사전 검사와 제곱 비교만 활용해도, 원이 많은 장면에서도 충돌 감지 성능을 크게 향상시킬 수 있습니다.