2013-10-31 4 views
0

내 프로젝트에는 두 개의 버튼이있는 대화 상자가 있습니다. 누군가 "예"를 누르면 프로그램을 닫고 싶습니다. 그러나 나는 그것이 작동하도록 할 수 없습니다.GUI 프로그램을 닫을 수 없습니다.

나는이 모든 것을 시도했다.

qApp->exit(); 
qApp->quit(); 
QApplication::exit(); 
QApplication::quit(); 
QCoreApplication::exit(); 
QCoreApplication::quit(); 

그리고 이들 중 어느 것도 프로그램을 닫지는 않습니다. main.cpp로 옮겨 보았습니다. 닫을 때 두 번째 함수를 만들려고했는데 아무 것도 작동하지 않았습니다.

이전에 업데이트를 확인하는 내 이벤트 루프와 관련이 있습니까? 그렇다면, 나는 그것을 게시 할 것입니다.

편집 :

#include "mainwindow.h" 
#include <QApplication> 

int main(int argc, char *argv[]) 
{ 
    Q_INIT_RESOURCE(icons); 
    QApplication a(argc, argv); 
    MainWindow w; 
    w.show(); 
    w.checkVersion(); 

    return a.exec(); 
} 

기능 : :

void MainWindow::checkVersion() 
{ 
    if((version != "1.0.0") && (version != ""))//version is a string that is filled when the mainwindow first opens. 
    { 
     QMessageBox::StandardButton reply; 
     reply = QMessageBox::question(this, "Update", "Version " + version + " is now available. Would you like to update now?\n\nOr visit http://www.youtube.com/oPryzeLP to download manually.", QMessageBox::Yes | QMessageBox::No); 

     if(reply == QMessageBox::Yes) 
     { 
     } 
     QApplication::exit();//moved out of reply just to test closing 
    } 
} 

이가 들어있는 기능입니다 여기

내 MAIN.CPP 나는 내 프로그램을 종료 할 수있는 기능입니다 이벤트 루프 :

void MainWindow::downloadFile(const QString &url, const QString &aPathInClient) 
{ 
    QNetworkAccessManager* m_NetworkMngr = new QNetworkAccessManager(this); 
    QNetworkReply *reply = m_NetworkMngr->get(QNetworkRequest(QUrl(url))); 
    QEventLoop loop; 
    connect(reply, SIGNAL(finished()), &loop, SLOT(quit())); 
    loop.exec(); 
    QUrl aUrl(url); 
    QFileInfo fileInfo=aUrl.path(); 

    QFile file(aPathInClient+"\\"+fileInfo.fileName()); 
    file.open(QIODevice::WriteOnly); 
    file.write(reply->readAll()); 
    delete reply; 
    loop.quit(); 
} 

이 downloadFile을 (호출 기능)입니다 : 당신이 종료 Qt는 이벤트 루프 목록

MainWindow::MainWindow(QWidget *parent) : 
    QMainWindow(parent), 
    ui(new Ui::MainWindow) 
{ 
    ui->setupUi(this); 
    downloadFile("link", "stuff"); 
    QFile info("stuff\\info.txt"); 
    if(info.open(QIODevice::ReadOnly)) 
    { 
     QTextStream in(&info); 
     while(!in.atEnd()) 
     { 
      version = in.readLine(); 
      versionLink = in.readLine(); 
      vidLink = in.readLine(); 
     } 
    } 
    info.close(); 

    setCentralWidget(ui->tabWidget); 
    ui->creativeFlag->setEnabled(false); 
    ui->structures->setEnabled(false); 
    ui->raining->setEnabled(false); 
    ui->thundering->setEnabled(false); 
    ui->hardcore->setEnabled(false); 
    AddSlotsToGroup(); 
    AddBlocksToGroup(); 
    QPalette palette = ui->blockFrame->palette(); 
    palette.setColor(backgroundRole(), QColor(139, 139, 139)); 
    ui->blockFrame->setPalette(palette); 
    ui->blockFrame->setAutoFillBackground(true); 
    QPixmap map_bg(":/images/mapbg.png"); 
    ui->mapBgLabel->setPixmap(map_bg.scaled(224, 224, Qt::IgnoreAspectRatio, Qt::FastTransformation)); 
    QShortcut *returnShortcut = new QShortcut(QKeySequence("Return"), ui->tab_4); 
    QObject::connect(returnShortcut, SIGNAL(activated()), ui->blockFind, SLOT(click())); 
} 
+0

문제를 재현하는 최소 테스트 사례를 게시하십시오. 모든 코드를 하나의 파일 (main.cpp, 클래스 선언 및 구현 모두)에 넣습니다. 'Q_OBJECT' 매크로가있는 경우 끝에 main.moc "를'#include 할 수 있습니다. –

+0

dialog.exec() 전에 app.exec()를 호출하거나 main()에 직접 열리는 대화 상자입니까? –

