Liste der Wörter am unteren Rand des Rahmens anzeigen?

20

Ich möchte 3 Wortlisten in separaten Zeilen horizontal am unteren Rand (obwohl oben auch funktionieren würde) jedes geöffneten Emacs-Frames anzeigen. Ich habe über 6 Möglichkeiten nachgedacht, und alle haben Probleme:

  1. Mein erster Gedanke war, meiner Mode-Zeile eine Zeile hinzuzufügen, aber AFAICT Sie können das Newline-Zeichen nicht in einer Mode-Zeile verwenden, es wird nur in "^ J" konvertiert.

  2. Mein zweiter Gedanke war, die Zeile über den oberen Bildschirmrand zu ziehen und die Kopfzeile zu verwenden, aber das Zeilenumbruch-Zeichen wird auch nicht unterstützt.

  3. Ich könnte ein Overlay über den letzten drei Zeilen des Fensters anzeigen, aber es scheint schwierig, dieses robust zu machen. Das Scrollen müsste ausgelöst werden, wenn der Punkt das Overlay erreicht und nicht das eigentliche Ende des Fensters, und ich müsste es ständig neu positionieren Die Überlagerung, da Überlagerungen im Textbereich und nicht im Fensterbereich liegen.

  4. Ich könnte versuchen, spezielle Fenster am unteren Rand des Rahmens zu erstellen. Ich habe versucht, dies zu codieren, aber es ist auch nicht sehr robust. Es scheint nicht richtig zu funktionieren, wenn ein Frame bereits geteilte Fenster enthält und ich Cx, 1 erneut an eine benutzerdefinierte Version von delete-other-windows binden musste, die ignoriert Meine Spezialfenster und ich bin mir sicher, dass es noch andere Eckverkleidungen gibt. Auch wenn ein Hilfefenster jetzt geöffnet wird, wird es vertikal geöffnet, weil es denkt, dass es bereits eine horizontale Aufteilung gibt (was technisch gesehen der Fall ist, aber es wird nur ein einzeiliges Fenster angezeigt).

  5. Ich könnte einen dedizierten Frame dafür haben, aber dann funktioniert meine Konfiguration im Terminalmodus nicht und ich müsste meinen Fenstermanager per Skript so einstellen, dass er am unteren Bildschirmrand bleibt und nicht ausgewählt werden kann, ohne das Layout zu beeinträchtigen. usw. usw.

  6. Ich könnte den Text für die 3 Zeilen direkt in den Minipuffer einfügen. Ich habe dies teilweise funktioniert, ich kann den Minipuffer vergrößern, um die 3 Zeilen aufzunehmen, und ich kann sie anzeigen. Jedes Mal, wenn eine Nachricht zurückgesendet wird, verschwinden die Zeilen, bis ich einen anderen Befehl erteile und sie wieder angezeigt werden. Idealerweise überlappen sich die drei Linien und der Echobereich nicht, sodass ich beide sehen kann. Dies wäre weniger ärgerlich, wenn ich zuverlässig filtern könnte, welche Nachrichten in den Echobereich gelangen. Ich habe eine Lösung in EmacsWiki gefunden, aber es scheint nicht für Nachrichten zu funktionieren, die aus der Emacs-C-Quelle stammen (speziell, die ich erhalten möchte) die dateispeichermeldungen loswerden, da ich oft auf einen timer autospeichere).

Für den Kontext ist es mein Ziel, ständig eine Anzeige der am häufigsten verwendeten Wörter im aktuellen Puffer, der Wörter am nächsten Punkt im aktuellen Puffer und der zuletzt im aktuellen Puffer verwendeten Wörter zu haben. Ich beabsichtige, sie über Sprachbefehle in den Puffer einfügen zu können. Also könnte ich "nächste 2" sagen und den zweiten Punkt aus der Liste der Wörter, die dem nächsten Punkt am nächsten sind, auswählen und einfügen. Mir ist nur wichtig, dass die Wortlisten für den Puffer angezeigt werden, den ich gerade bearbeite. Ich möchte nicht die Popup-Fenster verwenden, die von den verschiedenen Codevervollständigungsmodi verwendet werden, da die Listen immer sichtbar sein müssen.

Joseph Garvin
quelle
Gute Frage und gut gestellt. Ich hoffe, Sie erhalten einige nützliche Vorschläge.
Drew
Ich frage mich über die anderen Teile von # 5, abgesehen von dem Terminal-Modus-Bedarf (der sehr wichtig ist). Sie könnten einen speziellen Rahmen verwenden, der unten positioniert ist (kein Problem). Was meinst du mit unselektierbar und warum brauchst du das? Wenn Sie schreibgeschützt meinen, ist das auch kein Problem. Was meinen Sie damit , das Layout nicht zu beeinflussen ? Insgesamt ist mir Nummer 5 nicht klar.
Drew
@Drew: Ich meine, ich fahre mein WM mit der Tastatur, und es ist unwahrscheinlich, dass ich diesen Frame-Fokus jemals absichtlich aktivieren möchte, also möchte ich, dass meine Bindungen für das nächste / vorherige Fenster darüber hinweggehen. Ebenso möchte ich, dass die Fensterlayouts so aussehen, als ob dieser Rahmen nur Teil eines Panels / einer Taskleiste wäre. Bearbeiten: überall in diesem Kommentar sagte ich "Fenster" Ich meine X-Fenster, nicht Emacs-Fenster; p
Joseph Garvin
Eine andere Möglichkeit, die mir vorgeschlagen wurde, ist die Verwendung des Minipuffers. Ich habe keine Ahnung, ob es möglich ist, Text dort unten passiv anzuzeigen, ohne dass er alles andere beeinträchtigt, was versucht, ihn zu verwenden ...
Joseph Garvin
Hinweis zum Verwenden des Minipuffers hinzugefügt.
Joseph Garvin

