如何:在 Winform 动态启动、控制台命令行?
需求
winForm 程序输出类型为 windows 程序(不是命令行程序)
在运行时想输入一些信息编译开发调试,如何实现这一功能
解答:
AllocConsole、FreeConsole 这两个 API 可以在任何时候调用和关闭 命令行。
代码演示:
API 部分
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.InteropServices;
namespace WindowsFormsApplication1
{
public partial class NativeMethods {
/// <summary>
/// 启动控制台
/// </summary>
/// <returns></returns>
[DllImport("kernel32.dll")]
public static extern bool AllocConsole();
/// <summary>
/// 释放控制台
/// </summary>
/// <returns></returns>
[DllImport("kernel32.dll")]
public static extern bool FreeConsole();
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.InteropServices;
namespace WindowsFormsApplication1
{
public partial class NativeMethods {
/// <summary>
/// 启动控制台
/// </summary>
/// <returns></returns>
[DllImport("kernel32.dll")]
public static extern bool AllocConsole();
/// <summary>
/// 释放控制台
/// </summary>
/// <returns></returns>
[DllImport("kernel32.dll")]
public static extern bool FreeConsole();
}
}
启动参数的实现
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using System.Runtime.InteropServices;
using System.Diagnostics;
namespace WindowsFormsApplication1
{
static class Program
{
/// <summary>
/// 应用程序的主入口点。
/// </summary>
[STAThread]
static void Main(string[] args)
{
try
{
if(args.Length > 0 && args[0].ToLower() == "-c")
{//通过命令行 xxxx.exe -c 参数启动,Console
//注意:不用 Main(string[] args)、System.Environment.GetCommandLineArgs(); 也可以取得命令行参数在任何地方
//启动
NativeMethods.AllocConsole();
Console.WriteLine("控制台以启动");
}
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
}
finally
{
//关闭 (如果在这个位置其实写不写都行了)
NativeMethods.FreeConsole();
}
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using System.Runtime.InteropServices;
using System.Diagnostics;
namespace WindowsFormsApplication1
{
static class Program
{
/// <summary>
/// 应用程序的主入口点。
/// </summary>
[STAThread]
static void Main(string[] args)
{
try
{
if(args.Length > 0 && args[0].ToLower() == "-c")
{//通过命令行 xxxx.exe -c 参数启动,Console
//注意:不用 Main(string[] args)、System.Environment.GetCommandLineArgs(); 也可以取得命令行参数在任何地方
//启动
NativeMethods.AllocConsole();
Console.WriteLine("控制台以启动");
}
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new Form1());
}
finally
{
//关闭 (如果在这个位置其实写不写都行了)
NativeMethods.FreeConsole();
}
}
}
}
程序实现
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace WindowsFormsApplication1
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void btnOpenConsole_Click(object sender, EventArgs e)
{
//开启控制台
NativeMethods.AllocConsole();
}
private void btnCloseConsole_Click(object sender, EventArgs e)
{
//关闭控制台
NativeMethods.FreeConsole();
}
private void btnOut_Click(object sender, EventArgs e)
{
//模拟输出
Console.WriteLine(textBox1.Text);
}
}
}
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace WindowsFormsApplication1
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void btnOpenConsole_Click(object sender, EventArgs e)
{
//开启控制台
NativeMethods.AllocConsole();
}
private void btnCloseConsole_Click(object sender, EventArgs e)
{
//关闭控制台
NativeMethods.FreeConsole();
}
private void btnOut_Click(object sender, EventArgs e)
{
//模拟输出
Console.WriteLine(textBox1.Text);
}
}
}
代码下载:(VS2008 如果其他版本VS请自行修改)
/Files/flashelf/WinformShellConsole_VS08.rar
最后:
其实代码很简单,不过很适合在运行时输出一些临时调试信息
用GUI画图的操作一般下断点很容易影响Print 事件的情况
,有时候在客户那里程序问题在上打开控制台输出一些调试信息看着比较方便;
而且控制太没有线程限制的,所以使用起来要比单独的日志窗口方便、而且容易复制内容,还支持 paus 键;
曲滨 2008-07-15
--------------------------
这是我主板烧了以后的第一个blog 纪念一下
主板烧毁经过
硬件情况:
板子:我就不写了反正不是烂板子(省的有人说我是枪手)、芯片是 n570 的
cpu:amd6000+ (降频模式开)
显卡:ati2600xt
内存:金榜4G
电源:这个也不写了反正不是垃圾电源 400-500元的;440A 的
系统:win2003
以只知的烧毁经过:
当前室内气温:31-33 没空调;
开迅雷下载(美丽的中国记录片)设置自动关机(其他就一个杀毒软件)
第二天,早上发现显示器亮着死机键盘num lock 无效、鼠标无效、关机无效
机箱很热,cpu,板子都烫手、关闭电源
这台计算机是2007-8月买的所以没过保都,拿去送修
板子、电源 都不好用了,不过没有烧毁痕迹(郁闷)
所以现在我也不清楚啥原因(我家这里电很稳定的我都用好几个电脑了没有烧过)
电源换了,板子要返厂而且【奥运期间】可能会很久
因为电脑急用给我个替代板子不过很慢、一气之下买了一个新版子 asus 的、不过asus
就3款可选一个2000多太贵了、一个集成显卡的、剩下一个m3a 我买了 nnd (我只能选这个),问为啥这么少老板说因为【奥运】货进的慢(为什么又是“奥运”)
最后买了个板子,加了一个 九州风神贝塔400+ 的风扇 花了 700 多,终于告一段落了;
不过m3a 这个板子北桥也很热、前置usb有时候也不是很好用、担心啊不过世界上没有完美的事情忍了
以上是整个过程提醒大家天热注意你的电脑;小心烧毁
庆幸的是显卡、内存、cpu、硬盘 都还活着(尤其是硬盘照片太多了,好东西也太多了呵呵);