<?php

declare(strict_types=1);

/**
 * DentalCare v0.6.2 workflow enforcement helpers.
 *
 * These helpers keep the 360-stabilization work visible in the actual role
 * screens. They avoid destructive data changes and are safe on mixed-version
 * installs: if a caller cannot provide a field, the helper renders a readable
 * guard instead of throwing.
 */

if (!function_exists('dentalcare_v062_enforcement_items')) {
    function dentalcare_v062_enforcement_items(): array
    {
        return [
            'reception_modes' => [
                'area' => 'Reception intake mode lock',
                'enforces' => 'Booked appointment, online request, and walk-in intake must start from different actions and preserve their context until queue handoff.',
            ],
            'clinical_next_step' => [
                'area' => 'Dentist chairside next-step rail',
                'enforces' => 'The clinical workspace must identify the next missing step and move the Dentist there without page jump or guesswork.',
            ],
            'assistant_scope' => [
                'area' => 'Dental Assistant scope guard',
                'enforces' => 'Assistant work is support-only: vitals, media, materials, support notes, and delegated entries; Dentist-only final decisions stay protected.',
            ],
            'cashier_lock' => [
                'area' => 'Cashier POS transaction lock',
                'enforces' => 'A cashier with an active transaction must complete, cancel, or safely return the visit before leaving or switching patients.',
            ],
            'zero_balance' => [
                'area' => 'Zero-balance checkout reason',
                'enforces' => 'A zero-total visit must show why no payment is due; missing prices are blocked and returned for correction, not treated as free service.',
            ],
            'role_navigation' => [
                'area' => 'Role navigation visibility',
                'enforces' => 'Visible workflow links must be audited against role permissions and expected package routes before sell-ready sign-off.',
            ],
        ];
    }
}

if (!function_exists('dentalcare_render_reception_enforcement_panel')) {
    function dentalcare_render_reception_enforcement_panel(bool $canIntake): void
    {
        if (!$canIntake) return;
        ?>
        <section class="card v062-enforcement-panel reception-mode-enforcer" aria-label="Reception workflow enforcement">
            <div class="card-head">
                <div><span class="eyebrow">0.6.2 enforced flow</span><h2>Reception intake is mode-locked</h2><p>Choose the intake path first. The form now explains what it is allowed to do before the patient is added to the queue.</p></div>
                <span class="badge success">Flow enforced</span>
            </div>
            <div class="v062-rule-grid">
                <article><strong>Book appointment</strong><span>Future scheduling only. Do not check in from this path.</span></article>
                <article><strong>Approve online request</strong><span>Confirm or reschedule public requests before they become clinic appointments.</span></article>
                <article><strong>Check in appointment</strong><span>Requires a confirmed appointment scheduled for today.</span></article>
                <article><strong>Check in walk-in</strong><span>No appointment is required. Search an existing patient or quick-register.</span></article>
            </div>
        </section>
        <?php
    }
}

if (!function_exists('dentalcare_render_clinical_enforcement_rail')) {
    function dentalcare_render_clinical_enforcement_rail(array $items, bool $canWrite, bool $isAssistant): void
    {
        $total = count($items);
        $done = 0;
        $firstMissing = null;
        foreach ($items as $item) {
            if (!empty($item['ready'])) $done++;
            elseif ($firstMissing === null) $firstMissing = $item;
        }
        $percent = $total ? (int)round(($done / $total) * 100) : 0;
        ?>
        <section class="card v062-enforcement-panel clinical-enforcement-rail" data-v062-clinical-enforcement aria-label="Clinical workflow enforcement rail">
            <div class="card-head">
                <div>
                    <span class="eyebrow">0.6.2 chairside enforcement</span>
                    <h2><?= $isAssistant ? 'Assistant support boundary' : 'Dentist next-step rail' ?></h2>
                    <p><?= $isAssistant ? 'Support tasks stay inside this assigned encounter. Final diagnosis, prescription, discharge, and billing release remain Dentist-only.' : 'The record cannot be treated as complete until every clinical and cashier handoff requirement is satisfied.' ?></p>
                </div>
                <span class="badge <?= $done === $total ? 'success' : 'warning' ?>" data-v062-clinical-percent><?= (int)$done ?> / <?= (int)$total ?> ready</span>
            </div>
            <?php if ($firstMissing): ?><div class="alert warning compact-alert"><strong>Next required:</strong> <?= e((string)$firstMissing['label']) ?> — <?= e((string)($firstMissing['hint'] ?? 'Complete this section before finalizing.')) ?></div><?php endif; ?>
            <ol class="v062-enforcement-steps" style="--v062-progress:<?= (int)$percent ?>%">
                <?php foreach ($items as $item): $ready = !empty($item['ready']); ?>
                    <li class="<?= $ready ? 'complete' : 'missing' ?>" data-v062-step="<?= e((string)($item['key'] ?? 'step')) ?>" data-target-check-item="<?= e((string)($item['check'] ?? $item['key'] ?? '')) ?>">
                        <span><?= $ready ? '✓' : '!' ?></span>
                        <div><strong><?= e((string)$item['label']) ?></strong><small><?= e((string)($item['hint'] ?? ($ready ? 'Ready' : 'Needs completion'))) ?></small></div>
                    </li>
                <?php endforeach; ?>
            </ol>
            <?php if ($canWrite): ?><div class="status-actions"><button class="btn primary" type="button" data-next-clinical-required>Go to next missing item <kbd>Alt+N</kbd></button><button class="btn ghost" type="button" data-open="assistant-assignment-form">Assistant decision</button></div><?php endif; ?>
        </section>
        <?php
    }
}

