Postits en editable items.
This commit is contained in:
+161
-1
@@ -146,7 +146,167 @@ try {
|
||||
exit;
|
||||
}
|
||||
|
||||
// 4. Omzetten naar Roadmap!
|
||||
// 3c. Kaart bewerken (Inhoud, Categorie en/of Kleur)
|
||||
if ($action === 'update_card') {
|
||||
$data = json_decode(file_get_contents('php://input'), true) ?: $_POST;
|
||||
$cardId = (int)($data['card_id'] ?? 0);
|
||||
$content = trim($data['content'] ?? '');
|
||||
$category = trim($data['category'] ?? '');
|
||||
|
||||
if (!$cardId || empty($content)) {
|
||||
echo json_encode(['error' => 'Kaart ID en inhoud zijn verplicht']);
|
||||
exit;
|
||||
}
|
||||
|
||||
$colorMap = [
|
||||
'Ideeën' => 'amber',
|
||||
'Knelpunten' => 'rose',
|
||||
'Oplossingen' => 'teal',
|
||||
'Quick Wins' => 'indigo'
|
||||
];
|
||||
$color = $colorMap[$category] ?? 'amber';
|
||||
|
||||
if (!empty($category)) {
|
||||
$stmt = $db->prepare("UPDATE brainstorm_cards SET content = ?, category = ?, color = ? WHERE id = ?");
|
||||
$stmt->execute([$content, $category, $color, $cardId]);
|
||||
} else {
|
||||
$stmt = $db->prepare("UPDATE brainstorm_cards SET content = ? WHERE id = ?");
|
||||
$stmt->execute([$content, $cardId]);
|
||||
}
|
||||
|
||||
echo json_encode(['success' => true, 'card_id' => $cardId, 'content' => $content, 'category' => $category, 'color' => $color]);
|
||||
exit;
|
||||
}
|
||||
|
||||
// 3d. Kaart toewijzen aan collega en inplannen in agenda (Vrij blok)
|
||||
if ($action === 'assign_and_schedule') {
|
||||
$data = json_decode(file_get_contents('php://input'), true) ?: $_POST;
|
||||
$cardId = (int)($data['card_id'] ?? 0);
|
||||
$assigneeId = !empty($data['assignee_id']) ? (int)$data['assignee_id'] : null;
|
||||
$planDate = !empty($data['plan_date']) ? trim($data['plan_date']) : null;
|
||||
$startTime = !empty($data['start_time']) ? trim($data['start_time']) : null;
|
||||
$endTime = !empty($data['end_time']) ? trim($data['end_time']) : null;
|
||||
$durationMinutes = (int)($data['duration_minutes'] ?? 30);
|
||||
$syncOutlook = !empty($data['sync_outlook']);
|
||||
|
||||
if (!$cardId) {
|
||||
echo json_encode(['error' => 'Kaart ID ontbreekt']);
|
||||
exit;
|
||||
}
|
||||
|
||||
$stmtCard = $db->prepare("SELECT * FROM brainstorm_cards WHERE id = ?");
|
||||
$stmtCard->execute([$cardId]);
|
||||
$card = $stmtCard->fetch();
|
||||
if (!$card) {
|
||||
echo json_encode(['error' => 'Kaart niet gevonden']);
|
||||
exit;
|
||||
}
|
||||
|
||||
// Bereken eindtijd indien nodig
|
||||
if ($startTime && !$endTime && $durationMinutes > 0) {
|
||||
$tParts = explode(':', $startTime);
|
||||
$startMins = ((int)$tParts[0] * 60) + (int)($tParts[1] ?? 0);
|
||||
$endMins = $startMins + $durationMinutes;
|
||||
$endTime = sprintf('%02d:%02d', floor($endMins / 60), $endMins % 60);
|
||||
}
|
||||
|
||||
$createdTaskId = null;
|
||||
$outlookSyncMsg = null;
|
||||
|
||||
// Als er een datum & tijd is gekozen én een collega (of huidige gebruiker)
|
||||
if ($assigneeId && $planDate && $startTime) {
|
||||
// Zoek of maak daily plan
|
||||
$stmtPlan = $db->prepare("
|
||||
INSERT INTO daily_plans (user_id, plan_date)
|
||||
VALUES (?, ?)
|
||||
ON DUPLICATE KEY UPDATE id=LAST_INSERT_ID(id)
|
||||
");
|
||||
$stmtPlan->execute([$assigneeId, $planDate]);
|
||||
$planId = (int)$db->lastInsertId();
|
||||
|
||||
$taskTitle = "Brainstorm taak: " . mb_substr($card['content'], 0, 75);
|
||||
$taskDesc = "Afkomstig van Brainstormsessie. Inhoud:\n" . $card['content'];
|
||||
$source = 'BRAINSTORM';
|
||||
$externalId = null;
|
||||
$externalUrl = null;
|
||||
|
||||
// Indien Outlook sync gewenst is
|
||||
if ($syncOutlook) {
|
||||
require_once __DIR__ . '/../includes/integrations/microsoft.php';
|
||||
try {
|
||||
$msResult = microsoft_create_event($assigneeId, [
|
||||
'subject' => $taskTitle,
|
||||
'description' => $taskDesc,
|
||||
'date' => $planDate,
|
||||
'start_time' => $startTime,
|
||||
'end_time' => $endTime,
|
||||
'duration_minutes' => $durationMinutes,
|
||||
]);
|
||||
if (!empty($msResult['success']) && !empty($msResult['event_id'])) {
|
||||
$source = 'OUTLOOK';
|
||||
$externalId = $msResult['event_id'];
|
||||
$externalUrl = $msResult['web_link'] ?? null;
|
||||
$outlookSyncMsg = 'Ingepland in Outlook 365 agenda.';
|
||||
}
|
||||
} catch (Throwable $t) {
|
||||
// stil doorgaan
|
||||
}
|
||||
}
|
||||
|
||||
// Maak of update taak
|
||||
if (!empty($card['scheduled_task_id'])) {
|
||||
$stmtUpdateTask = $db->prepare("
|
||||
UPDATE tasks
|
||||
SET user_id = ?, daily_plan_id = ?, title = ?, description = ?, time_block_start = ?, time_block_end = ?, duration_minutes = ?
|
||||
WHERE id = ?
|
||||
");
|
||||
$stmtUpdateTask->execute([$assigneeId, $planId, $taskTitle, $taskDesc, $startTime, $endTime, $durationMinutes, $card['scheduled_task_id']]);
|
||||
$createdTaskId = (int)$card['scheduled_task_id'];
|
||||
} else {
|
||||
$stmtInsertTask = $db->prepare("
|
||||
INSERT INTO tasks (user_id, daily_plan_id, title, description, priority, time_block_start, time_block_end, duration_minutes, status, source, external_id, external_url)
|
||||
VALUES (?, ?, ?, ?, 'P2', ?, ?, ?, 'TODO', ?, ?, ?)
|
||||
");
|
||||
$stmtInsertTask->execute([$assigneeId, $planId, $taskTitle, $taskDesc, $startTime, $endTime, $durationMinutes, $source, $externalId, $externalUrl]);
|
||||
$createdTaskId = (int)$db->lastInsertId();
|
||||
}
|
||||
}
|
||||
|
||||
// Update brainstorm kaart
|
||||
$stmtUpdateCard = $db->prepare("
|
||||
UPDATE brainstorm_cards
|
||||
SET assignee_id = ?, scheduled_date = ?, scheduled_start_time = ?, scheduled_end_time = ?, scheduled_task_id = ?
|
||||
WHERE id = ?
|
||||
");
|
||||
$stmtUpdateCard->execute([$assigneeId, $planDate, $startTime, $endTime, $createdTaskId, $cardId]);
|
||||
|
||||
// Haal assignee naam & avatar op
|
||||
$assigneeName = null;
|
||||
$assigneeAvatar = null;
|
||||
if ($assigneeId) {
|
||||
$stmtUser = $db->prepare("SELECT name, avatar_url FROM users WHERE id = ?");
|
||||
$stmtUser->execute([$assigneeId]);
|
||||
$usr = $stmtUser->fetch();
|
||||
if ($usr) {
|
||||
$assigneeName = $usr['name'];
|
||||
$assigneeAvatar = $usr['avatar_url'];
|
||||
}
|
||||
}
|
||||
|
||||
echo json_encode([
|
||||
'success' => true,
|
||||
'card_id' => $cardId,
|
||||
'assignee_id' => $assigneeId,
|
||||
'assignee_name' => $assigneeName,
|
||||
'assignee_avatar' => $assigneeAvatar,
|
||||
'scheduled_date' => $planDate,
|
||||
'scheduled_start_time' => $startTime,
|
||||
'scheduled_end_time' => $endTime,
|
||||
'scheduled_task_id' => $createdTaskId,
|
||||
'outlook_message' => $outlookSyncMsg
|
||||
]);
|
||||
exit;
|
||||
}
|
||||
if ($action === 'convert_to_roadmap') {
|
||||
$data = json_decode(file_get_contents('php://input'), true);
|
||||
$cardIds = $data['card_ids'] ?? [];
|
||||
|
||||
+7
-6
@@ -695,6 +695,7 @@ try {
|
||||
$duration = max(5, (int)($data['duration_minutes'] ?? 30));
|
||||
$excludeTaskId = (int)($data['task_id'] ?? 0);
|
||||
$startFromNextWorkday = !empty($data['start_from_next_workday']);
|
||||
$targetUserId = !empty($data['target_user_id']) ? (int)$data['target_user_id'] : (int)$user['id'];
|
||||
|
||||
$workdaySettings = get_workday_settings();
|
||||
$workdayStartStr = $workdaySettings['workday_start'] ?? '08:30';
|
||||
@@ -757,7 +758,7 @@ try {
|
||||
$rangeEndObj->modify('+21 days'); // ruim venster incl. weekenden
|
||||
$rangeEndDate = $rangeEndObj->format('Y-m-d');
|
||||
|
||||
// 1. Batch SQL: haal alle bestaande taken van de gebruiker in 1 geoptimaliseerde query op
|
||||
// 1. Batch SQL: haal alle bestaande taken van de doelcollega in 1 geoptimaliseerde query op
|
||||
$tasksByDate = [];
|
||||
$stmtTasks = $db->prepare("
|
||||
SELECT t.id, dp.plan_date, t.time_block_start, t.time_block_end, t.duration_minutes
|
||||
@@ -769,7 +770,7 @@ try {
|
||||
AND t.time_block_start != ''
|
||||
AND t.status != 'CANCELLED'
|
||||
");
|
||||
$stmtTasks->execute([$user['id'], $rangeStartDate, $rangeEndDate]);
|
||||
$stmtTasks->execute([$targetUserId, $rangeStartDate, $rangeEndDate]);
|
||||
while ($t = $stmtTasks->fetch()) {
|
||||
if ($excludeTaskId > 0 && (int)$t['id'] === $excludeTaskId) {
|
||||
continue;
|
||||
@@ -777,11 +778,11 @@ try {
|
||||
$tasksByDate[$t['plan_date']][] = $t;
|
||||
}
|
||||
|
||||
// 2. Batch Microsoft Graph: haal alle Outlook events in 1 API call op voor het gehele venster
|
||||
// 2. Batch Microsoft Graph: haal alle Outlook events in 1 API call op voor het gehele venster van de doelcollega
|
||||
$outlookByDate = [];
|
||||
if (function_exists('microsoft_fetch_events_range')) {
|
||||
try {
|
||||
$allOutlookEvts = microsoft_fetch_events_range($user['id'], $rangeStartDate, $rangeEndDate, false);
|
||||
$allOutlookEvts = microsoft_fetch_events_range($targetUserId, $rangeStartDate, $rangeEndDate, false);
|
||||
foreach ($allOutlookEvts as $oe) {
|
||||
if (!empty($oe['date'])) {
|
||||
$outlookByDate[$oe['date']][] = $oe;
|
||||
@@ -790,11 +791,11 @@ try {
|
||||
} catch (Throwable $e) {}
|
||||
}
|
||||
|
||||
// 3. Batch Calendar Blocks: haal verlof en geblokkeerde vakantiedagen op voor dit venster
|
||||
// 3. Batch Calendar Blocks: haal verlof en geblokkeerde vakantiedagen op voor dit venster van de doelcollega
|
||||
$blockedDates = [];
|
||||
try {
|
||||
$stmtBlk = $db->prepare("SELECT start_date, end_date FROM calendar_blocks WHERE user_id = ? AND start_date <= ? AND end_date >= ?");
|
||||
$stmtBlk->execute([$user['id'], $rangeEndDate, $rangeStartDate]);
|
||||
$stmtBlk->execute([$targetUserId, $rangeEndDate, $rangeStartDate]);
|
||||
while ($b = $stmtBlk->fetch()) {
|
||||
$bStart = strtotime($b['start_date']);
|
||||
$bEnd = strtotime($b['end_date']);
|
||||
|
||||
@@ -57,6 +57,26 @@ try {
|
||||
$fields[] = "quarter = ?";
|
||||
$params[] = $data['quarter'];
|
||||
}
|
||||
if (isset($data['title']) && trim($data['title']) !== '') {
|
||||
$fields[] = "title = ?";
|
||||
$params[] = trim($data['title']);
|
||||
}
|
||||
if (isset($data['description'])) {
|
||||
$fields[] = "description = ?";
|
||||
$params[] = trim($data['description']);
|
||||
}
|
||||
if (isset($data['type'])) {
|
||||
$fields[] = "type = ?";
|
||||
$params[] = $data['type'];
|
||||
}
|
||||
if (isset($data['priority'])) {
|
||||
$fields[] = "priority = ?";
|
||||
$params[] = $data['priority'];
|
||||
}
|
||||
if (array_key_exists('due_date', $data)) {
|
||||
$fields[] = "due_date = ?";
|
||||
$params[] = !empty($data['due_date']) ? $data['due_date'] : null;
|
||||
}
|
||||
if ($progress !== null) {
|
||||
$fields[] = "progress = ?";
|
||||
$params[] = max(0, min(100, $progress));
|
||||
|
||||
Reference in New Issue
Block a user