Typing a zero-width space in TERMINAL emacs shows an underscore-ish character. How to make it showing nothing?
1 Answers
Refer to C-hig (elisp)Glyphless Chars
By default the zero-width characters are displayed using the thin-space
display method which will "Display a thin space, 1-pixel wide on graphical displays, or 1-character wide on text terminals"; also noting that "The ‘thin-space’, ‘empty-box’, ‘hex-code’, and ASCII string display methods are drawn with the ‘glyphless-char’ face" which by default inherits from the underline
face.
This default ensures that these (potentially-confusing) characters are not 100% invisible to the user, and can easily be made much more visible if desired; but there is also a zero-width
display method which you can use to truly hide them from display:
(set-char-table-range glyphless-char-display
(char-from-name "ZERO WIDTH SPACE") 'zero-width)
Personally I want these things to be as visible as possible -- I've encountered a situation where I was unwittingly copying and pasting zero-width joiners between visible characters, and I created a mess because I never knew they were there. To make sure they are apparent to me (as I don't expect such things to normally be in the text I edit), I use this:
(set-face-background 'glyphless-char "red")
(If you want to see how that looks, copy this sentence into Emacs and configure that background.)
To hide such chars for a particular mode only, you could make the char table buffer-local in that mode.
;; Make glyphless chars highly visible.
(set-face-background 'glyphless-char "red")
;; Hide ZERO WIDTH chars completely in `org-mode'.
(add-hook 'org-mode-hook #'my-hide-zero-width-chars)
(defun my-hide-zero-width-chars ()
"Make ZERO WIDTH characters completely invisible."
(setq-local glyphless-char-display
my-zero-width-glyphless-char-display))
(defvar my-zero-width-glyphless-char-display
(let ((table (copy-sequence glyphless-char-display))
(charnames (list "ZERO WIDTH SPACE"
"ZERO WIDTH NO-BREAK SPACE"
"ZERO WIDTH JOINER"
"ZERO WIDTH NON-JOINER")))
(dolist (name charnames)
(set-char-table-range table (char-from-name name) 'zero-width))
table)
"Variant of `glyphless-char-display' which hides ZERO WIDTH chars.")

- 48,657
- 3
- 76
- 115
-
Thanks for the answer. I also want to know what setting makes the zero width space become an underscore like thing. – FunkyBaby Jun 01 '21 at 23:54
-
Can I hide these only in org-mode? – HappyFace Jun 03 '21 at 15:00
-
n.b. I've updated the answer with all of the additional information and responses from my earlier comments. – phils Jun 30 '21 at 02:23
-
Not working for me. I run that code. In an org buffer I can confirm it partially worked, because if I eval `(aref glyphless-char-display (char-from-name "ZERO WIDTH SPACE"))` I get `zero-width`. But if I then insert that character in my org buffer, I still see an red underscore. – Rob N May 04 '23 at 17:44
-
phils, could a simalar method be used to change the glyph of `NARROW NO-BREAK SPACE`? It is the same as no-break space when using fixed-width font,and it would be useful to be able to distinguish them. – pglpm Jun 14 '23 at 21:38
-
1I can't reproduce your issue: for me, in a GUI emacs frame, the narrow no-break space *is* narrow (tested with `emacs -Q` for both Emacs 27 and 28). I only have "wide narrow glyphs" in terminal frames (which is expected). If you're not *already* getting narrow glyphs, I'm not sure whether this answer could help; you'd need to play with the code to find out. – phils Jun 14 '23 at 23:23
-
Thank you for the feedback. In a GUI frame and starting emacs (28) with `-Q`, `no-break space` is shown as an underlined empty space, which usefully distinguishes it from normal space. But `narrow no-break space` is shown in exactly the same way. Maybe I'll ask a question here about that. – pglpm Jun 15 '23 at 05:22