I am developing a student management program in Python using tkinter, utilizing classes. I have one class for the main window and another class for a fully functional CRUD (Create, Read, Update, Delete) interface that interacts with a SQLite database. The CRUD screen was intended to serve as a base for other functionalities, such as login screens and different menus. However, I need to implement a way to switch between different class screens to display these various menus and a login screen.
Here is my code:
import tkinter as tk
from tkinter import ttk
from ttkthemes import ThemedTk
from tkinter import messagebox
import sqlite3
class AplicacionGestionEstudiantes():
def __init__(self):
super().__init__()
self.root = ThemedTk(theme="radiance")
self.root.title("Gestión de perfiles de estudiantes v1.0")
# Maximizar la ventana
self.root.state('zoomed')
# Conectar a la base de datos
self.ruta_db = 'C:/Users/Admin/Documents/all/python/programa de gestión/sistema_estudiantes.db'
self.conn = sqlite3.connect(self.ruta_db)
self.cursor = self.conn.cursor()
# Configurar el sistema de gestión de geometría
self.root.grid_rowconfigure((0, 1, 2, 3, 4, 5, 6, 7, 8), weight=1)
self.root.grid_columnconfigure((0, 1, 2, 3, 4, 5, 6, 7, 8), weight=1)
self.contenedor_principal = tk.Frame(self.root, bg="yellow")
self.contenedor_principal.grid(columnspan=9, rowspan=9, sticky="nsew")
# Widgets
# Navbar
self.navbar = Navbar(self)
# Tabla Principal
self.tabla_principal = Frame_1(self.root, self.cursor, self.conn)
# Configurar evento de cierre personalizado para la ventana
self.root.protocol("WM_DELETE_WINDOW", self.cerrar_ventana)
# Bucle principal de la aplicación
self.root.mainloop()
# Cerrar la conexión a la base de datos
self.conn.close()
def cerrar_ventana(self):
self.root.destroy()
class Navbar:
def __init__(self, root):
self.root = root
# Crear los botones de navegación
self.button1 = ttk.Button(
text="Pantalla 1", command=self.mostrar_pantalla_1)
self.button1.grid(row=0, column=6)
self.button2 = ttk.Button(
text="Pantalla 2", command=self.mostrar_pantalla_2)
self.button2.grid(row=0, column=7)
self.button3 = ttk.Button(
text="Pantalla 3", command=self.mostrar_pantalla_3)
self.button3.grid(row=0, column=8)
def mostrar_pantalla_1(self):
print("Pantalla 1")
def mostrar_pantalla_2(self):
print("Pantalla 2")
def mostrar_pantalla_3(self):
print("Pantalla 3")
# Crear tabla
class Frame_1(tk.Frame):
def __init__(self, root, cursor, conn):
self.root = root
self.cursor = cursor
self.conn = conn
# Conectar a la base de datos
self.ruta_db = 'C:/Users/Admin/Documents/all/python/programa de gestión/sistema_estudiantes.db'
self.conn = sqlite3.connect(self.ruta_db)
self.cursor = self.conn.cursor()
self.tabla = ttk.Treeview(
columns=("ID", "Cedula", "Nombre", "Edad"), show="headings")
self.tabla.grid(row=1, rowspan=7, column=1,
columnspan=5, sticky="nsew")
# Configurar encabezados de columna
self.tabla.heading("ID", text="ID")
self.tabla.heading("Cedula", text="Cedula")
self.tabla.heading("Nombre", text="Nombre")
self.tabla.heading("Edad", text="Edad")
# Configurar anchos de columna
self.tabla.column("ID")
self.tabla.column("Cedula")
self.tabla.column("Nombre")
self.tabla.column("Edad")
# Crear etiquetas y campos de entrada
self.label_cedula = ttk.Label(self.root, text="Cédula:")
self.label_cedula.grid(row=1, column=6)
self.entry_cedula = ttk.Entry(self.root)
self.entry_cedula.grid(row=2, column=6)
self.label_nombre = ttk.Label(self.root, text="Nombre:")
self.label_nombre.grid(row=3, column=6)
self.entry_nombre = ttk.Entry(self.root)
self.entry_nombre.grid(row=4, column=6)
self.label_edad = ttk.Label(self.root, text="Edad:")
self.label_edad.grid(row=5, column=6)
self.entry_edad = ttk.Entry(self.root)
self.entry_edad.grid(row=6, column=6)
# Crear botones
self.btn_crear = ttk.Button(
self.root, text="Crear", command=self.crear_estudiante)
self.btn_crear.grid(row=0, column=2)
self.btn_leer = ttk.Button(
self.root, text="Leer", command=self.leer_estudiantes)
self.btn_leer.grid(row=0, column=3)
self.btn_actualizar = ttk.Button(
self.root, text="Actualizar", command=self.abrir_ventana_actualizacion)
self.btn_actualizar.grid(row=0, column=4)
self.btn_eliminar = ttk.Button(
self.root, text="Eliminar", command=self.eliminar_estudiante)
self.btn_eliminar.grid(row=0, column=5)
# Mostrar los datos de la base de datos en la tabla
self.mostrar_estudiantes()
def mostrar_estudiantes(self):
# Limpiar la tabla
records = self.tabla.get_children()
for element in records:
self.tabla.delete(element)
# Obtener los datos de la base de datos
self.cursor.execute("SELECT * FROM Estudiante")
rows = self.cursor.fetchall()
# Insertar los datos en la tabla
for row in rows:
self.tabla.insert("", "end", values=row)
def leer_estudiantes(self):
# Obtener el estudiante seleccionado
selected = self.tabla.focus()
values = self.tabla.item(selected, 'values')
# Mostrar los datos en los campos de entrada
self.entry_cedula.delete(0, tk.END)
self.entry_cedula.insert(tk.END, values[0])
self.entry_nombre.delete(0, tk.END)
self.entry_nombre.insert(tk.END, values[1])
self.entry_edad.delete(0, tk.END)
self.entry_edad.insert(tk.END, values[2])
def crear_estudiante(self):
# Obtener los datos de los campos de entrada
cedula = self.entry_cedula.get()
nombre = self.entry_nombre.get()
edad = self.entry_edad.get()
# Insertar el estudiante en la base de datos
self.cursor.execute(
"INSERT INTO Estudiante (cedula, nombre, edad) VALUES (?, ?, ?)", (cedula, nombre, edad))
self.conn.commit()
# Limpiar los campos de entrada
self.entry_cedula.delete(0, tk.END)
self.entry_nombre.delete(0, tk.END)
self.entry_edad.delete(0, tk.END)
# Actualizar la tabla
self.mostrar_estudiantes()
def actualizar_estudiante(self, estudiante_id, new_cedula, new_nombre, new_edad):
# Actualizar los valores en la base de datos
self.cursor.execute("UPDATE Estudiante SET cedula=?, nombre=?, edad=? WHERE estudiante_id=?",
(new_cedula, new_nombre, new_edad, estudiante_id))
self.conn.commit()
# Actualizar la tabla
self.mostrar_estudiantes()
messagebox.showinfo("Éxito", "Estudiante actualizado correctamente.")
def abrir_ventana_actualizacion(self):
# Obtener la fila seleccionada en la tabla
selected_row = self.tabla.selection()
if selected_row:
# Obtener los valores de la fila seleccionada
values = self.tabla.item(selected_row)["values"]
# Crear una nueva ventana
ventana_actualizacion = tk.Toplevel(self.root)
ventana_actualizacion.title("Actualizar Estudiante")
# Mostrar la información vieja en la nueva ventana
ttk.Label(ventana_actualizacion, text="Información:").pack()
ttk.Label(ventana_actualizacion, text="Cédula:").pack()
ttk.Label(ventana_actualizacion, text=values[1]).pack()
ttk.Label(ventana_actualizacion, text="Nombre:").pack()
ttk.Label(ventana_actualizacion, text=values[2]).pack()
ttk.Label(ventana_actualizacion, text="Edad:").pack()
ttk.Label(ventana_actualizacion, text=values[3]).pack()
# Crear campos de texto para introducir los nuevos valores
ttk.Label(ventana_actualizacion, text="Nuevos Valores:").pack()
ttk.Label(ventana_actualizacion, text="Cédula:").pack()
new_cedula = ttk.Entry(ventana_actualizacion)
new_cedula.pack()
ttk.Label(ventana_actualizacion, text="Nombre:").pack()
new_nombre = ttk.Entry(ventana_actualizacion)
new_nombre.pack()
ttk.Label(ventana_actualizacion, text="Edad:").pack()
new_edad = ttk.Entry(ventana_actualizacion)
new_edad.pack()
# Crear un botón para actualizar los valores
ttk.Button(ventana_actualizacion, text="Actualizar", command=lambda: self.actualizar_estudiante(
values[0], new_cedula.get(), new_nombre.get(), new_edad.get())).pack()
else:
messagebox.showerror("Error", "No se ha seleccionado ninguna fila.")
def eliminar_estudiante(self):
# Obtener la fila seleccionada en la tabla
selected_row = self.tabla.selection()
if selected_row:
# Obtener el ID del estudiante seleccionado
estudiante_id = self.tabla.item(selected_row)['values'][0]
# Confirmar eliminación con un cuadro de diálogo
confirmar = messagebox.askyesno(
"Confirmar", "¿Estás seguro de que deseas eliminar este estudiante?")
if confirmar:
# Eliminar el estudiante de la base de datos
self.cursor.execute(
"DELETE FROM Estudiante WHERE estudiante_id=?", (estudiante_id,))
self.conn.commit()
# Actualizar la tabla
self.mostrar_estudiantes()
messagebox.showinfo(
"Éxito", "Estudiante eliminado correctamente.")
else:
messagebox.showerror(
"Error", "No se ha seleccionado ninguna fila.")
# Instanciar la aplicación
if __name__ == "__main__":
app = AplicacionGestionEstudiantes()
I would like to know how to implement screen switching between these different classes in tkinter. I have seen suggestions to use frames to encompass each class, create a main frame in the main window, and define a dictionary to facilitate switching between screens. However, I am unsure how to implement this approach.
Could someone please provide guidance on how to implement screen switching between classes in tkinter using frames? Examples or code snippets would be greatly appreciated.
I apologize for any mistakes that the code may have; I'm still relatively new to programming in general xd
Thank you in advance for your help!