J'ai une application graphique Qt sous Windows qui permet de transmettre les options de ligne de commande. Dans certaines circonstances, je souhaite envoyer un message à la console, puis quitter, par exemple:
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
if (someCommandLineParam)
{
std::cout << "Hello, world!";
return 0;
}
MainWindow w;
w.show();
return a.exec();
}
Cependant, les messages de la console n'apparaissent pas lorsque j'exécute l'application à partir d'une invite de commande. Est-ce que quelqu'un sait comment je peux le faire fonctionner?
Windows ne prend pas vraiment en charge les applications en mode double.
Pour voir la sortie de la console, vous devez créer une application console.
CONFIG += console
Cependant, si vous double-cliquez sur le programme pour démarrer la version en mode graphique, une fenêtre de console apparaîtra, ce qui n'est probablement pas ce que vous voulez. Pour éviter que la fenêtre de la console n'apparaisse, vous devez créer une application en mode graphique, auquel cas vous n'obtenez aucune sortie dans la console.
Une idée peut être de créer une deuxième petite application qui est une application console et fournit le résultat. Cela peut appeler le second pour faire le travail.
Vous pouvez également placer toutes les fonctionnalités dans une DLL, puis créer deux versions du fichier .exe contenant des fonctions principales très simples qui appellent la DLL. L'un est pour l'interface graphique et l'autre est pour la console.
Ajouter:
#ifdef _WIN32
if (AttachConsole(ATTACH_PARENT_PROCESS)) {
freopen("CONOUT$", "w", stdout);
freopen("CONOUT$", "w", stderr);
}
#endif
au sommet de main()
. Cela activera la sortie vers la console uniquement si le programme est démarré dans une console et ne fera pas apparaître une fenêtre de console dans d'autres situations. Si vous souhaitez créer une fenêtre de console pour afficher des messages lorsque vous exécutez l'application en dehors d'une console, vous pouvez modifier la condition en:
if (AttachConsole(ATTACH_PARENT_PROCESS) || AllocConsole())
void Console()
{
AllocConsole();
FILE *pFileCon = NULL;
pFileCon = freopen("CONOUT$", "w", stdout);
COORD coordInfo;
coordInfo.X = 130;
coordInfo.Y = 9000;
SetConsoleScreenBufferSize(GetStdHandle(STD_OUTPUT_HANDLE), coordInfo);
SetConsoleMode(GetStdHandle(STD_OUTPUT_HANDLE),ENABLE_QUICK_EDIT_MODE| ENABLE_EXTENDED_FLAGS);
}
int main(int argc, char *argv[])
{
Console();
std::cout<<"start@@";
qDebug()<<"start!";
Vous ne pouvez pas utiliser std :: cout comme d'autres l'ont dit, ma méthode est parfaite, même si certains codes ne peuvent pas inclure "qdebug"!
Pas moyen de sortir un message sur la console en utilisant QT += gui
.
fprintf(stderr, ...)
également ne peut pas imprimer la sortie.
Utilisez plutôt QMessageBox
pour afficher le message.
Oh, vous pouvez générer un message lorsque vous utilisez QT += gui
et CONFIG += console
.
Vous avez besoin de printf("foo bar")
mais cout << "foo bar"
ne fonctionne pas
J'ai utilisé cet en-tête ci-dessous pour mes projets. J'espère que ça aide.
#ifndef __DEBUG__H
#define __DEBUG__H
#include <QtGui>
static void myMessageOutput(bool debug, QtMsgType type, const QString & msg) {
if (!debug) return;
QDateTime dateTime = QDateTime::currentDateTime();
QString dateString = dateTime.toString("yyyy.MM.dd hh:mm:ss:zzz");
switch (type) {
case QtDebugMsg:
fprintf(stderr, "Debug: %s\n", msg.toAscii().data());
break;
case QtWarningMsg:
fprintf(stderr, "Warning: %s\n", msg.toAscii().data());
break;
case QtCriticalMsg:
fprintf(stderr, "Critical: %s\n", msg.toAscii().data());
break;
case QtFatalMsg:
fprintf(stderr, "Fatal: %s\n", msg.toAscii().data());
abort();
}
}
#endif
PS: vous pouvez ajouter dateString
à la sortie si vous le souhaitez.
Vous voudrez peut-être étudier, du moins pour Windows, la fonction AllocConsole () dans l’API Windows. Il appelle plusieurs fois GetStdHandle pour rediriger stdout, stderr, etc. (Un test rapide montre que cela ne fait pas tout à fait ce que nous souhaitons. Vous ouvrez une fenêtre de console à côté de vos autres éléments Qt, mais vous Vraisemblablement, étant donné que la fenêtre de la console est ouverte, il existe un moyen d’y accéder, d’obtenir un descripteur, ou d’y accéder et de la manipuler d’une manière ou d’une autre. Voici la documentation MSDN pour ceux qui sont intéressés à comprendre ceci:
AllocConsole (): http://msdn.Microsoft.com/en-us/library/windows/desktop/ms681944%28v=vs.85%29.aspx
GetStdHandle (...): http://msdn.Microsoft.com/en-us/library/windows/desktop/ms683231%28v=vs.85%29.aspx
(J'ajouterais ceci comme commentaire, mais les règles m'empêchent de le faire ...)
Dans votre .pro ajouter
CONFIG += console
Tant de réponses à ce sujet. 0.0
Je l’ai donc essayé avec Qt5.x de Win7 à Win10. Il m'a fallu quelques heures pour trouver une solution efficace qui ne pose aucun problème quelque part dans la chaîne:
#include "mainwindow.h"
#include <QApplication>
#include <windows.h>
#include <stdio.h>
#include <iostream>
//
// Add to project file:
// CONFIG += console
//
int main( int argc, char *argv[] )
{
if( argc < 2 )
{
#if defined( Q_OS_WIN )
::ShowWindow( ::GetConsoleWindow(), SW_HIDE ); //hide console window
#endif
QApplication a( argc, argv );
MainWindow *w = new MainWindow;
w->show();
int e = a.exec();
delete w; //needed to execute deconstructor
exit( e ); //needed to exit the hidden console
return e;
}
else
{
QCoreApplication a( argc, argv );
std::string g;
std::cout << "Enter name: ";
std::cin >> g;
std::cout << "Name is: " << g << std::endl;
exit( 0 );
return a.exec();
}
}
Je l’ai essayé aussi sans la "CONFIG + = console", mais vous devez ensuite rediriger les flux et créer la console par vous-même:
#ifdef _WIN32
if (AttachConsole(ATTACH_PARENT_PROCESS) || AllocConsole()){
freopen("CONOUT$", "w", stdout);
freopen("CONOUT$", "w", stderr);
freopen("CONIN$", "r", stdin);
}
#endif
MAIS cela ne fonctionne que si vous le démarrez via un débogueur, sinon toutes les entrées sont également dirigées vers le système. Cela signifie que si vous tapez un nom via std :: cin, le système tente d’exécuter le nom en tant que commande. (très étrange)
Deux autres avertissements à cette tentative seraient, vous ne pouvez pas utiliser :: FreeConsole () il ne le fermera pas et si vous le démarrez via une console l'application ne se fermera pas.
Enfin, il existe une section d’aide Qt dans QApplication relative à ce sujet. J'ai essayé l'exemple ici avec une application et il ne fonctionne pas pour l'interface graphique, il s'est coincé quelque part dans une boucle sans fin et l'interface graphique ne sera pas rendue ou se bloque simplement:
QCoreApplication* createApplication(int &argc, char *argv[])
{
for (int i = 1; i < argc; ++i)
if (!qstrcmp(argv[i], "-no-gui"))
return new QCoreApplication(argc, argv);
return new QApplication(argc, argv);
}
int main(int argc, char* argv[])
{
QScopedPointer<QCoreApplication> app(createApplication(argc, argv));
if (qobject_cast<QApplication *>(app.data())) {
// start GUI version...
} else {
// start non-GUI version...
}
return app->exec();
}
Donc, si vous utilisez Windows et Qt utilisez simplement l'option console, masquez la console si vous avez besoin de l'interface graphique et fermez-la via exit.
Tout d’abord, pourquoi auriez-vous besoin de sortir vers la console dans une version en mode édition? Personne ne songe à y regarder quand il y a une gui ...
Deuxièmement, qDebug est chic :)
Troisièmement, vous pouvez essayer d'ajouter console
à votre CONFIG
de .pro
.
J'ai aussi joué avec cela, découvrant que la redirection de la sortie fonctionnait, mais je n'ai jamais vu de sortie dans la fenêtre de la console, présente pour toutes les applications Windows. C'est ma solution jusqu'à présent, jusqu'à ce que je trouve un remplaçant Qt pour ShowWindow et GetConsoleWindow.
Exécutez ceci à partir d'une invite de commande sans paramètre - récupérez la fenêtre. Exécuter à partir d'une invite de commande avec des paramètres (par exemple, cmd aaa bbb ccc) - vous obtenez le texte de sortie dans la fenêtre d'invite de commande - exactement comme vous le feriez pour n'importe quelle application de console Windows.
Veuillez excuser l’exemple boiteux - cela représente environ 30 minutes de bricolage.
#include "mainwindow.h"
#include <QTextStream>
#include <QCoreApplication>
#include <QApplication>
#include <QWidget>
#include <windows.h>
QT_USE_NAMESPACE
int main(int argc, char *argv[])
{
if (argc > 1) {
// User has specified command-line arguments
QCoreApplication a(argc, argv);
QTextStream out(stdout);
int i;
ShowWindow (GetConsoleWindow(),SW_NORMAL);
for (i=1; i<argc; i++)
out << i << ':' << argv [i] << endl;
out << endl << "Hello, World" << endl;
out << "Application Directory Path:" << a.applicationDirPath() << endl;
out << "Application File Path:" << a.applicationFilePath() << endl;
MessageBox (0,(LPCWSTR)"Continue?",(LPCWSTR)"Silly Question",MB_YESNO);
return 0;
} else {
QApplication a(argc, argv);
MainWindow w;
w.setWindowTitle("Simple example");
w.show();
return a.exec();
}
}
C’était peut-être un oubli des autres réponses, ou c’est peut-être une exigence de l’utilisateur d’avoir besoin de la sortie console, mais la réponse évidente est de créer une fenêtre secondaire pouvant être affichée ou masquée (avec une case à cocher ou un bouton) qui affiche tous les messages en ajoutant des lignes de texte à un widget de zone de texte et l’utilise comme console?
Les avantages d'une telle solution sont:
J'espère que cela vous donne matière à réflexion, bien que je ne sois en aucun cas qualifié pour postuler sur la façon de procéder, mais je peux imaginer que c'est quelque chose de très réalisable pour n'importe lequel d'entre nous avec un peu de recherche/lecture!
Assurez-vous que Qt5Core.dll est dans le même répertoire que l'exécutable de votre application.
J'ai eu un problème similaire dans Qt5 avec une application en console: .Très étrange!
Je l'ai résolu en copiant Qt5Core.dll dans le répertoire contenant l'exécutable de l'application.
Voici ma petite application console:
#include <QCoreApplication>
#include <QDebug>
int main(int argc, char *argv[])
{
int x=343;
QString str("Hello World");
qDebug()<< str << x<<"lalalaa";
QTextStream out(stdout);
out << "aldfjals alsdfajs...";
}