<?php
declare(strict_types=1);

namespace App\Modules\PlayerAffairs\Controllers;

use App\Core\Controller;
use App\Core\App;
use App\Core\Request;
use App\Core\Response;
use App\Modules\PlayerAffairs\Models\EvaluationCriterion;
use App\Modules\PlayerAffairs\Models\PlayerEvaluation;
use App\Modules\PlayerAffairs\Services\EvaluationService;

class EvaluationController extends Controller
{
    /**
     * List evaluations with filters.
     */
    public function index(Request $request): Response
    {
        $this->authorize('player.evaluate');

        $filters = [
            'q'                  => $request->get('q', ''),
            'player_id'          => $request->get('player_id', ''),
            'discipline_id'      => $request->get('discipline_id', ''),
            'evaluator_coach_id' => $request->get('evaluator_coach_id', ''),
            'status'             => $request->get('status', ''),
            'skill_level'        => $request->get('skill_level', ''),
            'date_from'          => $request->get('date_from', ''),
            'date_to'            => $request->get('date_to', ''),
        ];

        $page = max(1, (int) $request->get('page', '1'));
        $result = PlayerEvaluation::search($filters, 25, $page);

        // Load disciplines for filter dropdown
        $db = App::getInstance()->db();
        $disciplines = $db->select("SELECT id, name_ar FROM sport_disciplines WHERE is_active = 1 ORDER BY name_ar ASC", []);

        return $this->view('PlayerAffairs.Views.evaluations', [
            'evaluations' => $result['data'],
            'pagination'  => $result['pagination'],
            'filters'     => $filters,
            'disciplines' => $disciplines,
        ]);
    }

    /**
     * Show evaluation creation form.
     */
    public function create(Request $request): Response
    {
        $this->authorize('player.evaluate');

        $db = App::getInstance()->db();

        $playerId = (int) $request->get('player_id', '0');
        $disciplineId = (int) $request->get('discipline_id', '0');

        $player = null;
        if ($playerId > 0) {
            $player = $db->selectOne("SELECT id, full_name_ar, date_of_birth, gender FROM players WHERE id = ?", [$playerId]);
        }

        $discipline = null;
        $criteria = [];
        if ($disciplineId > 0) {
            $discipline = $db->selectOne("SELECT id, name_ar FROM sport_disciplines WHERE id = ?", [$disciplineId]);
            $criteria = EvaluationCriterion::getForDiscipline($disciplineId);
        }

        // Load players and disciplines for dropdowns
        $players = $db->select("SELECT id, full_name_ar FROM players WHERE is_archived = 0 ORDER BY full_name_ar ASC", []);
        $disciplines = $db->select("SELECT id, name_ar FROM sport_disciplines WHERE is_active = 1 ORDER BY name_ar ASC", []);
        $coaches = $db->select("SELECT id, full_name_ar FROM coaches WHERE is_active = 1 ORDER BY full_name_ar ASC", []);

        return $this->view('PlayerAffairs.Views.evaluation_create', [
            'player'      => $player,
            'discipline'  => $discipline,
            'criteria'    => $criteria,
            'players'     => $players,
            'disciplines' => $disciplines,
            'coaches'     => $coaches,
            'playerId'    => $playerId,
            'disciplineId'=> $disciplineId,
        ]);
    }

