Add full Radiology, Cardiology, and Psychiatry specialty clinical suites.
Deploy Ladill Care / deploy (push) Successful in 49s
Deploy Ladill Care / deploy (push) Successful in 49s
Mirror the Ophthalmology/Maternity shell pattern with stages, stage_tabs, workspace clinical records, reports/print, demo seeds, and suite tests. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -0,0 +1,89 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Cardiology summary · {{ $patient->fullName() }}</title>
|
||||
<style>
|
||||
body { font-family: system-ui, sans-serif; color: #0f172a; margin: 2rem; }
|
||||
h1 { font-size: 1.25rem; margin: 0 0 .25rem; }
|
||||
h2 { font-size: .95rem; margin: 1.25rem 0 .5rem; border-bottom: 1px solid #e2e8f0; padding-bottom: .25rem; }
|
||||
.meta { color: #64748b; font-size: .875rem; }
|
||||
dl { display: grid; grid-template-columns: 10rem 1fr; gap: .35rem .75rem; font-size: .875rem; }
|
||||
dt { color: #64748b; }
|
||||
dd { margin: 0; font-weight: 500; }
|
||||
@media print { .no-print { display: none; } }
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<p class="no-print"><a href="{{ route('care.specialty.workspace', ['module' => 'cardiology', 'visit' => $visit]) }}">Back</a></p>
|
||||
|
||||
<h1>{{ $patient->fullName() }}</h1>
|
||||
<p class="meta">
|
||||
{{ $patient->patient_number }}
|
||||
· Visit #{{ $visit->id }}
|
||||
· Stage {{ $visit->specialty_stage ?? '—' }}
|
||||
· {{ $visit->checked_in_at?->format('d M Y H:i') ?? '—' }}
|
||||
</p>
|
||||
|
||||
<h2>History</h2>
|
||||
@if ($history)
|
||||
<dl>
|
||||
<dt>HPI</dt><dd>{{ $history->payload['history'] ?? '—' }}</dd>
|
||||
<dt>Past cardiac</dt><dd>{{ $history->payload['past_cardiac'] ?? '—' }}</dd>
|
||||
<dt>Risk factors</dt><dd>{{ $history->payload['risk_factors'] ?? '—' }}</dd>
|
||||
<dt>Medications</dt><dd>{{ $history->payload['medications'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No history recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Exam / ECG</h2>
|
||||
@if ($exam)
|
||||
<dl>
|
||||
<dt>Complaint</dt><dd>{{ $exam->payload['chief_complaint'] ?? '—' }}</dd>
|
||||
<dt>NYHA</dt><dd>{{ $exam->payload['nyha_class'] ?? '—' }}</dd>
|
||||
<dt>BP / HR</dt><dd>{{ $exam->payload['bp'] ?? '—' }} · {{ $exam->payload['hr'] ?? '—' }}</dd>
|
||||
<dt>ECG</dt><dd>{{ $exam->payload['ecg_findings'] ?? '—' }}</dd>
|
||||
<dt>Exam</dt><dd>{{ $exam->payload['exam_findings'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No exam recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Investigations</h2>
|
||||
@if ($investigation)
|
||||
<dl>
|
||||
<dt>Investigation</dt><dd>{{ $investigation->payload['modality'] ?? '—' }}</dd>
|
||||
<dt>Findings</dt><dd>{{ $investigation->payload['findings'] ?? '—' }}</dd>
|
||||
<dt>Impression</dt><dd>{{ $investigation->payload['impression'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No investigation recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Diagnosis & plan</h2>
|
||||
@if ($plan)
|
||||
<dl>
|
||||
<dt>Diagnosis</dt><dd>{{ $plan->payload['diagnosis'] ?? '—' }}</dd>
|
||||
<dt>Plan</dt><dd>{{ $plan->payload['plan'] ?? '—' }}</dd>
|
||||
<dt>Medications</dt><dd>{{ $plan->payload['medications'] ?? '—' }}</dd>
|
||||
<dt>Follow-up</dt><dd>{{ $plan->payload['follow_up'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No plan recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Procedure</h2>
|
||||
@if ($procedure)
|
||||
<dl>
|
||||
<dt>Procedure</dt><dd>{{ $procedure->payload['procedure'] ?? '—' }}</dd>
|
||||
<dt>Outcome</dt><dd>{{ $procedure->payload['outcome'] ?? '—' }}</dd>
|
||||
<dt>Plan</dt><dd>{{ $procedure->payload['post_procedure_plan'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No procedure recorded.</p>
|
||||
@endif
|
||||
|
||||
<script>window.print();</script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,88 @@
|
||||
<x-app-layout title="Cardiology reports">
|
||||
<div class="space-y-6">
|
||||
<div class="flex flex-wrap items-center justify-between gap-3">
|
||||
<div>
|
||||
<h1 class="text-xl font-semibold text-slate-900">Cardiology reports</h1>
|
||||
<p class="mt-1 text-sm text-slate-500">Arrivals, NYHA III–IV open cases, diagnoses, procedures, length of stay, and cardiology revenue.</p>
|
||||
</div>
|
||||
<a href="{{ route('care.specialty.show', 'cardiology') }}" class="text-sm font-medium text-indigo-600">← Specialty home</a>
|
||||
</div>
|
||||
|
||||
<form method="GET" class="flex flex-wrap items-end gap-3 rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<div>
|
||||
<label class="block text-xs font-medium text-slate-600">From</label>
|
||||
<input type="date" name="from" value="{{ $report['from'] ?? '' }}" class="mt-1 rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
</div>
|
||||
<div>
|
||||
<label class="block text-xs font-medium text-slate-600">To</label>
|
||||
<input type="date" name="to" value="{{ $report['to'] ?? '' }}" class="mt-1 rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
</div>
|
||||
<button type="submit" class="rounded-xl bg-indigo-600 px-4 py-2 text-sm font-semibold text-white">Apply</button>
|
||||
</form>
|
||||
|
||||
<div class="grid gap-4 sm:grid-cols-4">
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Arrivals today</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">{{ number_format($report['arrivals_today']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Completed today</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">{{ number_format($report['completed_today']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">NYHA III–IV open</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-rose-700">{{ number_format($report['high_risk_open']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Avg LOS (range)</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">
|
||||
{{ $report['avg_los_minutes'] !== null ? $report['avg_los_minutes'].' min' : '—' }}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="grid gap-4 lg:grid-cols-2">
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Diagnoses</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['diagnosis_breakdown'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row['diagnosis'] }}</span>
|
||||
<span class="tabular-nums text-slate-600">{{ $row['total'] }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No care plans in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Procedures</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['procedure_breakdown'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row['procedure'] }}</span>
|
||||
<span class="tabular-nums text-slate-600">{{ $row['total'] }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No procedures in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
</div>
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Cardiology service revenue</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['revenue_by_service'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row->description }} <span class="text-slate-400">×{{ $row->total }}</span></span>
|
||||
<span class="tabular-nums">{{ $currency }} {{ number_format($row->amount_minor / 100, 2) }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No billed cardiology services in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
</div>
|
||||
</x-app-layout>
|
||||
@@ -0,0 +1,71 @@
|
||||
@php
|
||||
$hist = $cardiologyHistory?->payload ?? [];
|
||||
$exam = $cardiologyExam?->payload ?? [];
|
||||
$plan = $cardiologyPlan?->payload ?? [];
|
||||
@endphp
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<div class="flex flex-wrap items-start justify-between gap-3">
|
||||
<div>
|
||||
<h3 class="text-sm font-semibold text-slate-900">Cardiology overview</h3>
|
||||
<p class="mt-0.5 text-xs text-slate-500">History, exam / ECG, investigations, and care plan for this episode.</p>
|
||||
</div>
|
||||
<div class="flex flex-wrap gap-3 text-sm">
|
||||
<a href="{{ route('care.specialty.cardiology.print', $workspaceVisit) }}" target="_blank" class="font-medium text-indigo-600">Print summary</a>
|
||||
<a href="{{ route('care.specialty.cardiology.reports') }}" class="font-medium text-indigo-600">Cardiology reports</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="mt-4 grid gap-3 sm:grid-cols-3">
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Complaint</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">{{ $exam['chief_complaint'] ?? '—' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">NYHA {{ $exam['nyha_class'] ?? '—' }}</p>
|
||||
</div>
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Vitals / ECG</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">BP {{ $exam['bp'] ?? '—' }} · HR {{ $exam['hr'] ?? '—' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">{{ \Illuminate\Support\Str::limit($exam['ecg_findings'] ?? '—', 50) }}</p>
|
||||
</div>
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Diagnosis / plan</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">{{ $plan['diagnosis'] ?? 'Not set' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">{{ $plan['follow_up'] ?? '—' }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<dl class="mt-4 grid gap-3 text-sm sm:grid-cols-2">
|
||||
<div>
|
||||
<dt class="text-slate-500">History</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $hist['history'] ?? '—' }}</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Plan</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $plan['plan'] ?? '—' }}</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Queue</dt>
|
||||
<dd class="font-medium text-slate-900">
|
||||
{{ $workspaceVisit->appointment?->queue_ticket_number ?? '—' }}
|
||||
@if ($workspaceVisit->appointment?->queue_ticket_status)
|
||||
<span class="text-slate-500">({{ $workspaceVisit->appointment->queue_ticket_status }})</span>
|
||||
@endif
|
||||
</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Checked in</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $workspaceVisit->checked_in_at?->format('d M Y H:i') ?? '—' }}</dd>
|
||||
</div>
|
||||
</dl>
|
||||
|
||||
@if (! empty($clinicalAlerts))
|
||||
<div class="mt-4 space-y-1.5 border-t border-slate-100 pt-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Alerts</p>
|
||||
@foreach ($clinicalAlerts as $alert)
|
||||
<p class="text-sm {{ ($alert['severity'] ?? '') === 'critical' ? 'text-rose-700' : 'text-amber-800' }}">
|
||||
{{ $alert['message'] ?? '' }}
|
||||
</p>
|
||||
@endforeach
|
||||
</div>
|
||||
@endif
|
||||
</section>
|
||||
@@ -0,0 +1,70 @@
|
||||
@php
|
||||
$record = $cardiologyProcedure;
|
||||
$payload = $record?->payload ?? [];
|
||||
$canManage = $canManageClinical ?? $canConsult ?? false;
|
||||
@endphp
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<div class="flex flex-wrap items-start justify-between gap-3">
|
||||
<div>
|
||||
<h3 class="text-sm font-semibold text-slate-900">Procedure / intervention</h3>
|
||||
<p class="mt-0.5 text-xs text-slate-500">Completed interventions can close the cardiology visit.</p>
|
||||
</div>
|
||||
<a href="{{ route('care.specialty.cardiology.print', $workspaceVisit) }}" target="_blank" class="text-sm font-medium text-indigo-600">Print summary</a>
|
||||
</div>
|
||||
|
||||
@if ($canManage)
|
||||
<form method="POST" action="{{ route('care.specialty.cardiology.procedure', $workspaceVisit) }}" class="mt-4 space-y-4">
|
||||
@csrf
|
||||
<input type="hidden" name="tab" value="procedures">
|
||||
<div class="grid gap-3 sm:grid-cols-2">
|
||||
@foreach ($clinicalFields ?? [] as $field)
|
||||
@php
|
||||
$name = $field['name'];
|
||||
$value = old('payload.'.$name, $payload[$name] ?? '');
|
||||
$type = $field['type'] ?? 'text';
|
||||
@endphp
|
||||
<div @class(['sm:col-span-2' => in_array($type, ['textarea'], true)])>
|
||||
<label class="block text-xs font-medium text-slate-600">
|
||||
{{ $field['label'] }}
|
||||
@if (! empty($field['required'])) <span class="text-rose-600">*</span> @endif
|
||||
</label>
|
||||
@if ($type === 'textarea')
|
||||
<textarea name="payload[{{ $name }}]" rows="{{ $field['rows'] ?? 3 }}" @required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">{{ $value }}</textarea>
|
||||
@elseif ($type === 'select')
|
||||
<select name="payload[{{ $name }}]" @required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
<option value="">Select…</option>
|
||||
@foreach ($field['options'] ?? [] as $option)
|
||||
<option value="{{ $option }}" @selected((string) $value === (string) $option)>{{ $option }}</option>
|
||||
@endforeach
|
||||
</select>
|
||||
@elseif ($type === 'boolean')
|
||||
<label class="mt-2 inline-flex items-center gap-2 text-sm text-slate-700">
|
||||
<input type="checkbox" name="payload[{{ $name }}]" value="1" @checked(old('payload.'.$name, ! empty($payload[$name])))>
|
||||
Yes
|
||||
</label>
|
||||
@else
|
||||
<input type="{{ $type === 'number' ? 'number' : 'text' }}" name="payload[{{ $name }}]" value="{{ $value }}"
|
||||
@required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
@endif
|
||||
</div>
|
||||
@endforeach
|
||||
</div>
|
||||
<button type="submit" class="btn-primary">Save procedure</button>
|
||||
</form>
|
||||
@elseif ($record)
|
||||
<dl class="mt-4 grid gap-3 text-sm sm:grid-cols-2">
|
||||
@foreach ($clinicalFields ?? [] as $field)
|
||||
<div>
|
||||
<dt class="text-slate-500">{{ $field['label'] }}</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $payload[$field['name']] ?? '—' }}</dd>
|
||||
</div>
|
||||
@endforeach
|
||||
</dl>
|
||||
@else
|
||||
<p class="mt-4 text-sm text-slate-500">No procedure recorded yet.</p>
|
||||
@endif
|
||||
</section>
|
||||
@@ -47,6 +47,9 @@
|
||||
'ophthalmology' => 'check_in',
|
||||
'physiotherapy' => 'check_in',
|
||||
'maternity' => 'check_in',
|
||||
'radiology' => 'check_in',
|
||||
'cardiology' => 'check_in',
|
||||
'psychiatry' => 'check_in',
|
||||
default => collect($stages ?? [])->pluck('code')->first(),
|
||||
};
|
||||
$defaultStartLabel = match ($moduleKey) {
|
||||
@@ -56,6 +59,9 @@
|
||||
'ophthalmology' => 'Start check-in',
|
||||
'physiotherapy' => 'Start check-in',
|
||||
'maternity' => 'Start check-in',
|
||||
'radiology' => 'Start check-in',
|
||||
'cardiology' => 'Start check-in',
|
||||
'psychiatry' => 'Start check-in',
|
||||
default => 'Start',
|
||||
};
|
||||
$currentStage = $workspaceVisit?->specialty_stage;
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Psychiatry summary · {{ $patient->fullName() }}</title>
|
||||
<style>
|
||||
body { font-family: system-ui, sans-serif; color: #0f172a; margin: 2rem; }
|
||||
h1 { font-size: 1.25rem; margin: 0 0 .25rem; }
|
||||
h2 { font-size: .95rem; margin: 1.25rem 0 .5rem; border-bottom: 1px solid #e2e8f0; padding-bottom: .25rem; }
|
||||
.meta { color: #64748b; font-size: .875rem; }
|
||||
dl { display: grid; grid-template-columns: 10rem 1fr; gap: .35rem .75rem; font-size: .875rem; }
|
||||
dt { color: #64748b; }
|
||||
dd { margin: 0; font-weight: 500; }
|
||||
@media print { .no-print { display: none; } }
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<p class="no-print"><a href="{{ route('care.specialty.workspace', ['module' => 'psychiatry', 'visit' => $visit]) }}">Back</a></p>
|
||||
|
||||
<h1>{{ $patient->fullName() }}</h1>
|
||||
<p class="meta">
|
||||
{{ $patient->patient_number }}
|
||||
· Visit #{{ $visit->id }}
|
||||
· Stage {{ $visit->specialty_stage ?? '—' }}
|
||||
· {{ $visit->checked_in_at?->format('d M Y H:i') ?? '—' }}
|
||||
</p>
|
||||
|
||||
<h2>History / MSE</h2>
|
||||
@if ($history)
|
||||
<dl>
|
||||
<dt>Presenting</dt><dd>{{ $history->payload['chief_complaint'] ?? '—' }}</dd>
|
||||
<dt>History</dt><dd>{{ $history->payload['history'] ?? '—' }}</dd>
|
||||
<dt>Mood / affect</dt><dd>{{ $history->payload['mood_affect'] ?? '—' }}</dd>
|
||||
<dt>Thought</dt><dd>{{ $history->payload['thought'] ?? '—' }}</dd>
|
||||
<dt>MSE summary</dt><dd>{{ $history->payload['mse_summary'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No MSE recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Risk assessment</h2>
|
||||
@if ($risk)
|
||||
<dl>
|
||||
<dt>Overall risk</dt><dd>{{ $risk->payload['overall_risk'] ?? '—' }}</dd>
|
||||
<dt>Self-harm</dt><dd>{{ $risk->payload['self_harm'] ?? '—' }}</dd>
|
||||
<dt>Risk to others</dt><dd>{{ $risk->payload['harm_others'] ?? '—' }}</dd>
|
||||
<dt>Summary</dt><dd>{{ $risk->payload['risk_summary'] ?? '—' }}</dd>
|
||||
<dt>Actions</dt><dd>{{ $risk->payload['immediate_actions'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No risk assessment recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Formulation / plan</h2>
|
||||
@if ($plan)
|
||||
<dl>
|
||||
<dt>Formulation</dt><dd>{{ $plan->payload['formulation'] ?? '—' }}</dd>
|
||||
<dt>Diagnosis</dt><dd>{{ $plan->payload['diagnosis'] ?? '—' }}</dd>
|
||||
<dt>Plan</dt><dd>{{ $plan->payload['plan'] ?? '—' }}</dd>
|
||||
<dt>Medications</dt><dd>{{ $plan->payload['medications'] ?? '—' }}</dd>
|
||||
<dt>Follow-up</dt><dd>{{ $plan->payload['follow_up'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No formulation recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Follow-up</h2>
|
||||
@if ($followup)
|
||||
<dl>
|
||||
<dt>Review type</dt><dd>{{ $followup->payload['review_type'] ?? '—' }}</dd>
|
||||
<dt>Progress</dt><dd>{{ $followup->payload['progress'] ?? '—' }}</dd>
|
||||
<dt>Outcome</dt><dd>{{ $followup->payload['outcome'] ?? '—' }}</dd>
|
||||
<dt>Next steps</dt><dd>{{ $followup->payload['next_steps'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No follow-up recorded.</p>
|
||||
@endif
|
||||
|
||||
<script>window.print();</script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,88 @@
|
||||
<x-app-layout title="Psychiatry reports">
|
||||
<div class="space-y-6">
|
||||
<div class="flex flex-wrap items-center justify-between gap-3">
|
||||
<div>
|
||||
<h1 class="text-xl font-semibold text-slate-900">Psychiatry reports</h1>
|
||||
<p class="mt-1 text-sm text-slate-500">Arrivals, high-risk open cases, risk levels, review outcomes, length of stay, and psychiatry revenue.</p>
|
||||
</div>
|
||||
<a href="{{ route('care.specialty.show', 'psychiatry') }}" class="text-sm font-medium text-indigo-600">← Specialty home</a>
|
||||
</div>
|
||||
|
||||
<form method="GET" class="flex flex-wrap items-end gap-3 rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<div>
|
||||
<label class="block text-xs font-medium text-slate-600">From</label>
|
||||
<input type="date" name="from" value="{{ $report['from'] ?? '' }}" class="mt-1 rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
</div>
|
||||
<div>
|
||||
<label class="block text-xs font-medium text-slate-600">To</label>
|
||||
<input type="date" name="to" value="{{ $report['to'] ?? '' }}" class="mt-1 rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
</div>
|
||||
<button type="submit" class="rounded-xl bg-indigo-600 px-4 py-2 text-sm font-semibold text-white">Apply</button>
|
||||
</form>
|
||||
|
||||
<div class="grid gap-4 sm:grid-cols-4">
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Arrivals today</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">{{ number_format($report['arrivals_today']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Completed today</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">{{ number_format($report['completed_today']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">High risk open</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-rose-700">{{ number_format($report['high_risk_open']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Avg LOS (range)</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">
|
||||
{{ $report['avg_los_minutes'] !== null ? $report['avg_los_minutes'].' min' : '—' }}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="grid gap-4 lg:grid-cols-2">
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Risk levels</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['risk_breakdown'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row['risk'] }}</span>
|
||||
<span class="tabular-nums text-slate-600">{{ $row['total'] }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No risk assessments in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Review outcomes</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['review_outcomes'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row['outcome'] }}</span>
|
||||
<span class="tabular-nums text-slate-600">{{ $row['total'] }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No follow-up reviews in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
</div>
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Psychiatry service revenue</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['revenue_by_service'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row->description }} <span class="text-slate-400">×{{ $row->total }}</span></span>
|
||||
<span class="tabular-nums">{{ $currency }} {{ number_format($row->amount_minor / 100, 2) }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No billed psychiatry services in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
</div>
|
||||
</x-app-layout>
|
||||
@@ -0,0 +1,70 @@
|
||||
@php
|
||||
$record = $psychiatryFollowup;
|
||||
$payload = $record?->payload ?? [];
|
||||
$canManage = $canManageClinical ?? $canConsult ?? false;
|
||||
@endphp
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<div class="flex flex-wrap items-start justify-between gap-3">
|
||||
<div>
|
||||
<h3 class="text-sm font-semibold text-slate-900">Follow-up review</h3>
|
||||
<p class="mt-0.5 text-xs text-slate-500">Discharge and follow-up outcomes can close the psychiatry visit.</p>
|
||||
</div>
|
||||
<a href="{{ route('care.specialty.psychiatry.print', $workspaceVisit) }}" target="_blank" class="text-sm font-medium text-indigo-600">Print summary</a>
|
||||
</div>
|
||||
|
||||
@if ($canManage)
|
||||
<form method="POST" action="{{ route('care.specialty.psychiatry.followup', $workspaceVisit) }}" class="mt-4 space-y-4">
|
||||
@csrf
|
||||
<input type="hidden" name="tab" value="followup">
|
||||
<div class="grid gap-3 sm:grid-cols-2">
|
||||
@foreach ($clinicalFields ?? [] as $field)
|
||||
@php
|
||||
$name = $field['name'];
|
||||
$value = old('payload.'.$name, $payload[$name] ?? '');
|
||||
$type = $field['type'] ?? 'text';
|
||||
@endphp
|
||||
<div @class(['sm:col-span-2' => in_array($type, ['textarea'], true)])>
|
||||
<label class="block text-xs font-medium text-slate-600">
|
||||
{{ $field['label'] }}
|
||||
@if (! empty($field['required'])) <span class="text-rose-600">*</span> @endif
|
||||
</label>
|
||||
@if ($type === 'textarea')
|
||||
<textarea name="payload[{{ $name }}]" rows="{{ $field['rows'] ?? 3 }}" @required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">{{ $value }}</textarea>
|
||||
@elseif ($type === 'select')
|
||||
<select name="payload[{{ $name }}]" @required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
<option value="">Select…</option>
|
||||
@foreach ($field['options'] ?? [] as $option)
|
||||
<option value="{{ $option }}" @selected((string) $value === (string) $option)>{{ $option }}</option>
|
||||
@endforeach
|
||||
</select>
|
||||
@elseif ($type === 'boolean')
|
||||
<label class="mt-2 inline-flex items-center gap-2 text-sm text-slate-700">
|
||||
<input type="checkbox" name="payload[{{ $name }}]" value="1" @checked(old('payload.'.$name, ! empty($payload[$name])))>
|
||||
Yes
|
||||
</label>
|
||||
@else
|
||||
<input type="{{ $type === 'number' ? 'number' : 'text' }}" name="payload[{{ $name }}]" value="{{ $value }}"
|
||||
@required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
@endif
|
||||
</div>
|
||||
@endforeach
|
||||
</div>
|
||||
<button type="submit" class="btn-primary">Save follow-up</button>
|
||||
</form>
|
||||
@elseif ($record)
|
||||
<dl class="mt-4 grid gap-3 text-sm sm:grid-cols-2">
|
||||
@foreach ($clinicalFields ?? [] as $field)
|
||||
<div>
|
||||
<dt class="text-slate-500">{{ $field['label'] }}</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $payload[$field['name']] ?? '—' }}</dd>
|
||||
</div>
|
||||
@endforeach
|
||||
</dl>
|
||||
@else
|
||||
<p class="mt-4 text-sm text-slate-500">No follow-up review recorded yet.</p>
|
||||
@endif
|
||||
</section>
|
||||
@@ -0,0 +1,71 @@
|
||||
@php
|
||||
$mse = $psychiatryHistory?->payload ?? [];
|
||||
$risk = $psychiatryRisk?->payload ?? [];
|
||||
$plan = $psychiatryPlan?->payload ?? [];
|
||||
@endphp
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<div class="flex flex-wrap items-start justify-between gap-3">
|
||||
<div>
|
||||
<h3 class="text-sm font-semibold text-slate-900">Psychiatry overview</h3>
|
||||
<p class="mt-0.5 text-xs text-slate-500">MSE, risk, formulation, and follow-up for this episode. Clinical notes use the same access controls as other specialty records.</p>
|
||||
</div>
|
||||
<div class="flex flex-wrap gap-3 text-sm">
|
||||
<a href="{{ route('care.specialty.psychiatry.print', $workspaceVisit) }}" target="_blank" class="font-medium text-indigo-600">Print summary</a>
|
||||
<a href="{{ route('care.specialty.psychiatry.reports') }}" class="font-medium text-indigo-600">Psychiatry reports</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="mt-4 grid gap-3 sm:grid-cols-3">
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Presenting</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">{{ $mse['chief_complaint'] ?? '—' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">{{ $mse['mood_affect'] ?? '—' }}</p>
|
||||
</div>
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Risk</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">{{ $risk['overall_risk'] ?? 'Not assessed' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">{{ \Illuminate\Support\Str::limit($risk['risk_summary'] ?? '—', 50) }}</p>
|
||||
</div>
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Plan</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">{{ $plan['diagnosis'] ?? 'Not set' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">{{ $plan['follow_up'] ?? '—' }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<dl class="mt-4 grid gap-3 text-sm sm:grid-cols-2">
|
||||
<div>
|
||||
<dt class="text-slate-500">MSE summary</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $mse['mse_summary'] ?? '—' }}</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Management plan</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $plan['plan'] ?? '—' }}</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Queue</dt>
|
||||
<dd class="font-medium text-slate-900">
|
||||
{{ $workspaceVisit->appointment?->queue_ticket_number ?? '—' }}
|
||||
@if ($workspaceVisit->appointment?->queue_ticket_status)
|
||||
<span class="text-slate-500">({{ $workspaceVisit->appointment->queue_ticket_status }})</span>
|
||||
@endif
|
||||
</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Checked in</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $workspaceVisit->checked_in_at?->format('d M Y H:i') ?? '—' }}</dd>
|
||||
</div>
|
||||
</dl>
|
||||
|
||||
@if (! empty($clinicalAlerts))
|
||||
<div class="mt-4 space-y-1.5 border-t border-slate-100 pt-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Alerts</p>
|
||||
@foreach ($clinicalAlerts as $alert)
|
||||
<p class="text-sm {{ ($alert['severity'] ?? '') === 'critical' ? 'text-rose-700' : 'text-amber-800' }}">
|
||||
{{ $alert['message'] ?? '' }}
|
||||
</p>
|
||||
@endforeach
|
||||
</div>
|
||||
@endif
|
||||
</section>
|
||||
@@ -0,0 +1,79 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Radiology summary · {{ $patient->fullName() }}</title>
|
||||
<style>
|
||||
body { font-family: system-ui, sans-serif; color: #0f172a; margin: 2rem; }
|
||||
h1 { font-size: 1.25rem; margin: 0 0 .25rem; }
|
||||
h2 { font-size: .95rem; margin: 1.25rem 0 .5rem; border-bottom: 1px solid #e2e8f0; padding-bottom: .25rem; }
|
||||
.meta { color: #64748b; font-size: .875rem; }
|
||||
dl { display: grid; grid-template-columns: 10rem 1fr; gap: .35rem .75rem; font-size: .875rem; }
|
||||
dt { color: #64748b; }
|
||||
dd { margin: 0; font-weight: 500; }
|
||||
@media print { .no-print { display: none; } }
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<p class="no-print"><a href="{{ route('care.specialty.workspace', ['module' => 'radiology', 'visit' => $visit]) }}">Back</a></p>
|
||||
|
||||
<h1>{{ $patient->fullName() }}</h1>
|
||||
<p class="meta">
|
||||
{{ $patient->patient_number }}
|
||||
· Visit #{{ $visit->id }}
|
||||
· Stage {{ $visit->specialty_stage ?? '—' }}
|
||||
· {{ $visit->checked_in_at?->format('d M Y H:i') ?? '—' }}
|
||||
</p>
|
||||
|
||||
<h2>Request / protocol</h2>
|
||||
@if ($imagingRequest)
|
||||
<dl>
|
||||
<dt>Modality</dt><dd>{{ $imagingRequest->payload['modality'] ?? '—' }}</dd>
|
||||
<dt>Body part</dt><dd>{{ $imagingRequest->payload['body_part'] ?? '—' }}</dd>
|
||||
<dt>Urgency</dt><dd>{{ $imagingRequest->payload['urgency'] ?? '—' }}</dd>
|
||||
<dt>Contrast</dt><dd>{{ $imagingRequest->payload['contrast'] ?? '—' }}</dd>
|
||||
<dt>Clinical info</dt><dd>{{ $imagingRequest->payload['clinical_info'] ?? '—' }}</dd>
|
||||
<dt>Protocol</dt><dd>{{ $imagingRequest->payload['protocol'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No imaging request recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Acquisition</h2>
|
||||
@if ($acquisition)
|
||||
<dl>
|
||||
<dt>Status</dt><dd>{{ $acquisition->payload['acquisition_status'] ?? '—' }}</dd>
|
||||
<dt>Quality</dt><dd>{{ $acquisition->payload['quality'] ?? '—' }}</dd>
|
||||
<dt>Technologist</dt><dd>{{ $acquisition->payload['technologist'] ?? '—' }}</dd>
|
||||
<dt>Notes</dt><dd>{{ $acquisition->payload['notes'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No acquisition recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Findings / report</h2>
|
||||
@if ($imagingReport)
|
||||
<dl>
|
||||
<dt>Technique</dt><dd>{{ $imagingReport->payload['technique'] ?? '—' }}</dd>
|
||||
<dt>Findings</dt><dd>{{ $imagingReport->payload['findings'] ?? '—' }}</dd>
|
||||
<dt>Impression</dt><dd>{{ $imagingReport->payload['impression'] ?? '—' }}</dd>
|
||||
<dt>Recommendations</dt><dd>{{ $imagingReport->payload['recommendations'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No report recorded.</p>
|
||||
@endif
|
||||
|
||||
<h2>Verification</h2>
|
||||
@if ($verification)
|
||||
<dl>
|
||||
<dt>Status</dt><dd>{{ $verification->payload['verification_status'] ?? '—' }}</dd>
|
||||
<dt>Verified by</dt><dd>{{ $verification->payload['verified_by'] ?? '—' }}</dd>
|
||||
<dt>Notes</dt><dd>{{ $verification->payload['notes'] ?? '—' }}</dd>
|
||||
</dl>
|
||||
@else
|
||||
<p class="meta">No verification recorded.</p>
|
||||
@endif
|
||||
|
||||
<script>window.print();</script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,88 @@
|
||||
<x-app-layout title="Radiology reports">
|
||||
<div class="space-y-6">
|
||||
<div class="flex flex-wrap items-center justify-between gap-3">
|
||||
<div>
|
||||
<h1 class="text-xl font-semibold text-slate-900">Radiology reports</h1>
|
||||
<p class="mt-1 text-sm text-slate-500">Arrivals, urgent studies, modalities, verification outcomes, length of stay, and imaging revenue.</p>
|
||||
</div>
|
||||
<a href="{{ route('care.specialty.show', 'radiology') }}" class="text-sm font-medium text-indigo-600">← Specialty home</a>
|
||||
</div>
|
||||
|
||||
<form method="GET" class="flex flex-wrap items-end gap-3 rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<div>
|
||||
<label class="block text-xs font-medium text-slate-600">From</label>
|
||||
<input type="date" name="from" value="{{ $report['from'] ?? '' }}" class="mt-1 rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
</div>
|
||||
<div>
|
||||
<label class="block text-xs font-medium text-slate-600">To</label>
|
||||
<input type="date" name="to" value="{{ $report['to'] ?? '' }}" class="mt-1 rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
</div>
|
||||
<button type="submit" class="rounded-xl bg-indigo-600 px-4 py-2 text-sm font-semibold text-white">Apply</button>
|
||||
</form>
|
||||
|
||||
<div class="grid gap-4 sm:grid-cols-4">
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Arrivals today</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">{{ number_format($report['arrivals_today']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Completed today</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">{{ number_format($report['completed_today']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Urgent open</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-rose-700">{{ number_format($report['urgent_open']) }}</p>
|
||||
</div>
|
||||
<div class="rounded-2xl border border-slate-200 bg-white p-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Avg LOS (range)</p>
|
||||
<p class="mt-2 text-2xl font-semibold tabular-nums text-slate-900">
|
||||
{{ $report['avg_los_minutes'] !== null ? $report['avg_los_minutes'].' min' : '—' }}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="grid gap-4 lg:grid-cols-2">
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Modalities</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['modality_breakdown'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row['modality'] }}</span>
|
||||
<span class="tabular-nums text-slate-600">{{ $row['total'] }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No imaging requests in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Verification outcomes</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['verification_outcomes'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row['status'] }}</span>
|
||||
<span class="tabular-nums text-slate-600">{{ $row['total'] }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No verifications in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
</div>
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h2 class="text-sm font-semibold text-slate-900">Radiology service revenue</h2>
|
||||
<ul class="mt-3 space-y-2 text-sm">
|
||||
@forelse ($report['revenue_by_service'] as $row)
|
||||
<li class="flex justify-between gap-3">
|
||||
<span>{{ $row->description }} <span class="text-slate-400">×{{ $row->total }}</span></span>
|
||||
<span class="tabular-nums">{{ $currency }} {{ number_format($row->amount_minor / 100, 2) }}</span>
|
||||
</li>
|
||||
@empty
|
||||
<li class="text-slate-500">No billed radiology services in range.</li>
|
||||
@endforelse
|
||||
</ul>
|
||||
</section>
|
||||
</div>
|
||||
</x-app-layout>
|
||||
@@ -0,0 +1,72 @@
|
||||
@php
|
||||
$req = $radiologyRequest?->payload ?? [];
|
||||
$acq = $radiologyAcquisition?->payload ?? [];
|
||||
$rep = $radiologyReport?->payload ?? [];
|
||||
$ver = $radiologyVerification?->payload ?? [];
|
||||
@endphp
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<div class="flex flex-wrap items-start justify-between gap-3">
|
||||
<div>
|
||||
<h3 class="text-sm font-semibold text-slate-900">Radiology overview</h3>
|
||||
<p class="mt-0.5 text-xs text-slate-500">Request, acquisition, report, and verification for this study.</p>
|
||||
</div>
|
||||
<div class="flex flex-wrap gap-3 text-sm">
|
||||
<a href="{{ route('care.specialty.radiology.print', $workspaceVisit) }}" target="_blank" class="font-medium text-indigo-600">Print summary</a>
|
||||
<a href="{{ route('care.specialty.radiology.reports') }}" class="font-medium text-indigo-600">Radiology reports</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="mt-4 grid gap-3 sm:grid-cols-3">
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Request</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">{{ $req['modality'] ?? '—' }} · {{ $req['body_part'] ?? '—' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">{{ $req['urgency'] ?? 'Routine' }}</p>
|
||||
</div>
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Acquisition</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">{{ $acq['acquisition_status'] ?? 'Not started' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">{{ $acq['quality'] ?? '—' }}</p>
|
||||
</div>
|
||||
<div class="rounded-xl border border-slate-100 bg-slate-50 px-3 py-3">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Report / verify</p>
|
||||
<p class="mt-1 text-sm font-semibold text-slate-900">{{ $ver['verification_status'] ?? 'Draft' }}</p>
|
||||
<p class="mt-1 text-xs text-slate-500">{{ \Illuminate\Support\Str::limit($rep['impression'] ?? '—', 60) }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<dl class="mt-4 grid gap-3 text-sm sm:grid-cols-2">
|
||||
<div>
|
||||
<dt class="text-slate-500">Clinical info</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $req['clinical_info'] ?? '—' }}</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Impression</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $rep['impression'] ?? '—' }}</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Queue</dt>
|
||||
<dd class="font-medium text-slate-900">
|
||||
{{ $workspaceVisit->appointment?->queue_ticket_number ?? '—' }}
|
||||
@if ($workspaceVisit->appointment?->queue_ticket_status)
|
||||
<span class="text-slate-500">({{ $workspaceVisit->appointment->queue_ticket_status }})</span>
|
||||
@endif
|
||||
</dd>
|
||||
</div>
|
||||
<div>
|
||||
<dt class="text-slate-500">Checked in</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $workspaceVisit->checked_in_at?->format('d M Y H:i') ?? '—' }}</dd>
|
||||
</div>
|
||||
</dl>
|
||||
|
||||
@if (! empty($clinicalAlerts))
|
||||
<div class="mt-4 space-y-1.5 border-t border-slate-100 pt-4">
|
||||
<p class="text-xs font-semibold uppercase tracking-wide text-slate-500">Alerts</p>
|
||||
@foreach ($clinicalAlerts as $alert)
|
||||
<p class="text-sm {{ ($alert['severity'] ?? '') === 'critical' ? 'text-rose-700' : 'text-amber-800' }}">
|
||||
{{ $alert['message'] ?? '' }}
|
||||
</p>
|
||||
@endforeach
|
||||
</div>
|
||||
@endif
|
||||
</section>
|
||||
@@ -0,0 +1,70 @@
|
||||
@php
|
||||
$record = $radiologyVerification;
|
||||
$payload = $record?->payload ?? [];
|
||||
$canManage = $canManageClinical ?? $canConsult ?? false;
|
||||
@endphp
|
||||
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<div class="flex flex-wrap items-start justify-between gap-3">
|
||||
<div>
|
||||
<h3 class="text-sm font-semibold text-slate-900">Verification</h3>
|
||||
<p class="mt-0.5 text-xs text-slate-500">Final / verified reports can close the imaging episode.</p>
|
||||
</div>
|
||||
<a href="{{ route('care.specialty.radiology.print', $workspaceVisit) }}" target="_blank" class="text-sm font-medium text-indigo-600">Print summary</a>
|
||||
</div>
|
||||
|
||||
@if ($canManage)
|
||||
<form method="POST" action="{{ route('care.specialty.radiology.verification', $workspaceVisit) }}" class="mt-4 space-y-4">
|
||||
@csrf
|
||||
<input type="hidden" name="tab" value="verification">
|
||||
<div class="grid gap-3 sm:grid-cols-2">
|
||||
@foreach ($clinicalFields ?? [] as $field)
|
||||
@php
|
||||
$name = $field['name'];
|
||||
$value = old('payload.'.$name, $payload[$name] ?? '');
|
||||
$type = $field['type'] ?? 'text';
|
||||
@endphp
|
||||
<div @class(['sm:col-span-2' => in_array($type, ['textarea'], true)])>
|
||||
<label class="block text-xs font-medium text-slate-600">
|
||||
{{ $field['label'] }}
|
||||
@if (! empty($field['required'])) <span class="text-rose-600">*</span> @endif
|
||||
</label>
|
||||
@if ($type === 'textarea')
|
||||
<textarea name="payload[{{ $name }}]" rows="{{ $field['rows'] ?? 3 }}" @required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">{{ $value }}</textarea>
|
||||
@elseif ($type === 'select')
|
||||
<select name="payload[{{ $name }}]" @required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
<option value="">Select…</option>
|
||||
@foreach ($field['options'] ?? [] as $option)
|
||||
<option value="{{ $option }}" @selected((string) $value === (string) $option)>{{ $option }}</option>
|
||||
@endforeach
|
||||
</select>
|
||||
@elseif ($type === 'boolean')
|
||||
<label class="mt-2 inline-flex items-center gap-2 text-sm text-slate-700">
|
||||
<input type="checkbox" name="payload[{{ $name }}]" value="1" @checked(old('payload.'.$name, ! empty($payload[$name])))>
|
||||
Yes
|
||||
</label>
|
||||
@else
|
||||
<input type="{{ $type === 'number' ? 'number' : 'text' }}" name="payload[{{ $name }}]" value="{{ $value }}"
|
||||
@required(! empty($field['required']))
|
||||
class="mt-1 w-full rounded-xl border border-slate-200 px-3 py-2 text-sm">
|
||||
@endif
|
||||
</div>
|
||||
@endforeach
|
||||
</div>
|
||||
<button type="submit" class="btn-primary">Save verification</button>
|
||||
</form>
|
||||
@elseif ($record)
|
||||
<dl class="mt-4 grid gap-3 text-sm sm:grid-cols-2">
|
||||
@foreach ($clinicalFields ?? [] as $field)
|
||||
<div>
|
||||
<dt class="text-slate-500">{{ $field['label'] }}</dt>
|
||||
<dd class="font-medium text-slate-900">{{ $payload[$field['name']] ?? '—' }}</dd>
|
||||
</div>
|
||||
@endforeach
|
||||
</dl>
|
||||
@else
|
||||
<p class="mt-4 text-sm text-slate-500">No verification recorded yet.</p>
|
||||
@endif
|
||||
</section>
|
||||
@@ -67,6 +67,12 @@
|
||||
@include('care.specialty.physiotherapy.workspace-'.$activeTab)
|
||||
@elseif ($moduleKey === 'maternity' && in_array($activeTab, ['overview', 'postnatal'], true))
|
||||
@include('care.specialty.maternity.workspace-'.$activeTab)
|
||||
@elseif ($moduleKey === 'radiology' && in_array($activeTab, ['overview', 'verification'], true))
|
||||
@include('care.specialty.radiology.workspace-'.$activeTab)
|
||||
@elseif ($moduleKey === 'cardiology' && in_array($activeTab, ['overview', 'procedures'], true))
|
||||
@include('care.specialty.cardiology.workspace-'.$activeTab)
|
||||
@elseif ($moduleKey === 'psychiatry' && in_array($activeTab, ['overview', 'followup'], true))
|
||||
@include('care.specialty.psychiatry.workspace-'.$activeTab)
|
||||
@elseif ($activeTab === 'billing')
|
||||
<section class="rounded-2xl border border-slate-200 bg-white p-5">
|
||||
<h3 class="text-sm font-semibold text-slate-900">
|
||||
|
||||
@@ -43,6 +43,15 @@
|
||||
@if ($moduleKey === 'maternity')
|
||||
<a href="{{ route('care.specialty.maternity.reports') }}" class="text-slate-600 hover:text-slate-900">Reports</a>
|
||||
@endif
|
||||
@if ($moduleKey === 'radiology')
|
||||
<a href="{{ route('care.specialty.radiology.reports') }}" class="text-slate-600 hover:text-slate-900">Reports</a>
|
||||
@endif
|
||||
@if ($moduleKey === 'cardiology')
|
||||
<a href="{{ route('care.specialty.cardiology.reports') }}" class="text-slate-600 hover:text-slate-900">Reports</a>
|
||||
@endif
|
||||
@if ($moduleKey === 'psychiatry')
|
||||
<a href="{{ route('care.specialty.psychiatry.reports') }}" class="text-slate-600 hover:text-slate-900">Reports</a>
|
||||
@endif
|
||||
<a href="{{ route('care.specialty.history', $moduleKey) }}" class="text-slate-600 hover:text-slate-900">History</a>
|
||||
@if ($canManageClinical ?? $canManageSpecialty ?? true)
|
||||
<a href="{{ route('care.specialty.billing', $moduleKey) }}" class="text-slate-600 hover:text-slate-900">Billing</a>
|
||||
|
||||
Reference in New Issue
Block a user