add ElementBadge component, use in gw event pages
This commit is contained in:
parent
6f0870e37f
commit
00813ddd58
4 changed files with 81 additions and 199 deletions
72
src/lib/components/ui/ElementBadge.svelte
Normal file
72
src/lib/components/ui/ElementBadge.svelte
Normal file
|
|
@ -0,0 +1,72 @@
|
|||
<svelte:options runes={true} />
|
||||
|
||||
<script lang="ts">
|
||||
import { ELEMENT_LABELS, ELEMENT_CSS_CLASSES } from '$lib/utils/gw'
|
||||
|
||||
interface Props {
|
||||
element: number
|
||||
size?: 'small' | 'medium'
|
||||
}
|
||||
|
||||
let { element, size = 'small' }: Props = $props()
|
||||
|
||||
const label = $derived(ELEMENT_LABELS[element] ?? 'Unknown')
|
||||
const cssClass = $derived(ELEMENT_CSS_CLASSES[element] ?? 'null')
|
||||
</script>
|
||||
|
||||
<span class="element-badge element-{cssClass}" class:medium={size === 'medium'}>
|
||||
{label}
|
||||
</span>
|
||||
|
||||
<style lang="scss">
|
||||
@use '$src/themes/layout' as layout;
|
||||
@use '$src/themes/typography' as typography;
|
||||
|
||||
.element-badge {
|
||||
display: inline-block;
|
||||
padding: 2px 8px;
|
||||
border-radius: layout.$item-corner-small;
|
||||
font-size: typography.$font-small;
|
||||
font-weight: typography.$medium;
|
||||
|
||||
&.medium {
|
||||
padding: 4px 12px;
|
||||
font-size: typography.$font-regular;
|
||||
}
|
||||
|
||||
&.element-null {
|
||||
background: rgba(0, 0, 0, 0.04);
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
&.element-fire {
|
||||
background: #fee2e2;
|
||||
color: #dc2626;
|
||||
}
|
||||
|
||||
&.element-water {
|
||||
background: #dbeafe;
|
||||
color: #2563eb;
|
||||
}
|
||||
|
||||
&.element-earth {
|
||||
background: #fef3c7;
|
||||
color: #d97706;
|
||||
}
|
||||
|
||||
&.element-wind {
|
||||
background: #d1fae5;
|
||||
color: #059669;
|
||||
}
|
||||
|
||||
&.element-light {
|
||||
background: #fef9c3;
|
||||
color: #ca8a04;
|
||||
}
|
||||
|
||||
&.element-dark {
|
||||
background: #ede9fe;
|
||||
color: #7c3aed;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
|
@ -15,6 +15,8 @@
|
|||
import Input from '$lib/components/ui/Input.svelte'
|
||||
import CrewHeader from '$lib/components/crew/CrewHeader.svelte'
|
||||
import { formatDateJST } from '$lib/utils/date'
|
||||
import { formatScore } from '$lib/utils/gw'
|
||||
import ElementBadge from '$lib/components/ui/ElementBadge.svelte'
|
||||
import type { PageData } from './$types'
|
||||
|
||||
interface Props {
|
||||
|
|
@ -39,28 +41,6 @@
|
|||
staleTime: 1000 * 60 * 5
|
||||
}))
|
||||
|
||||
// Element labels (matches GranblueEnums::ELEMENTS)
|
||||
const elementLabels: Record<number, string> = {
|
||||
0: 'Null',
|
||||
1: 'Wind',
|
||||
2: 'Fire',
|
||||
3: 'Water',
|
||||
4: 'Earth',
|
||||
5: 'Dark',
|
||||
6: 'Light'
|
||||
}
|
||||
|
||||
// Element colors for badges
|
||||
const elementColors: Record<number, string> = {
|
||||
0: 'null',
|
||||
1: 'wind',
|
||||
2: 'fire',
|
||||
3: 'water',
|
||||
4: 'earth',
|
||||
5: 'dark',
|
||||
6: 'light'
|
||||
}
|
||||
|
||||
// Mutations
|
||||
const createCrewMutation = useCreateCrew()
|
||||
const updateCrewMutation = useUpdateCrew()
|
||||
|
|
@ -160,11 +140,6 @@
|
|||
settingsError = null
|
||||
}
|
||||
|
||||
// Helper for formatting scores with commas
|
||||
function formatScore(score: number): string {
|
||||
return score.toLocaleString()
|
||||
}
|
||||
|
||||
function formatEventStatus(status: string, startDate: string): string {
|
||||
if (status === 'upcoming') {
|
||||
const now = new Date()
|
||||
|
|
@ -283,9 +258,7 @@
|
|||
<li class="event-item" onclick={() => goto(`/crew/events/${event.eventNumber}`)}>
|
||||
<div class="event-info">
|
||||
<span class="event-number">{event.eventNumber}</span>
|
||||
<span class="element-badge element-{elementColors[event.element]}">
|
||||
{elementLabels[event.element] ?? 'Unknown'}
|
||||
</span>
|
||||
<ElementBadge element={event.element} />
|
||||
</div>
|
||||
<span class="event-dates">
|
||||
{formatDateJST(event.startDate)} – {formatDateJST(event.endDate)}
|
||||
|
|
@ -660,49 +633,6 @@
|
|||
}
|
||||
}
|
||||
|
||||
.element-badge {
|
||||
display: inline-block;
|
||||
padding: 2px 8px;
|
||||
border-radius: layout.$item-corner-small;
|
||||
font-size: typography.$font-small;
|
||||
font-weight: typography.$medium;
|
||||
|
||||
&.element-null {
|
||||
background: rgba(0, 0, 0, 0.04);
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
&.element-fire {
|
||||
background: #fee2e2;
|
||||
color: #dc2626;
|
||||
}
|
||||
|
||||
&.element-water {
|
||||
background: #dbeafe;
|
||||
color: #2563eb;
|
||||
}
|
||||
|
||||
&.element-earth {
|
||||
background: #fef3c7;
|
||||
color: #d97706;
|
||||
}
|
||||
|
||||
&.element-wind {
|
||||
background: #d1fae5;
|
||||
color: #059669;
|
||||
}
|
||||
|
||||
&.element-light {
|
||||
background: #fef9c3;
|
||||
color: #ca8a04;
|
||||
}
|
||||
|
||||
&.element-dark {
|
||||
background: #ede9fe;
|
||||
color: #7c3aed;
|
||||
}
|
||||
}
|
||||
|
||||
.empty-state {
|
||||
text-align: center;
|
||||
color: var(--text-secondary);
|
||||
|
|
|
|||
|
|
@ -8,6 +8,8 @@
|
|||
import { gwAdapter } from '$lib/api/adapters/gw.adapter'
|
||||
import Button from '$lib/components/ui/Button.svelte'
|
||||
import { formatDateJST } from '$lib/utils/date'
|
||||
import { ELEMENT_LABELS } from '$lib/utils/gw'
|
||||
import ElementBadge from '$lib/components/ui/ElementBadge.svelte'
|
||||
import type { GwEvent } from '$lib/types/api/gw'
|
||||
import type { PageData } from './$types'
|
||||
|
||||
|
|
@ -27,28 +29,6 @@
|
|||
staleTime: 1000 * 60 * 5
|
||||
}))
|
||||
|
||||
// Element labels (matches GranblueEnums::ELEMENTS)
|
||||
const elementLabels: Record<number, string> = {
|
||||
0: 'Null',
|
||||
1: 'Wind',
|
||||
2: 'Fire',
|
||||
3: 'Water',
|
||||
4: 'Earth',
|
||||
5: 'Dark',
|
||||
6: 'Light'
|
||||
}
|
||||
|
||||
// Element colors for badges
|
||||
const elementColors: Record<number, string> = {
|
||||
0: 'null',
|
||||
1: 'wind',
|
||||
2: 'fire',
|
||||
3: 'water',
|
||||
4: 'earth',
|
||||
5: 'dark',
|
||||
6: 'light'
|
||||
}
|
||||
|
||||
// Filter events by search
|
||||
const filteredEvents = $derived.by(() => {
|
||||
const events = eventsQuery.data ?? []
|
||||
|
|
@ -58,7 +38,7 @@
|
|||
return events.filter(
|
||||
(e) =>
|
||||
String(e.eventNumber).includes(term) ||
|
||||
elementLabels[e.element]?.toLowerCase().includes(term)
|
||||
ELEMENT_LABELS[e.element]?.toLowerCase().includes(term)
|
||||
)
|
||||
})
|
||||
|
||||
|
|
@ -110,9 +90,7 @@
|
|||
<span class="event-number">{event.eventNumber}</span>
|
||||
</td>
|
||||
<td class="col-element">
|
||||
<span class="element-badge element-{elementColors[event.element]}">
|
||||
{elementLabels[event.element] ?? 'Unknown'}
|
||||
</span>
|
||||
<ElementBadge element={event.element} />
|
||||
</td>
|
||||
<td class="col-dates">
|
||||
<span class="dates">
|
||||
|
|
@ -260,44 +238,6 @@
|
|||
color: #666;
|
||||
}
|
||||
|
||||
.element-badge {
|
||||
display: inline-block;
|
||||
padding: 2px 8px;
|
||||
border-radius: 4px;
|
||||
font-size: typography.$font-small;
|
||||
font-weight: 500;
|
||||
|
||||
&.element-fire {
|
||||
background: #fee2e2;
|
||||
color: #dc2626;
|
||||
}
|
||||
|
||||
&.element-water {
|
||||
background: #dbeafe;
|
||||
color: #2563eb;
|
||||
}
|
||||
|
||||
&.element-earth {
|
||||
background: #fef3c7;
|
||||
color: #d97706;
|
||||
}
|
||||
|
||||
&.element-wind {
|
||||
background: #d1fae5;
|
||||
color: #059669;
|
||||
}
|
||||
|
||||
&.element-light {
|
||||
background: #fef9c3;
|
||||
color: #ca8a04;
|
||||
}
|
||||
|
||||
&.element-dark {
|
||||
background: #ede9fe;
|
||||
color: #7c3aed;
|
||||
}
|
||||
}
|
||||
|
||||
.dates {
|
||||
font-size: typography.$font-small;
|
||||
color: #666;
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@
|
|||
import DetailItem from '$lib/components/ui/DetailItem.svelte'
|
||||
import SidebarHeader from '$lib/components/ui/SidebarHeader.svelte'
|
||||
import { formatDateJST, formatDateLongJST } from '$lib/utils/date'
|
||||
import ElementBadge from '$lib/components/ui/ElementBadge.svelte'
|
||||
import type { PageData } from './$types'
|
||||
|
||||
interface Props {
|
||||
|
|
@ -32,27 +33,6 @@
|
|||
const userRole = $derived(data.role || 0)
|
||||
const canEdit = $derived(userRole >= 7)
|
||||
|
||||
// Element labels and colors (matches GranblueEnums::ELEMENTS)
|
||||
const elementLabels: Record<number, string> = {
|
||||
0: 'Null',
|
||||
1: 'Wind',
|
||||
2: 'Fire',
|
||||
3: 'Water',
|
||||
4: 'Earth',
|
||||
5: 'Dark',
|
||||
6: 'Light'
|
||||
}
|
||||
|
||||
const elementColors: Record<number, string> = {
|
||||
0: 'null',
|
||||
1: 'wind',
|
||||
2: 'fire',
|
||||
3: 'water',
|
||||
4: 'earth',
|
||||
5: 'dark',
|
||||
6: 'light'
|
||||
}
|
||||
|
||||
// Navigate to edit
|
||||
function handleEdit() {
|
||||
goto(`/database/gw-events/${eventId}/edit`)
|
||||
|
|
@ -90,9 +70,7 @@
|
|||
<DetailsContainer title="Event Details">
|
||||
<DetailItem label="Event Number" value={`#${event.eventNumber}`} />
|
||||
<DetailItem label="Element">
|
||||
<span class="element-badge element-{elementColors[event.element]}">
|
||||
{elementLabels[event.element] ?? 'Unknown'}
|
||||
</span>
|
||||
<ElementBadge element={event.element} />
|
||||
</DetailItem>
|
||||
<DetailItem label="Start Date" value={formatDateLongJST(event.startDate)} />
|
||||
<DetailItem label="End Date" value={formatDateLongJST(event.endDate)} />
|
||||
|
|
@ -159,42 +137,4 @@
|
|||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.element-badge {
|
||||
display: inline-block;
|
||||
padding: 2px 8px;
|
||||
border-radius: 4px;
|
||||
font-size: typography.$font-small;
|
||||
font-weight: 500;
|
||||
|
||||
&.element-fire {
|
||||
background: #fee2e2;
|
||||
color: #dc2626;
|
||||
}
|
||||
|
||||
&.element-water {
|
||||
background: #dbeafe;
|
||||
color: #2563eb;
|
||||
}
|
||||
|
||||
&.element-earth {
|
||||
background: #fef3c7;
|
||||
color: #d97706;
|
||||
}
|
||||
|
||||
&.element-wind {
|
||||
background: #d1fae5;
|
||||
color: #059669;
|
||||
}
|
||||
|
||||
&.element-light {
|
||||
background: #fef9c3;
|
||||
color: #ca8a04;
|
||||
}
|
||||
|
||||
&.element-dark {
|
||||
background: #ede9fe;
|
||||
color: #7c3aed;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
|
|
|||
Loading…
Reference in a new issue