MinGW,用控制台构建GUI应用程序。

时间:2022-03-12 20:44:13

I'm using MinGW to build my application on Windows. When compiling and linking, the option "-mwindows" is put in command line to have Win32 API functions.

我正在使用MinGW在Windows上构建我的应用程序。在编译和链接时,选项“-mwindows”被放在命令行中,以拥有Win32 API函数。

To be more specific: when calling GCC of MinGW without "-mwindows" like this:

更具体的说:在没有“-mwindows”的情况下调用MinGW时:

c:\>g++ -c main.cpp 
c:\>g++ -o main.exe main.o

The 'main.exe' after the 2 command lines above will run with a console, and Win32 API functions won't be usable.

的主要。在上面的两条命令行之后,将使用一个控制台运行,而Win32 API函数将无法使用。

When calling GCC of MinGW with "-mwindows" like this:

当用“-mwindows”来调用MinGW时:

c:\>g++ -c main.cpp
c:\>g++ -o main.exe main.o -mwindows

Now linking with '-mwindows', the 'main.exe' can use Win32 API, however, it doesn't start a console when the application runs.

现在连接“-mwindows”,“main”。exe可以使用Win32 API,但是在应用程序运行时它不会启动控制台。

This "-mwindows" option disables the console, which makes me not able to print out debugging info. Any way to keep both console and the option '-mwindows'?

这个“-mwindows”选项禁用了控制台,这使我无法打印调试信息。任何保持控制台和选项“-mwindows”的方法?

3 个解决方案

#1


6  

I have no evidence for this answer, only a bit of experiments that were successful. If I have a hello app, like this:

我没有这个答案的证据,只是一些成功的实验。如果我有一个hello程序,像这样:

#include <stdio.h>
#include <windows.h>

int main(void)
{
    puts("hi");
    MessageBox(NULL, "test", "test", NULL);
    GetStockObject(0);
    return 0;
}

I cannot compile it with -mconsole, because linker complains about GetStockObject. But when I add the necessary library with -lgdi32 switch on my command line, the app compiles and executes cleanly. Maybe this is the way to keep both console and gdi. This is the command line:

我无法用-mconsole编译它,因为linker抱怨GetStockObject。但是,当我在命令行上添加-lgdi32开关的必要库时,应用程序就会编译并执行干净。也许这是保持控制台和gdi的方法。这是命令行:

gcc -mconsole test_gdi.c -lgdi32

#2


14  

The -mconsole switch is used to specify that you want to target the console subsystem. You really do want to do that to ensure that your process connects to the existing console if started from a console app. For example, suppose you do go down your route of targeting the GUI subsystem, and then calling AllocConsole(), as per your own answer. Then you'll find your app shows a brand new console rather than using the existing one when started from another console app, e.g. cmd.exe.

-mconsole开关用于指定您想要针对控制台子系统。您确实需要这样做,以确保您的进程从一个控制台应用程序开始连接到现有的控制台。然后,你会发现你的应用程序显示了一个全新的控制台,而不是在从另一个控制台应用程序(例如cmd.exe)开始使用现有的一个。

If you need to use other libraries, then you are free to add them on command line using -l. There's nothing special about a console app that means that it cannot link to any Win32 API function. It's just that the default set of libraries associated with -mconsole is missing some of the libraries that you want.

如果需要使用其他库,那么可以使用-l将它们添加到命令行中。控制台应用程序没有什么特别之处,这意味着它不能链接到任何Win32 API函数。只是与-mconsole相关的默认库集缺少一些您想要的库。

On the other hand, you can use both -mconsole and -mwindows when you build your app. They are not mutually exclusive.

另一方面,当您构建应用程序时,您可以同时使用-mconsole和-mwindows,它们不是互斥的。

gcc -mconsole -mwindows main.c

This produces an application that targets the console subsystem. And you get the standard -mwindows set of Win32 libraries automatically linked. It's probably the simplest way to achieve your goal.

