Qt之MVC編程


零、前言

MVC在Qt中叫做MVD,Model+View+Delegate。關於Model,Qt提供了以QAbstractItemModel為父類的相關類。如圖:

 

①、QAbstractItemModel提供給數據一個接口,它非常靈活,基本滿足views的需要,無論數據用什么樣的形式表現,如tables,lists,trees;
②、如果model基於list、table形式的數據結構,可從QAbstractListModel、QAbstractTableModel開始做起,因為它們提供了適當的常規功能的缺省實現;
③、QStringListModel 用於存儲簡單的QString列表;
④、QStandardItemModel 管理復雜的樹型結構數據項,每項都可以包含任意數據;
⑤、QDirModel 提供本地文件系統中的文件與目錄信息;
⑥、QSqlQueryModel、QSqlTableModel、QSqlRelationTableModel用來訪問數據庫;
假如這些標准Model不滿足需要,可子類化QAbstractItemModel、QAbstractListModel、QAbstractTableModel等來定制。

 

PS:

根據這個原理,QXXXView和QXXXWidget的區別:View可以手動設置自定義Model進去,Widget只能用標准的自帶Model;

在QML中Grid和GridView區別也是,帶View的是可以設置Model的。

 

一、靜態視圖

1、Repeater+model:數字

import QtQuick 2.0
Column{
    spacing:2
    Repeater{
        model:10
        Rectangle{
            width:100
            height:20
            radius:3
            color:"lightBlue"
            Text{
                anchors.centerIn: parent
                text:index
            }
        }
    }
}

Repeater會傳遞分配給delegate的index;

這里Rectangle前省略了delegate,建議都加上,免得看不懂。

 

 2、Repeater+model:js序列

序列可以是字符串、整數或者對象,以字符串為例

import QtQuick 2.0
Column {
    spacing: 2
    Repeater {
        model: ["Enterprise", "Colombia", "Challenger", "Discovery", "Endeav"]
        delegate:  Rectangle {
            width: 100
            height: 20
            radius: 3
            color: "lightBlue"
            Text {
                anchors.centerIn: parent
                text: index +": "+modelData
            }
        }
    }
}

 Repeater會傳遞分配給delegate的index和序列對象,這里是字符串。

 

  3、Repeater+model:ListModel

import QtQuick 2.0
import QtQml.Models 2.15
Column{
    spacing:2
    Repeater{
        model:ListModel{
            ListElement{name:"Mercury";surfaceColor:"gray"}
            ListElement{name:"Venus";surfaceColor:"yellow"}
            ListElement{name:"Earth";surfaceColor:"blue"}
            ListElement{name:"Mars";surfaceColor:"orange"}
            ListElement{name:"Jupiter";surfaceColor:"orange"}
            ListElement{name:"Saturn";surfaceColor:"yellow"}
            ListElement{name:"Uranus";surfaceColor:"lightBlue"}
            ListElement{name:"Neptune";surfaceColor:"lightBlue"}
        }
        delegate:Rectangle{
            width:100
            height:20
            radius:3
            color:"lightBlue"
            Text{
                anchors.centerIn:parent
                text:name
            }
            Rectangle{
                anchors.left:parent.left
                anchors.verticalCenter:parent.verticalCenter
                anchors.leftMargin:2
                width:16
                height:16
                radius:8
                border.color:"black"
                border.width:1
                color:surfaceColor
            }
        }
    }
}

 

 

  Repeater會傳遞分配給delegate的index和ListElement對象,可訪問ListElement里的所有元素,這是里name、serfaceColor。

 

PS:

①、Repeator的model里可以放的數據如下,

 

 

 一個數字代表着生成多少個模型;

一個ListModel或QAbstractItemModel子類;

一個字符串列表;

一個對象列表。

 

4、ListView+ListModel

import QtQuick 2.5

Item {
    id: root

    width: 400
    height: 300

    ListView {
        anchors.fill: parent
        model: fruitModel
        delegate: Row {
            Text { text: "Fruit: " + name }
            Text { text: "Cost: $" + cost }
        }
    }
    ListModel {
        id: fruitModel

        ListElement {
            name: "Apple"
            cost: 2.45
        }
        ListElement {
            name: "Orange"
            cost: 3.25
        }
        ListElement {
            name: "Banana"
            cost: 1.95
        }
    }
}

 

 

 二、動態視圖

1、動態為GridView增刪對象

import QtQuick 2.0
import QtQml.Models 2.15
Rectangle {
    width: 480;
    height: 300;

    //背景色漸變
    gradient: Gradient {
        GradientStop { position: 0.0; color: "#dbddde"; }
        GradientStop { position: 1.0; color: "#5fc9f8"; }
    }

    //list模型默認9項
    ListModel {
        id: theModel
        ListElement { number: 0; }
        ListElement { number: 1; }
        ListElement { number: 2; }
        ListElement { number: 3; }
        ListElement { number: 4; }
        ListElement { number: 5; }
        ListElement { number: 6; }
        ListElement { number: 7; }
        ListElement { number: 8; }
        ListElement { number: 9; }
    }

    //Add Item按鈕
    Rectangle {
        anchors.left: parent.left;
        anchors.right: parent.right;
        anchors.bottom: parent.bottom;
        anchors.margins: 20;
        height: 40;
        color: "#53d769";
        border.color: Qt.lighter(color, 1.1);
        Text {
            anchors.centerIn: parent;
            text: "Add item!";
        }
        //點擊時新增項  實現model的動態新增
        MouseArea {
            anchors.fill: parent;
            onClicked: {
                theModel.append({"number": ++parent.count});
            }
        }
        property int count: 9;//
    }
    GridView {
        anchors.fill: parent;
        anchors.margins: 20;
        anchors.bottomMargin: 80;
        clip: true;
        model: theModel;//綁定數據源
        cellWidth: 45;//設置項大小
        cellHeight: 45;
        delegate: numberDelegate;//設置繪制代理
    }

    //自定義繪制代理
    Component {
        id: numberDelegate;
        Rectangle {
            id: wrapper;
            width: 40;
            height: 40;
            //首先是一個漸變的矩形框
            gradient: Gradient {
                GradientStop { position: 0.0; color: "#f8306a"; }
                GradientStop { position: 1.0; color: "#fb5b40"; }
            }
            //文本值是number的數值
            Text {
                anchors.centerIn: parent;
                font.pixelSize: 10;
                text: number;
          //text: index;//顯示當前序號 }
//鼠標點擊代理時,移除點擊項 MouseArea { anchors.fill: parent; onClicked: { if (!wrapper.GridView.delayRemove)//是否延遲移除 { theModel.remove(index); } } } //GridView移除項 順序動畫 GridView.onRemove: SequentialAnimation { //屬性變化 PropertyAction { target: wrapper; property: "GridView.delayRemove"; value: true; } //數字動畫 NumberAnimation { target: wrapper;//目標對象 property: "scale";//執行動畫的屬性 to: 0;//結束值 duration: 250;//動畫持續時長 easing.type: Easing.InOutQuad;//動畫執行曲線 } PropertyAction { target: wrapper; property: "GridView.delayRemove"; value: false; } } //GridView新增項 順序動畫 GridView.onAdd: SequentialAnimation { NumberAnimation { target: wrapper; property: "scale"; from: 0;//開始值 to: 1; duration: 250; easing.type: Easing.InOutQuad; } } } } }

 

 

 

 

 

 

 

https://zhuanlan.zhihu.com/p/66928607


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2026 CODEPRJ.COM