[英]How can I make my terminal prompt extend the width of the terminal?
I noticed in this video , that the terminal prompt extends the entire width of the terminal before breaking down to a new line. 我注意到在这个视频中 ,终端提示在扩展到新行之前扩展了终端的整个宽度。 How can I set my
PS1
variable to fill the remaining terminal space with some character, like the way this user did? 如何设置我的
PS1
变量以用一些字符填充剩余的终端空间,就像这个用户的方式一样?
The issue is, I don't know how to update the PS1
variable per command. 问题是,我不知道如何更新每个命令的
PS1
变量。 It seems to me, that the string value for PS1
is only read in once just as the .bashrc
file is only read in once. 在我看来,
PS1
的字符串值只读入一次,就像.bashrc
文件只读入一次一样。 Do I have to write some kind of hook after each command or something? 在每个命令之后我是否必须编写某种钩子?
I should also point out, that the PS1
variable will be evaluated to a different length based on the escape characters that make up it. 我还应该指出,
PS1
变量将根据构成它的转义字符计算到不同的长度。 For example, \\w
print the path. 例如,
\\w
打印路径。
I know I can get the terminal width using $(COLUMNS)
, and the width of the current PS1
variable with ${#PS1}
, do the math, and print the right amount of buffer characters, but how do I get it to update everytime. 我知道我可以使用
$(COLUMNS)
获取终端宽度,并使用${#PS1}
获取当前PS1
变量的宽度,进行数学计算,并打印适量的缓冲区字符,但是如何让它更新每次。 Is there a preferred way? 有首选方式吗?
Let's suppose you want your prompt to look something like this: 假设您希望您的提示看起来像这样:
left text----------------------------------------------------------right text
prompt$
This is pretty straight-forward provided that right text
has a known size. 如果
right text
具有已知大小,这是非常简单的。 (For example, it might be the current date and time.) What we do is to print the right number of dashes (or, for utf-8 terminals, the prettier \─
), followed by right text
, then a carriage return ( \\r
, not a newline) and the left text, which will overwrite the dashes. (例如,它可能是当前的日期和时间。)我们所做的是打印正确数量的破折号(或者,对于utf-8终端,更漂亮的
\─
),然后是right text
,然后是回车符( \\r
, 不是换行符)和左侧文本,它将覆盖破折号。 The only tricky bit is "the right number of dashes", but we can use $(tput cols)
to see how wide the terminal is, and fortunately bash
will command-expand PS1
. 唯一棘手的问题是“正确的破折号”,但我们可以使用
$(tput cols)
来查看终端的宽度,幸运的是bash
将命令扩展PS1
。 So, for example: 所以,例如:
PS1='\[$(printf "%*s" $(($(tput cols)-20)) "" | sed "s/ /-/g") \d \t\r\u@\h:\w \]\n\$ '
Here, $(($(tput cols)-20))
is the width of the terminal minus 20, which is based on \\d \\t
being exactly 20 characters wide (including the initial space). 这里,
$(($(tput cols)-20))
是终端的宽度减去20,它基于\\d \\t
正好是20个字符宽(包括初始空间)。
PS1
does not understand utf-8 escapes ( \\uxxxx
), and inserting the appropriate substitution into the sed
command involves an annoying embedded quote issue, although it's possible. PS1
不理解utf-8转义( \\uxxxx
),并且在sed
命令中插入适当的替换涉及恼人的嵌入式引用问题,尽管它是可能的。 However, printf
does understand utf-8 escapes, so it is easier to produce the sequence of dashes in a different way: 但是,
printf
确实理解utf-8转义,因此以不同的方式生成破折号序列更容易:
PS1='\[$(printf "\\u2500%.0s" $(seq 21 $(tput cols))) \d \t\r\u@\h:\w \]\n\$ '
Yet another way to do this involves turning off the terminal's autowrap, which is possible if you are using xterm
or a terminal emulator which implements the same control codes (or the linux console itself). 另一种方法是关闭终端的自动装配,如果您使用
xterm
或实现相同控制代码的终端仿真器(或Linux控制台本身),这是可能的。 To disable autowrap, output the sequence ESC [ ? 要禁用自动换行,输出序列ESC [ ? 7 l .
7 升 To turn it back on, use ESC [ ?
要重新打开,请使用ESC [ ? 7 h .
7 小时 With autowrap disabled, once output reaches the end of a line, the last character will just get overwritten with the next character instead of starting a new line.
禁用自动换行后,一旦输出到达行尾,最后一个字符将被下一个字符覆盖而不是开始换行。 With this technique, it's not really necessary to compute the exact length of the dash sequence;
使用这种技术,没有必要计算短划线序列的确切长度; we just need a string of dashes which is longer than any console will be wide, say the following:
我们只需要一个破折号字符串,比任何控制台都宽,比如说:
DASHES="$(printf '\u2500%0.s' {1..1000})"
PS1='\[\e[?7l\u@\h:\w $DASHES \e[19D \d \t\e[?7h\]\n\$ '
Here, \\e[19D
is the terminal-emulator code for "move cursor backwards 19 characters". 这里,
\\e[19D
是“向后移动19个字符”的终端仿真器代码。 I could have used $(tput cub 19)
instead. 我可以用
$(tput cub 19)
代替。 (There might be a tput
parameter for turning autowrap on and off, but I don't know what it would be.) (可能有一个
tput
参数用于打开和关闭自动装载,但我不知道它会是什么。)
The example in the video also involves inserting a right-aligned string in the actual command line. 视频中的示例还涉及在实际命令行中插入右对齐的字符串。 I don't know any clean way of doing this with
bash
; 我不知道用
bash
做任何干净的方式; the console in the video is almost certainly using zsh
with the RPROMPT
feature. 视频中的控制台几乎肯定会使用带有
RPROMPT
功能的zsh
。 Of course, you can output right-aligned prompts in bash
, using the same technique as above, but readline
won't know anything about them, so as soon as you do something to edit the line, the right prompt will vanish. 当然,您可以使用与上面相同的技术在
bash
输出右对齐提示,但readline
对它们一无所知,因此只要您执行某些操作来编辑该行,右侧提示就会消失。
Use PROMPT_COMMAND
to reset the value of PS1
before each command. 使用
PROMPT_COMMAND
在每个命令之前重置PS1
的值。
PROMPT_COMMAND=set_prompt
set_prompt () {
PS1=...
}
Although some system script (or you yourself) may already use PROMPT_COMMAND
for something, in which case you can simply add to it. 虽然某些系统脚本(或您自己)可能已经使用
PROMPT_COMMAND
,但在这种情况下您只需添加它即可。
PROMPT_COMMAND="$PROMPT_COMMAND; set_prompt"
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.