这将生成一个针对控制台子系统的应用程序。然后,你就可以自动链接到Win32库的标准-mwindows集。这可能是实现目标最简单的方法。

#3


1  

I found the answer. As taken from Using STDIN with an AllocConsole()

我找到了答案。从使用一个AllocConsole()开始使用STDIN

AllocConsole();
freopen("CONIN$", "r",stdin); 
freopen("CONOUT$","w",stdout); 
freopen("CONOUT$","w",stderr);  

It works like magic!

它的工作原理就像魔法!

Reference for 'freopen': http://www.cplusplus.com/reference/clibrary/cstdio/freopen/

参考“freopen”:http://www.cplusplus.com/reference/clibrary/cstdio/freopen/

#1


6  

I have no evidence for this answer, only a bit of experiments that were successful. If I have a hello app, like this:

我没有这个答案的证据,只是一些成功的实验。如果我有一个hello程序,像这样:

#include <stdio.h>
#include <windows.h>

int main(void)
{
    puts("hi");
    MessageBox(NULL, "test", "test", NULL);
    GetStockObject(0);
    return 0;
}

I cannot compile it with -mconsole, because linker complains about GetStockObject. But when I add the necessary library with -lgdi32 switch on my command line, the app compiles and executes cleanly. Maybe this is the way to keep both console and gdi. This is the command line:

我无法用-mconsole编译它,因为linker抱怨GetStockObject。但是,当我在命令行上添加-lgdi32开关的必要库时,应用程序就会编译并执行干净。也许这是保持控制台和gdi的方法。这是命令行:

gcc -mconsole test_gdi.c -lgdi32

#2


14  

The -mconsole switch is used to specify that you want to target the console subsystem. You really do want to do that to ensure that your process connects to the existing console if started from a console app. For example, suppose you do go down your route of targeting the GUI subsystem, and then calling AllocConsole(), as per your own answer. Then you'll find your app shows a brand new console rather than using the existing one when started from another console app, e.g. cmd.exe.

-mconsole开关用于指定您想要针对控制台子系统。您确实需要这样做,以确保您的进程从一个控制台应用程序开始连接到现有的控制台。然后,你会发现你的应用程序显示了一个全新的控制台,而不是在从另一个控制台应用程序(例如cmd.exe)开始使用现有的一个。

If you need to use other libraries, then you are free to add them on command line using -l. There's nothing special about a console app that means that it cannot link to any Win32 API function. It's just that the default set of libraries associated with -mconsole is missing some of the libraries that you want.

如果需要使用其他库,那么可以使用-l将它们添加到命令行中。控制台应用程序没有什么特别之处,这意味着它不能链接到任何Win32 API函数。只是与-mconsole相关的默认库集缺少一些您想要的库。

On the other hand, you can use both -mconsole and -mwindows when you build your app. They are not mutually exclusive.

另一方面,当您构建应用程序时,您可以同时使用-mconsole和-mwindows,它们不是互斥的。

gcc -mconsole -mwindows main.c

This produces an application that targets the console subsystem. And you get the standard -mwindows set of Win32 libraries automatically linked. It's probably the simplest way to achieve your goal.

这将生成一个针对控制台子系统的应用程序。然后,你就可以自动链接到Win32库的标准-mwindows集。这可能是实现目标最简单的方法。

#3


1  

I found the answer. As taken from Using STDIN with an AllocConsole()

我找到了答案。从使用一个AllocConsole()开始使用STDIN

AllocConsole();
freopen("CONIN$", "r",stdin); 
freopen("CONOUT$","w",stdout); 
freopen("CONOUT$","w",stderr);  

It works like magic!

它的工作原理就像魔法!

Reference for 'freopen': http://www.cplusplus.com/reference/clibrary/cstdio/freopen/

参考“freopen”:http://www.cplusplus.com/reference/clibrary/cstdio/freopen/