Box2D Проверка, если точка пересекает тело

10

Есть ли способ проверить, пересекает ли точка тело?

Например, предположим, что в мире есть тело с позицией (100 100).

Есть ли способ проверить, пересекает ли точка в (100,100) это тело?

Другой пример связан с игрой под названием «PHUN». В PHUN вы можете щелкать и перетаскивать тела вокруг. Как бы вы проверили, пересекает ли точка мыши тело?

xAustechx
источник

Ответы:

5

Как и в случае с ответом Колина, b2World.Query () - полезная функция: если вы установите aabb для покрытия только одной точки, вы можете получить список объектов, которые могут перекрывать эту точку. Однако из-за проблем со скоростью он только проверяет ограничивающую рамку (AABB) на совпадение, которое не всегда является полностью точным.

Чтобы точно проверить прибор (форму, в более старых версиях), используйте функцию b2Fixture.TestPoint (). Поскольку тело может иметь несколько приборов, вам может понадобиться просмотреть весь список, чтобы быть уверенным. Объединение этих двух функций должно позволить вам воссоздать функциональность Phun, если хотите.

Toeofdoom
источник
2

Взгляните на то, b2QueryCallbackчтобы найти, какие приборы содержат точку, и использовать, b2MouseJointчтобы объекты следовали за мышью. У меня есть пример кода, но сейчас нет времени упростить его для вас. Если вам это нужно, я могу предоставить это позже.

Колин Гисласон
источник
2

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

альтернативный текст
(источник: co.uk )

Зеленые точки - это расположение мыши, а красные - это точка знания внутри фигуры.

Существуют случаи ребер - если линия, соединяющая точки, например, совпадает с ребром - но это должно дать вам 90% пути.

ChrisF
источник
0

Я знаю, что этот вопрос старый, но мне не хватает простого, основанного на коде ответа. Итак, вот оно:

    /// <summary>
    /// Return if a given position is inside the physical body.
    /// </summary>
    /// <param name="body">Body to test.</param>
    /// <param name="position">Position to check if inside the body.</param>
    /// <returns>If given point is inside the physical body.</returns>
    public bool TestPointCollision(FarseerPhysics.Dynamics.Body body, Vector2 position)
    {
        // get body transformation
        FarseerPhysics.Common.Transform trans;
        body.GetTransform(out trans);

        // iterate fixtures to see if any of them hit the point
        foreach (var fix in body.FixtureList)
        {
            if (fix.Shape.TestPoint(ref trans, ref position))
                return true;
        }

        // if there are no hits, return false
        return false;
    }

Обратите внимание, что это не обычный Box2D, а Farseer (и в C #), но он должен иметь точно такой же API.

Ронен Несс
источник