10

I'm trying to switch my editor from vscodium (telemetry free VS Code) to Emacs. So far, I've installed AUCTeX and tried some things in a testdocument. For regular LaTeX code everything is fine.

But for LaTeX3 code I couldn't figure out a satisfying solution so far. By default there seems to be whether proper syntax highlighting support, nor a running auto-completion mechanism for LaTeX3 code. It is possible to parse packages expl3 and xparse with ctrl+c,ctrl+n in a document or automate this with (setq TeX-parse-self t) in the .emacs init file. But to accomplish it, I've to load the packages with \usepackage or \RequirePackage before parsing. That seems very unnecessary since those macros are part of the kernel for some time.

Besides that, it works good for xparse command with a recognisable syntax and auto-completion. For LaTeX3 commands the result is not very pleasant regarding syntax highlighting (all in dim gray), and an auto-completion mechanism is totally missing (even with auto-completion-auctex package). As far as I have searched, there are not too many posts regarding that topic, whether on TeX.SE, nor anywhere else in the web. This question e.g. suggests in an up-to-date comment similar cluelessness (I also tried the possiblities suggested in other comments/linked posts of the same question). Searching for auctex/emacs in combination with expl3/latex3 on our site also offers very few answers: 1, 2, 3, 4.

Therefore, my question is: I know here are some longstanding (La)TeX vets who use emacs since decades. What setup are you using when working with LaTeX3 code? Is there a solution I've missed (which is a true possibility), do you edited/created needed lisp code yourself or do you just don't quarrel that much with code highlighting etc.


Edit: @AndrewStacey offers a good working solution in an answer linked to from the post I mentioned earlier. It produces good syntax highlighting in many cases. There are some things I might change, as that commands beginning with \str_ or\int_ are highlighted like token lists or sequences, but that can be accomplished by editing his lisp code (e.g. inserting str\\ and int\\ to the initial specials regex). Its at least a solution I could use and maybe adapt to my needs over time. But since it depends on emacs standard latex-mode (without caps), it doesn't offer the additional syntax highlighting features of AUCTeX. I'm sure that can be accomplished, but my emacs/lisp knowledge is too small at the moment to do so.

Beside that, it doesn't solve the auto complete question which would be even more helpful for programming purposes. Espacially concerning NewDocumentCommand and its siblings. Thus, I'm interested in more experience reports/own solutions etc.

15
  • I haven't seen a syntax highlighting for l3 code. Maybe ask here: lists.gnu.org/mailman/listinfo/auctex
    – Keks Dose
    Oct 8, 2023 at 19:16
  • @KeksDose. Sourcing the expl3.el file in AUCTeX's style/ directory indeed offers kind of "highlighting" (it adds _ and : as recognisable macro characters). But the highlighting is very unremarkable. Plus, the missing auto-completion is much more annoying while programming. Writing to the mailing list may be an option for later. But here, in the first way, I'm interested in the workflow/use-cases of experienced Latex developers/authors who are using Emacs and might be also aware of this shortcoming, as well as their practical solutions/ways dealing with it.
    – lukeflo
    Oct 8, 2023 at 19:29
  • 1
    Emacs is mentionned at tex.stackexchange.com/q/129439/86 Oct 9, 2023 at 5:50
  • @AndrewStacey thanks. Thats one of the post (if not the only improtant one) on TeX.SE which offers some useful informations. Its linked from the post I mentioned in my question. Of course, I tested your own latex3-mode and it works quite well with syntax highlighting, not to say, it might be the best working l3 highlighting I've found so far. I've edited my question to make that a little bit clearer.
    – lukeflo
    Oct 9, 2023 at 7:51
  • I once made the suggestion to move the xparse style file to latex.el, the answer was "that's the plan", but it's not ready yet (lists.gnu.org/archive/html/auctex-devel/2021-08/msg00021.html). Personally, in the meantime, I just run (TeX-run-style-hooks "xparse") at LaTeX-mode-hook. I do get proper syntax highlighting for expl3 commands with a current AUCTeX (not dim gray as you report), in both .tex and .dtx files. Regarding completion of commands, I'd say this is probably indeed lacking. I'm not even sure \NewDocumentCommand and friends automatically add the symbol ...
    – gusbrs
    Oct 9, 2023 at 11:06

2 Answers 2

5

I have looked (admittedly, not very hard), and like you, didn't find much. As a result, I currently use a self-written (in elisp) LaTeX3-mode, which is an extension of the basic latex-mode (not AucTeX) when dealing with LaTeX3 style and class files. Most of my code is syntax highlighting, with almost everything else (key-combos, autocomplete, indenting, etc) inherited from the LaTeX-mode which comes with emacs (tex-mode.el). I'm not sure how well it will work with .dtx files (if at all), or if I'll need to write a module for those as well.

