{% extends "base.html" %}
{% block title %}Beam Shear Design - ConcreteDesignPy{% endblock %}
{% block head %}<script src="https://cdn.jsdelivr.net/npm/plotly.js-dist-min/plotly.min.js"></script>
<style>
.st-section { margin-bottom: 1.25rem; }
.st-section h4 {
    font-size: .92rem; color: var(--primary-dark);
    border-bottom: 2px solid var(--primary-light);
    padding-bottom: .3rem; margin: 0 0 .6rem;
    display: flex; justify-content: space-between; align-items: baseline;
}
.st-section h4 .aci { font-size: .78rem; color: #3b82f6; font-weight: 400; }
.st-eq {
    background: var(--gray-50); padding: .55rem 1rem;
    border-radius: 4px; margin: .4rem 0; font-size: .9rem;
    border-left: 3px solid var(--gray-200);
}
.st-eq.result-eq {
    background: #dcfce7; font-weight: 700; font-size: 1rem;
    border-left-color: var(--success);
}
.st-eq.warn-eq { background: #fef3c7; border-left-color: var(--warning); }
.st-eq.fail-eq { background: #fef2f2; border-left-color: var(--danger); }
.st-grid {
    display: grid; grid-template-columns: 1fr 1fr 1fr; gap: .25rem 2.5rem;
    font-size: .85rem; margin: .4rem 0;
}
.st-grid dt { color: var(--gray-500); }
.st-grid dd { font-family: "SF Mono","Fira Code",monospace; font-weight: 500; text-align: right; }
.st-charts { display: flex; flex-wrap: wrap; gap: 12px; margin-bottom: 1.5rem; }
.st-charts > div { flex: 1; min-width: 420px; }

/* Header block */
.report-header {
    background: #fff; border: 1px solid var(--gray-200); border-radius: var(--radius);
    padding: 1rem 1.25rem; margin-bottom: 1.5rem;
    display: grid; grid-template-columns: 1fr auto; gap: .5rem 2rem;
    font-size: .82rem;
}
.report-header .company { font-size: 1.1rem; font-weight: 700; color: var(--primary-dark); }
.report-header .meta { display: grid; grid-template-columns: auto 1fr; gap: .15rem .75rem; }
.report-header .meta dt { color: var(--gray-500); font-weight: 600; white-space: nowrap; }
.report-header .meta dd { color: var(--gray-900); }
.header-form { margin-bottom: 1.25rem; }
.header-form .form-row { flex-wrap: wrap; }

.btn-print {
    background: #7c3aed; color: #fff; border: none; padding: .45rem 1.25rem;
    border-radius: 4px; font-size: .82rem; font-weight: 600; cursor: pointer;
}
.btn-print:hover { background: #6d28d9; }
.btn-actions { display: flex; gap: .5rem; align-items: center; margin-top: .75rem; }

/* Split layout: inputs left, output right */
.shear-layout {
    display: flex; gap: 1.5rem; align-items: flex-start;
}
.shear-layout-left {
    flex: 0 0 420px; min-width: 0;
}
.shear-layout-right {
    flex: 1; min-width: 0;
}
.shear-layout-right .st-charts {
    flex-direction: column;
}
.shear-layout-right .st-charts > div {
    min-width: 0 !important; flex: none !important;
}
@media (max-width: 1000px) {
    .shear-layout { flex-direction: column; }
    .shear-layout-left { flex: none; width: 100%; }
}

/* Print styles */
@media print {
    body { background: #fff !important; }
    .navbar, .disclaimer-bar, .footer, .calc-form, .back-link,
    .btn-actions, .btn-primary, .btn-print,
    .ref { display: none !important; }
    .calc-page { padding: 0 !important; }
    .calc-page h1 { display: none !important; }
    #results-area { display: block !important; }
    .report-header {
        border: 2px solid #1e3a8a !important; border-radius: 0 !important;
        page-break-after: avoid; margin-bottom: 1rem;
    }
    .st-charts { page-break-inside: avoid; }
    .st-section { page-break-inside: avoid; }
    .st-eq { border-left-width: 3px !important; }
    .st-eq.result-eq { background: #dcfce7 !important; -webkit-print-color-adjust: exact; print-color-adjust: exact; }
    .st-eq.fail-eq { background: #fef2f2 !important; -webkit-print-color-adjust: exact; print-color-adjust: exact; }
    .st-section h4 { color: #1e3a8a !important; -webkit-print-color-adjust: exact; print-color-adjust: exact; }
    .st-section h4 .aci { color: #3b82f6 !important; -webkit-print-color-adjust: exact; print-color-adjust: exact; }
}
</style>
{% endblock %}

{% block content %}
<div class="calc-page">
    <a href="/" class="back-link">&larr; All Calculators</a>
    <h1>Beam Shear Design</h1>
    <p class="ref">ACI 318M-14 / NSCP 2015</p>

    <div class="shear-layout">
        <div class="shear-layout-left">
            <form id="calc-form" class="calc-form">
                <div class="form-section header-form">
                    <h3>Project Header</h3>
                    <div class="form-row" style="flex-wrap:wrap;">
                        <div class="form-group" style="flex:1 1 100%;"><label>Company Name</label><input type="text" name="company" value="Albert Pamonag Engineering Consultancy"></div>
                        <div class="form-group"><label>Project Name</label><input type="text" name="project" value=""></div>
                        <div class="form-group"><label>Job No.</label><input type="text" name="job_no" value=""></div>
                    </div>
                    <div class="form-row">
                        <div class="form-group"><label>Prepared By</label><input type="text" name="prepared_by" value=""></div>
                        <div class="form-group"><label>Checked By</label><input type="text" name="checked_by" value=""></div>
                    </div>
                </div>
                <div class="form-section">
                    <h3>Material Properties</h3>
                    <div class="form-row" style="flex-wrap:wrap;">
                        <div class="form-group"><label>f'c (MPa)</label><input type="number" name="fc" value="40" step="0.1" required></div>
                        <div class="form-group"><label>fyv (MPa)</label><input type="number" name="fyv" value="420" step="0.1" required></div>
                        <div class="form-group"><label>&phi;</label><input type="number" name="phi" value="0.75" step="0.01"></div>
                    </div>
                </div>
                <div class="form-section">
                    <h3>Section Dimensions &amp; Covers</h3>
                    <div class="form-row" style="flex-wrap:wrap;">
                        <div class="form-group"><label>bw (mm)</label><input type="number" name="bw" value="300" required></div>
                        <div class="form-group"><label>h (mm)</label><input type="number" name="h" value="800" required></div>
                        <div class="form-group"><label>Cc (mm)</label><input type="number" name="cc" value="30" required></div>
                        <div class="form-group"><label>c (mm)</label><input type="number" name="c" value="100" required></div>
                    </div>
                </div>
                <div class="form-section">
                    <h3>Straining Actions</h3>
                    <div class="form-row" style="flex-wrap:wrap;">
                        <div class="form-group"><label>Vu (kN)</label><input type="number" name="vu" value="500" step="0.1" required></div>
                        <div class="form-group"><label>Tu (kN.m)</label><input type="number" name="tu" value="0" step="0.1"></div>
                        <div class="form-group"><label>Nu (kN) <small>+C/-T</small></label><input type="number" name="nu" value="10" step="0.1"></div>
                    </div>
                </div>
                <div class="form-section">
                    <h3>Stirrup Reinforcement</h3>
                    <div class="form-row" style="flex-wrap:wrap;">
                        <div class="form-group"><label>s (mm)</label><input type="number" name="s_chosen" value="150" required></div>
                        <div class="form-group"><label>Legs</label><input type="number" name="n_legs" value="4" required></div>
                        <div class="form-group"><label>db (mm)</label><input type="number" name="db_stirrup" value="10" required></div>
                    </div>
                </div>
                <div class="btn-actions">
                    <button type="submit" class="btn-primary">Calculate</button>
                    <button type="button" id="btn-print" class="btn-print" style="display:none;">Print Report</button>
                </div>
            </form>
        </div>

        <div class="shear-layout-right" id="results-area" style="display:none;">
            <div id="chart-section" style="margin-bottom:12px;"></div>
            <div id="chart-shear" style="margin-bottom:12px;"></div>
            <div id="chart-vc-nu" style="margin-bottom:12px;"></div>
            <div id="report-header"></div>
            <div id="report"></div>
        </div>
    </div>
</div>

<script>
function v(x, n) { return typeof x === 'number' ? (Number.isInteger(x) ? x : x.toFixed(n || 4).replace(/0+$/,'').replace(/\.$/,'')) : x; }

var _lastPayload = null;

function getPayload() {
    var f = document.getElementById('calc-form');
    var h_val = parseFloat(f.h.value);
    var c_val = parseFloat(f.c.value);
    return {
        fc: parseFloat(f.fc.value), fyv: parseFloat(f.fyv.value),
        phi: parseFloat(f.phi.value),
        bw: parseFloat(f.bw.value), h: h_val,
        cc: parseFloat(f.cc.value), c: c_val, d: h_val - c_val,
        vu: parseFloat(f.vu.value), tu: parseFloat(f.tu.value || 0), nu: parseFloat(f.nu.value),
        s_chosen: parseFloat(f.s_chosen.value),
        n_legs: parseInt(f.n_legs.value),
        db_stirrup: parseFloat(f.db_stirrup.value),
        header: {
            company: f.company.value,
            project: f.project.value,
            job_no: f.job_no.value,
            prepared_by: f.prepared_by.value,
            checked_by: f.checked_by.value,
        },
    };
}

function renderShearChart(r, p) {
    var av = p.n_legs * Math.PI * Math.pow(p.db_stirrup / 2, 2);
    var phiVc = p.phi * r.vc;
    var vsMax = r.vs_max;

    var sArr = [], vnArr = [], vcLine = [], vsMaxLine = [], vuLine = [];
    for (var s = 50; s <= 600; s += 5) {
        var vs_s = av * p.fyv * p.d / s / 1000;
        sArr.push(s);
        vnArr.push(p.phi * (r.vc + Math.min(vs_s, vsMax)));
        vcLine.push(phiVc);
        vsMaxLine.push(p.phi * (r.vc + vsMax));
        vuLine.push(p.vu);
    }

    var traces = [
        { x: sArr, y: vnArr, mode: 'lines', name: '\u03c6Vn = \u03c6(Vc+Vs)', line: { color: '#1e40af', width: 2.5 } },
        { x: sArr, y: vcLine, mode: 'lines', name: '\u03c6Vc (concrete only)', line: { color: '#16a34a', width: 1.5, dash: 'dash' } },
        { x: sArr, y: vsMaxLine, mode: 'lines', name: '\u03c6(Vc+Vs,max)', line: { color: '#dc2626', width: 1.5, dash: 'dot' } },
        { x: sArr, y: vuLine, mode: 'lines', name: 'Vu = ' + p.vu + ' kN', line: { color: '#f97316', width: 2, dash: 'dashdot' } },
        { x: [p.s_chosen], y: [p.phi * (r.vc + Math.min(av * p.fyv * p.d / p.s_chosen / 1000, vsMax))],
          mode: 'markers', name: 'Chosen s = ' + p.s_chosen + ' mm',
          marker: { size: 12, color: '#dc2626', symbol: 'star', line: { width: 1.5, color: '#fff' } } },
    ];
    Plotly.newPlot('chart-shear', traces, {
        title: { text: 'Shear Capacity vs Stirrup Spacing', font: { size: 13 } },
        xaxis: { title: 'Stirrup Spacing, s (mm)', gridcolor: '#e5e7eb', rangemode: 'tozero' },
        yaxis: { title: 'Shear Capacity, \u03c6Vn (kN)', gridcolor: '#e5e7eb', rangemode: 'tozero' },
        legend: { x: 1, xanchor: 'right', y: 1, font: { size: 9 }, bgcolor: 'rgba(255,255,255,0.9)', bordercolor: '#d1d5db', borderwidth: 1 },
        height: 420, margin: { t: 40, r: 10, b: 50, l: 60 },
        plot_bgcolor: '#fff', paper_bgcolor: '#fff', hovermode: 'x unified',
    }, { responsive: true, displaylogo: false });
}

function renderSectionChart(r, p) {
    // RC Beam Cross-Section — matches ACI 318M-14 reference rendering
    var bw = p.bw, h = p.h, cc = p.cc, c = p.c, d = p.d, db = p.db_stirrup;
    var nLegs = p.n_legs;

    // Bar positions
    var botBarY = cc + db;
    var topBarY = h - cc - db;
    var sLeft = cc + db / 2;
    var sRight = bw - cc - db / 2;
    var legX = [];
    for (var i = 0; i < nLegs; i++) legX.push(sLeft + i * (sRight - sLeft) / (nLegs - 1));

    var shapes = [], annotations = [];
    var dimC = '#374151';
    var stC = '#374151'; // stirrup color: dark gray/black like reference

    // ── 1. Concrete outline (thick dark border, light gray fill) ──
    shapes.push({ type: 'rect', x0: 0, y0: 0, x1: bw, y1: h,
        line: { color: '#1f2937', width: 3 }, fillcolor: 'rgba(243,244,246,0.5)' });

    // ── 2. Outer stirrup (solid dark lines, aligned to top/bottom bar rows) ──
    shapes.push({ type: 'rect', x0: sLeft, y0: botBarY, x1: sRight, y1: topBarY,
        line: { color: stC, width: 2 }, fillcolor: 'rgba(0,0,0,0)' });

    // Stirrup hooks at 4 outer corners (135-degree hooks inward)
    var hk = 14;
    shapes.push({ type: 'line', x0: sLeft, y0: botBarY, x1: sLeft + hk, y1: botBarY + hk, line: { color: stC, width: 2 } });
    shapes.push({ type: 'line', x0: sRight, y0: botBarY, x1: sRight - hk, y1: botBarY + hk, line: { color: stC, width: 2 } });
    shapes.push({ type: 'line', x0: sLeft, y0: topBarY, x1: sLeft + hk, y1: topBarY - hk, line: { color: stC, width: 2 } });
    shapes.push({ type: 'line', x0: sRight, y0: topBarY, x1: sRight - hk, y1: topBarY - hk, line: { color: stC, width: 2 } });

    // ── 3. Internal stirrup legs (vertical + hooks) ──
    if (nLegs > 2) {
        for (var i = 1; i < nLegs - 1; i++) {
            shapes.push({ type: 'line', x0: legX[i], y0: botBarY, x1: legX[i], y1: topBarY,
                line: { color: stC, width: 1.5 } });
            // hooks
            shapes.push({ type: 'line', x0: legX[i], y0: botBarY, x1: legX[i] + 9, y1: botBarY + 9, line: { color: stC, width: 1.5 } });
            shapes.push({ type: 'line', x0: legX[i], y0: topBarY, x1: legX[i] + 9, y1: topBarY - 9, line: { color: stC, width: 1.5 } });
        }
    }

    // ── 4. Rebar circles (black fill like reference) ──
    var barX = [], barY = [];
    // Bottom bars at every leg
    for (var i = 0; i < nLegs; i++) { barX.push(legX[i]); barY.push(botBarY); }
    // Top bars at every leg (same count as bottom, like reference image)
    for (var i = 0; i < nLegs; i++) { barX.push(legX[i]); barY.push(topBarY); }

    var barTrace = {
        x: barX, y: barY, mode: 'markers',
        marker: { size: 12, color: '#1f2937', symbol: 'circle',
                  line: { width: 1.5, color: '#000' } },
        hoverinfo: 'skip', showlegend: false,
    };

    // ── 5. Centroid + marker (red) ──
    var cx = bw / 2, cy = h / 2, cr = 18;
    shapes.push({ type: 'line', x0: cx - cr, y0: cy, x1: cx + cr, y1: cy, line: { color: '#dc2626', width: 2 } });
    shapes.push({ type: 'line', x0: cx, y0: cy - cr, x1: cx, y1: cy + cr, line: { color: '#dc2626', width: 2 } });

    // ── 6. Dimension lines (left side, matching reference exactly) ──
    // Reference layout: h outermost, d next, c as bracket at bottom
    var padL = 80;

    // h — vertical line with serifs at top and bottom of beam
    var hx = -padL + 5;
    shapes.push({ type: 'line', x0: hx, y0: 0, x1: hx, y1: h, line: { color: dimC, width: 1 } });
    // horizontal serifs
    shapes.push({ type: 'line', x0: hx - 5, y0: 0, x1: -5, y1: 0, line: { color: dimC, width: 0.5 } });
    shapes.push({ type: 'line', x0: hx - 5, y0: h, x1: -5, y1: h, line: { color: dimC, width: 0.5 } });
    annotations.push({ x: hx - 8, y: h / 2, text: '<b>h</b>', textangle: -90,
        showarrow: false, font: { size: 14, color: dimC, family: 'Arial' } });

    // d — from bottom of beam up to effective depth (d = h - c)
    // d is measured from extreme compression fiber to centroid of tension rft
    // In the diagram: from bottom (y=0) to y=d
    var ddx = -padL + 28;
    shapes.push({ type: 'line', x0: ddx, y0: 0, x1: ddx, y1: d, line: { color: dimC, width: 1 } });
    // horizontal serif at d level pointing to beam
    shapes.push({ type: 'line', x0: ddx - 3, y0: d, x1: -5, y1: d, line: { color: dimC, width: 0.5, dash: 'dot' } });
    // serifs
    shapes.push({ type: 'line', x0: ddx - 4, y0: 0, x1: ddx + 4, y1: 0, line: { color: dimC, width: 0.5 } });
    shapes.push({ type: 'line', x0: ddx - 4, y0: d, x1: ddx + 4, y1: d, line: { color: dimC, width: 0.5 } });
    annotations.push({ x: ddx - 8, y: d / 2, text: '<b>d</b>', textangle: -90,
        showarrow: false, font: { size: 14, color: dimC, family: 'Arial' } });

    // c — bracket from bottom of beam to bottom bar centroid
    var ccx = -padL + 48;
    shapes.push({ type: 'line', x0: ccx, y0: 0, x1: ccx, y1: c, line: { color: dimC, width: 1 } });
    // bracket serifs (horizontal ticks at top and bottom)
    shapes.push({ type: 'line', x0: ccx, y0: 0, x1: ccx + 8, y1: 0, line: { color: dimC, width: 0.8 } });
    shapes.push({ type: 'line', x0: ccx, y0: c, x1: ccx + 8, y1: c, line: { color: dimC, width: 0.8 } });
    // dotted line from c level to beam
    shapes.push({ type: 'line', x0: ccx + 8, y0: c, x1: -5, y1: c, line: { color: dimC, width: 0.5, dash: 'dot' } });
    annotations.push({ x: ccx - 6, y: c / 2, text: '<b>c</b>', textangle: -90,
        showarrow: false, font: { size: 12, color: dimC, family: 'Arial' } });

    // bw (bottom)
    var bwy = -50;
    shapes.push({ type: 'line', x0: 0, y0: bwy, x1: bw, y1: bwy, line: { color: dimC, width: 1 } });
    shapes.push({ type: 'line', x0: 0, y0: bwy - 4, x1: 0, y1: -5, line: { color: dimC, width: 0.5 } });
    shapes.push({ type: 'line', x0: bw, y0: bwy - 4, x1: bw, y1: -5, line: { color: dimC, width: 0.5 } });
    annotations.push({ x: bw / 2, y: bwy - 10,
        text: '<b>b<sub>w</sub></b>',
        showarrow: false, font: { size: 14, color: dimC, family: 'Arial' } });

    // ── 7. Force indicators (matching reference colors) ──

    // Vu arrow (dark blue, above beam, pointing down)
    var vuX = bw * 0.35;
    var vuTail = h + 80, vuTip = h + 12;
    shapes.push({ type: 'line', x0: vuX, y0: vuTail, x1: vuX, y1: vuTip, line: { color: '#1e3a8a', width: 4 } });
    shapes.push({ type: 'line', x0: vuX - 10, y0: vuTip + 16, x1: vuX, y1: vuTip, line: { color: '#1e3a8a', width: 3.5 } });
    shapes.push({ type: 'line', x0: vuX + 10, y0: vuTip + 16, x1: vuX, y1: vuTip, line: { color: '#1e3a8a', width: 3.5 } });
    annotations.push({ x: vuX, y: vuTail + 10,
        text: '<b><i>V<sub>u</sub></i></b>',
        showarrow: false, font: { size: 18, color: '#dc2626', family: 'Arial' } });

    // Tu curved arrow (dark blue arc + arrowhead, right of Vu)
    // Draw as arc segments using short line segments approximating a curve
    var tuCx = bw * 0.7, tuCy = h + 50, tuR = 28;
    var arcPts = 20;
    // Arc from ~200deg to ~340deg (bottom-left to bottom-right, curving right)
    for (var i = 0; i < arcPts; i++) {
        var a1 = (200 + i * 140 / arcPts) * Math.PI / 180;
        var a2 = (200 + (i + 1) * 140 / arcPts) * Math.PI / 180;
        shapes.push({ type: 'line',
            x0: tuCx + tuR * Math.cos(a1), y0: tuCy + tuR * Math.sin(a1),
            x1: tuCx + tuR * Math.cos(a2), y1: tuCy + tuR * Math.sin(a2),
            line: { color: '#1e3a8a', width: 3 } });
    }
    // Arrowhead at end of arc (~340 degrees)
    var aEnd = 340 * Math.PI / 180;
    var ax = tuCx + tuR * Math.cos(aEnd), ay = tuCy + tuR * Math.sin(aEnd);
    var aDir = aEnd + Math.PI / 2; // perpendicular to tangent
    shapes.push({ type: 'line', x0: ax, y0: ay,
        x1: ax + 10 * Math.cos(aDir + 0.5), y1: ay + 10 * Math.sin(aDir + 0.5),
        line: { color: '#1e3a8a', width: 3 } });
    shapes.push({ type: 'line', x0: ax, y0: ay,
        x1: ax + 10 * Math.cos(aDir - 0.7), y1: ay + 10 * Math.sin(aDir - 0.7),
        line: { color: '#1e3a8a', width: 3 } });

    annotations.push({ x: tuCx + tuR + 15, y: tuCy,
        text: '<b><i>T<sub>u</sub></i></b>',
        showarrow: false, font: { size: 18, color: '#16a34a', family: 'Arial' } });

    // Nu label (red, at centroid above +)
    annotations.push({ x: cx, y: cy + 35,
        text: '<b><i>N<sub>u</sub></i></b>',
        showarrow: false, font: { size: 18, color: '#dc2626', family: 'Arial' } });

    // ── 8. Right-side labels (Av, As) with leader lines ──
    var lx = bw + 55;

    // Av (mid-height)
    var avY = (topBarY + botBarY) / 2;
    shapes.push({ type: 'line', x0: sRight + 3, y0: avY, x1: lx - 3, y1: avY, line: { color: dimC, width: 0.8 } });
    annotations.push({ x: lx, y: avY, text: '<b><i>A<sub>v</sub></i></b>',
        showarrow: false, font: { size: 14, color: '#dc2626', family: 'Arial' }, xanchor: 'left' });

    // As (at bottom bar level)
    shapes.push({ type: 'line', x0: sRight + 3, y0: botBarY, x1: lx - 3, y1: botBarY, line: { color: dimC, width: 0.8 } });
    annotations.push({ x: lx, y: botBarY, text: '<b><i>A<sub>s</sub></i></b>',
        showarrow: false, font: { size: 14, color: '#dc2626', family: 'Arial' }, xanchor: 'left' });

    var xMin = -padL - 5, xMax = lx + 35;
    var yMin = bwy - 22, yMax = vuTail + 40;

    Plotly.newPlot('chart-section', [barTrace], {
        title: { text: 'RC Beam Cross-Section', font: { size: 13 } },
        xaxis: { range: [xMin, xMax], visible: false, fixedrange: true },
        yaxis: { range: [yMin, yMax], visible: false, fixedrange: true,
                 scaleanchor: 'x', scaleratio: 1 },
        shapes: shapes, annotations: annotations,
        height: 600, margin: { t: 35, r: 5, b: 5, l: 5 },
        plot_bgcolor: '#fff', paper_bgcolor: '#fff',
        hovermode: false,
    }, { responsive: true, displaylogo: false, staticPlot: true });
}

function renderVcNuChart(r, p) {
    // ACI 318M-14 Figure R22.5.6.1 (exact reproduction)
    // X-axis: Nu/Ag (MPa), compression positive (LEFT), tension negative (RIGHT)
    // Y-axis: Vc / (sqrt(f'c) * bw * d), dimensionless
    var fc = p.fc, bw = p.bw, d = p.d, h = p.h;
    var ag = bw * h;
    var sqrtFc = Math.sqrt(fc);

    // Eq. (22.5.6.1): Vc = 0.17*(1 + Nu/(14*Ag))*lambda*sqrt(f'c)*bw*d
    // Normalized: 0.17*(1 + x/14), for compression (x >= 0)
    var xComp = [], yEq22561 = [];
    for (var x = 0; x <= 8; x += 0.05) {
        xComp.push(x);
        yEq22561.push(0.17 * (1 + x / 14));
    }

    // Table expression 22.5.6.1(b) upper bound:
    // Vc,max = 0.29*lambda*sqrt(f'c)*bw*d*sqrt(1 + 0.29*Nu/Ag)
    // Normalized: 0.29*sqrt(1 + 0.29*x)
    var yTable22561b = [];
    for (var i = 0; i < xComp.length; i++) {
        yTable22561b.push(0.29 * Math.sqrt(1 + 0.29 * xComp[i]));
    }

    // Shaded area (fill between Eq. 22.5.6.1 and Table 22.5.6.1(b))
    // Use fill: 'tonexty' approach - lower curve first, then upper
    var xFill = xComp.slice();
    var yFillLower = yEq22561.slice();
    var yFillUpper = yTable22561b.slice();

    // Eq. (22.5.7.1): Vc = 0.17*(1 + Nu/(3.5*Ag))*lambda*sqrt(f'c)*bw*d
    // Normalized: 0.17*(1 + x/3.5), for tension (x <= 0)
    // At x = -3.5/0.17? No: goes to zero at x where (1 + x/3.5) = 0 => x = -3.5
    var xTens = [], yEq22571 = [];
    for (var x = -4; x <= 0.05; x += 0.05) {
        xTens.push(x);
        yEq22571.push(Math.max(0.17 * (1 + x / 3.5), 0));
    }

    // Design point
    var nuAg_pt = p.nu * 1000 / ag;
    var vcNorm_pt = r.vc * 1000 / (sqrtFc * bw * d);

    var traces = [
        // Shaded fill: lower bound (Eq. 22.5.6.1) as base
        { x: xFill, y: yFillLower, mode: 'lines', name: 'Eq. (22.5.6.1)',
          line: { color: '#16a34a', width: 2.5 },
          showlegend: true },
        // Shaded fill: upper bound with fill to lower
        { x: xFill, y: yFillUpper, mode: 'lines', name: 'Table 22.5.6.1(b)',
          line: { color: '#1e3a8a', width: 2.5, dash: 'dash' },
          fill: 'tonexty', fillcolor: 'rgba(200,200,200,0.35)',
          showlegend: true },
        // Tension line: Eq. (22.5.7.1)
        { x: xTens, y: yEq22571, mode: 'lines', name: 'Eq. (22.5.7.1)',
          line: { color: '#374151', width: 2.5, dash: 'dash' },
          showlegend: true },
        // Design point
        { x: [nuAg_pt], y: [vcNorm_pt], mode: 'markers', name: 'Design Point',
          marker: { size: 14, color: '#dc2626', symbol: 'diamond',
                    line: { width: 2, color: '#fff' } },
          showlegend: true },
    ];

    Plotly.newPlot('chart-vc-nu', traces, {
        title: { text: 'ACI 318M-14 Fig. R22.5.6.1', font: { size: 13 } },
        xaxis: {
            title: { text: 'N<sub>u</sub>/A<sub>g</sub>, MPa', font: { size: 12 } },
            range: [8.5, -4.5], // reversed: compression left, tension right
            dtick: 1, gridcolor: '#d1d5db', gridwidth: 1,
            zeroline: true, zerolinecolor: '#374151', zerolinewidth: 2,
            tickfont: { size: 10 },
        },
        yaxis: {
            title: { text: 'V<sub>c</sub> / (\u221af\'<sub>c</sub> \u00b7 b<sub>w</sub> \u00b7 d)', font: { size: 12 } },
            range: [0, 0.55], dtick: 0.1, gridcolor: '#d1d5db', gridwidth: 1,
            tickfont: { size: 10 },
        },
        legend: { x: 0.02, y: 0.98, font: { size: 9 }, bgcolor: 'rgba(255,255,255,0.9)',
                  bordercolor: '#d1d5db', borderwidth: 1 },
        height: 380, margin: { t: 40, r: 15, b: 55, l: 70 },
        plot_bgcolor: '#fff', paper_bgcolor: '#fff', hovermode: 'closest',
        annotations: [
            { x: 5, y: 0.5, text: '<b>Compression</b>', showarrow: false,
              font: { size: 11, color: '#374151' } },
            { x: -2.5, y: 0.5, text: '<b>Tension</b>', showarrow: false,
              font: { size: 11, color: '#374151' } },
            { x: nuAg_pt, y: vcNorm_pt, text: '  (' + v(nuAg_pt, 2) + ', ' + v(vcNorm_pt, 3) + ')',
              showarrow: true, arrowhead: 0, ax: 40, ay: -30,
              font: { size: 10, color: '#dc2626', weight: 700 } },
            { x: 2, y: 0.28, text: 'Shaded area shows approx.<br>range of values from<br>Table 22.5.6.1(a)',
              showarrow: false, font: { size: 8, color: '#6b7280' }, align: 'left' },
        ],
    }, { responsive: true, displaylogo: false });
}

function renderHeader(p) {
    var hdr = p.header || {};
    var h = '<div class="report-header">';
    h += '<div>';
    h += '<div class="company">' + (hdr.company || '') + '</div>';
    h += '</div>';
    h += '<dl class="meta">';
    if (hdr.project) { h += '<dt>Project:</dt><dd><strong>' + hdr.project + '</strong></dd>'; }
    if (hdr.job_no) { h += '<dt>Job No:</dt><dd>' + hdr.job_no + '</dd>'; }
    if (hdr.prepared_by) { h += '<dt>Prepared By:</dt><dd>' + hdr.prepared_by + '</dd>'; }
    if (hdr.checked_by) { h += '<dt>Checked By:</dt><dd>' + hdr.checked_by + '</dd>'; }
    h += '<dt>Page Type:</dt><dd>CALCULATION SHEET</dd>';
    h += '<dt>Section:</dt><dd>BEAM SHEAR DESIGN</dd>';
    h += '</dl></div>';
    document.getElementById('report-header').innerHTML = h;
}

function renderReport(r, p) {
    var h = '';
    var fc = p.fc, bw = p.bw, d = p.d, phi = p.phi, fyv = p.fyv;

    // ── 1. Material & Section ──
    h += '<div class="st-section"><h4>Material Properties & Section Dimensions <span class="aci">ACI 318M-14 Cl. 20.2, 22.5.3</span></h4>';
    h += '<dl class="st-grid">';
    h += '<dt>Concrete Strength, f\'c</dt><dd>' + fc + ' MPa</dd>';
    h += '<dt>Stirrup Yield Strength, fyv</dt><dd>' + fyv + ' MPa</dd>';
    h += '<dt>Strength Reduction Factor, \u03c6</dt><dd>' + phi + '</dd>';
    h += '<dt>Beam Width, bw</dt><dd>' + bw + ' mm</dd>';
    h += '<dt>Beam Height, h</dt><dd>' + p.h + ' mm</dd>';
    h += '<dt>Effective Depth, d = h \u2212 c</dt><dd>' + d + ' mm</dd>';
    h += '<dt>Factored Shear, Vu</dt><dd>' + p.vu + ' kN</dd>';
    h += '<dt>Axial Force, Nu</dt><dd>' + p.nu + ' kN</dd>';
    h += '</dl></div>';

    // ── 2. Concrete Shear Strength ──
    h += '<div class="st-section"><h4>Concrete Shear Strength, V<sub>c</sub> <span class="aci">ACI 318M-14 Cl. 22.5.5.1\u20137</span></h4>';
    if (p.nu > 0) {
        h += '<div class="st-eq">\\[ V_c = \\min\\left[\\left(1 + \\frac{N_u}{14 A_g}\\right) \\frac{\\sqrt{f\'_c}}{6} b_w d,\\; 0.3\\sqrt{f\'_c}\\, b_w d\\left(1+\\frac{0.3 N_u}{A_g}\\right)\\right] \\]</div>';
    } else if (p.nu < 0) {
        h += '<div class="st-eq">\\[ V_c = \\left(1 + \\frac{0.29 N_u}{A_g}\\right) \\frac{\\sqrt{f\'_c}}{6} b_w d \\geq 0 \\]</div>';
    } else {
        h += '<div class="st-eq">\\[ V_c = \\frac{\\sqrt{f\'_c}}{6} \\cdot b_w \\cdot d \\]</div>';
    }
    h += '<div class="st-eq">\\[ V_c = \\frac{\\sqrt{' + fc + '}}{6} \\times ' + bw + ' \\times ' + d + ' \\times 10^{-3} \\]</div>';
    h += '<div class="st-eq result-eq">\\[ \\boxed{V_c = ' + v(r.vc, 2) + ' \\text{ kN}} \\]</div>';
    h += '</div>';

    // ── 3. Required Vs ──
    h += '<div class="st-section"><h4>Required Stirrup Shear Strength, V<sub>s</sub> <span class="aci">ACI 318M-14 Cl. 22.5.10.5</span></h4>';
    h += '<div class="st-eq">\\[ V_{s,req} = \\frac{V_u - \\phi V_c}{\\phi} = \\frac{' + p.vu + ' - ' + phi + ' \\times ' + v(r.vc, 2) + '}{' + phi + '} \\]</div>';
    h += '<div class="st-eq result-eq">\\[ \\boxed{V_{s,req} = ' + v(r.vs, 2) + ' \\text{ kN}} \\]</div>';
    h += '<div class="st-eq">\\[ V_{s,max} = \\frac{2}{3}\\sqrt{f\'_c}\\, b_w\\, d = ' + v(r.vs_max, 2) + ' \\text{ kN} \\]</div>';
    var shearCls = r.shear_status === 'SAFE' ? 'result-eq' : 'fail-eq';
    h += '<div class="st-eq ' + shearCls + '">\\[ V_u \\leq \\phi(V_c + V_{s,max}) \\;\\Rightarrow\\; ' + p.vu + ' \\leq ' + v(r.vu_max, 2) + ' \\;\\rightarrow\\; \\boxed{\\textbf{' + r.shear_status + '}} \\]</div>';
    h += '</div>';

    // ── 4. Av/s Required ──
    h += '<div class="st-section"><h4>Required Shear Reinforcement, A<sub>v</sub>/s <span class="aci">ACI 318M-14 R22.5.10.5</span></h4>';
    h += '<div class="st-eq">\\[ \\frac{A_v}{s} = \\frac{V_u - \\phi V_c}{\\phi \\cdot f_{yv} \\cdot d} \\]</div>';
    h += '<div class="st-eq result-eq">\\[ \\boxed{\\frac{A_v}{s}_{req} = ' + v(r.av_s_req, 4) + ' \\text{ mm}^2\\text{/mm}} \\]</div>';
    h += '</div>';

    // ── 5. Minimum Reinforcement ──
    h += '<div class="st-section"><h4>Minimum Shear Reinforcement <span class="aci">ACI 318M-14 Table 9.6.3.3</span></h4>';
    h += '<div class="st-eq">\\[ \\frac{A_{v,min}}{s} = \\max\\left(\\frac{\\sqrt{f\'_c}}{16}\\frac{b_w}{f_{yv}},\\; \\frac{0.35\\, b_w}{f_{yv}}\\right) = ' + v(r.av_min, 4) + ' \\text{ mm}^2\\text{/mm} \\]</div>';
    h += '<div class="st-eq result-eq">\\[ \\boxed{\\frac{A_v}{s}_{govern} = ' + v(r.av_s_govern, 4) + ' \\text{ mm}^2\\text{/mm}} \\]</div>';
    h += '</div>';

    // ── 6. Chosen Reinforcement ──
    h += '<div class="st-section"><h4>Chosen Reinforcement Check <span class="aci">ACI 318M-14 Cl. 9.7.6.2.2</span></h4>';
    h += '<dl class="st-grid" style="grid-template-columns:1fr 1fr;">';
    h += '<dt>Stirrup Spacing, s</dt><dd>' + p.s_chosen + ' mm</dd>';
    h += '<dt>Maximum Spacing, S<sub>max</sub></dt><dd>' + v(r.smax, 0) + ' mm</dd>';
    h += '<dt>No. of Legs</dt><dd>' + p.n_legs + '</dd>';
    h += '<dt>Stirrup Diameter, db</dt><dd>' + p.db_stirrup + ' mm</dd>';
    h += '<dt>Provided A<sub>v</sub>/s</dt><dd>' + v(r.av_provided, 4) + ' mm\u00b2/mm</dd>';
    h += '<dt>Required A<sub>v</sub>/s</dt><dd>' + v(r.av_s_govern, 4) + ' mm\u00b2/mm</dd>';
    h += '</dl>';
    var spCls = r.spacing_ok === 'OK' ? 'result-eq' : 'fail-eq';
    h += '<div class="st-eq ' + spCls + '">\\[ s = ' + p.s_chosen + ' \\text{ mm}';
    h += (r.spacing_ok === 'OK' ? ' \\leq ' : ' > ');
    h += 'S_{max} = ' + v(r.smax, 0) + ' \\text{ mm} \\;\\rightarrow\\; \\boxed{\\textbf{Spacing ' + r.spacing_ok + '}} \\]</div>';
    var rftCls = r.rft_ok === 'OK' ? 'result-eq' : 'fail-eq';
    h += '<div class="st-eq ' + rftCls + '">\\[ \\frac{A_v}{s}_{provided} = ' + v(r.av_provided, 4) + (r.rft_ok === 'OK' ? ' \\geq ' : ' < ') + v(r.av_s_govern, 4) + ' = \\frac{A_v}{s}_{govern} \\;\\rightarrow\\; \\boxed{\\textbf{Reinforcement ' + r.rft_ok + '}} \\]</div>';
    h += '</div>';

    document.getElementById('report').innerHTML = h;
    if (window.MathJax) MathJax.typeset();
}

document.getElementById('calc-form').addEventListener('submit', function(e) {
    e.preventDefault();
    var payload = getPayload();
    _lastPayload = payload;

    document.getElementById('results-area').style.display = 'block';
    document.getElementById('report').innerHTML = '<div class="loading">Calculating...</div>';

    fetch('/api/beam/shear-design', {
        method: 'POST', headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify(payload),
    })
    .then(function(res) { return res.json(); })
    .then(function(data) {
        if (data.status === 'error') {
            document.getElementById('report').innerHTML = '<div class="error-msg">Error: ' + data.message + '</div>';
            return;
        }
        var r = data.result;
        document.getElementById('btn-print').style.display = 'inline-block';
        renderHeader(payload);
        renderSectionChart(r, payload);
        renderShearChart(r, payload);
        renderVcNuChart(r, payload);
        renderReport(r, payload);
    })
    .catch(function(err) {
        document.getElementById('report').innerHTML = '<div class="error-msg">Request failed: ' + err.message + '</div>';
    });
});

document.getElementById('btn-print').addEventListener('click', function() {
    window.print();
});


</script>
{% endblock %}
