// Woodbury Operator — Reports & Analytics. Registers window.ReportsScreen. (function () { const NS = window.WoodburyPropertiesDesignSystem_7290ca; const { Card, CardHeader, Button, Badge, StatCard, IconTile, Modal, Select, Eyebrow, ProgressBar } = NS; function BarChart() { const bars = [ { label: "Lashibi TH", v: 56 }, { label: "Lashibi Exec", v: 88 }, { label: "Mirage", v: 92 }, { label: "Onehive", v: 78 }, { label: "Hamlet", v: 100 }, { label: "Cant. City", v: 90 }, ]; return (
{bars.map((b) => (
{b.v}%
= 95 ? "var(--success)" : "var(--brand)" }} /> {b.label}
))}
); } // Simple SVG line chart — occupancy trend over 6 months. function TrendChart() { const pts = [86, 88, 87, 90, 91, 92]; const labels = ["Mar", "Apr", "May", "Jun", "Jul", "Aug"]; const W = 320, H = 150, pad = 10; const min = 82, max = 96; const x = (i) => pad + (i * (W - pad * 2)) / (pts.length - 1); const y = (v) => H - pad - ((v - min) / (max - min)) * (H - pad * 2); const d = pts.map((v, i) => (i ? "L" : "M") + x(i).toFixed(1) + " " + y(v).toFixed(1)).join(" "); const area = d + ` L ${x(pts.length - 1)} ${H - pad} L ${x(0)} ${H - pad} Z`; return (
{pts.map((v, i) => )}
{labels.map((l) => {l})}
); } // Report catalog grouped by category — the reports admins actually run. const CATALOG = [ { group: "Occupancy & Leasing", tone: "brand", items: [ { name: "Occupancy & Vacancy Summary", desc: "Occupied vs vacant units per estate, with trend.", icon: "building-2", scope: "both" }, { name: "Lease Expiry & Renewal Pipeline", desc: "Leases ending in 30/60/90 days and renewal status.", icon: "calendar-clock", scope: "both" }, { name: "Tenant Turnover & Retention", desc: "Move-ins, move-outs, and retention rate by site.", icon: "repeat", scope: "both" }, ]}, { group: "Maintenance & Facilities", tone: "accent", items: [ { name: "Maintenance Performance", desc: "Tickets opened/closed, avg resolution, by category.", icon: "wrench", scope: "both" }, { name: "Vendor SLA & Performance", desc: "Response time, jobs completed, and rating by vendor.", icon: "hard-hat", scope: "both" }, { name: "Recurring Issues Analysis", desc: "Most frequent fault types by unit and estate.", icon: "chart-column", scope: "super" }, ]}, { group: "Screening & Compliance", tone: "success", items: [ { name: "Applications Funnel", desc: "Applicants → verified → approved, with turnaround.", icon: "shield-check", scope: "both" }, { name: "Inspections & Compliance", desc: "Inspections done/overdue and certificate expiries.", icon: "clipboard-check", scope: "both" }, { name: "Communications Log", desc: "Broadcasts and resident notices sent, by site.", icon: "megaphone", scope: "both" }, ]}, { group: "Portfolio Oversight", tone: "sunken", items: [ { name: "Cross-Site Portfolio Scorecard", desc: "All estates compared on occupancy, tickets, SLA.", icon: "layout-grid", scope: "super" }, { name: "Staff Activity & Audit Summary", desc: "Actions per user and role across the portfolio.", icon: "scroll-text", scope: "super" }, ]}, ]; const RECENT = [ { name: "Q1 2026 Occupancy Summary", meta: "Generated 01 Apr · PDF", icon: "trending-up", tone: "brand" }, { name: "Maintenance Performance — Accra", meta: "Generated 28 Mar · PDF", icon: "wrench", tone: "accent" }, { name: "Lease Expiry Forecast", meta: "Generated 02 Mar · XLSX", icon: "calendar-clock", tone: "success" }, ]; function ReportsScreen() { const isSuper = (window.WB_ACTIVE_ROLE || "super") === "super"; const [period, setPeriod] = React.useState("This Quarter"); const [pick, setPick] = React.useState(false); const [gen, setGen] = React.useState(null); // null | {name} preselected const catalog = CATALOG.map((c) => ({ ...c, items: c.items.filter((it) => it.scope === "both" || (it.scope === "super" && isSuper)) })).filter((c) => c.items.length); const allTypes = catalog.flatMap((c) => c.items.map((it) => it.name)); return (
} />
window.WBNavigate && window.WBNavigate("Properties")} label="Portfolio Occupancy" value="92%" icon="building-2" iconTone="success" emphasis="success" delta="+1.2%" /> window.WBNavigate && window.WBNavigate("Maintenance")} label="Avg. Resolution" value="1.4d" icon="clock" iconTone="accent" /> window.WBNavigate && window.WBNavigate("Leases")} label="Renewals Due" value="5" icon="calendar-clock" iconTone="brand" />
{/* Charts */}
Live} />
+6% YTD} />
{/* Maintenance breakdown */}
{[["Plumbing", 34, "brand"], ["HVAC / Cooling", 28, "accent"], ["Electrical", 19, "success"], ["Structural / Roofing", 12, "sunken"], ["Access & Gates", 5, "brand"], ["Appliances", 2, "accent"]].map(([label, v, tone]) => (
{label}{v}%
))}
{/* Report library */}

Report Library

{allTypes.length} report types
{catalog.map((cat) => (
{cat.group}
{cat.items.map((it) => (
{it.name}

{it.desc}

))}
))}
{/* Recent */} {RECENT.map((r, i) => (
{r.name}
{r.meta}
))}
{/* Period picker */} setPick(false)} icon="calendar" title="Reporting Period" subtitle="Choose the time range for analytics." width={420}>
{["This Month", "This Quarter", "Year to Date", "Last 12 Months"].map((p) => ( ))}
{/* Generate report */} setGen(null)} icon="file-chart-column" title="Generate Report" subtitle="Build a new analytics export." footer={}> {gen && (
)}
); } window.ReportsScreen = ReportsScreen; })();