tputよりもシーケンスをエスケープする客観的な利点はありますか?


11

.*rc私がオンラインで見ている人のファイルやさまざまなコードで、多くの人がを使用する代わりにANSIエスケープシーケンスを手動で使用する傾向がありtputます。

tputはより普遍的/安全であるという理解を持っていたので、これは私に不思議に思います:

代わりにエスケープシーケンスを使用する必要がある客観的な理由はありますtputか?(移植性、エラーに対する堅牢性、異常な端末...?)


移植性の問題の裏側では、MobaXtermはprintfANSIエスケープシーケンスで動作しますが、tput失敗します(少なくとも私のボックスでは)。
ワイルドカード2016年

回答:


6

tputは、典型的なシェルスクリプトが使いにくいと感じる式(たとえば、sgrおよびsetaf)を処理できます。何が関係しているかを理解するにはinfocmp-f(フォーマット)オプションを適用した出力を参照してください。以下は、xtermのterminfoの説明にある文字列を使用した例の1つです。

xterm-16color|xterm with 16 colors,
        colors#16,
        pairs#256,
        setab=\E[
                %?
                        %p1%{8}%<
                        %t%p1%{40}%+
                %e
                        %p1%{92}%+
                %;%dm,
        setaf=\E[
                %?
                        %p1%{8}%<
                        %t%p1%{30}%+
                %e
                        %p1%{82}%+
                %;%dm,
        setb=
                %p1%{8}%/%{6}%*%{4}%+\E[%d%p1%{8}%m%Pa
                %?%ga%{1}%=
                        %t4
                %e%ga%{3}%=
                        %t6
                %e%ga%{4}%=
                        %t1
                %e%ga%{6}%=
                        %t3
                %e%ga%d
                %;
                m,
        setf=
                %p1%{8}%/%{6}%*%{3}%+\E[%d%p1%{8}%m%Pa
                %?%ga%{1}%=
                        %t4
                %e%ga%{3}%=
                        %t6
                %e%ga%{4}%=
                        %t1
                %e%ga%{6}%=
                        %t3
                %e%ga%d
                %;
                m,
        use=xterm+256color,
        use=xterm-new,

書式設定は物事を分割します-同じことを行うスクリプトまたはプログラムは、それらのねじれとターンに従う必要があります。ほとんどの人はあきらめて、最も簡単な文字列を使用します。

16色機能は、IBM aixtermから借用したもので、前景と背景のそれぞれに16個のコードを2つの範囲にマッピングします。

  • 30-37、90-97の前景
  • 40-47、100-107の背景

簡単なスクリプト

#!/bin/sh
TERM=xterm-16color
export TERM
printf '    %12s %12s\n' Foreground Background
for n in $(seq 0 15)
do
    F=$(tput setaf $n | cat -v)
    B=$(tput setab $n | cat -v)
    printf '%2d  %12s %12s\n' $n "$F" "$B"
done

そして出力はそれがどのように機能するかを示します:

      Foreground   Background
 0        ^[[30m       ^[[40m
 1        ^[[31m       ^[[41m
 2        ^[[32m       ^[[42m
 3        ^[[33m       ^[[43m
 4        ^[[34m       ^[[44m
 5        ^[[35m       ^[[45m
 6        ^[[36m       ^[[46m
 7        ^[[37m       ^[[47m
 8        ^[[90m      ^[[100m
 9        ^[[91m      ^[[101m
10        ^[[92m      ^[[102m
11        ^[[93m      ^[[103m
12        ^[[94m      ^[[104m
13        ^[[95m      ^[[105m
14        ^[[96m      ^[[106m
15        ^[[97m      ^[[107m

aixtermはECMA-48(「ANSI」とも呼ばれる)の色に一致するように30-37および40-47の範囲を使用し、標準で定義されていないコードには90-107の範囲を使用するため、数値は分割されます。

以下は、xtermを使用したスクリーンショットでTERM=xterm-16color、効果を確認できます。

ここに画像の説明を入力してください

参考文献:


私はあなたの主張を証明しているかもしれませんが、これらの表現の扱いは何ですか?infocmpのマニュアルを見ると、if-then-elseステートメントであることがわかります...しかし、これを見たことがないので、グーグルで検索するのに問題があります。ここで何が起きてるの。ありがとう!
キャプテンマン

2

UNIXプラットフォームにさまざまなデバイスを接続できる時代から来て、私はまだリテラルエスケープシーケンスよりもtputとその仲間をはるかに好みます。

本当の理由は、ほとんどの人が単にtputそれに関連するterminfo/ termcapファイルとライブラリを知らないためだと思います。


1

その理由の1つはtput外部コマンドであるため、組み込みのシェルエスケープコードよりも実行が遅くなる可能性があります。もう1つはbash、たとえばプロンプトのように、ANSIエスケープコードとシェル固有のエスケープ文字を組み合わせた1つのライナーを簡単に作成できることです。

PS1='\[\033[1;32m\]\u@\h\[\033[1;34m\] \w >\[\033[0m\] '

同様にzsh

PS1=$'%{\e[1;32m%}%n@%m%{\e[1;34m%} %3~> %{\e[0m%}'

ここではすべてが明確でコンパクトです。tput1は、複数の行にそれを分割するか、それがはるかに長く、複雑なラインを作り、実行する必要があるだろうtput、などを複数回


1
それでもoneliners、行うことができますTPUT付 PS1="$(tput setaf 2)\u@\h$(tput reset) >
キャプテン男

2
実際、それは$(tput sgr0)エンディングのためのものですが、tputが改善であることに同意します。
Thomas Dickey、2016
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.