using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using KashFlowPayPal.Classes;
using com.paypal.soap.api;
using KashFlowPayPal.uk.co.kashflow.secure;
namespace KashFlowPayPal
{
    public partial class frmTransactionSearch : Form
    {
        //For listview sorting
        private ListViewColumnSorter lvwColumnSorter;

        public frmTransactionSearch()
        {
            InitializeComponent();
            lvwColumnSorter = new ListViewColumnSorter();
            this.lstTransactions.ListViewItemSorter = lvwColumnSorter;
        }

        #region LOADING

        private void frmTransactionSearch_Load(object sender, EventArgs e)
        {

            PayPalConstants.LoadPayPalConstants();
            dtpStartDate.Value = DateTime.Now;
            dtpEndDate.Value = DateTime.Now;
            this.radWithin.Checked = true;
            cmbWithin.SelectedItem = "The Past Day";

            //This was removed as columns are now set in the designer
            //ColumnHeader header1 = this.lstTransactions.Columns.Add("ID", 21 * Convert.ToInt32(lstTransactions.Font.SizeInPoints), HorizontalAlignment.Left);
            //ColumnHeader header1 = this.lstTransactions.Columns.Add("Time", 150, HorizontalAlignment.Left);
            //ColumnHeader header2 = this.lstTransactions.Columns.Add("Status", 75, HorizontalAlignment.Left);
            //ColumnHeader header3 = this.lstTransactions.Columns.Add("Payer Name", 175, HorizontalAlignment.Left);
            //ColumnHeader header4 = this.lstTransactions.Columns.Add("Gross Amount", 175, HorizontalAlignment.Left);

            // Set the column default sorting options
            lvwColumnSorter.SortColumn = 0;
            lvwColumnSorter.Order = SortOrder.Ascending;
        }

        #endregion

        #region MENU BUTTONS


        private void mnukashFlowCredentials_Click(object sender, EventArgs e)
        {
            Program.frmWelco.ShowDialog();
        }

        private void mnupaypalCredentials_Click(object sender, EventArgs e)
        {
            Program.frmMain.ShowDialog();
        }

        private void programOptions_Click(object sender, EventArgs e)
        {
            Program.frmGenera.ShowDialog();
        }

        private void helpToolStripMenuItem_Click(object sender, EventArgs e)
        {
            System.Diagnostics.Process.Start("http://api.kashflow.co.uk");
        }

        #endregion

        #region SEARCHING PAYPAL

