65.9K
CodeProject 正在变化。 阅读更多。
Home

控制台增强功能

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.87/5 (102投票s)

2003年6月29日

CPOL

7分钟阅读

viewsIcon

323792

downloadIcon

4047

本文增强了 .NET 中的控制台支持,例如清除、彩色文本等;在 Windows 应用程序和 DOS 应用程序中启用控制台支持;并简化了 .NET 应用程序的测试和调试。

引言

System.Console 是框架提供的用于处理控制台 I/O 和重定向的类。Win32 API 还支持一组控制台 API。Win32 为每个应用程序(进程)支持一个控制台,即使是 Windows 窗体应用程序。控制台支持诸如缓冲、全屏模式、颜色等许多功能。您可以调用另一个进程并将其输出捕获到您自己的控制台中。对于控制台应用程序,控制台是从调用进程继承的;然而,Windows 应用程序与任何控制台都分离。

不幸的是,Console 类并未充分利用控制台 API 支持的大多数功能。因此,我引入了一个名为 WinConsole 的新类,它提供了 Win32 类提供的更多功能。它提供了一些更受欢迎的控制台功能,但尚未全部提供。它可以在控制台应用程序和 Windows 应用程序以及类库中使用。我计划在未来添加全部功能。

最初我打算将其用于调试目的,并打算将其命名为 DebugConsole,但它也被用作现有 Console 类的替代或扩展。我发现,在功能齐全的 Windows 应用程序中测试低级别的无 UI 数据结构或类非常困难。标准 I/O 不再起作用。调试器输出窗口只是控制台的糟糕替代品。它的功能比控制台少,并且需要应用程序和调试器之间切换。现在,有了 WinConsole,Console.WriteLine() Console.ReadLine() 都可用于 WinForms 应用程序。

Web 应用程序仍然无法使用。抱歉。

控制台应用程序中的 WinConsole

Console 应用程序中,WinConsole 提供了其他功能,例如:

1) 隐藏和显示控制台窗口 (WinConsole.Visible = false)
2) 清除控制台窗口 (WinConsole.Clear())
3) 获取或设置光标位置
4) 将文本颜色更改为 16 种不同的控制台颜色之一 (WinConsole.Color = ConsoleColor.Red)

<Sample image

5) 按照上面的示例,使用不同的颜色显示标准错误输出。
6) 写入错误消息时自动闪烁窗口并发出蜂鸣声。(WinConsole.Beep())
7) 以不同的颜色方案捕获断言和跟踪到标准错误

要读取输入和写入输出,您可以使用 Console.WriteLineConsole.ReadLine。您也可以使用 WinConsole.WriteLineWinConsole.ReadLine但它总是会转交给 Console 函数。

 

Windows 应用程序中的 WinConsole

WinConsole 在 Windows 应用程序环境中真正 shines。它允许在主应用程序窗口旁边使用一个额外的控制台窗口,该窗口可以随时隐藏和显示。它包含了上面列出的所有控制台应用程序的附加增强功能,以及更多功能。

WinConsole 特别适用于调试和跟踪。由于缺少控制台窗口来报告有趣的[有用的]消息,因此从控制台应用程序迁移到 Windows 应用程序时,测试数据结构会变得更加困难。标准的 Debug.WriteTrace.Write 调用 OutputDebugString,该函数将数据发送到有限的调试器输出窗口。

使用 WinConsole,来自 Debug.Write(Line)Trace.Write(Line) 甚至 Console.Write(Line)Console.Error.Write(Line) 的调用都可以输出到应用程序控制台窗口,每种输出都可以有自己独立的颜色。除了着色之外,还有一个可以选取的闪烁模式(闪烁一次,闪烁直到响应)来提醒开发人员/测试人员警告和错误消息。

还可以通过 Console.Read(Line). 从控制台窗口读取输入。这允许应用程序以简单的同步模型而不是更复杂的事件驱动模型轻松接收用户输入。这样,就可以为应用程序开发一个完整的命令行系统,用于在运行时执行各种测试。

最好的一点是,控制台窗口由操作系统在单独的线程中拥有和绘制,因此即使在进入中断模式或在调试器和应用程序之间切换后,它也始终可见。相比之下,普通应用程序窗口会冻结——由于中断后事件处理被挂起,它们无法重绘。

WinConsole API

要在 Windows 应用程序中使用 WinConsole,应在控制台使用之前某个时候为 WinConsole.Visible 赋值。当然,为了看到任何内容,赋值需要为 true。或者,可以调用 WinConsole.Initialize(),但控制台可能不可见。

