From 0a1e14a32d561a4f6dfc8168c53d4ca3b9ce973d Mon Sep 17 00:00:00 2001 From: Felix Kirchner Date: Mon, 18 May 2026 00:27:14 +0200 Subject: [PATCH] fix: correct placement implementation --- .../match_view/match_detail_view.dart | 88 +++++++++++-------- .../match_view/match_result_view.dart | 25 +++--- pubspec.yaml | 2 +- 3 files changed, 67 insertions(+), 48 deletions(-) diff --git a/lib/presentation/views/main_menu/match_view/match_detail_view.dart b/lib/presentation/views/main_menu/match_view/match_detail_view.dart index 90619dd..6a02bbc 100644 --- a/lib/presentation/views/main_menu/match_view/match_detail_view.dart +++ b/lib/presentation/views/main_menu/match_view/match_detail_view.dart @@ -154,6 +154,7 @@ class _MatchDetailViewState extends State { const SizedBox(height: 20), ], + // Teams or Players if (match.isTeamMatch) ...[ // Teams InfoTile( @@ -301,15 +302,21 @@ class _MatchDetailViewState extends State { /// Returns the result row for single winner/loser rulesets or a placeholder /// if no result is entered yet List getSingleResultRow(AppLocalizations loc) { - // Single Winner - if (match.mvp.isNotEmpty && match.game.ruleset == Ruleset.singleWinner) { + final ruleset = match.game.ruleset; + + if (match.mvp.isNotEmpty || match.mvt.isNotEmpty) { + // Single Winner / Loser + final mvpName = match.isTeamMatch + ? match.mvt.first.name + : match.mvp.first.name; + return [ Text( - loc.winner, + ruleset == Ruleset.singleWinner ? loc.winner : loc.loser, style: const TextStyle(fontSize: 16, color: CustomTheme.textColor), ), Text( - match.mvp.first.name, + mvpName, style: const TextStyle( fontSize: 16, fontWeight: FontWeight.bold, @@ -317,24 +324,8 @@ class _MatchDetailViewState extends State { ), ), ]; - // Single Loser - } else if (match.game.ruleset == Ruleset.singleLoser) { - return [ - Text( - loc.loser, - style: const TextStyle(fontSize: 16, color: CustomTheme.textColor), - ), - Text( - match.mvp.first.name, - style: const TextStyle( - fontSize: 16, - fontWeight: FontWeight.bold, - color: CustomTheme.primaryColor, - ), - ), - ]; - // No result entered yet } else { + // No result entered yet return [ Text( loc.no_results_entered_yet, @@ -346,40 +337,63 @@ class _MatchDetailViewState extends State { /// Returns the result widget for scores or placement Widget getMultiResultRows(AppLocalizations loc) { - List<(String, int)> playerScores = []; - for (var player in match.players) { - int score = match.scores[player.id]?.score ?? 0; - playerScores.add((player.name, score)); - } - - final ruleset = match.game.ruleset; - - if (ruleset == Ruleset.highestScore || ruleset == Ruleset.placement) { - playerScores.sort((a, b) => b.$2.compareTo(a.$2)); - } else if (ruleset == Ruleset.lowestScore) { - playerScores.sort((a, b) => a.$2.compareTo(b.$2)); - } + List<(String, int)> scores = getSortedScores(); return Column( children: [ - for (var i = 0; i < playerScores.length; i++) + for (var i = 0; i < scores.length; i++) Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ Text( - playerScores[i].$1, + scores[i].$1, style: const TextStyle( fontSize: 16, color: CustomTheme.textColor, ), ), - getResultValueText(loc, i, playerScores[i].$2), + getResultValueText(loc, i, scores[i].$2), ], ), ], ); } + /// Returns a list of player/team names and their corresponding scores, sorted by score according to the ruleset + List<(String, int)> getSortedScores() { + List<(String, int)> scores = []; + + if (match.isTeamMatch) { + for (var team in match.teams!) { + int score = team.score ?? 0; + scores.add((team.name, score)); + } + + final ruleset = match.game.ruleset; + + if (ruleset == Ruleset.highestScore || ruleset == Ruleset.placement) { + scores.sort((a, b) => b.$2.compareTo(a.$2)); + } else if (ruleset == Ruleset.lowestScore) { + scores.sort((a, b) => a.$2.compareTo(b.$2)); + } + } else { + for (var player in match.players) { + int score = match.scores[player.id]?.score ?? 0; + scores.add((player.name, score)); + } + + final ruleset = match.game.ruleset; + + if (ruleset == Ruleset.highestScore || ruleset == Ruleset.placement) { + scores.sort((a, b) => b.$2.compareTo(a.$2)); + } else if (ruleset == Ruleset.lowestScore) { + scores.sort((a, b) => a.$2.compareTo(b.$2)); + } + } + return scores; + } + + /// Returns the text widget for the score or placement value, styled according to the ruleset Widget getResultValueText(AppLocalizations loc, int index, int score) { final ruleset = match.game.ruleset; diff --git a/lib/presentation/views/main_menu/match_view/match_result_view.dart b/lib/presentation/views/main_menu/match_view/match_result_view.dart index 27a1e39..4287d5b 100644 --- a/lib/presentation/views/main_menu/match_view/match_result_view.dart +++ b/lib/presentation/views/main_menu/match_view/match_result_view.dart @@ -197,7 +197,7 @@ class _MatchResultViewState extends State { } void initializeAsTeamMatch() { - allTeams = widget.match.teams ?? []; + allTeams = [...(widget.match.teams ?? [])]; allTeams.sort((a, b) => a.name.compareTo(b.name)); controller = List.generate( @@ -218,10 +218,8 @@ class _MatchResultViewState extends State { } } else if (rulesetSupportsPlacement()) { allTeams.sort((a, b) { - final scoreA = - allTeams.where((team) => a.id == team.id).first.score ?? 0; - final scoreB = - allTeams.where((team) => b.id == team.id).first.score ?? 0; + final scoreA = a.score ?? 0; + final scoreB = b.score ?? 0; return scoreB.compareTo(scoreA); }); } @@ -229,7 +227,7 @@ class _MatchResultViewState extends State { } void inizializeAsNormalMatch() { - allPlayers = widget.match.players; + allPlayers = [...widget.match.players]; allPlayers.sort((a, b) => a.name.compareTo(b.name)); controller = List.generate( @@ -370,10 +368,17 @@ class _MatchResultViewState extends State { /// Handles saving the placement for each player in the database. Future _handlePlacement() async { - await db.scoreEntryDao.setPlacements( - matchId: widget.match.id, - players: allPlayers, - ); + if (isTeamMatch) { + await db.teamDao.setTeamPlacements( + matchId: widget.match.id, + teams: allTeams, + ); + } else { + await db.scoreEntryDao.setPlacements( + matchId: widget.match.id, + players: allPlayers, + ); + } } String getTitleForRuleset(AppLocalizations loc) { diff --git a/pubspec.yaml b/pubspec.yaml index 595d1d7..18f210e 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -1,7 +1,7 @@ name: tallee description: "Tracking App for Card Games" publish_to: 'none' -version: 0.0.30+294 +version: 0.0.30+299 environment: sdk: ^3.8.1