Skip to content

Commit

Permalink
Keyboard player control.
Browse files Browse the repository at this point in the history
Camera following entities but within specified bounds.
  • Loading branch information
MarcinSc committed Jul 4, 2016
1 parent f7b2787 commit 2ccd5eb
Show file tree
Hide file tree
Showing 11 changed files with 208 additions and 4 deletions.
6 changes: 6 additions & 0 deletions core/assets/prefabs/levels/level-sample.prefab
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,11 @@
"1,-1,0": "grass",
"2,-1,0": "grass"
}
},
"CameraBoundsComponent": {
"minX": 0,
"minY": 0,
"maxX": 10,
"maxY": 10
}
}
6 changes: 6 additions & 0 deletions core/assets/prefabs/levels/level-sample2.prefab
Original file line number Diff line number Diff line change
Expand Up @@ -8,5 +8,11 @@
"-3,0,0": "stone",
"-4,0,0": "dirt"
}
},
"CameraBoundsComponent": {
"minX": 0,
"minY": 0,
"maxX": 10,
"maxY": 10
}
}
6 changes: 5 additions & 1 deletion core/assets/prefabs/player.prefab
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"LocationComponent": {
"x": 2,
"x": 0,
"y": 0,
"z": 0
},
Expand All @@ -10,5 +10,9 @@
"texturesForParts": {
"all": "blockTiles/Stone.png"
}
},
"PlayerControlledComponent": {},
"CameraFocusComponent": {
"focusWeight": 1
}
}
19 changes: 19 additions & 0 deletions core/src/main/java/jgd/platformer/Platformer.java
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import com.badlogic.gdx.ApplicationAdapter;
import com.badlogic.gdx.graphics.FPSLogger;
import com.gempukku.gaming.rendering.RenderingEngine;
import com.gempukku.gaming.time.InternalTimeManager;
import com.gempukku.secsy.context.SECSyContext;
import com.gempukku.secsy.entity.game.InternalGameLoop;
import jgd.platformer.level.LevelLoader;
Expand All @@ -13,13 +14,22 @@
import org.reflections.util.ClasspathHelper;
import org.reflections.util.ConfigurationBuilder;

import java.util.Collection;
import java.util.HashSet;
import java.util.Set;

