reverse image display and use env var to omit certain records
This commit is contained in:
parent
ef20a69427
commit
d48108429b
@ -6,6 +6,7 @@ import { fetchAnimalRecords } from '../../services/laconicQueryService'
|
|||||||
import { MapPin } from 'lucide-react'
|
import { MapPin } from 'lucide-react'
|
||||||
|
|
||||||
interface AnimalRecord {
|
interface AnimalRecord {
|
||||||
|
id: string
|
||||||
species: string
|
species: string
|
||||||
location: {
|
location: {
|
||||||
latitude: number
|
latitude: number
|
||||||
@ -13,8 +14,13 @@ interface AnimalRecord {
|
|||||||
}
|
}
|
||||||
description: string
|
description: string
|
||||||
imageUrl: string
|
imageUrl: string
|
||||||
|
createTime: string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const hiddenIndices = (process.env.NEXT_PUBLIC_HIDDEN_INDICES?.split(',') || [])
|
||||||
|
.map(num => parseInt(num))
|
||||||
|
.filter(num => !isNaN(num))
|
||||||
|
|
||||||
export default function AnimalsPage() {
|
export default function AnimalsPage() {
|
||||||
const [records, setRecords] = useState<AnimalRecord[]>([])
|
const [records, setRecords] = useState<AnimalRecord[]>([])
|
||||||
const [loading, setLoading] = useState(true)
|
const [loading, setLoading] = useState(true)
|
||||||
@ -29,7 +35,19 @@ export default function AnimalsPage() {
|
|||||||
setLoading(true)
|
setLoading(true)
|
||||||
setError(null)
|
setError(null)
|
||||||
const data = await fetchAnimalRecords()
|
const data = await fetchAnimalRecords()
|
||||||
setRecords(data)
|
|
||||||
|
// Sort by creation time, oldest first
|
||||||
|
const sortedRecords = [...data].sort((a, b) =>
|
||||||
|
new Date(a.createTime).getTime() - new Date(b.createTime).getTime()
|
||||||
|
)
|
||||||
|
|
||||||
|
// Filter out records by their chronological index (1-based)
|
||||||
|
const filteredRecords = sortedRecords.filter((_, index) =>
|
||||||
|
!hiddenIndices.includes(index + 1)
|
||||||
|
)
|
||||||
|
|
||||||
|
// Reverse to show newest first
|
||||||
|
setRecords(filteredRecords.reverse())
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
setError('Failed to load animal records')
|
setError('Failed to load animal records')
|
||||||
} finally {
|
} finally {
|
||||||
@ -37,44 +55,38 @@ export default function AnimalsPage() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const renderContent = () => {
|
||||||
|
if (loading) {
|
||||||
return (
|
return (
|
||||||
<div className="min-h-screen w-full flex flex-col items-center bg-gradient-to-b from-emerald-950 via-green-900 to-emerald-950">
|
|
||||||
<div className="container max-w-7xl mx-auto px-4 py-8">
|
|
||||||
<Navigation />
|
|
||||||
|
|
||||||
{/* Header */}
|
|
||||||
<div className="text-center mb-8">
|
|
||||||
<h1 className="text-4xl sm:text-5xl font-bold mb-4 text-transparent bg-clip-text bg-gradient-to-r from-emerald-400 to-teal-300">
|
|
||||||
Animal Registry
|
|
||||||
</h1>
|
|
||||||
<p className="text-emerald-200 text-lg mb-8">
|
|
||||||
Discover wildlife sightings from around the world
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
{/* Loading State */}
|
|
||||||
{loading && (
|
|
||||||
<div className="text-emerald-200 text-center">
|
<div className="text-emerald-200 text-center">
|
||||||
Loading animal records...
|
Loading animal records...
|
||||||
</div>
|
</div>
|
||||||
)}
|
)
|
||||||
|
}
|
||||||
|
|
||||||
{/* Error State */}
|
if (error) {
|
||||||
{error && (
|
return (
|
||||||
<div className="text-red-400 text-center p-4 bg-red-900/20 rounded-xl">
|
<div className="text-red-400 text-center p-4 bg-red-900/20 rounded-xl">
|
||||||
{error}
|
{error}
|
||||||
</div>
|
</div>
|
||||||
)}
|
)
|
||||||
|
}
|
||||||
|
|
||||||
{/* Records Grid */}
|
if (records.length === 0) {
|
||||||
{!loading && !error && (
|
return (
|
||||||
|
<div className="text-emerald-200 text-center p-8 bg-emerald-900/20 rounded-xl">
|
||||||
|
No animal records found yet. Be the first to contribute!
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
|
<div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
|
||||||
{records.map((record, index) => (
|
{records.map((record, index) => (
|
||||||
<div
|
<div
|
||||||
key={index}
|
key={`${record.id}-${index}`}
|
||||||
className="bg-emerald-900/20 rounded-xl p-6 border border-emerald-800/50 hover:border-emerald-700/50 transition-colors"
|
className="bg-emerald-900/20 rounded-xl p-6 border border-emerald-800/50 hover:border-emerald-700/50 transition-colors"
|
||||||
>
|
>
|
||||||
{/* Image */}
|
|
||||||
<div className="aspect-video rounded-lg overflow-hidden mb-4 bg-emerald-900/50">
|
<div className="aspect-video rounded-lg overflow-hidden mb-4 bg-emerald-900/50">
|
||||||
<img
|
<img
|
||||||
src={record.imageUrl}
|
src={record.imageUrl}
|
||||||
@ -83,12 +95,10 @@ export default function AnimalsPage() {
|
|||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* Species */}
|
|
||||||
<h3 className="text-xl font-semibold text-emerald-300 capitalize mb-2">
|
<h3 className="text-xl font-semibold text-emerald-300 capitalize mb-2">
|
||||||
{record.species}
|
{record.species}
|
||||||
</h3>
|
</h3>
|
||||||
|
|
||||||
{/* Location */}
|
|
||||||
<div className="flex items-center text-emerald-200/80 text-sm mb-3">
|
<div className="flex items-center text-emerald-200/80 text-sm mb-3">
|
||||||
<MapPin className="w-4 h-4 mr-1" />
|
<MapPin className="w-4 h-4 mr-1" />
|
||||||
<span>
|
<span>
|
||||||
@ -96,21 +106,30 @@ export default function AnimalsPage() {
|
|||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* Description */}
|
|
||||||
<p className="text-emerald-200 text-sm">
|
<p className="text-emerald-200 text-sm">
|
||||||
{record.description}
|
{record.description}
|
||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
))}
|
))}
|
||||||
</div>
|
</div>
|
||||||
)}
|
)
|
||||||
|
}
|
||||||
|
|
||||||
{/* Empty State */}
|
return (
|
||||||
{!loading && !error && records.length === 0 && (
|
<div className="min-h-screen w-full flex flex-col items-center bg-gradient-to-b from-emerald-950 via-green-900 to-emerald-950">
|
||||||
<div className="text-emerald-200 text-center p-8 bg-emerald-900/20 rounded-xl">
|
<div className="container max-w-7xl mx-auto px-4 py-8">
|
||||||
No animal records found yet. Be the first to contribute!
|
<Navigation />
|
||||||
|
|
||||||
|
<div className="text-center mb-8">
|
||||||
|
<h1 className="text-4xl sm:text-5xl font-bold mb-4 text-transparent bg-clip-text bg-gradient-to-r from-emerald-400 to-teal-300">
|
||||||
|
Animal Registry
|
||||||
|
</h1>
|
||||||
|
<p className="text-emerald-200 text-lg mb-8">
|
||||||
|
Discover wildlife sightings from our community
|
||||||
|
</p>
|
||||||
</div>
|
</div>
|
||||||
)}
|
|
||||||
|
{renderContent()}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
)
|
)
|
||||||
|
Loading…
Reference in New Issue
Block a user