#!/bin/bash BASH_ARGV0=write-tty echo -n "$0" >/proc/$BASHPID/comm output_filter() { tokenize | colorize | soft_cursor } chr() { declare -i n="$*" printf "$(printf '\%o' "$n")" } colorize() { BASH_ARGV0=colorize echo -n "$0" >/proc/$BASHPID/comm while read -r do case "$REPLY" in \\[0-7][0-7][0-7] ) declare -i c=8#"${REPLY#?}" ;; \\U[0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F] ) declare -i c=16#"${REPLY#??}" ;; * ) printf '%s\n' "$REPLY" continue ;; esac if (( c > 128 + 127 )) then : elif (( c > 128 + 32 )) then REPLY=M-$(chr c - 128) elif (( c > 127 )) then REPLY=M-^$(chr c - 128 + 64) elif (( c < 32 )) then REPLY=^$(chr c + 64) fi printf $'\e[106m%s\e[m\n' "$REPLY" done } tokenize() { BASH_ARGV0=tokenize echo -n "$0" >/proc/$BASHPID/comm while read -r -n1 -d '' do if [[ "$REPLY" =~ [[:print:]] ]] then # Output one printable character per line. It may be a # multibyte unicode character. printf '%s\n' "$REPLY" continue elif [ "$REPLY" ] then # If it is a non-printable, then we output a # multi-character line. In this case we colorize it # later so that it won't be confused with multiple # printable characters. bytelen=$(LC_ALL=C; echo ${#REPLY}) if (( bytelen == 1 )) then printf '\\%.3o\n' "'$REPLY" else hexdigits=$(LC_ALL=C; for ((i=0; i<$bytelen; ++i)) do printf '%.2x' "'${REPLY:$i:1}" printf '%.2x\n' "'${REPLY:$i:1}" >&2 done) printf '%s%.8x\n' '\U' 0x"$hexdigits" fi else printf '\\%.3o\n' 0 fi done } soft_cursor() { BASH_ARGV0=soft_cursor echo -n "$0" >/proc/$BASHPID/comm FMT=$'%s \b\e[%sm \e[m \b\b' REPLY= color=105 while printf "$FMT" "$REPLY" "$color" do read -r || break done } output_filter