проблема столкновения круг-круг - PullRequest
1 голос
/ 07 декабря 2009

У меня проблема с обнаружением столкновения окружность-окружность. Я использовал следующий алгоритм

func collision(id,other.id)
{

 var vaP1,vaP2,dis,va1,vb1,va2,vb2,vp1,vp2,dx,dy,dt;


 if (id!=other.id)

    {
        dx=other.x-x;
        dy=other.y-y;
        dis=sqrt(sqr(dx)+sqr(dy));

        if dis<=radius+other.radius
        {
            //normalize
            dx/=dis;
            dy/=dis;

            //calculate the component of velocity in the direction
            vp1=hspeed*dx+vspeed*dy;
            vp2=other.hspeed*dx+other.vspeed*dy;

            if (vp1-vp2)!=0
            {
                dt=(radius+other.radius-dis)/(vp1-vp2);

                //move the balls back so they just touch
                x-=hspeed*dt;
                y-=vspeed*dt;
                other.x-=other.hspeed*dt;
                other.y-=other.vspeed*dt;

                //projection of the velocities in these axes
                va1=(hspeed*dx+vspeed*dy); 
                vb1=(vspeed*dx-hspeed*dy);
                va2=(other.hspeed*dx+other.vspeed*dy); 
                vb2=(other.vspeed*dx-other.hspeed*dy);

                //new velocities in these axes. take into account the mass of each ball.
                vaP1=(va1+bounce*(va2-va1))/(1+mass/other.mass);
                vaP2=(va2+other.bounce*(va1-va2))/(1+other.mass/mass);

                hspeed=vaP1*dx-vb1*dy; 
                vspeed=vaP1*dy+vb1*dx;
                other.hspeed=vaP2*dx-vb2*dy;  
                other.vspeed=vaP2*dy+vb2*dx;

                //we moved the balls back in time, so we need to move them forward
                x+=hspeed*dt;
                y+=vspeed*dt;
                other.x+=other.hspeed*dt;
                other.y+=other.vspeed*dt;
            }
        }
    }

x=ball 1 x-position

y=ball 1 y-position

other.x= ball 2 x position

other.y=ball 2 y position

этот алгоритм хорошо работает, когда у меня есть изображение шара размером 40 x 40 пикселей, а центр шара равен (20, 20), что означает, что изображение состоит только из шара. Но проблема возникает, когда размер изображения составляет 80 x 80. (60,60), означает, что мяч находится в правом нижнем углу с радиусом 20. в этом случае происходят множественные столкновения, означает, что часть </p> <pre>x+=hspeed*dt; y+=vspeed*dt; other.x+=other.hspeed*dt; other.y+=other.vspeed*dt;

не в состоянии отделить мяч / скорость не меняется в зависимости от столкновения. Я изменил значение x, которое является центром изображения 40,40, на 60,60 центра шара, добавив 20. Но результат тот же. Может кто-нибудь сказать мне, в чем проблема. Я думаю, что алгоритм правильный, потому что он работает хорошо во всех других случаях, и многие люди использовали этот алгоритм. Проблема меняет положение от центра изображения к центру шара. Какую коррекцию я должен сделать для этого ??? или любая идея. Если кто-то хочет помочь, пожалуйста, дайте мне адрес электронной почты, чтобы я мог отправить свой полный проект.

Ответы [ 2 ]

3 голосов
/ 07 декабря 2009

У меня не было умственной силы, чтобы переварить весь ваш вопрос, но вот мои 2 цента о том, как решить вашу проблему

1) Самый простой способ обнаружить столкновение окружности с другим - проверить, меньше ли их расстояние, чем радиус объединенных окружностей. (я могу ошибаться в математике, поэтому поправьте меня, если я ошибаюсь)

Circle c1,c2;
float distance = DISTANCE(c1.center,c2.center);
if(distance < c1.radius + c2.radius)
{
  // collision .. BOOOOOOM
}

2) Попробуйте использовать точные типы данных. Старайтесь не преобразовывать числа с плавающей точкой в ​​целые, не проверяя переполнение, занижение и десятичные точки. Еще лучше, просто используйте поплавки.

3) Напишите журнал и проследите ваши значения. Посмотрите, есть ли очевидные математические ошибки.

4) Разбейте ваш код на простейшую часть. Попробуйте удалить все эти вычисления скорости, чтобы получить самые простые движения, которые помогут вам отладить.

0 голосов
/ 07 декабря 2009

Я не дам вам ответ, который вы ищете, и я не уверен, что кто-то еще будет. Количество кода, которое необходимо расшифровать, чтобы получить ответ, может не гарантировать вознаграждение. Что я бы порекомендовал, так это ослабить связь в вашем алгоритме. Функция выше делает слишком много работы.

В идеале у вас должно быть обнаружение столкновений, которое сосредоточено только на столкновении, а не на продвижении шаров. Нечто подобное функции показано ниже, и это позволит другим разработчикам легче помочь вам, если у вас все еще есть проблемы.

function(firstCircleCenterX, firstCircleCenterY, secondCircleCenterX, secondCircleCenterY, firstCircleRadius, secondCircleRadius)
{
    ...this code should concentrate on logic to determine collision
    ...use pythagoran theory to find distance between the two centers
    ...if the distance between the two centers is less than ((2*firstCircleRadius)+(2*secondCircleRadius) then you have a collision

    ...return true or false depending on collision
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...