feat: initialize project structure with core components and pages
- Added shared styles for UI components in `src/components/styles.ts`. - Created configuration constants in `src/lib/config.ts`. - Implemented date formatting and greeting functions in `src/lib/dates.ts` and corresponding tests in `src/lib/dates.test.ts`. - Developed incident management functions in `src/lib/incidents.ts` with tests in `src/lib/incidents.test.ts`. - Established navigation structure in `src/lib/navigation.ts`. - Seeded demo data for incidents and users in `src/lib/seed.ts`. - Defined tone classes for UI elements in `src/lib/tones.ts`. - Created type definitions for incidents and related entities in `src/lib/types.ts`. - Set up main application entry point in `src/main.tsx`. - Developed various pages including About, Analytics, Incidents, Locations, Overview, and Report Incident. - Configured testing setup in `src/test/setup.ts` and TypeScript configurations. - Integrated Vite for development and testing with appropriate plugins.
This commit is contained in:
1 parent
732d4d8931
commit
a382fa904a
53 files changed
+3523
-31
No files matched your search
@@ -0,0 +1,80 @@
|
||||
import { AlertTriangle, MapPin } from 'lucide-react'
|
||||
import { formatDate } from '../lib/dates'
|
||||
import { severityDotClass, statusClass, typeTone } from '../lib/incidents'
|
||||
import { toneClasses } from '../lib/tones'
|
||||
import type { Incident } from '../lib/types'
|
||||
import { iconButton } from './styles'
|
||||
|
||||
const th = 'border-b border-line px-2.5 py-3 font-mono text-3xs font-medium tracking-[0.06em] text-faint uppercase first:pl-6 last:pr-[18px]'
|
||||
const td = 'border-b border-line-soft px-2.5 py-3.5 text-2xs whitespace-nowrap text-body first:pl-6 last:pr-[18px]'
|
||||
|
||||
interface IncidentTableProps {
|
||||
incidents: Incident[]
|
||||
limit?: number
|
||||
wide?: boolean
|
||||
}
|
||||
|
||||
export function IncidentTable({ incidents, limit, wide = false }: IncidentTableProps) {
|
||||
const rows = limit ? incidents.slice(0, limit) : incidents
|
||||
return (
|
||||
<div className="overflow-auto">
|
||||
<table className={`w-full border-collapse text-left ${wide ? 'min-w-[900px]' : 'min-w-[720px]'}`}>
|
||||
<thead>
|
||||
<tr>
|
||||
<th className={th}>Incident</th>
|
||||
<th className={th}>Type</th>
|
||||
<th className={th}>Severity</th>
|
||||
<th className={th}>Location</th>
|
||||
<th className={th}>Status</th>
|
||||
<th className={th}>Date</th>
|
||||
<th className={th}>
|
||||
<span className="sr-only">Actions</span>
|
||||
</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{rows.map((incident) => (
|
||||
<tr key={incident.id} className="[&:last-child>td]:border-b-0">
|
||||
<td className={td}>
|
||||
<div className="flex min-w-[250px] items-center gap-2.5">
|
||||
<span className={`grid size-7 place-items-center rounded-[7px] ${toneClasses[typeTone[incident.type]]}`}>
|
||||
<AlertTriangle size={14} />
|
||||
</span>
|
||||
<div>
|
||||
<strong className="block text-xs font-semibold text-ink">{incident.title}</strong>
|
||||
<small className="mt-1 block text-3xs text-faint">
|
||||
{incident.id} · {incident.reporter}
|
||||
</small>
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
<td className={td}>{incident.type}</td>
|
||||
<td className={td}>
|
||||
<span className="inline-flex items-center gap-[5px]">
|
||||
<i className={`size-1.5 rounded-full ${severityDotClass[incident.severity]}`} />
|
||||
{incident.severity}
|
||||
</span>
|
||||
</td>
|
||||
<td className={td}>
|
||||
<div className="flex max-w-[120px] flex-wrap items-center gap-1">
|
||||
<MapPin size={14} />
|
||||
{incident.location}
|
||||
<small className="mt-1 ml-[18px] block w-full text-3xs text-faint">{incident.building}</small>
|
||||
</div>
|
||||
</td>
|
||||
<td className={td}>
|
||||
<span className={`rounded px-2 py-[5px] text-3xs ${statusClass(incident.status)}`}>{incident.status}</span>
|
||||
</td>
|
||||
<td className={`${td} text-[#87938f]`}>{formatDate(incident.date)}</td>
|
||||
<td className={td}>
|
||||
<button type="button" className={iconButton} aria-label={`More actions for ${incident.id}`}>
|
||||
<span className="tracking-[2px] text-[#91aaa0]">•••</span>
|
||||
</button>
|
||||
</td>
|
||||
</tr>
|
||||
))}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
Reference in new issue
Block a user