Emacs: Reformat Lines for Source Code

By Xah Lee. Date: . Last updated: .

Here's a command to reformat current paragraph into 1 long line or multiple short lines.

When there's a text selection, work on that region. Else, work on current paragraph (between blank lines.).

This command is designed to work with programing language source code. It strictly exchange whitespaces and newline.

Code also available on github at https://github.com/xahlee/xah-reformat-code and https://melpa.org/#/xah-reformat-code

(defun xah-reformat-whitespaces-to-one-space (*begin *end)
  "Replace whitespaces by one space.
URL `http://ergoemacs.org/emacs/emacs_reformat_lines.html'
Version 2017-01-11"
  (interactive "r")
  (save-excursion
    (save-restriction
      (narrow-to-region *begin *end)
      (goto-char (point-min))
      (while
          (search-forward "\n" nil "NOERROR")
        (replace-match " "))
      (goto-char (point-min))
      (while
          (search-forward "\t" nil "NOERROR")
        (replace-match " "))
      (goto-char (point-min))
      (while
          (search-forward-regexp "  +" nil "NOERROR")
        (replace-match " ")))))

When working on programing language code, we want to reformat lines by a exchange of whitespaces.

  1. Whitespace here is defined to be space, tab, and newline character.
  2. Repeated whitespace is considered equivalent to just 1 space or just 1 newline char.
  3. Whitespace is never created if it didn't exist before.
  4. Whitespace is never removed.
  5. No character other than whitespace are removed or inserted.

The advantage of the code above is that they do not call emacs fill-region commands.

fill-region sometimes delete non-whitespace characters.

fill-region sometimes remove a run of whitespace(s) to none, or vice versa.

Here's examples of fill-region issues.

whitespaces added

- Xxxx xx xxxxxxxxx xxxxxxx xxxxxxx xxxx xxxxxxx xx xxxxxxxxxx xxxxxxxx xxxx, xxx xxx'x xxxx xxxxxxx xxxx xxx xxxxx xxxx xxxxxxxxxxxx xxxxx xxxx xxxx xxxxxx. Xxx xxxx-xxxxxx xxxxxxxx xxxxxxxxx xxxx xxx xxxxxx xx xxxxx xxxx, xx xxxxxx xxxxxx xxxxxxx xxxxxx x xxxxx xx xxxxx.

after fill-paragraph.

adaptive-fill-mode is t

becomes

- Xxxx xx xxxxxxxxx xxxxxxx xxxxxxx xxxx xxxxxxx xx xxxxxxxxxx
  xxxxxxxx xxxx, xxx xxx'x xxxx xxxxxxx xxxx xxx xxxxx xxxx
  xxxxxxxxxxxx xxxxx xxxx xxxx xxxxxx. Xxx xxxx-xxxxxx xxxxxxxx
  xxxxxxxxx xxxx xxx xxxxxx xx xxxxx xxxx, xx xxxxxx xxxxxx xxxxxxx
  xxxxxx x xxxxx xx xxxxx.

Notice the extra whitespaces.

if adaptive-fill-mode is nil, then this won't happen.

adaptive-fill-mode is t by default.

elisp code here for convenience.

(setq adaptive-fill-mode nil)
(setq adaptive-fill-mode t)

Asterisks Deleted

* Xxxx xx xxxxxxxxx xxxxxxx xxxxxxx xxxx xxxxxxx xx xxxxxxxxxx
* xxxxxxxx xxxx, xxx xxx'x xxxx xxxxxxx xxxx xxx xxxxx xxxx
* xxxxxxxxxxxx xxxxx xxxx xxxx xxxxxx. Xxx xxxx-xxxxxx xxxxxxxx
* xxxxxxxxx xxxx xxx xxxxxx xx xxxxx xxxx, xx xxxxxx xxxxxx xxxxxxx
* xxxxxx x xxxxx xx xxxxx.

after fill-paragraph with big fill-column value.

adaptive-fill-mode is t

becomes

* Xxxx xx xxxxxxxxx xxxxxxx xxxxxxx xxxx xxxxxxx xx xxxxxxxxxx xxxxxxxx xxxx, xxx xxx'x xxxx xxxxxxx xxxx xxx xxxxx xxxx xxxxxxxxxxxx xxxxx xxxx xxxx xxxxxx. Xxx xxxx-xxxxxx xxxxxxxx xxxxxxxxx xxxx xxx xxxxxx xx xxxxx xxxx, xx xxxxxx xxxxxx xxxxxxx xxxxxx x xxxxx xx xxxxx.

The asterisks are gone.

if adaptive-fill-mode is nil, then this won't happen.

elisp code here for convenience.

(setq fill-column 3045708747)
(setq fill-column 70) ; default

Whitespace Created When There Was None

混沌未分天地乱,茫茫渺渺无人见。自从盘古破鸿蒙,开辟从兹清浊辨。覆载群生仰至仁,发明万物皆成善。欲知造化会元功,须看西游释厄传。一派白虹起,千寻雪浪飞;海风吹不断,江月照还依。冷气分青嶂,馀流润翠微;潺湲名瀑布,真似挂帘帷。

after fill-paragraph.

becomes

混沌未分天地乱,茫茫渺渺无人见。自从盘古破鸿蒙,开辟从兹清浊辨。覆载群
生仰至仁,发明万物皆成善。欲知造化会元功,须看西游释厄传。一派白虹起,
千寻雪浪飞;海风吹不断,江月照还依。冷气分青嶂,馀流润翠微;潺湲名瀑布,
真似挂帘帷。

whitespaces are created at positions when there was none.

This is a problem when displayed in browser. Because, the newline characters will create a gap, and gaps in Chinese can change meaning.

Version Calling Emacs Fill

For a version that calls emacs fill-region, see Emacs: fill-region, unfill-region Toggle.

Like it? Buy Xah Emacs Tutorial. Thanks.

or, buy something from Best Keyboard for Emacs