/* ************************************
* void ScrollScreenBuffer(HANDLE h, INT x)
* 功能	滚动屏幕
* 参数	HANDLE h, 控制台句柄;		INT x, 行
**************************************/
void ScrollScreenBuffer(HANDLE h, INT x)
{
	SMALL_RECT srctScrollRect, srctClipRect;
	CHAR_INFO chiFill;
	COORD coordDest;

	srctScrollRect.Left = 0;
	srctScrollRect.Top = 1;
	srctScrollRect.Right = csbiInfo.dwSize.X - x; 
	srctScrollRect.Bottom = csbiInfo.dwSize.Y - x; 

	// 目的
	coordDest.X = 0; 
	coordDest.Y = 0; 

	// left unchanged. 
	srctClipRect = srctScrollRect; 

	// 设置填充的字符串和属性 
	chiFill.Attributes = FOREGROUND_RED|FOREGROUND_INTENSITY; 
	chiFill.Char.AsciiChar = (char)' '; 

	// 滚动一行
	ScrollConsoleScreenBuffer( 
		h,               // 屏幕缓冲区句柄 
		&srctScrollRect, // scrolling rectangle 
		&srctClipRect,   // clipping rectangle 
		coordDest,       // 右上角目的cell 
		&chiFill);       // 填充的字符的颜色
}
Exemplo n.º 2
0
co_rc_t
console_widget_NT_t::op_bmove(
		const co_console_unit &Y,
		const co_console_unit &X,
		const co_console_unit &T,
		const co_console_unit &L,
		const co_console_unit &B,
		const co_console_unit &R)
{
	SMALL_RECT r;
	COORD c;

	c.Y = Y;
	c.X = X;

	r.Top = T;
	r.Left = L;
	r.Bottom = B;
	r.Right = R;

	if(!ScrollConsoleScreenBuffer(buffer, &r, &region, c, &blank))
		co_debug("ScrollConsoleScreenBuffer() error %d\n", GetLastError());

	return CO_RC(OK);
}
Exemplo n.º 3
0
static void
scroll_line (int dist, int direction)
{
  /* The idea here is to implement a horizontal scroll in one line to
     implement delete and half of insert.  */
  SMALL_RECT scroll;
  COORD	     dest;
  CHAR_INFO  fill;
  struct frame *  f = PICK_FRAME ();

  scroll.Top = cursor_coords.Y;
  scroll.Bottom = cursor_coords.Y;

  if (direction == LEFT)
    {
      scroll.Left = cursor_coords.X + dist;
      scroll.Right = FRAME_COLS (f) - 1;
    }
  else
    {
      scroll.Left = cursor_coords.X;
      scroll.Right = FRAME_COLS (f) - dist - 1;
    }

  dest.X = cursor_coords.X;
  dest.Y = cursor_coords.Y;

  fill.Char.AsciiChar = 0x20;
  fill.Attributes = char_attr_normal;

  ScrollConsoleScreenBuffer (cur_screen, &scroll, NULL, dest, &fill);
}
Exemplo n.º 4
0
void ScrollScreenBuffer(HANDLE h, INT x)
{
	SMALL_RECT srctScrollRect, srctClipRect;
	CHAR_INFO chiFill;
	COORD coordDest;

	srctScrollRect.Left = 0;
	srctScrollRect.Top = 1;
	srctScrollRect.Right = csbiInfo.dwSize.X - (SHORT)x; 
	srctScrollRect.Bottom = csbiInfo.dwSize.Y - (SHORT)x; 

	// The destination for the scroll rectangle is one row up. 

	coordDest.X = 0; 
	coordDest.Y = 0; 

	// The clipping rectangle is the same as the scrolling rectangle. 
	// The destination row is left unchanged. 

	srctClipRect = srctScrollRect; 

	// Set the fill character and attributes. 

	chiFill.Attributes = FOREGROUND_RED|FOREGROUND_INTENSITY; 
	chiFill.Char.AsciiChar = (char)' '; 

	// Scroll up one line. 

	ScrollConsoleScreenBuffer( 
		h,               // screen buffer handle 
		&srctScrollRect, // scrolling rectangle 
		&srctClipRect,   // clipping rectangle 
		coordDest,       // top left destination cell 
		&chiFill);       // fill character and color 
}
Exemplo n.º 5
0
BOOL
Scroll5(
    IN HANDLE Handle
    )
{
    SMALL_RECT ScrollRectangle;
    CHAR_INFO Fill;
    COORD DestinationOrigin;
    CONSOLE_SCREEN_BUFFER_INFO ScreenInfo;

    if (!GetConsoleScreenBufferInfo(Handle,&ScreenInfo)) {
        DbgPrint("ERROR: GetConsoleScreenBufferInfo failed\n");
    }

    ScrollRectangle = ScreenInfo.srWindow;
    Fill.Attributes = BACKGROUND_GREEN;
    Fill.Char.UnicodeChar = 'T';
    DestinationOrigin.X = 0;
    DestinationOrigin.Y = -(ScreenInfo.srWindow.Bottom - ScreenInfo.srWindow.Top + 1);
    if (!ScrollConsoleScreenBuffer(Handle,
                                   &ScrollRectangle,
                                   NULL,
                                   DestinationOrigin,
                                   &Fill)) {
        DbgPrint("ScrollConsoleScreenBuffer failed\n");
        return FALSE;
    }
    DbgPrint("scrolled entire screen\n");
    DbgBreakPoint();
    return TRUE;
}
Exemplo n.º 6
0
//------------------------------------------------------------------------------
void win_screen_buffer::delete_chars(int count)
{
    if (count <= 0)
        return;

    CONSOLE_SCREEN_BUFFER_INFO csbi;
    GetConsoleScreenBufferInfo(m_handle, &csbi);

    SMALL_RECT rect;
    rect.Left = csbi.dwCursorPosition.X + count;
    rect.Right = csbi.dwSize.X - 1;
    rect.Top = rect.Bottom = csbi.dwCursorPosition.Y;

    CHAR_INFO fill;
    fill.Char.AsciiChar = ' ';
    fill.Attributes = csbi.wAttributes;

    ScrollConsoleScreenBuffer(m_handle, &rect, NULL, csbi.dwCursorPosition, &fill);

    int chars_moved = rect.Right - rect.Left + 1;
    if (chars_moved < count)
    {
        COORD xy = csbi.dwCursorPosition;
        xy.X += chars_moved;

        count -= chars_moved;

        DWORD written;
        FillConsoleOutputCharacterW(m_handle, ' ', count, xy, &written);
        FillConsoleOutputAttribute(m_handle, csbi.wAttributes, count, xy, &written);
    }
}
Exemplo n.º 7
0
VALUE
rb_ScrollConsoleScreenBuffer( VALUE self, VALUE hConsoleOutput, VALUE left1,
			      VALUE top1, VALUE right1, VALUE bottom1,
			      VALUE col, VALUE row, VALUE cChar, VALUE attr,
			      VALUE left2, VALUE top2, VALUE right2,
			      VALUE bottom2)
{
   HANDLE handle = ULongToPtr( NUM2ULONG( hConsoleOutput ) );
   
   CHAR_INFO fill;
   COORD origin;
   SMALL_RECT scroll, clip;
   scroll.Left   = NUM2INT( left1 );
   scroll.Right  = NUM2INT( right1 );
   scroll.Top    = NUM2INT( top1 );
   scroll.Bottom = NUM2INT( bottom1 );
   clip.Left   = NUM2INT( left2 );
   clip.Right  = NUM2INT( right2 );
   clip.Top    = NUM2INT( top2 );
   clip.Bottom = NUM2INT( bottom2 );
#ifdef UNICODE
   fill.Char.UnicodeChar = NUM2CHR( cChar );
#else
   fill.Char.AsciiChar = NUM2CHR( cChar );
#endif
   fill.Attributes = NUM2INT(attr);
   origin.X = NUM2UINT( col );
   origin.Y = NUM2UINT( row );
   
   if ( ScrollConsoleScreenBuffer( handle, &scroll, &clip, origin,
				   &fill ) )
      return INT2FIX(1);
   return rb_getWin32Error();
}
Exemplo n.º 8
0
unsigned int __stdcall Rain(void *param)
{
    DWORD		dwRead;
    SMALL_RECT	srcScrollRect;
    char		*bLengthOfRain, *bIsSpace, *buff;
    COORD		coordLine0 = {0, 0}, coordLine2 = {0, 2};
    CHAR_INFO	char_info = {' ', FOREGROUND_GREEN|FOREGROUND_INTENSITY};

    // 设置要移动的范围
//	srcScrollRect.Top		= coord.Y;
    srcScrollRect.Left		= 0;
    srcScrollRect.Right		= sColNum - 1;
    srcScrollRect.Bottom	= sRowNum - 1;

    buff			= (char *)malloc(sColNum);
    bIsSpace		= (char *)malloc(sColNum);
    bLengthOfRain	= (char *)malloc(sColNum);
    memset(bIsSpace, 0, sColNum);
    memset(bLengthOfRain, 0, sColNum);

    do
    {
        Sleep(50);
        /*		if (bStart)	coord.Y = 2;
        		else coord.Y = 0;
        */
        // 上面的if...else...简化如下
        coord.Y = bStart << 1;
        coordDest.Y = coord.Y + 1;
        srcScrollRect.Top = coord.Y;

        // 移动一块字符, 并用 char_info 填充空出来的区域
        ScrollConsoleScreenBuffer(hStdOut, &srcScrollRect, 0, coordDest, &char_info);

        // 输出一行字符
        for (char index = 0; index != sColNum; ++index)
        {
            if (!bLengthOfRain[index]--)
            {
                bIsSpace[index]			= GetRandom(0, 4);		// 25% 概率出字符
                bLengthOfRain[index]	= GetRandom(10, 25);	// 每列最短10, 最长25
            }
            buff[index] = bIsSpace[index] ? ' ' : GetRandom(0x30, 0x7E);
        }
        WriteConsoleOutputCharacter(hStdOut, buff, sColNum, coord, NULL);
        if (bStart)			// 读取第3行的内容并写到第1行
        {
            ReadConsoleOutputCharacter(hStdOut,  buff, sColNum, coordLine2, &dwRead);
            WriteConsoleOutputCharacter(hStdOut, buff, dwRead,  coordLine0, NULL);
        }
    } while (!kbhit());

    bRainExit = true;
    free(bLengthOfRain);
    free(bIsSpace);
    free(buff);
//	MessageBox(NULL, _T("t1 free success"), NULL, 0x40);
    return 0;
}
Exemplo n.º 9
0
void Screen::scroll (int destX, int destY, const SMALL_RECT& scrollRect, const SMALL_RECT *pClipRect)
{
    CHAR_INFO fill;
    fill.Char.AsciiChar = ' ';
    fill.Attributes = FOREGROUND_RED | FOREGROUND_BLUE | FOREGROUND_GREEN;
    COORD dest;
    dest.X = destX;
    dest.Y = destY;
    if (ScrollConsoleScreenBuffer (mScreenBuf, &scrollRect, pClipRect, dest, &fill) != TRUE)
	throw AppException (WHERE, ERR_WINDOWS_FMT, "ScrollConsoleScreenBuffer", GetLastError ());
}
Exemplo n.º 10
0
JNIEXPORT void JNICALL Java_com_yifanlu_Josh_Josh_SCROLLCONSOLESCREENBUFFER
  (JNIEnv *env, jclass jcls, jlong pointer, jint scrollLeft, jint scrollTop, jint scrollRight, jint scrollBottom, jint clipLeft, jint clipTop, jint clipRight, jint clipBottom, jint toX, jint toY, jchar fillChar, jint fillAttribute)
{
    HANDLE hConsole = pointerToHandle(pointer);
	SMALL_RECT scroll = {scrollLeft, scrollTop, scrollRight, scrollBottom};
	SMALL_RECT clip = {clipLeft, clipTop, clipRight, clipBottom};
	COORD to = {toX, toY};
	CHAR_INFO fill;
    fill.Attributes = fillAttribute; 
    fill.Char.UnicodeChar = (char)fillChar;

	ScrollConsoleScreenBuffer(hConsole, &scroll, clipLeft == -1 ? NULL : &clip, to, &fill);
}
Exemplo n.º 11
0
void Sys_ConScrollLine()
{
	SMALL_RECT src;
	COORD   dest;
	CHAR_INFO fill;

	src.Left = 0;
	src.Right = cbInfo.dwSize.X - 1;
	src.Top = 1;
	src.Bottom = cbInfo.dwSize.Y - 2;
	dest.X = 0;
	dest.Y = 0;
	fill.Attributes = TEXT_ATTRIB;
	fill.Char.AsciiChar = ' ';
	ScrollConsoleScreenBuffer(hcScreen, &src, NULL, dest, &fill);
}
Exemplo n.º 12
0
/* scroll down */
void ossscr(int top, int left, int bottom, int right, int blankcolor)
{
    COORD newpos;
    SMALL_RECT pos;
    SMALL_RECT clip;
    CHAR_INFO fill;

    pos.Top = clip.Top = top;
    pos.Left = clip.Left = left;
    pos.Bottom = clip.Bottom = bottom;
    pos.Right = clip.Right = right;

    newpos.X = left;
    newpos.Y = top - 1;

    fill.Char.AsciiChar = ' ';
    fill.Attributes = blankcolor;

    ScrollConsoleScreenBuffer(G_out_bufhdl, &pos, &clip, newpos, &fill);
}
Exemplo n.º 13
0
//------------------------------------------------------------------------------
void win_screen_buffer::insert_chars(int count)
{
    if (count <= 0)
        return;

    CONSOLE_SCREEN_BUFFER_INFO csbi;
    GetConsoleScreenBufferInfo(m_handle, &csbi);

    SMALL_RECT rect;
    rect.Left = csbi.dwCursorPosition.X;
    rect.Right = csbi.dwSize.X;
    rect.Top = rect.Bottom = csbi.dwCursorPosition.Y;

    CHAR_INFO fill;
    fill.Char.AsciiChar = ' ';
    fill.Attributes = csbi.wAttributes;

    csbi.dwCursorPosition.X += count;

    ScrollConsoleScreenBuffer(m_handle, &rect, NULL, csbi.dwCursorPosition, &fill);
}
Exemplo n.º 14
0
co_rc_t
console_widget_NT_t::op_scroll_down(
		const co_console_unit &T,
		const co_console_unit &B,
		const co_console_unit &L)
{
	SMALL_RECT r;
	COORD c;

	r.Left = region.Left;
	r.Right = region.Right;
	r.Top = T;
	r.Bottom = B;
	c.X = 0;
	c.Y = r.Top + L;

	if (!ScrollConsoleScreenBuffer(buffer, &r, &r, c, &blank))
		co_debug("ScrollConsoleScreenBuffer() error code: %d \n",
			 GetLastError());

	return CO_RC(OK);
}
Exemplo n.º 15
0
void InterpretEscSeq( void )
{
  int  i;
  WORD attribut;
  CONSOLE_SCREEN_BUFFER_INFO Info;
  CONSOLE_CURSOR_INFO CursInfo;
  DWORD len, NumberOfCharsWritten;
  COORD Pos;
  SMALL_RECT Rect;
  CHAR_INFO  CharInfo;

  if (prefix == '[')
  {
    if (prefix2 == '?' && (suffix == 'h' || suffix == 'l'))
    {
      if (es_argc == 1 && es_argv[0] == 25)
      {
	GetConsoleCursorInfo( hConOut, &CursInfo );
	CursInfo.bVisible = (suffix == 'h');
	SetConsoleCursorInfo( hConOut, &CursInfo );
	return;
      }
    }
    // Ignore any other \e[? or \e[> sequences.
    if (prefix2 != 0)
      return;

    GetConsoleScreenBufferInfo( hConOut, &Info );
    switch (suffix)
    {
      case 'm':
	if (es_argc == 0) es_argv[es_argc++] = 0;
	for (i = 0; i < es_argc; i++)
	{
	  switch (es_argv[i])
	  {
	    case 0:
	      foreground = org_fg;
	      background = org_bg;
	      bold	 = (es_argc == 1) ? org_bold : 0;
	      underline  = (es_argc == 1) ? org_ul   : 0;
	      rvideo	 = 0;
	      concealed  = 0;
	    break;
	    case  1: bold      = FOREGROUND_INTENSITY; break;
	    case  5: /* blink */
	    case  4: underline = BACKGROUND_INTENSITY; break;
	    case  7: rvideo    = 1; break;
	    case  8: concealed = 1; break;
	    case 21: bold      = 0; break;
	    case 25:
	    case 24: underline = 0; break;
	    case 27: rvideo    = 0; break;
	    case 28: concealed = 0; break;
	  }
	  if (30 <= es_argv[i] && es_argv[i] <= 37) foreground = es_argv[i]-30;
	  if (40 <= es_argv[i] && es_argv[i] <= 47) background = es_argv[i]-40;
	}
	if (concealed)
	{
	  if (rvideo)
	  {
	    attribut = foregroundcolor[foreground]
		     | backgroundcolor[foreground];
	    if (bold)
	      attribut |= FOREGROUND_INTENSITY | BACKGROUND_INTENSITY;
	  }
	  else
	  {
	    attribut = foregroundcolor[background]
		     | backgroundcolor[background];
	    if (underline)
	      attribut |= FOREGROUND_INTENSITY | BACKGROUND_INTENSITY;
	  }
	}
	else if (rvideo)
	{
	  attribut = foregroundcolor[background] | backgroundcolor[foreground];
	  if (bold)
	    attribut |= BACKGROUND_INTENSITY;
	  if (underline)
	    attribut |= FOREGROUND_INTENSITY;
	}
	else
	  attribut = foregroundcolor[foreground] | backgroundcolor[background]
		   | bold | underline;
	SetConsoleTextAttribute( hConOut, attribut );
      return;

      case 'J':
	if (es_argc == 0) es_argv[es_argc++] = 0; // ESC[J == ESC[0J
	if (es_argc != 1) return;
	switch (es_argv[0])
	{
	  case 0:		// ESC[0J erase from cursor to end of display
	    len = (Info.dwSize.Y - Info.dwCursorPosition.Y - 1) * Info.dwSize.X
		  + Info.dwSize.X - Info.dwCursorPosition.X - 1;
	    FillConsoleOutputCharacter( hConOut, ' ', len,
					Info.dwCursorPosition,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes, len,
					Info.dwCursorPosition,
					&NumberOfCharsWritten );
	  return;

	  case 1:		// ESC[1J erase from start to cursor.
	    Pos.X = 0;
	    Pos.Y = 0;
	    len   = Info.dwCursorPosition.Y * Info.dwSize.X
		    + Info.dwCursorPosition.X + 1;
	    FillConsoleOutputCharacter( hConOut, ' ', len, Pos,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes, len, Pos,
					&NumberOfCharsWritten );
	    return;

	  case 2:		// ESC[2J Clear screen and home cursor
	    Pos.X = 0;
	    Pos.Y = 0;
	    len   = Info.dwSize.X * Info.dwSize.Y;
	    FillConsoleOutputCharacter( hConOut, ' ', len, Pos,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes, len, Pos,
					&NumberOfCharsWritten );
	    SetConsoleCursorPosition( hConOut, Pos );
	  return;

	  default:
	  return;
	}

      case 'K':
	if (es_argc == 0) es_argv[es_argc++] = 0; // ESC[K == ESC[0K
	if (es_argc != 1) return;
	switch (es_argv[0])
	{
	  case 0:		// ESC[0K Clear to end of line
	    len = Info.srWindow.Right - Info.dwCursorPosition.X + 1;
	    FillConsoleOutputCharacter( hConOut, ' ', len,
					Info.dwCursorPosition,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes, len,
					Info.dwCursorPosition,
					&NumberOfCharsWritten );
	  return;

	  case 1:		// ESC[1K Clear from start of line to cursor
	    Pos.X = 0;
	    Pos.Y = Info.dwCursorPosition.Y;
	    FillConsoleOutputCharacter( hConOut, ' ',
					Info.dwCursorPosition.X + 1, Pos,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes,
					Info.dwCursorPosition.X + 1, Pos,
					&NumberOfCharsWritten );
	  return;

	  case 2:		// ESC[2K Clear whole line.
	    Pos.X = 0;
	    Pos.Y = Info.dwCursorPosition.Y;
	    FillConsoleOutputCharacter( hConOut, ' ', Info.dwSize.X, Pos,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes,
					Info.dwSize.X, Pos,
					&NumberOfCharsWritten );
	  return;

	  default:
	  return;
	}

      case 'L':                 // ESC[#L Insert # blank lines.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[L == ESC[1L
	if (es_argc != 1) return;
	Rect.Left   = 0;
	Rect.Top    = Info.dwCursorPosition.Y;
	Rect.Right  = Info.dwSize.X - 1;
	Rect.Bottom = Info.dwSize.Y - 1;
	Pos.X = 0;
	Pos.Y = Info.dwCursorPosition.Y + es_argv[0];
	CharInfo.Char.UnicodeChar = ' ';
	CharInfo.Attributes = Info.wAttributes;
	ScrollConsoleScreenBuffer( hConOut, &Rect, NULL, Pos, &CharInfo );
      return;

      case 'M':                 // ESC[#M Delete # lines.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[M == ESC[1M
	if (es_argc != 1) return;
	if (es_argv[0] > Info.dwSize.Y - Info.dwCursorPosition.Y)
	  es_argv[0] = Info.dwSize.Y - Info.dwCursorPosition.Y;
	Rect.Left   = 0;
	Rect.Top    = Info.dwCursorPosition.Y + es_argv[0];
	Rect.Right  = Info.dwSize.X - 1;
	Rect.Bottom = Info.dwSize.Y - 1;
	Pos.X = 0;
	Pos.Y = Info.dwCursorPosition.Y;
	CharInfo.Char.UnicodeChar = ' ';
	CharInfo.Attributes = Info.wAttributes;
	ScrollConsoleScreenBuffer( hConOut, &Rect, NULL, Pos, &CharInfo );
      return;

      case 'P':                 // ESC[#P Delete # characters.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[P == ESC[1P
	if (es_argc != 1) return;
	if (Info.dwCursorPosition.X + es_argv[0] > Info.dwSize.X - 1)
	  es_argv[0] = Info.dwSize.X - Info.dwCursorPosition.X;
	Rect.Left   = Info.dwCursorPosition.X + es_argv[0];
	Rect.Top    = Info.dwCursorPosition.Y;
	Rect.Right  = Info.dwSize.X - 1;
	Rect.Bottom = Info.dwCursorPosition.Y;
	CharInfo.Char.UnicodeChar = ' ';
	CharInfo.Attributes = Info.wAttributes;
	ScrollConsoleScreenBuffer( hConOut, &Rect, NULL, Info.dwCursorPosition,
				   &CharInfo );
      return;

      case '@':                 // ESC[#@ Insert # blank characters.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[@ == ESC[1@
	if (es_argc != 1) return;
	if (Info.dwCursorPosition.X + es_argv[0] > Info.dwSize.X - 1)
	  es_argv[0] = Info.dwSize.X - Info.dwCursorPosition.X;
	Rect.Left   = Info.dwCursorPosition.X;
	Rect.Top    = Info.dwCursorPosition.Y;
	Rect.Right  = Info.dwSize.X - 1 - es_argv[0];
	Rect.Bottom = Info.dwCursorPosition.Y;
	Pos.X = Info.dwCursorPosition.X + es_argv[0];
	Pos.Y = Info.dwCursorPosition.Y;
	CharInfo.Char.UnicodeChar = ' ';
	CharInfo.Attributes = Info.wAttributes;
	ScrollConsoleScreenBuffer( hConOut, &Rect, NULL, Pos, &CharInfo );
      return;

      case 'A':                 // ESC[#A Moves cursor up # lines
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[A == ESC[1A
	if (es_argc != 1) return;
	Pos.Y = Info.dwCursorPosition.Y - es_argv[0];
	if (Pos.Y < 0) Pos.Y = 0;
	Pos.X = Info.dwCursorPosition.X;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'B':                 // ESC[#B Moves cursor down # lines
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[B == ESC[1B
	if (es_argc != 1) return;
	Pos.Y = Info.dwCursorPosition.Y + es_argv[0];
	if (Pos.Y >= Info.dwSize.Y) Pos.Y = Info.dwSize.Y - 1;
	Pos.X = Info.dwCursorPosition.X;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'C':                 // ESC[#C Moves cursor forward # spaces
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[C == ESC[1C
	if (es_argc != 1) return;
	Pos.X = Info.dwCursorPosition.X + es_argv[0];
	if (Pos.X >= Info.dwSize.X) Pos.X = Info.dwSize.X - 1;
	Pos.Y = Info.dwCursorPosition.Y;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'D':                 // ESC[#D Moves cursor back # spaces
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[D == ESC[1D
	if (es_argc != 1) return;
	Pos.X = Info.dwCursorPosition.X - es_argv[0];
	if (Pos.X < 0) Pos.X = 0;
	Pos.Y = Info.dwCursorPosition.Y;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'E':                 // ESC[#E Moves cursor down # lines, column 1.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[E == ESC[1E
	if (es_argc != 1) return;
	Pos.Y = Info.dwCursorPosition.Y + es_argv[0];
	if (Pos.Y >= Info.dwSize.Y) Pos.Y = Info.dwSize.Y - 1;
	Pos.X = 0;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'F':                 // ESC[#F Moves cursor up # lines, column 1.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[F == ESC[1F
	if (es_argc != 1) return;
	Pos.Y = Info.dwCursorPosition.Y - es_argv[0];
	if (Pos.Y < 0) Pos.Y = 0;
	Pos.X = 0;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'G':                 // ESC[#G Moves cursor column # in current row.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[G == ESC[1G
	if (es_argc != 1) return;
	Pos.X = es_argv[0] - 1;
	if (Pos.X >= Info.dwSize.X) Pos.X = Info.dwSize.X - 1;
	if (Pos.X < 0) Pos.X = 0;
	Pos.Y = Info.dwCursorPosition.Y;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'f':                 // ESC[#;#f
      case 'H':                 // ESC[#;#H Moves cursor to line #, column #
	if (es_argc == 0)
	  es_argv[es_argc++] = 1; // ESC[H == ESC[1;1H
	if (es_argc == 1)
	  es_argv[es_argc++] = 1; // ESC[#H == ESC[#;1H
	if (es_argc > 2) return;
	Pos.X = es_argv[1] - 1;
	if (Pos.X < 0) Pos.X = 0;
	if (Pos.X >= Info.dwSize.X) Pos.X = Info.dwSize.X - 1;
	Pos.Y = es_argv[0] - 1;
	if (Pos.Y < 0) Pos.Y = 0;
	if (Pos.Y >= Info.dwSize.Y) Pos.Y = Info.dwSize.Y - 1;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 's':                 // ESC[s Saves cursor position for recall later
	if (es_argc != 0) return;
	SavePos = Info.dwCursorPosition;
      return;

      case 'u':                 // ESC[u Return to saved cursor position
	if (es_argc != 0) return;
	SetConsoleCursorPosition( hConOut, SavePos );
      return;

      case 'n':                 // ESC[#n Device status report
	if (es_argc != 1) return; // ESC[n == ESC[0n -> ignored
	switch (es_argv[0])
	{
	  case 5:		// ESC[5n Report status
	    SendSequence( L"\33[0n" ); // "OK"
	  return;

	  case 6:		// ESC[6n Report cursor position
	  {
	    TCHAR buf[32];
	    wsprintf( buf, L"\33[%d;%dR", Info.dwCursorPosition.Y + 1,
					  Info.dwCursorPosition.X + 1 );
	    SendSequence( buf );
	  }
	  return;

	  default:
	  return;
	}

      case 't':                 // ESC[#t Window manipulation
	if (es_argc != 1) return;
	if (es_argv[0] == 21)	// ESC[21t Report xterm window's title
	{
	  TCHAR buf[MAX_PATH*2];
	  DWORD len = GetConsoleTitle( buf+3, lenof(buf)-3-2 );
	  // Too bad if it's too big or fails.
	  buf[0] = ESC;
	  buf[1] = ']';
	  buf[2] = 'l';
	  buf[3+len] = ESC;
	  buf[3+len+1] = '\\';
	  buf[3+len+2] = '\0';
	  SendSequence( buf );
	}
      return;

      default:
      return;
    }
  }
  else // (prefix == ']')
  {
    // Ignore any \e]? or \e]> sequences.
    if (prefix2 != 0)
      return;

    if (es_argc == 1 && es_argv[0] == 0) // ESC]0;titleST
    {
      SetConsoleTitle( Pt_arg );
    }
  }
}
Exemplo n.º 16
0
BOOL
Scroll4(
    IN HANDLE Handle
    )
{
    CHAR_INFO CharBuffer[20][25];
    SMALL_RECT WriteRegion;
    COORD BufferSize;
    COORD BufferCoord;
    CHAR TextAttr;
    CHAR BackgroundAttr;
    int i,j;
    CHAR Char;
    SMALL_RECT ScrollRectangle,ClipRectangle;
    CHAR_INFO Fill;
    COORD DestinationOrigin;

    BackgroundAttr = BACKGROUND_BLUE;
    TextAttr = FOREGROUND_WHITE;
    for (i=0;i<20;i++) {
        for (Char='a',j=0;j<25;j++) {
            CharBuffer[i][j].Attributes = BackgroundAttr | TextAttr;
            CharBuffer[i][j].Char.AsciiChar = Char;
            Char++;
            if (Char > 'z') Char = 'a';
        }
    }

    //
    // write square to screen
    //

    BufferSize.X = 25;
    BufferSize.Y = 20;
    BufferCoord.X = 0;
    BufferCoord.Y = 0;
    WriteRegion.Left = 5;
    WriteRegion.Right = 15;
    WriteRegion.Top = 5;
    WriteRegion.Bottom = 15;
    if (!WriteConsoleOutput(Handle,
                            (PCHAR_INFO)CharBuffer,
                            BufferSize,
                            BufferCoord,
                            &WriteRegion
                           )) {
        DbgPrint("WriteConsoleOutput failed\n");
        return FALSE;
    }
    if (WriteRegion.Left != 5 || WriteRegion.Right != 15 ||
        WriteRegion.Top != 5 || WriteRegion.Bottom != 15) {
        DbgPrint("test 1: regions don't match\n");
        DbgPrint("WriteRegion is %ld\n",&WriteRegion);
    }
    DbgPrint("wrote rectangle to 5,5\n");
    DbgBreakPoint();

    ScrollRectangle.Left = 5;
    ScrollRectangle.Right = 15;
    ScrollRectangle.Top = 5;
    ScrollRectangle.Bottom = 15;
    ClipRectangle.Left = 9;
    ClipRectangle.Right = 25;
    ClipRectangle.Top = 9;
    ClipRectangle.Bottom = 25;
    Fill.Attributes = BACKGROUND_GREEN;
    Fill.Char.UnicodeChar = 'T';
    DestinationOrigin.X = 20;
    DestinationOrigin.Y = 20;
    if (!ScrollConsoleScreenBuffer(Handle,
                                   &ScrollRectangle,
                                   &ClipRectangle,
                                   DestinationOrigin,
                                   &Fill)) {
        DbgPrint("ScrollConsoleScreenBuffer failed\n");
        return FALSE;
    }
    DbgPrint("scrolled region (5,15)(5,15) to (20,20) with clip (9,9)(25,25)\n");
    DbgBreakPoint();
    return TRUE;
}
Exemplo n.º 17
0
Arquivo: ANSI.c Projeto: catoc/Comojs
void InterpretEscSeq( void )
{
  int  i;
  WORD attribut;
  CONSOLE_SCREEN_BUFFER_INFO Info;
  CONSOLE_CURSOR_INFO CursInfo;
  DWORD len, NumberOfCharsWritten;
  COORD Pos;
  SMALL_RECT Rect;
  CHAR_INFO  CharInfo;

  if (prefix == '[')
  {
    if (prefix2 == '?' && (suffix == 'h' || suffix == 'l'))
    {
      if (es_argc == 1 && es_argv[0] == 25)
      {
	GetConsoleCursorInfo( hConOut, &CursInfo );
	CursInfo.bVisible = (suffix == 'h');
	SetConsoleCursorInfo( hConOut, &CursInfo );
	return;
      }
    }
    // Ignore any other \e[? or \e[> sequences.
    if (prefix2 != 0)
      return;

    GetConsoleScreenBufferInfo( hConOut, &Info );
    switch (suffix)
    {
      case 'm':
	if (es_argc == 0) es_argv[es_argc++] = 0;
	for (i = 0; i < es_argc; i++)
	{
	  if (30 <= es_argv[i] && es_argv[i] <= 37)
	    grm.foreground = es_argv[i] - 30;
	  else if (40 <= es_argv[i] && es_argv[i] <= 47)
	    grm.background = es_argv[i] - 40;
	  else switch (es_argv[i])
	  {
	    case 0:
	    case 39:
	    case 49:
	    {
	      TCHAR def[4];
	      int   a;
	      *def = '7'; def[1] = '\0';
	      GetEnvironmentVariable( (LPCTSTR)L"ANSICON_DEF", def, lenof(def) );
	      a = wcstol( (const wchar_t*)def, NULL, 16 );
	      grm.reverse = FALSE;
	      if (a < 0)
	      {
		grm.reverse = TRUE;
		a = -a;
	      }
	      if (es_argv[i] != 49)
		grm.foreground = attr2ansi[a & 7];
	      if (es_argv[i] != 39)
		grm.background = attr2ansi[(a >> 4) & 7];
	      if (es_argv[i] == 0)
	      {
		if (es_argc == 1)
		{
		  grm.bold	= a & FOREGROUND_INTENSITY;
		  grm.underline = a & BACKGROUND_INTENSITY;
		}
		else
		{
		  grm.bold	= 0;
		  grm.underline = 0;
		}
		grm.rvideo    = 0;
		grm.concealed = 0;
	      }
	    }
	    break;

	    case  1: grm.bold	   = FOREGROUND_INTENSITY; break;
	    case  5: // blink
	    case  4: grm.underline = BACKGROUND_INTENSITY; break;
	    case  7: grm.rvideo    = 1; break;
	    case  8: grm.concealed = 1; break;
	    case 21: // oops, this actually turns on double underline
	    case 22: grm.bold	   = 0; break;
	    case 25:
	    case 24: grm.underline = 0; break;
	    case 27: grm.rvideo    = 0; break;
	    case 28: grm.concealed = 0; break;
	  }
	}
	if (grm.concealed)
	{
	  if (grm.rvideo)
	  {
	    attribut = foregroundcolor[grm.foreground]
		     | backgroundcolor[grm.foreground];
	    if (grm.bold)
	      attribut |= FOREGROUND_INTENSITY | BACKGROUND_INTENSITY;
	  }
	  else
	  {
	    attribut = foregroundcolor[grm.background]
		     | backgroundcolor[grm.background];
	    if (grm.underline)
	      attribut |= FOREGROUND_INTENSITY | BACKGROUND_INTENSITY;
	  }
	}
	else if (grm.rvideo)
	{
	  attribut = foregroundcolor[grm.background]
		   | backgroundcolor[grm.foreground];
	  if (grm.bold)
	    attribut |= BACKGROUND_INTENSITY;
	  if (grm.underline)
	    attribut |= FOREGROUND_INTENSITY;
	}
	else
	  attribut = foregroundcolor[grm.foreground] | grm.bold
		   | backgroundcolor[grm.background] | grm.underline;
	if (grm.reverse)
	  attribut = ((attribut >> 4) & 15) | ((attribut & 15) << 4);
	SetConsoleTextAttribute( hConOut, attribut );
      return;

      case 'J':
	if (es_argc == 0) es_argv[es_argc++] = 0; // ESC[J == ESC[0J
	if (es_argc != 1) return;
	switch (es_argv[0])
	{
	  case 0:		// ESC[0J erase from cursor to end of display
	    len = (Info.dwSize.Y - Info.dwCursorPosition.Y - 1) * Info.dwSize.X
		  + Info.dwSize.X - Info.dwCursorPosition.X - 1;
	    FillConsoleOutputCharacter( hConOut, ' ', len,
					Info.dwCursorPosition,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes, len,
					Info.dwCursorPosition,
					&NumberOfCharsWritten );
	  return;

	  case 1:		// ESC[1J erase from start to cursor.
	    Pos.X = 0;
	    Pos.Y = 0;
	    len   = Info.dwCursorPosition.Y * Info.dwSize.X
		    + Info.dwCursorPosition.X + 1;
	    FillConsoleOutputCharacter( hConOut, ' ', len, Pos,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes, len, Pos,
					&NumberOfCharsWritten );
	    return;

	  case 2:		// ESC[2J Clear screen and home cursor
	    Pos.X = 0;
	    Pos.Y = 0;
	    len   = Info.dwSize.X * Info.dwSize.Y;
	    FillConsoleOutputCharacter( hConOut, ' ', len, Pos,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes, len, Pos,
					&NumberOfCharsWritten );
	    SetConsoleCursorPosition( hConOut, Pos );
	  return;

	  default:
	  return;
	}

      case 'K':
	if (es_argc == 0) es_argv[es_argc++] = 0; // ESC[K == ESC[0K
	if (es_argc != 1) return;
	switch (es_argv[0])
	{
	  case 0:		// ESC[0K Clear to end of line
	    len = Info.srWindow.Right - Info.dwCursorPosition.X + 1;
	    FillConsoleOutputCharacter( hConOut, ' ', len,
					Info.dwCursorPosition,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes, len,
					Info.dwCursorPosition,
					&NumberOfCharsWritten );
	  return;

	  case 1:		// ESC[1K Clear from start of line to cursor
	    Pos.X = 0;
	    Pos.Y = Info.dwCursorPosition.Y;
	    FillConsoleOutputCharacter( hConOut, ' ',
					Info.dwCursorPosition.X + 1, Pos,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes,
					Info.dwCursorPosition.X + 1, Pos,
					&NumberOfCharsWritten );
	  return;

	  case 2:		// ESC[2K Clear whole line.
	    Pos.X = 0;
	    Pos.Y = Info.dwCursorPosition.Y;
	    FillConsoleOutputCharacter( hConOut, ' ', Info.dwSize.X, Pos,
					&NumberOfCharsWritten );
	    FillConsoleOutputAttribute( hConOut, Info.wAttributes,
					Info.dwSize.X, Pos,
					&NumberOfCharsWritten );
	  return;

	  default:
	  return;
	}

      case 'X':                 // ESC[#X Erase # characters.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[X == ESC[1X
	if (es_argc != 1) return;
	FillConsoleOutputCharacter( hConOut, ' ', es_argv[0],
				    Info.dwCursorPosition,
				    &NumberOfCharsWritten );
	FillConsoleOutputAttribute( hConOut, Info.wAttributes, es_argv[0],
				    Info.dwCursorPosition,
				    &NumberOfCharsWritten );
      return;

      case 'L':                 // ESC[#L Insert # blank lines.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[L == ESC[1L
	if (es_argc != 1) return;
	Rect.Left   = 0;
	Rect.Top    = Info.dwCursorPosition.Y;
	Rect.Right  = Info.dwSize.X - 1;
	Rect.Bottom = Info.dwSize.Y - 1;
	Pos.X = 0;
	Pos.Y = Info.dwCursorPosition.Y + es_argv[0];
	CharInfo.Char.UnicodeChar = ' ';
	CharInfo.Attributes = Info.wAttributes;
	ScrollConsoleScreenBuffer( hConOut, &Rect, NULL, Pos, &CharInfo );
      return;

      case 'M':                 // ESC[#M Delete # lines.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[M == ESC[1M
	if (es_argc != 1) return;
	if (es_argv[0] > Info.dwSize.Y - Info.dwCursorPosition.Y)
	  es_argv[0] = Info.dwSize.Y - Info.dwCursorPosition.Y;
	Rect.Left   = 0;
	Rect.Top    = Info.dwCursorPosition.Y + es_argv[0];
	Rect.Right  = Info.dwSize.X - 1;
	Rect.Bottom = Info.dwSize.Y - 1;
	Pos.X = 0;
	Pos.Y = Info.dwCursorPosition.Y;
	CharInfo.Char.UnicodeChar = ' ';
	CharInfo.Attributes = Info.wAttributes;
	ScrollConsoleScreenBuffer( hConOut, &Rect, NULL, Pos, &CharInfo );
      return;

      case 'P':                 // ESC[#P Delete # characters.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[P == ESC[1P
	if (es_argc != 1) return;
	if (Info.dwCursorPosition.X + es_argv[0] > Info.dwSize.X - 1)
	  es_argv[0] = Info.dwSize.X - Info.dwCursorPosition.X;
	Rect.Left   = Info.dwCursorPosition.X + es_argv[0];
	Rect.Top    = Info.dwCursorPosition.Y;
	Rect.Right  = Info.dwSize.X - 1;
	Rect.Bottom = Info.dwCursorPosition.Y;
	CharInfo.Char.UnicodeChar = ' ';
	CharInfo.Attributes = Info.wAttributes;
	ScrollConsoleScreenBuffer( hConOut, &Rect, NULL, Info.dwCursorPosition,
				   &CharInfo );
      return;

      case '@':                 // ESC[#@ Insert # blank characters.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[@ == ESC[1@
	if (es_argc != 1) return;
	if (Info.dwCursorPosition.X + es_argv[0] > Info.dwSize.X - 1)
	  es_argv[0] = Info.dwSize.X - Info.dwCursorPosition.X;
	Rect.Left   = Info.dwCursorPosition.X;
	Rect.Top    = Info.dwCursorPosition.Y;
	Rect.Right  = Info.dwSize.X - 1 - es_argv[0];
	Rect.Bottom = Info.dwCursorPosition.Y;
	Pos.X = Info.dwCursorPosition.X + es_argv[0];
	Pos.Y = Info.dwCursorPosition.Y;
	CharInfo.Char.UnicodeChar = ' ';
	CharInfo.Attributes = Info.wAttributes;
	ScrollConsoleScreenBuffer( hConOut, &Rect, NULL, Pos, &CharInfo );
      return;

      case 'k':                 // ESC[#k
      case 'A':                 // ESC[#A Moves cursor up # lines
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[A == ESC[1A
	if (es_argc != 1) return;
	Pos.Y = Info.dwCursorPosition.Y - es_argv[0];
	if (Pos.Y < 0) Pos.Y = 0;
	Pos.X = Info.dwCursorPosition.X;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'e':                 // ESC[#e
      case 'B':                 // ESC[#B Moves cursor down # lines
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[B == ESC[1B
	if (es_argc != 1) return;
	Pos.Y = Info.dwCursorPosition.Y + es_argv[0];
	if (Pos.Y >= Info.dwSize.Y) Pos.Y = Info.dwSize.Y - 1;
	Pos.X = Info.dwCursorPosition.X;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'a':                 // ESC[#a
      case 'C':                 // ESC[#C Moves cursor forward # spaces
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[C == ESC[1C
	if (es_argc != 1) return;
	Pos.X = Info.dwCursorPosition.X + es_argv[0];
	if (Pos.X >= Info.dwSize.X) Pos.X = Info.dwSize.X - 1;
	Pos.Y = Info.dwCursorPosition.Y;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'j':                 // ESC[#j
      case 'D':                 // ESC[#D Moves cursor back # spaces
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[D == ESC[1D
	if (es_argc != 1) return;
	Pos.X = Info.dwCursorPosition.X - es_argv[0];
	if (Pos.X < 0) Pos.X = 0;
	Pos.Y = Info.dwCursorPosition.Y;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'E':                 // ESC[#E Moves cursor down # lines, column 1.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[E == ESC[1E
	if (es_argc != 1) return;
	Pos.Y = Info.dwCursorPosition.Y + es_argv[0];
	if (Pos.Y >= Info.dwSize.Y) Pos.Y = Info.dwSize.Y - 1;
	Pos.X = 0;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'F':                 // ESC[#F Moves cursor up # lines, column 1.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[F == ESC[1F
	if (es_argc != 1) return;
	Pos.Y = Info.dwCursorPosition.Y - es_argv[0];
	if (Pos.Y < 0) Pos.Y = 0;
	Pos.X = 0;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case '`':                 // ESC[#`
      case 'G':                 // ESC[#G Moves cursor column # in current row.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[G == ESC[1G
	if (es_argc != 1) return;
	Pos.X = es_argv[0] - 1;
	if (Pos.X >= Info.dwSize.X) Pos.X = Info.dwSize.X - 1;
	if (Pos.X < 0) Pos.X = 0;
	Pos.Y = Info.dwCursorPosition.Y;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'd':                 // ESC[#d Moves cursor row #, current column.
	if (es_argc == 0) es_argv[es_argc++] = 1; // ESC[d == ESC[1d
	if (es_argc != 1) return;
	Pos.Y = es_argv[0] - 1;
	if (Pos.Y < 0) Pos.Y = 0;
	if (Pos.Y >= Info.dwSize.Y) Pos.Y = Info.dwSize.Y - 1;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 'f':                 // ESC[#;#f
      case 'H':                 // ESC[#;#H Moves cursor to line #, column #
	if (es_argc == 0)
	  es_argv[es_argc++] = 1; // ESC[H == ESC[1;1H
	if (es_argc == 1)
	  es_argv[es_argc++] = 1; // ESC[#H == ESC[#;1H
	if (es_argc > 2) return;
	Pos.X = es_argv[1] - 1;
	if (Pos.X < 0) Pos.X = 0;
	if (Pos.X >= Info.dwSize.X) Pos.X = Info.dwSize.X - 1;
	Pos.Y = es_argv[0] - 1;
	if (Pos.Y < 0) Pos.Y = 0;
	if (Pos.Y >= Info.dwSize.Y) Pos.Y = Info.dwSize.Y - 1;
	SetConsoleCursorPosition( hConOut, Pos );
      return;

      case 's':                 // ESC[s Saves cursor position for recall later
	if (es_argc != 0) return;
	SavePos = Info.dwCursorPosition;
      return;

      case 'u':                 // ESC[u Return to saved cursor position
	if (es_argc != 0) return;
	SetConsoleCursorPosition( hConOut, SavePos );
      return;

      case 'n':                 // ESC[#n Device status report
	if (es_argc != 1) return; // ESC[n == ESC[0n -> ignored
	switch (es_argv[0])
	{
	  case 5:		// ESC[5n Report status
	    SendSequence( (LPTSTR)L"\33[0n" ); // "OK"
	  return;

	  case 6:		// ESC[6n Report cursor position
	  {
	    TCHAR buf[32];
        
	    wsprintf( buf, (LPTSTR)L"\33[%d;%dR", Info.dwCursorPosition.Y + 1,
					  Info.dwCursorPosition.X + 1 );
	    SendSequence( buf );
	  }
	  return;

	  default:
	  return;
	}

      case 't':                 // ESC[#t Window manipulation
	if (es_argc != 1) return;
	if (es_argv[0] == 21)	// ESC[21t Report xterm window's title
	{
	  TCHAR buf[MAX_PATH*2];
	  DWORD len = GetConsoleTitle( buf+3, lenof(buf)-3-2 );
	  // Too bad if it's too big or fails.
	  buf[0] = ESC;
	  buf[1] = ']';
	  buf[2] = 'l';
	  buf[3+len] = ESC;
	  buf[3+len+1] = '\\';
	  buf[3+len+2] = '\0';
	  SendSequence( buf );
	}
      return;

      default:
      return;
    }
  }
  else // (prefix == ']')
  {
    // Ignore any \e]? or \e]> sequences.
    if (prefix2 != 0)
Exemplo n.º 18
0
void MessageEditor::delete_work() { //str_pos和cursor_pos不变
    int tmp_post_end_pos;
    DWORD cCharsWritten;

    if (line_str_pos[current_line_num] == line[current_line_num].size()) //最后一行行尾后一格
        return;
    character_count--;
    wch = line[current_line_num][line_str_pos[current_line_num]];
    int deleted_ch_width;
    if (!isascii(wch))
        deleted_ch_width = 2;
    else
        deleted_ch_width = 1;
    //在该行删去当前光标位置的字符,并将后面的字符向前移动
    if (line_str_pos[current_line_num] == line[current_line_num].size() - 1) { //当前位置在行尾
        tmp_post_end_pos = line_cursor_pos[current_line_num];
        FillConsoleOutputCharacter(stdout_handle, (TCHAR)' ', deleted_ch_width, input_cursor_pos, &cCharsWritten);
    }
    else {
        SMALL_RECT scroll_rect;
        scroll_rect.Bottom = scroll_rect.Top = input_cursor_pos.Y;
        scroll_rect.Left = line_cursor_pos[current_line_num] + deleted_ch_width;
        wch = line[current_line_num].back();
        if (!isascii(wch))
            scroll_rect.Right = line_end_pos[current_line_num] + 1;
        else
            scroll_rect.Right = line_end_pos[current_line_num];
        tmp_post_end_pos = scroll_rect.Right + 1 - deleted_ch_width;
        ScrollConsoleScreenBuffer(stdout_handle, &scroll_rect, NULL, input_cursor_pos, &blank_char);
    }
    line[current_line_num].erase(line_str_pos[current_line_num], 1);

    //将后面的行依次往前移动(每次操作某行时,从后一行提取若干字符,并将后一行左移)
    int operating_line_num = current_line_num;
    while (operating_line_num < line_str_pos.size()) {
        if (operating_line_num == line_str_pos.size() - 1) { //最后一行,只需设置line_end_pos
            if (line[operating_line_num].empty()) //最后一行被删成空行
                line_end_pos[operating_line_num] = -1;
            else {
                wch = line[operating_line_num].back();
                if (!isascii(wch))
                    line_end_pos[operating_line_num] = tmp_post_end_pos - 2;
                else
                    line_end_pos[operating_line_num] = tmp_post_end_pos - 1;
            }
        }
        else {
            COORD end_pos = { tmp_post_end_pos, input_cursor_pos.Y + (operating_line_num - current_line_num) };
            int deleted_chars_width = 0;
            int tmp_char_width;
            int tmp_line_count = line_str_pos.size();
            while (tmp_post_end_pos <= RIGHT) { //从下一行借取若干字接在此行最后
                if (line[operating_line_num + 1].empty()) { //下一行已经被取空,将下一行删去
                    line_str_pos.pop_back();
                    line_cursor_pos.pop_back();
                    line_end_pos.pop_back();
                    break;
                }
                else { //否则取出一个字,接在该行后
                    wch = line[operating_line_num + 1].front();
                    if (!isascii(wch))
                        tmp_char_width = 2;
                    else
                        tmp_char_width = 1;
                    tmp_post_end_pos += tmp_char_width;
                    if (tmp_post_end_pos > RIGHT + 1) { //太长,此步操作取消
                        tmp_post_end_pos -= tmp_char_width;
                        break;
                    }
                    deleted_chars_width += tmp_char_width;
                    line[operating_line_num + 1].erase(0, 1);
                    line[operating_line_num].push_back(wch);
                    FillConsoleOutputCharacter(stdout_handle, wch, tmp_char_width, end_pos, &cCharsWritten);
                    end_pos.X += tmp_char_width;
                }
            }

            //设置line_end_pos
            wch = line[operating_line_num].back();
            if (!isascii(wch))
                line_end_pos[operating_line_num] = tmp_post_end_pos - 2;
            else
                line_end_pos[operating_line_num] = tmp_post_end_pos - 1;

            if (deleted_chars_width == 0) { //未从下一行取走字符
                if ((operating_line_num == current_line_num) && //光标所在的行
                        (line_cursor_pos[current_line_num] > line_end_pos[current_line_num]) && //光标位置上已不存在字符
                        (current_line_num + 1 < line_str_pos.size())) { //下一行存在,光标应移动到下一行
                    line_str_pos[current_line_num] = 0;
                    line_cursor_pos[current_line_num] = LEFT;
                    current_line_num++;
                    line_str_pos[current_line_num] = 0;
                    line_cursor_pos[current_line_num] = LEFT;
                    input_cursor_pos.X = LEFT;
                    input_cursor_pos.Y++;
                }
                break; //无需对后面的行再进行操作
            }
            else { //取出了下一行的字符,因此将下一行的内容左移
                if (operating_line_num + 1 < tmp_line_count) { //如果下一行还存在
                    end_pos.Y++;
                    end_pos.X = LEFT;
                    if (line[operating_line_num + 1].empty()) //下一行为空
                        FillConsoleOutputCharacter(stdout_handle, (TCHAR)' ', deleted_chars_width, end_pos, &cCharsWritten);
                    else {
                        SMALL_RECT scroll_rect;
                        scroll_rect.Bottom = scroll_rect.Top = end_pos.Y;
                        scroll_rect.Left = LEFT + deleted_chars_width;
                        wch = line[operating_line_num + 1].back();
                        if (!isascii(wch))
                            scroll_rect.Right = line_end_pos[operating_line_num + 1] + 1;
                        else
                            scroll_rect.Right = line_end_pos[operating_line_num + 1];
                        tmp_post_end_pos = scroll_rect.Right + 1 - deleted_chars_width;
                        ScrollConsoleScreenBuffer(stdout_handle, &scroll_rect, NULL, end_pos, &blank_char);
                    }
                }
            }
        }
        operating_line_num++;
    }

    //对齐虚拟光标位置
    for (int i = current_line_num + 1; i < line_str_pos.size(); i++) {
        line_str_pos[i] = 0;
        line_cursor_pos[i] = 0;
    }
    make_align();

    refresh_character_count();
    SetConsoleCursorPosition(stdout_handle, input_cursor_pos);
}
Exemplo n.º 19
0
/* Insert n lines at vpos. if n is negative delete -n lines.  */
static void
w32con_ins_del_lines (int vpos, int n)
{
  int	     i, nb;
  SMALL_RECT scroll;
  COORD	     dest;
  CHAR_INFO  fill;
  struct frame *  f = PICK_FRAME ();

  if (n < 0)
    {
      scroll.Top = vpos - n;
      scroll.Bottom = FRAME_LINES (f);
      dest.Y = vpos;
    }
  else
    {
      scroll.Top = vpos;
      scroll.Bottom = FRAME_LINES (f) - n;
      dest.Y = vpos + n;
    }
  scroll.Left = 0;
  scroll.Right = FRAME_COLS (f);

  dest.X = 0;

  fill.Char.AsciiChar = 0x20;
  fill.Attributes = char_attr_normal;

  ScrollConsoleScreenBuffer (cur_screen, &scroll, NULL, dest, &fill);

  /* Here we have to deal with a w32 console flake: If the scroll
     region looks like abc and we scroll c to a and fill with d we get
     cbd... if we scroll block c one line at a time to a, we get cdd...
     Emacs expects cdd consistently... So we have to deal with that
     here... (this also occurs scrolling the same way in the other
     direction.  */

  if (n > 0)
    {
      if (scroll.Bottom < dest.Y)
        {
	  for (i = scroll.Bottom; i < dest.Y; i++)
            {
	      w32con_move_cursor (i, 0);
	      w32con_clear_end_of_line (FRAME_COLS (f));
            }
        }
    }
  else
    {
      nb = dest.Y + (scroll.Bottom - scroll.Top) + 1;

      if (nb < scroll.Top)
        {
	  for (i = nb; i < scroll.Top; i++)
            {
	      w32con_move_cursor (i, 0);
	      w32con_clear_end_of_line (FRAME_COLS (f));
            }
        }
    }

  cursor_coords.X = 0;
  cursor_coords.Y = vpos;
}
Exemplo n.º 20
0
void MessageEditor::insert_work(wchar_t input) {
    //如果输入Ascii字符,新浪微博、人人将其处理为半个“字”,输入“aa”算作输入了一个字,此处为符合作业要求也将其视作一个“字”
    if (character_count >= 140)
        return;
    wch = input;
    character_count++;

    int tmp_post_end_pos;
    DWORD cCharsWritten;
    int insert_ch_width;
    if (!isascii(wch))
        insert_ch_width = 2;
    else
        insert_ch_width = 1;

    bool move_right = true;
    if ((line_str_pos[current_line_num] == 0) && (current_line_num > 0)) { //试图在上一行末尾插入该字
        wch = line[current_line_num - 1].back();
        if (!isascii(wch))
            tmp_post_end_pos = line_end_pos[current_line_num - 1] + 2 + insert_ch_width;
        else
            tmp_post_end_pos = line_end_pos[current_line_num - 1] + 1 + insert_ch_width;
        if (tmp_post_end_pos <= RIGHT + 1) { //能插入,则跳过后面步骤,在上一行末尾插入完后直接前往END
            COORD new_pos = { tmp_post_end_pos - insert_ch_width, input_cursor_pos.Y - 1 };
            line[current_line_num - 1].push_back(input);
            line_end_pos[current_line_num - 1] = tmp_post_end_pos - insert_ch_width;
            FillConsoleOutputCharacter(stdout_handle, input, insert_ch_width, new_pos, &cCharsWritten);
            move_right = false;
            goto END;
        }
    }

    //先在该行插入该字
    if (line[current_line_num].empty())
        tmp_post_end_pos = LEFT + insert_ch_width;
    else {
        wch = line[current_line_num].back();
        if (!isascii(wch))
            tmp_post_end_pos = line_end_pos[current_line_num] + 2 + insert_ch_width;
        else
            tmp_post_end_pos = line_end_pos[current_line_num] + 1 + insert_ch_width;
    }
    line[current_line_num].insert(line_str_pos[current_line_num], 1, input);

    int overflow_chars_count, overflow_chars_width;
    line_overflow(current_line_num, tmp_post_end_pos, overflow_chars_count, overflow_chars_width);

    //重绘当前行
    int operating_line_num;
    if (line_cursor_pos[current_line_num] >= tmp_post_end_pos) { //原来光标所在位置也被顶到下一行
        FillConsoleOutputCharacter(stdout_handle, (TCHAR)' ', RIGHT + 1 - input_cursor_pos.X, input_cursor_pos, &cCharsWritten);
        line_cursor_pos[current_line_num] = LEFT;
        line_str_pos[current_line_num] = 0;
        current_line_num++;
        line_cursor_pos[current_line_num] = LEFT;
        line_str_pos[current_line_num] = 0;
        input_cursor_pos.X = LEFT;
        input_cursor_pos.Y++;
        operating_line_num = current_line_num;
    }
    else {
        COORD new_pos = { input_cursor_pos.X + insert_ch_width, input_cursor_pos.Y };
        SMALL_RECT scroll_rect;
        scroll_rect.Bottom = scroll_rect.Top = input_cursor_pos.Y;
        scroll_rect.Left = line_cursor_pos[current_line_num];
        scroll_rect.Right = tmp_post_end_pos - 1 - insert_ch_width;
        if (scroll_rect.Left <= scroll_rect.Right) //如果在行尾后一格插入,则无需移动
            ScrollConsoleScreenBuffer(stdout_handle, &scroll_rect, NULL, new_pos, &blank_char);
        FillConsoleOutputCharacter(stdout_handle, input, insert_ch_width, input_cursor_pos, &cCharsWritten);
        operating_line_num = current_line_num + 1;
    }

    //将后面的行依次向后移动
    while (operating_line_num < line_str_pos.size()) {
        if (overflow_chars_width == 0)
            break;
        wch = line[operating_line_num].back();
        if (!isascii(wch))
            tmp_post_end_pos = line_end_pos[operating_line_num] + 2 + overflow_chars_width;
        else
            tmp_post_end_pos = line_end_pos[operating_line_num] + 1 + overflow_chars_width;

        int tmp_overflow_chars_count, tmp_overflow_chars_width;
        line_overflow(operating_line_num, tmp_post_end_pos, tmp_overflow_chars_count, tmp_overflow_chars_width);

        //重绘当前行
        COORD new_pos = { LEFT + overflow_chars_width, input_cursor_pos.Y + (operating_line_num - current_line_num) };
        SMALL_RECT scroll_rect;
        scroll_rect.Bottom = scroll_rect.Top = new_pos.Y;
        scroll_rect.Left = LEFT;
        scroll_rect.Right = tmp_post_end_pos - 1 - overflow_chars_width;
        if (scroll_rect.Left <= scroll_rect.Right) //如果在行尾后一格插入,则无需移动
            ScrollConsoleScreenBuffer(stdout_handle, &scroll_rect, NULL, new_pos, &blank_char);
        new_pos.X = tmp_post_end_pos;
        FillConsoleOutputCharacter(stdout_handle, (TCHAR)' ', RIGHT + 1 - new_pos.X, new_pos, &cCharsWritten);

        new_pos.X = LEFT;
        int processing_ch_width;
        for (int i = 0; i < overflow_chars_count; i++) {
            wch = line[operating_line_num][i];
            if (!isascii(wch))
                processing_ch_width = 2;
            else
                processing_ch_width = 1;
            FillConsoleOutputCharacter(stdout_handle, wch, processing_ch_width, new_pos, &cCharsWritten);
            new_pos.X += processing_ch_width;
        }
        overflow_chars_count = tmp_overflow_chars_count;
        overflow_chars_width = tmp_overflow_chars_width;
        operating_line_num++;
    }

END:
    //对齐虚拟光标位置
    for (int i = current_line_num + 1; i < line_str_pos.size(); i++) {
        line_str_pos[i] = 0;
        line_cursor_pos[i] = 0;
    }
    make_align();

    if (move_right)
        right_work();
    refresh_character_count();
    SetConsoleCursorPosition(stdout_handle, input_cursor_pos);
}
Exemplo n.º 21
0
BOOL
consoleScrollVert (
    PSCREEN      pScreen,
    ROW          Top,
    COLUMN       Left,
    ROW          Bottom,
    COLUMN       Right,
    INT          Rows
    )
/*++

Routine Description:

    Scrolls

Arguments:

    pScreen     -   Supplies pointer to screen data
    Top         -   Supplies top row
    Left        -   Supplies left column
    Bottom      -   Supplies bottom row
    Right       -   Supplies right column
    Rows        -   Number of rows to scroll

Return Value:

    TRUE if scrolled
    FALSE otherwise

--*/

{
    PSCREEN_DATA    ScreenData = (PSCREEN_DATA)pScreen;
    SMALL_RECT      Rect;
    COORD           Coord;
    CHAR_INFO       CharInfo;
    BOOLEAN         Ok;
    PLINE_INFO      LineInfo;
    ROW             R;

    if ( Rows ) {

        EnterCriticalSection( &(ScreenData->CriticalSection) );

        //
        //  If there is something to flush, we flush it now
        //
        if ( ScreenData->FirstRow <= ScreenData->LastRow ) {
            consoleShowScreen( pScreen );
        }


        //
        //  Scroll
        //
	Coord.X = (SHORT)Left;
	Coord.Y = (SHORT)Top;

	Rect.Left   = (SHORT)Left;
	Rect.Top    = (SHORT)Top;
	Rect.Right  = (SHORT)Right;
	Rect.Bottom = (SHORT)Bottom;

        if ( Rows > 0 ) {

            Rect.Top    += Rows;

        } else {

            Rect.Bottom += Rows;
            Coord.Y     -= Rows;
        }


        CharInfo.Char.AsciiChar  = ' ';
        CharInfo.Attributes = ScreenData->AttributeNew;

        Ok = ScrollConsoleScreenBuffer(
                ScreenData->ScreenHandle,
                &Rect,
                NULL,
                Coord,
                &CharInfo
                );

        //
        //  Mark all the lines in our buffer as containing garbage
        //
        LineInfo = ScreenData->LineInfo + Top;
        R        = Bottom - Top + 1;

        while ( R-- ) {
            LineInfo->Garbage = TRUE;
            LineInfo++;
        }

        LeaveCriticalSection( &(ScreenData->CriticalSection) );
    }

    return Ok;
}
Exemplo n.º 22
0
//------------------------------------------------------------------------------
static void simulate_sigwinch(COORD expected_cursor_pos)
{
    // In the land of POSIX a terminal would raise a SIGWINCH signal when it is
    // resized. See rl_sigwinch_handler() in readline/signal.c.

    extern int _rl_vis_botlin;
    extern int _rl_last_v_pos;
    CONSOLE_SCREEN_BUFFER_INFO csbi;
    rl_voidfunc_t* redisplay_func_cache;
    int base_y;
    int bottom_line;
    HANDLE handle;

    bottom_line = _rl_vis_botlin - 1;
    handle = GetStdHandle(STD_OUTPUT_HANDLE);

    // Cache redisplay function. Need original as it handles redraw correctly.
    redisplay_func_cache = rl_redisplay_function;
    rl_redisplay_function = rl_redisplay;

    // Cursor may be out of sync with where Readline expects the cursor to be.
    // Put it back where it was, clamping if necessary.
    GetConsoleScreenBufferInfo(handle, &csbi);
    if (expected_cursor_pos.X >= csbi.dwSize.X)
    {
        expected_cursor_pos.X = csbi.dwSize.X - 1;
    }
    if (expected_cursor_pos.Y >= csbi.dwSize.Y)
    {
        expected_cursor_pos.Y = csbi.dwSize.Y - 1;
    }
    SetConsoleCursorPosition(handle, expected_cursor_pos);

    // Let Readline handle the buffer resize.
    RL_SETSTATE(RL_STATE_SIGHANDLER);
    rl_resize_terminal();
    RL_UNSETSTATE(RL_STATE_SIGHANDLER);

    rl_redisplay_function = redisplay_func_cache;

    // Now some redraw edge cases need to be handled.
    GetConsoleScreenBufferInfo(handle, &csbi);
    base_y = csbi.dwCursorPosition.Y - _rl_last_v_pos;

    if (bottom_line > _rl_vis_botlin)
    {
        // Readline SIGWINCH handling assumes that at most one line needs to
        // be cleared which is not the case when resizing from small to large
        // widths.

        CHAR_INFO fill;
        SMALL_RECT rect;
        COORD coord;

        rect.Left = 0;
        rect.Right = csbi.dwSize.X;
        rect.Top = base_y + _rl_vis_botlin + 1;
        rect.Bottom = base_y + bottom_line;

        fill.Char.AsciiChar = ' ';
        fill.Attributes = csbi.wAttributes;

        coord.X = rect.Right + 1;
        coord.Y = rect.Top;

        ScrollConsoleScreenBuffer(handle, &rect, NULL, coord, &fill);
    }
    else
    {
        // Readline never writes to the last column as it wraps the cursor. The
        // last column will have noise when making the width smaller. Clear it.

        CHAR_INFO fill;
        SMALL_RECT rect;
        COORD coord;

        rect.Left = rect.Right = csbi.dwSize.X - 1;
        rect.Top = base_y;
        rect.Bottom = base_y + _rl_vis_botlin;

        fill.Char.AsciiChar = ' ';
        fill.Attributes = csbi.wAttributes;

        coord.X = rect.Right + 1;
        coord.Y = rect.Top;

        ScrollConsoleScreenBuffer(handle, &rect, NULL, coord, &fill);
    }
}
Exemplo n.º 23
0
/* move howmany lines starting at from to to */
static void
ntconio_scroll(int from, int to, int n)
{
    SMALL_RECT sRect;
    COORD dest;
    CHAR_INFO fill;
    int scroll_pause;

    scflush();
    if (to == from)
	return;
#if OPT_PRETTIER_SCROLL
    if (ABS(from - to) > 1) {
	ntconio_scroll(from, (from < to) ? to - 1 : to + 1, n);
	if (from < to)
	    from = to - 1;
	else
	    from = to + 1;
    }
#endif
#ifdef UNICODE
    fill.Char.UnicodeChar = ' ';
#else
    fill.Char.AsciiChar = ' ';
#endif
    fill.Attributes = currentAttribute;

    sRect.Left = 0;
    sRect.Top = (SHORT) from;
    sRect.Right = (SHORT) (csbi.dwMaximumWindowSize.X - 1);
    sRect.Bottom = (SHORT) (from + n - 1);

    dest.X = 0;
    dest.Y = (SHORT) to;

    ScrollConsoleScreenBuffer(hConsoleOutput, &sRect, NULL, dest, &fill);
    if ((scroll_pause = global_g_val(GVAL_SCROLLPAUSE)) > 0) {
	/*
	 * If the user has cheap video HW (1 MB or less) and
	 * there's a busy background app (say, dev studio), then
	 * the console version of vile can exhibit serious repaint
	 * problems when the display is rapidly scrolled.  By
	 * inserting a user-defined sleep after the scroll, the
	 * video HW has a chance to properly paint before the
	 * next scroll operation.
	 */

	Sleep(scroll_pause);
    }
#if !OPT_PRETTIER_SCROLL
    if (ABS(from - to) > n) {
	DWORD cnt;
	COORD coordCursor;

	coordCursor.X = 0;
	if (to > from) {
	    coordCursor.Y = (SHORT) (from + n);
	    cnt = to - from - n;
	} else {
	    coordCursor.Y = (SHORT) (to + n);
	    cnt = from - to - n;
	}
	cnt *= csbi.dwMaximumWindowSize.X;
	erase_at(coordCursor, cnt);
    }
#endif
}
Exemplo n.º 24
0
int Execute(HANDLE hPlugin,const char *CmdStr,bool HideOutput,
            bool Silent,bool ShowTitle, int MWaitForExternalProgram,
			bool SeparateWindow)
{
    STARTUPINFO si;
    PROCESS_INFORMATION pi;
    int ExitCode, CreateProcessCode;

    memset(&si,0,sizeof(si));
    si.cb=sizeof(si);

	HANDLE hChildStdoutRd,hChildStdoutWr;
	HANDLE StdInput=GetStdHandle(STD_INPUT_HANDLE);
	HANDLE StdOutput=GetStdHandle(STD_OUTPUT_HANDLE);
	HANDLE StdError=GetStdHandle(STD_ERROR_HANDLE);
	HANDLE hScreen=NULL;
	CONSOLE_SCREEN_BUFFER_INFO csbi;

	if (HideOutput)
	{
		SECURITY_ATTRIBUTES saAttr;
		saAttr.nLength = sizeof(SECURITY_ATTRIBUTES);
		saAttr.bInheritHandle = TRUE;
		saAttr.lpSecurityDescriptor = NULL;

		if (CreatePipe(&hChildStdoutRd, &hChildStdoutWr, &saAttr, 32768))
		{
			SetStdHandle(STD_OUTPUT_HANDLE,hChildStdoutWr);
			SetStdHandle(STD_ERROR_HANDLE,hChildStdoutWr);

			if (Silent)
			{
				hScreen=Far::SaveScreen (0,0,-1,0);
				Far::Text (2,0,7,MWaitForExternalProgram);
			}
			else
			{
				hScreen=Far::SaveScreen();
				FarMessage msg;
				msg.AddLine ("");
				msg.AddLine (MWaitForExternalProgram);
				msg.Show();
			}
		}
		else
			HideOutput=false;
	}
	else
	{
		GetConsoleScreenBufferInfo(StdOutput,&csbi);

		char Blank[1024];
		FillMemory (Blank, csbi.dwSize.X, ' ');
		Blank [csbi.dwSize.X] = '\0';
		for (int Y=0;Y<csbi.dwSize.Y;Y++)
			Far::Text (0, Y, 7, Blank);
		Far::FlushText();

		COORD C;
		C.X=0;
		C.Y=csbi.dwCursorPosition.Y;
		SetConsoleCursorPosition(StdOutput,C);
	}


	DWORD ConsoleMode;
	GetConsoleMode(StdInput,&ConsoleMode);
	SetConsoleMode(StdInput,ENABLE_PROCESSED_INPUT|ENABLE_LINE_INPUT|
		             ENABLE_ECHO_INPUT|ENABLE_MOUSE_INPUT);

	char ExpandedCmd[260];
	ExpandEnvironmentStrings(CmdStr,ExpandedCmd,sizeof(ExpandedCmd));

	char SaveTitle[512];
	GetConsoleTitle(SaveTitle,sizeof(SaveTitle));
	if (ShowTitle)
		SetConsoleTitle(ExpandedCmd);

	CreateProcessCode=CreateProcess(NULL,ExpandedCmd,NULL,NULL,HideOutput,0,NULL,NULL,&si,&pi);

	if (HideOutput)
	{
		SetStdHandle(STD_OUTPUT_HANDLE,StdOutput);
		SetStdHandle(STD_ERROR_HANDLE,StdError);
		CloseHandle(hChildStdoutWr);
	}

	if (CreateProcessCode)
	{
		if (SeparateWindow)
			ExitCode = 0;
		else 
		{
			if (HideOutput)
			{
				WaitForSingleObject(pi.hProcess,1000);

				char PipeBuf[32768];
				DWORD Read;
				while (ReadFile(hChildStdoutRd,PipeBuf,sizeof(PipeBuf),&Read,NULL))
					;
				CloseHandle(hChildStdoutRd);
			}
			WaitForSingleObject(pi.hProcess,INFINITE);
			GetExitCodeProcess(pi.hProcess,(LPDWORD)&ExitCode);
		}
		CloseHandle(pi.hThread);
		CloseHandle(pi.hProcess);
	}
	else if (HideOutput)
		CloseHandle (hChildStdoutRd);
	SetConsoleTitle(SaveTitle);
	SetConsoleMode(StdInput,ConsoleMode);
	if (!HideOutput)
	{
		SMALL_RECT src;
		COORD dest;
		CHAR_INFO fill;
		src.Left=0;
		src.Top=2;
		src.Right=csbi.dwSize.X;
		src.Bottom=csbi.dwSize.Y;
		dest.X=dest.Y=0;
		fill.Char.AsciiChar=' ';
		fill.Attributes=7;
		ScrollConsoleScreenBuffer(StdOutput,&src,NULL,dest,&fill);
		FarCtrl (hPlugin).SetUserScreen();
	}
	if (hScreen)
	{
		Far::RestoreScreen (NULL);
		Far::RestoreScreen (hScreen);
	}
	if (!CreateProcessCode) return -1;
	else return ExitCode;
}
Exemplo n.º 25
0
HANDLE WINAPI OpenW(const struct OpenInfo *Info)
{
    const int CUR_DIR_SIZE = 100000;
    char* filename = 0;

    switch( Info->OpenFrom )
    {
    case OPEN_COMMANDLINE:
        {
            OpenCommandLineInfo* cinfo = (OpenCommandLineInfo*)Info->Data;

            const wchar_t* cmdline = cinfo->CommandLine;
            if( !cmdline )
                return INVALID_HANDLE_VALUE;

            while( *cmdline && *cmdline <= ' ' )
                cmdline++;

            if( *cmdline )
                filename = w2a( cmdline );
            else
                return 0;
            break;
        }
    case OPEN_PLUGINSMENU:
        {
            FarGetPluginPanelItem pinfo;
            PluginPanelItem* pitem = (PluginPanelItem*)malloc(CUR_DIR_SIZE);
            ZeroMemory(&pinfo, sizeof(pinfo));
            ZeroMemory(pitem, CUR_DIR_SIZE);
            pinfo.StructSize = sizeof(pinfo);
            pinfo.Size = CUR_DIR_SIZE;
            pinfo.Item = pitem;

            if(InfoW.PanelControl( PANEL_ACTIVE, FCTL_GETCURRENTPANELITEM, 0, &pinfo ))
            {
                filename = w2a( pinfo.Item->FileName );
                free(pitem);
            }
            else
            {
                free(pitem);
                return 0;
            }
            break;
        }
    default:
        return 0;
    }
    
    if( !filename )
        return 0;

    wchar_t comspec[MAX_PATH * 2];
    if( !GetEnvironmentVariableW( L"COMSPEC", comspec, sizeofa( comspec ) ) )
        lstrcpyW( comspec, L"cmd.exe" );

    char pipename[100];
    wsprintf( pipename, "\\\\.\\pipe\\FarCall%ul", GetCurrentProcessId() );

    char* batchstr = (char*)malloc( 10000 );
    wsprintf( batchstr, batch, filename, ModuleName, pipename );

    // obtaining temp file name
    wchar_t tmp[MAX_PATH * 10];
    GetTempPathW( sizeofa( tmp ), tmp );
    GetTempFileNameW( tmp, L"", 0, tmp );
    DeleteFileW( tmp );

    lstrcatW( tmp, L".bat" );

    HANDLE file = CreateFileW( tmp, GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE, 0, CREATE_ALWAYS, 0, 0 );
    if( !file || file == INVALID_HANDLE_VALUE )
    {
        DeleteFileW( tmp );
        free( filename );
        free( batchstr );
        return INVALID_HANDLE_VALUE;
    }

    DWORD written;
    WriteFile( file, batchstr, lstrlen( batchstr ), &written, 0 );
    CloseHandle( file );

    wchar_t cmd[MAX_PATH * 10] = L"\"";
    lstrcatW( lstrcatW( lstrcatW( lstrcatW( cmd, comspec ), L"\" /c \"" ), tmp ), L"\"");

    STARTUPINFOW sinfo;
    ZeroMemory( &sinfo, sizeof( sinfo ) );
    sinfo.cb = sizeof( sinfo );

    PROCESS_INFORMATION pinfo;

    Handle np( CreateNamedPipe( pipename, PIPE_ACCESS_DUPLEX, PIPE_WAIT,
                                PIPE_UNLIMITED_INSTANCES, 100, 100, 0, 0 ) );

    connected = false;

    DWORD id;
    Handle thread( CreateThread( 0, 0, ListenEnv, np, 0, &id ) );
    
    while( !connected )
        Sleep( 100 );
    
    CONSOLE_SCREEN_BUFFER_INFO csbi;
    GetConsoleScreenBufferInfo( GetStdHandle( STD_OUTPUT_HANDLE ), &csbi );
    
#ifndef LIGHTGRAY
#define LIGHTGRAY 7
#endif

    wchar_t Blank[1024];
    FSFW.sprintf(Blank,L"%*s",csbi.dwSize.X,L"");
    FarColor fc = {FCF_NONE, LIGHTGRAY, 0, 0};
    for (int Y=0;Y<csbi.dwSize.Y;Y++)
        InfoW.Text(0,Y,&fc,Blank);
    InfoW.Text(0,0,0,NULL);
    
    COORD C;
    C.X=0;
    C.Y=csbi.dwCursorPosition.Y;
    SetConsoleCursorPosition( GetStdHandle( STD_OUTPUT_HANDLE ), C );

    wchar_t* curr_dir = (wchar_t*)malloc(CUR_DIR_SIZE);
    
    FSFW.GetCurrentDirectory(CUR_DIR_SIZE, curr_dir);

    if( np && CreateProcessW( NULL, cmd, 0, 0, TRUE, 0, 0, curr_dir[0] ? curr_dir : 0, &sinfo, &pinfo ) )
    {

        HANDLE ar[] = {pinfo.hProcess, np};

        WaitForMultipleObjects( 2, ar, TRUE, INFINITE );
        CloseHandle(pinfo.hProcess);
        CloseHandle(pinfo.hThread);
        SMALL_RECT src;
        COORD dest;
        CHAR_INFO fill;
        src.Left=0;
        src.Top=2;
        src.Right=csbi.dwSize.X;
        src.Bottom=csbi.dwSize.Y;
        dest.X=dest.Y=0;
        fill.Char.AsciiChar=' ';
        fill.Attributes=7;
        ScrollConsoleScreenBuffer( GetStdHandle( STD_OUTPUT_HANDLE ), &src, NULL, dest, &fill);

        InfoW.AdvControl(0, ACTL_REDRAWALL, 0, 0);
    }
    else
        Handle onp( CreateFile( pipename, GENERIC_WRITE,
            FILE_SHARE_READ | FILE_SHARE_WRITE, 0, OPEN_EXISTING, 0, 0 ) );

    
    free( filename );
    free( batchstr );
    free( curr_dir );
    DeleteFileW( tmp );
    
    return 0;
}
Exemplo n.º 26
0
static void InterpretEscSeq(void)
{
	int i;
	WORD attribut;
	CONSOLE_SCREEN_BUFFER_INFO Info;
	DWORD NumberOfCharsWritten;
	COORD Pos;
	SMALL_RECT Rect;
	CHAR_INFO CharInfo;

	if (prefix != '[')
		return;
	GetConsoleScreenBufferInfo(hConOut, &Info);
	switch (suffix) {
	case 'm':
		if (es_argc == 0)
			es_argv[es_argc++] = 0;
		for (i = 0; i < es_argc; i++) {
			switch (es_argv[i]) {
			case 0:
				foreground = FOREGROUND_WHITE;
				background = BACKGROUND_BLACK;
				bold = 0;
				underline = 0;
				rvideo = 0;
				concealed = 0;
				break;
			case 1:
				bold = 1;
				break;
			case 21:
				bold = 0;
				break;
			case 4:
				underline = 1;
				break;
			case 24:
				underline = 0;
				break;
			case 7:
				rvideo = 1;
				break;
			case 27:
				rvideo = 0;
				break;
			case 8:
				concealed = 1;
				break;
			case 28:
				concealed = 0;
				break;
			}
			if ((30 <= es_argv[i]) && (es_argv[i] <= 37))
				foreground = (WORD)(es_argv[i] - 30);
			if ((40 <= es_argv[i]) && (es_argv[i] <= 47))
				background = (WORD)(es_argv[i] - 40);
		}
		if (rvideo)
			attribut = foregroundcolor[background] | backgroundcolor[foreground];
		else
			attribut = foregroundcolor[foreground] | backgroundcolor[background];
		if (bold)
			attribut |= FOREGROUND_INTENSITY;
		if (underline)
			attribut |= BACKGROUND_INTENSITY;
		SetConsoleTextAttribute(hConOut, attribut);
		return;

	case 'J':
		if (es_argc == 0)
			es_argv[es_argc++] = 0;	// ESC[J == ESC[0J
		if (es_argc != 1)
			return;
		switch (es_argv[0]) {
		case 0:	// ESC[0J erase from cursor to end of display
			FillConsoleOutputCharacter(hConOut, ' ', (Info.dwSize.Y - Info.dwCursorPosition.Y - 1) * Info.dwSize.X + Info.dwSize.X - Info.dwCursorPosition.X - 1, Info.dwCursorPosition, &NumberOfCharsWritten);
			FillConsoleOutputAttribute(hConOut, Info.wAttributes, (Info.dwSize.Y - Info.dwCursorPosition.Y - 1) * Info.dwSize.X + Info.dwSize.X - Info.dwCursorPosition.X - 1, Info.dwCursorPosition, &NumberOfCharsWritten);
			return;

		case 1:	// ESC[1J erase from start to cursor.
			Pos.X = 0;
			Pos.Y = 0;
			FillConsoleOutputCharacter(hConOut, ' ', Info.dwCursorPosition.Y * Info.dwSize.X + Info.dwCursorPosition.X + 1, Pos, &NumberOfCharsWritten);
			FillConsoleOutputAttribute(hConOut, Info.wAttributes, Info.dwCursorPosition.Y * Info.dwSize.X + Info.dwCursorPosition.X + 1, Pos, &NumberOfCharsWritten);
			return;

		case 2:	// ESC[2J Clear screen and home cursor
			Pos.X = 0;
			Pos.Y = 0;
			FillConsoleOutputCharacter(hConOut, ' ', Info.dwSize.X * Info.dwSize.Y, Pos, &NumberOfCharsWritten);
			FillConsoleOutputAttribute(hConOut, Info.wAttributes, Info.dwSize.X * Info.dwSize.Y, Pos, &NumberOfCharsWritten);
			SetConsoleCursorPosition(hConOut, Pos);
			return;

		default:
			return;
		}

	case 'K':
		if (es_argc == 0)
			es_argv[es_argc++] = 0;	// ESC[K == ESC[0K
		if (es_argc != 1)
			return;
		switch (es_argv[0]) {
		case 0:	// ESC[0K Clear to end of line
			FillConsoleOutputCharacter(hConOut, ' ', Info.srWindow.Right - Info.dwCursorPosition.X + 1, Info.dwCursorPosition, &NumberOfCharsWritten);
			FillConsoleOutputAttribute(hConOut, Info.wAttributes, Info.srWindow.Right - Info.dwCursorPosition.X + 1, Info.dwCursorPosition, &NumberOfCharsWritten);
			return;

		case 1:	// ESC[1K Clear from start of line to cursor
			Pos.X = 0;
			Pos.Y = Info.dwCursorPosition.Y;
			FillConsoleOutputCharacter(hConOut, ' ', Info.dwCursorPosition.X + 1, Pos, &NumberOfCharsWritten);
			FillConsoleOutputAttribute(hConOut, Info.wAttributes, Info.dwCursorPosition.X + 1, Pos, &NumberOfCharsWritten);
			return;

		case 2:	// ESC[2K Clear whole line.
			Pos.X = 0;
			Pos.Y = Info.dwCursorPosition.Y;
			FillConsoleOutputCharacter(hConOut, ' ', Info.dwSize.X, Pos, &NumberOfCharsWritten);
			FillConsoleOutputAttribute(hConOut, Info.wAttributes, Info.dwSize.X, Pos, &NumberOfCharsWritten);
			return;

		default:
			return;
		}

	case 'L':	// ESC[#L Insert # blank lines.
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[L == ESC[1L
		if (es_argc != 1)
			return;
			Rect.Left = 0;
			Rect.Top = Info.dwCursorPosition.Y;
			Rect.Right = Info.dwSize.X - 1;
			Rect.Bottom = Info.dwSize.Y - 1;
			Pos.X = 0;
			Pos.Y = (SHORT)(Info.dwCursorPosition.Y + es_argv[0]);
			CharInfo.Char.AsciiChar = ' ';
			CharInfo.Attributes = Info.wAttributes;
			ScrollConsoleScreenBuffer(hConOut, &Rect, NULL, Pos, &CharInfo);
			Pos.X = 0;
			Pos.Y = Info.dwCursorPosition.Y;
			FillConsoleOutputCharacter(hConOut, ' ', Info.dwSize.X * es_argv[0], Pos, &NumberOfCharsWritten);
			FillConsoleOutputAttribute(hConOut, Info.wAttributes, Info.dwSize.X * es_argv[0], Pos, &NumberOfCharsWritten);
			return;

	case 'M':	// ESC[#M Delete # line.
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[M == ESC[1M
		if (es_argc != 1)
			return;
		if (es_argv[0] > Info.dwSize.Y - Info.dwCursorPosition.Y)
			es_argv[0] = Info.dwSize.Y - Info.dwCursorPosition.Y;
		Rect.Left = 0;
		Rect.Top = (SHORT)(Info.dwCursorPosition.Y + es_argv[0]);
		Rect.Right = Info.dwSize.X - 1;
		Rect.Bottom = Info.dwSize.Y - 1;
		Pos.X = 0;
		Pos.Y = Info.dwCursorPosition.Y;
		CharInfo.Char.AsciiChar = ' ';
		CharInfo.Attributes = Info.wAttributes;
		ScrollConsoleScreenBuffer(hConOut, &Rect, NULL, Pos, &CharInfo);
		Pos.Y = (SHORT)(Info.dwSize.Y - es_argv[0]);
		FillConsoleOutputCharacter(hConOut, ' ', Info.dwSize.X * es_argv[0], Pos, &NumberOfCharsWritten);
		FillConsoleOutputAttribute(hConOut, Info.wAttributes, Info.dwSize.X * es_argv[0], Pos, &NumberOfCharsWritten);
		return;

	case 'P':	// ESC[#P Delete # characters.
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[P == ESC[1P
		if (es_argc != 1)
			return;
		if (Info.dwCursorPosition.X + es_argv[0] > Info.dwSize.X - 1)
			es_argv[0] = Info.dwSize.X - Info.dwCursorPosition.X;

		Rect.Left = (SHORT)(Info.dwCursorPosition.X + es_argv[0]);
		Rect.Top = Info.dwCursorPosition.Y;
		Rect.Right = Info.dwSize.X - 1;
		Rect.Bottom = Info.dwCursorPosition.Y;
		CharInfo.Char.AsciiChar = ' ';
		CharInfo.Attributes = Info.wAttributes;
		ScrollConsoleScreenBuffer(hConOut, &Rect, NULL, Info.dwCursorPosition, &CharInfo);
		Pos.X = (SHORT)(Info.dwSize.X - es_argv[0]);
		Pos.Y = Info.dwCursorPosition.Y;
		FillConsoleOutputCharacter(hConOut, ' ', es_argv[0], Pos, &NumberOfCharsWritten);
		return;

	case '@':	// ESC[#@ Insert # blank characters.
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[@ == ESC[1@
		if (es_argc != 1)
			return;
		if (Info.dwCursorPosition.X + es_argv[0] > Info.dwSize.X - 1)
			es_argv[0] = Info.dwSize.X - Info.dwCursorPosition.X;
		Rect.Left = Info.dwCursorPosition.X;
		Rect.Top = Info.dwCursorPosition.Y;
		Rect.Right = Info.dwSize.X - 1 - es_argv[0];
		Rect.Bottom = Info.dwCursorPosition.Y;
		Pos.X = Info.dwCursorPosition.X + es_argv[0];
		Pos.Y = Info.dwCursorPosition.Y;
		CharInfo.Char.AsciiChar = ' ';
		CharInfo.Attributes = Info.wAttributes;
		ScrollConsoleScreenBuffer(hConOut, &Rect, NULL, Pos, &CharInfo);
		FillConsoleOutputCharacter(hConOut, ' ', es_argv[0], Info.dwCursorPosition, &NumberOfCharsWritten);
		FillConsoleOutputAttribute(hConOut, Info.wAttributes, es_argv[0], Info.dwCursorPosition, &NumberOfCharsWritten);
		return;

	case 'A':	// ESC[#A Moves cursor up # lines
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[A == ESC[1A
		if (es_argc != 1)
			return;
		Pos.X = Info.dwCursorPosition.X;
		Pos.Y = Info.dwCursorPosition.Y - es_argv[0];
		if (Pos.Y < 0)
			Pos.Y = 0;
		SetConsoleCursorPosition(hConOut, Pos);
		return;

	case 'B':	// ESC[#B Moves cursor down # lines
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[B == ESC[1B
		if (es_argc != 1)
			return;
		Pos.X = Info.dwCursorPosition.X;
		Pos.Y = Info.dwCursorPosition.Y + es_argv[0];
		if (Pos.Y >= Info.dwSize.Y)
			Pos.Y = Info.dwSize.Y - 1;
		SetConsoleCursorPosition(hConOut, Pos);
		return;

	case 'C':	// ESC[#C Moves cursor forward # spaces
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[C == ESC[1C
		if (es_argc != 1)
			return;
		Pos.X = Info.dwCursorPosition.X + es_argv[0];
		if (Pos.X >= Info.dwSize.X)
			Pos.X = Info.dwSize.X - 1;
		Pos.Y = Info.dwCursorPosition.Y;
		SetConsoleCursorPosition(hConOut, Pos);
		return;

	case 'D':	// ESC[#D Moves cursor back # spaces
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[D == ESC[1D
		if (es_argc != 1)
			return;
		Pos.X = Info.dwCursorPosition.X - es_argv[0];
		if (Pos.X < 0)
			Pos.X = 0;
		Pos.Y = Info.dwCursorPosition.Y;
		SetConsoleCursorPosition(hConOut, Pos);
		return;

	case 'E':	// ESC[#E Moves cursor down # lines, column 1.
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[E == ESC[1E
		if (es_argc != 1)
			return;
		Pos.X = 0;
		Pos.Y = Info.dwCursorPosition.Y + es_argv[0];
		if (Pos.Y >= Info.dwSize.Y)
			Pos.Y = Info.dwSize.Y - 1;
		SetConsoleCursorPosition(hConOut, Pos);
		return;

	case 'F':	// ESC[#F Moves cursor up # lines, column 1.
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[F == ESC[1F
		if (es_argc != 1)
			return;
		Pos.X = 0;
		Pos.Y = Info.dwCursorPosition.Y - es_argv[0];
		if (Pos.Y < 0)
			Pos.Y = 0;
		SetConsoleCursorPosition(hConOut, Pos);
		return;

	case 'G':	// ESC[#G Moves cursor column # in current row.
		if (es_argc == 0)
			es_argv[es_argc++] = 1;	// ESC[G == ESC[1G
		if (es_argc != 1)
			return;
		Pos.X = es_argv[0] - 1;
		if (Pos.X >= Info.dwSize.X)
			Pos.X = Info.dwSize.X - 1;
		if (Pos.X < 0)
			Pos.X = 0;
		Pos.Y = Info.dwCursorPosition.Y;
		SetConsoleCursorPosition(hConOut, Pos);
		return;

	case 'f':
	case 'H':	// ESC[#;#H or ESC[#;#f Moves cursor to line #, column #
		if (es_argc == 0) {
			es_argv[es_argc++] = 1;	// ESC[G == ESC[1;1G
			es_argv[es_argc++] = 1;
		}
		if (es_argc == 1) {
			es_argv[es_argc++] = 1;	// ESC[nG == ESC[n;1G
		}
		if (es_argc > 2)
			return;
		Pos.X = es_argv[1] - 1;
		if (Pos.X < 0)
			Pos.X = 0;
		if (Pos.X >= Info.dwSize.X)
			Pos.X = Info.dwSize.X - 1;
		Pos.Y = es_argv[0] - 1;
		if (Pos.Y < 0)
			Pos.Y = 0;
		if (Pos.Y >= Info.dwSize.Y)
			Pos.Y = Info.dwSize.Y - 1;
		SetConsoleCursorPosition(hConOut, Pos);
		return;

	case 's':	// ESC[s Saves cursor position for recall later
		if (es_argc != 0)
			return;
		SavePos.X = Info.dwCursorPosition.X;
		SavePos.Y = Info.dwCursorPosition.Y;
		return;

	case 'u':	// ESC[u Return to saved cursor position
		if (es_argc != 0)
			return;
		SetConsoleCursorPosition(hConOut, SavePos);
		return;
	}
}