I have been using Emacs at work for whole week

So you’ve betrayed us?

WAIT

I’m not a traitor yet

I just wanted to see what we can learn and borrow from Emacs. It’s extremely mature text editor, and LISP environment, featuring many packages with interesting ideas.

I’m not pretending to know everything in Emacs, but I’m using it on daily basis for half of a year pretty much every day to do notes, various exercises, and configure it just for fun, because it features one of the most interesting configuration approaches, which I’ll discuss little bit later in this post.

Since Emacs is complex in some points, I’m going to try to briefly explain some Emacs local names of things in case someone here didn’t used it and doesn’t understand the terms, which actually very different from other editors from time to time. If you’re Emacs veteran fell free to correct me in direct messages, so you don’t elisp-shame me in public here, I’ll update the post text accordingly, or start a long long rant with you in the comments because why not? Anyway, this going to be quite big a post, so welcome if you’re interested in what 43 year old LISP machine could teach 8 year old code editor.

Visuals

Let’s start from the visuals. Both Emacs and Kakoune features color schemes, and syntax highlighting. Here’s how Emacs looks on my PC while I write this post:

I’ve put a lot of time to make it look like this, because by default it looks like 43 year old editor. Oh wait… Anyway, I’m liking how it looks , and this was only possible because of the great community of Emacs. I wish such community will built over time for Kakoune as well. I’ts amazing.

But back to the post.

Syntax highlighting.

I love when syntax highlighting has many consistent colors, so I could distinguish code structure just by glancing at the colors of the code block. Emacs has somewhat minimalist approach when it comes to highlighting, and I believe it is closely related to the underlying system that is being used for highlighting.

Emacs has regex based syntax highlighting, that can be extended or manipulated via regex syntax table. Various major modes provide syntax highlighting on it’s own, so there’s no general place where we could adjust syntax highlighting. If you don’t know what major mode is, here’s a quick explanation below.

About major modes...

A major mode in Emacs is a set of behaviors for specific task, of which you can think as of a filetype plugin in Vim, or filetype script, like those located in rc/filetype/. Usually it provides indentation rules, syntax highlighting, completion, checker, all that kind of stuff that meaningful to the language we’re working with. But it doesn’t have to be a language mode. It can be a whole new environment for Emacs, like git wrapper or PDF reader, so it is more complex then just a filetype plugin. We’re going to talk about it in terms of supporting languages, so doesn’t think much about it - just know that major mode provides set of behaviors for Emacs for certain task, like editing the code of specific type.

So major mode provides highlighting, but I’ve said that Emacs uses minimalist approach, due the underlying implementation of a font locking. Font locking is simply a mechanism to change font attributes, like color, height, font, weight, e.t.c. The name is kinda weird but I believe it’s going back to lisp machines having various lock keys, here’s nice post about that. And font locking in Emacs is kinda slow and somewhat memory expensive (not quite). Kakoune shared similar memory problems, but it’s highlighting system is faster, compared to Emacs one. So usually Emacs highlights text only when the highlighting will make something important stand out, like function definition of variable declaration, but not function call, or variable usage:


Emacs

Here the essential elements are highlighted, and everything that has less interest (as Emacs thinks) is not. Of course we can change this a bit by modifying font lock keywords to make it look more like modern editors highlight code, but that’s another story. Here’s how Kakoune handles highlighting for this code:


Kakoune (Note: I’ve changed some comments, treat them as part of the text of the post.)

Luckily for us, Kakoune, as well as Emacs features regex highlighting that we can easily modify to make it more distinguishable. Here’s how it looks in my setup:


Emacs


Kakoune

But I believe that this doesn’t count, because users who just installed Kakoune to write some Rust code won’t get that rich highlighting without investing their time into defining regexps for everything there, and even if such highlighting will get merged, still there’s lot of work to do for other languages, to provide semantic highlighting.

Currently Kakoune features highlighting scripts for many languages, with 70 scripts in total. I’m going to admit that it is good amount of languages already, but the highlighting may be broken sometimes. So this area really needs improvements. I have plans to rework some bits of highlighting for c-family.kak and rust.kak since these are my two primary languages that I use every day, and I want them to be highlighted meaningfully. Perhaps I’ll go with the Emacs way of highlighting, to mark important places in the code, leaving less important parts up to users.

