urxvt中的ncurses不会打印重复字符

时间:2017-09-30 22:08:41

标签: c ncurses urxvt

urxvt 中运行 ncurses 程序挤压重复字符串中的字符。例如,我希望"--------",但我得到"-"

我写了一个简短的程序来重现这个问题。代码如下。

我使用 xterm 而不是 urxvt 验证输出是否正确。

这是我第一次使用ncurses,但是,示例程序就像它们来的一样简单。因此,我不认为问题可能与我如何使用ncurses有关。 xterm给出了预期的结果,这也得到了支持。

我在Arch Linux上使用urxvt。我也在下面提供相关配置。我安装了vanilla xterm,没有任何其他配置。两者都运行了zsh。

示例程序(C)

#include <curses.h>

int main(){
  initscr();
  printw("------\n");        // (1) 6 '-' chars          urxvt: "------"   xterm: "------"
  printw("-------\n");       // (2) 7 '-' chars          urxvt: "-"        xterm: "-------"
  printw("--------\n");      // (3) 8 '-' chars          urxvt: "-"        xterm: "--------"
  printw("0--------0\n");    // (4) 8 '-' between '0'    urxvt: "0-0"      xterm: "0--------0"
  printw("xxxxxxxx\n");      // (5) Replacing '-' with 'x' does not make a difference.
  printw("---- ----\n");     // (6) Two '-' sequences separated by ' ' display correctly.
  printw("12345678\n");      // (7) Strings with different characters display correctly.
  for(int i=0; i<8; i++) addch('-');    // (8) 8 '-' chars      urxvt: "-"   xterm: "--------" 
  addch('\n');
  for(char c='0'; c<'8'; c++) addch(c); // (9) Both display correctly
  addch('\n');
  refresh();
  getch();
  endwin();
  return 0;
}

xterm输出(正确)

------
-------
--------
0--------0
xxxxxxxx
---- ----
12345678
--------
01234567

urxvt输出(不正确)

------
-
-
0-0
x
---- ----
12345678
-
01234567

观察

  • 最多可以正确显示6个重复字符。
  • 7个以上的重复字符显示为单个字符。
  • 如果字符不重复,则不会出现此问题,因此字符串本身的长度不是问题。
  • 重复子字符串的位置并不重要。在(7)中,被挤压的子串被两端夹着'0'个字符。
    • 问题不在于特定字符。它出现在'-'以及'x'
  • 使用printwaddch函数观察到问题。相关联的联机帮助页声明这些函数会移动光标,因此不需要显式移动光标。显然就是这种情况,否则问题不仅限于重复字符,而且xterm也会发生。

urxvt配置

  • rxvt-unicode v9.22
  • $TERMxterm-256color

1 个答案:

答案 0 :(得分:0)

urxvt不是xterm,因此$TERM应该是rxvt-unicode而不是xterm-256color

直到我输入问题的最后,当我添加urxvt配置时,我才意识到这一点。我想,考虑将哪些信息与SO问题相关可以导致解决自己的问题。而不是删除所有内容,我认为我可能会发布,但也许它会对那里的其他人有用。

事情是,我在很长一段时间之前添加了env设置,当时我第一次尝试使用Arch Linux和urxvt。我必须承认,我并没有花太多时间思考它。我记得当时我关心的是unicode字符,字体和颜色正确显示(除了漂亮的配色方案)。将$TERM设置为xterm-256color似乎在当时有效,并且在所有这些时间使用该系统,它似乎继续工作,直到今天。当然,这里和那里都有小故障,也许它们就是这样的结果。然后,也许他们是由于别的东西。我不得不说我对这个问题变得多么愚蠢和简单而感到好笑。

看到这个错误导致的奇怪行为也很有趣。我仍然很想知道为什么我的错误会导致我在问题中记录的行为。我有一段时间可能会因为踢球而回到这里。

修改

正如FAQ所指出的那样,ncurses的Thomas Dickey中提到了这个确切的问题。

  

...,在2017年中期,对xterm终端描述的更新添加了ECMA-48 REP(重复字符)控件。它是自1997年1月以来xterm的一部分,但使用该功能的终端描述仅是xterm的一部分(不是ncurses)。

使用TERM = xterm但不支持此xterm功能的终端仿真程序在将此功能引入ncurses后会出现错误。 rxvt没有受到影响,因为它不使用TERM = xterm,或者更确切地说,因为它不应该使用TERM = xterm,就像我一直在做的那样。

  

REP用于指示数据流中的前一个字符,如果它是包含SPACE的图形字符(由一个或多个位组合表示),则重复n次,其中n等于Pn的值。如果REP之前的字符是控制功能或控件的一部分   函数,REP的效果不是由本标准定义的。 REP - ECMA-048

我还应该提一下,ncurses常见问题包括一个很好的讨论,关于为什么人们倾向于使用TERM = xterm,以及为什么他们不应该直接从马的嘴里出来!