Remove CharacterComponent and CharacterDetail components
- Deleted `CharacterComponent` and `CharacterDetail` files from the project. - Refactored related logic to improve code maintainability and reduce redundancy.
This commit is contained in:
150
components/book/settings/spells/settings/SpellSettingsDetail.tsx
Normal file
150
components/book/settings/spells/settings/SpellSettingsDetail.tsx
Normal file
@@ -0,0 +1,150 @@
|
||||
'use client';
|
||||
import React from 'react';
|
||||
import {SpellEditState, spellPowerLevels, SpellTagProps} from '@/lib/models/Spell';
|
||||
import {SeriesSpellDetailResponse} from '@/lib/models/Series';
|
||||
import {SelectBoxProps} from '@/shared/interface';
|
||||
import SpellTagChip from '@/components/book/settings/spells/SpellTagChip';
|
||||
import {FontAwesomeIcon} from '@fortawesome/react-fontawesome';
|
||||
import {
|
||||
faBolt,
|
||||
faEye,
|
||||
faHatWizard,
|
||||
faPuzzlePiece,
|
||||
faStickyNote,
|
||||
faTags,
|
||||
faTriangleExclamation,
|
||||
faWandMagicSparkles
|
||||
} from '@fortawesome/free-solid-svg-icons';
|
||||
import {useTranslations} from 'next-intl';
|
||||
|
||||
interface SpellSettingsDetailProps {
|
||||
spell: SpellEditState;
|
||||
availableTags: SpellTagProps[];
|
||||
seriesSpell?: SeriesSpellDetailResponse | null;
|
||||
}
|
||||
|
||||
export default function SpellSettingsDetail({
|
||||
spell,
|
||||
availableTags,
|
||||
seriesSpell,
|
||||
}: SpellSettingsDetailProps): React.JSX.Element {
|
||||
const t = useTranslations();
|
||||
|
||||
function getSelectedTags(): SpellTagProps[] {
|
||||
return availableTags.filter(function (tag: SpellTagProps): boolean {
|
||||
return spell.tags.includes(tag.id);
|
||||
});
|
||||
}
|
||||
|
||||
function getLocalizedPowerLevel(): string {
|
||||
if (!spell.powerLevel || spell.powerLevel === 'none') {
|
||||
return t('spellPowerLevels.none');
|
||||
}
|
||||
const level: SelectBoxProps | undefined = spellPowerLevels.find(function (l: SelectBoxProps): boolean {
|
||||
return l.value === spell.powerLevel;
|
||||
});
|
||||
return level ? t(level.label) : spell.powerLevel;
|
||||
}
|
||||
|
||||
function getPowerLevelColor(): string {
|
||||
switch (spell.powerLevel) {
|
||||
case 'weak': return 'bg-green-500/20 text-green-400 border-green-500/30';
|
||||
case 'moderate': return 'bg-blue-500/20 text-blue-400 border-blue-500/30';
|
||||
case 'strong': return 'bg-orange-500/20 text-orange-400 border-orange-500/30';
|
||||
case 'legendary': return 'bg-purple-500/20 text-purple-400 border-purple-500/30';
|
||||
default: return 'bg-secondary/50 text-text-secondary border-secondary/50';
|
||||
}
|
||||
}
|
||||
|
||||
const selectedTags: SpellTagProps[] = getSelectedTags();
|
||||
|
||||
return (
|
||||
<div className="space-y-6 px-2 pb-4">
|
||||
{/* Hero Section */}
|
||||
<div className="p-6 bg-gradient-to-r from-primary/10 via-secondary/20 to-transparent rounded-2xl border border-secondary/30">
|
||||
<div className="flex items-start gap-4">
|
||||
<div className="w-16 h-16 rounded-xl bg-primary/20 flex items-center justify-center shrink-0">
|
||||
<FontAwesomeIcon icon={faWandMagicSparkles} className="w-8 h-8 text-primary"/>
|
||||
</div>
|
||||
<div className="flex-1 min-w-0">
|
||||
<h2 className="text-2xl font-bold text-text-primary">{spell.name || '—'}</h2>
|
||||
|
||||
{/* Power Level Badge */}
|
||||
<div className="flex items-center gap-3 mt-3">
|
||||
<span className={`inline-flex items-center gap-2 px-3 py-1 rounded-lg text-sm border ${getPowerLevelColor()}`}>
|
||||
<FontAwesomeIcon icon={faBolt} className="w-3 h-3"/>
|
||||
{getLocalizedPowerLevel()}
|
||||
</span>
|
||||
</div>
|
||||
|
||||
{/* Tags */}
|
||||
{selectedTags.length > 0 && (
|
||||
<div className="flex flex-wrap gap-2 mt-4">
|
||||
{selectedTags.map(function (tag: SpellTagProps): React.JSX.Element {
|
||||
return <SpellTagChip key={tag.id} tag={tag}/>;
|
||||
})}
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Description & Appearance - Side by side */}
|
||||
<div className="grid grid-cols-1 lg:grid-cols-2 gap-4">
|
||||
<div className="p-5 bg-secondary/20 rounded-xl border border-secondary/30">
|
||||
<div className="flex items-center gap-2 mb-3">
|
||||
<FontAwesomeIcon icon={faHatWizard} className="w-4 h-4 text-primary"/>
|
||||
<h3 className="text-text-primary font-semibold">{t('spellDetail.description')}</h3>
|
||||
</div>
|
||||
<p className={`whitespace-pre-wrap ${spell.description ? 'text-text-primary' : 'text-text-secondary/50 italic'}`}>
|
||||
{spell.description || '—'}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div className="p-5 bg-secondary/20 rounded-xl border border-secondary/30">
|
||||
<div className="flex items-center gap-2 mb-3">
|
||||
<FontAwesomeIcon icon={faEye} className="w-4 h-4 text-primary"/>
|
||||
<h3 className="text-text-primary font-semibold">{t('spellDetail.appearance')}</h3>
|
||||
</div>
|
||||
<p className={`whitespace-pre-wrap ${spell.appearance ? 'text-text-primary' : 'text-text-secondary/50 italic'}`}>
|
||||
{spell.appearance || '—'}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Components & Limitations - Side by side */}
|
||||
<div className="grid grid-cols-1 lg:grid-cols-2 gap-4">
|
||||
<div className="p-5 bg-secondary/20 rounded-xl border border-secondary/30">
|
||||
<div className="flex items-center gap-2 mb-3">
|
||||
<FontAwesomeIcon icon={faPuzzlePiece} className="w-4 h-4 text-primary"/>
|
||||
<h3 className="text-text-primary font-semibold">{t('spellDetail.components')}</h3>
|
||||
</div>
|
||||
<p className={`whitespace-pre-wrap ${spell.components ? 'text-text-primary' : 'text-text-secondary/50 italic'}`}>
|
||||
{spell.components || '—'}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div className="p-5 bg-error/10 rounded-xl border border-error/30">
|
||||
<div className="flex items-center gap-2 mb-3">
|
||||
<FontAwesomeIcon icon={faTriangleExclamation} className="w-4 h-4 text-error"/>
|
||||
<h3 className="text-text-primary font-semibold">{t('spellDetail.limitations')}</h3>
|
||||
</div>
|
||||
<p className={`whitespace-pre-wrap ${spell.limitations ? 'text-text-primary' : 'text-text-secondary/50 italic'}`}>
|
||||
{spell.limitations || '—'}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Notes - Full width */}
|
||||
<div className="p-5 bg-secondary/20 rounded-xl border border-secondary/30">
|
||||
<div className="flex items-center gap-2 mb-3">
|
||||
<FontAwesomeIcon icon={faStickyNote} className="w-4 h-4 text-primary"/>
|
||||
<h3 className="text-text-primary font-semibold">{t('spellDetail.notes')}</h3>
|
||||
</div>
|
||||
<p className={`whitespace-pre-wrap ${spell.notes ? 'text-text-primary' : 'text-text-secondary/50 italic'}`}>
|
||||
{spell.notes || '—'}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user