QT 模型/视图 编程 模型篇

模型类

在研究如何处理选择之前,您可能会发现研究模型/视图框架中使用的概念是很有用的。

基本概念

在模型/视图体系结构中,模型提供了视图和委托用于访问数据的标准接口。在Qt中,标准接口由QAbstractItemModel类定义。无论数据项如何存储在任何底层数据结构中,QAbstractItemModel的所有子类都将数据表示为包含项表的层次结构。视图使用这个约定来访问模型中的数据项,但是它们不受限于向用户显示这些信息的方式。

  模型还通过信号和插槽机制通知关于数据更改的任何附加视图。

  本节描述一些基本概念,这些概念是其他组件通过模型类访问数据项的方式的核心。后面几节将讨论更高级的概念。

模型索引

  为了确保数据的表示形式与访问方式分离,引入了模型索引的概念。通过模型可以获得的每一条信息都由模型索引表示。视图和委托使用这些索引请求要显示的数据项。

  因此,只有模型需要知道如何获取数据,并且模型管理的数据类型可以被相当普遍地定义。模型索引包含一个指向创建它们的模型的指针,这可以防止在处理多个模型时产生混淆。

  模型索引提供对信息片段的临时引用,并可用于通过模型检索或修改数据。由于模型可能会不时地重新组织它们的内部结构,所以模型索引可能会变得无效,并且不应该被存储。如果需要对一段信息的长期引用,则必须创建持久的模型索引。这提供了对模型保持最新的信息的引用。临时模型索引由QModelIndex类提供,持久模型索引由QPersistentModelIndex类提供。

  要获得与数据项对应的模型索引,必须为模型指定三个属性:行号、列号和父项的模型索引。下面几节将详细描述和解释这些属性。

行和列

  在最基本的形式中,可以将模型作为一个简单的表来访问,其中的项是根据行号和列号来定位的。这并不意味着底层数据存储在数组结构中;使用行号和列号只是允许组件彼此通信的一种约定。我们可以通过向模型指定其行号和列号来检索关于任何给定项的信息,并且我们收到一个表示该项的索引:

   为列表和表等简单的单级数据结构提供接口的模型不需要提供任何其他信息,但是,正如上面的代码所示,在获得模型索引时,我们需要提供更多的信息。

行和列

  该图显示了基本表模型的表示形式,其中每个项由一对行号和列号定位。我们通过向模型传递相关的行号和列号来获得引用数据项的模型索引。

   通过将QModelIndex()指定为它们的父项目,可以始终引用模型中的顶级项目。下一节将对此进行讨论。

父Item

  当在表或列表视图中使用数据时,模型提供的项数据的类表接口是理想的;行号和列号系统精确地映射到视图显示项目的方式。然而,像树视图这样的结构需要模型向其中的项公开更灵活的接口。因此,每个项也可以是另一个项表的父表,这与树视图中的顶级项可以包含另一个项列表的方式非常相似。

  在为模型项请求索引时,我们必须提供关于该项的父项的一些信息。在模型之外,引用一个项目的唯一方法是通过模型索引,因此必须给出父模型索引:

父行、行和列

该图显示了树模型的表示,其中每个项由父项、行号和列号引用。

项目“A”和“C”在模型中表示为顶级同级:

 项目A有多个子元素。项目“B”的模型索引如下代码所示:

 项角色

  模型中的项可以为其他组件执行各种角色,从而允许为不同的情况提供不同类型的数据。例如,Qt::DisplayRole用于访问可以在视图中显示为文本的字符串。通常,项目包含许多不同角色的数据,标准角色由Qt::ItemDataRole定义。

  我们可以通过向模型传递与项目对应的模型索引来请求项目的数据,并通过指定一个角色来获得我们想要的数据类型:

 

  项角色

  角色向模型指示引用的数据类型。视图可以以不同的方式显示角色,因此为每个角色提供适当的信息非常重要。

创建新模型一节更详细地介绍了角色的一些特定用法。

  项数据的最常见用法由Qt::ItemDataRole中定义的标准角色涵盖。通过为每个角色提供适当的项数据,模型可以向视图和委托提供关于应该如何向用户显示项的提示。不同类型的视图可以根据需要自由地解释或忽略这些信息。还可以为特定于应用程序的目的定义其他角色。

概述

  模型索引以一种独立于任何底层数据结构的方式,提供关于模型提供的项的位置的视图和委托信息。

  项目通过它们的行号和列号以及它们的父项目的模型索引来引用。

  模型索引是根据其他组件(如视图和委托)的请求由模型构建的。

  如果在使用index()请求索引时为父项目指定了有效的模型索引,那么返回的索引将引用模型中父项目下的一个项目。获得的索引引用该项的一个子元素。

  如果在使用index()请求索引时为父项目指定了无效的模型索引,则返回的索引引用模型中的顶级项目。

  角色区分与项关联的不同类型的数据。

使用模型索引

  为了演示如何使用模型索引从模型检索数据,我们设置了一个没有视图的QFileSystemModel,并在小部件中显示文件和目录的名称。虽然这并没有展示使用模型的正常方式,但是它演示了模型在处理模型索引时使用的约定。

  我们按照以下方式构建一个文件系统模型:

  在本例中,我们设置了一个默认的QFileSystemModel,使用该模型提供的index()的特定实现获得父索引,并使用rowCount()函数计算模型中的行数。

  为简单起见,我们只对模型第一列中的项目感兴趣。我们依次检查每一行,获得每一行中第一项的模型索引,并读取为该项目存储在模型中的数据。

   为了获得一个模型索引,我们指定行号、列号(第一列为0),以及我们想要的所有项目的父类的适当的模型索引。使用模型的data()函数检索每个项目中存储的文本。我们指定模型索引和DisplayRole来以字符串的形式获取项目的数据。

上面的例子演示了从模型中检索数据的基本原则:

  可以使用rowCount()和columnCount()找到模型的维数。这些函数通常需要指定父模型索引。

  模型索引用于访问模型中的项。需要行、列和父模型索引来指定项。

  要访问模型中的顶级项目,可以使用QModelIndex()将空模型索引指定为父索引。

  项包含不同角色的数据。要获取特定角色的数据,必须同时向模型提供模型索引和角色。

进一步阅读

  可以通过实现QAbstractItemModel提供的标准接口来创建新模型。在创建新模型一节中,我们通过创建一个用于保存字符串列表的方便的现成模型来演示这一点。

猜你喜欢

转载自www.cnblogs.com/helloc14/p/12383472.html