近日在測試軟體功能時,發現一些不是太顯眼問題,如希望在點擊視窗右上方的X按鈕關閉視窗時,能夠提示使用者是否確認關閉;使用完軟體並關閉主程式時,開啟的子視窗在主視窗關閉後能夠同時關閉等一些問題。當然,這些問題並不影響軟體的功能應用,但作為一個面向廣大使用者的實用軟體的話,這顯然不太符合使用者的使用習慣。並且,加入對話方塊的操作能避免一些不小心的錯誤操作給使用者帶來的麻煩。對此,我本人針對該問題做了一些修改工作,以使視窗關閉時,跳出對話方塊提示使用者是否確認關閉,以及在主視窗關閉時,響應已開啟的子視窗同時全部關閉。以下是本人對此做出的一些總結。 使用QT編輯介面,其中帶來很大方便的一點就是Qt中內建豐富的、種類齊全的類及其功能函數,程式員可以在編輯程式的過程中簡單地直接調用。關於視窗關閉的操作,在這裡指出常用的三個槽,即quit(),exit()以及close()。 首先說明視窗退出時,系統提示對話方塊的代碼編輯。對主程式的退出,可以調用成員函數exit(),同時也可以調用槽quit(),二者此時都能起到關閉應用程式的作用。只是應注意二者調用的方式不同。如下程式樣本: { QApplication* app; app->exit(0); } 或者: { QApplication* app; app->quit(); } 此時二者是等價的,即void QApplication::quit ()等價於函數調用 QApplication::exit( 0 )。此時,若需要給出使用者提示,則只需要在程式當中添加QMessageBox的訊息判斷語句,以提示使用者是否確定退出應用程式。另外,quit()作為槽,也可以串連訊號和槽的形式,響應某個訊號後關閉應用程式。如: QPushButton *quitButton = new QPushButton( "Quit" );
connect( quitButton, SIGNAL(clicked()), qApp, SLOT(quit()) ); 如果關閉的不是應用程式,而是關閉視窗等組件的形式,則必須調用close()函數,已關閉組件。如下: if (!(QMessageBox::information(this,tr("CT Control View"),tr("Do you really want to log out CT Control View?"),tr("Yes"),tr("No"))))
{
this->close();
} 其中通過一條if語句,判斷條件為一個對話方塊,根據使用者的選擇做出是否關閉該組件,this在這裡代表當前視窗組件對象的地址。當使用者選擇“Yes”時,該視窗組件退出;反之則取消退出操作。 至此,我們已經簡單瞭解了應用程式和視窗等組件的退出或關閉的代碼編輯。然而,如果使用者點擊視窗右上方的X按鍵時,你會發現視窗仍然會在不給出任何提示的情況下直接退出了,即便你在程式當中已添加了提示的對話方塊語句。那為什麼此時的關閉操作沒有按我們希望的那樣先給出提示對話方塊呢?原因是此時的關閉操作並沒有引起調用帶有提示訊息的關閉或退出語句。當使用者點擊X關閉視窗時,系統會自動將這個事件告之某個特定的函數,即void QWidget::closeEvent ( QCloseEvent * e ),因此,這種情況應特別注意。在關閉視窗前,可先定義一條訊息語句,以提示使用者是否確定關閉視窗。如: void mainWindow::closeEvent( QCloseEvent * event )
{
switch( QMessageBox::information( this, tr("CT Control View"),
tr("Do you really want to log out CT Control View?"),
tr("Yes"), tr("No"),
0, 1 ) )
{
case 0:
event->accept();
break;
case 1:
default:
event->ignore();
break;
}
} 編譯器後,系統會在使用者響應close操作時,自動調用該語句。也許這個時候你還會問,上面的那個功能函數究竟是把它定義成槽呢,還是定義成成員函數。答案是二者都可以。一方面槽本身就是一個特殊的成員函數,除了能與訊號串連之外,其功能與函數無異。另一方面,此時不需要額外設定串連訊號和槽,添加該功能函數之後,視窗一旦有了close操作,機會立即響應該。 儘管添加closeEvent( QCloseEvent * event )這一功能函數之後,視窗會在關閉時給出提示對話方塊。但有時候還會發生這樣一種情況:在點擊確認關閉後,還會再會出現一個對話方塊,即提示對話方塊會出現兩次。那這又是什麼原因呢?其實很簡單,那是因為closeEvent( QCloseEvent * event )只會響應close的操作,出現兩次對話方塊無疑是在自訂的關閉函數中又添加一條提示對話方塊語句,確認關閉後,響應close操作,這時系統又會馬上調用closeEvent( QCloseEvent * event )這個函數。因此,解決的辦法是只定義一個帶提示對話方塊的關閉函數,對不同的關閉操作都相應closeEvent( QCloseEvent * event )這個函數即可。 最後,如果想要在關閉主視窗或主程式時,所有開啟的獨立的子視窗都能同時被關閉。那麼這個時候一般是在main.cpp檔案中串連訊號void QApplication::lastWindowClosed ();關於lastWindowClosed()的詳細介紹,這裡不作說明,需要使用時可以使用Qt Assistant查看其使用發法。如:int main( int argc, char ** argv )
{
QApplication a( argc, argv ); ABMainWindow *mw = new ABMainWindow();
mw->setCaption( "Qt Example - Addressbook" );
a.setMainWidget( mw ); mw->show(); a.connect( &a, SIGNAL( lastWindowClosed() ), &a, SLOT( quit() ) );
int result = a.exec();
delete mw;
return result;
} 這樣,系統會在關閉主視窗組件時,同時關閉開啟的其它子視窗程式。比較值得說明的是,並不是使用了a.connect( &a, SIGNAL( lastWindowClosed() ), &a, SLOT( quit() ) )這條語句後就一定能實現該功能。在此之前,必須特別注意是否設定了主視窗組件,即調用setMainWidget這一功能函數,這樣,當關閉這一主視窗組件時,才會響應關閉這一時刻已開啟的其它子視窗組件。
本文出自 “萬裡晴空” 部落格,請務必保留此出處http://sunshine1106.blog.51cto.com/1371108/305106
在實際編寫時要注意:
connect(ui->pbExit,SIGNAL(clicked()),qApp,SLOT(quit()));
其中,qApp就是指向QApplication的指標。