2015-08-19 51 views
0

考慮這個SLOT,在我的主線程中,由一個按鈕觸發,它從QTreeWidget獲取QTreeWidgetItem的列表。它使用一個QtConcurrent::map()調用來執行長任務。 watcher連接到QProgressDialog以顯示進度。如果沒有顯示QProgressDialog,QtConcurrent :: map崩潰

void Main::on_actionButton_triggered() { 
    qRegisterMetaType<QVector<int> >("QVector<int>"); 

    //Setting up a progress dialog 
    QProgressDialog progressDialog; 

    //Holds the list 
    QList<QTreeWidgetItem*> list; 

    //Setup watcher 
    QFutureWatcher<void> watcher; 

    //Setting up connections 
    //Progress dialog 
    connect(&watcher, SIGNAL(progressValueChanged(int)), &progressDialog, SLOT(setValue(int))); 
    connect(&watcher, SIGNAL(progressRangeChanged(int, int)), &progressDialog, SLOT(setRange(int,int))); 
    connect(&watcher, SIGNAL(progressValueChanged(int)), ui->progressBar, SLOT(setValue(int))); 
    connect(&watcher, SIGNAL(progressRangeChanged(int, int)), ui->progressBar, SLOT(setRange(int,int))); 
    connect(&watcher, SIGNAL(finished()), &progressDialog, SLOT(reset())); 
    connect(&progressDialog, SIGNAL(canceled()), &watcher, SLOT(cancel())); 

    connect(&watcher, SIGNAL(started()), this, SLOT(processStarted())); 
    connect(&watcher, SIGNAL(finished()), this, SLOT(processFinished())); 

    //Gets the list filled 
    for (int i = 0; i < ui->listTreeWidget->topLevelItemCount(); i++) { 
     list.append(ui->listTreeWidget->topLevelItem(i)); 
    } 

    //And start 
    watcher.setFuture(QtConcurrent::map(list, processRoutine)); 

    //Show the dialog 
    progressDialog.exec(); 

} 

extern void processRoutine(QTreeWidgetItem* item) { 
    qDebug() << item->text(4); 
} 

我還增加,在用戶界面中(其保持所有先前的窗口小部件),具有相同的信號/插槽一個QProgressBar。像預期的那樣保持代碼像以前的工作:進度對話框出現,進度條更新與對話框完全一樣。 相反,如果我評論的

//progressDialog.exec(); 

或我隱藏對話框以某種方式,在進程崩潰(並非總是如此,有時順利)。看着qDebug() << item->text(4);它崩潰,輸出顯示隨機混合文本(它們應該是文件名)。此外,即使未計算QProgressDialog,進度條也不會自行更新,即使計算沒有崩潰。

注:我在另一個函數之前經歷了類似的問題,我通過設置

QThreadPool::globalInstance()->setMaxThreadCount(1); 
在Windows

解決它唯一的,OSX是確定的。

那麼QProgressDialog背後的訣竅是什麼讓所有的事情都做對了?有沒有辦法可以使用QProgressBar而不是QProgressDialog

注意

這是輸出時的過程中沒有煩惱完成:

"C:/Users/Utente/Pictures/Originals/unsplash_52cee67a5c618_1.jpg" 
"C:/Users/Utente/Pictures/Originals/photo-1428278953961-a8bc45e05f72.jpg" 
"C:/Users/Utente/Pictures/Originals/photo-1429152937938-07b5f2828cdd.jpg" 
"C:/Users/Utente/Pictures/Originals/photo-1429277158984-614d155e0017.jpg" 
"C:/Users/Utente/Pictures/Originals/photo-1430598825529-927d770c194f.jpg" 
"C:/Users/Utente/Pictures/Originals/photo-1433838552652-f9a46b332c40.jpg" 

回答

1

當您發表評論progressDialog.exec();on_actionButton_triggered()功能與破壞progressDialog所以你的信號通過指針無處完成。 另外watcher在執行所有映射之前或之後也被銷燬,並且afair不會停止線程,因此它們也無處可用。