+0

게시물을 main.cpp로 업데이트하고 닫을 위치를 함수로 지정합니다. – mrg95

답변

0

출구 기능. MainWindow::checkVersion()에서 이벤트 루프가 시작되기 전에 exit를 호출합니다. 루프가 이미 실행 중이더라도 다시 시작할 수 있습니다 (코드에서 수행함).

해결 방법 : MainWindow::checkVersion()이 결과 코드를 반환하거나 bool 만 반환하도록 설정 한 다음 확인 가능한 경우에만 Qt 이벤트 루프를 시작하십시오.

코드 (일치하는 프로토 타입을 변경해야합니다) :

bool MainWindow::checkVersion() 
{ 
    //version is a string that is filled IN MAINWINDOW CONSTRUCTOR, IT SEEMS 
    if((version != "1.0.0") && (version != "")) 
    { 
     QMessageBox::StandardButton reply; 
     reply = QMessageBox::question(this, "Update", "Version " + version + " is now available. Would you like to update now?\n\nOr visit http://www.youtube.com/oPryzeLP to download manually.", QMessageBox::Yes | QMessageBox::No); 

     // return true if current version is ok 
     return !(reply == QMessageBox::Yes); 
    } 
    else { 
     // version is either 1.0.0 or empty 
     return true; 
} 

그리고 main() 기능에 맞게 : 귀하의 질문에 코드가 3 개 이벤트 루프를 갖고있는 것 같아요

int main(int argc, char *argv[]) 
{ 
    Q_INIT_RESOURCE(icons); 
    QApplication a(argc, argv); 
    MainWindow w; 
    w.show(); 

    if (w.checkVersion()) { 
     // version is ok, start the main event loop 
     return a.exec(); 
    } else { 
     // user wants to upgrade, do something, or just exit? 
     return 0; // or whatever exit code you want 
    } 
} 

주 (부분 코드로는 알기 힘듭니다), 하나씩 실행하십시오.

  1. QNAM 그것에게 종료 신호를 보낼 때 loop.exec() 통화 중에 실행하고 반환 MainWindow 생성자의 지역 이벤트 루프. MainWindow를이 이벤트 루프에 의해 화면에 그리거나하지 않은 경우

  2. 대화 상자가 닫힐 때 결과 대화하고 종료 및 수익을 보여줍니다 QMessageBox::question() 방법에 의해 시작된 이벤트 루프 (나는 확실하지 않다 당신 show 이후 이 전에).

  3. 응용 프로그램 메인 이벤트 루프는 a.exec()과 함께 입력 한 다음 종료 될 때 프로그램 종료 코드로 반환 값을 반환합니다 (일반적으로 마지막 윈도우가 닫히면 자동으로 트리거 됨).w.show() 그냥 기본적으로 w이 볼 수 있어야합니다 플래그를 설정하고 몇 가지 이벤트를 전송하는

참고. 아직 무언가를 그려 내지는 않으며 Qt 이벤트는 이벤트 루프가 전달할 때까지 아무데도 전달되지 않습니다. 이벤트를 전달하기 위해 이벤트 루프를 시작할 때만 문제가 발생합니다.

또 다른 참고 사항 : MainWindow 구성자는 완전히 잘못된 곳입니다. 이상적으로 QWidget 생성자는 위젯 만 설정하면되고, 다른 작업은 수행되지 않습니다 (사용자 상호 작용이나 네트워크 액세스 없음). 일반적인 패턴은 보이는 것들을 설정 한 다음 여분의 초기화 메소드를가집니다.이 메소드는 윈도우가 실제로 표시되면 실행됩니다 (예 : 단일 샷 타이머 또는 오버라이드 showEvent()). 나는 이것이 당신이 실제로 당신의 코드에 사용하기를 원하는지 의심 스럽다.

+0

결과 코드를 반환해야하는 함수는 무엇입니까? 그리고 Qt 이벤트 루프는 checkVersion 기능 전에 실행됩니다. 이벤트 루프는 txt 파일을 다운로드하는 데 사용됩니다.이 파일에서 checkVersion은 txt 파일을 검사합니다. – mrg95

+0

이벤트 루프는 닫기 함수 전에 시작됩니다. checkVersion 함수는 표시 할 내용을 알지 못합니다 (이벤트 루프의 결과를 표시합니다) – mrg95

+0

w.show()에서 이벤트 루프를 시작합니다. 이벤트 루프는 파일을 디스크로 다운로드하여 문자열로 읽습니다. 그런 다음 checkVersion이 문자열을 표시합니다. checkVersion 뒤에 이벤트 루프가 발생하면 어떻게 문자열을 표시 할 수 있습니까? – mrg95

0

아직 시작하지 않은 상태에서 QEventLoop을 종료하려고합니까? 이 경우 std :: exit()를 사용하여 프로그램을 중지하십시오.

관련 문제