{{-- Part E §1 — Earned Value Analysis (SPI/CPI remarks follow Result value; extended metrics by report type) --}} @push('stylesheets') @endpush @php use App\Models\ReportSubSectorChecklistItem; use App\Support\MecReportType; $e1Base = 'report.part_e.earned_value_analysis.rows'; $evaReportType = (string) ($reportType ?? request()->query('report_type', '')); $itemsAll = isset($subSectorChecklistItemsEarnedValueAnalysis) ? collect($subSectorChecklistItemsEarnedValueAnalysis) : collect(); $items = ReportSubSectorChecklistItem::filterEarnedValueAnalysisItems($itemsAll, $evaReportType); $isPmrEva = MecReportType::isPmr($evaReportType); $rowsOld = report_wizard_rows('part_e.earned_value_analysis.rows', [], $reportPayload ?? null); $evaRowsByItemId = []; if (is_array($rowsOld)) { foreach ($rowsOld as $savedRow) { if (! is_array($savedRow)) { continue; } $itemId = (int) ($savedRow['report_sub_sector_checklist_item_id'] ?? 0); if ($itemId > 0) { $evaRowsByItemId[$itemId] = $savedRow; } } } $evaParseResult = static function (?string $s): ?float { if ($s === null || trim((string) $s) === '') { return null; } $t = str_replace([' ', ','], ['', '.'], trim((string) $s)); if ($t === '' || ! is_numeric($t)) { return null; } return (float) $t; }; $evaSpiRemarkHtml = static function (?float $n): string { if ($n === null) { return 'Enter a numeric result to show the matching remark.'; } if (abs($n - 1.0) < 1e-6) { return '
The Scheme is exactly on schedule.
'; } if ($n > 1.0) { return 'The Scheme is ahead of schedule, completing more work than planned.
'; } return 'The Scheme is behind schedule, completing less work than planned.
'; }; $evaCpiRemarkHtml = static function (?float $n): string { if ($n === null) { return 'Enter a numeric result to show the matching remark.'; } if ($n > 1.0) { return 'The Scheme is under budget and performing efficiently.
'; } if (abs($n - 1.0) < 1e-6) { return 'The Scheme is exactly on budget.
'; } return 'The Scheme is over budget, spending more than planned.
'; }; $evaFixedRemark = static function (int $ord): string { return match ($ord) { 1 => 'Budgeted Cost of Work Scheduled', 2 => 'Budgeted Cost of Work Performed', 3 => 'Actual cost of work performed (same unit as PV/EV)', 6 => 'Positive = underrun, negative = overrun', 7 => 'Positive = ahead of schedule, negative = behind', 8 => 'Forecast total cost at project completion', 9 => 'Performance needed to meet original BAC', 10 => 'Performance needed to meet forecasted EAC', default => '', }; }; $reportEvaCalcJsI18n = [ 'errBac' => __('Enter a valid project cost (BAC) greater than zero.'), 'errPhys' => __('Enter physical progress between 0 and 100%.'), 'errDuration' => __('Enter total planned duration in months (greater than zero).'), 'errStart' => __('Select the project start date.'), 'errAc' => __('Enter actual cost (ACWP) as zero or greater.'), 'errEtcNew' => __('Revised ETC is required when EAC Method 4 is selected.'), 'errInvalidDates' => __('Invalid date(s).'), 'errAssessBeforeStart' => __('Assessment date cannot be earlier than the start date.'), 'checkInputs' => __('Check inputs'), 'swalSuccessTitle' => __('EVA updated'), 'swalSuccessText' => $isPmrEva ? __('Earned value metrics (including variances, EAC, and TCPI) were filled from the calculator.') : __('Earned value metrics, EAC, and TCPI were filled from the calculator.'), ]; @endphpEarned Value Analysis catalog is empty. Run php artisan migrate (or seed ReportSubSectorChecklistSeeder).
| Items | Result | Remarks |
|---|---|---|
| {{ $it->name }} | @error($dotBase.'result') {{ $message }} @enderror |
@switch($ord)
@case(4)
{!! $evaSpiRemarkHtml($n) !!}
@break
@case(5)
{!! $evaCpiRemarkHtml($n) !!}
@break
@default
@php $fixedRm = $evaFixedRemark($ord); @endphp
@if ($fixedRm !== '')
{{ $fixedRm }}
@else
—
@endif
@endswitch
|