Simple Radar for Space Android game

In space-shooter-like game it is nice to have Radar on the Hud.

Tere is simple way to draw radar as a Rectangle shape with dots on it. To do it I will use special Scene to manage dots movement and Rectangle as a Radar to show position of the objects.

Becouse this is only how to to create radar I will use simple graphics – rectangle with colored dots.

1)
First thing we need to define our World size fields. I will handle differend size of world and camera view. World should be bigger than camera size lets set it to 2 times bigger.

In BaseGameActivity class “MrRadar”

    public static final int CAMERA_HEIGHT = 320;
    public static final int CAMERA_WIDTH = 480;

    public static final int SPACE_HEIGHT = CAMERA_HEIGHT * 2;
    public static final int SPACE_WIDTH = CAMERA_WIDTH * 2;

2)
To manage Entities on Radar I will define interface “IRadarObject”. I will extends IEntity becouse of simple get size and position of the object.

	public interface IRadarObject extends IEntity {
		public ObjectConfig getConfig();
	}

Also I define class to hold all graphic information about dot on the radar, like color, etc.

	public class ObjectConfig {
		public int red;
		public int green;
		public int blue;
		public ObjectConfig(int red, int green, int blue) {
			this.red = red;
			this.green = green;
			this.blue = blue;
		}
	}

3)
Now lets define Radar class.

It will be Rectangle – that is simplest way.
To handle all object I should create a Map – it will be managed from our Scene (defined in p.4).

Map radarObjectsMap = new HashMap();

Dots will be draw on rectangle but first I must find a way to transform space points to radar points.
To calculate x position of the object I get it is X position in the space and devide it by space width – this is my percentage of the space where object is paced, so this is also percentage of position on radar.
It is very simple and can be done like this:

	
private Pos convertPosition(IEntity ent) {
		Pos pos = new Pos();
		pos.x = (ent.getX() / MrChain.SPACE_WIDTH) * getWidth();
		pos.y = (ent.getY() / MrChain.SPACE_HEIGHT) * getHeight();
		pos.width = this.getWidth() * SCALER;
		pos.height = this.getHeight() * SCALER;
			
		return pos;
	}

Pos is special class that contains only fields: x,y, width and height.

I must add methods to handle adding, removing and moving objects on the radar.
I will just use Map. In adding I will define size of the object, first position and color. to define position I will use my method from above. Also I will check if Map already contains this object:

	
public void addObject(IRadarObject obj) {
		if (!radarObjectsMap.containsKey(obj)) {
			Pos pos = convertPosition(obj);
			Rectangle rec = new Rectangle(pos.x, pos.y, pos.width, pos.height);
			rec.setColor(obj.getConfig().red, obj.getConfig().green, obj.getConfig().blue);
			attachChild(rec);
			radarObjectsMap.put(obj, rec);
		}
	}

In similar way I remove objects and update its size, color and position.

Radar class looks like this:

public class Radar extends Rectangle {
	private static final float SCALER = 0.05f;
	
	Map radarObjectsMap = new HashMap();

	public Radar(float pX, float pY, float pWidth, float pHeight) {
		super(pX, pY, pWidth, pHeight);
		setAlpha(0.3f);
	}

	public void addObject(IRadarObject obj) {
		if (!radarObjectsMap.containsKey(obj)) {
			Pos pos = convertPosition(obj);
			Rectangle rec = new Rectangle(pos.x, pos.y, pos.width, pos.height);
			rec.setColor(obj.getConfig().red, obj.getConfig().green, obj.getConfig().blue);
			attachChild(rec);
			radarObjectsMap.put(obj, rec);
		}
	}
	
	public void removeObject(IRadarObject obj) {
		if (radarObjectsMap.containsKey(obj)) {
			Rectangle rec = radarObjectsMap.remove(obj);
			detachChild(rec);
		}
	}
	
	public void removeAllObjects() {
		radarObjectsMap.clear();
		this.detachChildren();
	}
	
	public void updateObject(IRadarObject obj) {
		Rectangle rec = radarObjectsMap.get(obj);
		if (rec != null) {
			Pos pos = convertPosition(obj);
			rec.setPosition(pos.x, pos.y);
			rec.setHeight(pos.height);
			rec.setWidth(pos.width);
		}
	}
	
	private Pos convertPosition(IEntity ent) {
		Pos pos = new Pos();
		pos.x = (ent.getX() / MrChain.SPACE_WIDTH) * getWidth();
		pos.y = (ent.getY() / MrChain.SPACE_HEIGHT) * getHeight();
		pos.width = this.getWidth() * SCALER;
		pos.height = this.getHeight() * SCALER;
			
		return pos;
	}
	private class Pos {
		float x;
		float y;
		float width;
		float height;
	}
}

4)
To define scene I will extends Scene from AndEngie API and in each attachChild and removeChild I will call Radar methods to add and remove objects. Finally I define UpdateHandler to manage object movement.

public class SceneWithRadar extends Scene {
	Radar radar;
	IUpdateHandler radarHandler = new IUpdateHandler() {
		@Override
		public void onUpdate(float pSecondsElapsed) {
			for (IEntity child : SceneWithRadar.this.mChildren) {
				if (child instanceof IRadarObject) {
					radar.updateObject((IRadarObject) child);
				}
			}
		}
		@Override
		public void reset() {
		}
	};
	public SceneWithRadar(float radarPosX, float radarPosY, float radarWidth, float radarHeight) {
		radar = new Radar(radarPosX, radarPosY, radarWidth, radarHeight);
		registerUpdateHandler(radarHandler);
	}
	@Override
	public void attachChild(IEntity pEntity) throws IllegalStateException {
		if (pEntity instanceof IRadarObject) {
			radar.addObject((IRadarObject) pEntity);
		}
		super.attachChild(pEntity);
	}
	
	@Override
	public boolean detachChild(IEntity pEntity) {
		if (pEntity instanceof IRadarObject) {
			radar.removeObject((IRadarObject) pEntity);
		}
		return super.detachChild(pEntity);
	}
	
	@Override
	public void detachChildren() {
		radar.removeAllObjects();
		super.detachChildren();
	}
}