import React, { useState, useEffect, useRef } from 'react'; import { PlusIcon, TrashIcon } from '@heroicons/react/24/outline'; import { useTranslation } from 'react-i18next'; import { fetchSubtasks } from '../../../utils/tasksService'; interface SubtaskData { id?: number; name: string; isNew?: boolean; isEdited?: boolean; } interface TaskSubtasksSectionProps { parentTaskId: number; subtasks: SubtaskData[]; onSubtasksChange: (subtasks: SubtaskData[]) => void; onSectionMount?: () => void; } const TaskSubtasksSection: React.FC = ({ parentTaskId, subtasks, onSubtasksChange, onSectionMount, }) => { const [newSubtaskName, setNewSubtaskName] = useState(''); const [isLoading, setIsLoading] = useState(false); const [editingIndex, setEditingIndex] = useState(null); const [editingName, setEditingName] = useState(''); const { t } = useTranslation(); const subtasksSectionRef = useRef(null); const addInputRef = useRef(null); // Remove the automatic reloading when subtasks.length === 0 // This was causing deleted subtasks to reappear // useEffect(() => { // if (parentTaskId && subtasks.length === 0) { // loadExistingSubtasks(); // } // }, [parentTaskId, subtasks.length]); useEffect(() => { // Scroll to bottom when section is mounted (opened) if (onSectionMount) { scrollToBottom(); onSectionMount(); } }, [onSectionMount]); const loadExistingSubtasks = async () => { try { setIsLoading(true); const existingSubtasks = await fetchSubtasks(parentTaskId); const subtaskData = existingSubtasks.map(task => ({ id: task.id, name: task.name, isNew: false, })); onSubtasksChange(subtaskData); } catch { // Handle silently or show error if needed } finally { setIsLoading(false); } }; const scrollToBottom = () => { setTimeout(() => { if (subtasksSectionRef.current) { subtasksSectionRef.current.scrollIntoView({ behavior: 'smooth', block: 'end' }); } }, 100); }; const handleCreateSubtask = () => { if (!newSubtaskName.trim()) return; const newSubtask: SubtaskData = { name: newSubtaskName.trim(), isNew: true, }; onSubtasksChange([...subtasks, newSubtask]); setNewSubtaskName(''); // Scroll to bottom after adding new subtask scrollToBottom(); }; const handleDeleteSubtask = (index: number) => { const updatedSubtasks = subtasks.filter((_, i) => i !== index); onSubtasksChange(updatedSubtasks); }; const handleKeyPress = (e: React.KeyboardEvent) => { if (e.key === 'Enter') { e.preventDefault(); handleCreateSubtask(); } }; const handleEditSubtask = (index: number) => { setEditingIndex(index); setEditingName(subtasks[index].name); }; const handleSaveEdit = () => { if (!editingName.trim() || editingIndex === null) return; const updatedSubtasks = subtasks.map((subtask, index) => { if (index === editingIndex) { const isNameChanged = subtask.name !== editingName.trim(); return { ...subtask, name: editingName.trim(), isNew: subtask.isNew || false, isEdited: !subtask.isNew && isNameChanged, // Mark as edited if it's existing and name changed }; } return subtask; }); onSubtasksChange(updatedSubtasks); setEditingIndex(null); setEditingName(''); }; const handleCancelEdit = () => { setEditingIndex(null); setEditingName(''); }; const handleEditKeyPress = (e: React.KeyboardEvent) => { if (e.key === 'Enter') { e.preventDefault(); handleSaveEdit(); } else if (e.key === 'Escape') { e.preventDefault(); handleCancelEdit(); } }; return (
{/* Existing Subtasks */} {isLoading ? (
{t('loading.subtasks', 'Loading subtasks...')}
) : subtasks.length > 0 ? (
{subtasks.map((subtask, index) => (
{editingIndex === index ? (
setEditingName(e.target.value)} onKeyPress={handleEditKeyPress} onBlur={handleSaveEdit} className="flex-1 px-2 py-1 text-sm border border-gray-300 dark:border-gray-600 rounded focus:outline-none focus:ring-2 focus:ring-blue-500 dark:bg-gray-600 dark:text-white" autoFocus />
) : ( handleEditSubtask(index)} title={t('actions.clickToEdit', 'Click to edit')} > {subtask.name} {subtask.isNew && ( (new) )} {subtask.isEdited && ( (edited) )} )}
))}
) : (
{t('subtasks.noSubtasks', 'No subtasks yet')}
)} {/* Add New Subtask */}
setNewSubtaskName(e.target.value)} onKeyPress={handleKeyPress} placeholder={t('subtasks.placeholder', 'Add a subtask...')} className="flex-1 px-3 py-2 text-sm border border-gray-300 dark:border-gray-600 rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500 dark:bg-gray-700 dark:text-white" />
); }; export default TaskSubtasksSection;