¿Cómo puedo configurar manualmente los enlaces en modo org?

7

Así que estoy tratando de hacer un "modo de enlaces automáticos" para emular la funcionalidad del software de toma de notas como Tomboy Notes o notes.vim, que vincula automáticamente cualquier texto que sea el título de una nota. Pero soy totalmente nuevo en Emacs y en Elisp. Esto es lo que tengo hasta ahora (es como el primer elisp que he escrito, sé amable):

;; Set directory of files to search for *.org files 
(setq autolinks-mode-dir "~/Dropbox/Org/")

;; Get all .org files in this directory. 
(setq autolinks-mode-files (directory-files autolinks-mode-dir t "[.]org\\'"))

;; Convert it to a list of just the filenames, without paths.
(setq autolinks-mode-files-bare
      (mapcar 'file-name-nondirectory autolinks-mode-files))

;; Strip extensions
(setq autolinks-mode-topics
      (mapcar 'file-name-sans-extension autolinks-mode-files-bare))

Hasta aquí todo bien. Ahora tengo una lista de temas y una lista de los archivos correspondientes. Por ejemplo, el tema "James" corresponde a un archivo de organización en "/path/to/notes/James.org". Ahora quiero actualizar manualmente la lista de enlaces de la organización para un búfer en particular con esta lista de temas, de modo que, cuando active este modo, resalte cualquier instancia de la palabra "James" en un búfer de organización y lo convierta en un enlace a /path/to/notes/James.org. Lo mismo con un multi-org palabra archivo, como "Henry James", lo que apuntaría a /path/to/notes/Henry James.org. Tenga en cuenta que no estoy tratando de reemplazar todas las instancias de Jamescon [[James]]o <James>o algo, solo estoy tratando de hacer que esos fragmentos de texto se comporten como enlaces.

Estuve navegando por org.el y vi esta variable:

(defvar org-link-re-with-space nil
  "Matches a link with spaces, optional angular brackets around it.")

Que en mi sistema tiene todo tipo de cosas, probablemente debido a org-ref y otras cosas:

org-link-re-with-space is a variable defined in ‘org.el’.
Its value is
"<?\\(A\\(?:cp?\\|utocite[*s]?\\)\\|Cite\\(?:a\\(?:l[pt]\\|uthor\\*?\\)\\|[pst]\\)?\\|Gls\\(?:pl\\)?\\|Notecite\\|P\\(?:arencites?\\|notecite\\)\\|Smartcites?\\|Textcites?\\|a\\(?:c\\(?:p\\|r\\(?:full\\|long\\|short\\)\\)?\\|ddbibresource\\|uto\\(?:cite[*s]?\\|ref\\)\\)\\|b\\(?:bdb\\|ib\\(?:entry\\|liography\\(?:style\\)?\\|tex\\)\\)\\|cite\\(?:a\\(?:l\\(?:[pt]\\*\\|[pt]\\)\\|uthor\\*?\\)\\|date\\*?\\|num\\|p\\*\\|t\\(?:\\*\\|ext\\|itle\\*?\\)\\|url\\|year\\*?\\|[*pst]\\)?\\|do\\(?:cview\\|i\\)\\|e\\(?:l\\(?:feed\\|isp\\)\\|qref\\)\\|f\\(?:ile\\(?:\\+\\(?:\\(?:emac\\|sy\\)s\\)\\)?\\|notecite\\|oot\\(?:cite\\(?:s\\|texts?\\)?\\|fullcite\\)\\|tp\\|ullcite\\)\\|g\\(?:ls\\(?:desc\\|link\\|\\(?:p\\|symbo\\)l\\)?\\|nus\\)\\|h\\(?:elp\\|ttps?\\)\\|i\\(?:n\\(?:dex\\|fo\\)\\|pynb\\|rc\\)\\|l\\(?:abel\\|ist-of-\\(?:\\(?:figur\\|tabl\\)es\\)\\)\\|m\\(?:ailto\\|\\(?:essag\\|h\\|u4\\)e\\)\\|n\\(?:ameref\\|ews\\|o\\(?:bibliography\\|\\(?:te\\)?cite\\)\\)\\|orgit\\(?:-\\(?:log\\|rev\\)\\)?\\|p\\(?:a\\(?:geref\\|rencite[*s]?\\)\\|notecite\\|rint\\(?:bibliography\\|index\\)\\)\\|r\\(?:ef\\|mail\\)\\|s\\(?:hell\\|martcites?\\|upercites?\\)\\|textcites?\\|w3m\\):\\([^]    

Por lo tanto, parece que Org tiene la funcionalidad para poder resaltar texto sin formato como un enlace. Simplemente no sé la mejor manera de hacerlo. Creo que puedo agregar mi lista de palabras de enlace org-link-re-with-space, ¿tal vez? Pero entonces, ¿cómo establezco sus objetivos? Cualquier ayuda sería muy apreciada.

Jonathan
fuente
Probablemente no pueda usar org-links para esto. Parece que desea utilizar el bloqueo de fuente para obtener el comportamiento que desea. Puede encontrar algo de inspiración aquí kitchingroup.cheme.cmu.edu/blog/2015/06/22/… . En particular, el uso de button-lock-set-button para hacer clic en algunos patrones.
John Kitchin
No estoy seguro de entender completamente lo que está tratando de hacer, pero ¿por qué no simplemente reemplazar todas las ocurrencias de Jamescon [[file:/path/to/notes/James.org][James]]en el búfer? Luego aparecerá como un enlace si el búfer está en org-modemodo principal.
Håkon Hægland
1
La idea no es crear nuevos enlaces, sino emular automáticamente enlaces para cualquier nombre de archivo. De esa manera, puedo eliminar James.org, cambiar su nombre y no tener que preocuparme por actualizar el enlace. El enlace duro es una tontería en comparación con el enlace automático.
Jonathan

Respuestas:

1

Creo que esto es esencialmente lo que quieres:

;; Set directory of files to search for *.org files
(setq autolinks-mode-dir "/Users/jkitchin/vc/journal/2018/08/07/")

;; Get all .org files in this directory.
(setq autolinks-mode-files (directory-files autolinks-mode-dir t "[.]org\\'"))

;; Convert it to a list of just the filenames, without paths.
(setq autolinks-mode-files-bare
      (mapcar 'file-name-nondirectory autolinks-mode-files))

;; Strip extensions
(setq autolinks-mode-topics
      (mapcar 'file-name-sans-extension autolinks-mode-files-bare))

(button-lock-set-button
 (regexp-opt autolinks-mode-topics)
 (lambda (event)
   (interactive "e")
   (let ((click-pos (posn-point (event-end event))))
     (save-mark-and-excursion
      (save-match-data
    ;; This is clunky, but with grouping the properties may not extend to
    ;; the whole regexp, e.g. if you set properties on a subgroup.
    (goto-char (previous-single-property-change click-pos
                            'button-lock))
    ;; now make sure we see it again to get the match-data
    (while (not (looking-at (regexp-opt autolinks-mode-topics)))
      (backward-char))
    (find-file (expand-file-name
            (concat (match-string 0) ".org")
            autolinks-mode-dir))))))
 :face (list 'org-link))

Puede incrustar eso en una función y luego llamarlo en un gancho de modo org y activar el modo de bloqueo de botones. Eso debería hacer que sus temas se vean como enlaces, y cuando haga clic en ellos abrirá el archivo. Un posible inconveniente es el orden en que se buscan los temas. Debes asegurarte de que se busque "Henry James" antes de James, lo que puede requerir cierta clasificación por longitud o algo así.

John Kitchin
fuente