通过libGDX的Box2D:如何创建每体内都有一种MouseJoint单独的Andr​​oid触摸? [英] Box2D via libGDX: How to create one MouseJoint per body for separate Android touches?

查看:189
本文介绍了通过libGDX的Box2D:如何创建每体内都有一种MouseJoint单独的Andr​​oid触摸?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是怎么回事大家,

感谢您的时间。

我想提出一个傍克隆,我想限制的Box2D两个MouseJoints最大; 1 MouseJoint最高每桨。的MouseJoints应创建仅当内的任一两个桨的边界的用户的两个触摸的土地中的一个。

我正在与我的code怪异的结果。如果左桨中我第一次触摸土地,要么桨之外我的第二个触摸土地,是在左边桨创建了第二个MouseJoint(见所附图片)。

请注意:除了左侧桨两个MouseJoints,有图像两PrismaticJoints;一头连着每个桨。

要无果,我已经尝试了所有的我能想到的,或从其他人的code相适应的算法。

如果一个code溶液为例或链接可以贴出来,我将非常感激。

下面是我的code:

 公共类自选实现屏幕,InputProcessor ​​{/ * ======一些变量和方法为清楚起见省略====== * /
/ *鼠标多次联合实验* /
公共MouseJoint mouseJoint [] =新MouseJoint [2];
车身hitBody [] =新机构[2];
车身tempBody;公共自选画面(乒乓球比赛){
    this.game =游戏;
}/ * ---------------------屏界面的方法------------------------ - * /
//为了清楚而省略方法
/ * ---------------------结束屏幕接口方法---------------------- * // * --------------------- InputProcessor接口方法------------------ * /
@覆盖
公共布尔KEYDOWN(INT键code){
    返回false;
}@覆盖
公共布尔KEYUP(INT键code){
    返回false;
}@覆盖
公共布尔的keyTyped(CHAR字符){
    返回false;
}@覆盖
公共布尔触地(INT screenX,诠释screenY,INT指针,INT按钮){
                testPoint.set(screenX,screenY,0);
                camera.unproject(测试点);                //问世界上哪个机构是在给定的
                //边框,鼠标指针周围
                hitBody [指针] = NULL;                world.QueryAABB(回调,testPoint.x - 1.0F,testPoint.y - 1.0F,testPoint.x + 1.0F,testPoint.y + 1.0F);
                hitBody [指针] = tempBody;                //如果我们碰到了什么东西,我们创建一个新的联合鼠标
                //并将其连接到命中身体。
                如果(hitBody [指针]!= NULL){                    MouseJointDef高清=新MouseJointDef();
                    def.bodyA = groundBody;
                    def.bodyB = hitBody [指针]
                    def.collideConnected = TRUE;
                    def.target.set(。hitBody [指针] .getPosition()X,hitBody [指针] .getPosition()Y);
                    def.maxForce = 3000.0f * hitBody [指针] .getMass();                    mouseJoint [指针] =(MouseJoint)world.createJoint(DEF);
                    hitBody [指针] .setAwake(真);
                }其他{                }
                返回false;
}@覆盖
公共布尔润色(INT screenX,诠释screenY,INT指针,INT按钮){
    如果(mouseJoint [指针]!= NULL){
        world.destroyJoint(mouseJoint [指针]);
        mouseJoint [指针] = NULL;
    }
    返回false;
}/ ** touchDragged()方法的过程中增量目标目的地临时向量** /
Vector2目标=新Vector2();@覆盖
公共布尔touchDragged(INT screenX,诠释screenY,诠释指针){
    如果(mouseJoint [指针]!= NULL){
        camera.unproject(testPoint.set(screenX,screenY,0));
        mouseJoint [指针] .setTarget(target.set(testPoint.x,testPoint.y));
    }
    返回false;
}@覆盖
公共布尔的mouseMoved(INT screenX,诠释screenY){
    返回false;
}@覆盖
公共布尔滚动(INT量){
    返回false;
}
    / * ----------------结束InputProcessor接口方法------------------ * // * ------------------------辅助方法---------------------- -------------- * /
    / *对鼠标的Andr​​oid联合屏触摸向量* /
    测试点的Vector3 =新的Vector3(); //我们实例化这个载体,回调在这里,所以我们不刺激GC
    QueryCallback回调=新QueryCallback(){
       @覆盖公共布尔reportFixture(治具夹具){
          //如果命中灯具的身体在地上的身体
          //我们忽略它
          如果(fixture.getBody()== groundBody)返回true;          如果(fixture.testPoint(testPoint.x,testPoint.y)){
              tempBody = fixture.getBody();
                返回false;
          }其他
                返回true;
       }
    };
/ * ------------------------结束辅助方法--------------------- ---------- * /
}


