#+TITLE: Smart-mode-line
[[https://gratipay.com/Malabarba/][Donate to developer]]

Smart Mode Line is a sexy mode-line for Emacs. It aims to be easy to
read from small to large monitors by using /colors/, a /prefix feature/,
and /smart truncation/.

* Images

*Dark Theme*\\
[[file:screenshot-2013-11-11-dark.png]]

*Light Theme*\\
[[file:screenshot-2013-11-11-light.png]]

*Atom-one Dark Theme*\\
[[file:screenshot-atom-one-dark.png]]

(Note: to use the Atom-one theme, install
=elpa-smart-mode-line-atom-one-dark-theme=)

*Solarized Dark Theme*\\
[[file:screenshot-solarized-dark-theme.png]]

*Solarized Light Theme*\\
[[file:screenshot-solarized-light-theme.png]]

(Note: to use the Solarized themes, install
=elpa-solarized-theme=)

*Powerline Theme*\\
[[file:screenshot-powerline-theme.png]]

*Light Powerline Theme*\\
[[file:screenshot-light-powerline-theme.png]]

(Note: to use either powerline theme, install
=elpa-smart-mode-line-powerline-theme=)

* Installation

After installing *smart-mode-line* simply activate it with:

#+BEGIN_SRC emacs-lisp
    (sml/setup)
#+END_SRC

By default, =sml= will try to figure out the best sml theme to go with
your Emacs theme. But if you want to chose the theme yourself, do one
of the following BEFORE =sml/setup=:

#+BEGIN_SRC emacs-lisp
    (setq sml/theme 'dark)
    (setq sml/theme 'light)
    (setq sml/theme 'respectful)
#+END_SRC

**** Installation Issues (FAQ)

-  *Problem:* If Emacs always warns you that /“Loading themes can
    run lisp code”/ and keeps asking /“Would you like to mark this theme
   as
    safe for future sessions?”/. That is probably an issue with your
    =init.el= or =.emacs= file, but we offer a workaround.
-  *Workaround:* Add the following snippet before =sml/setup=

   #+BEGIN_SRC emacs-lisp
       (setq sml/no-confirm-load-theme t)
   #+END_SRC

-  *Proper Solution:* Make sure the =(custom-set-variables ...)= sexp
    is at the very top of your =.emacs= file. That is the right place
    for it. If that doesn't work, forget about smart-mode-line for a
    moment and see if you have the same problem with other themes
    installed from Melpa.

* Features

Its main features include:

- Color coded ::
   Highlights the most important information for you
   (buffer name, modified state, line number). Don't
   like the colors? See item /5./!

- Fixed width (if you want) ::
   Lets you set a maximum width for the path name and mode names, and
   truncates them intelligently (truncates the directory, not the
   buffer name). Also let's you *right indent* strings in the
   mode-line (see =sml/mode-width=).

- Directory as Prefixes ::
   Prefix feature saves a LOT of space. e.g. =~/.emacs.d/=
   is translated to =:ED:= in the path (open a file inside
   this folder to see it in action). Long path names you
   are commonly working on are displayed as short
   abbreviations. Set your own prefixes to make best use
   of it (by configuring =sml/replacer-regexp-list=). Mousing
   over the abbreviated path will show you the full
   path. See below for examples.

- Hide or Highlight minor-modes ::
   The =rich-minority=
   package saves even more space. Select which minor modes you don't
   want to see listed by adding them to the variable
   =rm-blacklist=, or even highlight the modes that are more
   important with the variable =rm-text-properties=. This will filter
   out the modes you don't care about and unclutter the modes list
   (mousing over the modes list still shows the full list).

- Very easy to configure ::
   All colors and variables are customizable. You can change the
   whole theme with =sml/apply-theme=, or just customize anything
   manually with =sml/customize= and =sml/customize-faces=. There are
   /DOZENS/ of variables to customize your mode-line, just pop over
   there and have a look!

- Compatible with absolutely anything ::
   I'm serious. Versions 2.0 and above should be compatible with
   *any* other packages that display information in the mode-line
   (evil, nyan-mode, elscreen, display-battery-mode, etc). If you
   find /ANYTHING/ that does not appear as it should, file a bug report
   and I'll get to it.

* Important Variables:

All variables can be edited by running =sml/customize=, and the
documentations are mostly self explanatory, I list here only the
most important ones.

1. =sml/theme=\\
    Choose what theme you want to use for the mode-line colors. For now
    there are 3 different themes: =dark=, =light=, and =respectful=.

2. =sml/shorten-directory= and =sml/shorten-modes=\\
    Setting both of these to =t= guarantees a fixed width mode-line
    (directory name and minor-modes list will be truncated to fit). To
    actually define the width, see below.

3. =sml/name-width= and =sml/mode-width=\\
    Customize these according to the width of your emacs frame. I set
    them to =40= and =full= respectively, and the mode-line fits
    perfectly when the frame is split in two even on my laptop's small
    17" monitor. =full= means everything after the minor-modes will be
    right-indented.

4. =sml/replacer-regexp-list=\\
    This variable is a list of (REGEXP REPLACEMENT) that is used
    to parse the path. The replacements are applied
    sequentially. This allows you to greatly abbreviate the path
    that's shown in the mode-line. If this abbreviation is of
    the form =:SOMETHING:=, it is considered a prefix and get's
    a different color (you can change what's considered a prefix
    by customizing =sml/prefix-regexp=).
    For example, if you do a lot of work on a folder called
    =~/Dropbox/Projects/In-Development/= almost half the
    mode-line would be occupied just by the folder name, which
    is much less important than the buffer name. But, you can't
    just hide the folder name, since editting a file in
    =~/Dropbox/Projects/In-Development/Source= is VERY different
    from editting a file in =~/Dropbox/Projects/Source=. By
    setting up a prefix for your commonly used folders, you get
    all that information without wasting all that space. In this
    example you could set the replacement to =:ProjDev:= or just
    =:InDev:=, so the path shown in the mode-line will be
    =:ProjDev:Source/= (saves a lot of space without hiding
    information).

Some abbreviations are defined out of the box, for instance /(see the
documentation for a complete list)/:

#+BEGIN_SRC emacs-lisp
    ("^~/\\.emacs\\.d/" ":ED:")
    ("^/sudo:.*:" ":SU:")
    ("^~/Documents/" ":Doc:")
    ("^~/Dropbox/" ":DB:")
#+END_SRC

You can stack abbreviations sequentially, by adding them in order:

#+BEGIN_SRC emacs-lisp
    (add-to-list 'sml/replacer-regexp-list '("^~/Git-Projects/" ":Git:") t)
    (add-to-list 'sml/replacer-regexp-list '("^:Git:\(.*\)/src/main/java/" ":G/\1/SMJ:") t)
#+END_SRC

Note the =t= option ensures that your customizations are added to the
end of the list, which ensures that the second one is applied
*after* the first.

However, if you want to override one of the pre-defined abbreviations
with your own definition you need to add it to the start of the list
(note the omitted =t=):

#+BEGIN_SRC emacs-lisp
    (add-to-list 'sml/replacer-regexp-list '("^~/Dropbox/" ":DBox:"))
#+END_SRC

In order to use more complex transformations (like upcasing), you'll
need to write a more complex
replacement. The second argument needs to be a function that accepts the
matched string as its
argument and returns the replacement string. You can access matched data
with the =match-string=
function as explained
[[https://www.gnu.org/software/emacs/manual/html_node/elisp/Simple-Match-Data.html#Simple-Match-Data][in
the manual.]] For example, for using the upcased project name (assuming
the project is in the =~/Projects= directory:

#+BEGIN_SRC emacs-lisp
(add-to-list 'sml/replacer-regexp-list
             '("^~/Projects/\\(\\w+\\)/"
               (lambda (s) (concat ":" (upcase (match-string 1 s)) ":")))
             t)
#+END_SRC
