글쎄, 당신은 이미 답을 표시 :) 당신에게 코딩을 떠날거야,하지만 난 가서 넣어 완전히 기능 조각 학교됩니다 다음은 수학이다 어쨌든 코드를 사용하면됩니다. :) 내 댓글에서 :
그들은 단지 서클이므로 서클의 중심점 사이의 중간 점을 계산하면됩니다. 원의 반지름이 다른 경우 하나의 원을 으로 선택하고 반지름을 따라 한 점을 따라 의 중심을 계산합니다.
이것은 간단한 구현 일 수 있습니다. 아주 빈약 한 도우미 클래스를 만들었습니다. 나는 그것들을 확장하는 것을 완전히 고무 할 것이고, 구조체를 정말로 불변으로 만들고, 좋은 재즈를 만들 것이다. 그러나 지금은 데모 용으로 괜찮다. 헬퍼 클래스 그래서
는 :
private void CheckCollision(Circle circle1, Circle circle2)
{
CollisionResult result = new CollisionResult(circle1, circle2);
if (result.CalculateCollision())
{
Console.WriteLine(String.Format("Collision detected at {0}! Safe location for circle 1: {1}, circle 2: {2}", result.CollisionLocation, result.Circle1SafeLocation, result.Circle2SafeLocation));
}
else
{
Console.WriteLine("Did not collide.");
}
}
var circle1 = new Circle() {Radius = 5, Position = new Point(){X = 0, Y = 0} };
var circle2 = new Circle() {Radius = 5, Position = new Point(){X = 10, Y = 0} };
var circle3 = new Circle() {Radius = 3, Position = new Point(){X = 0, Y = 1} };
var circle4 = new Circle() {Radius = 5, Position = new Point(){X = 3, Y = 7} };
CheckCollision(circle1, circle2);
CheckCollision(circle3, circle4);
출력 :
public class CollisionResult
{
public Circle Circle1 { get; private set; }
public Circle Circle2 { get; private set; }
public Point Circle1SafeLocation { get; private set; }
public Point Circle2SafeLocation { get; private set; }
public Point CollisionLocation { get; private set; }
public CollisionResult(Circle circle1, Circle circle2)
{
this.Circle1 = circle1;
this.Circle2 = circle2;
}
public bool CalculateCollision()
{
double distanceFromCentres = Circle1.Position.Distance(Circle2.Position);
if (distanceFromCentres >= Circle1.Radius + Circle2.Radius)
return false;
double angleBetweenCircles = System.Math.Atan2(Circle2.Position.Y - Circle1.Position.Y, Circle2.Position.X - Circle1.Position.X);
Point midpointBetweenCircles = new Point(){X = (Circle1.Position.X + Circle2.Position.X)/2, Y = (Circle1.Position.Y + Circle2.Position.Y)/2};
Point circle1Offset = (new Polar() { Radius = Circle1.Radius, Angle = System.Math.PI + angleBetweenCircles }).ToCartesian();
Point circle2Offset = (new Polar() { Radius = Circle2.Radius, Angle = angleBetweenCircles }).ToCartesian();
CollisionLocation = midpointBetweenCircles;
Circle1SafeLocation = new Point(){X = midpointBetweenCircles.X + circle1Offset.X, Y = midpointBetweenCircles.Y + circle1Offset.Y };
Circle2SafeLocation = new Point(){X = midpointBetweenCircles.X + circle2Offset.X, Y = midpointBetweenCircles.Y + circle2Offset.Y };
return true;
}
}
사용법과 같습니다
public struct Point
{
public double X;
public double Y;
public double Distance(Point otherPoint)
{
double deltaX = this.X - otherPoint.X;
double deltaY = this.Y - otherPoint.Y;
return System.Math.Sqrt(deltaX * deltaX + deltaY * deltaY);
}
public override string ToString()
{
return String.Format("({0}, {1})", X, Y);
}
}
public struct Polar
{
public double Radius;
public double Angle;
public double X { get { return Radius * System.Math.Cos(Angle); } }
public double Y { get { return Radius * System.Math.Sin(Angle); } }
public Point ToCartesian()
{
return new Point() { X = X, Y = Y };
}
}
public class Circle
{
public double Radius { get; set; }
public Point Position { get; set; }
}
우리의 고기와-감자 클래스/메소드는이입니다
Did not collide.
Collision detected at (1.5, 4)! Safe location for circle 1: (0.158359213500125, 1.31671842700025), circle 2: (3.73606797749979, 8.47213595499958)
2 개의 원 (두 점에서 교차하는 점) 등의 실제 교차점을 계산하는 복잡성을 처리하는 것이 필요한지 잘 모르겠습니다. 이 줄을 따라 뭔가가 당신에게 충분할 것입니다. 나는 확실히 건강한 단위 테스트를 격려하고 반을 내가 여기있는 것 이상으로 만드는 것을 장려한다.:)
편집 : 중요한 것은이 경우에, 당신이 당신의 응용 프로그램을 위해 수행 할 작업에 따라 달라 이것은 원이 겹치는 경우, 단순히 다음 이동 각 원 를 그들 사이의 중간 점을 계산하는 것입니다 그 중간 지점으로부터 각각의 반경 인을 제거하십시오. 따라서 서클의 속도와 크기 또는 이동 방법에 따라 이상한 결과가 발생할 수 있습니다. 예를 들어 큰 반원 서클이 여전히 앉아 있으면 큰 원의 중심에서 0.5 개의 거리 만 반경의 원을 던져서 그 큰 원이 약 9.75 단위를 이동하게됩니다! 커다란 중첩 조건에 빠지지 않으면 그다지 문제가되지 않을 수도 있습니다. 제 생각에는 최소한 정보를에 충돌시킨 다음 을 님이 어떻게 반응 시킬지 궁금합니다.
그들은 단지 원이므로 원의 중심점 사이의 중간 점을 계산하면됩니다. 원의 반지름이 다른 경우 하나의 원을 선택하고 중심에서 반지름 1만큼 떨어진 선을 따라 점을 계산합니다. –
@Chris : Chris보다 훨씬 단순합니다. 아래를보십시오. –
@PieterGeerkens 나는 실제 충돌 _location_을 계산하여 충돌하지 않는지 아닌 단순히 상대적인 방향/각도를 (가능한) 유지하면서 가장 가까운 비 충돌 위치를 계산할 수있는 간단한 방법을 제안했습니다. 나는 Jesse가 요구 한 것이라고 생각했다. –