Invisible Character Finder

Find the hidden characters that break matching, code and forms, and get a cleaned copy.

Paste text that looks right but behaves wrong: a string that will not match, a code snippet that will not run, a form field that rejects input you swear you typed. This tool scans every character and lists the ones you cannot see, with their code point, name, position and what to do about them. Joiners that belong in emoji sequences and Arabic or Persian words are flagged as check-first, not removed. The cleaned copy keeps those joiners and removes the rest of the flagged characters, with space variants turned into plain spaces.

Honest limits. This tool only flags the character set listed in the reference table below. A character that renders blank in your font but is a normal letter in another script is not flagged, and a joiner inside a real emoji sequence is doing its job. Direction controls (U+202A to U+202E and U+2066 to U+2069) can be used to make code display in a different order from how it runs, the Trojan Source trick, so any of those in code from an untrusted source should be treated as suspicious, not just cleaned quietly.

The usual suspects, and what each one does

Zero-width space (U+200B) adds a line-break chance with no visible gap, and it splits one word into two for search, spellcheck and string comparison. Zero-width non-joiner (U+200C) stops two letters joining, which Persian and Arabic spelling needs; zero-width joiner (U+200D) joins emoji into one picture, such as a family emoji. Byte order mark (U+FEFF) at the start of a file is an encoding signature, but inside text it is a stray character that breaks parsers and shifts the first column heading of a CSV. Non-breaking space (U+00A0) and narrow no-break space (U+202F) look like spaces but never match a plain space in find and replace. Soft hyphen (U+00AD) stays invisible until a line wraps, then turns into a hyphen nobody typed.

The rest of the set is space variants (U+1680, U+2000 to U+200A, U+205F, U+3000), word joiner (U+2060, which blocks a line break), line and paragraph separators (U+2028, U+2029), direction marks and isolates (U+200E, U+200F, U+202A to U+202E, U+2066 to U+2069), variation selectors (U+FE00 to U+FE0F, which pick an emoji shape after an emoji and are leftovers after a plain letter), tag characters (U+E0000 to U+E007F), Hangul filler (U+3164) and Braille blank (U+2800, a blank Braille cell used for empty usernames). The tool names each one it finds, so you can decide case by case instead of deleting blindly.

When to keep a flagged character

Keep a joiner when it sits between emoji or inside an Arabic, Persian or Indic word: removing it changes the spelling or breaks the emoji. Keep a variation selector after an emoji: it picks the colour emoji form. Keep a non-breaking space when it is doing typography work, such as keeping a number with its unit. Everything else on the list is usually safe to remove from pasted text.

Why trim does not fix it

Trim removes whitespace at the ends of a string, and most of these characters are not whitespace in that sense, or they sit in the middle of the string. A zero-width space in the middle of a username survives trim, survives a visual check, and still makes two identical-looking strings compare as different. The fix is to find the exact code point, not to retype the text and hope.

Frequently Asked Questions

Unicode character U+200B, an invisible line-break chance with no visible gap. It sneaks in from chat apps, copied web pages and rich-text editors, and it splits one word into two for search, spellcheck and string comparison.
Because a character such as U+200B or U+FEFF landed outside a string, where the language parser does not expect it. Python reports an invalid non-printable character and Node reports an unexpected token. The fix is to find and remove that exact code point.
Not blindly. U+200D joins emoji into one picture and joins letters in Arabic, Persian and Indic scripts. Inside a real emoji sequence or a word in those scripts, it is doing its job. This tool flags joiners as check-first and the cleaned copy keeps them.
Direction override characters (U+202E and the isolates U+2066 to U+2069) can make source code display in a different order from how it runs. Code from an untrusted source that contains any of those should be treated as suspicious, not just cleaned quietly.
Some editors save UTF-8 files with a BOM, U+FEFF, at the very start. Parsers that do not strip it see the first column heading as a different string, so the first column stops matching. Removing the BOM at the start fixes it.
No. The scan runs in your browser. Nothing is sent to a server, which matters when the pasted text is code, a password-adjacent string or private content.

Related Tools

Was this tool helpful?

Comments

Loading comments...

Check Out Other Popular Tools