端末で以下の出力を生成するこの関数を作成しましたが、この関数は複雑に思われるため、改善または同じ代替ソリューションのためにここに投稿しました。
#!/bin/bash
function box_out() {
input_char=$(echo "$@" | wc -c)
line=$(for i in `seq 0 $input_char`; do printf "-"; done)
# tput This should be the best option. what tput does is it will read the terminal info and render the correctly escaped ANSI code for you. code like \033[31m will break the readline library in some of the terminals.
tput bold
line="$(tput setaf 3)${line}"
space=${line//-/ }
echo " ${line}"
printf '|' ; echo -n "$space" ; printf "%s\n" '|';
printf '| ' ;tput setaf 4; echo -n "$@"; tput setaf 3 ; printf "%s\n" ' |';
printf '|' ; echo -n "$space" ; printf "%s\n" '|';
echo " ${line}"
tput sgr 0
}
box_out $@
あなたのシバンと構文が移植できないbash
を示しているので、私はそれをこのように好みます:
function box_out()
{
local s="$*"
tput setaf 3
echo " -${s//?/-}-
| ${s//?/ } |
| $(tput setaf 4)$s$(tput setaf 3) |
| ${s//?/ } |
-${s//?/-}-"
tput sgr 0
}
もちろん、必要に応じて最適化できます。
pdateコメントで要求されているとおり、複数行のテキストも処理します。
function box_out()
{
local s=("$@") b w
for l in "${s[@]}"; do
((w<${#l})) && { b="$l"; w="${#l}"; }
done
tput setaf 3
echo " -${b//?/-}-
| ${b//?/ } |"
for l in "${s[@]}"; do
printf '| %s%*s%s |\n' "$(tput setaf 4)" "-$w" "$l" "$(tput setaf 3)"
done
echo "| ${b//?/ } |
-${b//?/-}-"
tput sgr 0
}
box_out 'first line' 'more line' 'even more line'
のような複数のパラメーターで呼び出します。
だから、私の解決策はquiteと同じではありませんが、厳密に言えば、テキストの周りにボックスを印刷し、実装は少し簡単なので、共有したいと思いました。
banner() {
msg="# $* #"
Edge=$(echo "$msg" | sed 's/./#/g')
echo "$Edge"
echo "$msg"
echo "$Edge"
}
そしてここでそれは動作しています:
$ banner "hi"
######
# hi #
######
$ banner "hi there"
############
# hi there #
############
プレーンテキストだけで、派手なANSIカラーなどはありません。
_$ echo 'Love Unix & Linux' | boxes -d stone -p a2v1
+---------------------+
| |
| Love Unix & Linux |
| |
+---------------------+
_
boxes
ではテキストをファイルとして送信する必要があるため、テキストをboxes
からecho
にパイプする上記の例の構文を使用することをお勧めします。
boxes
?」使い方は簡単です。使用したいボーダーデザインとその表示方法を伝えれば完了です。
もちろん、クリエイティブになりたい場合は、独自のデザインを作成できます。それは本当に簡単で楽しいことです。 boxes
を使用する唯一の欠点は、boxes
で生成されたボックスを中央に配置して画面の中央に配置する方法を理解していないことですが、bashハックがあります。
元の質問は、カラーコードの使用を示していました。したがって、boxes
がこれをどのように処理するかを示すのは正しいように思えます。
tput
は人気がありますが、私は古い学校のBashの人であり、エスケープコマンドを使用するのが好きです。 StackExchangeには反対意見を言う人もいるでしょうが、それぞれが独自のものです。とにかく、私はこれを行う個人的な好みを別にして、tput
方法で行う別の例を含めます。
当然、最初のステップは、内部のテキストの色を設定することだと思います。最初にそれをしましょう。
_printf "$(tput setaf 4)Love Unix & Linux$(tput sgr 0)" | boxes -d stone -p a2v1
+---------------------------------+
| |
| Love Unix & Linux |
| |
+---------------------------------+
_
これがターミナルにある場合、_Love Unix & Linux
_は青になります...しかし、ご覧のとおり、boxes
はこれをうまく処理できませんでした。では、何が悪いのでしょうか?
_printf "$(tput setaf 4)Love Unix & Linux$(tput sgr 0)" | boxes -d stone -p a2v1 | cat -A
+---------------------------------+$
| |$
| ^[[34mLove Unix & Linux^[(B^[[0m |$
| |$
+---------------------------------+$
_
_cat -A
_を使用して隠し文字を表示することにより、さらに詳しく調べると、boxes
はボックスの長さとしてテキストの長さとエスケープ文字を含むと想定されています。
ただし、lolcat
の- boxes
outsideのようなプログラムを使用すると、出力は次のようになります。このような
_$ echo 'Love Unix & Linux' | boxes -d stone -p a2v1 | lolcat -f
+---------------------+
| |
| Love Unix & Linux |
| |
+---------------------+
_
ただし、ボックスとテキストはレインボーカラーで表示されます。
ボーダーのデザインが同じ問題に陥る可能性があると想像するので、カラーコードを含む独自のボーダーデザインをまだ作成していなかったのは良いことです。
理解した。boxes
のもう1つの欠点は、Bashを使用してテキストを端末の中央に配置する方法を知っている場合でも、boxes
がボックスを画面の左側に揃えることです。
ボックス内にないテキストを中央揃えにしたい場合は、簡単に使用できます
_center(){
COLS=$(tput cols) # use the current width of the terminal.
printf "%*s\n" "$(((${#1}+${COLS})/2))" "$1"
}
_
それを使用して、1行のテキストを中央揃えにします。
_center 'Love Unix & Linux'
_
複数の線が使用され、定位置に固定する必要があるASCIIアートの場合、このオプションがあります。
_# Rather than removing text, even things out by padding lines with spaces
draw_banner(){
local banner="$1"
# Banner Width
BW=$(cat $banner | awk '{print length}' | sort -nr | head -1)
while IFS= read -r line; do
line=$(echo "${line}" | sed -n -e 's/^ / /g;p')
line=$(printf "%-${BW}s" "${line}")
center "${line}" # our center function from earlier.
done < "$banner"
}
draw_banner "path/to/your_ascii_art_logo.txt"
_
ただし、figlet
などを使用する場合は、_-c
_オプションが中央揃えのオプションを提供するため、これらの関数を使用する必要はありません。
_$figfontdir="path/to/figlet/fonts"
$figfont="Alligator"
text_banner(){
COLS=$(tput cols) # use the width of the terminal!
figlet -d "$figfontdir" -f "$figfont" -k -w $COLS -c "$1"
}
text_banner 'Love Unix & Linux'
_
boxes
の場合、draw_banner()
と同様の処理を行いますが、データをパイプ処理する必要があります。
_# Center a box created with `boxes
# It's like draw_banner, but `<<<` reads a string of data rather than a file.
$boxfile="/path/to/your_box_designs.box" # or ".txt". I like ".box".
$boxdesgin="stone"
center_box(){
local data="$(</dev/stdin)" # Read from standard input
# Banner Width
BW=$(cat <<< ${data} | awk '{print length}' | sort -nr | head -1)
while IFS= read -r line; do
line=$(echo "${line}" | sed -n -e 's/^ / /g;p')
line=$(printf "%-${BW}s" "${line}")
center "${line}" # our center command from earlier.
done <<< "${data}"
}
(
# A bunch of stuff to center!
) | boxes -f $boxfile -d $boxdesign -a hcvcjc | center_box
_
修正 これらの問題の両方 UTF/ANSI文字の問題は、boxes
をASCIIボックスにテキストをカプセル化するためのより良いソリューションにするだけでなく、手ではなく呼び出すことができる創造的な代替案を可能にします-コーディングボックス。