カラーバッシュプロンプトのラッピングを修正するにはどうすればいいですか?

カラーバッシュプロンプトのラッピングを修正するにはどうすればいいですか?

私は次のように bash プロンプト (PROMPT_FUNCTION を使用) を定義しました。

function get_hg_prompt_prefix() {
    local APPLIED_COLOR=$1; shift
    local UNAPPLIED_COLOR=$1; shift
    local ALERT_COLOUR=$1; shift
    local TEXTCOLOR=$1; shift
    local mercurial_prompt_line="{{patches|join(:)|pre_applied(${APPLIED_COLOR})|post_applied(${TEXTCOLOR})|pre_unapplied(${UNAPPLIED_COLOR})|post_unapplied(${TEXTCOLOR})}\n\r}"
    local mercurial_status_prompt="{ ${ALERT_COLOUR}{status}${TEXTCOLOR}}"

    echo "$(hg prompt "${mercurial_prompt_line}" 2>/dev/null)$(hg prompt "${mercurial_status_prompt}" 2>/dev/null)"
}

function set_prompt() {
    bright='\[[01m\]'
    colors_reset='\[[00m\]'
    HOSTCOLOR=${colors_reset}='\[[34m\]'
    USERCOLOR=${colors_reset}='\[[01m\]'
    TEXTCOLOR=${colors_reset}='\[[32m\]'
    APPLIED_COLOR=${colors_reset}='\[[32m\]'
    UNAPPLIED_COLOR=${colors_reset}='\[[37m\]'
    ALERT_COLOUR=${colors_reset}='\[[31m\]'

    hg_status="$(get_hg_prompt_prefix $APPLIED_COLOR $UNAPPLIED_COLOR $ALERT_COLOUR $TEXTCOLOR)"
    ps1_prefix="${hg_status}$colors_reset($bright$(basename $VIRTUAL_ENV)$colors_reset) "
    PROMPTEND='$'
    PS1="${ps1_prefix}${USERCOLOR}\u${colors_reset}${TEXTCOLOR}@${colors_reset}${HOSTCOLOR}\h${colors_reset}${TEXTCOLOR} (\W) ${PROMPTEND}${colors_reset} "
}

PROMPT_COMMAND=set_prompt

通常、これにより、hg ステータス情報と現在の仮想環境を表示する複数行のプロンプトが表示されます (色なし)。

buggy-wins.patch
 ! (saas) user@computer (~) $ 

問題は、これがプロンプトの長さの計算を台無しにし (そう思います!)、ターミナルの折り返しの問題やカーソルの配置がおかしくなることです。たとえば、80 文字のターミナルでは、次のようなプロンプトが表示されます (** で囲まれた文字はカーソルの位置です)。

~) $ **a**nis) crose@chris-rose (~

プロンプトを表示できるほど広い端末では、行の折り返しは本来よりもずっと早く行われます。ここに、私がこの端末に収めることができる最大のテキストを示します。初め108 文字幅のターミナル ウィンドウのプロンプトの行 (ここでも、** はカーソルの位置を示します)。

 **(**advanis) crose@chris-rose (~) $ sdkfjlskdjflksdjff

行が折り返されると、プロンプトが上書きされます。ただし、入力の 2 行目は端末の端まで達し、その後正しく折り返されます。

つまり、プロンプトの幅に何か問題があることは明らかです。PS1 文字列の長さを ANSI エスケープ コードではなく、プロンプトの実際の表示長さに基づいて bash に決定させるにはどうすればよいですか?

答え1

bashは「表示される長さ」を決定するために使用します\[ \]。これら 2 つのエスケープ文字の間にあるテキストは印刷不可能とみなされ、合計の長さにはカウントされません。それ以外はすべてカウントされます。

変数に問題があるようです:bright='\[[01m\]'実際には ESC 文字が含まれていないため、[01m通常のテキストとして印刷されますが、長さにはカウントされません。 である必要があります'\[\e[01m\]'。他のすべての変数についても同様です。


関連している:

  • Bash では、別個の を必要とせずに を直接 に\$(hg_status)配置できます。$PS1PROMPT_COMMAND

関連情報