我在AndEngine中遇到了物理問題。我的精靈在移動時抖動,有時跳躍。我製作了32x32的「地板」,每個人都是另一個身體,所以我認爲這是問題(與角落或某物碰撞)。我試圖使用一個形狀而不是那些盒子,但問題仍然存在。AndEngine物理 - 我的角色在移動時動搖
它看起來像我的地板surfece不直,但不知何故不規則...
我的問題是,如何讓我的性格在這個表面上平滑移動?
順便說一句,如何讓我的角色更重?
我的整個代碼是在這裏:
private final int CAMERA_WIDTH = 800;
private final int CAMERA_HEIGHT = 480;
enum PlayerAction {
RUN,
NONE,
JUMP
}
enum Direction {
RIGHT,
LEFT,
NONE
}
enum BodyId {
PLAYER,
BOX
}
Direction mPlayerDirection = Direction.NONE;
Direction mLastPlayerDirection = Direction.NONE;
private Camera mCamera;
private Scene mGameScene;
private PhysicsWorld mPhysicsWorld;
private BitmapTextureAtlas mBoxBitmapTextureAtlas;
private BitmapTextureAtlas mPlayerBitmapTextureAtlas;
private ITextureRegion mBoxTextureRegion;
private TiledTextureRegion mPlayerTextureRegion;
private AnimatedSprite mPlayer;
private Body mPlayerBody;
private BitmapTextureAtlas mOnScreenControlTexture;
private ITextureRegion mOnScreenControlBaseTextureRegion;
private ITextureRegion mOnScreenControlKnobTextureRegion;
private AnalogOnScreenControl mAnalogOnScreenControl;
@Override
public EngineOptions onCreateEngineOptions() {
this.mCamera = new Camera(0, 0, CAMERA_WIDTH, CAMERA_HEIGHT);
EngineOptions mEngineOptions = new EngineOptions(true, ScreenOrientation.LANDSCAPE_FIXED, new FillResolutionPolicy(), this.mCamera);
mEngineOptions.getTouchOptions().setNeedsMultiTouch(true);
return mEngineOptions;
}
@Override
public void onCreateResources(
OnCreateResourcesCallback pOnCreateResourcesCallback)
throws Exception {
BitmapTextureAtlasTextureRegionFactory.setAssetBasePath("gfx/");
this.mBoxBitmapTextureAtlas = new BitmapTextureAtlas(this.getTextureManager(), 32, 32, TextureOptions.BILINEAR);
this.mBoxTextureRegion = BitmapTextureAtlasTextureRegionFactory.createFromAsset(this.mBoxBitmapTextureAtlas, this, "box.png", 0, 0);
this.mBoxBitmapTextureAtlas.load();
this.mPlayerBitmapTextureAtlas = new BitmapTextureAtlas(this.getTextureManager(), 256, 128, TextureOptions.BILINEAR);
this.mPlayerTextureRegion = BitmapTextureAtlasTextureRegionFactory.createTiledFromAsset(this.mPlayerBitmapTextureAtlas, this, "player.png", 0, 0, 3, 4);
this.mPlayerBitmapTextureAtlas.load();
this.mOnScreenControlTexture = new BitmapTextureAtlas(this.getTextureManager(), 256, 128, TextureOptions.BILINEAR);
this.mOnScreenControlBaseTextureRegion = BitmapTextureAtlasTextureRegionFactory.createFromAsset(this.mOnScreenControlTexture, this, "onscreen_control_base.png", 0, 0);
this.mOnScreenControlKnobTextureRegion = BitmapTextureAtlasTextureRegionFactory.createFromAsset(this.mOnScreenControlTexture, this, "onscreen_control_knob.png", 128, 0);
this.mOnScreenControlTexture.load();
pOnCreateResourcesCallback.onCreateResourcesFinished();
}
@Override
public void onCreateScene(OnCreateSceneCallback pOnCreateSceneCallback)
throws Exception {
this.mGameScene = new Scene();
initPhysics(this.mGameScene);
for(int i = 0; i <= 50; i++) {
Sprite sprite = new Sprite(i*32, this.mCamera.getHeight() - this.mBoxTextureRegion.getHeight(), this.mBoxTextureRegion, this.getVertexBufferObjectManager());
createBody(sprite, BodyType.StaticBody, 1, 0, 0, BodyId.BOX);
this.mGameScene.attachChild(sprite);
}
/* Calculate the coordinates for the face, so its centered on the camera. */
final float playerX = (CAMERA_WIDTH - this.mPlayerTextureRegion.getWidth())/2;
final float playerY = CAMERA_HEIGHT - this.mPlayerTextureRegion.getHeight() - 128;
this.mPlayer = new AnimatedSprite(playerX, playerY, this.mPlayerTextureRegion, this.getVertexBufferObjectManager()) {
@Override
protected void onManagedUpdate(float pSecondsElapsed) {
super.onManagedUpdate(pSecondsElapsed);
switch (mPlayerDirection) {
case RIGHT:
if (!mPlayerDirection.equals(mLastPlayerDirection)) {
mLastPlayerDirection = Direction.RIGHT;
GameActivity.this.mPlayer.animate(new long[]{200, 200, 200}, 3, 5, true);
}
break;
case LEFT:
if (!mPlayerDirection.equals(mLastPlayerDirection)) {
mLastPlayerDirection = Direction.LEFT;
GameActivity.this.mPlayer.animate(new long[]{200, 200, 200}, 9, 11, true);
}
break;
case NONE:
mLastPlayerDirection = Direction.NONE;
GameActivity.this.mPlayer.setCurrentTileIndex(6);
GameActivity.this.mPlayer.stopAnimation();
break;
default:
mLastPlayerDirection = Direction.NONE;
GameActivity.this.mPlayer.setCurrentTileIndex(6);
GameActivity.this.mPlayer.stopAnimation();
break;
}
}
};
this.mPlayer.setScaleCenterY(this.mPlayerTextureRegion.getHeight());
this.mPlayer.setScale(2);
this.mGameScene.attachChild(this.mPlayer);
this.mCamera.setChaseEntity(mPlayer);
this.mPlayerBody = createMovingBody(this.mPlayer, BodyType.DynamicBody, 1, 0, 0, BodyId.PLAYER);
this.mAnalogOnScreenControl = new AnalogOnScreenControl(32, CAMERA_HEIGHT - this.mOnScreenControlBaseTextureRegion.getHeight() - 32, this.mCamera, this.mOnScreenControlBaseTextureRegion, this.mOnScreenControlKnobTextureRegion, 0.1f, 200, this.getVertexBufferObjectManager(), new IAnalogOnScreenControlListener() {
@Override
public void onControlChange(final BaseOnScreenControl pBaseOnScreenControl, final float pValueX, final float pValueY) {
GameActivity.this.mPlayerBody.setLinearVelocity(new Vector2(pValueX*10, GameActivity.this.mPlayerBody.getLinearVelocity().y));
if (pValueX > 0)
GameActivity.this.mPlayerDirection = Direction.RIGHT;
else if (pValueX < 0)
GameActivity.this.mPlayerDirection = Direction.LEFT;
else
GameActivity.this.mPlayerDirection = Direction.NONE;
}
@Override
public void onControlClick(
AnalogOnScreenControl pAnalogOnScreenControl) {
GameActivity.this.mPlayerBody.setLinearVelocity(new Vector2(GameActivity.this.mPlayerBody.getLinearVelocity().x, -8.0f));
}
});
this.mAnalogOnScreenControl.getControlBase().setBlendFunction(GLES20.GL_SRC_ALPHA, GLES20.GL_ONE_MINUS_SRC_ALPHA);
this.mAnalogOnScreenControl.getControlBase().setAlpha(0.2f);
this.mAnalogOnScreenControl.getControlBase().setScaleCenter(0, 128);
this.mAnalogOnScreenControl.getControlBase().setScale(1.25f);
this.mAnalogOnScreenControl.getControlKnob().setScale(1.25f);
this.mAnalogOnScreenControl.refreshControlKnobPosition();
this.mGameScene.setChildScene(this.mAnalogOnScreenControl);
pOnCreateSceneCallback.onCreateSceneFinished(this.mGameScene);
}
@Override
public void onPopulateScene(Scene pScene,
OnPopulateSceneCallback pOnPopulateSceneCallback) throws Exception {
this.mEngine.registerUpdateHandler(new TimerHandler(3f, true, new ITimerCallback() {
@Override
public void onTimePassed(TimerHandler pTimerHandler) {
// TODO Auto-generated method stub
}
}));
pOnPopulateSceneCallback.onPopulateSceneFinished();
}
private void initPhysics(Scene pScene)
{
mPhysicsWorld = new PhysicsWorld(new Vector2(0, SensorManager.GRAVITY_EARTH), false);
pScene.registerUpdateHandler(mPhysicsWorld);
}
private Body createBody(Sprite pSprite, BodyType pBodyType, float pDensity, float pElasticity, float pFriction, BodyId pBodyId)
{
final FixtureDef objectFixtureDef = PhysicsFactory.createFixtureDef(pDensity, pElasticity, pFriction);
Body body = PhysicsFactory.createBoxBody(this.mPhysicsWorld, pSprite, pBodyType, objectFixtureDef);
body.setUserData(pBodyId);
return body;
}
private Body createMovingBody(Sprite pSprite, BodyType pBodyType, float pDensity, float pElasticity, float pFriction, BodyId pBodyId) {
Body body = createBody(pSprite, pBodyType, pDensity, pElasticity, pFriction, pBodyId);
mPhysicsWorld.registerPhysicsConnector(new PhysicsConnector(pSprite, body, true, false));
return body;
}
其實我覺得我的手機速度夠快了......我用的是HTC Sensation,所以CPU不應該有任何問題。其他的,即使更復雜的遊戲與更先進的物理工作很好!效果不是那種滯後,而是它看起來像我的Sprite與每個盒子角落發生碰撞,或者像我的'地面'不規則,我不知道爲什麼......但是我會嘗試固定 - 一步物理 – daltostronic
好的。這是更好的使用你鏈接MaxStepPhysicsWorld類,但我仍然有一個問題,「因爲有時我的性格停止,我必須跳,使其走得更遠...你有什麼想法?非常感謝幫助 – daltostronic
好的,我把我的身體設置成了圓圈......我找不到任何其他的方式,現在它已經很好了。也許以後我會簡單地設置多邊形的左下角和右下角,現在不需要 – daltostronic