utilities to fix LaTeX issues
This commit is contained in:
1 parent
2a4c5f4f7c
commit
a56fc6e680
7 files changed
+164
-2
No files matched your search
@@ -20,6 +20,7 @@ from copienator.platform import (
|
||||
open_path,
|
||||
validate_windows_labels,
|
||||
)
|
||||
from copienator.utils import LATEX_WARNING_MARKER
|
||||
|
||||
from .diagnostics import collect_diagnostics
|
||||
from .batch_monitor import BatchMonitor
|
||||
@@ -281,6 +282,8 @@ class CopienatorApp(tk.Tk):
|
||||
self.pending_refaire_commands: list[list[str]] = []
|
||||
self.refaire_command_index = 0
|
||||
self._correction_progress_buffer = ""
|
||||
self._latex_warning_buffer = ""
|
||||
self._latex_warning_paths: list[Path] = []
|
||||
|
||||
self.title("Copienator — assistant de correction")
|
||||
self.geometry("1180x820")
|
||||
@@ -493,6 +496,13 @@ class CopienatorApp(tk.Tk):
|
||||
clipboard_actions.grid(row=1, column=0, columnspan=6, sticky="w", pady=(5, 0))
|
||||
ttk.Button(clipboard_actions, text="Copier la sélection", command=self._copy_console_selection).pack(side="left")
|
||||
ttk.Button(clipboard_actions, text="Copier toute la sortie", command=self._copy_console_all).pack(side="left", padx=6)
|
||||
self.latex_warning_button = ttk.Button(
|
||||
clipboard_actions,
|
||||
text="Problèmes LaTeX…",
|
||||
command=self._show_current_latex_warnings,
|
||||
)
|
||||
self.latex_warning_button.pack(side="left", padx=6)
|
||||
self.latex_warning_button.pack_forget()
|
||||
ttk.Label(console_actions, text="Réponse au script").grid(row=0, column=0, padx=(0, 6))
|
||||
self.stdin_var = tk.StringVar()
|
||||
self.stdin_entry = ttk.Entry(console_actions, textvariable=self.stdin_var)
|
||||
@@ -582,6 +592,7 @@ class CopienatorApp(tk.Tk):
|
||||
messagebox.showerror("Dossier invalide", "Choisissez un dossier d’évaluation existant.")
|
||||
return
|
||||
self.batch_monitor.stop()
|
||||
self._reset_latex_warnings()
|
||||
self._save_current_form()
|
||||
self.state_store.load(evaluation)
|
||||
for step in self.steps:
|
||||
@@ -1532,6 +1543,8 @@ class CopienatorApp(tk.Tk):
|
||||
last_run_values=run_values,
|
||||
)
|
||||
self.active_step_id = step.id
|
||||
if step.id == "statement":
|
||||
self._reset_latex_warnings()
|
||||
if step.id == "correction":
|
||||
self._correction_progress_buffer = ""
|
||||
self.info_var.set("Correction : préparation des groupes…")
|
||||
@@ -1642,6 +1655,7 @@ class CopienatorApp(tk.Tk):
|
||||
if event == "output":
|
||||
output = str(payload)
|
||||
self._track_correction_progress(output)
|
||||
self._track_latex_warnings(output)
|
||||
self._append_console(output)
|
||||
elif event == "input_echo":
|
||||
self._append_console(f"> {payload}")
|
||||
@@ -1670,6 +1684,88 @@ class CopienatorApp(tk.Tk):
|
||||
f"({percent} %)."
|
||||
)
|
||||
|
||||
def _reset_latex_warnings(self) -> None:
|
||||
self._latex_warning_buffer = ""
|
||||
self._latex_warning_paths = []
|
||||
if hasattr(self, "latex_warning_button"):
|
||||
self.latex_warning_button.pack_forget()
|
||||
|
||||
def _track_latex_warnings(self, output: str, *, flush: bool = False) -> None:
|
||||
if self.active_step_id != "statement":
|
||||
return
|
||||
combined = self._latex_warning_buffer + output
|
||||
lines = combined.splitlines(keepends=True)
|
||||
self._latex_warning_buffer = ""
|
||||
if lines and not lines[-1].endswith(("\n", "\r")) and not flush:
|
||||
self._latex_warning_buffer = lines.pop()
|
||||
for line in lines:
|
||||
marker_at = line.find(LATEX_WARNING_MARKER)
|
||||
if marker_at < 0:
|
||||
continue
|
||||
raw_path = line[marker_at + len(LATEX_WARNING_MARKER):].strip()
|
||||
if not raw_path:
|
||||
continue
|
||||
path = Path(raw_path).expanduser()
|
||||
if not path.is_absolute() and self.evaluation:
|
||||
path = self.evaluation / path
|
||||
path = path.resolve()
|
||||
if path not in self._latex_warning_paths:
|
||||
self._latex_warning_paths.append(path)
|
||||
if self._latex_warning_paths:
|
||||
self.latex_warning_button.pack(side="left", padx=6)
|
||||
|
||||
def _show_current_latex_warnings(self) -> None:
|
||||
if not self._latex_warning_paths:
|
||||
messagebox.showinfo("Compilation LaTeX", "Aucun problème de compilation détecté.")
|
||||
return
|
||||
dialog = tk.Toplevel(self)
|
||||
dialog.title("Problèmes de compilation LaTeX")
|
||||
dialog.geometry("900x380")
|
||||
dialog.transient(self)
|
||||
dialog.columnconfigure(0, weight=1)
|
||||
dialog.rowconfigure(1, weight=1)
|
||||
ttk.Label(
|
||||
dialog,
|
||||
text=(
|
||||
f"{len(self._latex_warning_paths)} fichier(s) n’ont pas été compilés "
|
||||
"correctement. Sélectionnez-en un pour ouvrir ses éléments."
|
||||
),
|
||||
padding=10,
|
||||
wraplength=850,
|
||||
justify="left",
|
||||
).grid(row=0, column=0, sticky="ew")
|
||||
paths = tk.Listbox(dialog, exportselection=False)
|
||||
for pdf_path in self._latex_warning_paths:
|
||||
try:
|
||||
label = str(pdf_path.relative_to(self.evaluation)) if self.evaluation else str(pdf_path)
|
||||
except ValueError:
|
||||
label = str(pdf_path)
|
||||
paths.insert("end", label)
|
||||
paths.grid(row=1, column=0, sticky="nsew", padx=10)
|
||||
paths.selection_set(0)
|
||||
|
||||
actions = ttk.Frame(dialog, padding=10)
|
||||
actions.grid(row=2, column=0, sticky="ew")
|
||||
|
||||
def selected_pdf() -> Path:
|
||||
selection = paths.curselection()
|
||||
index = selection[0] if selection else 0
|
||||
return self._latex_warning_paths[index]
|
||||
|
||||
def open_folder() -> None:
|
||||
self._open_desktop_path(selected_pdf().parent, "dossier de compilation")
|
||||
|
||||
def open_source() -> None:
|
||||
self._open_desktop_path(selected_pdf().with_suffix(".tex"), "fichier source LaTeX")
|
||||
|
||||
def open_pdf() -> None:
|
||||
self._open_desktop_path(selected_pdf(), "fichier PDF compilé")
|
||||
|
||||
ttk.Button(actions, text="Ouvrir le dossier", command=open_folder).pack(side="left")
|
||||
ttk.Button(actions, text="Ouvrir le .tex", command=open_source).pack(side="left", padx=6)
|
||||
ttk.Button(actions, text="Ouvrir le PDF", command=open_pdf).pack(side="left")
|
||||
ttk.Button(actions, text="Fermer", command=dialog.destroy).pack(side="right")
|
||||
|
||||
def _batch_watch_status_changed(self, message: str) -> None:
|
||||
self.batch_watch_status.set(message)
|
||||
self._update_controls()
|
||||
@@ -1710,6 +1806,8 @@ class CopienatorApp(tk.Tk):
|
||||
step_id = self.active_step_id
|
||||
if not step_id:
|
||||
return
|
||||
if step_id == "statement":
|
||||
self._track_latex_warnings("", flush=True)
|
||||
status = process_status(return_code, interrupted)
|
||||
if status == "success" and self.pending_refaire_commands:
|
||||
command = self.pending_refaire_commands.pop(0)
|
||||
@@ -1790,9 +1888,17 @@ class CopienatorApp(tk.Tk):
|
||||
title = self.step_by_id[step_id].title
|
||||
self._append_console(f"\n[Terminé — code {return_code} — {STATUS_LABELS[status]}]\n")
|
||||
self.info_var.set(f"{title} : {STATUS_LABELS[status].lower()} (code {return_code}).")
|
||||
if step_id == "statement" and self._latex_warning_paths:
|
||||
count = len(self._latex_warning_paths)
|
||||
self.info_var.set(
|
||||
f"{title} : {STATUS_LABELS[status].lower()} (code {return_code}) — "
|
||||
f"{count} problème(s) LaTeX."
|
||||
)
|
||||
self.active_step_id = None
|
||||
self._populate_tree()
|
||||
self._update_controls()
|
||||
if step_id == "statement" and self._latex_warning_paths:
|
||||
self.after_idle(self._show_current_latex_warnings)
|
||||
if step_id == "personal_read":
|
||||
if status == "success":
|
||||
self.info_var.set("Commande terminée. Poursuivez la relecture, puis cliquez sur « Marquer réussie ».")
|
||||
|
||||
@@ -706,7 +706,7 @@ def build_workflow(show_personal_steps: bool) -> list[StepDefinition]:
|
||||
"personal_deploy",
|
||||
"Étapes personnelles",
|
||||
"Déployer et publier les copies",
|
||||
"Étape manuelle : déployer miqmacs-copies-assets puis mettre à jour les copies depuis l’administration.",
|
||||
"Étape manuelle : déployer miqmacs-copies-assets et la section `Interro` (inutile : mettre à jour les copies depuis l’administration).",
|
||||
(manual("deploy"),),
|
||||
personal=True,
|
||||
),
|
||||
|
||||
Reference in new issue
Block a user