如何防止控制台在最后一行写一个字符?

时间:2014-01-08 15:05:35

标签: c# arrays char console-application console.writeline

我对C#的控制台项目有疑问。我想使用整个控制台屏幕在其中写入文本。例如,意味着沿着控制台的边界“绘制”边框。 问题是最后一行中不必要的最后一个字符。我该如何预防?

为了更好地理解,我添加了不需要的字符的图片。Screenshot of the console

我通过填充二维chars数组并使用以下方法转储它来绘制它。 yMax是高度,xMax是控制台窗口的宽度。

private void DumpCharacters()
    {
        for (int y = 0; y < yMax - 1; y++)
        {
            string line = string.Empty;
            for (int x = 0; x < xMax; x++)
            {
                line += characters[x, y];
            }
            Console.SetCursorPosition(0, y);
            Console.Write(line);
        }
    }

我已经尝试增加边框的高度,但之后,提到的字符会覆盖该位置的边框。

修改 对不起,我的解释不清楚。当然,就像AttilaBujáki所说,我的意思是跳到最后一行。是否有可能阻止这种情况?

3 个答案:

答案 0 :(得分:6)

使用Console

CursorVisible属性
Console.CursorVisible = false;

答案 1 :(得分:5)

如果你想用你的角色填充整个控制台窗口,可能的方法是将光标移回0,0位置。

示例:

Console.CursorVisible = false;
for(int i = 0; i < Console.WindowHeight * Console.WindowWidth; i ++)
{
     Console.Write((i / Console.WindowWidth) % 10);  // print your stuff
}
Console.SetCursorPosition(0, 0);

Console.ReadKey();

所以你可以在你的方法中这样做:

private void DumpCharacters()
    {
        for (int y = 0; y < yMax; y++)
        {
            string line = string.Empty;
            for (int x = 0; x < xMax; x++)
            {
                line += characters[x, y];
            }
            Console.SetCursorPosition(0, y);
            Console.Write(line);
        }
        Console.SetCursorPosition(0, 0);
    }

请注意,您不必从yMax中减去一个。这是因为现在您也可以使用控制台屏幕的最后一行。

Console with an character border

以下是生成所需结果的完整代码:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleChar
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.Title = "Stackoverflow - Super example";
            Console.CursorVisible = false;

            int yMax = Console.WindowHeight;
            int xMax = Console.WindowWidth;
            char[,] characters= new char[Console.WindowWidth, Console.WindowHeight];

            for (int i = 0; i < Console.WindowWidth; i++ )
            {
                for (int j = 0; j < Console.WindowHeight; j++)
                {
                    char currentChar = ' ';

                    if((i == 0) || (i == Console.WindowWidth - 1))
                    {
                        currentChar = '║';
                    }
                    else
                    {
                        if((j == 0) || (j == Console.WindowHeight - 1))
                        {
                            currentChar = '═';
                        }
                    }                    

                    characters[i, j] = currentChar;
                }
            }

            characters[0, 0] = '╔';
            characters[Console.WindowWidth-1, 0] = '╗';
            characters[0, Console.WindowHeight - 1] = '╚';
            characters[Console.WindowWidth - 1, Console.WindowHeight - 1] = '╝';

                for (int y = 0; y < yMax ; y++)
                {
                    string line = string.Empty;
                    for (int x = 0; x < xMax; x++)
                    {
                        line += characters[x, y];
                    }
                    Console.SetCursorPosition(0, y);
                    Console.Write(line);
                }
            Console.SetCursorPosition(0, 0);
        }
    }
}

答案 2 :(得分:1)

如果Console缓冲区大小与窗口大小相同,则接受的答案不起作用。如上所述Phillip Scott Givens,您必须使用Console.MoveBufferArea写入除右下角之外的其他位置。这是使用System.Console API解决问题的唯一方法,即使使用Console.CursorVisible = false也是如此。示例代码:

var w = Console.WindowWidth;
var h = Console.WindowHeight;
Console.SetBufferSize(w, h);

// Draw all but bottom-right 2 characters of box here ...

// HACK: Console.Write will automatically advance the cursor position at the end of each
// line which will push the buffer upwards resulting in the loss of the first line
var sourceReplacement = '═';
Console.SetCursorPosition(w - 2, h - 1); // bottom-right minus 1
Console.Write('╝');
// Move from bottom-right minus 1 to bottom-right overwriting the source
// with the replacement character
Console.MoveBufferArea(w - 2, h - 1, 1, 1, w - 1, h - 1,
    sourceReplacement, Console.ForegroundColor, Console.BackgroundColor);

如果您对此不满意,可以使用本机控制台API(但它仅限Windows):

// http://pinvoke.net/default.aspx/kernel32/FillConsoleOutputCharacter.html
[DllImport("kernel32.dll", SetLastError = true)]
static extern bool FillConsoleOutputCharacter(
    IntPtr hConsoleOutput,
    char cCharacter,
    uint nLength,
    COORD dwWriteCoord,
    out uint lpNumberOfCharsWritten
    );