## Keyboard shortcuts

Press `←` or `→` to navigate between chapters

Press `S` or `/` to search in the book

Press `?` to show this help

Press `Esc` to hide this help

# CSS-based styling Tutorial

### Before IDA 7.3

IDA used to store colors in the registry:

- `HKEY_CURRENT_USER\Software\Hex-Rays\IDA` on Windows,
- `~/.idapro/ida.reg` on Linux & Mac OSX.

This was somewhat inconvenient because color values were stored in binary format, and hard to move from computer to computer.

In addition, this only lets users style a small subset of the widgets that compose IDA, which can be insufficient.

### IDA 7.3: CSS-based styling

Since we had to introduce yet another set of new colors in 7.3, we took the opportunity to moved away from the registry-stored, binary-only approach, to a CSS-based approach.

This gives us the following advantages:

- CSS is a well-known format
- CSS is human-readable
- Qt understands CSS out-of-the-box (parts of it, at least)
- Using CSS will therefore let us style not only the custom IDA widgets, but all widgets

This last point is important, because many users have been asking for the ability to style IDA more thoroughly, rather than just styling a few custom widgets (such as the disassembly views, navigation band, …)

### How IDA 7.3 CSS-based styling works

IDA 7.3 ships with 2 themes by default:

- default
- dark

Those themes are located in `$IDA_INSTALL/themes/`:

    aundro@flatiron:~/IDA-7.3$ tree themes/
    themes/
    ├── _base
    │   └── theme.css
    ├── dark
    │   ├── icons
    │   │   ├── expand.png
    │   │   └── spacer.png
    │   └── theme.css
    └── default
        └── theme.css

    4 directories, 5 files
    aundro@flatiron:~/IDA-7.3$

Notice that, in addition to `dark` and `default` directories, you can also spot an additional `_base` directory.

The `_base` theme holds all the CSS directives that are required for IDA to work correctly, and therefore it must be “imported” by other themes (using the IDA-specific `@importtheme` directive) before any other styling directives are declared.

For example, here are the first 3 lines of `$IDA_RELEASE/themes/dark/theme.css`:

    aundro@flatiron:~/IDA-7.3$ head -n 3 themes/default/theme.css

    @importtheme "_base";

    aundro@flatiron:~/IDA-7.3$

### What happens when colors are modified through the “Colors” dialog?

When you change colors in the ‘Colors’ dialog, IDA will not modify the files that are present in `$IDA_INSTALL/themes/`.

Instead, IDA will create a file in IDA’s user directory, holding what we will refer to as “user overrides”.

Let’s assume the user:

- switched to the `dark` theme,
- modified the `Instruction` text color to red.
- clicked ‘OK’

IDA will then have created the file:

- `~/.idapro/themes/dark/user.css`
- `%APPDATA%\Hex-Rays\IDA Pro\themes\dark\user.css` on Windows

with the following contents:

    aundro@flatiron:~/.idapro$ tree themes
    themes
    └── dark
        └── user.css

    1 directory, 1 file
    aundro@flatiron:~/.idapro$
    aundro@flatiron:~/.idapro$ cat themes/dark/user.css
    /* NOTE: This is an autogenerated file; please do not edit. */

    CustomIDAMemo
    {
        qproperty-line-fg-insn: red;
    }
    aundro@flatiron:~/.idapro$

In other words, the themes that are shipped with IDA are never modified, but instead a “user override” file is created, that will contain whatever customization the user made to the theme.

### Importing/Exporting themes customization

IDA 7.3 removed the Import/Export feature from its `Colors` dialog, because an equivalent is already automatically present in the form of those “user overrides” files, which can be found in:

- `%APPDATA%\Hex-Rays\IDA Pro\themes\*\user.css` on Windows,
- `~/.idapro/themes/*/user.css` on Linux and Mac OSX.

In order to re-use customizations across different computers, it is enough to just copy those `user.css` file(s).

### Debugging style sheets lookup

In case IDA misbehaves, and appears to ignore some styling directives, it’s possible to launch IDA with the following command-line flag to debug themes loading: `ida -z1000000`