Antworten:

8

Mit viel hackigem Experimentieren konnte ich # 6 (unter Verwendung von Minibuffer-Text) auf einen 'gut genug' Arbeitszustand bringen. Hier ist ein Screenshot:

Screenshot von Gürtel in Aktion

Es gibt mehrere Schlüsselteile, um diese Arbeit zu machen:

  • Das Einfügen von Text in den Minipuffer ist überraschenderweise fast das Richtige. Der dort eingefügte Text wird tatsächlich angezeigt.
  • Indem Sie dafür sorgen, dass der Text anstelle von normalem Text die Nachfolge einer Überlagerung ist, können Sie die Auswahl aufheben und müssen sich keine Sorgen machen, dass der Cursor versehentlich in die Überlagerung gerät.
  • Damit die Befehle zum Auffordern des Minipuffers ordnungsgemäß funktionieren, müssen Sie das Einfügen von Text / Overlay unterbinden, wenn das Minipuffer-Fenster aktiv ist.
  • Wenn Sie versuchen, die Größe des Minibuffers mit normalen Fenstergrößenänderungsfunktionen zu ändern, erhalten Sie Fehler, wenn Fenster zu klein sind. Wenn Sie die undokumentierte Funktion md-resize-minibuf verwenden, können Sie die Größe auf die exakte Anzahl von Zeilen ändern, die Sie möchten, solange Sie möchten habe resize-mini-windows zuerst auf nil gesetzt.
  • Um das Verschwinden der Listen zu beheben, wenn eine Nachricht vorliegt, müssen Sie die Nachrichtenfunktion anweisen, Nachrichten abzufangen. Dann setzen Sie sie selbst in den Minipuffer ein. Sie müssen sich auch die Variable current-message ansehen, die das speichert, was zuletzt im Echobereich angezeigt wurde (überraschenderweise sind der Echobereich und der Minibuffer technisch unterschiedlich und einige C-Quellcodefunktionen werden direkt in den Echobereich gedruckt, ohne die Nachricht durchzugehen Funktion). Der Code, den ich unten dafür gebe, ist unvollkommen. Nachrichten bleiben länger bestehen als normalerweise, was ich noch untersuchen muss (das Prüfen des letzten Eintrags in * Messages * mag einfacher und robuster sein), aber dies ist 'gut genug' für den Moment.

Hier ist ein Link zu meiner Implementierung mit einem Beispielgürtel, der den Killring anzeigt. Letztendlich wird dies Teil eines richtigen Projekts sein: https://gist.github.com/jgarvin/ce37d08654978fd7e4c9

Dies ist mein erstes Mal, dass ich eine signifikante Menge an Elisp schreibe, so dass die Qualität wahrscheinlich unterdurchschnittlich ist, aber es funktioniert.

Joseph Garvin
quelle
1

Weder die Mode-Zeile noch die Header-Zeile dürfen leider mehrzeilig sein. Ich habe schon früher danach gefragt und es gibt (zumindest nicht) eine versteckte Option, um dies zum Laufen zu bringen. Also 1 und 2 sind raus. Ich denke auch, dass 3 und 6 Hacks sind, die dich auf lange Sicht nicht glücklich machen werden. 3 und 4 scheinen gute Ansätze zu sein, aber sie zuverlässig zum Laufen zu bringen, ist eine ziemliche Investition.

Daher würde ich empfehlen, dass Sie dies zuerst auf emacs-devel bringen . Nach meiner Erfahrung werden Dinge irgendwann umgesetzt, wenn Sie sich die Mühe machen, genau zu erklären, was Sie wollen und warum dies eine gute Sache ist. Es kann einige Zeit dauern, zumindest bis zur nächsten Veröffentlichung, aber wenn Sie ein wenig warten oder die Entwicklungsversion verwenden, können Sie möglicherweise mit viel weniger Aufwand genau das bekommen, was Sie wollen.

Tarsius
quelle
Vielen Dank für den Vorschlag, sich an emacs-devel zu wenden. Obwohl ich eine Lösung gefunden habe, war es ziemlich hackig und es wäre schön, eine echte API zu haben, um direkt auf Bildschirmkoordinaten zu zeichnen. Wenn ich also Zeit habe, werde ich wahrscheinlich eine E-Mail auf diese Weise abschießen.
Joseph Garvin