C++ 入門指南 4.01

單元 27 - 使用 QML 設計視窗外觀

-unit27-

設計圖形使用者介面 (graphical user interface, GUI) 應用程式 (application) 的步驟如下

建立視窗 → 設定版面編排
→ 加入視窗元件
→ 設定視窗元件的樣式
→ 建立實際功能

簡單的 GUI 程式不受此限,但是複雜一點的 GUI 程式按照這樣的步驟實際設計起來會比較輕鬆。

像是上個單元的物件層級 (object hierarchy) 範例, Window 是最外層的視窗

Window {

Window 這裡設定視窗尺寸及其他相關屬性,然後底下應該先進行版面編排 (layout) ,不過這裡簡化到 Buuton 裡面的 anchors.centerIn

anchors.centerIn: parent

anchors.centerIn 是讓 Button 放到指定視窗元件的中心位置, parent 就是指上一層視窗元件,在這個例子中就是 Window ,所以這個 Button 會出現在 Window 的正中央。

此外在這個例子中,除了選單列 MenuBar 之外,設定 Button 中的 onClicked 也就是建立這個 GUI 應用程式的實際功能

onClicked: {
    button.text = "按鈕"
}

MenuBarButton 就是物件層級範例所加入的視窗元件。

回到我們編密碼的 Encrypt 類別 (class) ,預計的 GUI 如下圖

-encryptwindow-

以視窗元件來看會是

TextTextField
TextTextField
ButtonButtonButtonButtonButtonButtonButton
Text

簡單說就是一組表格,就術語來講這是格子狀的版面編排方式,我們已經上個單元的練習中見過數種格子版面編排方式,在 Encrypt 類別的 GUI 範例預計採用 Column 為直欄,然後在 Column 建立四個 Row 來放置上表中的視窗元件。

以下先看到 import 的部分,除了要先 import QtQuick 外,也要 import QtQuick.Controls ,因為下面用到的視窗元件,例如 TextFieldButton 等都定義在 QtQuick.Controls 內,所以要先 import QtQuick.Controls

import QtQuick
import QtQuick.Controls

完整的 QML 檔案請參考「範例程式篇」的 encryptor_gui_demo/main.qml

接下來是把 Window 換成 ApplicationWindowApplicationWindow 繼承 (inherit) Window ,同樣定義在 QtQuick.Controls

ApplicationWindow {
    id: root
    width: 350
    height: 120
    visible: true

    title: qsTr("編密碼小工具")

以上設定了 idwidthheightvisibletitle 等屬性,基本設定跟 Window 一樣, ApplicationWindow 相較 Window 支援更多的 Controls 視窗元件,功能也更豐富。

繼續是 Column 有 4 個 Row ,每一個 Row 都是一個橫列

Column {

下面看到第一個 Row ,裡頭有一個 Text 及一個 TextField

Row {
    width: 350
    height: 25

    Text {
        width: 50
        horizontalAlignment: Text.AlignRight
        text: qsTr("輸入:")
    }

    TextField {
        id: input
        width: 300
        color: "blue"
        placeholderText: qsTr("輸入英文句子")
        text: ""
    }
}

其中, TexthorizontalAlignment 設定為 Text.AlignRight ,這是讓文字在 50 的寬度內向右對齊,因此 Text 的文字緊接右側的 TextField ,對齊也就是設定樣式 (style) ,基本上樣式多半由屬性來設定

horizontalAlignment: Text.AlignRight

然後注意到 TextField 的顏色 color 設定為 "blue" ,這是藍色的意思,文字顏色也是樣式,因此使用者輸入的文字會是藍色

color: "blue"

placeholderText 則是設定預設的提示文字,這裡提示使用者輸入「輸入英文句子」

placeholderText: qsTr("輸入英文句子")

繼續看到第二個 Row 中的 TextTextField ,由於 Text 大部分都相同,我們集中看到有不一樣的 TextField 部分

TextField {
    id: output
    width: 300
    color: "red"
    placeholderText: qsTr("這裡顯示編碼結果")
    readOnly: true
    text: ""
}

顏色設定為 "red" ,也就是顯示文字會是紅色

color: "red"

預設的提示文字為「這裡顯示編碼結果」

placeholderText: qsTr("這裡顯示編碼結果")

另外將 readOnly 設定為 true ,這是因為這個 TextField 用作顯示結果,因此設定為唯獨

readOnly: true

第三個 Row 是七個按鈕,每個按鈕都先用類似的設置

Row {
    width: 350
    height: 35

    Button {
        id: newButton
        width: 50
        text: qsTr("新建")

        onClicked: {
            display.text = qsTr("新建按鈕")
        }
    }

這裡每一個按鈕都設定成按下之後,在底下的 Text 顯示按下的按鈕名稱,注意這裡是呼叫底下 Textid

onClicked: {
    display.text = qsTr("新建按鈕")
}

最後一個 Row 就只有一個 Textiddisplay

Row {
    width: 350
    height: 50
    Text {
        id: display
        width: 350
        text: qsTr("提示訊息")
    }
}

目前版本執行如下圖

-qt_gui_01-

輸入文字,按下編碼按鈕如下圖

-qt_gui_02-

GUI 就用 QML 建立好了,接下來要先建立 EncryptController 類別,以便後續整合 Encrypt 類別,讓我們 Encrypt 類別的 GUI 具有實際編碼及解碼的功能。


中英文術語對照
應用程式application
類別class
圖形使用者介面graphical user interface, GUI
繼承inherit
版面編排layout
物件層級object hierarchy
樣式style
重點整理
1. QML 建立圖形使用者介面應用程式的步驟為建立視窗、設定版面編排、加入視窗元件、設定視窗元件的樣式、建立實際功能。
2. QML 的版面編排可由屬性或相關元件設定。
3. QML 可在原視窗元件的型態下建立其他的視窗元件,這樣新視窗元件就會加入到原視窗元件上。
4. QML 由屬性設定視窗元件的樣式。
5. QML 可在指定屬性設定具備實際功能的 JavaScript 程式碼,以實現視窗元件的功能。
6. ApplicationWindowQtQuick.Controls 底下的視窗型態,比 Window 支援更多的 Controls 型態及功能。
7. Encrypt 的 GUI 用 ColumnRow 形成格子版面編排, Column 為直欄, Row 為橫列,預計採用一個 Column 有四個 Row ,也就是一個直欄中有四個橫列。
8. TexthorizontalAlignment 可以設定文字的水平對齊方式。
9. TextFieldcolor 可以設定輸入文字的顏色, placeholderText 是設定文字方塊中的預設文字, readOnly 設定文字方塊是否為唯讀, text 設定文字方塊的文字。
10. Buttontext 設定按鈕的文字, onClicked 設定互動的 JavaScript 程式。
11. 視窗元件如果設定 id ,就可以利用 JavaScript 程式碼控制這個視窗元件。。
問題與討論
1. 建立 GUI 應用程式的步驟為何?為什麼要用這些步驟?
2. QML 要怎麼做版面編排?
3. QML 的視窗元件要怎麼設定樣式?
4. ApplicationWindowWindow 有何不同?
5. QML 的視窗元件要怎麼建立實際功能?
練習
1. QML 中的 CheckBox 為讓使用者勾選的核取方塊,建立一個 QtQuick 的 checkbox_demo 專案,裡頭繼續建立 5CheckBox ,並且把 CheckBox 放到 ColumnLayoutColumn 中,同時把數個 CheckBoxchecked 設定為 true ,使之為預設勾選。 參考程式碼
2. QML 中的 DelayButton 為具有進度點擊效果的按鈕,建立一個 QtQuick 的 delaybutton_demo 專案,裡頭建立一個 DelayButtonwidth 設定為 200 或更寬, height 設定為 120 或更低。 參考程式碼
3. QML 中的 RadioButton 為只能單選的核取方塊,建立一個 QtQuick 的 radiobutton_demo 專案,裡頭繼續建立 5RadioButton ,並且把 RadioButton 放到 ColumnLayoutColumn 中,同時將其中一個 RadioButtonchecked 設定為 true ,使之為預設選項。 參考程式碼
4. QML 中的 RoundButton 為圓形的按鈕,建立一個 QtQuick 的 roundbutton_demo 專案,裡頭建立一個 RoundButton ,並設定按下按鈕將視窗背景改為紅色。 參考程式碼
5. QML 中的 Switch 為滑動開啟功能選項的按鈕,建立一個 QtQuick 的 switch_demo 專案,裡頭建立兩個 Switch ,一個設定為網路,另一個設定為藍芽。 參考程式碼
6. QML 中的 ToolBar 用來設定工具列, ToolBar 裡面利用 ToolButton 設定工具列按鈕,建立一個 QtQuick 的 toolbar_demo 專案,裡頭建立工具列,並可用工具列按鈕改變視窗背景顏色。 參考程式碼
7. QML 中的 Popup 為顯示在視窗中的新視窗,這可用來顯示附加內容,建立一個 QtQuick 的 popup_demo 專案,裡頭建立一個 Popupid 設定為 popup ,尺寸設定為原視窗的四分之一, modalfocus 設定為 trueclosePolicy 設定為 Popup.CloseOnEscape | Popup.CloseOnPressOutsideParent ,然後在 Popup 裡頭建立一個 Text ,顯示任意文字,另外建立一個 Button ,使按下按鈕呼叫 popup.open() ,打開這個 Popup參考程式碼
8. QML 中的 ToolTip 用來顯示視窗元件的提示訊息,建立一個 QtQuick 的 tooltip_demo 專案,裡頭建立一個 Button ,然後將 ToolTip.visible 設定為 hovered ,這讓滑鼠游標在按鈕上方就顯示提示訊息,然後 ToolTip.text 的提示文字。 參考程式碼
9. QML 中的 BusyIndicator 用來顯示忙碌載入的動畫效果,建立一個 QtQuick 的 busy_demo 專案,裡頭建立一個 BusyIndicator ,然後將 running 設定為 image.status === Image.Loading參考程式碼
10. QML 中的 ProgressBar 用來顯示進度條,建立一個 QtQuick 的 progress_demo 專案,裡頭建立一個 ProgressBarheight 設定為 20width 設定為 200value 設定為 0.75參考程式碼

相關教學影片

上一頁 單元 26 - MVC 模式與 QML
回 C++ 入門指南 4.01 目錄
下一頁 單元 28 - EncryptController 類別
回 C++ 教材
回程式語言教材首頁