public class Platformer extends ApplicationAdapter {
private FPSLogger fpsLogger;
private SECSyContext context;

private long lastUpdateTime;

private Collection<String> additionalProfiles;

public Platformer(Collection<String> additionalProfiles) {
this.additionalProfiles = additionalProfiles;
}

@Override
public void create() {
fpsLogger = new FPSLogger();
Expand All @@ -34,6 +44,8 @@ public void create() {
activeProfiles.add("prefabManager");
activeProfiles.add("annotationEventDispatcher");
activeProfiles.add("simpleEntityIndexManager");
activeProfiles.add("time");
activeProfiles.addAll(additionalProfiles);

Configuration scanBasedOnAnnotations = new ConfigurationBuilder()
.setScanners(new TypeAnnotationsScanner())
Expand All @@ -53,12 +65,19 @@ public void create() {
for (Object system : context.getSystems()) {
System.out.println(system.getClass().getSimpleName());
}

lastUpdateTime = System.currentTimeMillis();
}

@Override
public void render() {
fpsLogger.log();

long timePassed = System.currentTimeMillis() - lastUpdateTime;
lastUpdateTime += timePassed;

context.getSystem(InternalTimeManager.class).updateTime(timePassed);

context.getSystem(InternalGameLoop.class).processUpdate();

context.getSystem(RenderingEngine.class).render();
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package jgd.platformer.logic;

import com.gempukku.gaming.time.TimeEntityProvider;
import com.gempukku.secsy.context.annotation.Inject;
import com.gempukku.secsy.context.annotation.RegisterSystem;
import com.gempukku.secsy.context.system.LifeCycleSystem;
import com.gempukku.secsy.entity.EntityManager;
import com.gempukku.secsy.entity.EntityRef;

@RegisterSystem(
shared = TimeEntityProvider.class
)
public class PlatformerTimeEntityProvider implements TimeEntityProvider, LifeCycleSystem {
@Inject
private EntityManager entityManager;

private EntityRef timeEntity;

@Override
public void initialize() {
timeEntity = entityManager.createEntity();
}

@Override
public EntityRef getTimeEntity() {
return timeEntity;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
package jgd.platformer.logic.controls;

import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.Input;
import com.gempukku.gaming.time.TimeManager;
import com.gempukku.secsy.context.annotation.Inject;
import com.gempukku.secsy.context.annotation.RegisterSystem;
import com.gempukku.secsy.context.system.LifeCycleSystem;
import com.gempukku.secsy.entity.EntityRef;
import com.gempukku.secsy.entity.game.GameLoop;
import com.gempukku.secsy.entity.game.GameLoopListener;
import com.gempukku.secsy.entity.index.EntityIndex;
import com.gempukku.secsy.entity.index.EntityIndexManager;
import jgd.platformer.component.LocationComponent;

@RegisterSystem(
profiles = "keyboard"
)
public class KeyboardSystem implements LifeCycleSystem, GameLoopListener {
private static final float BLOCKS_PER_MILLISECOND = (4f / 1000);
@Inject
private GameLoop gameLoop;
@Inject
private TimeManager timeManager;
@Inject
private EntityIndexManager entityIndexManager;

private int[] leftKeys = {Input.Keys.LEFT, Input.Keys.A};
private int[] rightKeys = {Input.Keys.RIGHT, Input.Keys.D};
private EntityIndex controlledEntities;

@Override
public void initialize() {
gameLoop.addGameLoopListener(this);

controlledEntities = entityIndexManager.addIndexOnComponents(PlayerControlledComponent.class, LocationComponent.class);
}

@Override
public void update() {
boolean leftPressed = isLeftPressed();
boolean rightPressed = isRightPressed();

long timeSinceLastUpdate = timeManager.getTimeSinceLastUpdate();

float xDiff = 0;

if (leftPressed && !rightPressed) {
xDiff -= timeSinceLastUpdate * BLOCKS_PER_MILLISECOND;
} else if (rightPressed && !leftPressed) {
xDiff += timeSinceLastUpdate * BLOCKS_PER_MILLISECOND;
}

if (xDiff != 0) {
for (EntityRef entityRef : controlledEntities.getEntities()) {
LocationComponent location = entityRef.getComponent(LocationComponent.class);
location.setX(location.getX() + xDiff);
entityRef.saveChanges();
}
}
}

private boolean isLeftPressed() {
return isAnyPressed(leftKeys);
}

private boolean isRightPressed() {
return isAnyPressed(rightKeys);
}

private boolean isAnyPressed(int[] keys) {
for (int key : keys) {
if (Gdx.input.isKeyPressed(key))
return true;
}
return false;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
package jgd.platformer.logic.controls;

import com.gempukku.secsy.entity.Component;

public interface PlayerControlledComponent extends Component {
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package jgd.platformer.rendering;

import com.gempukku.secsy.entity.Component;

public interface CameraBoundsComponent extends Component {
float getMinX();

float getMaxX();

float getMinY();

float getMaxY();
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package jgd.platformer.rendering;

import com.gempukku.secsy.entity.Component;

public interface CameraFocusComponent extends Component {
float getFocusWeight();

void setFocusWeight(float focusWeight);
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@
import com.gempukku.secsy.context.system.LifeCycleSystem;
import com.gempukku.secsy.entity.EntityManager;
import com.gempukku.secsy.entity.EntityRef;
import com.gempukku.secsy.entity.index.EntityIndex;
import com.gempukku.secsy.entity.index.EntityIndexManager;
import jgd.platformer.component.LocationComponent;

@RegisterSystem(
shared = RenderingEntityProvider.class
Expand All @@ -15,12 +18,18 @@ public class PlatformerRenderingEntityProvider implements RenderingEntityProvide
private static final int DISTANCE_FROM_TERRAIN = 8;
@Inject
private EntityManager entityManager;
@Inject
private EntityIndexManager entityIndexManager;

private EntityRef cameraEntity;
private EntityIndex cameraFocusedEntities;
private EntityIndex cameraBoundsEntities;

@Override
public void initialize() {
cameraEntity = entityManager.createEntity();
cameraFocusedEntities = entityIndexManager.addIndexOnComponents(CameraFocusComponent.class, LocationComponent.class);
cameraBoundsEntities = entityIndexManager.addIndexOnComponents(CameraBoundsComponent.class);
}

@Override
Expand All @@ -30,8 +39,32 @@ public EntityRef getRenderingEntity() {

@Override
public void setupRenderingCamera(Camera camera) {
camera.position.set(0, 0, DISTANCE_FROM_TERRAIN);
camera.lookAt(0, 0, 0);
float weightSum = 0;
float sumX = 0;
float sumY = 0;

for (EntityRef entityRef : cameraFocusedEntities.getEntities()) {
CameraFocusComponent cameraFocus = entityRef.getComponent(CameraFocusComponent.class);
float weight = cameraFocus.getFocusWeight();
if (weight > 0) {
LocationComponent location = entityRef.getComponent(LocationComponent.class);
sumX += location.getX() * weight;
sumY += location.getY() * weight;
weightSum += weight;
}
}

float resultX = sumX / weightSum;
float resultY = sumY / weightSum;

EntityRef boundsEntity = cameraBoundsEntities.getEntities().iterator().next();
CameraBoundsComponent cameraBounds = boundsEntity.getComponent(CameraBoundsComponent.class);

resultX = Math.max(Math.min(resultX, cameraBounds.getMaxX()), cameraBounds.getMinX());
resultY = Math.max(Math.min(resultY, cameraBounds.getMaxY()), cameraBounds.getMinY());

camera.position.set(resultX, resultY, DISTANCE_FROM_TERRAIN);
camera.lookAt(resultX, resultY, 0);
camera.up.set(0, 1, 0);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,15 @@
import com.badlogic.gdx.backends.lwjgl.LwjglApplicationConfiguration;
import jgd.platformer.Platformer;

import java.util.Collections;

public class DesktopLauncher {
public static void main(String[] arg) {
LwjglApplicationConfiguration config = new LwjglApplicationConfiguration();
// Only for debug purposes, remove for production
config.backgroundFPS = 0;
config.foregroundFPS = 0;
config.vSyncEnabled = false;
new LwjglApplication(new Platformer(), config);
new LwjglApplication(new Platformer(Collections.singleton("keyboard")), config);
}
}

0 comments on commit 2ccd5eb

Please sign in to comment.