Форум Flasher.ru

Форум Flasher.ru (http://www.flasher.ru/forum/index.php)
-   API приложений и сред (http://www.flasher.ru/forum/forumdisplay.php?f=61)
-   -   [Box2D] стандартная задача для box2d (http://www.flasher.ru/forum/showthread.php?t=141563)

greegreeman 28.06.2010 20:06

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

greegreeman 02.07.2010 19:58

да. ситуация с бокс2д печальная на форуме...

Dos87 02.07.2010 23:44

Думаю не стоит объяснять что такое world, fixture, fixtureDef, body, bodyDef и userData.

Для того, чтобы определить столкновение 2х объектов нужно повесить на игровой мир Box2D прослушиватель столкновений:
Код AS3:

var contactListener:ContactListener = new ContactListener();
world.SetContactListener(contactListener);

Предварительно в userData записываем нужный нам объект:
Код AS1/AS2:

public function set userData(value:*):void
{
        bodyDef.userData = value;
        fixtureDef.userData = value;
}

Класс ContactListener, полное переопределение (Нам потребуется только BeginContact):
Код AS3:

package
{
        import Box2D.Collision.b2Manifold;
        import Box2D.Dynamics.b2ContactListener;
        import Box2D.Dynamics.b2ContactImpulse;
        import Box2D.Dynamics.Contacts.b2Contact;
 
        public class ContactListener extends b2ContactListener
        {
                public override function BeginContact(contact:b2Contact):void
                {
                        var obj1:* = contact.GetFixtureA().GetUserData();
                        var obj2:* = contact.GetFixtureB().GetUserData();
                }
 
                public override function EndContact(contact:b2Contact):void
                {
 
                }
 
                public override function PreSolve(contact:b2Contact, oldManifold:b2Manifold):void
                {
 
                }
 
                public override function PostSolve(contact:b2Contact, impulse:b2ContactImpulse):void
                {
 
                }
        }
}

3 объекта одновременно столкнуться ни как не могут. В любом случае между столкновениями будет промежуток времени, возможно незначительно маленький. Можем предположить, что разница между столкновениями в 30ms - это всё одно столкновение. Тогда мы можем создать массив столкнувшихся объектов и перед каждым столкновением его обновлять:
Код AS3:

public class CollisionObject
{
        private var __userData:*;
        private var __time:*;
 
        public function CollisionObject(userData:*, time:Number)
        {
                __userData = userData;
                __time = time;
        }
 
        public function get userData(value:*):void
        {
                return __userData;
        }
        public function get time(value:Number):void
        {
                return __time;
        }
}
 
 
private static const MAX_COL_TIME:int = 30;
//Тут все недавно столкнувшиеся объекты
private var collisionArray:Vector.<CollisionObject> = new Vector.<CollisionObject>();
 
public override function BeginContact(contact:b2Contact):void
{
        var obj1:FieldObject = contact.GetFixtureA().GetUserData();
        var obj2:FieldObject = contact.GetFixtureB().GetUserData();
        obj1.hit(obj2);
        obj2.hit(obj1);
 
 
        if (obj1.color == obj2.color)
                if (checkForColor(obj1.color))
                {
                        //3 объекта столкнулись
                        //тут можно их всех уничтожить
                }
                else
                {
                        //тут можно всех добавить
                        var time:int = getTimer();
                        collisionArray.push(new CollisionObject(obj1, time));
                        collisionArray.push(new CollisionObject(obj1, time));
                }
}
private function checkForColor(color:uint):Boolean
{
        //тут проверяем каждый объект в collisionArray.
        //Если он находится в массиве дольше MAX_COL_TIME - удаляем и проверяем дальше,
        //иначе проверяем по цвету.
        //Если совпал - return true,
        //иначе проверяем дальше
}


greegreeman 03.07.2010 22:12

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

Dos87 03.07.2010 22:26

Может быть body.SetActive(false)?
Как joints в таком случае использовать я не знаю). Сам похожий вопрос задаю =):
http://www.flasher.ru/forum/showthread.php?t=141716

Можешь еще здесь поискать (правда там не AS3, но вроде всё понятно):
http://docs.google.com/View?id=dfh3v...tqs6wf4#d0e987

greegreeman 05.07.2010 18:06

Спасибо. Буду разбираться. Может поможет


Часовой пояс GMT +4, время: 15:10.

Copyright © 1999-2008 Flasher.ru. All rights reserved.
Работает на vBulletin®. Copyright ©2000 - 2026, Jelsoft Enterprises Ltd. Перевод: zCarot
Администрация сайта не несёт ответственности за любую предоставленную посетителями информацию. Подробнее см. Правила.