# Affordability calculator

Estimate how much you can borrow from your income, existing debt payments and the debt-to-income limit a lender is likely to apply.

/**
 * Calculator maths for costreference.com.
 *
 * Plain functions on `window.CRCALC`. This file is the single source of the maths: it is
 * served to the browser as the calculator bundle and it is the file the Node test
 * (scripts/test-tool-math.mjs) imports. The tests therefore exercise exactly the code users run.
 *
 * Every function validates its inputs and returns NaN rather than throwing, so a bad input
 * produces an error message instead of a broken page.
 */
(function (root) {
  "use strict";

  function isNum(v) { return typeof v === "number" && Number.isFinite(v); }

  /** Standard amortising payment. i = monthly rate, n = months. */
  function monthlyPayment(principal, annualRatePct, months) {
    if (!isNum(principal) || !isNum(annualRatePct) || !isNum(months)) return NaN;
    if (principal  balance) princ = balance;
      if (princ  1e-9) cheaper = a  0
        ? Math.abs(a - b) / Math.max(a, b) * 100 : 0 };
  }

  /** Months to clear a balance at a fixed payment, plus the effect of paying more. */
  function payoffMonths(balance, annualRatePct, payment) {
    if (!isNum(balance) || !isNum(annualRatePct) || !isNum(payment)) return null;
    if (balance

      Gross annual income (USD)

      Other monthly debt payments (USD)

      Expected annual rate (%)

      Term (months)

      Debt-to-income limit (%)

  Estimate borrowing capacity

The estimate applies a debt-to-income limit to gross monthly income, subtracts
your existing monthly debt payments, and converts the remaining payment into a loan amount using
the standard amortisation formula. Lenders apply their own limits — 36% is a common benchmark,
some allow more and many allow less — and they also weigh credit history, employment and
property. Treat the result as a ceiling to test against quotes, not an approval.

(function () {
  var C = window.CRCALC;
  function $(id) { return document.getElementById(id); }
  function num(id) { var el = $(id); if (!el) return NaN; var v = el.value === "" ? NaN : Number(el.value); return Number.isFinite(v) ? v : NaN; }
  function money(n) { return "$" + n.toLocaleString("en-US", { minimumFractionDigits: 0, maximumFractionDigits: 0 }); }
  function render() {
    var income = num("af-income"), debts = num("af-debts"), rate = num("af-rate"),
        months = num("af-months"), dti = num("af-dti");
    var err = $("af-err"), out = $("af-out");
    err.hidden = true;
    if (!Number.isFinite(income) || income  100) { err.hidden = false; err.textContent = "Enter an annual rate between 0 and 100."; out.innerHTML = ""; return; }
    if (!Number.isFinite(months) || months  600) { err.hidden = false; err.textContent = "Enter a term between 1 and 600 months."; out.innerHTML = ""; return; }
    if (!Number.isFinite(dti) || dti  60) { err.hidden = false; err.textContent = "Enter a debt-to-income limit between 1 and 60."; out.innerHTML = ""; return; }
    var r = C.affordableLoan(income, debts, rate, months, dti / 100);
    if (!r) { err.hidden = false; err.textContent = "Those inputs cannot be calculated."; out.innerHTML = ""; return; }
    if (!r.affordable) {
      out.innerHTML = "" + money(r.maxPayment) + " available per month

" +
        "Your existing debt payments already meet or exceed a " + dti + "% debt-to-income limit on this income, so there is no room for another instalment payment at that limit. Paying down existing balances raises the ceiling.

";
      return;
    }
    var totalInterest = C.monthlyPayment(r.principal, rate, months) * months - r.principal;
    out.innerHTML = "" + money(r.principal) + " estimated maximum

" +
      "That is a monthly payment of " + money(r.maxPayment) + " at " + rate + "% over " + months + " months, and about " + money(totalInterest) + " of interest across the term.

" +
      "How the estimate is builtStepAmount

" +
      "Gross monthly income" + money(income / 12) + "

" +
      "Maximum total debt payment at " + dti + "% DTI" + money(income / 12 * dti / 100) + "

" +
      "Less existing monthly debts" + money(debts) + "

" +
      "Payment available for a new loan" + money(r.maxPayment) + "

" +
      "Loan amount that payment supports" + money(r.principal) + "

" +
      "

";
  }
  window.__crRender = render;
  $("af-go").addEventListener("click", render);
  ["af-income", "af-debts", "af-rate", "af-months", "af-dti"].forEach(function (id) { $(id).addEventListener("input", render); });
  render();
})();

Source: https://costreference.com/tools/affordability-calculator/
