Search code examples
javajavafxunicodejavafx-11

How to show control characters Unicode in JavaFX?



I'm using javafx 11 and jdk 8 to make a program which you can write something in a textarea and it will do some operation on that text, then it will show to result to you.

The problem is that I want to paste some special characters of unicode like "U+0011 : DEVICE CONTROL ONE [DC1]" but when I paste in the input textarea It will not appear.
Is there any way to make these kind of characters appear and get used?
These chars appear in notepad++ like this:

DC1 in notepad++


Solution

  • It appears JavaFX is stripping control characters before inserting text.

    You can’t show the characters directly, but Unicode has a block of characters specifically for showing control characters: Control Pictures.

    So, showing a visual representation of a character is as easy as:

    char charToDisplay = (c >= 32 || c == '\n' ? c : (char) (c + 0x2400));
    

    You can transform any String fairly easily:

    static String makeControlCharactersVisible(String s) {
        if (s == null) {
            return s;
        }
    
        int len = s.length();
        StringBuilder visible = new StringBuilder(len);
    
        for (int i = 0; i < len; i++) {
            char c = s.charAt(i);
            visible.append(c >= 32 || c == '\n' ? c : (char) (c + 0x2400));
        }
    
        return visible.toString();
    }
    

    In a JavaFX text component, you can intercept the paste:

    TextArea textArea = new TextArea() {
        @Override
        public void paste() {
            String text = Clipboard.getSystemClipboard().getString();
            replaceSelection(makeControlCharactersVisible(text));
        }
    };
    

    There are two disadvantages to this:

    • Most fonts have terrible glyphs for the control pictures characters, which are barely readable at normal font sizes like 12 points.
    • It’s conceivable that a user might want to actually paste a control picture character, in which case there would be no way to know whether they pasted, for example, '\u0011' or '\u2411'.