/*
*  Finance Calculator with Adjustable APR
*
* Author: Marlon King <marlon.king@gforces.co.uk>
*
* Notes: For use without APR being adjustable, pass in a fixed interest rate
*/



function updateResultsFromApr( price, rate, adjustableApr ){
    //reset values before starting
    var totalPrice          = price; //passed in from php page
    var deposit             = 0;     //selectable
    var loanPeriod          = 0;     //selectable in years
    var monthlyPayments     = 0;
    var creditAmount        = 0;
    var interestPayable     = 0;
    var totalAmountPayable  = 0;
    var apr                 = 0;
    var totalNumberOfMonths = 0;
    var interestRate        = rate;  //ie 12.2


    //retrieve inputed values

    deposit             = parseInt( $('input_deposit').value );
    loanPeriod          = parseInt( $('input_loanPeriod').value );
    apr_selected        = parseFloat( $('input_apr').value )/100;

    if ( deposit > 0 && loanPeriod > 0 ) {

        //calculate all
        creditAmount        = (totalPrice - deposit);
        creditAmountIni     = (totalPrice - deposit); //without 165 added
        totalNumberOfMonths = loanPeriod * 12;
        interestRate        = interestRate / 100;
        monthlyPayments     = creditAmount / totalNumberOfMonths;


        //creditAmount = creditAmount + 165;

        interestPayable      = ( creditAmount * interestRate) * loanPeriod ;
        totalAmountPayable   = ( creditAmount + interestPayable );
        monthlyPayments      = ( totalAmountPayable / totalNumberOfMonths );

        apr = calculateAPR( creditAmountIni, totalNumberOfMonths, monthlyPayments );

        interestPayable    = ((monthlyPayments * totalNumberOfMonths)) - creditAmountIni;
        totalAmountPayable = ((monthlyPayments * totalNumberOfMonths) + (deposit));



        //display results
        //$('totalPrice').innerHTML         = '<strong>£' + addCommas(Math.round(totalPrice * 100 ) / 100 ) + '</strong>';
        $('creditAmount').innerHTML       = '£' + addCommas(Math.round(creditAmountIni * 100 ) / 100 );
        $('interestPayable').innerHTML    = '£' + addCommas(Math.round( interestPayable  * 100 ) / 100 );
        $('monthlyPayments').innerHTML    = '£' + addCommas(Math.round( monthlyPayments * 100 ) / 100 );
        $('totalAmountPayable').innerHTML = '£' + addCommas(Math.round( totalAmountPayable * 100 ) / 100);

        if ( adjustableApr == true ){

            apr = reverseCalculateAPR( creditAmountIni, totalNumberOfMonths, totalAmountPayable, apr_selected, deposit );

        }else{

            $('apr').innerHTML                =  Math.round( parseFloat( apr ) * 10 ) / 10 + '%';
        }

    }else if ( deposit >= 0 ){

        creditAmount        = (totalPrice - deposit);
        $('creditAmount').innerHTML       = '£' + addCommas(Math.round( creditAmount * 100 ) / 100);

    }
}


function calculateLoanFromAPR( apr, totalNumberOfMonths, monthlyPayments ) {

    var loan = 0;

    for( time = 1; time <= totalNumberOfMonths; time++ ) {

        payment = monthlyPayments;

        //payment += ( time == totalNumberOfMonths ) ? 45 : 0;//final sum added on to final payment - REMOVE AS NECESSARY

        interest = ( payment / ( Math.pow( 1 + apr, time / 12 ) ) );

        loan +=interest;

        //alert('debug ' + time + ' - loan: ' + loan + ', payment: ' + payment + ', period: ' + time  + ' PV: ' + interest );
    }

    return loan;

}



function calculateAPR( creditAmount, totalNumberOfMonths, monthlyPayments ) {

    //alert( creditAmount + ' - ' + totalNumberOfMonths + ' - ' + monthlyPayments );

    minApr = 0;
    minAprCalculatedLoan = calculateLoanFromAPR( minApr, totalNumberOfMonths, monthlyPayments );
    maxApr = 1;
    maxAprCalculatedLoan = calculateLoanFromAPR( maxApr, totalNumberOfMonths, monthlyPayments );

    time_to_live = 200;

    target_amount = creditAmount;

    do {
        midApr = ( ( maxApr - minApr ) / 2 ) + minApr;
        midAprCalculatedLoan = calculateLoanFromAPR( midApr, totalNumberOfMonths, monthlyPayments );

        if( target_amount < midAprCalculatedLoan ) {

            minApr = midApr;

        } else if( target_amount > midAprCalculatedLoan ) {

            maxApr = midApr;
        }

        difference = Math.abs(midAprCalculatedLoan - target_amount);

        //alert('debug - apr: ' + midApr + ', ' + midAprCalculatedLoan + ' < ' + target_amount + ', loan difference: ' + difference + ', loan: ' + creditAmount );

    } while ( (midAprCalculatedLoan < target_amount || difference > 0.001) && time_to_live-- > 0 );

    if( time_to_live < 0 ) {

        return "NAN";

    } else {

        return midApr * 100;

    }

}

//change the month payment
function reverseCalculateAPR( creditAmount, totalNumberOfMonths, monthlyPayments, newApr, deposit ) {

    var loan   = 0;
    //var adjust = 0;

    payment = creditAmount/totalNumberOfMonths;

    for( time = 1; time <= totalNumberOfMonths; time++ ) {

        interest = ( payment * ( Math.pow( 1 + newApr, time / 12 ) ) );


        loan +=interest;
        //alert ( "interest: " +  interest );
        //adjust += ( time / 12 );
    }

    //alert ( 'Adjust: ' + adjust );

    //alert ('loan2: ' + loan);
    //alert ('monthly payment' + ( loan / (totalNumberOfMonths )) );


    monthlyPayments        = ( loan / ( totalNumberOfMonths ) );
    loan                   = monthlyPayments * totalNumberOfMonths;
    var newInterest        = loan - creditAmount;
    var totalAmountPayable = ( loan + deposit);

    //display results
    $('interestPayable').innerHTML    = '£' + addCommas(Math.round( newInterest  * 100 ) / 100 );
    $('monthlyPayments').innerHTML    = '£' + addCommas(Math.round( monthlyPayments * 100 ) / 100 );
    $('totalAmountPayable').innerHTML = '£' + addCommas(Math.round( totalAmountPayable * 100 ) / 100);
    // $('apr').innerHTML                =  Math.round( parseFloat( (newApr*100)) * 10 ) / 10 + '%';


}




function addCommas(nStr)
{
    nStr += '';
    x = nStr.split('.');
    x1 = x[0];
    if ( x.length > 1 ){
        theDec = x[1];
        theDec = ( theDec.length == 1 )? x[1] + '0' : theDec;
        x2 = '.' + theDec;
    }else{
        x2 = '';
    }
    var rgx = /(\d+)(\d{3})/;
    while (rgx.test(x1)) {
        x1 = x1.replace(rgx, '$1' + ',' + '$2');
    }
    return x1 + x2;
}