if (!function_exists('dentalcare_cashier_item_source_label')) {
    function dentalcare_cashier_item_source_label(array $item): string
    {
        $source = (string)($item['source_type'] ?? '');
        return match ($source) {
            'procedure' => 'Dentist procedure',
            'clinical_usage' => 'Clinical material/medicine',
            'service' => 'Service catalogue',
            'retail_product' => 'Retail product',
            'manual' => 'Manual authorized charge',
            'existing_invoice' => 'Existing account balance',
            default => $source !== '' ? ucwords(str_replace('_', ' ', $source)) : 'Invoice item',
        };
    }
}

if (!function_exists('dentalcare_render_cashier_enforcement_panel')) {
    function dentalcare_render_cashier_enforcement_panel(?array $selectedPatient, ?array $selectedInvoice, array $selectedItems, ?array $selectedQueue, string $completionMode, bool $transactionActive): void
    {
        if (!$selectedPatient) return;
        $patientName = trim((string)($selectedPatient['first_name'] ?? '') . ' ' . (string)($selectedPatient['last_name'] ?? '')) ?: 'Selected patient';
        $itemTotal = 0.0;
        foreach ($selectedItems as $item) $itemTotal += (float)($item['gross_amount'] ?? $item['unit_price'] ?? 0);
        ?>
        <details class="card cashier-enforcement-compact" aria-label="Cashier register rules">
            <summary><span><strong>Focused transaction rules</strong><small><?= e($patientName) ?><?= !empty($selectedPatient['patient_no']) ? ' · ' . e((string)$selectedPatient['patient_no']) : '' ?> · payment references, itemized receipt, and fee controls</small></span><span class="badge <?= $transactionActive ? 'warning' : 'success' ?>"><?= $transactionActive ? 'Locked' : 'Ready' ?></span></summary>
            <?php if ($transactionActive): ?><div class="alert warning compact-alert"><strong>Patient focus is active.</strong> Complete or cancel this transaction before switching accounts.</div><?php endif; ?>
            <div class="v062-rule-grid cashier-rules">
                <article><strong>Payment reference</strong><span>Required for card, GCash, Maya, bank, cheque, mixed, and digital payments.</span></article>
                <article><strong>Itemized receipt</strong><span>Shows procedures, materials, clinic services, and retail products.</span></article>
                <article><strong>Zero balance</strong><span><?= $completionMode === 'zero_charge' ? 'Allowed only with a documented reason.' : 'Available only when the system confirms no patient amount is due.' ?></span></article>
                <article><strong>Missing fees</strong><span>Return to Dentist or Administrator. Cashier cannot invent a clinical fee.</span></article>
            </div>
            <?php if ($selectedInvoice): ?><p class="muted compact-summary"><?= count($selectedItems) ?> itemized line<?= count($selectedItems) === 1 ? '' : 's' ?> · displayed total ₱<?= number_format($itemTotal, 2) ?>.</p><?php endif; ?>
        </details>
        <?php
    }
}

if (!function_exists('dentalcare_render_v062_release_gate')) {
    function dentalcare_render_v062_release_gate(): void
    {
        ?>
        <section class="card v062-enforcement-panel"><div class="card-head"><div><span class="eyebrow">0.6.2 360 enforcement</span><h2>Sell-readiness now requires enforced workflows</h2><p>These are the 360 weaknesses converted into browser-testable controls inside the live role screens.</p></div><span class="badge warning">Pilot until passed</span></div>
        <div class="v062-rule-grid"><?php foreach (dentalcare_v062_enforcement_items() as $item): ?><article><strong><?= e((string)$item['area']) ?></strong><span><?= e((string)$item['enforces']) ?></span></article><?php endforeach; ?></div></section>
        <?php
    }
}