        private void btnSubmit_Click(object sender, EventArgs e)
        {
            PayPalConstants.LoadPayPalConstants();

            if (PayPalConstants.API_PASSWORD == "" || PayPalConstants.API_SIGNATURE == "" || PayPalConstants.API_USERNAME == "")
            {

                MessageBox.Show("Please enter your PayPal credentials before attempting to search for transactions", "PP:Konnect", MessageBoxButtons.OK, MessageBoxIcon.Error);
                return;
            }

            DateTime startDate = DateTime.Now;
            DateTime endDate = DateTime.Now;

            //ensure the user has selected a valid date range
            if (this.radWithin.Checked)
            {
                switch (cmbWithin.Text)
                {
                    case "":
                        MessageBox.Show("Please select a time period", "PP:Konnect", MessageBoxButtons.OK, MessageBoxIcon.Error);
                        return;
                    case "The Past Day":
                        startDate = startDate.AddDays(-1);
                        break;
                    case "The Past Week":
                        startDate = startDate.AddDays(-7);
                        break;
                    case "The Past Two Weeks":
                        startDate = startDate.AddDays(-14);
                        break;
                    case "The Past Month":
                        startDate = startDate.AddMonths(-1);
                        break;
                    case "The Past Two Months":
                        startDate = startDate.AddMonths(-2);
                        break;
                    case "The Past Six Months":
                        startDate = startDate.AddMonths(-6);
                        break;
                    case "The Past Year":
                        startDate = startDate.AddYears(-1);
                        break;
                }
            }
            else
            {
                startDate = DateTime.Parse(dtpStartDate.Text + " 00:00:00");
                endDate = DateTime.Parse(dtpEndDate.Text + " 23:59:59");
            }

            btnAssignTransactions.Enabled = false;
            lblMessage.Text = "Searching PayPal...";
            Application.DoEvents();
            lstTransactions.Items.Clear();
            PayPalAPI api = new PayPalAPI();


            TransactionSearchResponseType tra = api.TransactionSearch(startDate, endDate, "");
            if (tra.Errors != null)
            {
                MessageBox.Show(tra.Errors[0].LongMessage, "PP:Konnect", MessageBoxButtons.OK, MessageBoxIcon.Error);
                lblMessage.Text = "";
                return;
            }
            if (tra.PaymentTransactions == null)
            {
                MessageBox.Show("No transactions found between the dates provided", "PP:Konnect", MessageBoxButtons.OK, MessageBoxIcon.Error);
                lblMessage.Text = "";
            }
            else
            {
                int j = 0;
                btnAssignTransactions.Enabled = true;
                for (int i = 0; i < tra.PaymentTransactions.Length; i++)
                {
                    if (tra.PaymentTransactions[i].Status.ToString() == "Completed")
                    {
                        j += 1;
                        string timeStamp = "";
                        if (tra.PaymentTransactions[i].Timestamp != null)
                            timeStamp = tra.PaymentTransactions[i].Timestamp.ToString();

                        ListViewItem item3 = new ListViewItem(timeStamp);
                        item3.Checked = true;
                        item3.Tag = tra.PaymentTransactions[i].TransactionID;
                        if (tra.PaymentTransactions[i].Status != null)
                            item3.SubItems.Add(tra.PaymentTransactions[i].Status);
                        else
                            item3.SubItems.Add("");
                        if (tra.PaymentTransactions[i].PayerDisplayName != null)
                            item3.SubItems.Add(tra.PaymentTransactions[i].PayerDisplayName);
                        else
                            item3.SubItems.Add("");

                        if (tra.PaymentTransactions[i].GrossAmount != null)
                            item3.SubItems.Add(tra.PaymentTransactions[i].GrossAmount.currencyID + " " + tra.PaymentTransactions[i].GrossAmount.Value);
                        else
                            item3.SubItems.Add("");

                        lstTransactions.Items.AddRange(new ListViewItem[] { item3 });
                        lblMessage.Text = " Results:" + j.ToString();
                        Application.DoEvents();
                    }
                }

            }

            // Perform the sort with these new sort options.
            this.lstTransactions.Sort();
        }

        #endregion

        #region IMPORTING INTO KASHFLOW

