>> I'm interested in adjusting org-latex-preview to work in other major >> modes (most notably LaTeX-mode itself, so one can get rid of preview.el). >> On the advice of Karthik (Cc'd) I'll move the discussion from private >> mails to this list, so more people who might be interested can join in. >> ... >> [1]: >> https://abode.karthinks.com/org-latex-preview/latex-preview-everywhere.html > > Abstracting away previews is certainly welcome. > RMS explicitly asked Org mode team to work towards this goal: > https://list.orgmode.org/e1kikxv-0007iy...@fencepost.gnu.org/
I recently spent some time on this feature (LaTeX previews in all major-modes) and produced a few prototypes. You can see some demos in https://www.youtube.com/watch?v=u44X_th6_oY [1] The way support for other major modes works right now is based on the following observation: The `org-latex-preview' feature uses a tiny subset of the `org-element' API. Specifically, it uses only the functions - `org-element-context' - `org-element-property', referring to the properties :value, :begin and :end, and optionally :post-blank and :post-affiliated - `org-element-type', which returns either latex-fragment, latex-environment or any other symbol In addition, it uses two functions to generate the preamble and find section bounds: - `org-latex-preview--get-preamble' - `org-latex-preview--section-bounds' If a major-mode can provide drop-in replacements for all these functions, we can run org-latex-preview -- all of it, including live previews etc, in that mode.[2] I can share the full code in a dev branch soon after cleaning it up. In this email, I was hoping to solicit some feedback on the Emacs-wide API for this, which I describe below: ---------------------- I made calls to the above `org-elment-*' functions "pluggable", by storing these functions in buffer-local variables named - `org-latex-preview--fcontext' - `org-latex-preview--fproperty' - `org-latex-preview--ftype' and so on. Instead of calling `org-element-*' like this: (org-element-property :value (org-element-context)) org-latex-preview now uses (funcall org-latex-preview--fproperty :value (funcall org-latex-preview--fcontext)) A major mode can register these handlers with org-latex-preview like this (example for previews in LaTeX-mode, adapted from Tony's code): (setf (alist-get 'LaTeX-mode org-latex-preview-interfaces) `(:preamble ,#'latex-latex-preview--make-preamble :section ,#'latex-latex-preview-section-bounds :context ,#'latex-latex-preview-context :type ,#'latex-latex-preview-type :property ,#'latex-latex-preview-property)) See [1] for the definition of these `latex-latex-*' functions. These functions in `org-latex-preview-interfaces' are set as the values of the various `org-latex-preview--f*' variables during the first call to org-latex-preview in the buffer. There is no continuous runtime dispatch based on the major-mode. (Since we run many of these functions in the `after-change-functions' hook, we really want to avoid runtime dispatch.) Is this the best way to go about this? Karthik [1]: To see what the "adapter" code looks like for different modes, here are some examples: https://paste.karthinks.com/ac64169c-prog-latex-preview.el.html https://paste.karthinks.com/6ba26238-calc-latex-preview.el.html https://paste.karthinks.com/44930b4e-latex-latex-preview.el.html [2]: This is without handling accurate numbering. Numbering requires a couple more replacement functions that I can describe if required.