Files
2026-06-13 16:03:15 +07:00

345 lines
11 KiB
PHP

<?php
require_once(APPPATH . 'third_party/fpdf/fpdf.php');
class PDF extends FPDF
{
// ----------------------------------------------------------------
// PROPERTI HEADER
// ----------------------------------------------------------------
private $nama;
private $alamat;
private $logo;
private $periodeStr = '';
// ----------------------------------------------------------------
// KONFIGURASI TABEL
// ----------------------------------------------------------------
// A4 Portrait efektif = 190mm, margin 10+10
// Kolom: Kode 20 | Nama Akun 120 | Saldo 50 → TOTAL 190
private $colWidths = [20, 120, 50];
// ----------------------------------------------------------------
// SETTER
// ----------------------------------------------------------------
public function setHeaderData($nama, $alamat, $logo = '')
{
$this->nama = $nama;
$this->alamat = $alamat;
$this->logo = $logo;
}
public function setInfoLaporan($periodeStr)
{
$this->periodeStr = $periodeStr;
}
// ----------------------------------------------------------------
// HEADER HALAMAN
// ----------------------------------------------------------------
function Header()
{
// Logo (opsional)
if (!empty($this->logo) && file_exists($this->logo)) {
$this->Image($this->logo, 10, 6, 18);
$this->SetXY(31, 10);
} else {
$this->SetXY(10, 10);
}
// Nama perusahaan
$this->SetFont('Arial', 'B', 12);
$this->Cell(0, 6, $this->nama, 0, 1, 'L');
// Alamat
$this->SetFont('Arial', '', 9);
$x = !empty($this->logo) && file_exists($this->logo) ? 31 : 10;
$this->SetX($x);
$this->Cell(0, 5, $this->alamat, 0, 1, 'L');
// Garis pemisah (A4 Portrait: x=10 s/d x=200)
$this->Ln(2);
$this->SetLineWidth(0.6);
$this->Line(10, $this->GetY(), 200, $this->GetY());
$this->SetLineWidth(0.2);
$this->Line(10, $this->GetY() + 1, 200, $this->GetY() + 1);
$this->Ln(5);
// Judul
$this->SetFont('Arial', 'B', 13);
$this->SetTextColor(245, 140, 0);
$this->Cell(0, 7, 'LAPORAN LABA RUGI', 0, 1, 'C');
$this->SetTextColor(0, 0, 0);
// Periode
$this->SetFont('Arial', '', 10);
$this->Cell(0, 5, $this->periodeStr, 0, 1, 'C');
// Tanggal cetak
$this->SetFont('Arial', '', 9);
$this->Cell(0, 5, 'Di Cetak Pada : ' . date('d-m-Y') . ' Jam ' . date('H:i:s'), 0, 1, 'C');
$this->Ln(4);
// Header kolom tabel
$this->_drawTableHeader();
}
// ----------------------------------------------------------------
// FOOTER HALAMAN
// ----------------------------------------------------------------
function Footer()
{
$this->SetY(-10);
$this->SetFont('Arial', 'I', 8);
$this->Cell(0, 5, 'Halaman ' . $this->PageNo(), 0, 0, 'C');
}
// ----------------------------------------------------------------
// HELPER: posisi X awal — TABEL RATA TENGAH KERTAS
// ----------------------------------------------------------------
private function _startX()
{
$tableW = array_sum($this->colWidths);
return ($this->GetPageWidth() - $tableW) / 2;
}
// ----------------------------------------------------------------
// HELPER: Gambar header kolom tabel
// ----------------------------------------------------------------
private function _drawTableHeader()
{
$startX = $this->_startX();
$this->SetX($startX);
$this->SetFillColor(245, 140, 0);
$this->SetTextColor(255, 255, 255);
$this->SetFont('Arial', 'B', 9);
$this->Cell($this->colWidths[0], 8, 'Kode', 1, 0, 'C', true);
$this->Cell($this->colWidths[1], 8, 'Nama Akun', 1, 0, 'C', true);
$this->Cell($this->colWidths[2], 8, 'Saldo', 1, 1, 'C', true);
$this->SetTextColor(0, 0, 0);
}
// ----------------------------------------------------------------
// HELPER: Gambar baris judul section (PENDAPATAN / BEBAN)
// ----------------------------------------------------------------
private function _drawSectionTitle($title)
{
if ($this->GetY() + 8 > 270) {
$this->AddPage('P', 'A4');
}
$startX = $this->_startX();
$tableW = array_sum($this->colWidths);
$this->SetX($startX);
$this->SetFillColor(255, 224, 178);
$this->SetFont('Arial', 'B', 9);
$this->Cell($tableW, 7, $title, 1, 1, 'L', true);
}
// ----------------------------------------------------------------
// HELPER: Gambar baris detail akun (dengan dukungan multiline Nama Akun)
// ----------------------------------------------------------------
private function _drawRow($kode, $namaAkun, $saldo)
{
$lineH = 6;
$nbLines = $this->NbLines($this->colWidths[1], $namaAkun);
$rowH = max(1, $nbLines) * $lineH;
if ($this->GetY() + $rowH > 270) {
$this->AddPage('P', 'A4');
}
$startX = $this->_startX();
$y = $this->GetY();
$this->SetFont('Arial', '', 9);
$this->SetXY($startX, $y);
$this->Cell($this->colWidths[0], $rowH, $kode, 1, 0, 'C');
$xNama = $this->GetX();
$this->MultiCell($this->colWidths[1], $lineH, $namaAkun, 1, 'L');
$this->SetXY($xNama + $this->colWidths[1], $y);
$this->Cell($this->colWidths[2], $rowH, number_format($saldo, 0, ',', '.'), 1, 0, 'R');
$this->SetXY($startX, $y + $rowH);
}
// ----------------------------------------------------------------
// HELPER: Gambar baris total section
// ----------------------------------------------------------------
private function _drawSectionTotal($label, $total)
{
if ($this->GetY() + 7 > 270) {
$this->AddPage('P', 'A4');
}
$startX = $this->_startX();
$this->SetX($startX);
$this->SetFillColor(255, 224, 178);
$this->SetFont('Arial', 'B', 9);
$this->Cell($this->colWidths[0] + $this->colWidths[1], 7, $label, 1, 0, 'L', true);
$this->Cell($this->colWidths[2], 7, number_format($total, 0, ',', '.'), 1, 1, 'R', true);
}
// ----------------------------------------------------------------
// TABEL LABA RUGI (PENDAPATAN, BEBAN, masing-masing dengan rincian akun)
// ----------------------------------------------------------------
public function LabaRugiTable($pendapatan, $beban, $totalPendapatan, $totalBeban)
{
// ---- SECTION PENDAPATAN ----
$this->_drawSectionTitle('PENDAPATAN');
if (empty($pendapatan)) {
$this->_drawRow('-', 'Tidak ada data', 0);
} else {
foreach ($pendapatan as $row) {
$this->_drawRow($row['kode'], $row['nama'], $row['saldo']);
}
}
$this->_drawSectionTotal('TOTAL PENDAPATAN', $totalPendapatan);
// ---- SECTION BEBAN ----
$this->AddPage('P', 'A4');
$this->_drawSectionTitle('BEBAN');
if (empty($beban)) {
$this->_drawRow('-', 'Tidak ada data', 0);
} else {
foreach ($beban as $row) {
$this->_drawRow($row['kode'], $row['nama'], $row['saldo']);
}
}
$this->_drawSectionTotal('TOTAL BEBAN', $totalBeban);
}
// ----------------------------------------------------------------
// RINGKASAN: LABA / RUGI BERSIH
// ----------------------------------------------------------------
public function LabaRugiRingkasan($laba)
{
if ($this->GetY() + 9 > 270) {
$this->AddPage('P', 'A4');
}
$startX = $this->_startX();
$tableW = array_sum($this->colWidths);
$labelW = $tableW - $this->colWidths[2];
$this->Ln(2);
$this->SetX($startX);
$this->SetFont('Arial', 'B', 10);
if ($laba >= 0) {
$this->SetFillColor(198, 239, 206); // hijau, laba
$label = 'LABA BERSIH';
} else {
$this->SetFillColor(255, 199, 206); // merah, rugi
$label = 'RUGI BERSIH';
}
$this->Cell($labelW, 8, $label, 1, 0, 'L', true);
$this->Cell($this->colWidths[2], 8, number_format($laba, 0, ',', '.'), 1, 1, 'R', true);
}
// ----------------------------------------------------------------
// TANDA TANGAN
// ----------------------------------------------------------------
public function Pembuat($nama, $jabatan = '')
{
$startX = $this->_startX();
$tableW = array_sum($this->colWidths);
$signWidth = 70;
$signX = $startX + $tableW - $signWidth; // sejajar sisi kanan tabel
$this->Ln(10);
$this->SetX($signX);
$this->SetFont('Arial', '', 10);
$this->Cell($signWidth, 6, 'Mengetahui,', 0, 1, 'R');
$this->Ln(10);
$this->SetX($signX);
$this->SetFont('Arial', 'B', 10);
$this->Cell($signWidth, 6, $nama, 0, 1, 'R');
if (!empty($jabatan)) {
$this->SetX($signX);
$this->SetFont('Arial', '', 9);
$this->Cell($signWidth, 5, '(' . $jabatan . ')', 0, 1, 'R');
}
}
// ----------------------------------------------------------------
// HELPER: Hitung jumlah baris yang dibutuhkan MultiCell
// ----------------------------------------------------------------
private function NbLines($w, $txt)
{
$cw = &$this->CurrentFont['cw'];
if ($w == 0) {
$w = $this->w - $this->rMargin - $this->x;
}
$wmax = ($w - 2 * $this->cMargin) * 1000 / $this->FontSize;
$s = str_replace("\r", '', $txt);
$nb = strlen($s);
if ($nb > 0 && $s[$nb - 1] == "\n") {
$nb--;
}
$sep = -1;
$i = 0;
$j = 0;
$l = 0;
$nl = 1;
while ($i < $nb) {
$c = $s[$i];
if ($c == "\n") {
$i++;
$sep = -1;
$j = $i;
$l = 0;
$nl++;
continue;
}
if ($c == ' ') {
$sep = $i;
}
$l += isset($cw[ord($c)]) ? $cw[ord($c)] : 600;
if ($l > $wmax) {
if ($sep == -1) {
if ($i == $j) {
$i++;
}
} else {
$i = $sep + 1;
}
$sep = -1;
$j = $i;
$l = 0;
$nl++;
} else {
$i++;
}
}
return $nl;
}
}