        private void btnAssignTransactions_Click(object sender, EventArgs e)
        {

            ProgramOptions objProgramOptions = new ProgramOptions();
            objProgramOptions.LoadCustomerSettings();
            if (PayPalConstants.KASH_API_USERNAME == "" || PayPalConstants.KASH_API_PASSWORD == "")
            {
                lblMessage.Text = "Please enter your KashFlow credentials";
                return;
            }
            if (!objProgramOptions.AllCustomers && objProgramOptions.CustomerName.Trim() == "")
            {
                lblMessage.Text = "Please select a customer name first using \"Program Options\"";
                return;
            }
            if (objProgramOptions.BankAccountID.Trim() == "")
            {
                lblMessage.Text = "Please select a transaction bank account using \"Program Options\"";
                return;
            }
            /*if (objProgramOptions.PaypalBankAccountID.Trim() == "")
            {
                lblMessage.Text = "Please select a PayPal bank account using \"Program Options\"";
                return;
            }*/
            if (objProgramOptions.BankTransactionTypeID == 0)
            {
                lblMessage.Text = "Please select a PayPal bank transaction type using \"Program Options\"";
                return;
            }

            PayPalAPI objApi = new PayPalAPI();
            foreach (ListViewItem itm in lstTransactions.Items)
            {
                #region INSERT ITEMS
                if (!itm.Checked)
                    continue;

                lblMessage.Text = "Obtaining transaction " + itm.Tag.ToString().Trim() + " details from PayPal";
                Application.DoEvents();

                GetTransactionDetailsResponseType resType = objApi.GetTransactionDetails(itm.Tag.ToString().Trim());
                if (resType.Errors != null)
                {
                    lblMessage.Text = resType.Errors[0].LongMessage;
                    Application.DoEvents();
                    System.Threading.Thread.Sleep(1000);
                    continue;
                }

                //invoice line settings goes here
                lblMessage.Text = "Inserting transaction " + itm.Tag.ToString().Trim();
                Application.DoEvents();

                InvoiceLine invLine = new InvoiceLine();

                invLine.Quantity = 1;
                try
                {
                    invLine.Description = resType.PaymentTransactionDetails.PaymentItemInfo.PaymentItem[0].Name;
                }
                catch (Exception ex) { Console.WriteLine(ex.Message); }


                string note = resType.PaymentTransactionDetails.PayerInfo.PayerName.FirstName + " " + resType.PaymentTransactionDetails.PayerInfo.PayerName.LastName + "\n";
                note += resType.PaymentTransactionDetails.PayerInfo.PayerBusiness + "\n";
                note += resType.PaymentTransactionDetails.PayerInfo.Address.StateOrProvince + "\n";
                note += resType.PaymentTransactionDetails.PayerInfo.PayerCountry + "\n";

                //invLine.Description = note;

                decimal grossAmount = 0.00M;
                //decimal VATAmount = 0.00M;
                try
                {
                    grossAmount = Convert.ToDecimal(resType.PaymentTransactionDetails.PaymentInfo.GrossAmount.Value);
                }
                catch { }

                //if (resType.PaymentTransactionDetails.PaymentInfo.TaxAmount != null)
                    //VATAmount = Convert.ToDecimal(resType.PaymentTransactionDetails.PaymentInfo.TaxAmount.Value);

                //If user is VAT registered
                if (KashAPI.isUserVATRegistered() == true)
                {
                    //Calculate netAmount ourselves
                        //Calculate net amount based on gross amount using VAT rate
                    decimal netAmount = grossAmount;
                    decimal vatDivision = 0M;
                        //divided by 1.175

                    if (objProgramOptions.VATRate != 0)
                        {
                            vatDivision = (objProgramOptions.VATRate / 100) + 1;
                            netAmount = grossAmount / vatDivision;
                        }

                        
                        invLine.Rate = netAmount;
                        //Setting the VATRate will calculate VAT server side based on netAmount
                        invLine.VatRate = objProgramOptions.VATRate;
                }
                else
                {
                    //User is not VAT regsitered, combine total and VAT amount.  Set VAT rate to zero
                    invLine.Rate = grossAmount;
                    invLine.VatAmount = 0M;
                    invLine.VatRate = 0M;
                }

                //Removed as the ChargeType option is now set in the Program Options
                //invLine.ChargeType = 0;
                invLine.ChargeType = objProgramOptions.ProductID;

                //invLine.VatRate = Convert.ToDecimal(resType.PaymentTransactionDetails.PaymentInfo.TaxAmount);

                Invoice invoice = new Invoice();

                invoice.Lines = new object[1];
                invoice.Lines.SetValue(invLine, 0);
                //set invoice id
                // string inv = resType.PaymentTransactionDetails.PaymentInfo.TransactionID;
                invoice.InvoiceNumber = 0;
                KashFlowAPI kash = new KashFlowAPI();
                //check if transactions to be assigned to individual customer rather than single
                if (objProgramOptions.AllCustomers)
                {
                    string strStatus = "";
                    string strStatusDetail = "";
                    #region INDV CUSTOMER
                    //check if customer exists
                    Customer c = kash.GetCustomerByEmail(PayPalConstants.KASH_API_USERNAME, PayPalConstants.KASH_API_PASSWORD, resType.PaymentTransactionDetails.PayerInfo.Payer, out   strStatus, out   strStatusDetail);
                    if (strStatus == "OK" && c != null)
                    {
                        invoice.CustomerID = c.CustomerID;
                    }
                    else
                    {
                        //create a new customer in KashFlow
                        Customer cc = new Customer();
                        if (resType.PaymentTransactionDetails.PaymentInfo.TransactionID.Length > 12)
                            cc.Code = itm.Tag.ToString().Trim().Substring(0, 11);
                        else
                            cc.Code = itm.Tag.ToString().Trim();

                        cc.Name = resType.PaymentTransactionDetails.PayerInfo.PayerName.FirstName + " " + resType.PaymentTransactionDetails.PayerInfo.PayerName.LastName;
                        cc.Contact = resType.PaymentTransactionDetails.PayerInfo.PayerName.FirstName + " " + resType.PaymentTransactionDetails.PayerInfo.PayerName.LastName;
                        cc.Telephone = resType.PaymentTransactionDetails.PayerInfo.ContactPhone;
                        cc.Email = resType.PaymentTransactionDetails.PayerInfo.Payer;
                        cc.Address1 = resType.PaymentTransactionDetails.PayerInfo.Address.Street1;
                        cc.Address2 = resType.PaymentTransactionDetails.PayerInfo.Address.Street2;
                        cc.Address3 = resType.PaymentTransactionDetails.PayerInfo.Address.CityName;
                        cc.Address4 = resType.PaymentTransactionDetails.PayerInfo.Address.StateOrProvince;
                        cc.Postcode = resType.PaymentTransactionDetails.PayerInfo.Address.PostalCode;
                        cc.Notes = "Created by PPKonnect";
                        //insert new customer here
                        int cusid = kash.InsertCustomer(PayPalConstants.KASH_API_USERNAME, PayPalConstants.KASH_API_PASSWORD, cc, out   strStatus, out   strStatusDetail);
                        if (strStatus != "OK")
                        {
                            lblMessage.Text = "Customer can not be inserted." + strStatusDetail;
                            if (lblMessage.Text.EndsWith("access list"))
                                lnkAccesslist.Visible = true;
                            else
                                lnkAccesslist.Visible = false;
                            Application.DoEvents();
                            return;
                        }
                        invoice.CustomerID = cusid;

                    }
                    #endregion
                }
                else
                {
                    invoice.CustomerID = Convert.ToInt32(objProgramOptions.CustomerName.Trim());
                }
                //PayPal transaction date goes here
                //
                invoice.InvoiceDate = resType.PaymentTransactionDetails.PaymentInfo.PaymentDate;  // resType.Timestamp;
                invoice.DueDate = resType.PaymentTransactionDetails.PaymentInfo.PaymentDate;  // resType.Timestamp;


                string strStatus1 = "";
                string strStatusDetail1 = "";
                int newInvoiceNo = kash.InsertInvoice(PayPalConstants.KASH_API_USERNAME, PayPalConstants.KASH_API_PASSWORD, invoice, out   strStatus1, out   strStatusDetail1);
                if (strStatus1 == "OK")
                {
                    //kash.InsertInvoicePayment(
                    //now insert payment in newly created invoice
                    Payment objPayment = new Payment();
                    objPayment.PayAccount = Convert.ToInt32(objProgramOptions.BankAccountID.Trim());
                    objPayment.PayAmount = Convert.ToDecimal(resType.PaymentTransactionDetails.PaymentInfo.GrossAmount.Value);
                    objPayment.PayDate = resType.PaymentTransactionDetails.PaymentInfo.PaymentDate; //resType.Timestamp;
                    // objPayment.PayID = "";
                    objPayment.PayInvoice = newInvoiceNo;
                    objPayment.PayMethod = 8;
                    objPayment.PayNote = note;
                    int res = kash.InsertInvoicePayment(PayPalConstants.KASH_API_USERNAME, PayPalConstants.KASH_API_PASSWORD, objPayment, out   strStatus1, out   strStatusDetail1);
                    if (strStatus1 == "OK")
                    {
                        lblMessage.Text = "Tranasaction has been inserted" + res;
                        Application.DoEvents();
                    }


                }

                //Insert bank charge for paypal transaction
                if (resType.PaymentTransactionDetails.PaymentInfo.FeeAmount != null)
                {
                    BankTransaction banktrans = new BankTransaction();
                    banktrans.TransactionType = objProgramOptions.BankTransactionTypeID;
                    banktrans.accid = int.Parse(objProgramOptions.BankAccountID);
                    banktrans.TransactionDate = resType.PaymentTransactionDetails.PaymentInfo.PaymentDate;  //resType.Timestamp;
                    banktrans.Comment = "PayPal Fee";

                    banktrans.moneyout = decimal.Parse(resType.PaymentTransactionDetails.PaymentInfo.FeeAmount.Value);

                    int res = kash.InsertBankTransaction(PayPalConstants.KASH_API_USERNAME, PayPalConstants.KASH_API_PASSWORD, banktrans, out   strStatus1, out   strStatusDetail1);
                    if (strStatus1 == "OK")
                    {
                        lblMessage.Text = "PayPal fee has been inserted" + res;
                        Application.DoEvents();
                    }

                }
                #endregion
            }
            lblMessage.Text = "Import Complete";

        }

