From 30cbaf69f874af5f9812cb0c5cc6187bc387d07b Mon Sep 17 00:00:00 2001 From: Matt Young Date: Mon, 20 Oct 2025 01:01:27 -0500 Subject: [PATCH] Allow admin and tabulators to enter and modify prelim scores. --- .../Tabulation/ScoreController.php | 67 +++++++- app/Models/PrelimScoreSheet.php | 6 + .../tabulation/entry_score_sheet.blade.php | 147 ++++++++++++++++-- routes/tabulation.php | 1 + 4 files changed, 206 insertions(+), 15 deletions(-) diff --git a/app/Http/Controllers/Tabulation/ScoreController.php b/app/Http/Controllers/Tabulation/ScoreController.php index d506b47..b25509a 100644 --- a/app/Http/Controllers/Tabulation/ScoreController.php +++ b/app/Http/Controllers/Tabulation/ScoreController.php @@ -2,11 +2,13 @@ namespace App\Http\Controllers\Tabulation; +use App\Actions\Tabulation\EnterPrelimScore; use App\Actions\Tabulation\EnterScore; use App\Exceptions\AuditionAdminException; use App\Http\Controllers\Controller; use App\Models\Entry; use App\Models\EntryTotalScore; +use App\Models\PrelimScoreSheet; use App\Models\ScoreSheet; use App\Models\User; use Illuminate\Http\Request; @@ -67,8 +69,25 @@ class ScoreController extends Controller 'This entry is marked as a no-show. Entering a score will remove the no-show flag'); } + if ($entry->audition->prelimDefinition) { + $existing_prelim_sheets = []; + $prelim_subscores = $entry->audition->prelimDefinition->scoringGuide->subscores->sortBy('display_order'); + $prelim_judges = $entry->audition->prelimDefinition->room->judges; + foreach ($prelim_judges as $judge) { + $prelim_scoreSheet = PrelimScoreSheet::where('entry_id', $entry->id)->where('user_id', $judge->id)->first(); + if ($prelim_scoreSheet) { + Session::flash('caution', 'Prelim scores exist for this entry. Now editing existing scores'); + $existing_prelim_sheets[$judge->id] = $prelim_scoreSheet; + } + } + } else { + $prelim_subscores = null; + $prelim_judges = null; + $existing_prelim_sheets = null; + } + return view('tabulation.entry_score_sheet', - compact('entry', 'judges', 'scoring_guide', 'subscores', 'existing_sheets')); + compact('entry', 'judges', 'scoring_guide', 'subscores', 'existing_sheets', 'prelim_subscores', 'prelim_judges', 'existing_prelim_sheets')); } public function saveEntryScoreSheet(Request $request, Entry $entry, EnterScore $scoreRecorder) @@ -85,7 +104,7 @@ class ScoreController extends Controller * The array should have a key for each subscore and the value of the score submitted */ foreach ($request->all() as $key => $value) { - // We're not interested in submission values that don't ahve judge in the name + // We're not interested in submission values that don't have judge in the name if (! str_contains($key, 'judge')) { continue; } @@ -114,6 +133,50 @@ class ScoreController extends Controller return redirect()->route('scores.chooseEntry')->with('success', 'Scores saved'); } + public function savePrelimEntryScoreSheet(Request $request, Entry $entry, EnterPrelimScore $scoreRecorder) + { + $publishedCheck = $this->checkIfPublished($entry); + if ($publishedCheck) { + return $publishedCheck; + } + + /** + * Here we process the submission from the scoring form. + * We're expecting submitted data to include an array for each judge. + * Each array should be called judge+ the judges ID number + * The array should have a key for each subscore and the value of the score submitted + */ + foreach ($request->all() as $key => $value) { + // We're not interested in submission values that don't have judge in the name + if (! str_contains($key, 'judge')) { + continue; + } + // Extract the judge ID from the field name and load the user + $judge_id = str_replace('judge', '', $key); + $judge = User::find($judge_id); + + // Check for existing scores, if so, tell EnterScores action that we're updating it, otherwise a new score + $existingScore = PrelimScoreSheet::where('entry_id', $entry->id) + ->where('user_id', $judge->id)->first(); + if ($existingScore === null) { + $existingScore = false; + } + + try { + $scoreRecorder($judge, $entry, $value, $existingScore); + } catch (AuditionAdminException $e) { + return redirect()->route('scores.entryScoreSheet', ['entry_id' => $entry->id]) + ->with('error', $e->getMessage()); + } + } + + // Since we're entering a score, this apparently isn't a no show. + $entry->removeFlag('no_show'); + + return redirect()->route('scores.chooseEntry')->with('success', 'Prelim Scores Saved'); + + } + protected function checkIfPublished($entry) { // We're not going to enter scores if seats are published diff --git a/app/Models/PrelimScoreSheet.php b/app/Models/PrelimScoreSheet.php index 2502e25..67ff953 100644 --- a/app/Models/PrelimScoreSheet.php +++ b/app/Models/PrelimScoreSheet.php @@ -25,4 +25,10 @@ class PrelimScoreSheet extends Model { return $this->hasOne(Entry::class); } + + public function getSubscore($id) + { + return $this->subscores[$id]['score'] ?? false; + // this function is used at resources/views/tabulation/entry_score_sheet.blade.php + } } diff --git a/resources/views/tabulation/entry_score_sheet.blade.php b/resources/views/tabulation/entry_score_sheet.blade.php index 248b417..6f25d0f 100644 --- a/resources/views/tabulation/entry_score_sheet.blade.php +++ b/resources/views/tabulation/entry_score_sheet.blade.php @@ -3,7 +3,17 @@ Entry Score Sheet - {{ $entry->audition->name }} #{{ $entry->draw_number }} + {{ $entry->audition->name }} #{{ $entry->draw_number }} FINALS SCORES + @if($entry->hasFlag('failed_prelim')) + Failed Prelim + @elseif($entry->hasFlag('passed_prelim')) + Passed Prelim + @elseif($entry->audition->prelimDefinition) + Prelim Pending + @endif ID #{{ $entry->id }}

{{ $entry->student->full_name() }}

@@ -11,7 +21,8 @@
- + @@ -33,7 +44,7 @@ @foreach($judges as $judge) @php($existingSheet = $existing_sheets[$judge->id] ?? null) - + {{ $judge->full_name() }} @foreach($subscores as $subscore) @@ -48,11 +59,11 @@ value="{{ $existingSheet->getSubscore($subscore->id) }}" @endif required -{{-- onchange="judge{{$judge->id}}sum()"--}} + {{-- onchange="judge{{$judge->id}}sum()"--}} > @endforeach - +

0.000

@@ -67,35 +78,145 @@
+ + @if($entry->audition->prelimDefinition) + + + {{ $entry->audition->name }} #{{ $entry->draw_number }} PRELIM SCORES + ID #{{ $entry->id }} + +

{{ $entry->student->full_name() }}

+

{{ $entry->student->school->name }}

+
+
+ + + + + + Judges + @foreach($prelim_subscores as $subscore) + +
+
{{ $subscore->name }}
+
+ Max: {{ $subscore->max_score }} + Weight: {{ $subscore->weight }} +
+
+
+ @endforeach + Total + + + + @foreach($prelim_judges as $judge) + @php($existingSheet = $existing_prelim_sheets[$judge->id] ?? null) + + {{ $judge->full_name() }} + @foreach($prelim_subscores as $subscore) + + + + @endforeach + +

+ 0.000 +

+
+ + @endforeach +
+
+ + Save Scores + +
+ +
+ @endif + + + + @if($entry->audition->prelimDefinition) + + @endif + diff --git a/routes/tabulation.php b/routes/tabulation.php index d2e5ab1..bf1acfe 100644 --- a/routes/tabulation.php +++ b/routes/tabulation.php @@ -21,6 +21,7 @@ Route::middleware(['auth', 'verified', CheckIfCanTab::class])->group(function () Route::get('/choose_entry', 'chooseEntry')->name('scores.chooseEntry'); Route::get('/entry', 'entryScoreSheet')->name('scores.entryScoreSheet'); Route::post('/entry/{entry}', 'saveEntryScoreSheet')->name('scores.saveEntryScoreSheet'); + Route::post('/entry/prelim/{entry}', 'savePrelimEntryScoreSheet')->name('scores.savePrelimEntryScoreSheet'); Route::delete('/{score}', 'destroyScore')->name('scores.destroy'); });