Mejorado de la ventana de Plot

This commit is contained in:
Miguel 2025-06-01 19:09:36 +02:00
parent 085e99632f
commit 1eea99fde2
3 changed files with 98 additions and 110 deletions

View File

@ -1,4 +1,4 @@
{
"window_geometry": "1000x700+175+111",
"window_geometry": "1000x700+127+123",
"sash_pos_x": 339
}

View File

@ -136,11 +136,35 @@ class InteractiveResultManager:
def _show_plot_window(self, plot_result: PlotResult, window_key: str):
"""Muestra ventana con plot matplotlib"""
window = self._create_base_window(f"Plot - {plot_result.plot_type}", "800x600")
# Asegurar que las dimensiones de la ventana principal estén actualizadas
self.parent.update_idletasks()
parent_x = self.parent.winfo_x()
parent_y = self.parent.winfo_y()
parent_width = self.parent.winfo_width()
parent_height = self.parent.winfo_height()
# Definir dimensiones y posición para la ventana del plot
plot_window_width = 600 # Ancho deseado para la ventana del plot (puedes ajustarlo)
plot_window_height = parent_height # Misma altura que la ventana principal
# Posicionar la ventana del plot a la derecha de la ventana principal
plot_window_x = parent_x + parent_width
plot_window_y = parent_y # Misma posición Y que la ventana principal
window_title = f"Plot - {plot_result.plot_type}"
# Crear la ventana base especificando la posición
window = self._create_base_window(
window_title,
width=plot_window_width,
height=plot_window_height,
pos_x=plot_window_x,
pos_y=plot_window_y
)
self.open_windows[window_key] = window
try:
fig, ax = plt.subplots(figsize=(8, 6))
fig, ax = plt.subplots(figsize=(8, 6)) # Tamaño de la figura interna del plot
if plot_result.plot_type == "plot":
self._create_2d_plot(fig, ax, plot_result.args, plot_result.kwargs)
@ -247,7 +271,23 @@ class InteractiveResultManager:
def _show_matrix_window(self, matrix: sympy.Matrix, window_key: str):
"""Muestra ventana con matriz formateada"""
rows, cols = matrix.shape
window = self._create_base_window(f"Matriz {rows}×{cols}", "600x400")
window_title = f"Matriz {rows}×{cols}"
# Asegurar que las dimensiones de la ventana principal estén actualizadas
self.parent.update_idletasks()
parent_x = self.parent.winfo_x()
parent_y = self.parent.winfo_y()
parent_width = self.parent.winfo_width()
parent_height = self.parent.winfo_height()
# Definir dimensiones y posición para la ventana de la matriz
matrix_window_width = 600 # Ancho deseado
matrix_window_height = parent_height # Misma altura que la ventana principal
matrix_window_x = parent_x + parent_width # A la derecha
matrix_window_y = parent_y # Misma posición Y
window = self._create_base_window(window_title, width=matrix_window_width, height=matrix_window_height,
pos_x=matrix_window_x, pos_y=matrix_window_y)
self.open_windows[window_key] = window
# Crear frame con scroll
@ -332,7 +372,7 @@ class InteractiveResultManager:
def _show_matrix_property(self, matrix: sympy.Matrix, prop_name: str, prop_value: Any):
"""Muestra propiedad de matriz en ventana separada"""
prop_window = self._create_base_window(f"Matriz - {prop_name.title()}", "400x300")
prop_window = self._create_base_window(f"Matriz - {prop_name.title()}", width=400, height=300)
text_widget = scrolledtext.ScrolledText(
prop_window,
@ -353,7 +393,23 @@ class InteractiveResultManager:
def _show_list_window(self, lst: list, window_key: str):
"""Muestra ventana con lista expandida"""
window = self._create_base_window(f"Lista ({len(lst)} elementos)", "500x400")
window_title = f"Lista ({len(lst)} elementos)"
# Asegurar que las dimensiones de la ventana principal estén actualizadas
self.parent.update_idletasks()
parent_x = self.parent.winfo_x()
parent_y = self.parent.winfo_y()
parent_width = self.parent.winfo_width()
parent_height = self.parent.winfo_height()
# Definir dimensiones y posición para la ventana de la lista
list_window_width = 500 # Ancho deseado
list_window_height = parent_height # Misma altura que la ventana principal
list_window_x = parent_x + parent_width # A la derecha
list_window_y = parent_y # Misma posición Y
window = self._create_base_window(window_title, width=list_window_width, height=list_window_height,
pos_x=list_window_x, pos_y=list_window_y)
self.open_windows[window_key] = window
text_widget = scrolledtext.ScrolledText(
@ -374,7 +430,7 @@ class InteractiveResultManager:
def _show_dict_window(self, dct: dict, window_key: str):
"""Muestra ventana con diccionario expandido"""
window = self._create_base_window(f"Diccionario ({len(dct)} entradas)", "500x400")
window = self._create_base_window(f"Diccionario ({len(dct)} entradas)", width=500, height=400)
self.open_windows[window_key] = window
text_widget = scrolledtext.ScrolledText(
@ -395,7 +451,7 @@ class InteractiveResultManager:
def _show_object_window(self, obj: Any, window_key: str):
"""Muestra ventana con detalles de objeto"""
window = self._create_base_window(f"Objeto - {type(obj).__name__}", "600x500")
window = self._create_base_window(f"Objeto - {type(obj).__name__}", width=600, height=500)
self.open_windows[window_key] = window
text_widget = scrolledtext.ScrolledText(
@ -424,19 +480,40 @@ class InteractiveResultManager:
text_widget.insert("1.0", content)
text_widget.config(state="disabled")
def _create_base_window(self, title: str, geometry: str = "500x400") -> Toplevel:
"""Crea ventana base con estilo consistente"""
def _create_base_window(self,
title: str,
width: int = 500,
height: int = 400,
pos_x: Optional[int] = None,
pos_y: Optional[int] = None) -> Toplevel:
"""Crea ventana base con estilo consistente y posición opcional"""
window = Toplevel(self.parent)
window.title(title)
window.geometry(geometry)
window.configure(bg="#2b2b2b")
window.transient(self.parent)
window.transient(self.parent) # Hace que la ventana aparezca encima del padre
# Centrar ventana
window.update_idletasks()
x = (window.winfo_screenwidth() // 2) - (window.winfo_width() // 2)
y = (window.winfo_screenheight() // 2) - (window.winfo_height() // 2)
window.geometry(f"+{x}+{y}")
# Construir la cadena de geometría completa WxH+X+Y
geometry_str = f"{width}x{height}"
if pos_x is not None and pos_y is not None:
# Usar posición provista, asegurándose de que no sea negativa
final_x = max(0, pos_x)
final_y = max(0, pos_y)
geometry_str += f"+{final_x}+{final_y}"
else:
# Centrar ventana si no se especifica posición
# Para centrar, necesitamos las dimensiones de la pantalla
# y las dimensiones de la ventana (width, height ya las tenemos)
screen_width = window.winfo_screenwidth()
screen_height = window.winfo_screenheight()
center_x = (screen_width // 2) - (width // 2)
center_y = (screen_height // 2) - (height // 2)
final_x = max(0, center_x)
final_y = max(0, center_y)
geometry_str += f"+{final_x}+{final_y}"
window.geometry(geometry_str) # Aplicar tamaño y posición de una sola vez
return window

View File

@ -411,91 +411,6 @@ def launch_application():
show_error_with_log_info(e, log_file, "Error durante la ejecución de la aplicación")
def show_startup_splash():
"""Muestra splash screen durante la carga"""
if not logger:
return # Skip splash si no hay logger
try:
logger.info("Mostrando splash screen...")
splash = tk.Tk()
splash.title("Calculadora MAV")
splash.geometry("400x200")
splash.configure(bg="#2b2b2b")
splash.resizable(False, False)
# Centrar ventana
splash.update_idletasks()
x = (splash.winfo_screenwidth() // 2) - (splash.winfo_width() // 2)
y = (splash.winfo_screenheight() // 2) - (splash.winfo_height() // 2)
splash.geometry(f"+{x}+{y}")
# Contenido del splash
title_label = tk.Label(
splash,
text="Calculadora MAV",
font=("Arial", 20, "bold"),
fg="#ffffff",
bg="#2b2b2b"
)
title_label.pack(pady=20)
subtitle_label = tk.Label(
splash,
text="CAS Híbrido",
font=("Arial", 14),
fg="#82aaff",
bg="#2b2b2b"
)
subtitle_label.pack()
status_label = tk.Label(
splash,
text="Cargando componentes...",
font=("Arial", 10),
fg="#c8c8c8",
bg="#2b2b2b"
)
status_label.pack(pady=20)
# Barra de progreso simple
progress_frame = tk.Frame(splash, bg="#2b2b2b")
progress_frame.pack(pady=10)
progress_bar = tk.Canvas(
progress_frame,
width=300,
height=10,
bg="#1e1e1e",
highlightthickness=0
)
progress_bar.pack()
# Animar barra de progreso
def animate_progress():
for i in range(0, 301, 10):
progress_bar.delete("all")
progress_bar.create_rectangle(
0, 0, i, 10,
fill="#4fc3f7",
outline=""
)
splash.update()
splash.after(50)
splash.after(100, animate_progress)
splash.after(2000, splash.destroy)
logger.info("Splash screen mostrado correctamente")
splash.mainloop()
except Exception as e:
# Si hay error con splash, continuar sin él
logger.warning(f"Error mostrando splash screen: {e}")
pass
def main():
"""Función principal del launcher"""
global logger, log_file
@ -560,12 +475,8 @@ def main():
logger.info("✅ Todas las dependencias disponibles")
# Mostrar splash screen
if "--no-splash" not in sys.argv:
logger.info("Mostrando splash screen...")
show_startup_splash()
else:
logger.info("Splash screen omitido por argumento --no-splash")
# Splash screen eliminado
logger.info("Splash screen ha sido eliminado.")
# Lanzar aplicación
logger.info("Lanzando aplicación principal...")