package speiger.src.coreengine.math.collision2d;

import java.util.Iterator;

import speiger.src.coreengine.math.vector.ints.Vec2i;
import speiger.src.coreengine.math.vector.ints.Vec3i;

public class Circle implements I2DCollision {
	final Vec2i center;
	final int radius;
	
	public Circle(int x, int y, int radius) {
		center = Vec2i.of(x, y);
		this.radius = radius;
	}
	
	public Circle(Vec2i center, int radius) {
		this.center = center.asImmutable();
		this.radius = radius;
	}
	
	public Circle(Vec3i data) {
		this(data.x(), data.y(), data.z());
	}
	
	public Vec2i getCenter() { return center; }
	
	public int getRadius() { return radius; }
	
	@Override
	public boolean isColliding(int x, int y) {
		int xDiff = center.x() - x;
		int yDiff = center.y() - y;
		return ((xDiff * xDiff) + (yDiff * yDiff)) < radius * radius;
	}
	
	@Override
	public Iterator<Vec2i> iterator() {
		return new Iterator<Vec2i>() {
			Vec2i iter = step(Vec2i.mutable(center).sub(radius));
			Vec2i result = Vec2i.mutable();
			
			@Override
			public boolean hasNext() {
				return iter != null;
			}
			
			@Override
			public Vec2i next() {
				result.set(iter);
				iter = step(iter);
				return result;
			}
			
			Vec2i step(Vec2i iter) {
				while(iter != null) {
					if(iter.add(1, 0).x() >= center.x() + radius) {
						if(iter.sub((radius * 2), 0).add(0, 1).y() >= center.y() + radius) iter = null;
					}
					if(iter != null && isColliding(iter)) break;
				}
				return iter;
			}
		};
	}
}