在控制台应用程序中,WinConsole.Initialize() 就足够了。WinConsole 中的大多数属性和方法也会在尚未发生初始化的情况下触发初始化。

以下是属性列表。

属性 描述
缓冲区 (IntPtr) 获取当前的 Win32 缓冲区句柄
缓冲区大小 (Coord) 返回缓冲区大小
Color (ConsoleColor) 获取或设置当前文本和背景颜色以及其他文本属性
CtrlBreakPressed (bool) 指示是否按下了 Ctrl+Break。读取后值会自动清除。
CursorPosition (Coord) 获取和设置当前光标位置
句柄 (IntPtr) 获取控制台窗口的 HWNDof the console window
MaximumScreenSize (Coord) 返回给定桌面尺寸的最大屏幕尺寸
ParentHandle 获取并设置控制台窗口的新父 hwnd
ScreenSize (Coord) 返回缓冲区可见窗口的坐标
标题 获取或设置控制台窗口的标题
Visible 指定控制台窗口是可见还是隐藏

要更改文本颜色,必须将 Color 分配给 ConsoleColor

ConsoleColor 是一个 enum,包含标志 Red, Blue, Green, Intensified, RedBG, BlueBG, GreenBG, IntensifiedBG。BG 颜色用于背景色。通过使用各种颜色标志的组合,可以为文本实现 16 种颜色,为背景实现 16 种颜色。要产生白色,必须设置 Red|Green|Blue|Intensified。当缺少 intensified 标志时,unintensified 颜色介于黑色和所选颜色之间。因此,白色变为灰色,红色变为暗红色,依此类推。

以下是属性列表。

方法 描述
Beep() 发出简单的蜂鸣声
Clear() 清空控制台窗口
Flash(bool) 闪烁控制台窗口(目前在我机器上无法正常工作,如果您能弄清楚原因,我将不胜感激)
GetWindowPosition(out int x, out int y, out int width, out int height) 获取控制台窗口的像素位置和大小
Initialize() 初始化 WinConsole -- 应在使用它的程序的开头调用
LaunchNotepadDialog(string arguments)  
RedirectDebugOutput(bool clear, ConsoleColor color, bool beep) 将调试输出重定向到控制台
clear - 先清除所有其他监听器
color - 用于显示调试输出的颜色
RedirectTraceOutput(bool clear, ConsoleColor color)
 
将跟踪输出重定向到控制台
SetWindowPosition(int x, int y, int width, int height) 设置控制台窗口的像素位置和大小

除了这些方法和属性之外,WinConsole 还包含所有标准的 Console 方法和属性,它只是将它们重定向到 Console 类,因此调用 Console 方法与其对应的 WinConsole 方法之间没有任何区别。例如,WinConsole.WriteLine 调用 Console.WriteLine

对标准错误输出、调试输出或跟踪输出进行着色

我还包含了一个 ConsoleWriter 类,可用于为控制台窗口提供彩色输出、闪烁和/或蜂鸣声。

ConsoleWriter 是通过调用 ConsoleWriter(TextWriter writer, ConsoleColor color, ConsoleFlashingMode mode, bool beep) 构造函数来构造的。

重定向标准错误
    Console.Error = new ConsoleWriter(Console.Error, ConsoleColor.Red|ConsoleColor.Intensified, 0, true);

重定向调试或跟踪输出
    Debug.Listeners.Remove("default"); // Debug.Listeners.Clear();
    Debug.Listeners.Add( new TextWriterTraceListener( new ConsoleWriter(Console.Error, ...) ) );

您也可以使用方便的函数:WinConsole.RedirectDebugOutput(...)。

启动记事本对话框

在微软,几乎每个团队都使用命令行环境进行构建、测试等;这有时会因为没有 UI 的环境而难以从用户那里获取复杂的[大量]信息。

因此,发明了臭名昭著的记事本对话框。一个命令会启动一个带有文件名参数的 notepad.exe 并等待其退出。文件预填充了帮助注释和默认信息。用户编辑文件并通过退出记事本表示 OK。挂起的命令现在会恢复,并准备处理记事本文件。

该图显示了一个典型的记事本对话框。

Sample image

WinConsole.LaunchNotepadDialog 接受一个文件名参数,并启动一个记事本对话框,用户可以在其中修改指定的文件。

结论

这代表了我关于调试系列文章中的一篇。还会有其他的。

我将非常感谢您的投票;这对我来说是强大的激励。

版本历史

  • 2003 年 6 月 28 日 - 原始文章。
© . All rights reserved.