From 24fbfb9d8238103312b8ab643251b4755b18ca55 Mon Sep 17 00:00:00 2001 From: Niek Rabelink Date: Mon, 14 Sep 2026 11:10:54 +0200 Subject: [PATCH] Brainstorm huge refactor --- api/ai.php | 60 ++++++++++++++-- api/mail.php | 32 +++++++++ api/planner.php | 55 ++++++++++++++- brainstorm.php | 83 ++++++++++++++++------ brainstorm_canvas.php | 70 +++++++++++++++--- includes/ai.php | 49 ++++++++++++- includes/boards.php | 160 ++++++++++++++++++++++++++++++++++++++++++ mail.php | 135 ++++++++++++++++++++++++++++++++++- planner.php | 144 ++++++++++++++++++++++++++++++++++++- 9 files changed, 747 insertions(+), 41 deletions(-) create mode 100644 includes/boards.php diff --git a/api/ai.php b/api/ai.php index 27b3a8e..3afdf5e 100644 --- a/api/ai.php +++ b/api/ai.php @@ -72,6 +72,7 @@ try { $data = json_decode(file_get_contents('php://input'), true); $sessionId = (int)($data['session_id'] ?? 0); $count = min(6, max(2, (int)($data['count'] ?? 4))); + $fullBoard = !empty($data['full_board']); // Genereren over alle 4 categorieën o.b.v. briefing if (!$sessionId) { echo json_encode(['error' => 'Sessie ID ontbreekt']); @@ -87,7 +88,59 @@ try { exit; } - $aiRes = fociz_ai_generate_ideas($session['title'], $session['theme'] ?? 'Algemeen', $count, $user['id']); + $authorName = 'AI Co-Pilot'; + $createdCards = []; + + $colorMap = [ + 'Ideeën' => 'amber', + 'Knelpunten' => 'rose', + 'Oplossingen' => 'teal', + 'Quick Wins' => 'indigo', + ]; + + if ($fullBoard || !empty($session['description'])) { + // Gebruik de volledige board generator die alle 4 categorieën vult aan de hand van de briefing + $aiRes = fociz_ai_generate_session_board( + $session['title'], + $session['theme'] ?? 'Algemeen', + $session['description'] ?? '', + $user['id'] + ); + + if ($aiRes['success'] && !empty($aiRes['cards'])) { + $insertStmt = $db->prepare(" + INSERT INTO brainstorm_cards (session_id, content, category, color, author_name, votes) + VALUES (?, ?, ?, ?, ?, 1) + "); + + foreach ($aiRes['cards'] as $cardItem) { + $cText = trim($cardItem['content'] ?? ''); + $cCat = trim($cardItem['category'] ?? 'Ideeën'); + if (!isset($colorMap[$cCat])) { + $cCat = 'Ideeën'; + } + $cColor = $colorMap[$cCat]; + + if (!empty($cText)) { + $insertStmt->execute([$sessionId, $cText, $cCat, $cColor, $authorName]); + $createdCards[] = [ + 'id' => (int)$db->lastInsertId(), + 'content' => $cText, + 'category' => $cCat, + 'color' => $cColor, + 'author_name' => $authorName, + 'votes' => 1, + ]; + } + } + + echo json_encode(['success' => true, 'cards' => $createdCards, 'mode' => 'full_board']); + exit; + } + } + + // Fallback: reguliere generatie + $aiRes = fociz_ai_generate_ideas($session['title'], $session['theme'] ?? 'Algemeen', $count, $user['id'], $session['description'] ?? ''); if (!$aiRes['success']) { echo json_encode(['error' => $aiRes['error']]); @@ -99,9 +152,6 @@ try { VALUES (?, ?, 'Ideeën', 'amber', ?, 1) "); - $createdCards = []; - $authorName = 'AI Co-Pilot'; - foreach ($aiRes['ideas'] as $ideaText) { $ideaText = trim($ideaText); if (!empty($ideaText)) { @@ -117,7 +167,7 @@ try { } } - echo json_encode(['success' => true, 'cards' => $createdCards]); + echo json_encode(['success' => true, 'cards' => $createdCards, 'mode' => 'ideas']); exit; } diff --git a/api/mail.php b/api/mail.php index c116478..4708eca 100644 --- a/api/mail.php +++ b/api/mail.php @@ -6,6 +6,7 @@ require_once __DIR__ . '/../includes/auth.php'; require_once __DIR__ . '/../includes/integrations/microsoft.php'; +require_once __DIR__ . '/../includes/boards.php'; $user = require_auth(); $userId = (int)$user['id']; @@ -213,11 +214,42 @@ try { ]); $taskId = (int)$db->lastInsertId(); + // Optioneel toevoegen aan Bord en Tijdlijn + $boardSyncResult = null; + $addToBoard = !empty($input['add_to_board']) && !empty($input['board_id']); + if ($addToBoard) { + $boardId = (int)$input['board_id']; + $laneId = (int)($input['lane_id'] ?? 0); + $scheduleOnTimeline = !empty($input['schedule_on_timeline']); + $timelineStartDate = !empty($input['timeline_start_date']) ? trim($input['timeline_start_date']) : $planDate; + $timelineEndDate = !empty($input['timeline_end_date']) ? trim($input['timeline_end_date']) : $timelineStartDate; + + $mailDesc = "Afzender: " . ($sender ?: 'Onbekend'); + if (!empty($webLink)) { + $mailDesc .= "\nWeblink: " . $webLink; + } + + $boardSyncResult = fociz_add_item_to_board_and_timeline($db, $userId, (($user['role'] ?? '') === 'ADMIN'), [ + 'board_id' => $boardId, + 'lane_id' => $laneId, + 'title' => $taskTitle, + 'description' => $mailDesc, + 'priority' => $priority, + 'color' => !empty($input['board_color']) ? $input['board_color'] : 'blue', + 'schedule_on_timeline' => $scheduleOnTimeline, + 'start_date' => $timelineStartDate, + 'end_date' => $timelineEndDate, + 'start_time' => $timeBlockStart ?: '09:00', + 'end_time' => $timeBlockEnd ?: '10:00', + ]); + } + echo json_encode([ 'success' => true, 'task_id' => $taskId, 'plan_date' => $planDate, 'outlook_synced' => ($source === 'OUTLOOK'), + 'board_sync' => $boardSyncResult, 'message' => "E-mail succesvol ingepland voor {$planDate}." . ($outlookSyncMsg ? " ({$outlookSyncMsg})" : "") ]); exit; diff --git a/api/planner.php b/api/planner.php index 8fe2ee4..e5aee91 100644 --- a/api/planner.php +++ b/api/planner.php @@ -6,6 +6,7 @@ require_once __DIR__ . '/../includes/auth.php'; require_once __DIR__ . '/../includes/settings.php'; require_once __DIR__ . '/../includes/integrations/microsoft.php'; +require_once __DIR__ . '/../includes/boards.php'; $user = require_auth(true); $db = get_db_connection(); @@ -182,6 +183,31 @@ try { $stmt->execute([$user['id'], $planId, $title, $priority, $timeBlockStart, $timeBlockEnd, $durationMinutes, $source, $externalId, $externalUrl]); $taskId = (int)$db->lastInsertId(); + // Optioneel toevoegen aan Bord en Tijdlijn + $boardSyncResult = null; + $addToBoard = !empty($data['add_to_board']) && !empty($data['board_id']); + if ($addToBoard) { + $boardId = (int)$data['board_id']; + $laneId = (int)($data['lane_id'] ?? 0); + $scheduleOnTimeline = !empty($data['schedule_on_timeline']); + $timelineStartDate = !empty($data['timeline_start_date']) ? trim($data['timeline_start_date']) : $date; + $timelineEndDate = !empty($data['timeline_end_date']) ? trim($data['timeline_end_date']) : $timelineStartDate; + + $boardSyncResult = fociz_add_item_to_board_and_timeline($db, (int)$user['id'], ($user['role'] === 'ADMIN'), [ + 'board_id' => $boardId, + 'lane_id' => $laneId, + 'title' => $title, + 'description' => (!empty($data['description']) ? trim((string)$data['description']) : "") . (!empty($externalUrl) ? "\n\nReferentie: " . $externalUrl : ""), + 'priority' => $priority, + 'color' => !empty($data['board_color']) ? $data['board_color'] : 'blue', + 'schedule_on_timeline' => $scheduleOnTimeline, + 'start_date' => $timelineStartDate, + 'end_date' => $timelineEndDate, + 'start_time' => $timeBlockStart ?: '09:00', + 'end_time' => $timeBlockEnd ?: '10:00', + ]); + } + echo json_encode([ 'success' => true, 'task' => [ @@ -199,6 +225,7 @@ try { ], 'outlook_synced' => ($source === 'OUTLOOK' && !empty($externalId)), 'outlook_error' => $outlookSyncError, + 'board_sync' => $boardSyncResult, ]); exit; } @@ -337,12 +364,38 @@ try { $stmtUpdate->execute([$title, $description, $priority, $timeBlockStart, $timeBlockEnd, $durationMinutes, $source, $externalId, $externalUrl, $taskId, $user['id']]); } + // Optioneel toevoegen aan Bord en Tijdlijn bij herplannen + $boardSyncResult = null; + $addToBoard = !empty($data['add_to_board']) && !empty($data['board_id']); + if ($addToBoard) { + $boardId = (int)$data['board_id']; + $laneId = (int)($data['lane_id'] ?? 0); + $scheduleOnTimeline = !empty($data['schedule_on_timeline']); + $timelineStartDate = !empty($data['timeline_start_date']) ? trim($data['timeline_start_date']) : $planDate; + $timelineEndDate = !empty($data['timeline_end_date']) ? trim($data['timeline_end_date']) : $timelineStartDate; + + $boardSyncResult = fociz_add_item_to_board_and_timeline($db, (int)$user['id'], ($user['role'] === 'ADMIN'), [ + 'board_id' => $boardId, + 'lane_id' => $laneId, + 'title' => $title, + 'description' => (!empty($description) ? trim((string)$description) : "") . (!empty($externalUrl) ? "\n\nReferentie: " . $externalUrl : ""), + 'priority' => $priority, + 'color' => !empty($data['board_color']) ? $data['board_color'] : 'blue', + 'schedule_on_timeline' => $scheduleOnTimeline, + 'start_date' => $timelineStartDate, + 'end_date' => $timelineEndDate, + 'start_time' => $timeBlockStart ?: '09:00', + 'end_time' => $timeBlockEnd ?: '10:00', + ]); + } + echo json_encode([ 'success' => true, 'time_block_start' => $timeBlockStart, 'time_block_end' => $timeBlockEnd, 'duration_minutes' => $durationMinutes, - 'date' => $planDate + 'date' => $planDate, + 'board_sync' => $boardSyncResult, ]); exit; } diff --git a/brainstorm.php b/brainstorm.php index 8414560..4a26d87 100644 --- a/brainstorm.php +++ b/brainstorm.php @@ -19,7 +19,7 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_POST['action']) && $_POST[' $theme = $firstActive ? $firstActive['name'] : 'Product & Strategie'; } $description = trim($_POST['description'] ?? ''); - + $autoAi = !empty($_POST['auto_ai']) ? 1 : 0; if (!empty($title)) { $stmt = $db->prepare(" @@ -28,7 +28,8 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST' && isset($_POST['action']) && $_POST[' "); $stmt->execute([$title, $theme, $description, $currentUser['id']]); $newId = $db->lastInsertId(); - header("Location: /brainstorm_canvas.php?id={$newId}"); + $redirectUrl = "/brainstorm_canvas.php?id={$newId}" . ($autoAi ? "&auto_ai=1" : ""); + header("Location: {$redirectUrl}"); exit; } else { $error = "Titel van de brainstormsessie is verplicht."; @@ -147,13 +148,18 @@ require_once __DIR__ . '/includes/header.php'; -