diff --git a/.continue/agents/new-config.yaml b/.continue/agents/new-config.yaml new file mode 100644 index 0000000..5caf2a7 --- /dev/null +++ b/.continue/agents/new-config.yaml @@ -0,0 +1,32 @@ +name: Local Config +version: 1.0.0 +schema: v1 + +models: + - name: Qwen Coder 32B + provider: ollama + model: qwen2.5-coder:32b + apiBase: http://localhost:11434 + roles: + - chat + - edit + - apply + + - name: Qwen Coder Autocomplete + provider: ollama + model: qwen2.5-coder:1.5b-base + apiBase: http://localhost:11434 + roles: + - autocomplete + + - name: Nomic Embed + provider: ollama + model: nomic-embed-text:latest + apiBase: http://localhost:11434 + roles: + - embed + +context: + - provider: code + - provider: docs + - provider: diff diff --git a/src/main/java/MarkNote.java b/src/main/java/MarkNote.java index 1fe4316..1e3ccf1 100644 --- a/src/main/java/MarkNote.java +++ b/src/main/java/MarkNote.java @@ -1034,8 +1034,9 @@ private void setupDocumentTab(DocumentTab tab) { previewDebouncer.debounce(() -> { Platform.runLater(() -> { previewPanel.updatePreview(text); - // Realigner la preview avec la position actuelle de l'éditeur - if (editorSplit.getItems().contains(previewPanel)) { + // Realigner la preview sur l'éditeur, mais pas en reading mode + // (l'éditeur est hors-scène, getScrollFraction() peut être faux) + if (!readingModeActive && editorSplit.getItems().contains(previewPanel)) { previewPanel.scrollToFraction(tab.getScrollFraction()); } updateStatusBarForTab(tab); @@ -1054,6 +1055,14 @@ private void setupDocumentTab(DocumentTab tab) { // Mettre à jour la preview et la statusbar quand on change d'onglet mainTabPane.getSelectionModel().selectedItemProperty().addListener((obs, oldTab, newTab) -> { if (newTab instanceof DocumentTab docTab) { + if (readingModeActive) { + // En mode lecture : remettre la scrollbar à zéro sur le nouveau document + docTab.scrollToTop(); + previewPanel.scrollToFractionAfterLoad(0.0); + } else { + // En mode normal : synchroniser la preview sur la position de l'éditeur + previewPanel.scrollToFractionAfterLoad(docTab.getScrollFraction()); + } previewPanel.updatePreview(docTab.getFullContent()); previewPanel.setCurrentFile(docTab.getFile()); updateStatusBarForTab(docTab); @@ -1063,9 +1072,10 @@ private void setupDocumentTab(DocumentTab tab) { } }); - // Synchroniser le défilement éditeur → preview + // Synchroniser le défilement éditeur → preview (pas en reading mode : éditeur hors-scène) tab.setOnScrollFractionChanged(fraction -> { - if (mainTabPane.getSelectionModel().getSelectedItem() == tab + if (!readingModeActive + && mainTabPane.getSelectionModel().getSelectedItem() == tab && editorSplit.getItems().contains(previewPanel)) { previewPanel.scrollToFraction(fraction); } diff --git a/src/main/java/ui/DocumentTab.java b/src/main/java/ui/DocumentTab.java index 39d1c52..f840396 100644 --- a/src/main/java/ui/DocumentTab.java +++ b/src/main/java/ui/DocumentTab.java @@ -606,6 +606,10 @@ public StyleClassedTextArea getEditor() { return editor; } + public void scrollToTop() { + scrollPane.scrollYToPixel(0); + } + /** * Insère du texte à la ligne suivant la position courante du curseur. * Si l'éditeur n'a pas de focus, le texte est ajouté à la fin du document. diff --git a/src/main/java/ui/PreviewPanel.java b/src/main/java/ui/PreviewPanel.java index c7321f8..cc5f13b 100644 --- a/src/main/java/ui/PreviewPanel.java +++ b/src/main/java/ui/PreviewPanel.java @@ -89,6 +89,9 @@ public class PreviewPanel extends BasePanel { /** Fichier source Markdown courant (peut être null pour les documents non sauvegardés). */ private File currentFile; + /** Fraction de défilement à appliquer après le prochain chargement de page. */ + private Double pendingScrollFraction = null; + /** Thème highlight.js courant, synchronisé avec le thème applicatif. */ private SyntaxTheme syntaxTheme = new SyntaxTheme("github", "#f6f8fa", "#24292e"); @@ -215,9 +218,19 @@ public PreviewPanel() { } } } - } else if (newState == Worker.State.SUCCEEDED && !pendingLocalPumlBlocks.isEmpty()) { - // Page chargée : déclencher le rendu async des blocs PlantUML locaux - dispatchLocalPumlRendering(); + } else if (newState == Worker.State.SUCCEEDED) { + // Page chargée : appliquer le scroll en attente si défini + if (pendingScrollFraction != null) { + double fraction = pendingScrollFraction; + pendingScrollFraction = null; + webView.getEngine().executeScript( + "window.scrollTo(0, (document.body.scrollHeight - window.innerHeight) * " + fraction + ")" + ); + } + // Déclencher le rendu async des blocs PlantUML locaux + if (!pendingLocalPumlBlocks.isEmpty()) { + dispatchLocalPumlRendering(); + } } }); @@ -1127,6 +1140,17 @@ public void scrollToFraction(double fraction) { ); } } + + /** + * Planifie un défilement vers la fraction donnée après le prochain chargement de page. + * À utiliser juste avant ou juste après {@link #updatePreview(String)} lors d'un changement + * de document, quand le WebView n'a pas encore terminé de charger le nouveau contenu. + * + * @param fraction La fraction de défilement dans [0.0, 1.0] + */ + public void scrollToFractionAfterLoad(double fraction) { + this.pendingScrollFraction = Math.min(1.0, Math.max(0.0, fraction)); + } /** * Définit le fichier Markdown source actuellement affiché.