QtitanDataGrid supports relations between two associated models. The mechanism is independent from such SQL models as QSqlRelationalTableModel and can be used for any models inherited from QAbstractItemModel. This mechanism is configured separately for each grid column.
The Relation mechanism supports two operating modes:
This operating mode allows you to use a foreign key to represent data from an external model in the same way as if they were inside the master model. For instance, the mode makes it possible to configure the grid in such a way that the data for the Qt::DisplayRole role will be taken from the master model connected to the grid controller, while the icon data (Qt::DecorationRole role) will be loaded from the external model. As a rule, the master model only contains the foreign key that points to the location of data for other roles in the external model.
The scheme below illustrates the mechanism structure:
The mechanism can be managed with the help of the Qtitan::ModelDataBinding object accessible from grid columns. You can enable the Relation mode using the setRelationMode() method and by passing the necessary mode as a parameter.
Qtitan::GridTableColumn* column = (Qtitan::GridTableColumn *)view->getColumnByModelColumnName("Country"); column->dataBinding()->setRelationMode(ModelDataBinding::Relation); column->dataBinding()->setRelationModel(countriesModel); column->dataBinding()->setForeignKey("id"); column->dataBinding()->setRoleMapping(Qt::DisplayRole, "Name"); column->dataBinding()->setRoleMapping(Qt::DecorationRole, "Flag");
The setRelationModel() function defines a relation with an external model. Calling setForeignKey("id") will define the "id" column of the external model as a storage of external keys. By default, Qt::DisplayRole is used as the role for obtaining values from the external model ("id" column). This value is used as the second paramter in the setForeignKey() function:
setForeignKey("id", Qt::UserRole)
The third paramter of the setForeignKey() function defines the value of the role that will be used for obtaining the value of the external key from the master model of the current row. Qt::EditRole is the default value.
setForeignKey("id", Qt::UserRole, Qt::DisplayRole)
The setRoleMapping(Qt::DisplayRole, "Name") method defines the rule for obtaining the Qt::DisplayRole role from the master model. To get the Qt::DisplayRole value of the master model, the grid will use the value from the "Name" column of the foreign model (foreignModel). By default, the Qt::DisplayRole role is used for obtaining this value from the external model. It can be redefined by passing it as the third parameter to the setRoleMapping() function. Example:
column->dataBinding()->setRoleMapping(Qt::DecorationRole, "Flag", Qt::DecorationRole);
Let's take a look at a Qt example.
QSqlRelationalTableModel* model = new QSqlRelationalTableModel; ....... model->setTable("employee"); model->setRelation(2, QSqlRelation("city", "id", "name")); model->setRelation(3, QSqlRelation("country", "id", "name")); QTableView *view = new QTableView; view->setModel(model);
Let's see how this Qt example should be adapted for working with QtitanDataGrid.
QSqlRelationalTableModel* model = new QSqlRelationalTableModel; model->setTable("employee"); QSqlQueryModel* city = new QSqlQueryModel; city->setTable("city"); QSqlQueryModel* country = new QSqlQueryModel; country->setTable("country"); Qtitan::GridTableView* view = qtitangrid->view<Qtitan::GridTableView>(); view->setModel(model); Qtitan::GridTableColumn* column = (Qtitan::GridTableColumn *)view->getColumnByModelColumn(2); column->dataBinding()->setRelationMode(ModelDataBinding::Relation); column->dataBinding()->setRelationModel(city); column->dataBinding()->setForeignKey("id"); column->dataBinding()->setRoleMapping(Qt::DisplayRole, "name"); column = (Qtitan::GridTableColumn *)view->getColumnByModelColumn(3); column->dataBinding()->setRelationMode(ModelDataBinding::Relation); column->dataBinding()->setRelationModel(country); column->dataBinding()->setForeignKey("id"); column->dataBinding()->setRoleMapping(Qt::DisplayRole, "name");
QtitanDataGrid has several editors supporting this mode.
This is a special mode that enables you to show additional tabular data in grid cells. Each grid cell is associated with an external data source represented by a model inherited from an abstract class. A model cell for which a table of details is generated must contain a foreign key besides a readable description. The value of the foreign key should be accessible through a configurable role. By default, Qt::EditRole is used. The external model should contain a column with foreign keys. The role for obtaining a key from the external model can be configured.
The rows of the table of details are the rows from the external model for which the values of keys from the keys column match the value of the foreign key from the cell of the master model.
Let's take a look at an example that demonstrates the process of configuring this mode:
QSqlTableModel* actorsModel = new QSqlTableModel; Qtitan::GridTableColumn* column = (Qtitan::GridTableColumn *)view->getColumnByModelColumnName("Cast"); column->dataBinding()->setRelationMode(ModelDataBinding::MasterDetailsRelation); column->dataBinding()->setRelationModel(actorsModel); column->dataBinding()->setForeignKey("film_id");
The setRelationMode() and setModel() methods set the master details mode and define an external data source represented by a Qt model. The setForeignKey() method sets the settings of the foreign key that will be represented by the "film_id" column and the Qt::DisplayRole role of the external model. The value of the foreign key for which a table of details should be generated can be obtained with the help of the Qt::EditRole role of the current cell. If you need to use another role, it can be set by passing it as the third parameter of the setForeignKey() function.
QtitanDataGrid comes with an editor (Qtitan::GridTableEditor) supporting this mode. To start using it, switch the column editor to Qtitan::GridTableEditor using the code below:
column = (Qtitan::GridTableColumn *)view->getColumnByModelColumnName("Cast"); column->setEditorType(Qtitan::TableEditorType);
The cell editor automatically detects the mode used and keeps working on its own.
Although both modes use the Foreign Key, they are fundamentally different in the following aspects:
See also Qtitan::ModelDataBinding.