using System;
using System.Collections;
using System.Xml;
using System.Data.OleDb;
using System.Data.SqlClient;
using banco1.persistencia;

namespace banco1.domain
{
	/// <summary>
	/// Representa una cuenta corriente
	/// </summary>
	public class Cuenta : Producto
	{
		public Cuenta(String sucursal) : base(sucursal) 
		{
		}

		public Cuenta(String s, String ccc) : base(s, ccc)
		{
			this.cargaMovimientos();
		}

		public override void insert() 
		{
			base.insert();
			String SQL="Insert into Cuentas " +
				"(Sucursal, CCC) values (?, ?)";
			OleDbCommand cmd = Broker.getCommand(SQL);
			cmd.Parameters.Add("", OleDbType.VarChar).Value=this.mSucursal;
			cmd.Parameters.Add("", OleDbType.VarChar).Value=this.mCCC;
			cmd.ExecuteNonQuery();
			cmd.Connection.Close();
		}

		/*** Operaciones con dinero ****/
		public double saldo 
		{
			get { 
				double result=0;
				for (int i=0; i<this.mMovimientos.Count; i++) 
				{
					Movimiento m=(Movimiento) this.mMovimientos[i];
					result+=m.importe;
				}
				return result;
			}
		}

		public void ingresar(double importe) 
		{
			if (importe<=0)
				throw new Exception("Debe ingresar un importe positivo");
			if (this.cancelado || !this.estaActivo())
				throw new Exception("La cuenta está bloqueada o cancelada");
			Movimiento m=new Movimiento("Ingreso en efectivo", System.DateTime.Now, importe, this);
			this.mMovimientos.Add(m);
			m.insert();
		}

		public void retirar(double importe) 
		{
			if (importe<=0)
				throw new Exception("Debe retirar un importe positivo");
			if (importe>saldo)
				throw new Exception("No dispone de suficiente saldo");
			if (this.cancelado || !this.estaActivo())
				throw new Exception("La cuenta está bloqueada o cancelada");
			importe=-importe;
			Movimiento m=new Movimiento("Retirada de efectivo", System.DateTime.Now, importe, this);
			this.mMovimientos.Add(m);
			m.insert();
		}

		public void transferir(Cuenta destino, double importe) 
		{
			if (importe<=0)
				throw new Exception("Debe transferir un importe positivo");
			if (importe>saldo)
				throw new Exception("No dispone de suficiente saldo para realizar la operación");
			if (this.cancelado || !this.estaActivo())
				throw new Exception("La cuenta ordenante está bloqueada o cancelada");
			if (destino.cancelado || !destino.estaActivo())
				throw new Exception("La cuenta destino está bloqueada o cancelada");
			Movimiento m=new Movimiento("Orden de transferencia", System.DateTime.Now, -importe, this);
			this.mMovimientos.Add(m);
			m.insert();
			Movimiento m2=new Movimiento("Transferencia a su favor", DateTime.Now, importe, destino);
			destino.mMovimientos.Add(m2);
			m2.insert();
		}

		public void reciboDomiciliado(String organismo, double importe) 
		{
			if (this.cancelado || !this.estaActivo())
				throw new Exception("La cuenta está bloqueada o cancelada");
			Movimiento m=new Movimiento("Recibo de " + organismo, System.DateTime.Now, -importe, this);
			this.mMovimientos.Add(m);
			m.insert();
		}

		/******* Otras operaciones ********/
		public override bool esCancelable() 
		{
			if (saldo<0 || !mActivo) return false;
			return true;
		}

	}
}
