From 15b00e1e54c672e7b72e448f3c240108d07aa8ff Mon Sep 17 00:00:00 2001 From: BTMS2 Date: Mon, 7 Apr 2025 16:09:52 +0800 Subject: [PATCH] tambah laporan aging keseluruhan --- .../AgingAllExportExcel.php | 184 ++++++++++++++++++ .../Controllers/Reports/AgingController.php | 84 ++++++++ resources/views/indexOverallReport.blade.php | 6 + resources/views/reports/aging/index.blade.php | 158 +++++++++++++++ routes/reports.php | 3 + 5 files changed, 435 insertions(+) create mode 100644 app/Exports/LaporanKeseluruhan/AgingAllExportExcel.php create mode 100644 app/Http/Controllers/Reports/AgingController.php create mode 100644 resources/views/reports/aging/index.blade.php diff --git a/app/Exports/LaporanKeseluruhan/AgingAllExportExcel.php b/app/Exports/LaporanKeseluruhan/AgingAllExportExcel.php new file mode 100644 index 0000000..fbb9f7c --- /dev/null +++ b/app/Exports/LaporanKeseluruhan/AgingAllExportExcel.php @@ -0,0 +1,184 @@ +aging = $aging; + } + + public function array(): array + { + $rows = []; + $totals = []; + + foreach ($this->aging as $branch) { + $row = [$branch['cawangan']]; + $i = 0; + + foreach ($branch['summary_by_tempoh'] as $summary) { + $row[] = $summary['count']; + $row[] = $summary['sum_bakipjm']; + + // Totals per column + $totals[$i]['count'] = ($totals[$i]['count'] ?? 0) + $summary['count']; + $totals[$i]['sum_bakipjm'] = ($totals[$i]['sum_bakipjm'] ?? 0) + $summary['sum_bakipjm']; + $i++; + } + + // Total per row (cawangan) + $jumlahBil = collect($branch['summary_by_tempoh'])->sum('count'); + $jumlahRM = collect($branch['summary_by_tempoh'])->sum('sum_bakipjm'); + $row[] = $jumlahBil; + $row[] = $jumlahRM; + + // Add to column totals + $totals['jumlah']['count'] = ($totals['jumlah']['count'] ?? 0) + $jumlahBil; + $totals['jumlah']['sum_bakipjm'] = ($totals['jumlah']['sum_bakipjm'] ?? 0) + $jumlahRM; + + $rows[] = $row; + } + + // Add final total row + $totalRow = ['Jumlah']; + foreach ($totals as $key => $val) { + $totalRow[] = $val['count']; + $totalRow[] = $val['sum_bakipjm']; + } + + $rows[] = $totalRow; + + return $rows; + } + + + /** + * Multi-row headings (2 rows) + */ + public function headings(): array + { + $row1 = ['Cawangan']; + $row2 = ['']; + + if (!empty($this->aging[0]['summary_by_tempoh'])) { + foreach ($this->aging[0]['summary_by_tempoh'] as $summary) { + $row1[] = $summary['label']; + $row1[] = ''; // empty to allow merged cell + $row2[] = 'Bil'; + $row2[] = 'RM'; + } + } + + $row1[] = 'Jumlah'; + $row1[] = ''; // for merged "Jumlah" cell + $row2[] = 'Bil'; + $row2[] = 'RM'; + + return [$row1, $row2]; + } + + public function columnFormats(): array +{ + $formats = []; + $colIndex = 2; // Start at column B (Cawangan is A) + + $tempohCount = count($this->aging[0]['summary_by_tempoh'] ?? []); + for ($i = 0; $i < $tempohCount; $i++) { + // Bil column + $bilCol = \PhpOffice\PhpSpreadsheet\Cell\Coordinate::stringFromColumnIndex($colIndex++); + $formats[$bilCol] = NumberFormat::FORMAT_NUMBER; // ✅ No decimal + + // RM column + $rmCol = \PhpOffice\PhpSpreadsheet\Cell\Coordinate::stringFromColumnIndex($colIndex++); + $formats[$rmCol] = NumberFormat::FORMAT_NUMBER_COMMA_SEPARATED1; // RM with comma and decimals + } + + // Jumlah Bil + $jumlahBilCol = \PhpOffice\PhpSpreadsheet\Cell\Coordinate::stringFromColumnIndex($colIndex++); + $formats[$jumlahBilCol] = NumberFormat::FORMAT_NUMBER; // ✅ No decimal + + // Jumlah RM + $jumlahRMCol = \PhpOffice\PhpSpreadsheet\Cell\Coordinate::stringFromColumnIndex($colIndex++); + $formats[$jumlahRMCol] = NumberFormat::FORMAT_NUMBER_COMMA_SEPARATED1; + + return $formats; +} + + + public function bindValue(Cell $cell, $value) + { + if (is_numeric($value)) { + $cell->setValueExplicit($value, DataType::TYPE_NUMERIC); + return true; + } + + return parent::bindValue($cell, $value); + } + + /** + * Merge heading cells using AfterSheet event + */ + public function registerEvents(): array + { + return [ + AfterSheet::class => function(AfterSheet $event) { + $sheet = $event->sheet->getDelegate(); + $colIndex = 2; // Start from column B (A = Cawangan) + $tempohCount = count($this->aging[0]['summary_by_tempoh'] ?? []); + + $headingRow = 1; // Change this to 1 for the first row + $rowToMerge = $headingRow; + + // Merge each tempoh (e.g. "1 Bulan") across 2 columns: Bil & RM + for ($i = 0; $i < $tempohCount; $i++) { + $startCol = \PhpOffice\PhpSpreadsheet\Cell\Coordinate::stringFromColumnIndex($colIndex); + $endCol = \PhpOffice\PhpSpreadsheet\Cell\Coordinate::stringFromColumnIndex($colIndex + 1); + $sheet->mergeCells("{$startCol}{$rowToMerge}:{$endCol}{$rowToMerge}"); + $colIndex += 2; + } + + // Merge "Jumlah" header across 2 columns (Bil & RM) + $startCol = \PhpOffice\PhpSpreadsheet\Cell\Coordinate::stringFromColumnIndex($colIndex); + $endCol = \PhpOffice\PhpSpreadsheet\Cell\Coordinate::stringFromColumnIndex($colIndex + 1); + $sheet->mergeCells("{$startCol}{$rowToMerge}:{$endCol}{$rowToMerge}"); + }, + ]; + } + + + + + + + // Mulakan sel untuk data bermula dari A4 (Baris 3 adalah header) + public function startCell(): string + { + return 'A3'; // Data bermula dari baris 4 + } +} diff --git a/app/Http/Controllers/Reports/AgingController.php b/app/Http/Controllers/Reports/AgingController.php new file mode 100644 index 0000000..b74b5cc --- /dev/null +++ b/app/Http/Controllers/Reports/AgingController.php @@ -0,0 +1,84 @@ +hostname = config('api.url'); + // dd($request->hostname ); + $kod_cawangan = $request->kod_cawangan; + $action = $request->input('action', 'search'); + // dd($action); + + $getReportDate = function ($date_string) use ($current) { + if ($date_string == null) { + return $current->toDateString(); + } + + return $date_string; + }; + + $request->hostname = config('api.url'); + + $aging = Http::get($request->hostname . '/api/reports/aging', [ + 'endDate' => $getReportDate($request->endDate), + ])->json(); + + $endDate = $getReportDate($request->endDate); + + if ($action === 'excel') { + $file_title = sprintf("LaporanAging(%s).xlsx", $kod_cawangan, $request->endDate); + return Excel::download(new AgingAllExportExcel($aging), $file_title); + } + + $aging = $aging ?? []; + + return view('reports.aging.index', compact('aging', 'endDate')); + } + + public function show(Request $request) +{ + $current = Carbon::now(); + $action = $request->input('action', 'search'); + + $getReportDate = function ($date_string) use ($current) { + return $date_string ? $date_string : $current->toDateString(); + }; + + $hostname = config('api.url'); + + $response = Http::get("$hostname/api/reports/aging", [ + 'endDate' => $getReportDate($request->endDate), + ]); + + $aging = $response->json() ?? []; // Ensure it's an array + + // Debugging: Check the response before using it + if (empty($aging)) { + return back()->with('error', 'Failed to fetch data from API.'); + } + + $endDate = $getReportDate($request->endDate); + + if ($action === 'excel') { + // Ensure $kod_cawangan is defined (Modify as per your data structure) + $kod_cawangan = $request->input('kod_cawangan', 'DEFAULT'); + + $file_title = sprintf("LaporanAging(%s).xlsx", $kod_cawangan, $endDate); + return Excel::download(new AgingAllExportExcel($aging), $file_title); + } + return view('reports.aging.index', compact('aging', 'endDate')); +} +} diff --git a/resources/views/indexOverallReport.blade.php b/resources/views/indexOverallReport.blade.php index aaf134f..1d2b3bf 100644 --- a/resources/views/indexOverallReport.blade.php +++ b/resources/views/indexOverallReport.blade.php @@ -49,6 +49,12 @@

Laporan Lelongan

+
+ +

Laporan Aging

+
+
diff --git a/resources/views/reports/aging/index.blade.php b/resources/views/reports/aging/index.blade.php new file mode 100644 index 0000000..930987e --- /dev/null +++ b/resources/views/reports/aging/index.blade.php @@ -0,0 +1,158 @@ +@extends('layouts.app') + +@section('content') + +
+
+ +
+ + + + +
+
+
+
+ + + + Laporan Aging +
+ +
+ +
+
+ +
+ + + + + + + +
+
+ +
+
+
+
+
+ +
+
+ + +
+
+ + +
+
+ +
+ + @if(empty($aging)) +
+ Tiada data dijumpai untuk tarikh {{ $endDate }}. +
+ @else + + +
+ + + + + + + @foreach ($aging[0]['summary_by_tempoh'] as $summary) + + @endforeach + + + + + + @foreach ($aging[0]['summary_by_tempoh'] as $summary) + + + @endforeach + + + + + + + @php + $counter = 1; // Initialize counter + $totalGrandCountByTempoh = array_fill(0, count($aging[0]['summary_by_tempoh']), 0); + $totalGrandBakipjmByTempoh = array_fill(0, count($aging[0]['summary_by_tempoh']), 0); + @endphp + @foreach ($aging as $branch) + @php + $totalCount = 0; + $totalBakipjm = 0; + @endphp + + + + @foreach ($branch['summary_by_tempoh'] as $index => $summary) + + + + @php + $totalCount += $summary['count']; // Summing up the count + $totalBakipjm += $summary['sum_bakipjm']; // Summing up the Bakipjm + + // Adding values to grand totals for each tempoh + $totalGrandCountByTempoh[$index] += $summary['count']; + $totalGrandBakipjmByTempoh[$index] += $summary['sum_bakipjm']; + @endphp + @endforeach + + + + @endforeach + + + + + + @foreach ($totalGrandCountByTempoh as $index => $grandCount) + + + @endforeach + + + + +
Bil. Cawangan{{ $summary['label'] }} Keseluruhan
Bil RM BilRM
{{ $counter++ }} {{ $branch['cawangan'] }}{{ $summary['count'] }} {{ number_format($summary['sum_bakipjm'], 2) }} {{ $totalCount }} {{ number_format($totalBakipjm , 2) }}
Total{{ $grandCount }} {{ number_format($totalGrandBakipjmByTempoh[$index], 2) }} {{ array_sum($totalGrandCountByTempoh) }} {{ number_format(array_sum($totalGrandBakipjmByTempoh), 2) }}
+
+ + @endif +
+
+
+ @include('layouts.footer') + +
+@endsection + + + diff --git a/routes/reports.php b/routes/reports.php index 76a5efe..56c6e9b 100644 --- a/routes/reports.php +++ b/routes/reports.php @@ -6,6 +6,7 @@ use App\Http\Controllers\Reports\AnsuranController; use App\Http\Controllers\Reports\RingkasanHarianController; use App\Http\Controllers\Reports\StokAuditController; use App\Http\Controllers\Reports\LelonganController; +use App\Http\Controllers\Reports\AgingController; use Illuminate\Support\Facades\Route; Route::middleware(['roleChecker:admin,akaun,operasi,kpo, null'])->group(function () { @@ -24,4 +25,6 @@ Route::middleware(['roleChecker:admin,akaun,operasi,kpo, null'])->group(function Route::get('lelongan/{kod_cawangan}', [LelonganController::class, 'downloadLelonganCawanganExcel'])->name('reports.lelongan.cawangan.excel'); Route::get('laporan-lelong/view', [LelonganController::class, 'show'])->name('reports.lelongan.show'); Route::get('laporan-ansuran/view', [AnsuranController::class, 'show'])->name('reports.ansuran.show'); + Route::get('aging/view', [AgingController::class, 'index'])->name('reports.aging.index'); + Route::get('laporan-aging/view', [AgingController::class, 'show'])->name('reports.aging.show'); });