解决方案

从我所看到的 tempBody 是不会被重置为null。这也就意味着,你第一次接触它设置了 tempBody 来触摸的桨,然后当你在身体之外preSS回调不会找到垫新的身体,但不会重置 testBody 为null,所以当你指定 testBody hitBody [指针] 是将其设置为第一桨。

您触摸降功能应该看起来像的方法是:

  @覆盖
公共布尔触地(INT screenX,诠释screenY,INT指针,INT按钮){
            testPoint.set(screenX,screenY,0);
            camera.unproject(测试点);            //问世界上哪个机构是在给定的
            //边框,鼠标指针周围
            hitBody [指针] = NULL;            world.QueryAABB(回调,testPoint.x - 1.0F,testPoint.y - 1.0F,testPoint.x + 1.0F,testPoint.y + 1.0F);
            hitBody [指针] = tempBody;            //如果我们碰到了什么东西,我们创建一个新的联合鼠标
            //并将其连接到命中身体。
            如果(hitBody [指针]!= NULL){                MouseJointDef高清=新MouseJointDef();
                def.bodyA = groundBody;
                def.bodyB = hitBody [指针]
                def.collideConnected = TRUE;
                def.target.set(。hitBody [指针] .getPosition()X,hitBody [指针] .getPosition()Y);
                def.maxForce = 3000.0f * hitBody [指针] .getMass();                mouseJoint [指针] =(MouseJoint)world.createJoint(DEF);
                hitBody [指针] .setAwake(真);
            }其他{            }
            tempBody = NULL;            返回false;

}

这方式tempBody总是被置空后使用。

What's up everyone,

Thanks for your time.

I am making a Pong clone, and I want to restrict Box2D to two MouseJoints maximum; one MouseJoint maximum per paddle. The MouseJoints should be created only if one of the user's two touches lands within either of the two paddle's boundaries.

I am getting a weird result with my code. If my first touch lands within the left paddle and my second touch lands outside of either paddle, a second MouseJoint is created on the left paddle (see attached image).

Note: In addition to the two MouseJoints on the left paddle, there are two PrismaticJoints in the image; one attached to each paddle.

To no avail, I've tried all of the algorithms that I could think of or adapt from other people's code.

If a code solution example or link could be posted, I would be much obliged.

Here is my code:

