En nuestro recorrido por la creación de sistemas CRUD con Java y JDBC, nos adentramos en la gestión de profesores, un proceso que resulta más sencillo que el de alumnos debido a la menor cantidad de campos involucrados, limitándose a nombre y apellidos. Para mantener el orden en nuestro proyecto, comenzamos organizando el código en paquetes específicos, lo que facilita la encapsulación y el control de acceso a las clases, aunque nos encontramos con la necesidad de hacer públicos ciertos paneles para evitar problemas con el editor de NetBeans.
Al diseñar la interfaz, optamos por un JFrame llamado ListProfesoresFrame, que utiliza un BorderLayout para distribuir los componentes. En la parte superior, colocamos una barra de herramientas (toolbar) con botones para agregar, editar, borrar, guardar y cancelar, separados adecuadamente para mejorar la usabilidad. La tabla que mostrará los datos de los profesores se sitúa en el centro, dentro de un panel que también alojará un panel lateral para detalles o formularios.
Para manejar los datos de la tabla, creamos un modelo personalizado llamado ProfesoresTableModel que extiende de AbstractTableModel. Este modelo se conecta con un ProfesorDAO que gestiona la comunicación con la base de datos. Implementamos los métodos esenciales como getRowCount, getColumnCount y getValueAt, donde definimos que la tabla tendrá tres columnas: identificador, apellidos y nombre. Además, sobrescribimos getColumnName para que la tabla muestre los encabezados adecuados. Este enfoque nos permite mantener una separación clara de responsabilidades y un código más limpio y mantenible.
En cuanto a la apariencia de los botones, personalizamos sus iconos y desactivamos elementos visuales como bordes y rellenos para lograr un estilo más moderno y limpio, similar al que se ve en sistemas Mac. También deshabilitamos la capacidad de mover la barra de herramientas para evitar comportamientos no deseados. Inicialmente, los botones de acción están desactivados y se habilitan solo cuando corresponde, según la interacción del usuario.
Para mostrar el estado de la aplicación, utilizamos una etiqueta (Label) en la parte inferior que indica, por ejemplo, cuántos profesores están visibles en la tabla. Ajustamos su fuente y agregamos un borde vacío para mejorar la presentación y evitar que el texto se vea apretado.
La conexión con la base de datos se realiza mediante un MySQLDaoManager, configurado con los parámetros adecuados para acceder a nuestra base de datos de ejemplo. Esto nos permite cargar y mostrar la lista de profesores en la tabla, aunque inicialmente los botones de acción no están activos.
La interactividad se implementa creando un panel de detalles con campos para nombre y apellidos, que puede ser editable o no según el contexto. Definimos métodos para cargar datos (loadData) y guardar datos (saveData) en este panel, manejando casos donde el profesor sea nulo para evitar errores. También incluimos métodos para establecer y obtener el profesor actual, y para activar o desactivar la edición de los campos.
Al integrar este panel en el frame principal, configuramos los eventos de los botones para que respondan adecuadamente. Por ejemplo, al pulsar Nuevo, se limpia el formulario y se habilita la edición para crear un nuevo profesor. Al seleccionar un profesor en la tabla y pulsar Editar, se cargan sus datos en el panel para modificar. Para obtener el profesor seleccionado, extraemos el identificador de la fila seleccionada y consultamos el DAO correspondiente.
El botón Borrar muestra un diálogo de confirmación antes de eliminar el profesor seleccionado de la base de datos. Tras la eliminación, actualizamos la tabla y limpiamos la selección, además de desactivar los botones de edición y borrado para evitar acciones inválidas.
Manejamos la selección en la tabla con un ListSelectionListener que habilita o deshabilita los botones según si hay una fila seleccionada. Esto garantiza que las acciones solo estén disponibles cuando tengan sentido.
El botón Cancelar desactiva la edición y recarga los datos originales del profesor, permitiendo al usuario revertir cambios no deseados. Finalmente, el botón Guardar recopila los datos del formulario y decide si debe insertar un nuevo registro o actualizar uno existente, basándose en si el identificador del profesor es nulo. Después de guardar, actualizamos la tabla para reflejar los cambios y desactivamos la edición.
Probamos el sistema creando un profesor de prueba, modificándolo, cancelando cambios y borrándolo, confirmando que todas las funcionalidades básicas del CRUD funcionan correctamente. Este ejemplo nos prepara para abordar casos más complejos, como la gestión de asignaturas, donde tendremos que combinar datos de varias tablas y manejar relaciones más elaboradas.
public class ProfesoresTableModel extends AbstractTableModel {
private List<Profesor> profesores = new ArrayList<>();
private ProfesorDAO profesorDAO;
public ProfesoresTableModel(ProfesorDAO profesorDAO) {
this.profesorDAO = profesorDAO;
updateModel();
}
public void updateModel() {
try {
profesores = profesorDAO.obtenerTodos();
} catch (DAOException e) {
profesores = new ArrayList<>();
// Manejo de excepción
}
fireTableDataChanged();
}
@Override
public int getRowCount() {
return profesores.size();
}
@Override
public int getColumnCount() {
return 3; // ID, Apellidos, Nombre
}
@Override
public Object getValueAt(int rowIndex, int columnIndex) {
Profesor prof = profesores.get(rowIndex);
switch (columnIndex) {
case 0: return prof.getId();
case 1: return prof.getApellidos();
case 2: return prof.getNombre();
default: return null;
}
}
@Override
public String getColumnName(int column) {
switch (column) {
case 0: return "ID";
case 1: return "Apellidos";
case 2: return "Nombre";
default: return "";
}
}
}
public class DetalleProfesorPanel extends JPanel {
private JTextField nombreField;
private JTextField apellidosField;
private Profesor profesor;
private boolean editable;
public DetalleProfesorPanel() {
setLayout(new GridLayout(2, 2, 5, 5));
add(new JLabel("Nombre:"));
nombreField = new JTextField();
add(nombreField);
add(new JLabel("Apellidos:"));
apellidosField = new JTextField();
add(apellidosField);
}
public void setProfesor(Profesor profesor) {
this.profesor = profesor != null ? profesor : new Profesor();
loadData();
}
public Profesor getProfesor() {
saveData();
return profesor;
}
public void setEditable(boolean editable) {
this.editable = editable;
nombreField.setEditable(editable);
apellidosField.setEditable(editable);
}
private void loadData() {
if (profesor != null) {
nombreField.setText(profesor.getNombre());
apellidosField.setText(profesor.getApellidos());
} else {
nombreField.setText("");
apellidosField.setText("");
}
}
private void saveData() {
if (profesor == null) {
profesor = new Profesor();
}
profesor.setNombre(nombreField.getText());
profesor.setApellidos(apellidosField.getText());
}
}
Este enfoque modular y organizado nos permite gestionar de forma sencilla y clara la información de profesores, facilitando la extensión y mantenimiento del sistema.