I do intend on publishing it "Real Soon Now" (so, eventually - probably late next year). If there is a high enough level of interest, my effort and attention may be increased, and it will be "early next year" rather than "probably next year, maybe about September or so at the earliest". (Comments indicating interest gratefully received, as are suggestions of how and where to publish and announce the publication for best effect.)

I am also interested in other people's solutions, mostly so I know if I should keep working on mine, or use theirs and abandon my attempts.


Edit to add:

The mode I am working on is similar to (but not based on) @AndrewStacy's mode, which is linked to here. At least, not directly based on. I am fairly sure that I saw Andrew's mode before I coded mine, but didn't directly copy anything.


Further edit, in case the comments are culled at any point: This has now been published at github.

20
  • That sounds very interesting and I would like to try it out as soon as you've published it. But if I got it right, you're not using/deriving commands etc. from AUCTeX. I would like to keep all advantages of AUCTeX with a really good working latex3 mode like yours or the one Andrew Stacey provided.
    – lukeflo
    Oct 10, 2023 at 19:19
  • From comments (on the question and other answer) and upvotes, it appears that there is a bit of interest here. I will look more seriously at getting my code available to the public for use and comment.
    – enkorvaks
    Oct 11, 2023 at 21:52
  • @enkorvaks If I may suggest, why don't you consider contributing improved support for LaTeX3 to AUCTeX itself? (It may or may not be your cup of tea, and all is welcome either way ;-).
    – gusbrs
    Oct 11, 2023 at 22:01
  • @gusbrs, I was intending on getting AUCTeX soon, to at least look at. I had a quick peek last night, but the dependencies (from the package manager) look like they want to download all of TeX common. I currently use a manually installed TeX-Live, and haven't done package equiv workaround, so it may be a few days before I can check it out. I will see what time the weekend allows me...
    – enkorvaks
    Oct 11, 2023 at 22:14
  • 1
    @lukeflo I derived from the standard latex-mode rather than auctex largely because I haven't used Auctex much (not at all until earlier this week). The way I work (which I realise isn't for everyone) is that I don't tend to use automating features. Mostly, I just use the syntax-highlight, and ignore most of the other things the mode can do (except compile). Since I have looked more at Auctex, I will be updating my code to change the face-names to more closely match the Auctex naming, so it may be more compatible. I may see if deriving from Auctex works, and may make that an option.
    – enkorvaks
    Oct 19, 2023 at 20:27
3

The many comments and hints so far have shown me different approaches to adapt a LaTeX setup which is a good workaround.

I provide it as kind of a partial answer to show some possible solutions and maybe invoke some more comments/advices. I will not accept it as answer to my own question as long as there are some unresolved issues and update it with new insights. Of course, other answers are still very welcome. Since there seems to be no final native solution up to this point, maybe we can collect different approaches/hacks here.

At the moment, I'm using the following (very reduced) setup in my .emacs.d/init.el file:

