You've already forked Atomcms-edit
240 lines
8.1 KiB
PHP
Executable File
240 lines
8.1 KiB
PHP
Executable File
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
namespace App\Filament\Pages\Radio;
|
|
|
|
use App\Models\RadioContest;
|
|
use Filament\Actions\Action;
|
|
use Filament\Forms\Components\DateTimePicker;
|
|
use Filament\Forms\Components\Select;
|
|
use Filament\Forms\Components\Textarea;
|
|
use Filament\Forms\Components\TextInput;
|
|
use Filament\Forms\Components\Toggle;
|
|
use Filament\Forms\Concerns\InteractsWithForms;
|
|
use Filament\Forms\Contracts\HasForms;
|
|
use Filament\Notifications\Notification;
|
|
use Filament\Pages\Page;
|
|
use Filament\Schemas\Components\Section;
|
|
use Filament\Schemas\Schema;
|
|
|
|
final class ContestManagement extends Page implements HasForms
|
|
{
|
|
use InteractsWithForms;
|
|
|
|
#[\Override]
|
|
protected static string|\BackedEnum|null $navigationIcon = 'heroicon-o-trophy';
|
|
|
|
#[\Override]
|
|
protected static string|\UnitEnum|null $navigationGroup = 'Radio';
|
|
|
|
#[\Override]
|
|
protected static ?string $navigationLabel = null;
|
|
|
|
#[\Override]
|
|
public static function getNavigationLabel(): string
|
|
{
|
|
return __('Contests');
|
|
}
|
|
|
|
#[\Override]
|
|
protected static ?string $title = 'Competities Beheer';
|
|
|
|
#[\Override]
|
|
protected string $view = 'filament.pages.radio.contest-management';
|
|
|
|
/** @var array<string, mixed> */
|
|
public array $data = [];
|
|
|
|
public function mount(): void
|
|
{
|
|
$this->fillForm();
|
|
}
|
|
|
|
protected function fillForm(): void
|
|
{
|
|
$contests = RadioContest::orderBy('created_at', 'desc')->get();
|
|
|
|
$this->data['contests'] = $contests->toArray();
|
|
$this->data['active_contest'] = $contests->firstWhere('is_active', true)?->id;
|
|
}
|
|
|
|
public function form(Schema $schema): Schema
|
|
{
|
|
return $schema
|
|
->components([
|
|
Section::make('Nieuwe Competitie Aanmaken')
|
|
->description('Maak een nieuwe competitie aan')
|
|
->columns(1)
|
|
->headerActions([
|
|
Action::make('create_contest')
|
|
->label('Competitie Aanmaken')
|
|
->action('createContest')
|
|
->color('success'),
|
|
])
|
|
->schema([
|
|
TextInput::make('contest.title')
|
|
->label('Titel')
|
|
->required()
|
|
->placeholder('Bijv. Beste Song Suggestie'),
|
|
Textarea::make('contest.description')
|
|
->label('Beschrijving')
|
|
->rows(3)
|
|
->placeholder('Beschrijf de competitie regels...'),
|
|
TextInput::make('contest.prize')
|
|
->label('Prijs')
|
|
->required()
|
|
->placeholder('Bijv. VIP voor 1 maand'),
|
|
TextInput::make('contest.max_winners')
|
|
->label('Aantal Winnaars')
|
|
->numeric()
|
|
->default(1)
|
|
->placeholder('1'),
|
|
DateTimePicker::make('contest.starts_at')
|
|
->label('Start Datum/Tijd')
|
|
->required()
|
|
->default(now()),
|
|
DateTimePicker::make('contest.ends_at')
|
|
->label('Eind Datum/Tijd')
|
|
->required()
|
|
->default(now()->addDays(14)),
|
|
Toggle::make('contest.require_approval')
|
|
->label('Goedkeuring Vereist')
|
|
->default(false),
|
|
]),
|
|
Section::make('Actieve Competities')
|
|
->description('Beheer lopende competities')
|
|
->columns(1)
|
|
->schema([
|
|
Select::make('selected_contest')
|
|
->label('Selecteer Competitie')
|
|
->options(RadioContest::where('is_active', true)->pluck('title', 'id'))
|
|
->placeholder('Kies een competitie...')
|
|
->live(),
|
|
]),
|
|
Section::make('Acties')
|
|
->description('Competitie beheer')
|
|
->columns(2)
|
|
->schema([
|
|
Action::make('end_contest')
|
|
->label('Competitie Beëindigen')
|
|
->action('endContest')
|
|
->color('danger')
|
|
->requiresConfirmation(),
|
|
Action::make('declare_winners')
|
|
->label('Winnaars Bekend Maken')
|
|
->action('declareWinners')
|
|
->color('warning')
|
|
->requiresConfirmation(),
|
|
]),
|
|
Section::make('Afgelopen Competities')
|
|
->description('Bekijk resultaten van afgelopen competities')
|
|
->columns(1)
|
|
->schema([
|
|
Select::make('ended_contest')
|
|
->label('Selecteer Afgelopen Competitie')
|
|
->options(RadioContest::where('is_ended', true)->pluck('title', 'id'))
|
|
->placeholder('Kies een competitie...'),
|
|
]),
|
|
])
|
|
->statePath('data');
|
|
}
|
|
|
|
public function createContest(): void
|
|
{
|
|
$data = $this->data['contest'] ?? [];
|
|
|
|
$contest = RadioContest::create([
|
|
'title' => $data['title'],
|
|
'description' => $data['description'] ?? '',
|
|
'prize' => $data['prize'],
|
|
'max_winners' => $data['max_winners'] ?? 1,
|
|
'starts_at' => $data['starts_at'] ?? now(),
|
|
'ends_at' => $data['ends_at'] ?? now()->addDays(14),
|
|
'is_active' => true,
|
|
'is_ended' => false,
|
|
'winners_announced' => false,
|
|
'require_approval' => $data['require_approval'] ?? false,
|
|
]);
|
|
|
|
$this->fillForm();
|
|
|
|
Notification::make()
|
|
->success()
|
|
->title('Competitie Aangemaakt')
|
|
->body("Competitie '{$contest->title}' is succesvol aangemaakt!")
|
|
->send();
|
|
}
|
|
|
|
public function endContest(): void
|
|
{
|
|
$contestId = $this->data['selected_contest'] ?? null;
|
|
|
|
if (! $contestId) {
|
|
Notification::make()
|
|
->warning()
|
|
->title('Geen Competitie Geselecteerd')
|
|
->body('Selecteer eerst een competitie.')
|
|
->send();
|
|
|
|
return;
|
|
}
|
|
|
|
$contest = RadioContest::find($contestId);
|
|
|
|
$contest->update(['is_ended' => true, 'is_active' => false]);
|
|
|
|
$this->fillForm();
|
|
|
|
Notification::make()
|
|
->success()
|
|
->title('Competitie Beëindigd')
|
|
->body("Competitie '{$contest->title}' is beëindigd.")
|
|
->send();
|
|
}
|
|
|
|
public function declareWinners(): void
|
|
{
|
|
$contestId = $this->data['selected_contest'] ?? null;
|
|
|
|
if (! $contestId) {
|
|
Notification::make()
|
|
->warning()
|
|
->title('Geen Competitie Geselecteerd')
|
|
->body('Selecteer eerst een competitie.')
|
|
->send();
|
|
|
|
return;
|
|
}
|
|
|
|
$contest = RadioContest::find($contestId);
|
|
$entries = $contest->entries()->with('user')->get();
|
|
|
|
if ($entries->isEmpty()) {
|
|
Notification::make()
|
|
->warning()
|
|
->title('Geen Inzendingen')
|
|
->body('Er zijn nog geen inzendingen.')
|
|
->send();
|
|
|
|
return;
|
|
}
|
|
|
|
$winners = $entries->random(min($contest->max_winners, $entries->count()));
|
|
|
|
foreach ($winners as $winner) {
|
|
$winner->markAsWinner();
|
|
}
|
|
|
|
$contest->update(['winners_announced' => true]);
|
|
|
|
$this->fillForm();
|
|
|
|
Notification::make()
|
|
->success()
|
|
->title('Winnaars Bekend!')
|
|
->body(count($winners) . ' winnaars zijn geselecteerd!')
|
|
->send();
|
|
}
|
|
}
|