如果整个 PROMPT 太长,则提示扩展 ZSH 删除主机名
Prompt Expansion ZSH Remove Hostname if entire PROMPT is too long
目前,我的 zshrc
看起来像这样
setopt prompt_subst # real time reevaluation of prompt
zmodload zsh/mathfunc # int function
function widthHelper() { echo $(( int(${COLUMNS:-80}) * /100)) } # calc % of prompt
outWidth='$(widthHelper 40)'
inWidth='$(widthHelper 90)'
export PROMPT="%F{cyan}%${outWidth}<◀︎<%f" # truncation based on terminal width
PROMPT+="%(l." # inner truncation group
PROMPT+="%F{cyan}%8>‣>%n%>>%f" # username truncated
PROMPT+="%-${inWidth}(l. %F{blue}%5>‣>%m%>>%f.) " # hostname truncated
PROMPT+=".)" # end truncation
PROMPT+="%F{magenta}%1~%f%<< " # pwd 1 depth
PROMPT+="%# " # privilege group
influenced by this question
和
my other question
当前按预期工作的内容
- 它将主机名和用户名截断为常量值
- 它根据
widthHelper()
动态截断整个 PROMPT,这允许我调整终端大小并动态截断 PROMPT
目前,我有这条线在工作,但不是以我想要的方式工作
PROMPT+="%-${inWidth}(l. %F{blue}%5>‣>%m%>>%f.) " # hostname truncated
我想要的
我想让主机名的显示取决于整个PROMPT
的长度,而不是在当前终端的宽度上COLUMNS
.
即如果我输入一个名称很长的目录,我希望主机名消失 before 我开始截断整个提示。但我确实希望两者都发生 按此顺序
- 主机名会消失(这种情况发生但不依赖于
PROMPT
长度,而是依赖于整个终端的宽度,COLUMNS
)
- 整个提示将开始在左侧截断(目前有效)
例子
如果我在一个目录中 ~
然后移动到一个名称很长的目录 ~/abcdefghijklmnopqrstuvwxyzabcd
我希望主机名消失,但是发生的事情是我的提示首先被截断了。
william‣ wmbp‣ ~ %
william‣ wmbp‣ ~ % cd abcdefghijklmnopqrstuvwxyzabcd
◀︎m‣ wmbp‣ abcdefghijklmnopqrstuvwxyzabcd %
我想要的
william‣ wmbp‣ ~ %
william‣ wmbp‣ ~ % cd abcdefghijklmnopqrstuvwxyzabcd
william‣ abcdefghijklmnopqrstuvwxyzabcd %
如果我可以使 # hostname truncated
行取决于 PROMPT
长度,那么我就可以解决这个问题。
tldr
如何根据当前 PROMPT
的长度删除部分 PROMPT
。
好的,所以我解决了我自己的问题,但首先我不得不说这个问题是有缺陷的,因为我将提示的长度控制在终端的固定百分比 window 上。所以,我不能指望提示会这样做
william‣ wmbp‣ ~ %
william‣ wmbp‣ ~ % cd abcdefghijklmnopqrstuvwxyzabcd
william‣ abcdefghijklmnopqrstuvwxyzabcd %
但我能做的就是期待终端这样做
william‣ wmbp‣ Desktop %
william‣ wmbp‣ Desktop % cd abcdefghijk
william‣ abcdefghijk %
因为 %
从一行到下一行对齐。
我得到这个解决方案的方法是在我的 zshrc
中使用它
LENGTH_OF_USERNAME=8
LENGTH_OF_HOSTNAME=5
# calc % of prompt
function termWidthPercentHelper() { echo $(( int(${COLUMNS:-80}) * /100)) }
function hostNameInPromptHelper() {
# if you are in the home directory or if you are in a directory with a name
# that has a length which is less than % of the terminal's width
if [[ ${PWD##*/} == ${HOME##*/} ]] || [[ ${#PWD##*/} -lt $(termWidthPercentHelper ) ]] then
echo "%F{blue}%${LENGTH_OF_HOSTNAME}>‣>%m%>>%f "
fi
}
PROMPT_PERCENTAGE='$(termWidthPercentHelper 30)'
HOST_NAME_IN_PROMPT='$(hostNameInPromptHelper 9)'
# left prompt
export PROMPT="%F{cyan}%${PROMPT_PERCENTAGE}<◀︎<%f" # truncation based on terminal width
PROMPT+='%(l.' # inner truncation group
PROMPT+="%F{cyan}%${LENGTH_OF_USERNAME}>‣>%n%>>%f " # username truncated
PROMPT+="${HOST_NAME_IN_PROMPT}"
PROMPT+='.)' # end truncation
PROMPT+='%F{magenta}%1~%f%<< ' # pwd 1 depth
PROMPT+='%# ' # privilege group
我用函数调用 PROMPT+="${HOST_NAME_IN_PROMPT}"
替换了旧行 PROMPT+="%-${inWidth}(l. %F{blue}%5>‣>%m%>>%f.) " # hostname truncated
。这样我就可以检查当前目录的长度,然后显示 主机名 或者如果当前目录太长则不显示主机名。
帮助我找到这个解决方案的事情
[[ ${PWD##*/} == ${HOME##*/} ]]
returns 如果您在主目录中则为真
${#PWD##*/}
gives the length of the present working directory without calling a subprocess
结论
如果我想将整个提示保留在我的终端屏幕的某个百分比,如之前命名的 widthHelper
函数调用中所示,我想做的事情是不可能的。
如果我输入一个名称很长的目录(请参阅上面 hostNameInPromptHelper
的定义),我的终端将无法显示我的 PROMPT
的一部分。我还调整了提示的屏幕百分比值(即 PROMPT_PERCENTAGE='$(termWidthPercentHelper 30)'
)和在我不显示之前目录名称的长度可以占用我的屏幕百分比的值主机名(即 HOST_NAME_IN_PROMPT='$(hostNameInPromptHelper 9)'
)。这些值对我有用,但如果您可能想调整这些值直到您喜欢您的提示。
来源
- https://zsh.sourceforge.io/Doc/Release/Conditional-Expressions.html
- Get current directory name (without full path) in a Bash script
- https://zsh.sourceforge.io/Doc/Release/Prompt-Expansion.html#Prompt-Expansion
- https://linuxhint.com/length_of_string_bash/
目前,我的 zshrc
看起来像这样
setopt prompt_subst # real time reevaluation of prompt
zmodload zsh/mathfunc # int function
function widthHelper() { echo $(( int(${COLUMNS:-80}) * /100)) } # calc % of prompt
outWidth='$(widthHelper 40)'
inWidth='$(widthHelper 90)'
export PROMPT="%F{cyan}%${outWidth}<◀︎<%f" # truncation based on terminal width
PROMPT+="%(l." # inner truncation group
PROMPT+="%F{cyan}%8>‣>%n%>>%f" # username truncated
PROMPT+="%-${inWidth}(l. %F{blue}%5>‣>%m%>>%f.) " # hostname truncated
PROMPT+=".)" # end truncation
PROMPT+="%F{magenta}%1~%f%<< " # pwd 1 depth
PROMPT+="%# " # privilege group
influenced by this question 和 my other question
当前按预期工作的内容
- 它将主机名和用户名截断为常量值
- 它根据
widthHelper()
动态截断整个 PROMPT,这允许我调整终端大小并动态截断 PROMPT
目前,我有这条线在工作,但不是以我想要的方式工作
PROMPT+="%-${inWidth}(l. %F{blue}%5>‣>%m%>>%f.) " # hostname truncated
我想要的
我想让主机名的显示取决于整个PROMPT
的长度,而不是在当前终端的宽度上COLUMNS
.
即如果我输入一个名称很长的目录,我希望主机名消失 before 我开始截断整个提示。但我确实希望两者都发生 按此顺序
- 主机名会消失(这种情况发生但不依赖于
PROMPT
长度,而是依赖于整个终端的宽度,COLUMNS
) - 整个提示将开始在左侧截断(目前有效)
例子
如果我在一个目录中 ~
然后移动到一个名称很长的目录 ~/abcdefghijklmnopqrstuvwxyzabcd
我希望主机名消失,但是发生的事情是我的提示首先被截断了。
william‣ wmbp‣ ~ %
william‣ wmbp‣ ~ % cd abcdefghijklmnopqrstuvwxyzabcd
◀︎m‣ wmbp‣ abcdefghijklmnopqrstuvwxyzabcd %
我想要的
william‣ wmbp‣ ~ %
william‣ wmbp‣ ~ % cd abcdefghijklmnopqrstuvwxyzabcd
william‣ abcdefghijklmnopqrstuvwxyzabcd %
如果我可以使 # hostname truncated
行取决于 PROMPT
长度,那么我就可以解决这个问题。
tldr
如何根据当前 PROMPT
的长度删除部分 PROMPT
。
好的,所以我解决了我自己的问题,但首先我不得不说这个问题是有缺陷的,因为我将提示的长度控制在终端的固定百分比 window 上。所以,我不能指望提示会这样做
william‣ wmbp‣ ~ %
william‣ wmbp‣ ~ % cd abcdefghijklmnopqrstuvwxyzabcd
william‣ abcdefghijklmnopqrstuvwxyzabcd %
但我能做的就是期待终端这样做
william‣ wmbp‣ Desktop %
william‣ wmbp‣ Desktop % cd abcdefghijk
william‣ abcdefghijk %
因为 %
从一行到下一行对齐。
我得到这个解决方案的方法是在我的 zshrc
LENGTH_OF_USERNAME=8
LENGTH_OF_HOSTNAME=5
# calc % of prompt
function termWidthPercentHelper() { echo $(( int(${COLUMNS:-80}) * /100)) }
function hostNameInPromptHelper() {
# if you are in the home directory or if you are in a directory with a name
# that has a length which is less than % of the terminal's width
if [[ ${PWD##*/} == ${HOME##*/} ]] || [[ ${#PWD##*/} -lt $(termWidthPercentHelper ) ]] then
echo "%F{blue}%${LENGTH_OF_HOSTNAME}>‣>%m%>>%f "
fi
}
PROMPT_PERCENTAGE='$(termWidthPercentHelper 30)'
HOST_NAME_IN_PROMPT='$(hostNameInPromptHelper 9)'
# left prompt
export PROMPT="%F{cyan}%${PROMPT_PERCENTAGE}<◀︎<%f" # truncation based on terminal width
PROMPT+='%(l.' # inner truncation group
PROMPT+="%F{cyan}%${LENGTH_OF_USERNAME}>‣>%n%>>%f " # username truncated
PROMPT+="${HOST_NAME_IN_PROMPT}"
PROMPT+='.)' # end truncation
PROMPT+='%F{magenta}%1~%f%<< ' # pwd 1 depth
PROMPT+='%# ' # privilege group
我用函数调用 PROMPT+="${HOST_NAME_IN_PROMPT}"
替换了旧行 PROMPT+="%-${inWidth}(l. %F{blue}%5>‣>%m%>>%f.) " # hostname truncated
。这样我就可以检查当前目录的长度,然后显示 主机名 或者如果当前目录太长则不显示主机名。
帮助我找到这个解决方案的事情
[[ ${PWD##*/} == ${HOME##*/} ]]
returns 如果您在主目录中则为真${#PWD##*/}
gives the length of the present working directory without calling a subprocess
结论
如果我想将整个提示保留在我的终端屏幕的某个百分比,如之前命名的 widthHelper
函数调用中所示,我想做的事情是不可能的。
如果我输入一个名称很长的目录(请参阅上面 hostNameInPromptHelper
的定义),我的终端将无法显示我的 PROMPT
的一部分。我还调整了提示的屏幕百分比值(即 PROMPT_PERCENTAGE='$(termWidthPercentHelper 30)'
)和在我不显示之前目录名称的长度可以占用我的屏幕百分比的值主机名(即 HOST_NAME_IN_PROMPT='$(hostNameInPromptHelper 9)'
)。这些值对我有用,但如果您可能想调整这些值直到您喜欢您的提示。
来源
- https://zsh.sourceforge.io/Doc/Release/Conditional-Expressions.html
- Get current directory name (without full path) in a Bash script
- https://zsh.sourceforge.io/Doc/Release/Prompt-Expansion.html#Prompt-Expansion
- https://linuxhint.com/length_of_string_bash/