Syntax highlighting is a waste of an information channel (2020)
buttondown.email
buttondown.email
A lot of the suggestions here are things VS Code has been incrementally adding as visual guides over time though. For example the way VS Code highlights other instances of the same symbol (variable/function name) under the cursor goes a long way to address the specific Import, Argument, Type, and Exception cases listed in the article.
Combined with heat maps for test coverage and git commit recency in the gutter, I am skeptical that switching out syntax highlighting on demand (I.e keyboard shortcuts I’m assuming) would be ergonomic and viable.
That said, I love that there’s thinking in this space on how to improve the visual comprehension of code. There still are plenty of crutches I use, such as expanding the selection along the syntax tree (⌃⇧⌘→ on Mac) just to trace all the parenthesis and braces in JS/TS – I don’t find the rainbow braces very useful at all.
I don't get that conclusion from the article. The summary is that modes are useful for exposing a large number of features using a limited number of input controls, but that care should be taken to make each mode visually distinctive, and to not use them when mode input errors could have disastrous consequences.
I get some of the criticism, but those are minor concerns to decide to avoid them altogether. Modal UIs can make users much more productive, and input more intuitive, after an initial adjustment period.
Consider the Normal/command mode in Vim. With just a few keystrokes you can operate on text in a fraction of time and effort than in Insert/editing mode. Not only that, but commands are combined using intuitive mnemonics (`cw`, `di(`, etc.), which makes them easy to remember and discover.
Whenever I go back to an editor that uses key chords for commands, I gain a larger appreciation for modal UIs.
This is much more user friendly than remembering a list of Ctrl+Alt+<something> key combinations found in non-modal UIs.
Move-by-word is a motion: w
Search is a motion: /foo
Next match is a motion: n
Delete is a command that takes a motion:
* dw
* dn
* d/bar
...nearly ad-infinitum. (eg: numeric repetition is a command that takes a command or a motion: 3dw, 3j)I can't say how they're implemented, but I think of repetitions as a distinct third thing, because this also works: d3w
3dw is 3(dw) is dw dw dw
d3w is d(3w) is d(w w w)
So the number is doing basically the same thing in both cases.
(this is not a criticism of your mental model, jusst me musing)
Something i wanna try at some point, is to make all faces in a file equal to the background, except for comments, so as to read only the comments of a file. Or read only comments and function definitions. Or only function definitions and variables.
You can create different themes, like a comment theme, in which every part of the code is invisible (i.e. hex value black) except for the part you want visible, comments in that case. Then when you want everything visible again, you toggle the loaded theme.
I don't know if i will create such themes myself, my github account is on github/pramatias. I may upload something in the future, or may not.
[1]https://gitlab.com/protesilaos/modus-themes/-/blob/main/modu...
So, yes, definitely sounds worth a try to me. Be fun to figure out how to do it if nothing else :D
You can have the best of both worlds, by switching themes with appropriate coloration whenever you like. In emacs there are a ton of themes, each with it's own emphasis on coloration, but you can also make your own easily, or tune an existing one. I have commented already on how to tune one, using modus themes, on the same thread.
Not convinced by 'should' because it seems like it would make it easier to not notice a comment that needs updating and humans in general (myself definitely included) are bad enough at that already.
(Note that that doesn't mean I'm arguing that it's a -wrong- choice, just yet another trade-off to be considered)
That said, I totally agree with the notion that the color channel can be used in different ways during different tasks. For example, when reviewing a book, highlighting is a useful way to utilize the color channel. But what percent of the time do we spend re-reading text versus reading it the first time?
I actually created a startup around and idea I had that makes better use of color during the first reading. [1]
My approach improves visual tracking and attention by using subtle color gradients that wrap from the end of one line to the beginning of the next.
Not on the website it isn't.
1. I don't understand how these colour gradients are meant to help. Explain it;
2. Formatting on mobile (Firefox android) is not great.
I have, and suspect a lot of people have. Very minor issue, but the fact it happens suggests there is some small cognitive load that could be alleviated in general.
I do suspect that the optimal type of visual affordance may vary from person to person.
Your technique seems able to help people who likely learned to read with a ruler hiding upcoming lines, or with a finger pointing at the word they say aloud, and people who read with subvocalization.
Such readers generally process text at not much higher rates than speech, and often prefer audio books or YouTube which add visuals or emotion since reading holds no particular advantage.
Other readers take in chunks of meaning, mapping from word form sequences to concepts without going through phonics. It's not skimming. (It's possible it's the same pathway but subconscious instead of aware of the tracking and subvocalization.) These readers can still play back the individual words, with the same recall accuracy as the word by word or sound by sound readers. For these folks, audio books and YouTube are an excruciatingly slow way to transfer information.
These faster readers are "close reading", not skimming. They are reading every word, but mapping word shapes into phrases at a time (perhaps similar to how LLMs can correctly answer completely typo-garbled questions).
The difference between these methods of reading is at least 4x and often 10x or more speed with the same or better concept learning and recall.
Your method is clearly (pun intended) able to assist those who would 'need' the ruler or fingertip to go sound by sound or word by word, with crossing end of line to start of next. (Likely similar reasons some folks read web pages successively highlighting lines with their mouse; your approach would likely help them too.)
But as you're seeing in these comments, it generally brings sequence absorbers to a crashing slowdown.
I think sometimes i accidentally start to, but my comprehension drops, then I have to stop go back and try again with the slower style.
Is this more of just a practice sort of skill?
> Such readers generally process text at not much higher rates than speech, and often prefer audio books or YouTube which add visuals or emotion since reading holds no particular advantage.
I'm somewhere in between these - I subvocalize, but at about 2-3 times the speed of speech, and I hate audiobooks/etc. My eyes jump several words at once and I read them individually with my peripheral vision - so the while their example isn't really slowing me down much, it is distracting.
It's got me wondering if zebra-striping background shades as in spreadsheets would be a better compromise. To help some readers with their eyeball "carriage return" without disrupting those of us who visually parse larger blocks of text.
I think you completely missed the point of the square/circle example. The red circle is just a circle with syntax highlighting. The task is still to find the circle, but you are supposed to know in advance that the syntax highlight color for "a circle" is red.
The first circle is shown without syntax highlighting, the second circle is shown with syntax highlighting. "Square" and "circle" is the syntax, red is the highlighting. The point of the first example is to show how much easier it is to spot the circle when it takes advantage of syntax highlighting.
It's a very good example of why syntax highlighting helps with these kinds of tasks. The squares could be blue, black, yellow or white and it would still be easier to spot the circle because it's highlighted in red.
It doesn't even matter what color the circle was highlighted with, so long as it's different than the syntax highlighting of the squares.
My mind keeps trying to associate meaning with why some words are highlighted and others are not.
Since there is no particular reason, my mind came up with an alternation in recital: redder words are spoken more loudly, and bluer words are spoken with a higher pitch.
Somehow, it is still easier to listen to an oscillating rollercoaster of an internal monologue than constantly seeking a reason behind the highlights.
Maybe the colours help if a text is really boring.
Highlight variables across function calls and produce hues of that colour as the variable is consumed by computation into other variables.
Colour functions by how big their test coverage is using flamegraph metadata.
My IDE already tells me through colours (lighter hues) and squigglies if a function is transitively unused (when not exported), or a variable is declared but not consumed.
I've already experienced it in practice in NetBeans 6+ where there was so much information (not just colors but various types of underlines etc.) that the code just looked like a rainbow and was hard to focus. I had to disable half of the features to be able to work again.
(Interestingly there were more issues with the newer NetBeans versions that I decided at one point, screw it and downgraded to NetBeans 5.5 and it was the best decision for my productivity in Java, I use it to this day).
Am thinking about 3D software where switching view modes is fundamental to building things in them. Hmm
Cool ideas!
Argument/field/etc highlighting already leaked into popular IDEs and gosh I hate it when it's a non-tunable default. Feels like reading through a christmas tree. And I can never tell which shade of cyan is which anyway, unless it's textually obvious.
To be honest it wasn't that big of a deal. Definitely not a game changer. Although I like that people are at least considering these things. Most people I showed the lexical highlighter to couldn't imagine not having syntax highlighting (which is silly, you get used to it quickly).
(I usually use this observation from the other side, as a reductio ad absurdum about coding guidelines that could as well be implemented as editor settings.)
The funny thing is we were supposed to be making Ada compliant websites. But I guess it didn't prevent using the website, just an aesthetic choice. Or "can't see one specific shade of green" isn't a disability.
For what it's worth I also have never been entirely convinced "navy blue" is different from "black" and that the existence of navy blue as a distinct color isn't some elaborate joke being played on me. Someone gave me a pack of dress socks of all different shades of grey, black, and navy blue as a Christmas gift, and they meant well but do not know the apprehension they caused.
And that light green just looks tan to me (kind of like the background here on HN), or like a normal monitor with the blue light blocking turned on.
1. shell-like commands - ls *.py
2. python-like expressions - 42 + a[i] + f(x, y)
So it would be nice to highlight them differently to help people learn the language. It's not always obvious where commands are valid and where expressions are.
(I use VSCode in case anyone knows a way to do it in any language)
Colour as syntax.
Nesting parens and/or braces - Breaking things into functions and clear indentation within those functions is already a much clearer information channel. Color is nice and all, but it's no substitute for communicating abstractions and invariants. If nothing else, code should still be clear even to people using different tools or with color blindness.
Many of the suggestions, such as "Highlight all functions with try blocks" and "All functions more than 100 lines long", point to code quality problems due to leaky abstraction. If it matters to a function's caller whether it has 99 or 101 lines, or whether it can internally handle errors, something is desperately wrong. If you want to discourage such functions, we have linters for conditions like that, it shouldn't be a distraction to people maintaining the callers of such functions.
An example I almost agree with is "All functions that transitively call functions that make an http call", though I would generalize that to any network IO. Conventionally, in Rust such functions should now be async functions, and in Go they should take a `Context` for cancellation, both of which are visible at the call site, so idiomatic code is already clear in these ways. Again, it's a way we make things clear and explicit in the code itself, not just the highlight. (It's one of the reasons people blasted Scala's implicit arguments design; the saving wasn't worth the loss of clarity, highlighted or not)
"All lines last edited by a particular member of the team" - IDEs already have git blame views that provide much more information such as the commit comment and date. Either way these often fall down in practice; if you so much as change the indent level, it's your line now as far as the tooling is concerned.
Now for examples where we actually do this already and deserve to be credited:
JetBrains Rust Rover highlights unsafe functions very distinctly. unsafe{} blocks are allowed to call safe or unsafe functions, and this just shows you which of them are unsafe. That's a lot more useful than "All functions more than 100 lines long". I don't care how long it is, I do care if it could be the reason my project becomes the next vulnerability news cycle.
Unlike Rust and Java, Go doesn't have a way to limit a binding to at-most-once initialization, so "All variable identifiers we assign to twice" might actually be useful though in many cases it would just be ugly for no reason. For now though, JetBrains GoLand highlights shadowed variables, including in cases where they avoid bugs more than they cause them, but at least the right intention was there; whether a variable is shadowed is visually unclear in Go because := reuses an existing binding or makes a new one depending on the scope (unlike Rust's `let` which always makes a new binding even in the same scope), so the highlighting does provide information that's easy to miss otherwise. Where I disagree most is that the puke-green color makes it look like you're supposed to avoid it. Of course GoLand also highlights reused bindings specially too, with a neat underline that doesn't make it look like a problem to avoid.
I could go on but this is already a very long comment. I hope this is enough to demonstrate that many of the examples don't make a lot of sense because there are already better highlights or other tooling available, and tools already do use semantic highlighting for a few useful things without reducing the value of syntax highlighting. This is a well-understood idea in modern tools, it's just used more sparingly than suggested here.