In IDA’s `Output window`, you should spot something along the lines of this:

    Themes: Trying file "/home/aundro/IDA-7.3/themes/dark/theme.css" ... found.
    Themes: Trying file "/home/aundro/.idapro/themes/dark/theme.css" ... not found.
    Themes: Found @importtheme (/home/aundro/IDA-7.3/themes/dark/theme.css:6)
    Themes: Trying file "/home/aundro/IDA-7.3/themes/_base/theme.css" ... found.
    Themes: Trying file "/home/aundro/.idapro/themes/_base/theme.css" ... not found.
    Themes: Trying file "/home/aundro/IDA-7.3/themes/dark/user.css" ... not found.
    Themes: Trying file "/home/aundro/.idapro/themes/dark/user.css" ... found.

First of all, IDA tries to load the desired (`dark`) theme contents (that corresponds to the first 5 lines):

- IDA looked for `$IDA_INSTALL/themes/dark/theme.css`, and found it
- IDA also looked for `~/.idapro/themes/dark/theme.css`! (we’ll discuss this in the following chapter)
- IDA spotted that the `dark` theme imports the `_base` theme, and loaded contents from that one as well.

Then, IDA tries to load user overrides for the `dark` theme (corresponds to the 2 final lines):

- IDA looked for `$IDA_INSTALL/themes/dark/user.css`, but didn’t find it (this is, in fact, pretty much unnecessary, since user overrides should never be in IDA’s installation directory. We’ll eventually get rid of this.)
- IDA looked for in `~/.idapro/themes/dark/user.css`, and found it.

### Adding themes

As was mentioned in the previous chapter, IDA also looks for themes contents in IDA’s user directory:

- `%APPDATA%\Hex-Rays\IDA Pro\themes` on Windows,
- `~/.idapro/themes` on Linux & Mac OSX

That means it’s possible to add your own themes there, without having to modify the (possibly read-only) `$IDA_INSTALL` directory.

In addition, putting additional themes in IDA’s user directory means that new version of IDA will be able to pick them up automatically.

### Example new theme

Let’s say you want to create a new theme, called `blue`.

You should therefore create the following CSS file:

- `~/.idapro/themes/blue/theme.css`

…in which you can override anything you want, after importing the `_base` theme.

For example:

    aundro@flatiron:~/.idapro$ cat themes/blue/theme.css

    @importtheme "_base";

    QWidget
    {
        background-color: lightblue;
    }

    CustomIDAMemo
    {
        qproperty-line-fg-regular-comment: red;
        [...snipped...]
    }
    aundro@flatiron:~/.idapro$

You can then ship that `~/.idapro/themes/blue/theme.css` file to other users, and any personal modifications they make to it, will be stored in `~/.idapro/themes/blue/user.css`, leaving your original `blue` theme untouched.

### What can be styled, and how?

Conceptually, IDA’s CSS styling can be “split” into 2 categories:

1. Core Qt widgets styling
2. IDA custom widgets styling

#### 1) Core Qt widgets styling

In order to know what, and how to style Qt widgets, the best is to have a look at the references:

- Qt Style Sheets, and
- Qt Style Sheets Reference

#### 2) IDA custom widgets styling

IDA’s main stylable custom widgets have the following class names:

- CustomIDAMemo
- TextArrows
- MainMsgList
- TCpuRegs
- navband_t

You can find the entire set of properties supported by those, by looking at the contents of:

- `$IDA_INSTALL/themes/_base/theme.css`
- `$IDA_INSTALL/themes/default/theme.css`

## A note about the “.clr” file format

In order to re-use color schemes with IDA < 7.3, users had to export, and then import them using `.clr` files.

It’s worth pointing out that colors in those files, are in the form `"BBGGRR"`, while CSS expects `"#RRGGBB"`, so you will need to pay attention to that when porting colors from a `.clr` file.

Alternatively, you can use the following script, which might help get most of the job done.

{% file src=“../.gitbook/assets/port_clr72_to_css.py” %} Download a script {% endfile %}

### A note about the dark theme

Note that even though IDA ships with a ‘dark’ theme, the version of Qt we use still doesn’t support OS-induced theme switches, and therefore IDA won’t automatically switch to it; the user will still have to change it manually.

### Restrictions

Qt is mostly stylable using CSS, but it has a few restrictions:

- Styling of URLs in `QLabel` instances is not supported (see this question)
- In tabular views (e.g., the `Functions window` widget), we added the ability to highlight the portions of text that match the “quick filter” query (which can be opened using `Ctrl+F`). Unfortunately, the code we added to do that, will simply not be called for items in those views to which CSS directives apply. This is the case for e.g., “selected” items, in the `dark` mode. We will try and solve this in the future, but currently don’t have a fix.