都是为了方便自己调试而在测试阶段使用的功能。
正如上一章提到的:我们也需要加些方便程序员自己的控制功能,包括后门。以方便调试。
在WorldController里加入:
public void update(float deltaTime) {
handleDebugInput(deltaTime);
updateTestObjects(deltaTime);
}
private void handleDebugInput(float deltaTime) {
if (Gdx.app.getType() != ApplicationType.Desktop)
return;
// Selected Sprite Controls
float sprMoveSpeed = 5 * deltaTime;
if (Gdx.input.isKeyPressed(Keys.A))
moveSelectedSprite(-sprMoveSpeed, 0);
if (Gdx.input.isKeyPressed(Keys.D))
moveSelectedSprite(sprMoveSpeed, 0);
if (Gdx.input.isKeyPressed(Keys.W))
moveSelectedSprite(0, sprMoveSpeed);
if (Gdx.input.isKeyPressed(Keys.S))
moveSelectedSprite(0, -sprMoveSpeed);
}
private void moveSelectedSprite(float x, float y) {
testSprites[selectedSprite].translate(x, y);
}
我们为什么要闲得在update里做判断呢,为什么不用监听器?(用监听器照样可以实现,这里略了,有兴趣可以自己试试)
因为我们需要知道按键是不是一直按着isKeyPressed()。监听器是事件触发的,直接这样做更省事。你可以按A, D, W, S看看现在效果。
当然了,现在我们要实现Reset功能,按R键游戏重新开始。因为不用一直判断,所以我们使用监听器。
public class WorldController extends InputAdapter {
// ...
}
注册监听
private void init () {
Gdx.input.setInputProcessor(this);
initTestObjects();
}
这时候,Libgdx会把所有的input事件都发给注册了的监听器,你接到了input事件,该干嘛干嘛去。比如现在我们要处理R键和空格键。
@Override
public boolean keyUp(int keycode) {
// Reset game world
if (keycode == Keys.R) {
init();
Gdx.app.debug(TAG, "Game world resetted");
}
// Select next sprite
else if (keycode == Keys.SPACE) {
selectedSprite = (selectedSprite + 1) % testSprites.length;
Gdx.app.debug(TAG, "Sprite #" + selectedSprite + " selected");
}
return false;
}
跑起来,试试这些实现的功能吧。
接下来,我们来玩摄像机:
增加一个类:CameraHelper
package com.packtpub.libgdx.canyonbunny.util;
import com.badlogic.gdx.graphics.OrthographicCamera;
import com.badlogic.gdx.graphics.g2d.Sprite;
import com.badlogic.gdx.math.MathUtils;
import com.badlogic.gdx.math.Vector2;
public class CameraHelper {
private static final String TAG = CameraHelper.class.getName();
private final float MAX_ZOOM_IN = 0.25f;
private final float MAX_ZOOM_OUT = 10.0f;
private Vector2 position;
private float zoom;
private Sprite target;
public CameraHelper() {
position = new Vector2();
zoom = 1.0f;
}
public void update(float deltaTime) {
if (!hasTarget())
return;
position.x = target.getX() + target.getOriginX();
position.y = target.getY() + target.getOriginY();
}
public void setPosition(float x, float y) {
this.position.set(x, y);
}
public Vector2 getPosition() {
return position;
}
public void addZoom(float amount) {
setZoom(zoom + amount);
}
public void setZoom(float zoom) {
this.zoom = MathUtils.clamp(zoom, MAX_ZOOM_IN, MAX_ZOOM_OUT);
}
public float getZoom() {
return zoom;
}
public void setTarget(Sprite target) {
this.target = target;
}
public Sprite getTarget() {
return target;
}
public boolean hasTarget() {
return target != null;
}
public boolean hasTarget(Sprite target) {
return hasTarget() && this.target.equals(target);
}
public void applyTo(OrthographicCamera camera) {
camera.position.x = position.x;
camera.position.y = position.y;
camera.zoom = zoom;
camera.update();
}
}
这个类可以控制摄像机上下左右移动,拉近放远,跟随目标等动作,方便自己调试。
ok,把它加入到controller中:
首先申明一个对象:public CameraHelper cameraHelper;
然后在init里初始化:cameraHelper = new CameraHelper();
接着在update里加上:cameraHelper.update(deltaTime);
最后修改keyup里的控制:
public CameraHelper cameraHelper;
private void init() {
Gdx.input.setInputProcessor(this);
cameraHelper = new CameraHelper();
initTestObjects();
}
public void update(float deltaTime) {
handleDebugInput(deltaTime);
updateTestObjects(deltaTime);
cameraHelper.update(deltaTime);
}
@Override
public boolean keyUp(int keycode) {
// Reset game world
if (keycode == Keys.R) {
init();
Gdx.app.debug(TAG, "Game world resetted");
}
// Select next sprite
else if (keycode == Keys.SPACE) {
selectedSprite = (selectedSprite + 1) % testSprites.length;
// Update camera's target to follow the currently
// selected sprite
if (cameraHelper.hasTarget()) {
cameraHelper.setTarget(testSprites[selectedSprite]);
}
Gdx.app.debug(TAG, "Sprite #" + selectedSprite + "selected");
}
// Toggle camera follow
else if (keycode == Keys.ENTER) {
cameraHelper.setTarget(cameraHelper.hasTarget() ? null
: testSprites[selectedSprite]);
Gdx.app.debug(TAG,
"Camera follow enabled: " + cameraHelper.hasTarget());
}
return false;
}
把对摄像机的上下左右控制加上:
private void handleDebugInput(float deltaTime) {
if (Gdx.app.getType() != ApplicationType.Desktop)
return;
// Selected Sprite Controls
float sprMoveSpeed = 5 * deltaTime;
if (Gdx.input.isKeyPressed(Keys.A))
moveSelectedSprite(-sprMoveSpeed, 0);
if (Gdx.input.isKeyPressed(Keys.D))
moveSelectedSprite(sprMoveSpeed, 0);
if (Gdx.input.isKeyPressed(Keys.W))
moveSelectedSprite(0, sprMoveSpeed);
if (Gdx.input.isKeyPressed(Keys.S))
moveSelectedSprite(0, -sprMoveSpeed);
// Camera Controls (move)
float camMoveSpeed = 5 * deltaTime;
float camMoveSpeedAccelerationFactor = 5;
if (Gdx.input.isKeyPressed(Keys.SHIFT_LEFT))
camMoveSpeed *= camMoveSpeedAccelerationFactor;
if (Gdx.input.isKeyPressed(Keys.LEFT))
moveCamera(-camMoveSpeed, 0);
if (Gdx.input.isKeyPressed(Keys.RIGHT))
moveCamera(camMoveSpeed, 0);
if (Gdx.input.isKeyPressed(Keys.UP))
moveCamera(0, camMoveSpeed);
if (Gdx.input.isKeyPressed(Keys.DOWN))
moveCamera(0, -camMoveSpeed);
if (Gdx.input.isKeyPressed(Keys.BACKSPACE))
cameraHelper.setPosition(0, 0);
// Camera Controls (zoom)
float camZoomSpeed = 1 * deltaTime;
float camZoomSpeedAccelerationFactor = 5;
if (Gdx.input.isKeyPressed(Keys.SHIFT_LEFT))
camZoomSpeed *= camZoomSpeedAccelerationFactor;
if (Gdx.input.isKeyPressed(Keys.COMMA))
cameraHelper.addZoom(camZoomSpeed);
if (Gdx.input.isKeyPressed(Keys.PERIOD))
cameraHelper.addZoom(-camZoomSpeed);
if (Gdx.input.isKeyPressed(Keys.SLASH))
cameraHelper.setZoom(1);
}
private void moveCamera(float x, float y) {
x += cameraHelper.getPosition().x;
y += cameraHelper.getPosition().y;
cameraHelper.setPosition(x, y);
}
让摄像机跟随,还需要修改render:这样才能保证移动之后的摄像机,更新到了新的位置。
public void renderTestObjects() {
worldController.cameraHelper.applyTo(camera);
batch.setProjectionMatrix(camera.combined);
batch.begin();
for (Sprite sprite : worldController.testSprites) {
sprite.draw(batch);
}
batch.end();
}
按键说明:
AWSD-控制箱子移动,空格键选择下一个箱子,R键重置游戏。
上下左右控制摄像机,逗号句号-放大缩小,破折号恢复正常大小。backspace键恢复原点位置,enter键让摄像机跟随控制的箱子。
开心的跑起来耍吧,骚年!