Highlighting Overriding

There’s one more thing I want to cover in syntax highlighting that is done little bit better in Emacs -highlighting overriding.

You see that I’ve added highlighting of function calls and methods to Emacs and Kakoune, but in Emacs it was easier, because we can choose where this highlighting will be put in the table. The syntax for highlighting is:

(font-lock-add-keywords MODE KEYWORDS &optional HOW)

Where MODE is a mode to which we want restrict the highlighting, KEYWORDS are regular expressions paired with face and optional HOW argument that can help us choose if we want to override existing highlighting, or highlight only unhighlighted text.

In Kakoune, we only have option to add one highlighter before another, so the latter will just override the former. So for example if I want to highlight function call in Kakoune but don’t really highlight control flow operator as functions I have two options:

add-highlighter shared/rust/code/functions regex ([a-z_]\w*)\b\h*(?=\() 1:function
add-highlighter shared/rust/code/keywords  regex \b(?:for|in|while|break)\b 0:keyword

This everything that was highlighted as functions but matches highlighting of a keyword would be re-highlighted. Or I could:

add-highlighter shared/rust/code/functions regex ([a-z_]*?\w*?)\b(for|in|while|break)?\h*(?=\() 1:function

This carefully avoids everything that in the second group, and such highlighting is independent from it’s position in the list of highlighters, but it involves extra calculations, and rich highlighting can get slow because of it.

I would like to propose an -override switch for add-highlighter function, so it will ignore if highlighting was already applied to this match. This way users will be able to extend highlighting easier without worrying to override builtin keywords, and override things if they need.

Smarter Highlighting

Another note on syntax highlighting in Emacs, is that it is more smart. It detects types in C where syntax really expects type to be:

image
Emacs

Look at the casts and user defined types. It is just regular expression highlighting, it doesn’t actually knows that this type is defined somewhere, it just understands the syntax. Now look at Kakoune:

image
Kakoune

As I’ve already mentioned, this issue is on my list of TODOs for Kakoune, so I’m going to work on this to bring such semantic highlighting to the languages that I use. I don’t write in other languages that often but I know that there’s also minor problems with Perl highlighting:

image
Kakoune (Doesn’t know arrays in Perl?)

image
Emacs

Syntax… Indentation

Another topic that I would like to discuss is indentation rules. Emacs has some mechanisms to make indentation rules for different languages, and it is actually awesome. Emacs sets correct indentation for current line based on syntax around this line, typically by searching upwards from the cursor in order to find which syntax constructions are there and which indentation rules they provide. This is really nice, compared to really basic indentation handling in Kakoune. Vim is no exception here, but it had something similar to Emacs called smartindent and cindent. It does some sort of parsing of a code to provide automatic indentation. Kakoune typically checks some conditions which can be failed if syntax isn’t that what is expected by these conditions but still valid in the language, like comments after curly braces in C:

image
Kakoune

Emacs handles this better, providing correct indentation, based on syntax around the cursor on each line while typing.

image
Emacs

The issue with syntax highlighting and indentation can be solved by external tools like tree sitter, but this means a dependency on external tool, or including parses generated by tree sitter into the core of Kakoune, like it was done with Atom, which can also provide nice syntax aware features, like folding, selections (Kakoune actually can have huge benefit from that), and even error highlighting, since tree sitter can indicate syntax errors.

But I think that it should be implemented in that way so users could extend syntax indentation rules based easier, that writing a grammar for tree sitter. Not sure how to implement it, I’ve tried to write a generic parser for C-like languages in Perl to provide semantic indentation but it’s kinda hard task with many quirks here and there.

Since Kakoune focuses on code editing task I believe that this particular problem should be one of the top priorities, because incorrect indentation always gets in your way when you write or edit code.

Documentation

There was a poll somewhere about favorite editor documentation, with three votes and all for Vim documentation system, including my own. But it doesn’t mean that we shouldn’t discuss Emacs way of documenting things. And it’s pretty good too.

Because Emacs is written and configured in Emacs LISP (which is nice) a full featured programming language, which allows to add documentations to the code, we also are able to browse these documentations. In Emacs, you can call describe-SOMETHING and pass the name of SOMETHING to it. If that something has documentation (it has 99% of the time) you’ll be prompted with it. The buffer will show up, containing documentation text, as well as information about that something, e.g. is it a function or variable, and location of where it was declared:


Emacs help buffer on the right, function definition on the left.

You can see that there are highlighted references available in the help buffer. Since this function calls two other functions I would like to read documentation of those too. I can do that because I’ve specified these references in the docstring by using this syntax: `function_name’, and Emacs automatically references it in help buffer by adding clickable link.

Kakoune follows similar approach, but in a different way. We all know -docstring switch for declare-option and define-function which can be browsed while we’re in the prompt writing command. But there’s no way to look to the definition of that variable or function, unless we go and dig in rc directory where this thing is.

Another problem is that we can’t include documentation with the scripts that will be accessible with the :doc command. Usually there’s no documentation in Emacs packages, but being able to quickly locate their source and read documentation there isn’t big problem.

Modes, Packages, Plugins, Extensions

This is where Emacs really shines. Possibilities are endless. You can play tetris, you can order salads, you can even play nes games in pure Elisp:

image
Emacs features Super Mario Bros. in emacs-nes.el

Heeey, that’s not fair! Kakoune is a code editor!
Yeah, but have you heard about Sokoban?

image
Kakoune features sokoban.kak

Just kidding, I’m not going to game-shame Kakoune, since who needs games in text editor? If you need, I recommend you to open Emacs and visit a doctor via M-x doctor RET. Damn it! Emacs actually has a builtin psychotherapist! (Try it, it’s awesome)

But games are not the main point here. The point is that in Emacs it is possible to do any kind of thing, because Emacs isn’t a text editor really. You can think of it as an editor with side features, but in fact it is a LISP machine with editor as a side feature.

So when we load our configuration file, we actually load a proper program, like those C files that you may write at work, or those JavaScript programs that are being executed in the browser. And because buffers in Emacs are just an Area where we can display and manipulate text as data, we can do such amazing things as Magit or Treemacs.

Well, Kakoune also capable of manipulating text in a buffer, hence that’s what editor is all about usually, so we could implement many things like in Emacs too. Also, since we’re able to use any language from shell expansion, plugins for Kakoune can be as complex as in Emacs, as long as Kakoune provides some features. As some quick examples of simple text manipulations to provide UI like plugins are file browsing plugins, or tag browsing:

image
Kakoune plugin edit-or-dir

Well, that’s not really a side panel file explorer, but I mean that nothing prevent us from implementing one. We don’t even need folding for that really. Folds will make things easier, for sure, but instead we can request list of files in the directory and rebuild whole buffer.
Here’s how filetree plugin looks in Emacs:

image
Emacs package Treemacs

Sure, it looks just like in GUI application, and Emacs in GUI mode is capable of displaying graphics, but these are custom font icons, so this buffer technically contains text only.

And there’s far more useful packages that can help you with any kind of task in Emacs. Sure, that’s because Emacs is a full featured LISP environment and highly extensible on its own. But I think that Kakoune is mostly as extensible, as it exposes it’s state via shell, and we can control it from external tools pretty much just as we would do it by hands, so for such plugins to show up we only need to wait or implement them ourselves.

I’ve mentioned that when we configure Emacs we’re loading a program into LISP machine. That’s quite interesting topic, so let’s discuss it too:

Configuring Emacs

Emacs understands any .el file when it knows where to get it. We need to manage paths to our scripts in order to (require 'feature) in Emacs, in the very same way as source command works in Kakoune. We can write tools to automatically load our scripts like use-package for Emacs, and plug.kak for Kakoune, but essentially it all comes down to sourcing script from particular place at particular time. This can be done on loading, or when certain event happens, it doesn’t really matter here, since in these places Emacs and Kakoune share the pretty much the same mechanics. But what Emacs can offer is non Emacs LISP configuration files.

You see, Emacs is extremely powerful tool and it has its exclusive features like Org Mode. Org mode is a markup language for Emacs, that is far more than just a markup language. It features spreadsheets with calculations, rendering to various formats, linking, and most importantly for us now, it can execute code blocks. What does this mean? Well, it means that we can write our configuration in Org Mode, and have nice formatting, and commentary on every piece of our configuration file. And then load this configuration file as if it was generic .el file into our Emacs with org mode command org-babel-load-file. This command strips away all the text from the org file, and puts all source blocks into separate .el file, or to different files if you want it to.

I’m using this approach myself, and find it really useful and unique way to configure my editor:


Fragment of my configuration file for Emacs.

This file is actual configuration file for Emacs. When I change configuration of the editor I edit this file, and not the Emacs Lisp files. And you can render it to PDF and print it if you want! Question - how cool is that? Answer - very.

A bit about Org mode

Org mode is capable to do a lot of things. You can write books in Org mode, calculate in tables, do you presentations, generate websites, run your agenda, and more. Here’s for example some math lab from the university I helped my friend to plot in Emacs:


Org mode buffer with some LaTeX formulas and gnu plot code

Now we can press C-u C-u C-c x l to render LaTeX, and C-c C-c to execute code block where our cursor is:


Same Org mode buffer, but with Inline LaTeX previewed, and gnu plot code executed within Emacs providing a picture as a result.

And here’s PDF that you can get from this buffer with C-c C-e o l:


Emacs viewing PDF generated from the Org file.

If you’re got interested in Org mode, I can recommend you this talk that briefly explains basics of using Org mode.

So how can this apply to Kakoune. Well, certainly we can’t just start using Org mode for configuring Kakoune (which is a bit of a shame), but I think that it won’t be too hard to implement such a thing. Basically we just need to strip away every text that is not in source code blocks, and then parse source code blocks parameters to generate .kak files, or even just source them without it. The benefits of such method is that one can have beautiful document with everything commented and set up in single place. I’m currently trying to have up to date README.md for Kakoune, but I change configuration quite often so it’s hard to update it every time. The downside is that it isn’t really the script, so it’s harder to debug. I see this as an interesting idea though.

Minor Modes

Lastly I want to talk about plugins once more. We already know about Major modes, but what about minor modes? What’s the difference?

You see, in Emacs, there can be only one Major mode that is active at a time. But you can have any amount of Minor modes simultaneously active when you’re using Major mode. Minor modes usually provide extra features. For example multiple-cursors in Emacs is a minor mode. Or for example, when you’re working with C you may want to use aggressive indent. So this is essentially just a plugins that provide additional functions to the editor.

What makes Emacs stand out is not that you can load minor modules, but the fact that you can unload them.

For example, I’m using Racer when I’m writing quick examples of Rust code in Emacs. But sometimes I actually want to switch to language server for Rust. So I can unload racer-mode and load eglot minor mode, effectively replacing one functionality with another.

Kakoune, and Vim shares the problem of being unable to unload functionality. Recently, Kakoune added support of loading code with require-module, that was written in provide-module block. But we can’t really unload a module. So if I require some plugin in, it will stay there as long as Kakoune is active. That can cause problems when you have some things that you want to use from time to time but that conflict, and if you load one, you’ll get the error if you’re load another. Sure there’s no such situations currently, but I’m not sure what will happen if, I load racer.kak and kak-lsp together and try to edit Rust code. Who will win? One who was loaded latest?

Vim actually has a plugin, that allows to unload other plugins: vim-scriptease. That’s another level of sorcery, but I think that it shows the state of the art with Vim plugins and how Emacs minor modes are little bit better in this particular aspect.

Kakoune also can benefit form unloading modes to provide long working sessions that do not grow in size when working for several days with different files, which can also help to narrow down amount of conflicts in various plugins that may appear. And at some point I’m sure they’ll appear.

Context

In Emacs context is a huge part of the editor. Indentation is context based, interactive features are context based too. Kakoune lacks this a bit and here’s how it can make things interesting.

Take for example Org Mode. In org mode when your cursor is on the heading, you can arrange headings of the same depths, but you can’t go past the bottom. You use alt and arrow keys for that. Tab key opens and closes nodes. When you’re in table, alt and arrow keys now arrange columns and rows. Tab key now is used to jump between cells. If you press C-c C-c on the heading options Org mode will reload them. If you press the same shortcut while your cursor is inside source block, it will execute it. So the thing is that Emacs is always aware of the context of where your cursor is. It’s not default functionality, and Org mode is implementing all of this by itself, but it is common practice in Emacs to be context aware.

We can achieve something similar in Kakoune. I’ve already mentioned some plugins that transform buffers into interactive buffers instead of plain text buffers, like grep.kak or edit-or-dir.kak, but in order to do that we need to redefine keys in these buffers. And there may be some problems with these approach. Not sure what could be done here, but currently most obvious way is to remap keys only in normal mode, but usually user can enter insert mode and break such buffer.

Narrowing

Another great feature from Emacs which also relates to context, is narrowing. One can narrow the scope of the buffer to current function/tree-node/s expressions/e.t.c. if mode provides such contexts.

So for example my config file is 1700 lines long. I want to edit part of it and don’t mess with other parts, and since I’m using Org mode I have different setting placed in separate subtrees:

image
Emacs showing full file contents with a lot of subtrees

Let’s imagine I want to work with Geiser configuration only, do some global replaces, and run spell checking on that part of the file. I can narrow to this subtree with C-x n s (Ctrl x narrow subtree):

image
Emacs showing narrowed part of the file, which now only 14 lines long.

Now I can do any kind of global actions, and it won’t affect the rest of my file. Kakoune solves this problem by allowing to select some area and then select things inside it, or run commands for current selection, but what if you need to do a lot of things with this area? You’ll have to select it every time after every action. Instead you could narrow the buffer to current selection, and widen it back when you’re done.

Another example is editing code. As you can see on the screenshot above, there’s a #+BEGIN+SRC emacs-lisp block, that ends with #+END_SRC. It is a source block that has highlighting inside it. What if I told you, that you can edit this part of the buffer, as a file of the type of this language? Meaning that all fancy features like auto completion, paren matching, and other stuff that specific to LISP will work for that code, while you’re working with Org mode? Remember when you’re writing markdown, you always need to switch to different buffer with appropriate filetype loaded in order to have correct indentation and completions? Well, in Org mode you can narrow to this part in a separate window like so:


You can see in the modeline that left window is Org and right is Emacs-Lisp

Now you can edit code in the right window and when you finish it will appear in the left window. But what if I edit it in the left window while I’m editing it in the right? Well, you can’t. Emacs understands that in this context you’re effectively editing this part of a file in another place so this part must not change. You can change text around this source code block, but not inside. Once you press C-c ' in the right window it will apply those changes in the left:

image
Changes appeared in the Org buffer

Automatic Completion

But the most great thing about context is completions. Yes, completions in Emacs are context aware too. When you type something in a buffer that can provide contextual information to completion fronted your completions will display functions where you need to insert functions, variables where you need variable, and so on:

image
Help message at the bottom line of the screen.

See the advice-add: (SYMBOL WHERE FUNCTION &optional PROPS) at the bottom? It’s context help for you that actually understood by completion system, so when I start typing, I’ll get contextual completions:


Completion window with functions for FUNCTION parameter of advice-add

Kakoune also features semantic completions in various places, like when we write things in prompt mode, usually it suggests switches for commands just right. Now imagine if the same worked when you write kakscript? I’m going to prompt mode quite often just to check correct switches when writing plugins, so I’d like this feature very much in Kakoune. It really helps you not to make mistakes.

Kakoune also has contextual completions with LSP, but that’s different story, and Emacs also can do that.

Summary

While Kakoune is a great editing tool, I think it can be improved, and here are my thoughts. If you disagree with me, feel free to throw you thoughts in, since that’s why we’re here. In case you’ve missed something in this post, here’s brief summary of things that I’ve touched:

  • Visuals
    • Syntax highlighting
      • Highlighting Overriding
      • Smarter Highlighting
    • Syntax indentation
  • Documentation
  • Packages, Plugins, Modes, Configurations
    • Configuration
    • Minor modes
  • Context
    • Narrowing
    • Automatic Completion

Sure that doesn’t cover whole Emacs world, but I hope that I’ve brought to the light some design points that can be rethought, borrowed, or improved by looking at a extremely well made editor that stood the test of time for 43 years and still continues to improve.

15 Likes

First of all, of course, banned for betrayal.

Secondly, this is awesome, what a massive post! Thanks. (more comments coming soon).

5 Likes
tfw no comments are coming

2 Likes

I would love to see some equivalent to context in Kakoune, it would require a good number of internal changes though. It would be really nice if when editing kak scripts if %sh{ } blocks could have indention and auto-complete.

1 Like

I think Kakoune equivalent of minor modes is foo-enable foo-disable pattern. When plugins correctly implement this, it should provide similar functionality. There is no point in unloading modules unless we hit memory issues.

1 Like

maybe you’re right. But my point was that in Emacs it’s a general mechanism. When I’ve implemented my own minor mode (just for fun) that centers text, I didn’t done anything to make unloading possible. So even if in Kakoune we can make foo-disable this will not be as common as in Emacs, and will depend only on plugin author, that decided to do or not to do such mechanism in the plugin.

Syntax Highlighting isn’t something I find particularly useful personally, I prefer adhoc highlighting. But I will say trying to “parse” syntax with a regexp is a losing proposition. It will always break, at some point I would like to dig into the math of it – but I think the only way to highlight properly is with a real parser. I think at best regexp highlighting is a good “fallback”. I would to see lsp-style parsers emitting syntax highlighting to become the norm.

Syntax Indentation, same problems as above, and something I am simply becoming less worried about as autoformatters rule the day – computers are good at formatting humans aren’t.

Documentation… your point about docstring, declare-option and define-function is really an important one… I wonder if we could make them the primary source of documentation for user commands. Maybe if there was the idea of a so a brief blurb could be displayed with a way to dig into and see more (also would be useful for documentation overlays for code bits). I think this is actually a really great idea, how much of the whole documentation for kakoune could be re-imagined as docstrings? It seems it is already the primary source for many users.

Modes, Packages, Plugins, Extensions, here is where I get concerned. The more complex and integrated the plugins are – the more breakable everything becomes. This is an increasing issue in the Vim world and is already a critical issue in Emacs. Feeling like your editor is unreliable or fickle is scary. I want the opposite of deeper integration, I want more stuff like @alexherbo2’s :connect and light and reasonable integration. Reliable being the core word.

Configuring Emacs, org mode and friends. I definitely do not ever want to pay the org mode tax in my day to day life, I am not personally a fan of org mode. It is indeed a technical marvel (as is Magit) but it isn’t my cup and tea so any motivation derived from it falls on deaf ears with me. Basically, I want brutal simplicity, that is what brought me to Kakoune.

On unloading… you hit on this repeatedly, and I think it really is a fair point and something to nip in the bud before it becomes a more pervasive problem as it did with Vim.

On context… I don’t know about Emacs, but the implementation of contexts in Vim is… inelegant. I can see the value of it, but the complexity cost feels very high to me, I will have to investigate the Emacs way of doing it.

On narrowing, I know myself and @eraserhd want it enough we both have made sort of homebrew implementations of it, but never something that was released (unless I missed it!). Narrowing and better code-oriented navigation is absolutely something I think would be terrific.

On autocomplete… I don’t mind the fact that LSP has to be used to get good semantic autocomplete, I don’t want something that complex to be baked in I don’t think. That said, I understand the reasoning, as my LSP configuration recently has broken a bit and I haven’t put together enough info on it to report it to @ulis – just turned it off!

3 Likes

@robertmeta I think what you mean is composability over extensibility.

1 Like

Indeed, that is a concise way to say it.


I loathe fragility in my editor.

Great additions. I’ll put here some thought on your thoughts that I don’t particularly agree with.

Well, sure, a parser will do the job better, but my old point still valid. There’s no parsers for many languages and may never be. Writing parser is a hard task. Tree sitter is capable to create parsers based on grammar, but afaik it isn’t general enough, and for some languages with obscure syntax it needs to be modified in order to provide a parser.

Regular expression highlighting can be really hard to do, and it can be wrong in some sithuations, but it doesn’t mean we do not have to improve it and work on it. It is the most general way to create a highlighting as of today. Grammars are good, but are the same convoluted as the regexps and can be incorrect too.

Again, a real parser is better, but we may do not have one. And providing some simple mechanics to create indentation rules may significantly improve initial support of the languages. Current situation is really bad and must be improved.

I don’t know what is a critical issue with Emacs, but in my experience there was literally no problems with many packages. About 4 month ago my private configuration of Emacs (that doesn’t go to the github) had around 180 packages and everything was working at its finest.

Vim on the other hand had troubles with 20 packages. Vim is actually the most unpleasant editor to make packages.

That’s what I never felt with Emacs or Kakoune.

I didn’t knew there was a context feature in Vim.

I use spacemacs along with kakoune. If we compare number of open issues, it is:


Though those are completely different editors, but it is very good sign, at least for me, that kakoune’s contributors handle issues with steady pace. When I first started using spacemacs about two years ago, it was roughly the same amount of open issues as it is now.

Yeah, and this is given that fact that spacemacs is 1 year younger than Kakoune (It was started in 2012), mind you! But I’m afraid that spacemacs simply far more popular than kakoune, that’s why there are so many issues. Sure, Kakoune is simpler in design, so may be there will not be such issues like in spacemacs, but still I think if Kakoune will get this kind of popularity, @mawww wouldn’t be able to maintain fill list of issues all by himself.

Regarding minor modes, I still plan to implement them as shared scopes. Currently we have global/buffer/window scopes, I would like to add support for declaring scopes, in which we can put everything a scope can contain (aliases, option values, highlighters…), so that we can just group-up language support/plugins inside a scope, and enable/disable it by “linking” it into one of global/buffer/window scope.

That would generalize the current “shared” highlighter support, and make enabling disabling those modes/scopes uniform (:link-scope window cpp, :unlink-scope window lsp…).

This would also remove the need for cleanup commands (like the ones removing the hook groups from the window), as that would be taken care of automatically by unlinking the scope.

12 Likes

@andreyorst Thanks for this post.

Well, I came across this post because I am like you, I am trying to move from emacs to kakoune. However, the syntax highlight is making things difficult for me. Actually, I am C/C++ developer, and I am trying to get the same highlight in kakoune as I have it in emacs.
I have noticed that you have started several pull request in github for this issue, I do not know if they all merged to kakoune yet or not but nice work.
Also I have noticed your langauges.kak file to improve the highlighting, it is a great work but still not like emacs. Have you managed to get the same highlight in kakoune for C++ as it is in emacs??

Except I’ve used Kakoune before Emacs :smiley:

No. I’ve gave up on writing regular expressions for various type castings in C++, and I’m actually C programmer, and write C++ occasionally. I have high hopes for tree-sitter, and I wish someone wrote a plugin for Kakoune that uses tree-sitter for highlighting.

I’ve gave up on writing regular expressions for various type castings

That’s actually why I’ve stopped contributing to language highlighters, since I’m incapable of writing such complex highlighter. There’s always some quirks in C++ syntax that drive me crazy. In comparison, highlighting Rust with regular expressions is easy, because syntax forms more or less are have single meaning.

I guess one might port Emacs regular expressions used to highlight C++ to Kakoune regular expressions, but that might violate some license bits though i’m not sure.

IMHO – a plugin that did that would be up there with kak-lsp in terms of very high value.

1 Like

I actually wish Kakoune could use grammars instead of regular expressions.

1 Like

Kakoune is not limited to regular expressions, regions highlighters do provide already some ways to define complex grammars (although not as expressive as EBNFs). There is a fine balance between correctness, ease of use (especially in ad-hoc cases), tolerance to invalid states, and performance. grammars are the best for correctness, but are not great for all the others.

can we update multiple region highlighters on every keypress without noticeable lag?

It should be mostly fine except in pathological cases, region highlighters apply their regexes by-line so that they can just re-parse the modified lines when needed. This means in the most common case (1 line modified every keypress), region highlighters are very quick (I think they run in log-n time with n the number of matches for the delimieters).

They do use a lot of memory though, as they store all the candidate delimiter positions.