如何在box2d(Andengine)中禁用两个物体之间的接触。我使用过contact.setEnabled(false)
,但这不适合我。我在下面给出了代码以供参考。
@Override
public void beginContact(final Contact pContact)
{
final Fixture fixtureA = pContact.getFixtureA();
final Body bodyA = fixtureA.getBody();
final Object userDataA = bodyA.getUserData();
final Fixture fixtureB = pContact.getFixtureB();
final Body bodyB = fixtureB.getBody();
final Object userDataB = bodyB.getUserData();
if(userDataA==null || userDataB==null)
return;
if(userDataA.equals(target) && userDataB.equals(ball)
{
pContact.setEnabled(false);
}
}
答案 0 :(得分:2)
@Override public void preSolve(Contact contact, Manifold oldManifold) { PhysicsConnectorManager mPC = this.mPhysicsWorld.getPhysicsConnectorManager(); Body targetBody = mPC.findBodyByShape(target); Body ballBody = mPC.findBodyByShape(ball); if (contact.getFixtureA().getBody() == targetBody && contact.getFixtureB().getBody() == ballBody) { contact.setEnabled(false); } else { contact.setEnabled(true); } }
答案 1 :(得分:1)
就Box2D而言,你的代码看起来大致正确,除此之外你还需要检查球和目标是否相反:
if( (userDataA.equals(target) && userDataB.equals(ball)) ||
(userDataB.equals(target) && userDataA.equals(ball)) )
但我认为你的主要问题可能是使用最终......为什么是最终?我不是Java专家,但看起来很可疑,快速浏览维基百科说:“最后一个变量只能初始化一次”。要保持联系人禁用,您需要每帧都执行SetEnabled(false)。
答案 2 :(得分:0)
我有同样的问题,感谢@Rooban和他的评论“fixture.isSensor = true;”我解决了我正在使用box2dweb(JavaScript端口),因为所有的box2d API都很相似,这可能对你有帮助。
假设您有两个对象,一个WALL和一个TOY。 TOY正在穿过WALL。
//WALL (toy detector)
var toyDetectorFixDef = new box2d.b2FixtureDef();
toyDetectorFixDef.density = 1;
toyDetectorFixDef.friction = 0.5;
toyDetectorFixDef.restitution = 0.5;
toyDetectorFixDef.shape = new box2d.b2PolygonShape;
toyDetectorFixDef.shape.SetAsBox(80 / SCALE, 5 / SCALE);//, new box2d.b2Vec2(bodyDef3.x, bodyDef3.y ), 4);
//BE SURE YOU ADDED THIS LINE, SO THIS OBJECT IS ACTING AS A SENSOR
toyDetectorFixDef.isSensor = true;
var toyDetectorBodyDef = new box2d.b2BodyDef();
toyDetectorBodyDef.type = box2d.b2Body.b2_staticBody;
toyDetectorBodyDef.position.x = 100 / SCALE;
toyDetectorBodyDef.position.y = 280 / SCALE;
var rbDataToyDetector = new Object();
rbDataToyDetector.bodyType = "toyDetector";
toyDetectorBodyDef.userData = rbDataToyDetector;
var toyDetectorBox = world.CreateBody(toyDetectorBodyDef);
toyDetectorBox.CreateFixture(toyDetectorFixDef);
然后你必须添加TOY对象。
//TOY object
var fixDef = new box2d.b2FixtureDef();
fixDef.density = 1;
fixDef.friction = 0.5;
fixDef.restitution = 0.5;
bodyDef = new box2d.b2BodyDef();
bodyDef.type = box2d.b2Body.b2_dynamicBody;
bodyDef.position.x = 200 / SCALE + Math.random() * 400 / SCALE;
bodyDef.position.y = 0;
var rbDataBall = new Object();
rbDataBall.bodyType = "toy";
bodyDef.userData = rbDataBall;
fixDef.shape = new box2d.b2CircleShape(20 / SCALE);
var toyBox = world.CreateBody(bodyDef);
toyBox.CreateFixture(fixDef);
现在有了物体,你必须检查碰撞。
try {
var listener = new Box2D.Dynamics.b2ContactListener;
listener.BeginContact = function (contact) {
if ((contact.GetFixtureA().GetBody().GetUserData().bodyType == "toyDetector" && contact.GetFixtureB().GetBody().GetUserData().bodyType == "toy") ||
(contact.GetFixtureA().GetBody().GetUserData().bodyType == "toy" && contact.GetFixtureB().GetBody().GetUserData().bodyType == "toyDetector")) {
//YOUR CODE HERE
console.log("Toy detected!");
}
}
world.SetContactListener(listener);
}
catch (e) {
console.log(e.toString());
}
我希望这会对你有所帮助。