        #endregion

        #region LISTVIEW TRIGGERS

        private void lstTransactions_DoubleClick(object sender, EventArgs e)
        {
            foreach (ListViewItem itm in lstTransactions.Items)
            {

                if (itm.Selected)
                {
                    frmSearchDetailView fDv = new frmSearchDetailView();
                    frmSearchDetailView._strTransactionID = itm.Tag.ToString();
                    fDv.ShowDialog();
                    break;
                }
            }
        }

        #region DOUBLE CLICK CHECK BLOCK
        /// <summary>
        /// Blocks ItemCheck event when DoubleClick in used a ListView
        /// </summary>
        private bool blItemCheckBlocking = false;
        private void lstTransactions_MouseDown(object sender, System.Windows.Forms.MouseEventArgs e)
        {
            if (e.Button == MouseButtons.Left)
            {
                if (e.Clicks >= 2)
                {
                    //double click
                    blItemCheckBlocking = true;
                }

            }
        }

        private void lstTransactions_ItemCheck(object sender, System.Windows.Forms.ItemCheckEventArgs e)
        {
            if (blItemCheckBlocking)
            { // Handle itemcheck clicking
                e.NewValue = e.CurrentValue;
                blItemCheckBlocking = !blItemCheckBlocking;
                return;
            }
        }
        #endregion

