using Newtonsoft.Json.Linq;
using System.Collections.Generic;
using UnityEngine;
using System;

public class CIWSModule : AngularModule {
	private int ammo;
	private int roundPerSec;
	private float damagePerRound;
	private float roundSpeed;
	private float hitProbability;

	public CIWSModule(JObject json) : base(json) {
		ammo = (int)json["ammo"];
		roundPerSec = (int)json["roundPerSec"];
		damagePerRound = (float)json["damagePerRound"];
		roundSpeed = (float)json["roundSpeed"];
		hitProbability = (float)json["hitProbability"];

		icon = Resources.Load("Sprites/Modules/Icons/CIWS/" + getUniqueName(), typeof(Sprite)) as Sprite;
		silhouette = Resources.Load("Sprites/Modules/Silhouettes/CIWS/" + getUniqueName(), typeof(Sprite)) as Sprite;
	}

	public int getMaxAmmo() {
		return ammo;
	}

	public int getRoundPerSec() {
		return roundPerSec;
	}

	public float getDamagePerRound() {
		return damagePerRound;
	}

	public float getRoundSpeed() {
		return roundSpeed;
	}

	public float getHitProbability() {
		return hitProbability;
	}

	public static CIWSModule[] loadModules(string[] filenames) {
		Array.Sort(filenames);
		CIWSModule[] array = new CIWSModule[filenames.Length];

		for (int i = 0; i < filenames.Length; i++) {
			array[i] = new CIWSModule(jsonFromFile(filenames[i]));
		}

		return array;
	}

	override public void updateClasses() {
	}

	override public ModuleData getData(int parent, float angleOffset, Vector position) {
		return new CIWSModuleData(parent, this, angleOffset, position);
	}
}

public class CIWSModuleData : AngularModuleData {
	private int ammoLeft;
	private DeployedUnit target;

	public CIWSModuleData(int parent, Module template, float angleOffset, Vector position) : base(parent, template, angleOffset, position) {
		ammoLeft = ((CIWSModule)template).getMaxAmmo();
	}

	public int getAmmoLeft() {
		return ammoLeft;
	}

	public void setAmmo(int newAmmo) {
		ammoLeft = newAmmo;
	}

	public bool canFire(DeployedUnit missile) {
		return target == null && ammoLeft > 0 && isInRangeAndAngle(missile);
	}

	public void beginFire(DeployedUnit target) {
		this.target = target;
	}

	override public void checkDestroyedUnits(List<DeployedUnit> destroyedUnits) {
		if (target != null && destroyedUnits.Contains(target)) {
			target = null;
		}
	}

	override public bool isFiring() {
		return target != null && ammoLeft > 0;
	}

	override public void updateTime(float delta) {
		if (!isFiring()) {
			return;
		}

		int hits = 0;
		int total = 0;
		for (int i = 0; i < ((CIWSModule)template).getRoundPerSec() * delta && i < ammoLeft; i++) {
			if (UnityEngine.Random.value < ((CIWSModule)template).getHitProbability()) {
				hits ++;
			}
			total ++;
		}

		Requests.setCIWSAmmo(this, ammoLeft - total);
		float distance = GameController.fromID(parent).getPosition().distance(target.getPosition());

		//no requests needed, as bullets are not shared with the clients
		GameController.addBullets(new Bullets(hits, distance / (((CIWSModule)template).getRoundSpeed() + target.getcurrentSpeed()), ((CIWSModule)template).getDamagePerRound(), target, template.getName()));
	}
}