diff --git a/app/Professor/Alunos/ListaAlunos.tsx b/app/Professor/Alunos/ListaAlunos.tsx index cf7a21f..076aee8 100644 --- a/app/Professor/Alunos/ListaAlunos.tsx +++ b/app/Professor/Alunos/ListaAlunos.tsx @@ -1,18 +1,31 @@ import { Ionicons } from '@expo/vector-icons'; import { useRouter } from 'expo-router'; -import { memo, useState } from 'react'; -import { FlatList, Platform, SafeAreaView, StatusBar, StyleSheet, Text, TextInput, TouchableOpacity, View } from 'react-native'; +import { memo, useEffect, useState } from 'react'; +import { + FlatList, + Platform, + SafeAreaView, + StatusBar, + StyleSheet, + Text, + TextInput, + TouchableOpacity, + View, +} from 'react-native'; import { useTheme } from '../../../themecontext'; +import { supabase } from '../../lib/supabase'; + +/* ======================= + Interfaces +======================= */ export interface Aluno { - id: number; + id: string; nome: string; - estado: string; email: string; telefone: string; + estado: string; // virá da tabela estagios turma: string; - empresa: string; - cargo: string; } interface Turma { @@ -20,16 +33,18 @@ interface Turma { alunos: Aluno[]; } -const turmasData: Turma[] = [ - { nome: '12ºA', alunos: [{ id: 1, nome: 'João Silva', estado: 'Em estágio', email: 'joao@escola.pt', telefone: '912345678', turma: '12ºA', empresa: 'Empresa X', cargo: 'Dev' }] }, - { nome: '12ºB', alunos: [{ id: 2, nome: 'Maria Fernandes', estado: 'Em estágio', email: 'maria@escola.pt', telefone: '912345681', turma: '12ºB', empresa: 'Empresa W', cargo: 'Design' }] }, -]; +/* ======================= + Componente +======================= */ const ListaAlunosProfessor = memo(() => { const { isDarkMode } = useTheme(); const router = useRouter(); + const [search, setSearch] = useState(''); - const [expanded, setExpanded] = useState<{ [key: string]: boolean }>({}); + const [expanded, setExpanded] = useState>({}); + const [turmas, setTurmas] = useState([]); + const [loading, setLoading] = useState(true); const cores = { fundo: isDarkMode ? '#121212' : '#f1f3f5', @@ -39,29 +54,105 @@ const ListaAlunosProfessor = memo(() => { azul: '#0d6efd', }; - const toggleExpand = (turmaNome: string) => setExpanded(prev => ({ ...prev, [turmaNome]: !prev[turmaNome] })); + /* ======================= + Fetch Supabase + ======================= */ - const filteredTurmas = turmasData + useEffect(() => { + fetchAlunos(); + }, []); + + const fetchAlunos = async () => { + setLoading(true); + + const { data, error } = await supabase + .from('profiles') + .select(` + id, + nome, + email, + telefone, + turma_curso, + ano, + n_escola + `) + .order('ano', { ascending: false }); + + if (error) { + console.error('Erro ao buscar alunos:', error); + setLoading(false); + return; + } + + const agrupadas: Record = {}; + + data.forEach((item: any) => { + const nomeTurma = `${item.ano} ${item.turma_curso}`; + + if (!agrupadas[nomeTurma]) { + agrupadas[nomeTurma] = []; + } + + agrupadas[nomeTurma].push({ + id: item.id, + nome: item.nome, + email: item.email, + telefone: item.telefone ?? '—', + estado: 'Sem estágio', + turma: nomeTurma, + }); + }); + + const turmasFormatadas: Turma[] = Object.keys(agrupadas).map(nome => ({ + nome, + alunos: agrupadas[nome], + })); + + setTurmas(turmasFormatadas); + setLoading(false); + }; + + const toggleExpand = (turmaNome: string) => + setExpanded(prev => ({ ...prev, [turmaNome]: !prev[turmaNome] })); + + /* ======================= + Pesquisa + ======================= */ + + const filteredTurmas = turmas .map(turma => ({ ...turma, - alunos: turma.alunos.filter(a => a.nome.toLowerCase().includes(search.toLowerCase())), + alunos: turma.alunos.filter(a => + a.nome.toLowerCase().includes(search.toLowerCase()) + ), })) .filter(t => t.alunos.length > 0); + /* ======================= + Render + ======================= */ + return ( - {/* Header com botão voltar */} + {/* Header */} - router.back()}> + router.back()} + > - Alunos + + + Alunos + + - {/* Input de pesquisa */} + {/* Pesquisa */} { onChangeText={setSearch} /> - {/* Lista de turmas e alunos */} + {loading && ( + + A carregar alunos... + + )} + + {/* Lista */} item.nome} + contentContainerStyle={{ paddingBottom: 20 }} renderItem={({ item }) => ( toggleExpand(item.nome)}> - {item.nome} ({item.alunos.length}) + + {item.nome} ({item.alunos.length}) + {expanded[item.nome] && ( @@ -89,12 +189,21 @@ const ListaAlunosProfessor = memo(() => { onPress={() => router.push({ pathname: '/Professor/Alunos/DetalhesAluno', - params: { aluno: JSON.stringify(aluno) } + params: { aluno: JSON.stringify(aluno) }, }) } > - {aluno.nome} - {aluno.estado} + + {aluno.nome} + + + {aluno.estado} + ))} @@ -108,17 +217,66 @@ const ListaAlunosProfessor = memo(() => { export default ListaAlunosProfessor; +/* ======================= + Styles +======================= */ + const styles = StyleSheet.create({ - safe: { flex: 1, paddingTop: Platform.OS === 'android' ? StatusBar.currentHeight : 0 }, - header: { flexDirection: 'row', alignItems: 'center', justifyContent: 'space-between', paddingHorizontal: 20, paddingVertical: 10 }, - btnVoltar: { width: 40, height: 40, borderRadius: 20, justifyContent: 'center', alignItems: 'center', elevation: 2 }, - tituloGeral: { fontSize: 22, fontWeight: 'bold' }, - spacer: { width: 40 }, - search: { borderRadius: 10, padding: 10, margin: 10 }, - card: { borderRadius: 10, padding: 15, marginBottom: 10, elevation: 2 }, - turmaNome: { fontSize: 18, fontWeight: 'bold' }, - listaAlunos: { marginTop: 10, paddingLeft: 10 }, - alunoItem: { paddingVertical: 8 }, - alunoNome: { fontSize: 16, fontWeight: '600' }, - alunoEstado: { fontSize: 14, marginTop: 2 }, + safe: { + flex: 1, + paddingTop: Platform.OS === 'android' ? StatusBar.currentHeight : 0, + }, + header: { + flexDirection: 'row', + alignItems: 'center', + justifyContent: 'space-between', + paddingHorizontal: 20, + paddingVertical: 10, + }, + btnVoltar: { + width: 40, + height: 40, + borderRadius: 20, + justifyContent: 'center', + alignItems: 'center', + elevation: 2, + }, + tituloGeral: { + fontSize: 22, + fontWeight: 'bold', + }, + spacer: { + width: 40, + }, + search: { + borderRadius: 10, + padding: 10, + margin: 10, + }, + card: { + borderRadius: 10, + padding: 15, + marginHorizontal: 10, + marginBottom: 10, + elevation: 2, + }, + turmaNome: { + fontSize: 18, + fontWeight: 'bold', + }, + listaAlunos: { + marginTop: 10, + paddingLeft: 10, + }, + alunoItem: { + paddingVertical: 8, + }, + alunoNome: { + fontSize: 16, + fontWeight: '600', + }, + alunoEstado: { + fontSize: 14, + marginTop: 2, + }, });