How I came to create my own theme Nova.
A color scheme that is easy on the eyes by day and night.
Nova.app by Panic - creators of Firewatch (game), Transmit (FTP), and Coda (editor)
Not too long ago, Panic introduced Nova that follows Coda but is not a new infusion; instead, it is an entirely new developed editor.
Nova is a native macOS app, and as such, boots very quickly, almost as fast as Sublime Text. Nova is also very light on memory usage compatible with Sublime Text.
Nova looks promising, and after reading the documentation Library and also briefly checked out the Extension Library, I decided to give Nova a try.
Nova is fast, and it comes with a CLI tool and allows me to open files quickly, just like Sublime Text. The single window editor appears instantly. Scrolling through huge files feels buttery smooth.
The list of extensions is short, but someone releases a plugin I felt missing almost daily. I installed some of the available themes to check how themes affect the editor and its performance when scrolling through large files.
Soon I noticed that even Nova's themes often have a weakness that I can't accept. Namely, using the warning color red for syntax highlighting. For me, red indicates invalid code and linting errors. I can't get enthusiastic about other themes in which keywords are colored reddish, for example. I reread the Extension Library and decided I want to create my own theme.
Creating a Nova theme
The list of extensions you can create is quite extensive for an application released only a short while ago. It's easy to get going with Actions, Themes, Sidebar, Keyboard bindings, Language definitions, Code Completion, and more. I picked Themes, and I was surprised by seeing an (almost) complete collection of CSS selectors ready to be modified.
(1) How to define a color palette
Defining a color palette is not easy – at least not for me.
There are several ways to get theme colors.
- You can 'help yourself' by finding inspiration in other themes.
- You can open a drawing program and copy their color palette.
- You can have randomly generated colors displayed on various websites,
- Or you can define the colors in a complicated way and get lucky in the process.
I tried all these possibilities, and in the end, luck was the deciding factor. I never noticed the colorful glowing LEDs; but, I also never before wanted to create a Nova theme.
A friend works as a digital designer. She regularly takes pictures of things to determine the photo's color value. I had an idea of how to do it too.
I took some photos of the LEDs, also at different times of the day, and then I loaded all the pictures into the App Spectrum by Eigenlogik.
(2) Collection thoughts and stay focused
I had now invested enough time and made a series of decisions that still needed documenting.
As usual, I used Xmind and filled a mind map with everything that seemed important to me. It helped me concentrate on the important parts rather than on the nice-to-have parts.
(3) Stylus savior of the ... CSS
Nova supports only a subset of CSS and, unfortunately, no CSS variables. I found working with copy and paste not very productive and decided to go another way.
I went with Stylus and started converting the CSS file. Nova's CSS file contains color values in the HSB format, while Stylus only understands HEX, RGB(A), and HSL(A).
After converting color formats, I created a source code example using the colors I just finished converting.
(4) Working with the Syntax Inspector
Identifying CSS scopes is easy with Nova's Inspector.
The scopes are sorted by priority, and the scope shown at the top has overwritten all conflicting properties of the scopes below.
For debugging, I use white font on a red background.
(5) Eureka effect
I didn't save the extracted colors in a swatch or palette, so I had to use Affinity Photo again. I couldn't find the exact places where I initially took the color values. A bit in anger and frustration about myself, I almost just carelessly 'clicked' on the LED colored areas in the pictures and copied the HSL format values to get it done.
I created a Victor Mono font powered code style example in Figma for testing purposes.
On my MacBook, I have True Tone and Night Shift enabled. On my LG 34UM95, both are not available. Surprisingly, the colors were still legible on both displays. Even after several hours, I had no problems reading the colored code.
I had discovered a marketing-capable feature of my theme. Easy on the eyes by day and night.
(6) Finding a project name
Now I needed a name for the theme as I started to develop the impression that I could create an excellent theme. When I started creating this theme, my local project folder was called 'test-nova-theme'.
I have sunglasses with polarized lenses. When I wear these sunglasses, some colors change behind safety glass, shop windows, or computer monitors.
However, all colors remain identifiable and visible. I had the spontaneous idea to find a name that is maybe derived from 'polarized'.
I found many name generators on the Internet and fed each of them the word 'polarized'. I don't remember which page exactly displayed 'Polisis', but I knew it sounded quite good, but the last two letters bothered me, so I made it Polis — time to go public!
What is done so far
Polis has now reached a significant milestone, and coloring of all CSS selectors as specified in the theme template is done.
Polis has a logo that I created in Figma.
Within the project, I defined two custom tasks and three steps.
- Tasks
Prepare Environment
Build
-Step - Installs Stylus ifyarn
andnode
is found. Tells you to install bothnode
andyarn
if not found.
Polis Theme
Clean
-step - Removes thebuild
folder andPolis.novaextension
folder if presentBuild
-step - Runs Stylus to generatePolis.css
then createsPolis.novaextension
folder and copies files as defined in project settingsArguments
tab.
With the current release v0.4.0, Every single color shade is mathematically generated. I only defined a few primary colors, and a color-function generates all the other colors.
// helper function to turn colors dark/light or add alpha
polis( $color, $shade = 1.0, $alpha )
$alpha = $shade if $shade is a 'unit'
$c = get_color( $color, $colors )
/* code shortened to focus on the important part */
$c = l( de( $c, 50% ), 25 ) if 'light_50' in $shade
$c = l( de( $c, 30% ), 15 ) if 'light_30' in $shade
$c = l( de( $c, 10% ), 5 ) if 'light_10' in $shade
$c = da( s( $c, 25% ), 50% ) if 'dark_50' in $shade
$c = da( s( $c, 15% ), 30% ) if 'dark_30' in $shade
$c = da( s( $c, 5% ), 10% ) if 'dark_10' in $shade
return hsla( $c, $alpha )
What will be done
The next releases will target specific languages as Polis should support all of Nova's 27 integrated languages.
After releasing version v1.0, Polis will begin supporting language extensions - mainly LSP based.
What could be done
The polis()
function could check if shading makes sense. Calling white( 'light_90' )
makes no sense as every value above light_50
is already pure white #fff
. I plan to develop a color map generator which generates X dark shades and Y light shades. light_90
and dark_90
should never be #fff
or #000
for any other color than white for black.
I envision people fork Polis, replace magenta
with say violet
, generate their theme, and the generated color shades don't shift into white
when calling, for example magenta( 'light_90' )
.
Improve Polis, fork it or make it your own
Give Polis a try and install it right away by clicking on the link below:
I host the project source code on GitLab under the permissive MIT license. Fork Polis and help improve it or make it your own.
Polis derivatives
- Polis for iTerm2 already exists but needs fine-tuning because bold-text in green and yellow is not readable in some situations. The Starship prompt I'm using injects a darker blue for commands, which conflicts with the cursor guide color.
- Polis for Typora should also be no problem since Typora uses CSS too.
Useless Markdown stats:
190 Lines
1564 Words
11307 Characters