(custom-set-faces
 '(font-latex-sedate-face ((t (:foreground "dark orange"))))
 '(font-lock-comment-face ((t (:foreground "dim gray")))))

;;LaTeX;;

(setq TeX-parse-self t) ; Enable parse on load.
(setq TeX-auto-save t) ; Enable parse on save.

;; parse xparse by default
(add-hook 'LaTeX-mode-hook 'my/LaTeX-mode-setup)
(add-hook 'docTeX-mode-hook 'my/LaTeX-mode-setup)
(defun my/LaTeX-mode-setup ()
  (TeX-run-style-hooks "xparse")
  (visual-line-mode)
  (electric-pair-local-mode))

The most important part regarding latex3 syntax is the automatic parsing of xparse.el with (TeX-run-style-hooks "xparse"). It solves two issues partially:

  1. Xparse macros like \NewDocumentCommand etc. are now accessable through TeX-insert-macro mechanism, including suggested insertion of argument specifiers etc, and highlighted properly.
  2. At least, xparse.el parses expl3.el itself which results in latex3 commands being recognized as cohesive command-name. The highlighting of these commands can be altered setting (font-latex-sedate-face ((t (:foreground "dark orange"))) (here in orange).

Both aspects together are really supporting programming in latex3. Unfortunately, latex3 commands like e.g. \seq_new:N are still totally missing from auto-completion/macro insertion!

As the answers resp. comments of @gusbrs and @enkorvaks imply, such an adaption might be not so easy to implement properly. My own lisp knowledge is too small to evaluate this issue.

Regarding better syntax highlighting the solution by @AndrewStacey is also very interesting. His syntax highlighting of latex3 is definitly superior to the simple solution provided by expl3.el. It would be great to adapt this code to the LaTeX-mode-hook of AUCTeX. Maybe I (or someone else) will be able to realise that in the future. Moreover, I'm anxious to have a look at enkorvaks own solution.

Up to this point, there can some things be done/adapted but others are still up to be solved.

At least in my case, the mentioned adaptions are satisfying enough to finally switch from VSCode/vscodium to emacs. I'm still very new to the latter but the speed to manage programming tasks (esp. in LaTeX) with all those key-shortcuts totally convinced me. Thus, the flaws in latex3 recognition do not weigh that heavily.


Edit

Thanks again to @gusbrs for providing his workaround for latex3 syntax highlighting using AUCTeX. I took it and added some new font-lock faces which are reserved for highlighting latex3 commands to avoid confusion with latex2e commands. So far, it works great and I hope others can use it as well. If someone detects a inconsistency or similar, I'm happy to hear it.

Here the adapted code in my .emacs.d/init.el (just added below the snippet posted above):

;; try own face setup ; https://emacs.stackexchange.com/a/53023/41665
(defface flo-font-lock-latex3-variable-face `((t (:foreground "chocolate")))  "Chocolate highlight")
(defvar flo-font-lock-latex3-variable-face 'flo-font-lock-latex3-variable-face
  "Variable for face flo-font-lock-latex3-variable-face.")
(defface flo-font-lock-latex3-keyword-face `((t (:foreground "orchid"))) "Orchid highlight")
(defvar flo-font-lock-latex3-keyword-face 'flo-font-lock-latex3-keyword-face
  "Variable for face flo-font-lock-latex3-keyword-face.")
(defface flo-font-lock-latex3-type-face `((t (:foreground "dark orchid"))) "Dark Orchid highlight")
(defvar flo-font-lock-latex3-type-face 'flo-font-lock-latex3-type-face
  "Variable for face flo-font-lock-latex3-type-face.")

;; latex3 highlighting, adapted from https://gist.github.com/gusbrs/730758305ae701c915eb928f8c803328
(with-eval-after-load 'font-latex
  (add-hook 'LaTeX-mode-hook 'flo/LaTeX-expl3-font-lock-setup)
  (add-hook 'docTeX-mode-hook 'flo/LaTeX-expl3-font-lock-setup)
  (defun flo/LaTeX-expl3-font-lock-setup ()
    (let ((signatures "NncVvoxefTFpwD")
          (vartypes '("clist" "dim" "fp" "int" "muskip" "seq" "skip"
                      "str" "tl" "bool" "box" "coffin" "flag" "fparray"
                      "intarray" "ior" "iow" "prop" "regex")))
      (font-lock-add-keywords
       nil
       `((,(concat "\\(\\\\\\(?:@@_\\|\\(?:__\\)?[a-zA-Z]+_\\)[a-zA-Z_]+\\)"
                   "\\(:[" signatures "]*\\)")
          .
          ((1 'flo-font-lock-latex3-keyword-face)
           (2 'flo-font-lock-latex3-type-face)))
         (,(concat "\\(\\\\[lgc]_[a-zA-Z@_]+"
                   "_\\(?:" (mapconcat #'identity vartypes "\\|") "\\)\\_>"
                   "\\)")
          1 'flo-font-lock-latex3-variable-face))))))
18
  • Nice, thanks! +1
    – gusbrs
    Oct 10, 2023 at 22:25
  • Note though that you can add any given macro you wish to completion using style files, this is just not done for you automatically. Do you know how to do that?
    – gusbrs
    Oct 10, 2023 at 22:26
  • Also, it should not be too complicated to adapt Andrew Stacey's answer without the need of a specialized latex3-mode. As far as I can tell, all you need is to feed the same keywords to (font-lock-add-keywords 'latex-mode ....).
    – gusbrs
    Oct 10, 2023 at 22:50
  • 1
    I did something a little different than Andrew Stacey, see gist.github.com/gusbrs/730758305ae701c915eb928f8c803328. I'm not sure I like it yet, but it looks good at first sight, and I'll experiment with this for some time. Feel free to include it in the answer if you happen to like it.
    – gusbrs
    Oct 11, 2023 at 14:44
  • 1
    Good to hear. :-) And, I don't see the need to distinguish much from latex2e macros, specially since the names are quite conspicuous. But, of course, choose whatever faces you like.
    – gusbrs
    Oct 11, 2023 at 19:32

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .