C++ Qt學習筆記(2)簡易計算器設計(爲計算器添加菜單功能)

       Qt中的主窗口爲建立桌面應用程序的用戶提供了一個框架,Qt中提供了QMainWindow和一些相關的類共同完成主窗口的管理。Qt中的QWidget是一個最基本的窗口控件,只有一個最基本的窗口,其餘什麼也沒有。而QMainWindow爲用戶提供了一個具有菜單,工具欄以及底部狀態欄的窗口。

1. 菜單欄

        Qt中的菜單欄主要由QMenu和QAction類來表示。QMenu表示菜單對象,QAction表示菜單按下的事件。例如新建一個QMainWindow項目:

通過雙擊“在這裏輸入”來添加菜單以及添加子菜單。例如添加文件菜單,需要輸入文件(&F),&F稱爲加速鍵,表明程序在運行時可以按下ALT+F鍵來激活菜單,添加子菜單的時候,可能會由於Qt版本問題無法輸入中文。解決方法:再別的地方寫好,再複製粘貼到菜單欄裏面即可   新建(&N)   打開(&O)。

在新建完成菜單之後,可以看到,在Qt中的Action編輯器中已經出現了兩個菜單,

將菜單和相應的槽函數相連接,有兩種實現方法:

1. 右擊按鈕,點擊跳轉到槽選項,Qt會自己創建相應的槽函數,編寫業務代碼即可

2. 在QMainWindow.h文件中自定義槽函數,然後通過connect函數將菜單與相應的槽函數相連。

private slots:
    void on_action_N_triggered();
    void on_action_O_triggered();
    connect(ui->action_O, SIGNAL(triggered()), this, SLOT(on_action_O_triggered));   // 通過connect函數也可以連接

2. 工具欄

工具欄QToolBar類提供了一個包含一組控件,且可以移動的面板。在工具欄中,可以添加其他的窗口控件,例如可以添加彈出菜單以及非彈出菜單。

在工具欄中添加新的彈出式 的菜單,以及添加spinbox控件:

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    connect(ui->action_O, SIGNAL(triggered()), this, SLOT(on_action_O_triggered));   // 通過connect函數也可以連接

    // 添加工具欄內容  按鈕類型
    QToolButton* toolbtn = new QToolButton(this);
    toolbtn->setText("Color");
    
    // 爲按鈕添加菜單
    QMenu* colormenu = new QMenu(this);  
    colormenu->addAction("red");
    colormenu->addAction("pink");
    toolbtn->setMenu(colormenu);
    toolbtn->setPopupMode(QToolButton::MenuButtonPopup);
    // 將按鈕添加到工具欄
    ui->mainToolBar->addWidget(toolbtn);
    
    // 將一個spinbox添加到工具欄
    QSpinBox* spinbox = new QSpinBox(this);
    spinbox->setMaximum(100);
    spinbox->setMinimum(0);
    spinbox->setValue(50);
    ui->mainToolBar->addWidget(spinbox);
    
    // 將新建按鈕QAction添加到工具欄
    ui->mainToolBar->addAction(ui->action_N);  
}

工具欄效果如圖所示:

 

3.狀態欄

狀態欄QStatusBar提供了一個水平條控件,用於向用戶顯示狀態信息。QMainWindow中提供一個默認的狀態欄。

狀態欄中的信息分爲三類:
1.臨時信息,如一般的提示性的信息

2. 正常信息:例如顯示當前的頁碼以及行號‘

3. 永久信息:顯示版本號或者日期

可以使用showMessage()函數顯示臨時信息,它會出現在狀態欄的最左邊。一般添加一個Qlabel到狀態欄上顯示正常信息,它也會出現在狀態欄的左邊,可能被臨時信息覆蓋。如果需要顯示永久信息,則需要使用addPermanentWidget()添加一個類似於Qlabel的可以顯示信息的控件,他會生成在狀態欄的右邊。

    // 向狀態欄中添加信息
    QLabel* normal_info = new QLabel(this);
    QLabel* permanent_info = new QLabel(this);
    normal_info->setText("Normal information");
    permanent_info->setText("Permanent infomation");
    // 向狀態欄添加相應的控件

    ui->statusBar->addWidget(normal_info);
    ui->statusBar->addPermanentWidget(permanent_info);

如果需要顯示提示信息,則需要調用:

ui->statusBar->showMessage("New file Created!");   // 顯示提示信息

可以將提示信息的顯示寫入相應的槽函數中,例如爲新建按鈕添加提示信息:

void MainWindow::on_action_N_triggered()
{
    qDebug() << "The new file button pushed" << endl;
    ui->statusBar->showMessage("New file Created!");   // 顯示提示信息
}

則在新建按鈕按下後,會出現提示信息,覆蓋掉正常信息,但是當進行別的操作的時候,提示信息會消失,顯示正常的信息。

 

4. 對話框

對話框窗口是一種比較特殊的窗口,對話框窗口通常用來完成短小任務或者和用戶進行簡單交互的頂級窗口,QDialog是所有對話框窗口的基類,下面介紹幾種標準的對話框:
1. 模態與非模態對話框

按照運行對話框時,是否還可以與該程序的其他窗口進行交互,對話框可以分爲兩類,模態和非模態。

例如:對於上述的open菜單,設計一個對話框,非模態對話框就是當對話框彈出時,用戶任然可以和其他的窗口進行交互。模態對話框則不行,只有將對話框關閉,纔可以和其他的對話框進行交互。

void MainWindow::on_action_N_triggered()
{
    qDebug() << "The new file button pushed" << endl;
    ui->statusBar->showMessage("New file Created!");   // 顯示提示信息

    // 創建一個模態對話框
    QDialog* dialog_new = new QDialog(this);
    dialog_new->setModal(true);
    dialog_new->show();
}

void MainWindow::on_action_O_triggered()
{
    // 創建一個非模態對話框
    QDialog* dialog_open = new QDialog(this);
    dialog_open->setModal(false);   // 非模態
    dialog_open->show();
    // qDebug() << "The open file button pushed" << endl;
}

通過dialog的setModal()函數設置對話框是模態還是非模態。

2. 自定義對話框

上述的對話框都是直接使用了QDialog類,這樣的對話框時是空白的,裏面沒有其他的東西,爲了能夠使用Qt Designer來設計對話框,則需要繼承QDialog類來設計一個自定義的會話框。

選中項目->右擊選擇“添加文件”->Qt Designer界面類,界面類模板選擇Dialog without buttons, 類名默認即可。創建成功後,會自動轉到設計模式,就可以進行設計了。

繼續選擇:

創建完成後,跳轉到設計界面,此時在生成.ui文件的同時,也生成了對應的.cpp以及.h文件。

例如可以在對話框中拖入兩個按鈕:

然後在diaog.h文件以及dialog.cpp文件中,將按鈕與相應的槽函數綁定:

1. 在dialog.h中定義槽函數:

private slots:
    void dialog_btn_ok();

2. 在dialog.cpp中連接按鈕信號和槽函數:

connect(ui->dialog_btn_ok, SIGNAL(clicked()), this, SLOT(dialog_btn_ok())); // 連接槽函數
    connect(ui->dialog_btn_cancel, SIGNAL(clicked()), this, SLOT(close()));     // 關閉對話框

這樣,就完成了對話框中信號和槽的連接。

在QMainWindow中調用設計的對話框:QMainWindow.cpp中需要include dialog.h文件即可

void MainWindow::on_action_O_triggered()
{
    Dialog* dialog_open = new Dialog(this);
    dialog_open->setModal(true);
    dialog_open->show();
    // qDebug() << "The open file button pushed" << endl;
}

效果如下所示:

3. 標準對話框:
Qt爲用戶提供了一些常用的對話框,同樣他們也繼承自QDialog類,並且增加了特定的功能,例如獲取顏色以及顯示特定信息等。下面分別介紹這些對話框。

首先需要將相應的頭文件包含到程序中:

#include <QColorDialog>       // 顏色
#include <QFontDialog>        // 字體
#include <QMessageBox>        // 消息
#include <QErrorMessage>      // 錯誤信息
#include <QFileDialog>        // 文件
#include <QInputDialog>       // 輸入
#include <QProgressDialog>    // 進度
#include <QWizard>            // 嚮導

在設計模式下,向QMainWindow中拖入按鈕,並且修改按鈕的屬性和名稱:

                       

定義按鈕對應的槽函數:

    // 標準對話框
    void dialog_color();      // 顏色對話框
    void dialog_font();       // 字體對話框
    void dialog_info();       // 消息對話框
    void dialog_error();      // 錯誤消息對話框
    void dialog_file();       // 文件對話框
    void dialog_input();      // 輸入對話框
    void dialog_progress();   // 進度對話框
    void dialog_navi();       // 嚮導對話框

連接按鈕與對應的槽函數:

void MainWindow::connect_dialogs()
{
    connect(ui->btn_dialog_color, SIGNAL(clicked()), this, SLOT(dialog_color()));
    connect(ui->btn_dialog_error, SIGNAL(clicked()), this, SLOT(dialog_error()));
    connect(ui->btn_dialog_file, SIGNAL(clicked()), this, SLOT(dialog_file()));
    connect(ui->btn_dialog_font, SIGNAL(clicked()), this, SLOT(dialog_font()));
    connect(ui->btn_dialog_info, SIGNAL(clicked()), this, SLOT(dialog_info()));
    connect(ui->btn_dialog_input, SIGNAL(clicked()), this, SLOT(dialog_input()));
    connect(ui->btn_dialog_navi, SIGNAL(clicked()), this, SLOT(dialog_navi()));
    connect(ui->btn_dialog_progress, SIGNAL(clicked()), this, SLOT(dialog_progress()));

}

1. 顏色對話框:

可以使用QColorDialog的靜態方法getColor,這樣不需要聲明對象:

// 1. 顏色對話框
void MainWindow::dialog_color()
{
    // 使用QColorDialog直接顯示對話框,無需創建對象
    QColor color = QColorDialog::getColor(Qt::red, this, "Color");  // 參數: 初始顏色  父窗口 窗口標題
    qDebug() << "color: " << color;
}

如果需要更加靈活的設置顏色對話框,可以通過創建對象來實現:

// 1. 顏色對話框
void MainWindow::dialog_color()
{
    QColorDialog* color_dialog = new QColorDialog(Qt::red, this);
    color_dialog->setOption(QColorDialog::ShowAlphaChannel);   // 顯示alpha通道
    color_dialog->exec();
    QColor color = color_dialog->currentColor();               // 獲取當前的顏色
    qDebug() << "Color: " << color << endl;
}

顏色對話框如下圖所示:

2. 錯誤消息對話框

錯誤消息對話框QErrorMessage類提供了一個現實錯誤消息的對話框,它的使用方法如下所示:

// 2. 錯誤消息對話框
void MainWindow::dialog_error()
{
    QErrorMessage* error_dialog = new QErrorMessage(this);    // 創建對話框
    error_dialog->setWindowTitle("Error");                    // 設置對話框標題
    error_dialog->showMessage("An operation error accured");  // 設置對話框的錯誤信息
}

錯誤消息對話框如下所示:

3. 文件對話框:

文件對話框QFileDialog爲用戶提供了一個允許用戶選擇文件或者文件夾的界面。使用方式如下所示:

// 3. 文件對話框
void MainWindow::dialog_file()
{
    // 獲取一個文件名,可以使用靜態方法getOpenFileName
    // 獲取多個文件名,使用靜態方法getOpenFileNames
    // 函數參數分別是:對話框的父窗口 對話框標題 打開時的默認路徑 文件過濾器(Pictures格式需要加空格),以";;"進行分隔  
    QString file_name = QFileDialog::getOpenFileName(this, "File open", "D:", "Pictures(* png * jpg);;TXT(*txt)");
    qDebug() << "Filename is: " << file_name << endl;
}

對話框如下:

4. 字體對話框:

向用戶提供一個可以選擇字體的對話框:

// 4. 字體對話框
void MainWindow::dialog_font()
{
    bool ok = false;      // 用來判斷用戶是否選擇了字體
    QFont font = QFontDialog::getFont(&ok, this);   // 獲取字體
    if(ok)
    {
        qDebug() << "Font: " << font << endl;
        ui->btn_dialog_font->setFont(font);         // 將font按鈕的字體改編爲選擇的字體
    }
    else
    {
        qDebug() << "Not select font" << endl;
    }

}

字體對話框如下所示:

可以看到,在選擇字體後,字體按鈕所對應的字體發生了變化:

5. 消息對話框:

消息對話框提供一個模態的對話框來通知用戶一些信息,或者向用戶提出問題並獲取答案,具體的使用如下所示:

// 5. 消息對話框
void MainWindow::dialog_info()
{
    // 提問對話框,用於和用戶交互簡單問題
    int ret1 = QMessageBox::question(this, "Question dialog", "Do u know Qt?", QMessageBox::Yes, QMessageBox::No);
    if(ret1==QMessageBox::Yes)
    {
        qDebug() << "Very goood";
    }
    // 提示對話框
    int ret2 = QMessageBox::information(this, "Tip dialog", "This is a book about Qt", QMessageBox::Yes);
    if(ret2==QMessageBox::Yes)
    {
        qDebug() << "This is a tip";
    }
    // 警告對話框
    int ret3 = QMessageBox::warning(this, "waring dialog", "You can not operate", QMessageBox::Abort);
    if(ret3==QMessageBox::Abort)
    {
        qDebug() << "This is a warning" << endl;
    }
    // 嚴重錯誤對話框
    int ret4 = QMessageBox::critical(this, "criticalerror dialog", "An critical occured!", QMessageBox::YesAll);
    if(ret4==QMessageBox::YesAll)
    {
        qDebug() << "Error happen" << endl;
    }
    QMessageBox::about(this, "about dialog", "Qt dialog object");
}

上面的實例中展示了不同的消息對話框,按照重要等級遞進:

a1. 問題對話框:和用戶進行簡單的交互

a2. 提示對話框,對用戶進行簡單的提示

a3. 警告對話框,提示可能會 發生的錯誤

a4. 嚴重錯誤對話框,告知用戶發生嚴重錯誤

a5.關於對話框

--------------------------------------------------------------------------------------------------------------------------------

6. 輸入對話框:

輸入對話框QInputDialog類用來提供一個輸入對話框,用戶可以輸入單一的數值或者字符串。

// 6. 輸入對話框
void MainWindow::dialog_input()
{
    bool ok;
    // 獲取輸入的文本信息
    // getText()參數 父窗口 標題 label 輸入框 默認字符串 ok
    QString name = QInputDialog::getText(this, "Input Dialog", "Name", QLineEdit::Normal, "Admin", &ok);
    if(ok)
    {
        qDebug() << "name: " << name << endl;
    }

    // 獲取輸入的數值信息
    // getInt()參數:父窗口 標題 label 默認數值 最小值 最大值 步長 ok
    int ret = QInputDialog::getInt(this, "Input Dialog", "age", 20, 10, 100, 1, &ok);
    if(ok)
    {
        qDebug() << "Age: " << ret << endl;
    }
    // 獲取輸入的數值信息
    double salary = QInputDialog::getDouble(this, "Input Dialog", "Salary", 20000, 5000, 100000, 500.45, &ok);
    if(ok)
    {
        qDebug() << "Salary: " << salary << endl;
    }
    // 相當於一個多選一的對話框,下拉的選擇菜單
    QStringList items;
    items << "male" << "female";     // 對話框內容
    QString item = QInputDialog::getItem(this, "Input dialog", "Select sex", items, 0, true, &ok);
    if(ok)
    {
        qDebug() << "Sex: " << item;
    }

}

輸入對話框可以實現用戶輸入字符串,數值,下拉菜單選擇等。

a1. 輸入字符串:

a2. 輸入數值:

a3. 下拉菜單:

7. 嚮導對話框:

QWizard是嚮導對話框,它向用戶提供了一個設計嚮導界面的框架,例如,安裝軟件以及創建項目的時候,就是典型的嚮導對話框。Qwizard是一個嚮導對話框的框架,它可以設計一個嚮導全部的功能函數,需要首先創建出嚮導頁面WizardPage,然後將嚮導頁面添加到嚮導對話框。

a1, 定義首先創建嚮導頁面的函數:

private:
    // 創建導航頁面
    QWizardPage* create_page1();
    QWizardPage* create_page2();
    QWizardPage* create_page3();


// 創建導航頁
QWizardPage* MainWindow::create_page1()
{
    QWizardPage* page = new QWizardPage(this);
    page->setTitle("Recommendation");
    return page;
}


QWizardPage* MainWindow::create_page2()
{
    QWizardPage* page = new QWizardPage(this);
    page->setTitle("Custom choose infmation");
    return page;
}

QWizardPage* MainWindow::create_page3()
{
    QWizardPage* page = new QWizardPage(this);
    page->setTitle("End");
    return page;
}

a2. 創建嚮導對話框:

// 7. 嚮導對話框
void MainWindow::dialog_navi()
{
    QWizard wizard(this);    // 創建一個導航窗口對象
    wizard.setWindowTitle("Wizard dialog");
    wizard.addPage(create_page1());    // 添加頁面
    wizard.addPage(create_page2());
    wizard.addPage(create_page3());
    wizard.exec();
}

嚮導對話框頁面:

8. 進度條對話框:

對一個時間較長的操作提供時間反饋:

// 8. 進度對話框
void MainWindow::dialog_progress()
{
    QProgressDialog progress_dialog("File copy progress", "Cancel", 0, 5000, this);
    progress_dialog.setWindowTitle("Copy file");
    progress_dialog.show();
    for(int i=0; i<50000; i++)
    {
        progress_dialog.setValue(i);
        QCoreApplication::processEvents();   // 避免長時間操作而使用戶界面凍結
        if(progress_dialog.wasCanceled())
        {
            break;
        }
    }
    progress_dialog.setValue(50000);
    qDebug() << "copy finished" << endl;

}

給app添加圖標:

第一步;將圖片轉化爲.ico文件:

網上的免費工具即可完成轉換: http://www.bitbug.net/

第二步: 將.ico文件放入到目錄中:

第三步:

在pro文件中,添加以下代碼:

RC_ICONS += appico.ico

但是我的頓操作之後並沒有顯示,百度也沒有解決,再查查看

------------------------------------------------------------------------------------------------------------------

發佈了103 篇原創文章 · 獲贊 57 · 訪問量 8萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章