move season field to Metadata section
This commit is contained in:
parent
75a97cabaa
commit
879a3bd8bd
2 changed files with 40 additions and 77 deletions
|
|
@ -6,8 +6,10 @@
|
||||||
import DetailItem from '$lib/components/ui/DetailItem.svelte'
|
import DetailItem from '$lib/components/ui/DetailItem.svelte'
|
||||||
import SuggestionDetailItem from '$lib/components/ui/SuggestionDetailItem.svelte'
|
import SuggestionDetailItem from '$lib/components/ui/SuggestionDetailItem.svelte'
|
||||||
import CopyableText from '$lib/components/ui/CopyableText.svelte'
|
import CopyableText from '$lib/components/ui/CopyableText.svelte'
|
||||||
|
import Select from '$lib/components/ui/Select.svelte'
|
||||||
import { getRarityLabel, getRarityOptions } from '$lib/utils/rarity'
|
import { getRarityLabel, getRarityOptions } from '$lib/utils/rarity'
|
||||||
import { getWeaponImage } from '$lib/utils/images'
|
import { getWeaponImage } from '$lib/utils/images'
|
||||||
|
import { CHARACTER_SEASON_NAMES, getSeasonName } from '$lib/types/enums'
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
character: any
|
character: any
|
||||||
|
|
@ -32,6 +34,15 @@
|
||||||
|
|
||||||
const rarityOptions = getRarityOptions()
|
const rarityOptions = getRarityOptions()
|
||||||
|
|
||||||
|
// Season options (nullable, so include a "None" option)
|
||||||
|
const seasonOptions = [
|
||||||
|
{ value: 0, label: 'None' },
|
||||||
|
...Object.entries(CHARACTER_SEASON_NAMES).map(([value, label]) => ({
|
||||||
|
value: Number(value),
|
||||||
|
label
|
||||||
|
}))
|
||||||
|
]
|
||||||
|
|
||||||
function formatPromotions(promotionNames: string[] | undefined): string {
|
function formatPromotions(promotionNames: string[] | undefined): string {
|
||||||
if (!promotionNames || promotionNames.length === 0) return '—'
|
if (!promotionNames || promotionNames.length === 0) return '—'
|
||||||
return promotionNames.join(', ')
|
return promotionNames.join(', ')
|
||||||
|
|
@ -52,13 +63,30 @@
|
||||||
onDismissSuggestion={() => onDismissSuggestion?.('rarity')}
|
onDismissSuggestion={() => onDismissSuggestion?.('rarity')}
|
||||||
/>
|
/>
|
||||||
<DetailItem
|
<DetailItem
|
||||||
label="Granblue ID"
|
label="Season"
|
||||||
bind:value={editData.granblueId}
|
sublabel="Used to disambiguate characters with the same name"
|
||||||
|
editable={true}
|
||||||
|
>
|
||||||
|
<Select
|
||||||
|
size="medium"
|
||||||
|
options={seasonOptions}
|
||||||
|
bind:value={editData.season}
|
||||||
|
contained
|
||||||
|
/>
|
||||||
|
</DetailItem>
|
||||||
|
<DetailItem
|
||||||
|
label="Character ID"
|
||||||
|
sublabel="Separate multiple IDs with commas"
|
||||||
|
bind:value={editData.characterId}
|
||||||
editable={true}
|
editable={true}
|
||||||
type="text"
|
type="text"
|
||||||
|
placeholder="Character IDs"
|
||||||
/>
|
/>
|
||||||
{:else}
|
{:else}
|
||||||
<DetailItem label="Rarity" value={getRarityLabel(character.rarity)} />
|
<DetailItem label="Rarity" value={getRarityLabel(character.rarity)} />
|
||||||
|
{#if character.season}
|
||||||
|
<DetailItem label="Season" value={getSeasonName(character.season) || '—'} />
|
||||||
|
{/if}
|
||||||
<DetailItem label="Granblue ID">
|
<DetailItem label="Granblue ID">
|
||||||
{#if character.granblueId}
|
{#if character.granblueId}
|
||||||
<CopyableText value={character.granblueId} />
|
<CopyableText value={character.granblueId} />
|
||||||
|
|
@ -66,6 +94,11 @@
|
||||||
—
|
—
|
||||||
{/if}
|
{/if}
|
||||||
</DetailItem>
|
</DetailItem>
|
||||||
|
{#if character.characterId?.length}
|
||||||
|
<DetailItem label="Character ID">
|
||||||
|
<CopyableText value={character.characterId.join(', ')} />
|
||||||
|
</DetailItem>
|
||||||
|
{/if}
|
||||||
{#if character.recruitedBy}
|
{#if character.recruitedBy}
|
||||||
<DetailItem label="Recruited By">
|
<DetailItem label="Recruited By">
|
||||||
<a href="/database/weapons/{character.recruitedBy.id}" class="recruited-by-link">
|
<a href="/database/weapons/{character.recruitedBy.id}" class="recruited-by-link">
|
||||||
|
|
|
||||||
|
|
@ -8,22 +8,11 @@
|
||||||
import MultiSelect from '$lib/components/ui/MultiSelect.svelte'
|
import MultiSelect from '$lib/components/ui/MultiSelect.svelte'
|
||||||
import ElementLabel from '$lib/components/labels/ElementLabel.svelte'
|
import ElementLabel from '$lib/components/labels/ElementLabel.svelte'
|
||||||
import ProficiencyLabel from '$lib/components/labels/ProficiencyLabel.svelte'
|
import ProficiencyLabel from '$lib/components/labels/ProficiencyLabel.svelte'
|
||||||
import { getElementLabel, getElementOptions } from '$lib/utils/element'
|
import { getElementOptions } from '$lib/utils/element'
|
||||||
import { getRaceLabel, getRaceOptions } from '$lib/utils/race'
|
import { getRaceLabel, getRaceOptions } from '$lib/utils/race'
|
||||||
import { getGenderLabel, getGenderOptions } from '$lib/utils/gender'
|
import { getGenderLabel, getGenderOptions } from '$lib/utils/gender'
|
||||||
import { getProficiencyOptions } from '$lib/utils/proficiency'
|
import { getProficiencyOptions } from '$lib/utils/proficiency'
|
||||||
import {
|
import { CHARACTER_SERIES_NAMES, getSeriesNames } from '$lib/types/enums'
|
||||||
CharacterSeason,
|
|
||||||
CharacterSeries,
|
|
||||||
CHARACTER_SEASON_NAMES,
|
|
||||||
CHARACTER_SERIES_NAMES,
|
|
||||||
PROMOTION_NAMES,
|
|
||||||
getSeasonName,
|
|
||||||
getSeriesNames,
|
|
||||||
getPromotionNames
|
|
||||||
} from '$lib/types/enums'
|
|
||||||
|
|
||||||
type ElementName = 'wind' | 'fire' | 'water' | 'earth' | 'dark' | 'light'
|
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
character: any
|
character: any
|
||||||
|
|
@ -51,45 +40,17 @@
|
||||||
const genderOptions = getGenderOptions()
|
const genderOptions = getGenderOptions()
|
||||||
const proficiencyOptions = getProficiencyOptions()
|
const proficiencyOptions = getProficiencyOptions()
|
||||||
|
|
||||||
// Season options (nullable, so include a "None" option)
|
|
||||||
const seasonOptions = [
|
|
||||||
{ value: 0, label: 'None' },
|
|
||||||
...Object.entries(CHARACTER_SEASON_NAMES).map(([value, label]) => ({
|
|
||||||
value: Number(value),
|
|
||||||
label
|
|
||||||
}))
|
|
||||||
]
|
|
||||||
|
|
||||||
// Series options for multiselect
|
// Series options for multiselect
|
||||||
const seriesOptions = Object.entries(CHARACTER_SERIES_NAMES).map(([value, label]) => ({
|
const seriesOptions = Object.entries(CHARACTER_SERIES_NAMES).map(([value, label]) => ({
|
||||||
value: Number(value),
|
value: Number(value),
|
||||||
label
|
label
|
||||||
}))
|
}))
|
||||||
|
|
||||||
// Promotion options for multiselect
|
|
||||||
const promotionOptions = Object.entries(PROMOTION_NAMES).map(([value, label]) => ({
|
|
||||||
value: Number(value),
|
|
||||||
label
|
|
||||||
}))
|
|
||||||
|
|
||||||
// Get element name for checkbox theming
|
|
||||||
const elementName = $derived.by((): ElementName | undefined => {
|
|
||||||
const el = editMode ? editData?.element : character?.element
|
|
||||||
const label = getElementLabel(el)
|
|
||||||
return label !== '—' && label !== 'Null' ? (label.toLowerCase() as ElementName) : undefined
|
|
||||||
})
|
|
||||||
|
|
||||||
// Format series for display
|
// Format series for display
|
||||||
function formatSeriesDisplay(series: number[]): string {
|
function formatSeriesDisplay(series: number[]): string {
|
||||||
if (!series || series.length === 0) return '—'
|
if (!series || series.length === 0) return '—'
|
||||||
return getSeriesNames(series).join(', ')
|
return getSeriesNames(series).join(', ')
|
||||||
}
|
}
|
||||||
|
|
||||||
// Format promotions for display
|
|
||||||
function formatPromotionsDisplay(promotions: number[]): string {
|
|
||||||
if (!promotions || promotions.length === 0) return '—'
|
|
||||||
return getPromotionNames(promotions).join(', ')
|
|
||||||
}
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<DetailsContainer title="Details">
|
<DetailsContainer title="Details">
|
||||||
|
|
@ -160,39 +121,15 @@
|
||||||
onAcceptSuggestion={() => onAcceptSuggestion?.('proficiency2', suggestions?.proficiency2)}
|
onAcceptSuggestion={() => onAcceptSuggestion?.('proficiency2', suggestions?.proficiency2)}
|
||||||
onDismissSuggestion={() => onDismissSuggestion?.('proficiency2')}
|
onDismissSuggestion={() => onDismissSuggestion?.('proficiency2')}
|
||||||
/>
|
/>
|
||||||
<DetailItem
|
|
||||||
label="Season"
|
|
||||||
bind:value={editData.season}
|
|
||||||
editable={true}
|
|
||||||
type="select"
|
|
||||||
options={seasonOptions}
|
|
||||||
/>
|
|
||||||
<DetailItem
|
<DetailItem
|
||||||
label="Series"
|
label="Series"
|
||||||
bind:value={editData.series}
|
|
||||||
editable={true}
|
|
||||||
type="multiselect"
|
|
||||||
options={seriesOptions}
|
|
||||||
element={elementName}
|
|
||||||
/>
|
|
||||||
<DetailItem
|
|
||||||
label="Gacha Available"
|
|
||||||
sublabel="Can be pulled from gacha"
|
|
||||||
bind:value={editData.gacha_available}
|
|
||||||
editable={true}
|
|
||||||
type="checkbox"
|
|
||||||
element={elementName}
|
|
||||||
/>
|
|
||||||
<DetailItem
|
|
||||||
label="Promotions"
|
|
||||||
sublabel="Gacha pools where this character appears"
|
|
||||||
editable={true}
|
editable={true}
|
||||||
>
|
>
|
||||||
<MultiSelect
|
<MultiSelect
|
||||||
size="medium"
|
size="medium"
|
||||||
options={promotionOptions}
|
options={seriesOptions}
|
||||||
bind:value={editData.promotions}
|
bind:value={editData.series}
|
||||||
placeholder="Select promotions"
|
placeholder="Select series"
|
||||||
contained
|
contained
|
||||||
/>
|
/>
|
||||||
</DetailItem>
|
</DetailItem>
|
||||||
|
|
@ -209,13 +146,6 @@
|
||||||
<DetailItem label="Proficiency 2">
|
<DetailItem label="Proficiency 2">
|
||||||
<ProficiencyLabel proficiency={character.proficiency?.[1] ?? 0} size="medium" />
|
<ProficiencyLabel proficiency={character.proficiency?.[1] ?? 0} size="medium" />
|
||||||
</DetailItem>
|
</DetailItem>
|
||||||
<DetailItem label="Season" value={getSeasonName(character.season) || '—'} />
|
|
||||||
<DetailItem label="Series" value={formatSeriesDisplay(character.series)} />
|
<DetailItem label="Series" value={formatSeriesDisplay(character.series)} />
|
||||||
<DetailItem label="Gacha Available" value={character.gachaAvailable ? 'Yes' : 'No'} />
|
|
||||||
<DetailItem
|
|
||||||
label="Promotions"
|
|
||||||
sublabel="Gacha pools where this character appears"
|
|
||||||
value={formatPromotionsDisplay(character.promotions)}
|
|
||||||
/>
|
|
||||||
{/if}
|
{/if}
|
||||||
</DetailsContainer>
|
</DetailsContainer>
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue