繁体   English   中英

如何在C中实现终端中的擦除输出?

[英]How is erasing output in terminal implemented in C?

终端中运行的某些应用程序可以擦除其输出。 例如,当它告诉您等待时,它将显示不同长度之间交替的一系列点。

如何在C中实现终端中的擦除输出? 是通过反向换行完成的吗?

程序只能删除当前行中的前一个字符,而不是stdout中前一行中的字符吗?

谢谢。

这取决于终端。

Windows上的COMSPEC shell(通常称为DOS提示符或command.com)在C中公开API以控制游标。 我没有做任何Windows编程,所以我不能告诉你太多。

大多数其他终端(特别是在unixen上)模拟类似于VT100串行终端的协议(VT100终端是物理设备,监视器和键盘,您连接到调制解调器或串行端口以与服务器通信)。

在VT100终端上,回车和换行是单独的命令,都是一个字节。 回车命令将光标设置为行的开头。 换行命令将光标向下移动一行(但不会将光标自身带到行的开头)。 unixen上的大多数shell会在换行后自动插入回车符,但在回车后几乎不会插入换行符。

有了这些知识,最简单的实现是简单地输出一个回车并重新打印整行:

printf("\rprogress: %d percent  ", x);

注意该行末尾的额外空格。 打印"\\r"不会删除该行,因此在旧行上重新打印可能会在屏幕上留下一些旧字符串。 额外的空格用于尝试和擦除旧行的其余部分。

如果您使用Google搜索“VT100 escape secquence” ,您将找到允许您执行的操作,例如擦除当前行,更改文本颜色,转到屏幕上的特定行/列等.VT100序列最常用的用途是输出彩色文字。 但你也可以用它们做其他事情。

下一个最简单的实现是干净地删除该行并重新打印它:

printf("\033[2K\rprogress: %d percent", x);

\\033[2K是删除当前行的转义序列(ESC [2K])。

如果您愿意,可以从这里获得更多创意。 您可以使用cursor save / restore命令和erase to line of line命令仅擦除要更新的部分(而不是整行)。 您可以使用goto命令将光标放在屏幕上的特定位置以更新文本等。

应该注意的是,更先进的东西,如VT102序列或一些完整的ANSI转义序列通常不能在终端上移植(通过终端我不是指shell,我的意思是终端:rxvt,xterm,linux终端,超级终端(在Windows上)等)。

如果您想要可移植性(和/或理智的API),您应该使用curses或ncurses库。

如果你想知道它是如何完成的,那就是它的完成方式。 它只是将特殊格式的字符串打印到屏幕上(COMSPEC shell除外)。 有点像HTML但是老派。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM