Irr Calculation Formula Excel

IRR Calculation Formula Excel: Master Internal Rate of Return :root { –primary-color: #004a99; –success-color: #28a745; –background-color: #f8f9fa; –text-color: #333; –border-color: #ddd; –card-background: #fff; –shadow: 0 2px 5px rgba(0,0,0,0.1); } body { font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif; background-color: var(–background-color); color: var(–text-color); line-height: 1.6; margin: 0; padding: 0; } .container { max-width: 960px; margin: 20px auto; padding: 20px; background-color: var(–card-background); border-radius: 8px; box-shadow: var(–shadow); } h1, h2, h3 { color: var(–primary-color); margin-bottom: 1em; } h1 { text-align: center; font-size: 2.5em; } h2 { font-size: 1.8em; border-bottom: 2px solid var(–primary-color); padding-bottom: 0.3em; } h3 { font-size: 1.4em; margin-top: 1.5em; } .calculator-wrapper { background-color: var(–card-background); padding: 30px; border-radius: 8px; box-shadow: var(–shadow); margin-bottom: 40px; } .calculator-wrapper h2 { margin-top: 0; text-align: center; border-bottom: none; margin-bottom: 1.5em; } .input-group { margin-bottom: 20px; text-align: left; } .input-group label { display: block; margin-bottom: 8px; font-weight: bold; color: var(–primary-color); } .input-group input[type="number"], .input-group input[type="text"], .input-group select { width: calc(100% – 22px); padding: 10px; border: 1px solid var(–border-color); border-radius: 4px; font-size: 1em; box-sizing: border-box; } .input-group input[type="number"]:focus, .input-group input[type="text"]:focus, .input-group select:focus { outline: none; border-color: var(–primary-color); box-shadow: 0 0 0 2px rgba(0, 74, 153, 0.2); } .input-group .helper-text { font-size: 0.85em; color: #666; margin-top: 5px; display: block; } .error-message { color: #dc3545; font-size: 0.85em; margin-top: 5px; display: none; /* Hidden by default */ } .error-message.visible { display: block; } .button-group { display: flex; justify-content: space-between; margin-top: 30px; gap: 10px; } .button-group button { padding: 12px 20px; border: none; border-radius: 4px; cursor: pointer; font-size: 1em; font-weight: bold; transition: background-color 0.3s ease; flex: 1; } .btn-calculate { background-color: var(–primary-color); color: white; } .btn-calculate:hover { background-color: #003366; } .btn-reset { background-color: #6c757d; color: white; } .btn-reset:hover { background-color: #5a6268; } .btn-copy { background-color: var(–success-color); color: white; margin-top: 10px; width: 100%; } .btn-copy:hover { background-color: #218838; } #results { margin-top: 30px; padding: 25px; background-color: #e9ecef; border-radius: 8px; border: 1px solid #dee2e6; } #results h3 { margin-top: 0; color: var(–primary-color); text-align: center; border-bottom: 1px solid var(–border-color); padding-bottom: 0.5em; } .result-item { margin-bottom: 15px; font-size: 1.1em; } .result-item strong { color: var(–primary-color); display: inline-block; min-width: 200px; } .primary-result { font-size: 1.8em; font-weight: bold; color: var(–success-color); text-align: center; margin-top: 15px; padding: 10px; background-color: #fff; border-radius: 4px; border: 1px solid var(–success-color); } .formula-explanation { font-size: 0.95em; color: #555; margin-top: 20px; padding: 15px; background-color: #f0f0f0; border-left: 4px solid var(–primary-color); border-radius: 4px; } table { width: 100%; border-collapse: collapse; margin-top: 25px; margin-bottom: 25px; box-shadow: var(–shadow); } th, td { padding: 12px 15px; text-align: left; border: 1px solid var(–border-color); } thead { background-color: var(–primary-color); color: white; } th { font-weight: bold; } tbody tr:nth-child(even) { background-color: #f2f2f2; } caption { font-size: 1.1em; font-weight: bold; color: var(–primary-color); margin-bottom: 10px; text-align: left; } canvas { display: block; margin: 25px auto; max-width: 100%; background-color: var(–card-background); border-radius: 4px; box-shadow: var(–shadow); } .article-content { margin-top: 40px; background-color: var(–card-background); padding: 30px; border-radius: 8px; box-shadow: var(–shadow); } .article-content h2, .article-content h3 { margin-top: 2em; border-bottom: 1px solid var(–border-color); padding-bottom: 0.5em; } .article-content h2:first-of-type { margin-top: 0; } .article-content p { margin-bottom: 1.2em; } .article-content ul, .article-content ol { margin-bottom: 1.2em; padding-left: 25px; } .article-content li { margin-bottom: 0.5em; } .faq-item { margin-bottom: 1.5em; } .faq-item strong { display: block; color: var(–primary-color); margin-bottom: 0.5em; } .internal-links { margin-top: 30px; padding: 20px; background-color: #e9ecef; border-radius: 8px; border: 1px solid #dee2e6; } .internal-links h3 { margin-top: 0; text-align: center; color: var(–primary-color); border-bottom: none; } .internal-links ul { list-style: none; padding: 0; margin: 0; } .internal-links li { margin-bottom: 10px; } .internal-links a { color: var(–primary-color); text-decoration: none; font-weight: bold; } .internal-links a:hover { text-decoration: underline; } .internal-links p { font-size: 0.9em; color: #555; margin-top: 5px; } .highlight { background-color: var(–success-color); color: white; padding: 2px 5px; border-radius: 3px; font-weight: bold; } .formula-variable-table th, .formula-variable-table td { text-align: center; } .formula-variable-table td:first-child { text-align: left; font-weight: bold; } .formula-variable-table td:nth-child(2), .formula-variable-table td:nth-child(3) { font-style: italic; } .formula-variable-table td:nth-child(4) { font-weight: bold; } .chart-container { position: relative; width: 100%; height: 300px; /* Adjust as needed */ margin-top: 25px; background-color: var(–card-background); border-radius: 4px; box-shadow: var(–shadow); padding: 15px; box-sizing: border-box; } .chart-container canvas { box-shadow: none; margin: 0; padding: 0; height: 100% !important; /* Ensure canvas fills container */ } .chart-caption { font-size: 1em; font-weight: bold; color: var(–primary-color); margin-top: 10px; text-align: center; }

IRR Calculation Formula Excel: Master Internal Rate of Return

IRR Calculator

Calculate the Internal Rate of Return (IRR) for a series of cash flows. This tool helps you determine the discount rate at which the net present value (NPV) of all cash flows equals zero.

Enter the initial cost of the investment as a positive number.
Enter cash flows for each period, separated by commas. Use negative for outflows, positive for inflows.

Calculation Results

IRR (Internal Rate of Return):
NPV at 0% Discount Rate:
Number of Periods:
Sum of Cash Flows:
Formula Explanation: The Internal Rate of Return (IRR) is the discount rate that makes the Net Present Value (NPV) of a series of cash flows equal to zero. It's found by iteratively solving the equation:

NPV = Σ [CFt / (1 + IRR)^t] - Initial Investment = 0

Where: CFt is the cash flow in period t, IRR is the internal rate of return, and t is the time period. This calculator uses an iterative numerical method to approximate the IRR.

What is IRR Calculation Formula Excel?

The IRR calculation formula Excel refers to the method and function used within Microsoft Excel to determine the Internal Rate of Return (IRR) for an investment. IRR is a crucial metric in financial analysis used to estimate the profitability of potential investments. It represents the annualized effective compounded rate of return that an investment is expected to yield. Essentially, it's the discount rate at which the Net Present Value (NPV) of all cash flows from a particular project or investment equals zero. Understanding how to implement the IRR calculation formula Excel is vital for making informed financial decisions.

Who should use it: Financial analysts, investors, business owners, project managers, and anyone evaluating the potential return on an investment over time. It's particularly useful when comparing mutually exclusive projects, as it provides a standardized measure of profitability.

Common misconceptions:

  • IRR is always the actual return: IRR is a projected rate, not a guaranteed return. Actual returns can vary due to changing market conditions and unforeseen events.
  • Higher IRR is always better: While generally true, it's important to consider the investment's risk profile and the company's cost of capital. A high IRR on a very risky project might not be as attractive as a moderate IRR on a safer one.
  • IRR works for all cash flow patterns: The standard IRR calculation assumes reinvestment of cash flows at the IRR itself, which may not be realistic. For projects with unconventional cash flows (multiple sign changes), multiple IRRs or no IRR might exist.
  • IRR is a substitute for NPV: While related, NPV provides the absolute value of an investment's expected return in today's dollars, whereas IRR provides a percentage rate. For mutually exclusive projects, NPV is often the preferred decision criterion.

IRR Calculation Formula and Mathematical Explanation

The core concept behind the IRR calculation formula Excel is finding the discount rate (r) that sets the Net Present Value (NPV) of a series of cash flows to zero. The formula is derived from the NPV formula:

NPV = CF₀ + CF₁/(1+r)¹ + CF₂/(1+r)² + ... + CFn/(1+r)ⁿ

Where:

  • NPV = Net Present Value
  • CF₀ = Initial Investment (usually negative, representing an outflow)
  • CFt = Cash Flow during period t (t = 1, 2, …, n)
  • r = Discount Rate (this is what we are solving for – the IRR)
  • n = Total number of periods

To find the IRR, we set NPV to 0 and solve for 'r':

0 = CF₀ + CF₁/(1+IRR)¹ + CF₂/(1+IRR)² + ... + CFn/(1+IRR)ⁿ

This equation is a polynomial equation, and for more than a few periods, it cannot be solved directly with simple algebra. Excel's `IRR` function (and similar financial calculators) uses numerical methods, such as the Newton-Raphson method or a secant method, to iteratively approximate the value of IRR that satisfies the equation. The calculator you see above simulates this process.

Variables in IRR Calculation

IRR Calculation Variables
Variable Meaning Unit Typical Range
CF₀ Initial Investment (Cash Outflow) Currency (e.g., USD, EUR) Negative Value (e.g., -100,000)
CFt Cash Flow in Period t Currency (e.g., USD, EUR) Positive (Inflow) or Negative (Outflow)
t Time Period Discrete Units (e.g., Years, Months) 0, 1, 2, …, n
n Total Number of Periods Count Integer (e.g., 5, 10)
IRR Internal Rate of Return Percentage (%) Varies widely based on investment type and risk

Practical Examples (Real-World Use Cases)

Example 1: Evaluating a New Equipment Purchase

A company is considering purchasing new manufacturing equipment for $50,000. They project the following net cash flows over the next 5 years:

  • Year 0 (Initial Investment): -$50,000
  • Year 1: $10,000
  • Year 2: $15,000
  • Year 3: $20,000
  • Year 4: $25,000
  • Year 5: $30,000

Using the IRR calculation formula Excel or our calculator:

  • Inputs: Initial Investment = 50000, Cash Flows = -50000, 10000, 15000, 20000, 25000, 30000
  • Outputs:
    • IRR: Approximately 29.6%
    • NPV at 0%: $80,000
    • Number of Periods: 6 (including initial investment)
    • Sum of Cash Flows: $100,000

Financial Interpretation: The IRR of 29.6% suggests that this investment is expected to yield an annualized return of 29.6%. If the company's required rate of return (or cost of capital) is less than 29.6%, this investment would likely be considered profitable and acceptable.

Example 2: Real Estate Investment Analysis

An investor buys a rental property for $200,000 (initial outflow). They expect to receive net rental income (after expenses) of $15,000 per year for 10 years, and they anticipate selling the property at the end of year 10 for $250,000 (net of selling costs).

  • Year 0: -$200,000
  • Years 1-9: +$15,000 per year
  • Year 10: +$15,000 (rental income) + $250,000 (sale proceeds) = +$265,000

Using the IRR calculation formula Excel or our calculator:

  • Inputs: Initial Investment = 200000, Cash Flows = -200000, 15000, 15000, 15000, 15000, 15000, 15000, 15000, 15000, 265000
  • Outputs:
    • IRR: Approximately 11.4%
    • NPV at 0%: $115,000
    • Number of Periods: 11 (including initial investment)
    • Sum of Cash Flows: $65,000

Financial Interpretation: The calculated IRR of 11.4% represents the effective annual rate of return for this real estate investment. The investor would compare this to their target rate of return or the returns available from alternative investments of similar risk to decide if it's a worthwhile venture.

How to Use This IRR Calculator

Our IRR calculator is designed to be intuitive and provide quick insights into investment profitability. Follow these simple steps:

  1. Enter Initial Investment: Input the total cost required to start the investment. This is typically a single, negative cash flow at the beginning (Year 0). Enter it as a positive number in the "Initial Investment (Outflow)" field.
  2. Input Cash Flows: List all subsequent expected cash flows (both inflows and outflows) for each period (e.g., year, month). Separate each cash flow value with a comma. Use negative numbers for outflows and positive numbers for inflows. Ensure the order matches the time sequence of the investment.
  3. Calculate IRR: Click the "Calculate IRR" button.
  4. Review Results: The calculator will display:
    • IRR (Internal Rate of Return): The primary result, shown as a percentage. This is the discount rate where NPV = 0.
    • NPV at 0% Discount Rate: This is simply the sum of all cash flows, including the initial investment. It shows the total undiscounted profit/loss.
    • Number of Periods: The total count of cash flow periods, including the initial investment.
    • Sum of Cash Flows: The total net cash generated over the life of the investment (excluding the initial investment itself).
  5. Interpret the IRR: Compare the calculated IRR to your required rate of return (hurdle rate) or cost of capital. If IRR > Required Rate, the investment is generally considered financially attractive.
  6. Copy Results: Use the "Copy Results" button to easily transfer the calculated figures for reporting or further analysis.
  7. Reset: Click "Reset" to clear the fields and start over with default values.

Decision-Making Guidance: A common rule of thumb is to accept projects where the IRR exceeds the company's cost of capital or a predetermined minimum acceptable rate of return. However, always consider the project's risk, strategic alignment, and potential for alternative investments.

Key Factors That Affect IRR Results

Several factors can significantly influence the calculated IRR, making it crucial to understand their impact:

  1. Accuracy of Cash Flow Projections: This is the most critical factor. Overly optimistic revenue forecasts or underestimated costs will inflate the IRR, leading to potentially poor investment decisions. Conversely, pessimistic projections might cause a good project to be rejected.
  2. Timing of Cash Flows: IRR is sensitive to when cash flows occur. Earlier positive cash flows and later negative cash flows generally lead to higher IRRs. The discounting nature of the formula gives more weight to cash flows received sooner.
  3. Initial Investment Amount: A larger initial investment, even with the same subsequent cash flows, will generally result in a lower IRR. This is because the base against which returns are measured is higher.
  4. Project Lifespan (Number of Periods): A longer project lifespan, assuming positive net cash flows, can potentially lead to a higher IRR, as there are more periods to generate returns. However, it also increases uncertainty.
  5. Reinvestment Rate Assumption: The standard IRR calculation implicitly assumes that intermediate positive cash flows are reinvested at the IRR itself. If the actual reinvestment rate is lower, the project's true economic return might be less than the calculated IRR. The Modified Internal Rate of Return (MIRR) addresses this limitation.
  6. Inflation: Inflation can distort cash flow projections. If cash flow estimates don't account for future inflation, the nominal IRR might appear higher than the real (inflation-adjusted) return. It's essential to use consistent assumptions (either all nominal or all real).
  7. Financing Costs (Cost of Capital): While IRR itself doesn't directly include financing costs, it's compared against the cost of capital (the required rate of return). A higher cost of capital makes it harder for a project's IRR to exceed the threshold, thus affecting the decision to proceed.
  8. Taxes: Corporate income taxes reduce the net cash flows available to the company. Tax rates and the timing of tax payments must be factored into cash flow projections for an accurate IRR calculation.

Frequently Asked Questions (FAQ)

Q1: What is the difference between IRR and NPV?

NPV calculates the absolute dollar value of an investment's expected return in today's terms, while IRR calculates the percentage rate of return. NPV is generally preferred for deciding between mutually exclusive projects because it directly measures value creation. IRR is useful for understanding the project's efficiency and breakeven discount rate.

Q2: Can IRR be negative?

Yes, IRR can be negative if the sum of the discounted future cash flows is less than the initial investment, even at a 0% discount rate. This typically happens when the project generates losses or very low returns over its life.

Q3: What does it mean if the IRR is lower than the cost of capital?

If the IRR is lower than the company's cost of capital (or required rate of return), it implies that the project is not expected to generate sufficient returns to cover the cost of financing it. Such projects are typically rejected.

Q4: What are the limitations of the IRR calculation?

Key limitations include the assumption of reinvesting cash flows at the IRR, potential for multiple IRRs with non-conventional cash flows, and difficulty in comparing projects of different scales using IRR alone.

Q5: How does Excel calculate IRR?

Excel's `IRR` function uses an iterative numerical method (like Newton's method) to find the discount rate where the NPV equals zero. It starts with a guess and refines it until the equation is satisfied within a certain tolerance.

