
答案1
這裡要注意的重要一點是問題的標籤。此行為特定於 GNOME 終端機和基於 libvte 建構的任何其他終端模擬器。您不會在 Xterm、Unicode RXVT、Linux 核心內建的終端模擬器或 FreeBSD 控制台中看到這一點。
一般發生的情況是這樣的。
- 該
clear
指令查看 terminfo/termcap 並發出適當的控制序列。- 如果 terminfo/termcap 條目具有
E3
此功能,它會先寫出該功能。這會發出控制序列來清除回滾緩衝區。這及其背後的歷史詳細記錄在clear
該指令的 Dickey ncurses 手冊頁。 - 然後它使用
clear
清除可見螢幕的功能。
- 如果 terminfo/termcap 條目具有
- terminfo/termcap條目中的控制序列由終端類型決定;但是,除了使用 FormFeed 清除螢幕的終端(現在很少見)(DEC VT 及其模仿者不這樣做)之外,它們要么只是普通的舊 ECMA-48 控制序列,要么是其擴展。舉些例子:
putty
入口定義E3=\E[3J
Xterm 擴充控制序列。- NetBSD 控制台的
pcvtxx
入口clear=\E[H\E[J
是許多定義或類似內容之一。這是兩個普通的 ECMA-48 控制序列。
- 終端仿真器根據控制序列進行操作。根據 ECMA-48 及其 Xterm 擴充的定義:
- CSI
H
(CUP) 將遊標歸位。 - CSI
0
J
(ED 0) 或僅 CSIJ
從目前遊標位置擦除到螢幕末端。 - CSI
2
J
(ED 2) 擦除整個螢幕。 - CSI
3
J
(ED 3) 擦除回溯緩衝區。
- CSI
特別是對於 GNOME 終端機:
- 終端類型是正確的
gnome
,但有些人錯誤地將其設定為xterm
。 - terminfo
gnome
條目沒有定義E3
功能,並且在許多系統上仍然如此! - 該條目也沒有,xterm
因為這還沒有從迪基術語訊息。所以clear
只寫出clear
能力的內容。 - 這些 terminfo 條目的功能內容
clear
是使遊標歸位然後擦除整個螢幕的控制序列。 - 但 GNOME 終端機無法正確執行擦除整個螢幕。 更具體地說,它所基於的庫 libvte 在程式碼中並沒有這樣做它的
VteTerminalPrivate::seq_clear_screen()
功能。相反,libvte 將螢幕向下捲動整個螢幕的空白行,並將遊標位置移到這些空白行中的第一行。
這就是為什麼你會看到你所看到的。當被告知時,libvte 不會擦除整個螢幕。相反,它正在做一些表面上與此相似的事情,直到有人完全按照提問者在這裡所做的那樣:向後滾動終端視窗以查看向後滾動緩衝區。那麼差別就很明顯了。
在其他終端模擬器(例如 Xterm 和 Unicode RXVT)上,ED 2 控制序列確實會擦除螢幕,從上到下擦除螢幕上的每個位置,並且不會更改回滾緩衝區。但在 libvte 終端模擬器上,它只是將當前螢幕推入回滾緩衝區並添加一個螢幕的空白行。先前的螢幕內容不會被刪除,而是移入回滾緩衝區。
如果您運行該clear
命令兩次,它會添加二螢幕上的空白行。如果你的回滾緩衝區夠大,你可以仍然找到原始螢幕內容,只需在回滾緩衝區中進一步找到即可。
進一步閱讀
- 編碼字符集的控制函數。 ECMA-48。 1976年。
- 格奧爾基·基里洛夫 (2007-12-30)。Ctrl-L 將空白區域加入回滾緩衝區。 GNOME 錯誤#506438。
- xterm、xterm-color 和 linux 終端模擬器在多大程度上是基於 VT100?
- 清除“舊”回滾緩衝區
- Bash clear 指令奇怪的行為會刪除回滾緩衝區。
- https://superuser.com/questions/1094599/
- 托馬斯·迪基 (2018)。 」XTerm 和類似程式中的已知錯誤:GNOME 終端」。 XTerm 常見問題解答。隱形島.net。
- 托馬斯·迪基 (2018)。 」XTerm 和 Look-alikes 中的已知錯誤:VTE 註釋」。 XTerm 常見問題解答。隱形島.net。
答案2
如果您想清除終端並銷毀整個輸出緩衝區,我建議您這樣做tput reset
。如果例如任何先前的程式崩潰並使終端處於不乾淨的狀態,這肯定會清除終端並修復其狀態作為獎勵。此外,它tput
應該足夠聰明,能夠確定正確的終端類型,因此您不需要知道您的終端是否使用 VT100 或其他命令序列。
正如tput reset
POSIX 所定義的,它也應該在任何 POSIX 相容系統中運作:https://pubs.opengroup.org/onlinepubs/007904975/utilities/tput.html