Qt 模型视图结构学习教案

上传人:可**** 文档编号:113188025 上传时间:2022-06-24 格式:PPTX 页数:42 大小:598.16KB
收藏 版权申诉 举报 下载
Qt 模型视图结构学习教案_第1页
第1页 / 共42页
Qt 模型视图结构学习教案_第2页
第2页 / 共42页
Qt 模型视图结构学习教案_第3页
第3页 / 共42页
资源描述:

《Qt 模型视图结构学习教案》由会员分享,可在线阅读,更多相关《Qt 模型视图结构学习教案(42页珍藏版)》请在装配图网上搜索。

1、会计学1Qt 模型视图模型视图(sht)结构结构第一页,共42页。Qt的模型/视图结构分为三部分(b fen):模型(Model)、视图(View)和代理(Delegate)。其中,模型与数据源通信,并为其他部件提供接口;而视图从模型中获得用来引用数据条目的模型索引(Model Index)。在视图中,代理负责绘制数据条目,当编辑条目时,代理和模型直接进行通信。模型/视图/代理之间通过信号和槽进行通信,如图8.1所示。第1页/共42页第二页,共42页。8.1.1 基本概念基本概念1模型模型(mxng)(Model)InterView框架中的所有模型框架中的所有模型(mxng)都基于抽象基类都基

2、于抽象基类QAbstractItemModel类,此类,此类由类由QProxyModel、QAbstractListModel、QAbstractTableModel、QAbstractProxyModel、QDirModel、QFileSystemModel、QHelpContentModel 和和 QStandardItemModel类继承。其中,类继承。其中,QAbstractListModel类和类和QAbstractTableModel类类是列表和表格模型是列表和表格模型(mxng)的抽象基类,如果需要实现列表或表格模型的抽象基类,如果需要实现列表或表格模型(mxng),则应,则应从