Q6: What is a "conventional" vs. "non-conventional" cash flow stream?

A conventional cash flow stream has one initial outflow followed only by inflows. A non-conventional stream has multiple sign changes (e.g., outflow, inflow, outflow, inflow). Non-conventional streams can lead to multiple IRRs or no real IRR.

Q7: Should I use IRR or MIRR?

MIRR (Modified Internal Rate of Return) addresses the reinvestment assumption of IRR by allowing you to specify a different rate for reinvesting positive cash flows and a financing rate for negative cash flows. MIRR often provides a more realistic picture, especially for longer-term projects.

Q8: How do I handle taxes in IRR calculations?

You should use after-tax cash flows. Calculate the expected revenue and expenses, determine the taxable income, subtract the taxes, and then add back any non-cash expenses (like depreciation) to arrive at the after-tax cash flow for each period.

Net Present Value (NPV) vs. Discount Rate

© 2023 Your Financial Tools. All rights reserved.

var initialInvestmentInput = document.getElementById('initialInvestment'); var cashFlowsInput = document.getElementById('cashFlows'); var irrResultSpan = document.getElementById('irrResult'); var npvZeroResultSpan = document.getElementById('npvZeroResult'); var periodsResultSpan = document.getElementById('periodsResult'); var sumCashFlowsResultSpan = document.getElementById('sumCashFlowsResult'); var resultsDiv = document.getElementById('results'); var initialInvestmentError = document.getElementById('initialInvestmentError'); var cashFlowsError = document.getElementById('cashFlowsError'); var chart = null; var ctx = null; function validateInputs() { var isValid = true; var initialInvestment = parseFloat(initialInvestmentInput.value); var cashFlowsStr = cashFlowsInput.value.trim(); initialInvestmentError.innerText = "; initialInvestmentError.classList.remove('visible'); cashFlowsError.innerText = "; cashFlowsError.classList.remove('visible'); if (isNaN(initialInvestment) || initialInvestment <= 0) { initialInvestmentError.innerText = 'Please enter a valid positive number for the initial investment.'; initialInvestmentError.classList.add('visible'); isValid = false; } var cashFlowsArray = []; if (cashFlowsStr) { var parts = cashFlowsStr.split(','); for (var i = 0; i < parts.length; i++) { var cf = parseFloat(parts[i].trim()); if (isNaN(cf)) { cashFlowsError.innerText = 'Invalid cash flow value detected. Ensure all values are numbers.'; cashFlowsError.classList.add('visible'); isValid = false; break; } cashFlowsArray.push(cf); } } else { cashFlowsError.innerText = 'Please enter at least one cash flow value.'; cashFlowsError.classList.add('visible'); isValid = false; } if (!isValid) { return false; } // Check for multiple sign changes in cash flows (excluding initial investment) var positiveFlows = 0; var negativeFlows = 0; for (var j = 0; j 0) positiveFlows++; if (cashFlowsArray[j] 0 && negativeFlows > 0 && (positiveFlows + negativeFlows) !== cashFlowsArray.length) { // This check is a simplified way to detect non-conventional flows if initial investment is handled separately // A more robust check would analyze sign changes directly. // For this calculator, we'll proceed but warn the user implicitly via potential multiple IRRs. } return isValid; } function calculateIRR() { if (!validateInputs()) { resultsDiv.style.display = 'none'; return; } var initialInvestment = parseFloat(initialInvestmentInput.value); var cashFlowsStr = cashFlowsInput.value.trim(); var cashFlows = []; var parts = cashFlowsStr.split(','); for (var i = 0; i 0) { irrResultSpan.classList.add('success'); } else if (irr < 0) { irrResultSpan.classList.add('error'); // Assuming an error class for negative results if desired } } npvZeroResultSpan.innerText = formatCurrency(npvZero); periodsResultSpan.innerText = numPeriods.toString(); sumCashFlowsResultSpan.innerText = formatCurrency(sumCashFlows + initialInvestment); // Sum of inflows only resultsDiv.style.display = 'block'; updateChart(allCashFlows); } // Numerical method to find IRR (Newton-Raphson or similar iterative approach) // This is a simplified implementation. Real-world IRR solvers are more complex. function irrSolver(cashFlows) { var maxIterations = 1000; var tolerance = 0.00001; var guess = 0.1; // Initial guess for IRR for (var i = 0; i < maxIterations; i++) { var npv = calculateNPV(guess, cashFlows); var derivative = calculateNPVDerivative(guess, cashFlows); if (Math.abs(derivative) < 1e-10) { // Avoid division by zero return NaN; // Cannot solve } var newGuess = guess – npv / derivative; if (Math.abs(newGuess – guess) < tolerance) { return newGuess; // Converged } guess = newGuess; } return NaN; // Did not converge within max iterations } function calculateNPV(rate, cashFlows) { var npv = 0; for (var t = 0; t < cashFlows.length; t++) { npv += cashFlows[t] / Math.pow(1 + rate, t); } return npv; } function calculateNPVDerivative(rate, cashFlows) { var derivative = 0; for (var t = 1; t < cashFlows.length; t++) { // Start from t=1 for derivative derivative -= t * cashFlows[t] / Math.pow(1 + rate, t + 1); } return derivative; } function formatCurrency(amount) { return amount.toLocaleString(undefined, { style: 'currency', currency: 'USD' }); // Default to USD } function resetCalculator() { initialInvestmentInput.value = '100000'; cashFlowsInput.value = '-5000, 20000, 30000, 40000, 50000, 60000'; irrResultSpan.innerText = '–'; npvZeroResultSpan.innerText = '–'; periodsResultSpan.innerText = '–'; sumCashFlowsResultSpan.innerText = '–'; resultsDiv.style.display = 'none'; initialInvestmentError.innerText = ''; initialInvestmentError.classList.remove('visible'); cashFlowsError.innerText = ''; cashFlowsError.classList.remove('visible'); if (ctx) { ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height); } } function copyResults() { var resultsText = "IRR Calculation Results:\n"; resultsText += "IRR: " + irrResultSpan.innerText + "\n"; resultsText += "NPV at 0% Discount Rate: " + npvZeroResultSpan.innerText + "\n"; resultsText += "Number of Periods: " + periodsResultSpan.innerText + "\n"; resultsText += "Sum of Cash Flows: " + sumCashFlowsResultSpan.innerText + "\n"; resultsText += "\nKey Assumptions:\n"; resultsText += "Initial Investment: " + formatCurrency(parseFloat(initialInvestmentInput.value)) + "\n"; resultsText += "Cash Flows: " + cashFlowsInput.value + "\n"; var textArea = document.createElement("textarea"); textArea.value = resultsText; document.body.appendChild(textArea); textArea.select(); try { document.execCommand("copy"); alert("Results copied to clipboard!"); } catch (err) { console.error("Failed to copy results: ", err); alert("Failed to copy results. Please copy manually."); } textArea.remove(); } function updateChart(allCashFlows) { var canvas = document.getElementById('irrChart'); if (!canvas) return; if (!ctx) { ctx = canvas.getContext('2d'); } else { ctx.clearRect(0, 0, canvas.width, canvas.height); } var chartWidth = canvas.clientWidth; var chartHeight = canvas.clientHeight; canvas.width = chartWidth; // Set canvas dimensions to match its display size canvas.height = chartHeight; var discountRates = []; var npvValues = []; var maxRate = 1.0; // Max rate to display on chart (100%) var minRate = -0.5; // Min rate to display on chart (-50%) var rateStep = (maxRate – minRate) / 20; // Number of points for the curve for (var r = minRate; r <= maxRate; r += rateStep) { discountRates.push(r); npvValues.push(calculateNPV(r, allCashFlows)); } // Find IRR for reference line var calculatedIRR = irrSolver(allCashFlows); var irrLineX = isNaN(calculatedIRR) ? -100 : calculatedIRR; // Position off-screen if NaN // Charting logic using native canvas API var padding = 40; var chartAreaWidth = chartWidth – 2 * padding; var chartAreaHeight = chartHeight – 2 * padding; // Find max/min NPV for scaling var maxNpv = Math.max(…npvValues); var minNpv = Math.min(…npvValues); var npvRange = maxNpv – minNpv; // Avoid division by zero if all NPVs are the same if (npvRange === 0) npvRange = 1; // Y-axis scaling var yScale = chartAreaHeight / npvRange; var yOffset = padding + chartAreaHeight – (minNpv * yScale); // Base Y position // X-axis scaling var xScale = chartAreaWidth / (maxRate – minRate); var xOffset = padding – (minRate * xScale); // Base X position // Draw Axes ctx.strokeStyle = '#ccc'; ctx.lineWidth = 1; ctx.beginPath(); // Y-axis (NPV) ctx.moveTo(padding, padding); ctx.lineTo(padding, chartHeight – padding); // X-axis (Rate) var zeroRateY = padding + chartAreaHeight – (0 * yScale); // Y position for 0% rate ctx.moveTo(padding, zeroRateY); ctx.lineTo(chartWidth – padding, zeroRateY); ctx.stroke(); // Draw NPV Curve ctx.strokeStyle = 'var(–primary-color)'; ctx.lineWidth = 2; ctx.beginPath(); for (var i = 0; i < discountRates.length; i++) { var x = xOffset + discountRates[i] * xScale; var y = yOffset – npvValues[i] * yScale; if (i === 0) { ctx.moveTo(x, y); } else { ctx.lineTo(x, y); } } ctx.stroke(); // Draw IRR Line (if calculated) if (!isNaN(calculatedIRR)) { ctx.strokeStyle = 'var(–success-color)'; ctx.lineWidth = 2; ctx.setLineDash([5, 5]); // Dashed line ctx.beginPath(); var irrXPos = xOffset + irrLineX * xScale; ctx.moveTo(irrXPos, padding); ctx.lineTo(irrXPos, chartHeight – padding); ctx.stroke(); ctx.setLineDash([]); // Reset line dash } // Add Labels and Ticks (simplified) ctx.fillStyle = '#555'; ctx.font = '10px Arial'; ctx.textAlign = 'center'; // X-axis labels var tickInterval = 5; // Show ticks every 5 steps for (var r = minRate; r = padding && yPos <= chartHeight – padding) { ctx.beginPath(); ctx.moveTo(padding – 5, yPos); ctx.lineTo(padding + 5, yPos); ctx.stroke(); ctx.textAlign = 'right'; ctx.fillText(formatCurrency(npvVal), padding – 10, yPos + 4); } }); ctx.textAlign = 'left'; // Reset alignment ctx.fillText('NPV', padding – 35, padding – 10); ctx.fillText('Discount Rate', chartWidth / 2, chartHeight – padding + 30); // Add legend ctx.font = '12px Arial'; ctx.fillStyle = 'var(–primary-color)'; ctx.fillText('NPV Curve', padding + 10, padding + 15); if (!isNaN(calculatedIRR)) { ctx.fillStyle = 'var(–success-color)'; ctx.fillText('IRR (' + (calculatedIRR * 100).toFixed(1) + '%)', padding + 10, padding + 30); } } // Initial calculation on load if inputs have default values document.addEventListener('DOMContentLoaded', function() { if (initialInvestmentInput.value && cashFlowsInput.value) { calculateIRR(); } }); // Add event listeners for real-time updates initialInvestmentInput.addEventListener('input', calculateIRR); cashFlowsInput.addEventListener('input', calculateIRR);

Leave a Comment