        private void lstTransactions_ColumnClick(object sender, ColumnClickEventArgs e)
        {
            // Determine if clicked column is already the column that is being sorted.
            if (e.Column == lvwColumnSorter.SortColumn)
            {
                // Reverse the current sort direction for this column.
                if (lvwColumnSorter.Order == SortOrder.Ascending)
                {
                    lvwColumnSorter.Order = SortOrder.Descending;
                }
                else
                {
                    lvwColumnSorter.Order = SortOrder.Ascending;
                }
            }
            else
            {
                // Set the column number that is to be sorted; default to ascending.
                lvwColumnSorter.SortColumn = e.Column;
                lvwColumnSorter.Order = SortOrder.Ascending;
            }

            // Perform the sort with these new sort options.
            this.lstTransactions.Sort();
        }

        #endregion

        private void btnExit_Click(object sender, EventArgs e)
        {
            Application.Exit();
        }

        private void lnkAccesslist_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            System.Diagnostics.Process.Start("http://api.kashflow.co.uk/enableAPI.asp?highlight=4");
        }

        private void cmbWithin_SelectedIndexChanged(object sender, EventArgs e)
        {
            this.radWithin.Checked = true;
        }

        private void dtpStartDate_ValueChanged(object sender, EventArgs e)
        {
            this.radFrom.Checked = true;
        }

        private void dtpEndDate_ValueChanged(object sender, EventArgs e)
        {
            this.radFrom.Checked = true;
        }

    }
}