<b>Auto Loan Calculator<b> body { background: #f7f7f7; font-family: 'Segoe UI', Arial, sans-serif; margin: 0; color: #222; } h1 { font-size: 2.2rem; text-align: center; margin-top: 32px; margin-bottom: 18px; font-weight: 400; } .calc-container { background: #fff; max-width: 900px; margin: 0 auto 30px auto; border-radius: 10px; box-shadow: 0 2px 12px rgba(0,0,0,0.08); padding: 24px 24px 12px 24px; } .form-row { display: flex; flex-wrap: wrap; gap: 18px 24px; margin-bottom: 18px; justify-content: space-between; } .form-group { flex: 1 1 180px; min-width: 180px; } .form-group label { display: block; font-size: 1rem; margin-bottom: 5px; font-weight: 500; } .form-group input[type="number"], .form-group input[type="date"] { width: 100%; padding: 7px 10px; font-size: 1rem; border: 1.5px solid #c4c4c4; border-radius: 5px; background: #f8f8f8; transition: border-color 0.2s; } .form-group input[type="number"]:focus, .form-group input[type="date"]:focus { border-color: #007bff; outline: none; } .form-group.inline { display: flex; align-items: center; } .form-group.inline label { margin-right: 6px; margin-bottom: 0; } .form-group.inline input { width: 60px; margin-right: 6px; } .form-actions { display: flex; align-items: flex-end; justify-content: flex-end; } .form-actions button { padding: 10px 32px; background: #1976d2; color: #fff; font-size: 1.1rem; font-weight: 600; border: none; border-radius: 5px; cursor: pointer; margin-top: 10px; transition: background 0.2s; } .form-actions button:hover { background: #1259a7; } .summary-row { display: flex; justify-content: space-between; align-items: flex-end; margin: 22px 0 10px 0; flex-wrap: wrap; gap: 18px 0; } .monthly-payment { width: 100%; text-align: center; font-size: 2rem; font-weight: 600; color: #1976d2; margin-bottom: 2px; } .summary-boxes { display: flex; justify-content: space-between; gap: 10px; width: 100%; margin: 0 auto; flex-wrap: wrap; } .summary-box { flex: 1 1 160px; background: #f3f7fb; border-radius: 7px; padding: 12px 10px 8px 10px; text-align: center; margin: 0 2px; min-width: 130px; } .summary-box .label { font-size: 0.98rem; color: #888; margin-bottom: 2px; display: block; } .summary-box .value { font-size: 1.1rem; font-weight: 600; color: #222; } .chart-section { background: #fff; border-radius: 10px; margin: 18px auto 0 auto; padding: 20px 14px 10px 14px; max-width: 900px; box-shadow: 0 2px 8px rgba(0,0,0,0.06); } .tabs { display: flex; margin-bottom: 0; border-bottom: 2px solid #e3e3e3; margin-top: 18px; } .tab-btn { padding: 10px 22px; background: #e3e3e3; border: none; border-radius: 7px 7px 0 0; font-weight: 500; font-size: 1.02rem; cursor: pointer; margin-right: 6px; transition: background 0.2s; } .tab-btn.active { background: #1976d2; color: #fff; } .amort-table { width: 100%; border-collapse: collapse; margin-top: 0; font-size: 0.98rem; background: #fff; } .amort-table th, .amort-table td { border: 1px solid #e3e3e3; padding: 7px 10px; text-align: right; } .amort-table th { background: #f3f7fb; color: #1976d2; font-weight: 600; } .amort-table td:first-child, .amort-table th:first-child { text-align: left; } .amort-table tfoot td { font-weight: bold; background: #f8f8f8; color: #1976d2; } @media (max-width: 900px) { .calc-container, .chart-section { max-width: 98vw; padding: 10px 2vw 10px 2vw; } .summary-row, .summary-boxes { flex-direction: column; align-items: stretch; } .summary-box { margin-bottom: 8px; } }

Auto Loan Calculator

%
%
Mo
Loan Amount
Over Payments
Total Interest
Pay-off Date
Amortization Schedule
function formatCurrency(n) { return n.toLocaleString('en-US', {style: 'currency', currency: 'USD', minimumFractionDigits: 2}); } function formatDate(date) { return date.toLocaleDateString('en-US', {year: 'numeric', month: 'short'}); } function formatFullDate(date) { return date.toLocaleDateString('en-US', {year: 'numeric', month: 'short', day: '2-digit'}); } function getPayoffDate(startDate, months) { let d = new Date(startDate); d.setMonth(d.getMonth() + months - 1); return formatDate(d); } function getPayoffFullDate(startDate, months) { let d = new Date(startDate); d.setMonth(d.getMonth() + months - 1); return formatFullDate(d); } function calcLoanAmount(vehiclePrice, downPayment, tradeIn, owedOnTrade, salesTax) { // Loan Amount = (Vehicle Price - Down Payment - Trade-In + Owed on Trade) * (1 + Sales Tax Rate) let base = vehiclePrice - downPayment - tradeIn + owedOnTrade; let tax = base * (salesTax / 100); return base + tax; } function calcMonthlyPayment(P, annualRate, n) { let r = annualRate / 100 / 12; if (r === 0) return P / n; return P * r / (1 - Math.pow(1 + r, -n)); } function buildAmortization(P, annualRate, n, startDate) { let r = annualRate / 100 / 12; let payment = calcMonthlyPayment(P, annualRate, n); let schedule = []; let balance = P; let date = new Date(startDate); for (let i = 1; i <= n; i++) { let interest = balance * r; let principal = payment - interest; if (balance < principal) principal = balance; balance -= principal; if (balance { let y = row.date.getFullYear(); if (!years[y]) years[y] = {principal: 0, interest: 0, payment: 0, balance: row.balance, lastDate: row.date}; years[y].principal += row.principal; years[y].interest += row.interest; years[y].payment += row.payment; years[y].balance = row.balance; years[y].lastDate = row.date; }); let result = []; let i = 1; for (let y in years) { result.push({ year: y, principal: years[y].principal, interest: years[y].interest, totalPaid: years[y].payment, balance: years[y].balance, lastDate: years[y].lastDate }); i++; } return result; } function renderTable(schedule, type) { let html = ''; if (type === 'year') { html += ``; let totalPrincipal = 0, totalInterest = 0, totalPaid = 0; schedule.forEach(row => { totalPrincipal += row.principal; totalInterest += row.interest; totalPaid += row.totalPaid; html += ``; }); html += ``; } else { html += ``; let totalPrincipal = 0, totalInterest = 0, totalPaid = 0; schedule.forEach(row => { totalPrincipal += row.principal; totalInterest += row.interest; totalPaid += row.payment; html += ``; }); html += ``; } html += '
YearPrincipalInterestTotal PaidBalance
${row.year} ${formatCurrency(row.principal)} ${formatCurrency(row.interest)} ${formatCurrency(row.totalPaid)} ${formatCurrency(row.balance)}
Totals ${formatCurrency(totalPrincipal)} ${formatCurrency(totalInterest)} ${formatCurrency(totalPaid)}
#DatePrincipalInterestPaymentBalance
${row.paymentNum} ${formatFullDate(row.date)} ${formatCurrency(row.principal)} ${formatCurrency(row.interest)} ${formatCurrency(row.payment)} ${formatCurrency(row.balance)}
Totals ${formatCurrency(totalPrincipal)} ${formatCurrency(totalInterest)} ${formatCurrency(totalPaid)}
'; document.getElementById('amortTableWrap').innerHTML = html; } // Chart let loanChart; function renderChart(yearly) { let ctx = document.getElementById('loanChart').getContext('2d'); let labels = yearly.map(row => row.year); let principalData = yearly.map(row => row.principal); let interestData = yearly.map(row => row.interest); let balanceData = yearly.map(row => row.balance); if (loanChart) loanChart.destroy(); loanChart = new Chart(ctx, { type: 'bar', data: { labels: labels, datasets: [ { label: 'Principal', type: 'bar', data: principalData, backgroundColor: '#1976d2', stack: 'stack1' // ...bar options }, { label: 'Interest', type: 'bar', data: interestData, backgroundColor: '#ff9800', stack: 'stack1' // ...bar options }, { label: 'End Balance', data: balanceData, backgroundColor: '#bdbdbd', type: 'line', borderColor: '#222', borderWidth: 2, fill: false, pointRadius: 4, yAxisID: 'y1' // ...line options } ] }, options: { plugins: { legend: {display: true, position: 'top'}, tooltip: {mode: 'index', intersect: false} }, responsive: true, scales: { x: {stacked: true}, y: { stacked: true, title: {display: true, text: 'Amount ($)'}, beginAtZero: true }, y1: { position: 'right', grid: {drawOnChartArea: false}, title: {display: true, text: 'Balance ($)'}, beginAtZero: true } } } }); } // Main calculation function calcAndRender() { let vehiclePrice = parseFloat(document.getElementById('vehiclePrice').value) || 0; let downPayment = parseFloat(document.getElementById('downPayment').value) || 0; let tradeIn = parseFloat(document.getElementById('tradeIn').value) || 0; let owedOnTrade = parseFloat(document.getElementById('owedOnTrade').value) || 0; let interestRate = parseFloat(document.getElementById('interestRate').value) || 0; let salesTax = parseFloat(document.getElementById('salesTax').value) || 0; let term = parseInt(document.getElementById('term').value) || 1; let startDate = document.getElementById('startDate').value; if (!startDate) startDate = new Date().toISOString().slice(0,10); let loanAmount = calcLoanAmount(vehiclePrice, downPayment, tradeIn, owedOnTrade, salesTax); let monthlyPayment = calcMonthlyPayment(loanAmount, interestRate, term); let totalPaid = monthlyPayment * term; let totalInterest = totalPaid - loanAmount; let payoffDate = getPayoffDate(startDate, term); document.getElementById('monthlyPayment').innerHTML = formatCurrency(monthlyPayment) + '
Monthly Payment
'; document.getElementById('loanAmountBox').textContent = formatCurrency(loanAmount); document.getElementById('totalPaymentsBox').textContent = term; document.getElementById('totalPaidBox').textContent = formatCurrency(totalPaid); document.getElementById('totalInterestBox').textContent = formatCurrency(totalInterest); document.getElementById('payoffDateBox').textContent = payoffDate; let schedule = buildAmortization(loanAmount, interestRate, term, startDate); let yearly = buildYearlyAmortization(schedule); renderChart(yearly); renderTable(yearly, 'year'); // Tab switching document.getElementById('yearTab').onclick = function() { this.classList.add('active'); document.getElementById('monthTab').classList.remove('active'); renderTable(yearly, 'year'); }; document.getElementById('monthTab').onclick = function() { this.classList.add('active'); document.getElementById('yearTab').classList.remove('active'); renderTable(schedule, 'month'); }; } document.getElementById('loanForm').onsubmit = function(e) { e.preventDefault(); calcAndRender(); }; // Set start date to today by default window.onload = function() { let today = new Date(); let yyyy = today.getFullYear(); let mm = String(today.getMonth() + 1).padStart(2, '0'); let dd = String(today.getDate()).padStart(2, '0'); document.getElementById('startDate').value = yyyy + '-' + mm + '-' + dd; calcAndRender(); };