    /**
     * Store a new evaluation.
     */
    public function store(Request $request): Response
    {
        $this->authorize('player.evaluate');

        $data = $this->validated($_POST, [
            'player_id'          => 'required|numeric',
            'discipline_id'      => 'required|numeric',
            'evaluation_date'    => 'required',
            'evaluator_coach_id' => 'nullable|numeric',
            'strengths_ar'       => 'nullable',
            'weaknesses_ar'      => 'nullable',
            'coach_notes'        => 'nullable',
            'parent_visible'     => 'nullable',
        ]);

        // Build scores from POST
        $scores = [];
        $criteriaIds = $_POST['criterion_id'] ?? [];
        $criteriaScores = $_POST['criterion_score'] ?? [];
        $criteriaNotes = $_POST['criterion_notes'] ?? [];

        foreach ($criteriaIds as $index => $criterionId) {
            $scores[] = [
                'criterion_id' => (int) $criterionId,
                'score'        => (float) ($criteriaScores[$index] ?? 0),
                'notes'        => $criteriaNotes[$index] ?? '',
            ];
        }

        $data['scores'] = $scores;
        $data['parent_visible'] = isset($_POST['parent_visible']) ? 1 : 0;
        $data['session_id'] = !empty($_POST['session_id']) ? (int) $_POST['session_id'] : null;

        try {
            $evaluation = EvaluationService::submitEvaluation($data);
            return $this->redirect('/evaluations/' . $evaluation['id'])->withSuccess('تم تقديم التقييم بنجاح');
        } catch (\Throwable $e) {
            return $this->back()->withError('حدث خطأ أثناء حفظ التقييم: ' . $e->getMessage());
        }
    }

    /**
     * Show evaluation detail.
     */
    public function show(Request $request, int $id): Response
    {
        $this->authorize('player.evaluate');

        $db = App::getInstance()->db();

        $evaluation = $db->selectOne(
            "SELECT pe.*, p.full_name_ar AS player_name, p.date_of_birth, p.gender,
                    d.name_ar AS discipline_name, c.full_name_ar AS coach_name,
                    approver.full_name_ar AS approver_name
             FROM player_evaluations pe
             LEFT JOIN players p ON p.id = pe.player_id
             LEFT JOIN sport_disciplines d ON d.id = pe.discipline_id
             LEFT JOIN coaches c ON c.id = pe.evaluator_coach_id
             LEFT JOIN employees approver ON approver.id = pe.approved_by
             WHERE pe.id = ?",
            [$id]
        );

        if (!$evaluation) {
            throw new \RuntimeException('التقييم غير موجود', 404);
        }

        // Decode scores
        $scores = json_decode($evaluation['scores_json'] ?? '[]', true) ?: [];

        // Get criteria for this discipline
        $criteria = EvaluationCriterion::getForDiscipline((int) $evaluation['discipline_id']);
        $criteriaMap = [];
        foreach ($criteria as $c) {
            $criteriaMap[(int) $c['id']] = $c;
        }

        // Enrich scores with criterion names
        foreach ($scores as &$s) {
            $criterionId = (int) ($s['criterion_id'] ?? 0);
            if (isset($criteriaMap[$criterionId])) {
                $s['criterion_name'] = $criteriaMap[$criterionId]['criterion_name_ar'];
                $s['max_score'] = (int) $criteriaMap[$criterionId]['max_score'];
            } else {
                $s['criterion_name'] = 'معيار غير معروف';
                $s['max_score'] = 10;
            }
        }
        unset($s);

        // Get progression history for chart
        $progression = EvaluationService::getProgressionHistory(
            (int) $evaluation['player_id'],
            (int) $evaluation['discipline_id']
        );

        return $this->view('PlayerAffairs.Views.evaluation_show', [
            'evaluation'  => $evaluation,
            'scores'      => $scores,
            'criteria'    => $criteria,
            'progression' => $progression,
        ]);
    }

    /**
     * Approve an evaluation.
     */
    public function approve(Request $request, int $id): Response
    {
        $this->authorize('player.evaluate');

        $employee = $this->currentEmployee();
        $approvedBy = (int) ($employee->id ?? 0);

        try {
            EvaluationService::approveEvaluation($id, $approvedBy);
            return $this->redirect('/evaluations/' . $id)->withSuccess('تم اعتماد التقييم بنجاح');
        } catch (\Throwable $e) {
            return $this->back()->withError('حدث خطأ: ' . $e->getMessage());
        }
    }

    /**
     * API: Get criteria for a discipline (AJAX).
     */
    public function apiCriteria(Request $request, int $disciplineId): Response
    {
        $this->authorize('player.evaluate');

        $criteria = EvaluationCriterion::getForDiscipline($disciplineId);
        return $this->json(['criteria' => $criteria]);
    }
}
