'Bienvenue dans l\'application', 'content' => 'Ceci est le contenu principal de la page d\'accueil.', 'loaded_map' => null, 'map_data' => null ]; // Vérifier si une carte doit être chargée if (isset($_GET['load']) && is_numeric($_GET['load'])) { $mapId = (int) $_GET['load']; $map = MapModel::findMap($mapId); $mapRow = MapModel::getRowById($mapId); if ($map && $mapRow) { // Récupérer le template depuis les données JSON $mapJsonData = json_decode($mapRow['data'], true) ?: []; $template = $mapJsonData['template'] ?? 'neutral'; // Charger les définitions de tuiles du template require_once __DIR__ . '/../Models/Templates/TemplateFactory.php'; $templateClass = TemplateFactory::get($template); $tileDefinitions = $templateClass ? $templateClass::tileDefinitions() : []; // Obtenir les données des hexagones $hexes = []; foreach ($map->getAllHexagons() as $q => $row) { foreach ($row as $r => $hexagon) { $tile = $hexagon->getTile(); $hexes[] = [ 'q' => $hexagon->getQ(), 'r' => $hexagon->getR(), 'tile' => $tile ? [ 'type' => $tile->getType(), 'properties' => $tile->getAllProperties() ] : null ]; } } $data['loaded_map'] = $map; $data['map_data'] = [ 'id' => $mapId, 'name' => $map->getName(), 'width' => $map->getWidth(), 'height' => $map->getHeight(), 'created_at' => $map->getCreatedAt(), 'updated_at' => $map->getUpdatedAt(), 'statistics' => $map->getStatistics(), 'template' => $template, 'tileDefinitions' => $tileDefinitions, 'hexes' => $hexes ]; $data['title'] = $map->getName() . ' - Map Generator'; } else { $data['load_error'] = 'Carte non trouvée (ID: ' . $mapId . '). Vérifiez que l\'ID est correct.'; } } Renderer::render('home', $data); } /** * Affiche le formulaire de création d'un nouveau projet. */ public static function newProject() { $data = [ 'title' => 'Nouveau projet - Map Generator', 'page' => 'new_project' ]; // Découvrir les templates disponibles require_once __DIR__ . '/../Models/Templates/TemplateFactory.php'; $templates = TemplateFactory::listAvailable(); $data['templates'] = $templates; Renderer::render('projects/new', $data); } /** * Crée un nouveau projet (endpoint POST) * Accepte form POST classique ou JSON */ public static function createProject() { if ($_SERVER['REQUEST_METHOD'] !== 'POST') { http_response_code(405); echo json_encode(['success' => false, 'message' => 'Méthode non autorisée']); return; } $contentType = $_SERVER['CONTENT_TYPE'] ?? ''; if (strpos($contentType, 'application/json') !== false) { $raw = file_get_contents('php://input'); $input = json_decode($raw, true) ?: []; } else { $input = $_POST; } $name = isset($input['name']) ? trim($input['name']) : ''; $description = $input['description'] ?? null; $template = $input['template'] ?? null; if (!$name) { http_response_code(400); echo json_encode(['success' => false, 'message' => 'Le nom est requis']); return; } // Si un radius est envoyé, créer la map via radius $radius = isset($input['radius']) ? (int) $input['radius'] : null; $map = null; if ($radius && $radius > 0) { $map = Map::fromRadius($name, $radius); } else { // Fallback: utiliser width/height $width = isset($input['width']) ? (int) $input['width'] : 10; $height = isset($input['height']) ? (int) $input['height'] : 10; $map = new Map($name, $width, $height); } // Appliquer le template si fourni (ou template neutre par défaut) require_once __DIR__ . '/../Models/Templates/TemplateFactory.php'; $templateClass = TemplateFactory::get($template); if (class_exists($templateClass) && method_exists($templateClass, 'applyTemplate')) { $templateClass::applyTemplate($map); } $created = MapModel::create($map, $description, $template, $radius); // Détecter AJAX $isAjax = false; $xrw = $_SERVER['HTTP_X_REQUESTED_WITH'] ?? ''; if (strtolower($xrw) === 'xmlhttprequest' || strpos($contentType, 'application/json') !== false) { $isAjax = true; } if ($created) { if ($isAjax) { echo json_encode(['success' => true, 'id' => $created]); } else { header('Location: /projects'); } } else { if ($isAjax) { http_response_code(500); echo json_encode(['success' => false, 'message' => 'Erreur lors de la création']); } else { header('Location: /projects'); } } } /** * Affiche la liste des projets (cartes) disponibles. */ public static function projects() { // Récupérer la liste des cartes depuis la base de données $maps = MapModel::paginate(1, 20)['data']; // Récupérer les 20 premières cartes // Récupérer les statistiques globales $stats = MapModel::getGlobalStats(); $data = [ 'title' => 'Mes projets - Map Generator', 'page' => 'projects', 'maps' => $maps, 'stats' => $stats ]; Renderer::render('projects/index', $data); } /** * Affiche le formulaire d'édition pour une carte existante * @param int $id */ public static function editProject(int $id) { // Charger la map via MapModel $map = MapModel::findMap($id); if (!$map) { http_response_code(404); echo 'Carte non trouvée'; return; } // Préparer les données de la view require_once __DIR__ . '/../Models/Templates/TemplateFactory.php'; $templates = TemplateFactory::listAvailable(); // Récupérer la row brute pour extraire les métadonnées JSON $rawRow = null; try { $rawRow = MapModel::getRowById($id); } catch (Throwable $e) { $rawRow = null; } $templateId = null; $radiusVal = null; if (!empty($rawRow['data'])) { $decoded = is_string($rawRow['data']) ? json_decode($rawRow['data'], true) : $rawRow['data']; if (is_array($decoded)) { $templateId = $decoded['template'] ?? null; $radiusVal = isset($decoded['radius']) ? (int)$decoded['radius'] : null; } } $data = [ 'title' => 'Édition de la carte - ' . $map->getName(), 'page' => 'projects_edit', 'map' => $map, 'templates' => $templates, 'templateId' => $templateId, 'radiusVal' => $radiusVal, 'mapId' => $id, 'mapDescription' => $rawRow['description'] ?? '' ]; Renderer::render('projects/edit', $data); } /** * Traite la mise à jour d'une carte (POST) */ public static function updateProject() { if ($_SERVER['REQUEST_METHOD'] !== 'POST') { http_response_code(405); echo json_encode(['success' => false, 'message' => 'Méthode non autorisée']); return; } $input = $_POST; $id = isset($input['id']) ? (int)$input['id'] : null; if (!$id) { http_response_code(400); echo json_encode(['success' => false, 'message' => 'ID manquant']); return; } $name = isset($input['name']) ? trim($input['name']) : ''; $description = $input['description'] ?? null; $template = $input['template'] ?? null; $radius = isset($input['radius']) ? (int)$input['radius'] : null; $existing = MapModel::findMap($id); if (!$existing) { http_response_code(404); echo json_encode(['success' => false, 'message' => 'Carte non trouvée']); return; } // Par défaut, préserver le contenu existant $map = $existing; // Récupérer la row brute pour comparer le radius existant $existingRow = MapModel::getRowById($id); $existingRadius = null; if (!empty($existingRow['data'])) { $decoded = is_string($existingRow['data']) ? json_decode($existingRow['data'], true) : $existingRow['data']; if (is_array($decoded) && isset($decoded['radius'])) { $existingRadius = (int)$decoded['radius']; } } // Si l'utilisateur a fourni un radius et qu'il est différent de l'existant, reconstruire la map if ($radius && $radius > 0 && $radius !== $existingRadius) { $map = Map::fromRadius($name ?: $existing->getName(), $radius); } else { // Ne pas reconstruire : mettre à jour seulement le nom si fourni if (!empty($name)) { $map->setName($name); } } // Appliquer le template si fourni require_once __DIR__ . '/../Models/Templates/TemplateFactory.php'; $templateClass = TemplateFactory::get($template); if (class_exists($templateClass) && method_exists($templateClass, 'applyTemplate')) { $templateClass::applyTemplate($map); } // Mettre à jour $ok = MapModel::update($id, $map, $description, $template, $radius); if ($ok) { header('Location: /projects'); } else { http_response_code(500); echo 'Erreur lors de la mise à jour'; } } /** * Supprime une carte (endpoint POST) * Accepte JSON (AJAX) ou form POST standard. */ public static function deleteProject() { // Méthode attendue: POST if ($_SERVER['REQUEST_METHOD'] !== 'POST') { http_response_code(405); echo json_encode(['success' => false, 'message' => 'Méthode non autorisée']); return; } // Lire input JSON si présent $input = []; $contentType = $_SERVER['CONTENT_TYPE'] ?? ''; if (strpos($contentType, 'application/json') !== false) { $raw = file_get_contents('php://input'); $input = json_decode($raw, true) ?: []; } else { $input = $_POST; } $id = isset($input['id']) ? (int) $input['id'] : null; if (!$id) { http_response_code(400); echo json_encode(['success' => false, 'message' => 'ID manquant']); return; } // Vérifier existence if (!MapModel::exists($id)) { http_response_code(404); echo json_encode(['success' => false, 'message' => 'Carte non trouvée']); return; } $deleted = MapModel::delete($id); // Détecter si la requête est AJAX $isAjax = false; $xrw = $_SERVER['HTTP_X_REQUESTED_WITH'] ?? ''; if (strtolower($xrw) === 'xmlhttprequest' || strpos($contentType, 'application/json') !== false) { $isAjax = true; } if ($isAjax) { if ($deleted) { echo json_encode(['success' => true]); } else { http_response_code(500); echo json_encode(['success' => false, 'message' => 'Erreur lors de la suppression']); } return; } // Pour les requêtes classiques (form POST), utiliser les messages flash en session avant redirection if (session_status() === PHP_SESSION_NONE) { session_start(); } if ($deleted) { $_SESSION['flash'][] = ['type' => 'success', 'message' => 'La carte a été supprimée avec succès.']; } else { $_SESSION['flash'][] = ['type' => 'error', 'message' => 'Une erreur est survenue lors de la suppression de la carte.']; } header('Location: /projects'); return; } } }