feat: contador en las pestañas de Tareas/Comentarios/Documentos de una actividad
Circulo con el numero al lado del nombre de la pestaña: Tareas muestra las pendientes (sin marcar), Comentarios y Documentos el total. Soporte agregado al componente Tabs reutilizable (tab.count), no solo al detalle de actividad. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
@@ -8,6 +8,8 @@ import { listTasks, createTask, updateTask, setTaskDone, deleteTask, reorderTask
|
||||
import { promoteTaskToRecurring } from '../../services/recurringTasks.js';
|
||||
import { listCatalog } from '../../services/catalogs.js';
|
||||
import { listUsers } from '../../services/users.js';
|
||||
import { listComments } from '../../services/comments.js';
|
||||
import { listAttachments } from '../../services/attachments.js';
|
||||
import { Button } from '../../components/Button.jsx';
|
||||
import { Field, FieldRow } from '../../components/Field.jsx';
|
||||
import { ComboBox } from '../../components/ComboBox.jsx';
|
||||
@@ -41,6 +43,10 @@ export default function ActivityDetailPanel({ activity, projectId, siblingActivi
|
||||
});
|
||||
|
||||
const [tab, setTab] = useState('detail');
|
||||
// Recargadas al cambiar de pestaña (listas livianas) para que los contadores de las pestañas
|
||||
// se mantengan al dia sin necesidad de que CommentsPanel/AttachmentsPanel avisen al padre.
|
||||
const { data: comments } = useAsync(() => listComments('activity', activity.id), [activity.id, tab]);
|
||||
const { data: attachments } = useAsync(() => listAttachments('activity', activity.id), [activity.id, tab]);
|
||||
const [editing, setEditing] = useState(false);
|
||||
const [form, setForm] = useState(() => toForm(activity));
|
||||
const [newTask, setNewTask] = useState('');
|
||||
@@ -53,6 +59,7 @@ export default function ActivityDetailPanel({ activity, projectId, siblingActivi
|
||||
useEffect(() => { setForm(toForm(activity)); setEditing(false); }, [activity]);
|
||||
|
||||
const hasTasks = tasks && tasks.length > 0;
|
||||
const pendingTasksCount = (tasks || []).filter((task) => !task.is_done).length;
|
||||
const priorityOptions = (priorities || []).map((p) => ({ value: p.id, label: p.name }));
|
||||
const statusOptions = (statuses || []).map((s) => ({ value: s.id, label: s.name }));
|
||||
const userOptions = (users || []).map((u) => ({ value: u.id, label: u.name }));
|
||||
@@ -141,10 +148,10 @@ export default function ActivityDetailPanel({ activity, projectId, siblingActivi
|
||||
<Tabs
|
||||
tabs={[
|
||||
{ key: 'detail', label: t('tab_info') },
|
||||
{ key: 'tasks', label: t('tasks_title') },
|
||||
{ key: 'tasks', label: t('tasks_title'), count: pendingTasksCount },
|
||||
{ key: 'dependencies', label: t('activity_dependencies') },
|
||||
{ key: 'comments', label: t('tab_comments') },
|
||||
{ key: 'documents', label: t('tab_documents') },
|
||||
{ key: 'comments', label: t('tab_comments'), count: (comments || []).length },
|
||||
{ key: 'documents', label: t('tab_documents'), count: (attachments || []).length },
|
||||
]}
|
||||
active={tab}
|
||||
onChange={setTab}
|
||||
|
||||
Reference in New Issue
Block a user