3、这两个类继承。从这两个类继承。第2页/共42页第三页,共42页。2视图(视图(View)InterView框架中的所有视图都基于抽象基类框架中的所有视图都基于抽象基类QAbstractItemView类,此类由类,此类由QColumnView、QHeaderView、QListView、QTableView和和QTreeView类继承。其中,类继承。其中,QListView类由类由QUndoView类和类和QListWidget类继承;类继承;QTableView类由类由QTableWidget类继承;类继承;QTreeView类由类由QTreeWidget类继承。而类继承。而QListWid

4、get类、类、QTableWidget类和类和QTreeWidget类实际上已经包含了数据,是模型类实际上已经包含了数据,是模型/视图集成在一起的类。视图集成在一起的类。3代理代理(dil)(Delegate)InterView框架中的所有代理框架中的所有代理(dil)都基于抽象基类都基于抽象基类QAbstractItemDelegate类,此类由类,此类由QItemDelegate 和和 QStyledItemDelegate类继承。其中,类继承。其中,QItemDelegate类由表示数据库中关系代理类由表示数据库中关系代理(dil)的的QSqlRelationalDelegate类继承。

5、类继承。第3页/共42页第四页,共42页。【例】(简单(jindn)) 实现一个简单(jindn)的文件目录浏览器,完成效果如图8.2所示。实例文件见光盘CH801。创建工程“DirModeEx.pro”,其源文件“main.cpp”中的具体代码。最后(zuhu)运行结果如图8.2所示。第4页/共42页第五页,共42页。【例】(难度(nd)一般) 通过实现将数值代码转换为文字的模型来介绍如何使用自定义模型。此模型中保存了不同军种的各种武器,实现效果如图8.3所示。实例文件见光盘CH802。第5页/共42页第六页,共42页。具体操作步骤如下。(1)ModelEx类继承(jchng)自QAbstr

6、actTableModel类,头文件“modelex.h”中的具体代码。(2)源文件“modelex.cpp”中的具体代码。populateModel()函数的具体实现代码如下:void ModelEx:populateModel() headertr(军种)tr(种类)tr(武器); army12342431; weaponType13574862; weapontr(B-2)tr(尼米兹级)tr(阿帕奇)tr(黄蜂级) tr(阿利伯克级)tr(AAAV)tr(M1A1)tr(F-22);第6页/共42页第七页,共42页。columnCount()函数中,模型的列固定为“3”,所以直接(zh

7、ji)返回“3”。int ModelEx:columnCount(const QModelIndex &parent) const return 3; rowCount()函数返回模型的行数。int ModelEx:rowCount(const QModelIndex &parent) const return army.size();data()函数返回指定索引的数据,即将数值映射为文字。第7页/共42页第八页,共42页。表8.1列出了Item主要的角色(ju s)及其描述。常 量描 述Qt:DisplayRole显示文字Qt:DecorationRole绘制装饰数据(通常是图标)Qt:Ed

8、itRole在编辑器中编辑的数据Qt:ToolTipRole工具提示Qt:StatusTipRole状态栏提示Qt:WhatsThisRoleWhats This文字Qt:SizeHintRole尺寸提示Qt:FontRole默认代理的绘制使用的字体Qt:TextAlignmentRole默认代理的对齐方式Qt:BackgroundRole默认代理的背景画刷Qt:ForegroundRole默认代理的前景画刷Qt:CheckStateRole默认代理的检查框状态Qt:UserRole用户自定义的数据的起始位置第8页/共42页第九页,共42页。headerData()函数(hnsh)返回固定的表

9、头数据,设置水平表头的标题,具体代码如下:QVariant ModelEx:headerData(int section, Qt:Orientation orientation, int role) const if(role=Qt:DisplayRole&orientation=Qt:Horizontal) return headersection; return QAbstractTableModel:headerData(section,orientation,role);第9页/共42页第十页,共42页。(3)在源文件“main.cpp”中,将模型和视图关联,具体代码如下(rxi):#

10、include #include modelex.h#include int main(int argc,char *argv) QApplication a(argc,argv); ModelEx modelEx; QTableView view; view.setModel(&modelEx); view.setWindowTitle(QObject:tr(modelEx); view.resize(400,400); view.show(); return a.exec();(4)运行结果如图8.3所示。第10页/共42页第十一页,共42页。【例】(难度中等) 通过利用自定义的View,

11、实现一个对TableModel的表格数据进行显示(xinsh)的柱状统计图例子,以此介绍如何应用自定义的View。实现效果如图8.4所示。实例文件见光盘CH803。第11页/共42页第十二页,共42页。具体实现步骤如下。(1)完成主窗体,以便显示View的内容。MainWindow 类继承自QMainWindow类,作为主窗体。以下是头文件“mainwindow.h”的具体代码。(2)下面是源文件“mainwindow.cpp”中的具体代码。setupModel()函数新建一个Model,并设置表头(bio tu)数据,其具体实现代码如下:void MainWindow:setupModel(

12、) model = new QStandardItemModel(4,4,this); model-setHeaderData(0,Qt:Horizontal,tr(部门); model-setHeaderData(1,Qt:Horizontal,tr(男); model-setHeaderData(2,Qt:Horizontal,tr(女); model-setHeaderData(3,Qt:Horizontal,tr(退休);第12页/共42页第十三页,共42页。setupView()函数的具体实现代码如下(rxi):void MainWindow:setupView() table =

13、new QTableView;/新建一个QTableView对象 table-setModel(model);/为QTableView对象设置相同的Model QItemSelectionModel *selectionModel=new QItemSelectionModel(model);/(a) table-setSelectionModel(selectionModel); connect(selectionModel,SIGNAL(selectionChanged(QItemSelection, ItemSelection),table,SLOT(selectionChanged(Q

14、ItemSelection,QItemSelec-tion);/(b) splitter = new QSplitter; splitter-setOrientation(Qt:Vertical); splitter-addWidget(table); setCentralWidget(splitter);第13页/共42页第十四页,共42页。(3)此时,运行(ynxng)效果如图8.5所示。第14页/共42页第十五页,共42页。(1)在头文件“mainwindow.h”中添加代码(di m)如下:public: void openFile(QString);public slots: voi

15、d slotOpen();(2)在源文件mainwindow.cpp中添加代码(di m)如下:#include #include #include #include 其中,在createAction()函数中添加代码(di m)如下:connect(openAct,SIGNAL(triggered(),this,SLOT(slotOpen();第15页/共42页第十六页,共42页。槽函数slotOpen()完成(wn chng)打开标准文件对话框,具体代码如下:void MainWindow:slotOpen() QString name; name = QFileDialog:getOpe

16、nFileName(this,打开,.,histogram files (*.txt); if (!name.isEmpty() openFile(name);openFile()函数完成(wn chng)打开所选的文件内容,其具体实现代码。第16页/共42页第十七页,共42页。新建一个文本文件,命名为“histogram.txt”,保存在项目(xingm)D:QtCH8CH803 build-ViewEx-Desktop_Qt_5_4_0_MinGW_32bit-Debug目录下,文件内容及打开后的效果如图8.6所示。第17页/共42页第十八页,共42页。以上完成了表格数据的加载,下面介绍柱

17、状统计图的绘制。具体实现步骤如下。(1)自定义HistogramView类继承自QAbstractItemView类,用于对表格数据进行柱状图显示。下面是头文件“histogramview.h”的具体代码(di m)。(2)源文件“histogramview.cpp”的具体代码(di m)。dataChanged()函数实现当Model中的数据更改时,调用绘图设备的update()函数进行更新,反映数据的变化。具体实现代码(di m)。void HistogramView:dataChanged(const QModelIndex &topLeft, const QModelIndex &bo

18、ttomRight) QAbstractItemView:dataChanged(topLeft,bottomRight); viewport()-update();setSelectionModel()函数为selections赋初值,具体代码(di m)如下:void HistogramView:setSelectionModel(QItemSelectionModel *selectionModel) selections=selectionModel;第18页/共42页第十九页,共42页。(3)下面的工作就是完成对选择项的更新。selectionChanged()函数中完成当数据项发生

19、变化时调用update()函数,重绘绘图设备(shbi)即可工作。此函数是将其他View中的操作引起的数据项选择变化反映到自身View的显示中。具体代码如下:void HistogramView:selectionChanged(const QItemSelection &selected, const QItemSelection &deselected) viewport()-update();鼠标按下事件函数mousePressEvent(),在调用setSelection()函数时确定鼠标单击点是否在某个数据项的区域内,并设置选择项。具体代码如下:void HistogramView:

20、mousePressEvent(QMouseEvent *event) QAbstractItemView:mousePressEvent(event); setSelection(QRect(event-pos().x(),event-pos().y(),1,1),QItemSelec tionModel:SelectCurrent);第19页/共42页第二十页,共42页。setSelection()函数的具体代码(di m)如下:void HistogramView:setSelection(const QRect &rect,QItemSelectionModel:SelectionFl

21、ags flags) int rows = model()-rowCount(rootIndex();/获取总行数 int columns = model()-columnCount(rootIndex();/获取总列数 QModelIndex selectedIndex;/(a) for (int row=0; rowrows; +row)/(b) for (int column=1; columnindex(row,column,rootIndex(); QRegion region=itemRegion(index);/(c) if (!region.intersected(rect).

22、isEmpty() selectedIndex = index; if(selectedIndex.isValid()/(d) selections-select(selectedIndex,flags); else QModelIndex noIndex; selections-select(noIndex,flags); 第20页/共42页第二十一页,共42页。indexAt()函数的具体内容。由于本例未用到以下函数的功能,所以没有实现具体内容,但仍然要写出函数体的框架,代码(di m)如下:QRect HistogramView:visualRect(const QModelIndex

23、&index)constvoid HistogramView:scrollTo(const QModelIndex &index,ScrollHint)QModelIndex HistogramView:moveCursor(QAbstractItemView:CursorAction cursor Action, Qt:KeyboardModifiers modifiers)int HistogramView:horizontalOffset()constint HistogramView:verticalOffset()constbool HistogramView:isIndexHidd

24、en(const QModelIndex &index)constQRegion HistogramView:visualRegionForSelection(const QItemSelection & selection)const第21页/共42页第二十二页,共42页。itemRegion()函数的具体(jt)代码如下:QRegion HistogramView:itemRegion(QModelIndex index) QRegion region; if (index.column() = 1)/男 region = MRegionListindex.row(); if (index

25、.column() = 2)/女 region = FRegionListindex.row(); if (index.column() = 3)/退休 region = SRegionListindex.row(); return region;第22页/共42页第二十三页,共42页。(4)在头文件“mainwindow.h”中添加代码如下:#include histogramview.hprivate: HistogramView *histogram;(5)在源文件“mainwindow.cpp”中添加代码,其中,setupView()函数的代码修改(xigi)。(6)运行结果如图8.4

26、所示。第23页/共42页第二十四页,共42页。【例】(难度中等) 利用Delegate设计(shj)表格中控件如图8.7所示。实例文件见光盘CH804。第24页/共42页第二十五页,共42页。具体实现步骤如下。(1)首先,加载表格数据,以便后面的操作。源文件“main.cpp”中的具体代码如下:(2)选择“构建(u jin)”“构建(u jin)项目DateDelegate”菜单项,首先按照如图8.8所示的格式编辑本例所用的数据文件“test.txt”,保存在项目D:QtCH8CH804 build- DateDelegate-Desktop_Qt_5_4_0_MinGW_32bit- Deb

27、ug目录下,然后运行程序,结果如图8.7所示。第25页/共42页第二十六页,共42页。(3)在图8.7中,使用手动的方式实现对生日的录入编辑。下面(xi mian)使用日历编辑框QDateTimeEdit 控件实现对生日的编辑,用自定义的Delegate来实现。(4)DateDelegate 继承自QItemDelegate类。头文件“datedelegate.h”中的具体代码如下:#include class DateDelegate : public QItemDelegate Q_OBJECTpublic: DateDelegate(QObject *parent = 0); QWidg

28、et *createEditor(QWidget *parent, const QStyleOptionViewItem & option, const QModelIndex &index) const;/(a) void setEditorData(QWidget *editor, const QModelIndex &index) const;/(b) void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const;/将Delegate中对数据的改变更新至Model

29、中 void updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem & option, const QModelIndex &index) const;/更新控件区的显示;第26页/共42页第二十七页,共42页。(5)源文件“datedelegate.cpp”中的具体代码如下:#include datedelegate.h#include DateDelegate:DateDelegate(QObject *parent) : QItemDelegate(parent)createEditor()函数(hnsh)的具体

30、实现代码如下:QWidget *DateDelegate:createEditor(QWidget *parent,const QStyleOption ViewItem &/*option*/,const QModelIndex &/*index*/) const QDateTimeEdit *editor = new QDateTimeEdit(parent);/(a) editor-setDisplayFormat(yyyy-MM-dd);/(b) editor-setCalendarPopup(true);/(c) editor-installEventFilter(const_cas

31、t(this);/(d) return editor;第27页/共42页第二十八页,共42页。setEditorData()函数的具体代码(di m)如下:void DateDelegate:setEditorData(QWidget *editor, const QModelIndex &index) const QString dateStr= index.model()-data(index).toString();/(a) QDate date = QDate:fromString(dateStr,Qt:ISODate);/(b) QDateTimeEdit *edit=static_

32、cast(editor);/(c) edit-setDate(date);/设置控件的显示数据第28页/共42页第二十九页,共42页。setModelData()函数(hnsh)的具体代码如下:void DateDelegate:setModelData(QWidget *editor,QAbstractItemModel *model, const QModelIndex &index) const QDateTimeEdit *edit=static_cast(editor);/(a) QDate date = edit-date();/(b) model-setData(index,QV

33、ariant(date.toString(Qt:ISODate);/(c)updateEditorGeometry()函数(hnsh)的具体代码如下:void DateDelegate:updateEditorGeometry(QWidget *editor,const QStyle OptionViewItem &option,const QModelIndex &index) const editor-setGeometry(option.rect);第29页/共42页第三十页,共42页。(6)在“main.cpp”文件中添加如下代码(di m):#include datedelegate

34、.h在语句tableView.setModel(&model);后面添加如下代码(di m):DateDelegate dateDelegate;tableView.setItemDelegateForColumn(1,&dateDelegate);(7)此时运行程序,双击第1行第2列,将显示如图8.9所示的日历编辑框控件。第30页/共42页第三十一页,共42页。下面使用下拉列表框QComboBox控件实现对职业类型的输入(shr)编辑,使用自定义的Delegate实现。(1)ComboDelegate继承自QItemDelegate类。头文件“combodelegate.h”中的具体代码如下

35、:#include class ComboDelegate : public QItemDelegate Q_OBJECTpublic: ComboDelegate(QObject *parent = 0); QWidget *createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex&index) const; void setEditorData(QWidget *editor, const QModelIndex &index) const; void setModelData(Q

36、Widget *editor, QAbstractItemModel *model, const QModelIndex &index) const; void updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const;第31页/共42页第三十二页,共42页。(2)源文件“combodelegate.cpp”中的具体代码(di m)如下:#include combodelegate.h#include ComboDelegate:ComboD

37、elegate(QObject *parent) : QItemDelegate(parent)第32页/共42页第三十三页,共42页。createEditor()函数中创建了一个QComboBox控件,并插入可显示的条目,安装(nzhung)事件过滤器。具体代码如下:QWidget *ComboDelegate:createEditor(QWidget *parent,const QStyleOption ViewItem &/*option*/,const QModelIndex &/*index*/) const QComboBox *editor = new QComboBox(par

38、ent); editor-addItem(工人); editor-addItem(农民); editor-addItem(医生); editor-addItem(律师); editor-addItem(军人); editor-installEventFilter(const_cast(this); return editor;第33页/共42页第三十四页,共42页。setEditorData()函数中更新了Delegate控件中的数据显示,具体代码(di m)如下:void ComboDelegate:setEditorData(QWidget *editor,const QModelInde

39、x &index) const QString str =index.model()-data(index).toString(); QComboBox *box = static_cast(editor); int i=box-findText(str); box-setCurrentIndex(i);setModelData()函数中更新了Model中的数据,具体代码(di m)如下:void ComboDelegate:setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) co

40、nst QComboBox *box = static_cast(editor); QString str = box-currentText(); model-setData(index,str);第34页/共42页第三十五页,共42页。updateEditorGeometry()函数的具体代码如下(rxi):void ComboDelegate:updateEditorGeometry(QWidget *editor,const QStyleOptionViewItem &option, const QModelIndex &/*index*/) const editor-setGeome

41、try(option.rect);在“main.cpp”文件中添加以下内容:#include combodelegate.h在语句tableView.setModel(&model)的后面添加以下代码:ComboDelegate comboDelegate;tableView.setItemDelegateForColumn(2,&comboDelegate);第35页/共42页第三十六页,共42页。此时运行(ynxng)程序,双击第1行第3列,显示如图8.10所示的下拉列表。第36页/共42页第三十七页,共42页。下面使用QSpinBox控件实现对收入的输入编辑,调用自定义的Delegate

42、来实现。SpinDelegate类的实现与ComboDelegate类的实现类似(li s),此处不再详细讲解。(1)头文件“spindelegate.h”中的具体代码如下:#include class SpinDelegate : public QItemDelegate Q_OBJECTpublic: SpinDelegate(QObject *parent = 0); QWidget *createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const; voi

43、d setEditorData(QWidget *editor, const QModelIndex &index) const; void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const; void updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const;第37页/共42页第三十八页,共42页。(2)源文件“s

44、pindelegate.cpp”中的具体代码如下(rxi):#include spindelegate.h#include SpinDelegate:SpinDelegate(QObject *parent): QItemDelegate(parent)createEditor()函数的具体实现代码如下(rxi):QWidget *SpinDelegate:createEditor(QWidget *parent,const QStyleOption ViewItem &/*option*/,const QModelIndex &/*index*/) const QSpinBox *edito

45、r = new QSpinBox(parent); editor-setRange(0,10000); editor-installEventFilter(const_cast(this); return editor;第38页/共42页第三十九页,共42页。setEditorData()函数的具体实现(shxin)代码如下:void SpinDelegate:setEditorData(QWidget *editor,const QModelIndex &index) const int value =index.model()-data(index).toInt(); QSpinBox *

46、box = static_cast(editor); box-setValue(value);setModelData()函数的具体实现(shxin)代码如下:void SpinDelegate:setModelData(QWidget *editor, QAbstractItemModel *model,const QModelIndex &index) const QSpinBox *box = static_cast(editor); int value = box-value(); model-setData(index,value);第39页/共42页第四十页,共42页。update

47、EditorGeometry()函数的具体(jt)实现代码如下:void SpinDelegate:updateEditorGeometry(QWidget *editor,const QStyleOptionViewItem &option, const QModelIndex &/*index*/) const editor-setGeometry(option.rect);第40页/共42页第四十一页,共42页。(3)在“main.cpp”文件(wnjin)中添加代码如下:#include spindelegate.h在语句tableView.setModel(&model)的后面添加内容如下:SpinDelegate spinDelegate;tableView.setItemDelegateForColumn(3,&spinDelegate); (4)此时运行程序,双击第1行第4列后的效果如图8.11所示。第41页/共42页第四十二页,共42页。

展开阅读全文
温馨提示:
1: 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
2: 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
3.本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
5. 装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
关于我们 - 网站声明 - 网站地图 - 资源地图 - 友情链接 - 网站客服 - 联系我们

copyright@ 2023-2025  zhuangpeitu.com 装配图网版权所有   联系电话:18123376007

备案号:ICP2024067431-1 川公网安备51140202000466号


本站为文档C2C交易模式,即用户上传的文档直接被用户下载,本站只是中间服务平台,本站所有文档下载所得的收益归上传人(含作者)所有。装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。若文档所含内容侵犯了您的版权或隐私,请立即通知装配图网,我们立即给予删除!