diff options
| author | nsfisis <nsfisis@gmail.com> | 2025-12-31 13:31:46 +0900 |
|---|---|---|
| committer | nsfisis <nsfisis@gmail.com> | 2025-12-31 13:31:46 +0900 |
| commit | 25f29d1016a6083f97d3ed094142ff1ca9faf775 (patch) | |
| tree | b43455e14f0a90f07ca11e2e408840082f326575 /src/client/pages | |
| parent | ce9011bf351d9666bb2e81c92ae06a0eb1716d12 (diff) | |
| download | kioku-25f29d1016a6083f97d3ed094142ff1ca9faf775.tar.gz kioku-25f29d1016a6083f97d3ed094142ff1ca9faf775.tar.zst kioku-25f29d1016a6083f97d3ed094142ff1ca9faf775.zip | |
feat(client): add EditNoteModal for editing note-based cards
- Create EditNoteModal component that loads note and field values
- Update DeckDetailPage to use EditNoteModal for cards with noteId
- Keep EditCardModal for legacy cards without note association
- Add visual indicator for reversed cards in card list
- Add comprehensive tests for EditNoteModal
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Diffstat (limited to 'src/client/pages')
| -rw-r--r-- | src/client/pages/DeckDetailPage.tsx | 29 |
1 files changed, 27 insertions, 2 deletions
diff --git a/src/client/pages/DeckDetailPage.tsx b/src/client/pages/DeckDetailPage.tsx index 9a158f6..a06fcc7 100644 --- a/src/client/pages/DeckDetailPage.tsx +++ b/src/client/pages/DeckDetailPage.tsx @@ -14,10 +14,13 @@ import { ApiClientError, apiClient } from "../api"; import { CreateNoteModal } from "../components/CreateNoteModal"; import { DeleteCardModal } from "../components/DeleteCardModal"; import { EditCardModal } from "../components/EditCardModal"; +import { EditNoteModal } from "../components/EditNoteModal"; interface Card { id: string; deckId: string; + noteId: string | null; + isReversed: boolean | null; front: string; back: string; state: number; @@ -56,6 +59,7 @@ export function DeckDetailPage() { const [error, setError] = useState<string | null>(null); const [isCreateModalOpen, setIsCreateModalOpen] = useState(false); const [editingCard, setEditingCard] = useState<Card | null>(null); + const [editingNoteId, setEditingNoteId] = useState<string | null>(null); const [deletingCard, setDeletingCard] = useState<Card | null>(null); const fetchDeck = useCallback(async () => { @@ -311,6 +315,11 @@ export function DeckDetailPage() { > {CardStateLabels[card.state] || "Unknown"} </span> + {card.isReversed && ( + <span className="px-2 py-0.5 rounded-full font-medium bg-slate/10 text-slate"> + Reversed + </span> + )} <span className="text-muted"> {card.reps} reviews </span> @@ -326,9 +335,15 @@ export function DeckDetailPage() { <div className="flex items-center gap-1 shrink-0"> <button type="button" - onClick={() => setEditingCard(card)} + onClick={() => { + if (card.noteId) { + setEditingNoteId(card.noteId); + } else { + setEditingCard(card); + } + }} className="p-2 text-muted hover:text-slate hover:bg-ivory rounded-lg transition-colors" - title="Edit card" + title={card.noteId ? "Edit note" : "Edit card"} > <FontAwesomeIcon icon={faPen} @@ -379,6 +394,16 @@ export function DeckDetailPage() { )} {deckId && ( + <EditNoteModal + isOpen={editingNoteId !== null} + deckId={deckId} + noteId={editingNoteId} + onClose={() => setEditingNoteId(null)} + onNoteUpdated={fetchCards} + /> + )} + + {deckId && ( <DeleteCardModal isOpen={deletingCard !== null} deckId={deckId} |
