package dwarf.engine.core;

import java.util.Objects;

import dwarf.GameObject;
import dwarf.util.Vector2;

import static dwarf.util.Vector2.ZERO;

/**
 * @author Matthew 'siD' Van der Bijl
 *
 * @see dwarf.GameObject
 * @see java.lang.Object
 * @see java.lang.Cloneable
 */
public class Camera extends java.lang.Object implements Cloneable, GameObject {

    /**
     * the default view port.
     */
    public static Camera mainCamera = new Camera();

    public static void setMainCamera(Camera mainCamera) {
        Camera.mainCamera = mainCamera;
    }

    public static Camera getMainCamera() {
        return Camera.mainCamera;
    }

    private Vector2 position;

    /**
     * Default constructor.
     */
    public Camera() {
        super();
        this.position = ZERO;
    }

    public Camera(Vector2 position) {
        super();
        this.position = position;
    }

    public Camera(Camera camera) {
        super();
        this.position = camera.getPosition();
    }

    /**
     * Callback function used to update the state of the game every frame.
     */
    @Override
    public void update() {
    }

    /**
     * Callback function used to update the state of the game every frame.
     */
    @Override
    public void render() {
    }

    public Vector2 getPosition() {
        return this.position;
    }

    public void setPosition(Vector2 position) {
        this.position = position;
    }

    public void translate(float deltaX, float deltaY) {
        this.position.translateX(deltaX);
        this.position.translateY(deltaY);
    }

    public void translateX(float deltaX) {
        this.position.translateX(deltaX);
    }

    public void translateY(float deltaY) {
        this.position.translateY(deltaY);
    }

    @Override
    public String toString() {
        return "Camera = {"
                + "position: " + getPosition() + ", "
                + "super: " + super.toString()
                + "}";
    }

    @Override
    public int hashCode() {
        int hash = 3;
        hash = 47 * hash + Objects.hashCode(getPosition());
        return hash;
    }

    @Override
    public boolean equals(Object obj) {
        if (obj == null) {
            return false;
        } else if (getClass() != obj.getClass()) {
            return false;
        }
        final Camera other = (Camera) obj;
        if (!Objects.equals(this.getPosition(), other.getPosition())) {
            return false;
        }
        return true;
    }

    public void gotoPos(Vector2 destination, float speed) {
        if (this.getPosition().getX() > destination.getX()) {
            this.getPosition().translateX(-speed);
        }
        if (this.getPosition().getX() < destination.getX()) {
            this.getPosition().translateX(speed);
        }
        if (this.getPosition().getY() < destination.getY()) {
            this.getPosition().translateY(speed);
        }
        if (this.getPosition().getY() > destination.getY()) {
            this.getPosition().translateY(-speed);
        }
    }

    public void gotoPos(Vector2 destination) {
        this.gotoPos(destination, 1);
    }

    public void gotoPos(double xPos, double yPos) {
        this.gotoPos(new Vector2(xPos, yPos), 1);
    }

    public void gotoPos(double xPos, double yPos, float speed) {
        this.gotoPos(new Vector2(xPos, yPos), speed);
    }

    public Vector2 getCenterPosition() {
        return new Vector2(
                this.getPosition().getX() + Window.getWidth() / 2,
                this.getPosition().getY() + Window.getHeight() / 2
        );
    }

    @Override
    public Object clone() throws CloneNotSupportedException {
        return new Camera(this);
    }

}

@@ -632,24 +632,79 @@
 mera;%0A    %7D%0A
+    %0A    /**%0A     * the location of the camera.%0A     */
 %0A    private

Update Camera.java