feat: [frontend] Start to play around with Flashcard creation UI
This commit is contained in:
parent
f463454e8e
commit
170f851344
3 changed files with 109 additions and 0 deletions
45
frontend/src/lib/components/Flashcard.svelte
Normal file
45
frontend/src/lib/components/Flashcard.svelte
Normal file
|
|
@ -0,0 +1,45 @@
|
||||||
|
<script lang="ts">
|
||||||
|
interface Props {
|
||||||
|
promptText: string;
|
||||||
|
correctAnswers: string[];
|
||||||
|
}
|
||||||
|
|
||||||
|
let { promptText, correctAnswers }: Props = $props();
|
||||||
|
|
||||||
|
let mode: 'guess' | 'reveal' = 'reveal';
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<section class="flashcard">
|
||||||
|
<div class="prompt-text">
|
||||||
|
<p class="prompt-text__text">{promptText}</p>
|
||||||
|
</div>
|
||||||
|
<div class="answer-text">
|
||||||
|
<label for="answer" class="label">Answer</label>
|
||||||
|
<input type="text" id="answer" class="input" />
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{#if mode === 'reveal'}
|
||||||
|
<div class="correct-answers">
|
||||||
|
<p class="correct-answers__label">Correct Answers:</p>
|
||||||
|
<ul class="correct-answers__list">
|
||||||
|
{#each correctAnswers as answer}
|
||||||
|
<li class="correct-answers__item">{answer}</li>
|
||||||
|
{/each}
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
{/if}
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.flashcard {
|
||||||
|
padding: var(--space-1);
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr;
|
||||||
|
place-items: center;
|
||||||
|
max-width: 500px;
|
||||||
|
border: 1px solid var(--colour-grey-300);
|
||||||
|
}
|
||||||
|
|
||||||
|
.prompt-text {
|
||||||
|
}
|
||||||
|
</style>
|
||||||
6
frontend/src/routes/app/flashcards/new/+page.svelte
Normal file
6
frontend/src/routes/app/flashcards/new/+page.svelte
Normal file
|
|
@ -0,0 +1,6 @@
|
||||||
|
<script>
|
||||||
|
import FlashcardForm from './FlashcardForm.svelte';
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<h1>New Flashcard</h1>
|
||||||
|
<FlashcardForm />
|
||||||
58
frontend/src/routes/app/flashcards/new/FlashcardForm.svelte
Normal file
58
frontend/src/routes/app/flashcards/new/FlashcardForm.svelte
Normal file
|
|
@ -0,0 +1,58 @@
|
||||||
|
<script lang="ts">
|
||||||
|
import Flashcard from '$lib/components/Flashcard.svelte';
|
||||||
|
import {
|
||||||
|
dictionarySearch,
|
||||||
|
type DictionarySearchResult
|
||||||
|
} from '../../admin/dictionary-search/dictionarySearch.remote';
|
||||||
|
|
||||||
|
let dictionarySearchDebouncer: NodeJS.Timeout | null = null;
|
||||||
|
let dictionarySearchTerm = $state('');
|
||||||
|
let promptText = $state('bonjour');
|
||||||
|
let answerText = $state('hello');
|
||||||
|
let dictionarySearchResults: DictionarySearchResult[] = $state([]);
|
||||||
|
let correctAnswers = $derived(
|
||||||
|
answerText
|
||||||
|
.split(',')
|
||||||
|
.map((t) => t.trim())
|
||||||
|
.filter((t) => t.length)
|
||||||
|
);
|
||||||
|
|
||||||
|
$effect(() => {
|
||||||
|
if (dictionarySearchDebouncer) {
|
||||||
|
clearTimeout(dictionarySearchDebouncer);
|
||||||
|
}
|
||||||
|
|
||||||
|
dictionarySearchDebouncer = setTimeout(() => {
|
||||||
|
dictionarySearch({ langCode: 'fr', text: dictionarySearchTerm }).then((results) => {
|
||||||
|
dictionarySearchResults = results;
|
||||||
|
});
|
||||||
|
}, 500);
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="form-container">
|
||||||
|
<form class="form">
|
||||||
|
<div class="field">
|
||||||
|
<label for="target_word">French Word</label>
|
||||||
|
<input type="text" id="target_word" name="target_word" bind:value={dictionarySearchTerm} />
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="field">
|
||||||
|
<label for="prompt_text">Prompt Text</label>
|
||||||
|
<input type="text" id="prompt_text" name="prompt_text" bind:value={promptText} />
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="field">
|
||||||
|
<label for="answer_text">Answers (comma separated)</label>
|
||||||
|
<input type="text" id="answer_text" name="answer_text" bind:value={answerText} />
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<Flashcard {promptText} {correctAnswers} />
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.form-container {
|
||||||
|
max-width: 500px;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
Loading…
Reference in a new issue