linux - 历史 - 控制屏幕在原地滚动文本(向上箭头 -> 循环原地/相同位置的命令)

标签 linux bash history implementation

当您滚动历史记录时,文本会根据提示发生变化。我已经查看了所涉及的结构,但没有深入研究源代码以找出它如何更改屏幕上的文本而不更改其上方的所有文本(提示,已打印出的过去文本。)

它不能只清除屏幕并在提示后仅进行微小更改就重新打印所有内容——那样效率太低了。他们是怎么做到的?

这听起来可能真的很愚蠢,但我尝试打印一个退格字符,这会导致将光标移动到提示中,当您在其中键入它时,它只会写在提示的顶部。

我只是想不通他们是如何打印出文本并更改它或在适当的位置循环显示文本的。

如果有人知道这是如何完成的,我将不胜感激。

谢谢

最佳答案

bash 使用 GNU readline library去做这个。它最终是 terminfo 库(来自 System V 或 ncurses library )的包装器,其目的是使用终端描述来确定如何进行这些更新。如果终端类型未知或声明不正确,您会注意到您要么以垃圾结束,要么所有漂亮的就地更新都消失了。

终端描述看起来像

xterm-color|nxterm|generic color xterm,
        am, km, mir, msgr, xenl,
        colors#8, cols#80, it#8, lines#24, ncv@, pairs#64,
        acsc=``aaffggiijjkkllmmnnooppqqrrssttuuvvwwxxyyzz{{||}}~~,
        bel=^G, bold=\E[1m, clear=\E[H\E[2J, cr=^M,
        csr=\E[%i%p1%d;%p2%dr, cub=\E[%p1%dD, cub1=^H,
        cud=\E[%p1%dB, cud1=^J, cuf=\E[%p1%dC, cuf1=\E[C,
        cup=\E[%i%p1%d;%p2%dH, cuu=\E[%p1%dA, cuu1=\E[A,
        dch=\E[%p1%dP, dch1=\E[P, dl=\E[%p1%dM, dl1=\E[M, ed=\E[J,
        el=\E[K, enacs=\E)0, home=\E[H, ht=^I, hts=\EH, il=\E[%p1%dL,
        il1=\E[L, ind=^J,
        is2=\E[m\E[?7h\E[4l\E>\E7\E[r\E[?1;3;4;6l\E8, kbs=^H,
        kcub1=\EOD, kcud1=\EOB, kcuf1=\EOC, kcuu1=\EOA,
        kdch1=\E[3~, kf1=\E[11~, kf10=\E[21~, kf11=\E[23~,
        kf12=\E[24~, kf13=\E[25~, kf14=\E[26~, kf15=\E[28~,
        kf16=\E[29~, kf17=\E[31~, kf18=\E[32~, kf19=\E[33~,
        kf2=\E[12~, kf20=\E[34~, kf3=\E[13~, kf4=\E[14~,
        kf5=\E[15~, kf6=\E[17~, kf7=\E[18~, kf8=\E[19~, kf9=\E[20~,
        kfnd=\E[1~, kich1=\E[2~, kmous=\E[M, knp=\E[6~, kpp=\E[5~,
        kslt=\E[4~, meml=\El, memu=\Em, op=\E[m, rc=\E8, rev=\E[7m,
        ri=\EM, rmacs=^O, rmcup=\E[2J\E[?47l\E8, rmir=\E[4l,
        rmkx=\E[?1l\E>, rmso=\E[m, rmul=\E[m,
        rs2=\E[m\E[?7h\E[4l\E>\E7\E[r\E[?1;3;4;6l\E8, sc=\E7,
        setab=\E[4%p1%dm, setaf=\E[3%p1%dm, sgr0=\E[m, smacs=^N,
        smcup=\E7\E[?47h, smir=\E[4h, smkx=\E[?1h\E=, smso=\E[7m,
        smul=\E[4m, tbc=\E[3g, u6=\E[%i%d;%dR, u7=\E[6n,
        u8=\E[?1;2c, u9=\E[c,

并描述了如何进行各种屏幕更新,有哪些功能键和 Action 键可用以及它们发送什么,以及特殊的终端行为(画线字符、颜色和其他高亮形式,是否可以在中间插入字符)一条线等)。通常,您不需要了解它,除非设置有误或您正在使用高级终端黑客技术。 (如果您确实想理解它,请从 terminfo(5) 和其他 curses/ncurses 开始/terminfo 文档。如果不出意外,您将学习如何制作真正精美的 shell 提示符。)

关于linux - 历史 - 控制屏幕在原地滚动文本(向上箭头 -> 循环原地/相同位置的命令),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5527264/

相关文章:

windows - Windows ANSI Western (cp 1252) 首先出现在哪个 Windows 版本中?

linux - 在 bash 脚本中循环执行命令时,如何将来自 cURL 的响应主体保存在文件中?

bash - 将 bash while 循环限制为 10 次重试

.net - 如何在 Linux 上转储 .NET Core 应用程序

python - 如何在 python + linux 中监听端口并行

c++ - Debian 上的线程用完

terminal - 进程接收 SIGTTYIN/TTOU 而不是阻塞的历史原因是什么?

Linux 重命名带有时间戳的文件

linux - 如何使用 sed 命令将数字更改为字母?