public class MyScreen implements Screen, InputProcessor{

/*========some variables and methods omitted for clarity========*/


/*multiple mouse joint experiment*/
public MouseJoint mouseJoint[] = new MouseJoint[2];    
Body hitBody[] = new Body[2];
Body tempBody;

public MyScreen(Pong game) {
    this.game = game;
}        

/*---------------------Screen interface methods--------------------------*/
//methods omitted for clarity
/*---------------------end Screen interface methods----------------------*/

/*---------------------InputProcessor interface methods------------------*/
@Override
public boolean keyDown(int keycode) {
    return false;
}

@Override
public boolean keyUp(int keycode) {
    return false;
}

@Override
public boolean keyTyped(char character) {
    return false;
}

@Override
public boolean touchDown(int screenX, int screenY, int pointer, int button) {                                       
                testPoint.set(screenX, screenY, 0);
                camera.unproject(testPoint);

                // ask the world which bodies are within the given
                // bounding box around the mouse pointer
                hitBody[pointer] = null;

                world.QueryAABB(callback, testPoint.x - 1.0f, testPoint.y - 1.0f, testPoint.x + 1.0f, testPoint.y + 1.0f);
                hitBody[pointer] = tempBody;

                // if we hit something we create a new mouse joint
                // and attach it to the hit body.
                if (hitBody[pointer] != null) {

                    MouseJointDef def = new MouseJointDef();
                    def.bodyA = groundBody;
                    def.bodyB = hitBody[pointer];
                    def.collideConnected = true;                                                 
                    def.target.set(hitBody[pointer].getPosition().x, hitBody[pointer].getPosition().y);
                    def.maxForce = 3000.0f * hitBody[pointer].getMass();

                    mouseJoint[pointer] = (MouseJoint)world.createJoint(def);
                    hitBody[pointer].setAwake(true);
                } else {

                }
                return false;                 
}

@Override
public boolean touchUp(int screenX, int screenY, int pointer, int button) { 
    if (mouseJoint[pointer] != null) {
        world.destroyJoint(mouseJoint[pointer]);
        mouseJoint[pointer] = null;
    }
    return false;
}

/**a temporary vector for delta target destination during touchDragged() method**/
Vector2 target = new Vector2();

@Override
public boolean touchDragged(int screenX, int screenY, int pointer) {
    if (mouseJoint[pointer] != null) {
        camera.unproject(testPoint.set(screenX, screenY, 0));
        mouseJoint[pointer].setTarget(target.set(testPoint.x, testPoint.y));
    }
    return false;
}

@Override
public boolean mouseMoved(int screenX, int screenY) {
    return false;
}

@Override
public boolean scrolled(int amount) {
    return false;
}
    /*----------------end InputProcessor interface methods------------------*/

/*------------------------helper methods------------------------------------*/
    /*android screen touch vector for a mouse joint*/
    Vector3 testPoint = new Vector3(); //we instantiate this vector and the callback here so we don't irritate the GC
    QueryCallback callback = new QueryCallback() {
       @Override public boolean reportFixture (Fixture fixture) {
          // if the hit fixture's body is the ground body
          // we ignore it
          if (fixture.getBody() == groundBody) return true;

          if (fixture.testPoint(testPoint.x, testPoint.y)) {
              tempBody = fixture.getBody();
                return false;
          } else
                return true;
       }
    };          
/*------------------------end helper methods-------------------------------*/
}

解决方案

From what I can see the tempBody is never reset to null. What that means is that the first time you touch the pad it sets the tempBody to the touched paddle and then when you press outside the body the callback will not find a new body but not reset the testBody to null, so when you assign testBody to hitBody[pointer] it is setting it to the first paddle.

The way your touch down function should look like is:

@Override
public boolean touchDown(int screenX, int screenY, int pointer, int button) {                                       
            testPoint.set(screenX, screenY, 0);
            camera.unproject(testPoint);

            // ask the world which bodies are within the given
            // bounding box around the mouse pointer
            hitBody[pointer] = null;

            world.QueryAABB(callback, testPoint.x - 1.0f, testPoint.y - 1.0f, testPoint.x + 1.0f, testPoint.y + 1.0f);
            hitBody[pointer] = tempBody;

            // if we hit something we create a new mouse joint
            // and attach it to the hit body.
            if (hitBody[pointer] != null) {

                MouseJointDef def = new MouseJointDef();
                def.bodyA = groundBody;
                def.bodyB = hitBody[pointer];
                def.collideConnected = true;                                                 
                def.target.set(hitBody[pointer].getPosition().x, hitBody[pointer].getPosition().y);
                def.maxForce = 3000.0f * hitBody[pointer].getMass();

                mouseJoint[pointer] = (MouseJoint)world.createJoint(def);
                hitBody[pointer].setAwake(true);
            } else {

            }
            tempBody = null;

            return false;                 

}

This way the tempBody is always reset to null after use.

这篇关于通过libGDX的Box2D:如何创建每体内都有一种MouseJoint单独的Andr​​oid触摸?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