WalkAnimator.java
package com.devcharles.piazzapanic.utility;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.g2d.Animation;
import com.badlogic.gdx.graphics.g2d.TextureRegion;
/**
* Abstract class that helps with setting up animations for characters in the
* game.
* To use, initialise each directional animation.
*/
public abstract class WalkAnimator {
protected ArrayList<Animation<TextureRegion>> walkRight = new ArrayList<>();
protected ArrayList<Animation<TextureRegion>> walkLeft = new ArrayList<>();
protected ArrayList<Animation<TextureRegion>> walkUp = new ArrayList<>();
protected ArrayList<Animation<TextureRegion>> walkDown = new ArrayList<>();
/**
* All directions that the animations support.
*/
public enum Direction {
left,
right,
up,
down
}
/**
* Tuple Representing the dimensions of the spritesheet to be used.
* The values represent columns and rows, respectively.
*/
private static final Pair<Integer, Integer> dimensions = new Pair<Integer, Integer>(10, 1);
/**
* @param rotation box2d body rotation
* @param isMoving whether the entity is moving or not
* @param frameTime elapsed time for the animation
* @param holding how many items the character is holding
* @return A texture region to draw, and a rotation used for rendering the
* region.
*/
public abstract TextureRegion getFrame(float rotation, boolean isMoving, float frameTime, int holding);
private static HashMap<Integer, Direction> directionMap = new HashMap<Integer, Direction>() {
{
put(0, Direction.right);
put(45, Direction.up);
put(-45, Direction.down);
put(90, Direction.up);
put(-90, Direction.down);
put(135, Direction.up);
put(-135, Direction.down);
put(180, Direction.left);
}
};
private static int[] directions = { -135, -90, -45, 0, 45, 90, 135, 180 };
/**
* Approximate the Box2D rotation to the nearest mapped value.
*
* @param rotation body rotation in degrees.
* @return {@link Direction} the character should be facing in.
*/
public static Direction rotationToDirection(float rotation) {
int orientation = Math.round(rotation);
// Find closest mapped integer value in directions
int minDistance = Math.abs(directions[0] - orientation);
int index = 0;
for (int i = 0; i < directions.length; i++) {
int currentDistance = Math.abs(directions[i] - orientation);
if (currentDistance < minDistance) {
index = i;
minDistance = currentDistance;
}
}
rotation = directions[index];
Direction dir = directionMap.get((int) Math.round(rotation));
return dir;
}
/**
* Generate Animations from a {@link Texture}, override this if you want to
* parse the texture spritesheet differently.
*
* @param currentSheet The {@link Texture} containing all the frames of the
* animation.
* @param value Variant of the spritesheet (0 -> walk, 1 -> hold one
* item, 2 -> hold crate)
*/
protected void addTextures(Texture currentSheet, int value) {
// Split the spritesheet into separate textureregions
TextureRegion[][] tmp = TextureRegion.split(currentSheet, 32, 32);
// Flatten the array
TextureRegion[] frames = new TextureRegion[dimensions.first * dimensions.second];
int index = 0;
for (int i = 0; i < dimensions.second; i++) {
for (int j = 0; j < dimensions.first; j++) {
frames[index++] = tmp[i][j];
}
}
walkDown.add(new Animation<TextureRegion>(0.1f, Arrays.copyOfRange(frames, 0, 3)));
walkUp.add(new Animation<TextureRegion>(0.1f, Arrays.copyOfRange(frames, 3, 6)));
walkRight.add(new Animation<TextureRegion>(0.1f, Arrays.copyOfRange(frames, 6, 10)));
// Create the left animation by copying and flipping textures.
TextureRegion[] toCopy = walkRight.get(value).getKeyFrames();
TextureRegion[] flippedRegions = new TextureRegion[toCopy.length];
for (int i = 0; i < flippedRegions.length; i++) {
flippedRegions[i] = new TextureRegion(toCopy[i]);
flippedRegions[i].flip(true, false);
}
walkLeft.add(new Animation<TextureRegion>(0.1f, flippedRegions));
}
}