0

这是代码:

#include <curses.h>
int main() {
  initscr();
  curs_set(2);
  for(int i=0;i<COLS;i++){ //COLS NUMERO MASSIMO DI COLONNE
      mvaddch(0,i,'*');
      mvaddch(LINES-1,i,'*'); //LINES NUMERO MASSIMO RIGHE SE PARTO DALL'ULTIMO RIGA = (LINES -1)
      }
  refresh();
  endwin(); 
  return 0; 
}

一切都很好,但是如果我调整 cygwin 的窗口大小,屏幕就会变空。我有薄荷味的cygwin。

4

2 回答 2

1

该示例具有误导性:

  • 如果 ncurses 由于调整大小而清除了屏幕,那么您将不得不getch阻止程序退出(并捕获KEY_RESIZE),
  • 但是该示例在屏幕上写入了一些字符并退出。

如果您的终端(例如mintty)使用xterm终端描述,它将暂时切换到备用屏幕(写入这些字符的位置),并且在退出 ncurses 时(按照终端描述中的说明)切换回正常屏幕(以及那些字符消失,让您的屏幕空白。

切换到/从备用屏幕的终端功能是smcuprmcup。您可以使用不同的(或修改的)终端描述。或者你可以告诉mintty不要切换到/从备用屏幕。根据其手册页,它可以在设置对话框中执行此操作:

备用屏幕 (NoAltScreen=false)
使用此设置,可以禁用备用屏幕。

手册指出这些设置对应于菜单条目,您可能会发现它比编辑配置文件更简单:

Mintty 还在窗口菜单中添加了几个项目,可以通过单击程序图标或按 Alt+Space 来访问这些项目。

两个菜单都有一个条目,可通向更改 mintty 配置的选项对话框

于 2017-11-18T21:49:12.893 回答
0

ncurses 通过三种方法获取窗口大小:

  • 在支持 TIOCGWINSZ 的终端中ioctl(2),通过调用获取窗口尺寸initscr(3)
  • 通过 terminfo 数据库提供的信息。许多终端类型都有固定的尺寸尺寸,行和列的适当值是从这个数据库中获得的。
  • 通过获取 LINES 和 COLUMNS 环境变量的值。

好吧,bash(1)通常在程序退出时和调用下一个之前将这些环境变量值调整为正确的值,如果这可用于bash(1),但如果您的程序不支持该SIGWINCH信号(或不处理它),很可能是 ncurses库不会知道在程序运行期间窗口大小发生了变化(默认情况下,我没有看到 ncurses 检测到这一点)。即使您在支持它的系统上运行,如果您没有为该信号安装信号处理程序,ncurses 库本身也无法承受窗口尺寸的变化,因为它必须调整stdscr内容的大小并且可以使用几个标准处理旧内容和新的可用空间。

我观察到的标准是 ncurses 本身不处理窗口更改(至少在默认情况下,您还必须考虑这与 ncurses 发生的情况相同,它没有检测到另一个进程是否已写入您的 tty,并且屏幕出现乱码)。为了处理这个问题,你必须为信号安装一个信号处理程序SIGWINCH(当终端尺寸发生变化时,这个信号被发送到整个进程组,通常是从 pty 主机端),并使ioctl(2)适用于 tty 设备获取新的窗口尺寸并调用适当的低级 ncurses 例程来更改新的几何形状stdsrcstdwin缓冲区,因为这将需要为它们重新分配内存。这意味着您可以自由决定在终端调整大小时窗口内容会发生什么,但会让您做所有的工作来处理它。我有一个程序,它SIGWINCH可以exec(2)自行启动并重新启动,因此它会在initscr(3)调用时获得新的屏幕尺寸。如果您无法自动exec(2)执行程序,只需深入了解如何重置stdscr尺寸以及正确更改LINSCOLS全局变量的文档。(如果我找到有关如何操作的文档,我将使用适当的信息编辑此答案。)

笔记

我已经运行了你的程序,它按预期工作......用星号填充第一行和最后一行。只需调用getch()beforeendwin()即可看到绘制的屏幕。

于 2017-11-20T08:31:42.300 回答