From 4e61e08638123ab4ae2b91b587954658ab805609 Mon Sep 17 00:00:00 2001 From: Potenz Date: Thu, 19 Jun 2025 23:11:39 +0530 Subject: [PATCH] claimpdf page setup --- apps/Frontend/src/App.tsx | 2 + apps/Frontend/src/pages/claims-pdf-page.tsx | 328 ++++++++++++++++++++ 2 files changed, 330 insertions(+) create mode 100644 apps/Frontend/src/pages/claims-pdf-page.tsx diff --git a/apps/Frontend/src/App.tsx b/apps/Frontend/src/App.tsx index ebd9d94..2251003 100644 --- a/apps/Frontend/src/App.tsx +++ b/apps/Frontend/src/App.tsx @@ -16,6 +16,7 @@ const SettingsPage = lazy(() => import("./pages/settings-page")); const ClaimsPage = lazy(() => import("./pages/claims-page")); const PreAuthorizationsPage = lazy(() => import("./pages/preauthorizations-page")); const PaymentsPage = lazy(() => import("./pages/payments-page")); +const ClaimsPdfPage = lazy(() => import("./pages/claims-pdf-page")); const NotFound = lazy(() => import("./pages/not-found")); function Router() { @@ -28,6 +29,7 @@ function Router() { } /> } /> } /> + }/> } /> } /> diff --git a/apps/Frontend/src/pages/claims-pdf-page.tsx b/apps/Frontend/src/pages/claims-pdf-page.tsx new file mode 100644 index 0000000..11e9b6b --- /dev/null +++ b/apps/Frontend/src/pages/claims-pdf-page.tsx @@ -0,0 +1,328 @@ +import { useState } from "react"; +import { useQuery } from "@tanstack/react-query"; +import { TopAppBar } from "@/components/layout/top-app-bar"; +import { Sidebar } from "@/components/layout/sidebar"; +import { Input } from "@/components/ui/input"; +import { Button } from "@/components/ui/button"; +import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card"; +import { + Search, + Edit, + Eye, + ChevronLeft, + ChevronRight, + Settings +} from "lucide-react"; +import { PatientUncheckedCreateInputObjectSchema } from "@repo/db/usedSchemas"; +import { useAuth } from "@/hooks/use-auth"; +import { cn } from "@/lib/utils"; +import { + Select, + SelectContent, + SelectItem, + SelectTrigger, + SelectValue, +} from "@/components/ui/select"; +import {z} from "zod"; + + +const PatientSchema = ( + PatientUncheckedCreateInputObjectSchema as unknown as z.ZodObject +).omit({ + appointments: true, +}); +type Patient = z.infer; + +const insertPatientSchema = ( + PatientUncheckedCreateInputObjectSchema as unknown as z.ZodObject +).omit({ + id: true, + createdAt: true, + userId: true, +}); +type InsertPatient = z.infer; + +const updatePatientSchema = ( + PatientUncheckedCreateInputObjectSchema as unknown as z.ZodObject +) + .omit({ + id: true, + createdAt: true, + userId: true, + }) + .partial(); + +type UpdatePatient = z.infer; + + +export default function DocumentsPage() { + const { user } = useAuth(); + const [isMobileMenuOpen, setIsMobileMenuOpen] = useState(false); + const [searchTerm, setSearchTerm] = useState(""); + const [searchField, setSearchField] = useState("all"); + const [currentPage, setCurrentPage] = useState(1); + const itemsPerPage = 5; + + // Fetch patients + const { + data: patients = [], + isLoading: isLoadingPatients, + } = useQuery({ + queryKey: ["/api/patients"], + enabled: !!user, + }); + + // Filter patients based on search + const filteredPatients = patients.filter(patient => { + if (!searchTerm) return true; + + const searchLower = searchTerm.toLowerCase(); + const fullName = `${patient.firstName} ${patient.lastName}`.toLowerCase(); + const patientId = `PID-${patient.id.toString().padStart(4, '0')}`; + + switch (searchField) { + case "name": + return fullName.includes(searchLower); + case "id": + return patientId.toLowerCase().includes(searchLower); + case "phone": + return patient.phone?.toLowerCase().includes(searchLower) || false; + case "all": + default: + return ( + fullName.includes(searchLower) || + patientId.toLowerCase().includes(searchLower) || + patient.phone?.toLowerCase().includes(searchLower) || + patient.email?.toLowerCase().includes(searchLower) || + false + ); + } + }); + + // Pagination + const totalPages = Math.ceil(filteredPatients.length / itemsPerPage); + const startIndex = (currentPage - 1) * itemsPerPage; + const endIndex = startIndex + itemsPerPage; + const currentPatients = filteredPatients.slice(startIndex, endIndex); + + const toggleMobileMenu = () => { + setIsMobileMenuOpen(!isMobileMenuOpen); + }; + + const formatDate = (dateString: string) => { + const date = new Date(dateString); + return date.toLocaleDateString('en-US', { + month: 'short', + day: 'numeric', + year: 'numeric' + }); + }; + + const getPatientInitials = (firstName: string, lastName: string) => { + return `${firstName.charAt(0)}${lastName.charAt(0)}`.toUpperCase(); + }; + + return ( +
+ + +
+ + +
+
+ {/* Header */} +
+

Documents

+

View and manage all patient information

+
+ + {/* Search and Filters */} + + +
+
+ + setSearchTerm(e.target.value)} + className="pl-10" + /> +
+
+ + +
+
+
+
+ + {/* Patient List */} + + + {isLoadingPatients ? ( +
Loading patients...
+ ) : ( + <> + {/* Table Header */} +
+
Patient
+
DOB / Gender
+
Contact
+
Insurance
+
Status
+
Actions
+
+ + {/* Table Rows */} + {currentPatients.length === 0 ? ( +
+ {searchTerm ? "No patients found matching your search." : "No patients available."} +
+ ) : ( + currentPatients.map((patient) => ( +
+ {/* Patient Info */} +
+
+ {getPatientInitials(patient.firstName, patient.lastName)} +
+
+
+ {patient.firstName} {patient.lastName} +
+
+ PID-{patient.id.toString().padStart(4, '0')} +
+
+
+ + {/* DOB / Gender */} +
+
+ {formatDate(patient.dateOfBirth)} +
+
+ {patient.gender} +
+
+ + {/* Contact */} +
+
+ {patient.phone || 'Not provided'} +
+
+ {patient.email || 'No email'} +
+
+ + {/* Insurance */} +
+
+ {patient.insuranceProvider ? + `${patient.insuranceProvider.charAt(0).toUpperCase()}${patient.insuranceProvider.slice(1)}` : + 'Not specified' + } +
+
+ ID: {patient.insuranceId || 'N/A'} +
+
+ + {/* Status */} +
+ + {patient.status === 'active' ? 'Active' : 'Inactive'} + +
+ + {/* Actions */} +
+
+ + +
+
+
+ )) + )} + + {/* Pagination */} + {totalPages > 1 && ( +
+
+ Showing {startIndex + 1} to {Math.min(endIndex, filteredPatients.length)} of {filteredPatients.length} results +
+
+ + + {/* Page Numbers */} + {Array.from({ length: totalPages }, (_, i) => i + 1).map((page) => ( + + ))} + + +
+
+ )} + + )} +
+
+
+
+
+
+ ); +} \ No newline at end of file