flag and end of attempt

master
gitea 4 weeks ago
parent fe9c5a9fec
commit 187d74db8d

@ -3,6 +3,7 @@ import 'package:practice_engine/practice_engine.dart';
import '../routes.dart';
import '../widgets/status_chip.dart';
import '../services/deck_storage.dart';
import '../utils/top_snackbar.dart';
class AttemptResultScreen extends StatefulWidget {
const AttemptResultScreen({super.key});
@ -82,6 +83,42 @@ class _AttemptResultScreenState extends State<AttemptResultScreen> {
);
}
Question? _currentQuestionInDeck(String questionId) {
if (_deck == null) return null;
try {
return _deck!.questions.firstWhere((q) => q.id == questionId);
} catch (_) {
return null;
}
}
void _toggleFlag(String questionId) {
if (_deck == null) return;
setState(() {
_deck = DeckService.toggleQuestionFlag(deck: _deck!, questionId: questionId);
});
_deckStorage.saveDeckSync(_deck!);
final q = _currentQuestionInDeck(questionId);
showTopSnackBar(
context,
q?.isFlagged == true ? 'Question flagged for review' : 'Question unflagged',
backgroundColor: q?.isFlagged == true ? Colors.orange : null,
);
}
void _markNeedsPractice(String questionId) {
if (_deck == null) return;
setState(() {
_deck = DeckService.markQuestionAsNeedsPractice(deck: _deck!, questionId: questionId);
});
_deckStorage.saveDeckSync(_deck!);
showTopSnackBar(
context,
'Marked as needs practice',
backgroundColor: Colors.blue,
);
}
@override
Widget build(BuildContext context) {
if (_deck == null || _result == null) {
@ -217,6 +254,8 @@ class _AttemptResultScreenState extends State<AttemptResultScreen> {
),
const SizedBox(height: 12),
..._result!.incorrectQuestions.map((answerResult) {
final currentQ = _currentQuestionInDeck(answerResult.question.id);
final isFlagged = currentQ?.isFlagged ?? false;
return Card(
margin: const EdgeInsets.only(bottom: 8),
child: Padding(
@ -250,6 +289,25 @@ class _AttemptResultScreenState extends State<AttemptResultScreen> {
fontWeight: FontWeight.bold,
),
),
const SizedBox(height: 12),
Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
TextButton.icon(
onPressed: () => _markNeedsPractice(answerResult.question.id),
icon: const Icon(Icons.replay, size: 20),
label: const Text('Needs practice'),
),
IconButton(
onPressed: () => _toggleFlag(answerResult.question.id),
icon: Icon(
isFlagged ? Icons.flag : Icons.outlined_flag,
color: isFlagged ? Colors.red : null,
),
tooltip: isFlagged ? 'Unflag' : 'Flag for review',
),
],
),
],
),
),
@ -265,6 +323,8 @@ class _AttemptResultScreenState extends State<AttemptResultScreen> {
),
const SizedBox(height: 12),
..._result!.allResults.map((answerResult) {
final currentQ = _currentQuestionInDeck(answerResult.question.id);
final isFlagged = currentQ?.isFlagged ?? false;
return Card(
margin: const EdgeInsets.only(bottom: 8),
child: ListTile(
@ -274,7 +334,26 @@ class _AttemptResultScreenState extends State<AttemptResultScreen> {
? 'Correct'
: 'Incorrect - Selected: ${answerResult.userAnswerIndices.map((idx) => answerResult.question.answers[idx]).join(', ')}',
),
trailing: StatusChip(statusChange: answerResult.statusChange),
trailing: Row(
mainAxisSize: MainAxisSize.min,
children: [
StatusChip(statusChange: answerResult.statusChange),
IconButton(
onPressed: () => _markNeedsPractice(answerResult.question.id),
icon: const Icon(Icons.replay, size: 22),
tooltip: 'Mark as needs practice',
),
IconButton(
onPressed: () => _toggleFlag(answerResult.question.id),
icon: Icon(
isFlagged ? Icons.flag : Icons.outlined_flag,
color: isFlagged ? Colors.red : null,
size: 22,
),
tooltip: isFlagged ? 'Unflag' : 'Flag for review',
),
],
),
),
);
}),

Loading…
Cancel
Save

Powered by TurnKey Linux.