我正在使用lolcat获得ls颜色的输出。为此,我已将/ usr / bin / ls复制到/ usr / bin / lsslss(以避免死循环,因为别名不能接受$ *或$ @),并且添加了以下功能:
ls(){ lsslss $* | lolcat; }
到.bashrc
问题是,当我使用ls时,管道一次通过管道传输每个文件,因此它显示为如下所示的长列表:
而不是像这样的表:
要将其更改为表,我可以将输出通过管道传递到columns命令。但是当我这样做时,它又变回了一个长长的列表(可能是因为列只格式化了它,而不是将它变成了行)
我本来打算做的:
ls(){ lsslss $* | columns | lolcat; }
无论如何,我想知道是否有一种方法可以通过管道传递原始输出,而不是使用| 能够将列的输出通过管道传输到lolcat?
提前致谢。抱歉,我的问题措辞不当或难以理解。我几乎总是找到已经问过的问题,所以我不会经常发布问题。
扩展@dessert的答案,您需要做更多的工作才能使彩色ls
版本ls
在所有情况下都像真实情况一样(希望吗?)。问题在于,这ls
不是要解析的,而仅是供人眼使用的。为此,它会根据环境(例如是连接到终端还是输出到管道)强烈适应其工作方式。
首先,您不需要单独的/bin/lsslss
可执行文件来避免递归。使用内置的外壳command
程序从磁盘调用可执行文件,而忽略任何外壳程序功能或同名别名。
其次,$*
为您提供所有函数参数作为单个字符串,然后将其进行分词,因为它未加引号。如果您使用带空格的参数,这可能会出乎意料的错误结果。始终使用"$@"
,它会完全保留最初给出的所有参数,而不会串联或进一步拆分。
第三,根据定义的放置位置,ls () { ... ;}
如果函数ls
已经是别名,则定义函数的语法可能不起作用,因为别名会首先发生扩展,从而导致语法错误。通过在显式语法function
之前编写来使用显式语法。
然后,我们可以使用ls
'-C
标志来手动启用列输出:
function ls() { command ls -C "$@" | lolcat ;}
但是,如果我们只是这样做,然后将输出通过管道传输lolcat
(或其他方式),您会注意到它不再使用终端的整个宽度,而最多仅使用80列。这是因为如果不再将其标准输出直接连接到端子上,则无法检测端子宽度。您的外壳程序仍然知道终端,并且COLUMNS
将检测到的宽度填充到变量中。但是,由于默认情况下未导出此变量,因此ls
不会看到该值。我们可以仅为此命令手动传递它,例如:
function ls() { COLUMNS="$COLUMNS" command ls -C "$@" | lolcat ;}
现在,我们应该总是获得正确的宽度,但是如果我们真的想ls
通过其他管道传输,会发生什么呢?通常,您不应该那样做,因为正如我在开始时所说,ls
永远都不应被解析。尽管有时它可能仍然有用(并且某些脚本可能不幸地依赖它),所以让我们至少尝试保留原始行为。现在,我们将始终将这些列作为eg的输出ls | cat
。(那里不再有颜色,因为lolcat
还要检查它是否输出到端子或管道并在后一种情况下关闭颜色)
让我们在函数中添加一个检查,该函数使用纯实数(ls
如果已通过管道传输),并且使用花哨的彩虹列版本(仅用于终端视图)。可以使用以下命令检查标准输出(文件描述符1)是否为终端/ TTY [[ -t 1 ]]
:
function ls() {
if [[ -t 1 ]] ; then COLUMNS="$COLUMNS" command ls -C "$@" | lolcat ; else command ls "$@" ; fi
}
我认为这应该足以应付所有ls
预期会有特殊/不同行为的情况,以便您的函数仅在直接在终端中查看时才添加颜色,否则不会改变任何内容。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句