source: trunk/doc/src/examples/sqlwidgetmapper.qdoc@ 846

Last change on this file since 846 was 846, checked in by Dmitry A. Kuminov, 14 years ago

trunk: Merged in qt 4.7.2 sources from branches/vendor/nokia/qt.

File size: 8.1 KB
Line 
1/****************************************************************************
2**
3** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
4** All rights reserved.
5** Contact: Nokia Corporation (qt-info@nokia.com)
6**
7** This file is part of the documentation of the Qt Toolkit.
8**
9** $QT_BEGIN_LICENSE:FDL$
10** Commercial Usage
11** Licensees holding valid Qt Commercial licenses may use this file in
12** accordance with the Qt Commercial License Agreement provided with the
13** Software or, alternatively, in accordance with the terms contained in a
14** written agreement between you and Nokia.
15**
16** GNU Free Documentation License
17** Alternatively, this file may be used under the terms of the GNU Free
18** Documentation License version 1.3 as published by the Free Software
19** Foundation and appearing in the file included in the packaging of this
20** file.
21**
22** If you have questions regarding the use of this file, please contact
23** Nokia at qt-info@nokia.com.
24** $QT_END_LICENSE$
25**
26****************************************************************************/
27
28/*!
29 \example sql/sqlwidgetmapper
30 \title SQL Widget Mapper Example
31
32 The SQL Widget Mapper example shows how to use a map information from a
33 database to widgets on a form.
34
35 \image sql-widget-mapper.png
36
37 In the \l{Combo Widget Mapper Example}, we showed how to use a named
38 mapping between a widget mapper and a QComboBox widget with a special
39 purpose model to relate values in the model to a list of choices.
40
41 Again, we create a \c Window class with an almost identical user interface,
42 providing a combo box to allow their addresses to be classified as "Home",
43 "Work" or "Other". However, instead of using a separate model to hold these
44 address types, we use one database table to hold the example data and
45 another to hold the address types. In this way, we store all the
46 information in the same place.
47
48 \section1 Window Class Definition
49
50 The class provides a constructor, a slot to keep the buttons up to date,
51 and a private function to set up the model:
52
53 \snippet examples/sql/sqlwidgetmapper/window.h Window definition
54
55 In addition to the QDataWidgetMapper object and the controls used to make
56 up the user interface, we use a QStandardItemModel to hold our data and
57 a QStringListModel to hold information about the types of address that
58 can be applied to each person's data.
59
60 \section1 Window Class Implementation
61
62 The first act performed by the \c Window class constructor is to set up
63 the model used to hold the example data. Since this is a key part of the
64 example, we will look at this first.
65
66 The model is initialized in the window's \c{setupModel()} function. Here,
67 we create a SQLite database containing a "person" table with primary key,
68 name, address and type fields.
69
70 \snippet examples/sql/sqlwidgetmapper/window.cpp Set up the main table
71
72 On each row of the table, we insert default values for these fields,
73 including values for the address types that correspond to the address
74 types are stored in a separate table.
75
76 \image widgetmapper-sql-mapping-table.png
77
78 We create an "addresstype" table containing the identifiers used in the
79 "person" table and the corresponding strings:
80
81 \snippet examples/sql/sqlwidgetmapper/window.cpp Set up the address type table
82
83 The "typeid" field in the "person" table is related to the contents of
84 the "addresstype" table via a relation in a QSqlRelationalTableModel.
85 This kind of model performs all the necessary work to store the data in
86 a database and also allows any relations to be used as models in their
87 own right.
88
89 In this case, we have defined a relation for the "typeid" field in the
90 "person" table that relates it to the "id" field in the "addresstype"
91 table and which causes the contents of the "description" field to be
92 used wherever the "typeid" is presented to the user. (See the
93 QSqlRelationalTableModel::setRelation() documentation for details.)
94
95 \image widgetmapper-sql-mapping.png
96
97 The constructor of the \c Window class can be explained in three parts.
98 In the first part, we set up the model used to hold the data, then we set
99 up the widgets used for the user interface:
100
101 \snippet examples/sql/sqlwidgetmapper/window.cpp Set up widgets
102
103 We obtain a model for the combo box from the main model, based on the
104 relation we set up for the "typeid" field. The call to the combo box's
105 \l{QComboBox::}{setModelColumn()} selects the field in the field in the
106 model to display.
107
108 Note that this approach is similar to the one used in the
109 \l{Combo Widget Mapper Example} in that we set up a model for the
110 combo box. However, in this case, we obtain a model based on a relation
111 in the QSqlRelationalTableModel rather than create a separate one.
112
113 Next, we set up the widget mapper, relating each input widget to a field
114 in the model:
115
116 \snippet examples/sql/sqlwidgetmapper/window.cpp Set up the mapper
117
118 For the combo box, we already know the index of the field in the model
119 from the \c{setupModel()} function. We use a QSqlRelationalDelegate as
120 a proxy between the mapper and the input widgets to match up the "typeid"
121 values in the model with those in the combo box's model and populate the
122 combo box with descriptions rather than integer values.
123
124 As a result, the user is able to select an item from the combo box,
125 and the associated value is written back to the model.
126
127 The rest of the constructor is very similar to that of the
128 \l{Simple Widget Mapper Example}:
129
130 \snippet examples/sql/sqlwidgetmapper/window.cpp Set up connections and layouts
131
132 We show the implementation of the \c{updateButtons()} slot for
133 completeness:
134
135 \snippet examples/sql/sqlwidgetmapper/window.cpp Slot for updating the buttons
136
137 \omit
138 \section1 Delegate Class Definition and Implementation
139
140 The delegate we use to mediate interaction between the widget mapper and
141 the input widgets is a small QItemDelegate subclass:
142
143 \snippet examples/sql/sqlwidgetmapper/delegate.h Delegate class definition
144
145 This provides implementations of the two standard functions used to pass
146 data between editor widgets and the model (see the \l{Delegate Classes}
147 documentation for a more general description of these functions).
148
149 Since we only provide an empty implementation of the constructor, we
150 concentrate on the other two functions.
151
152 The \l{QItemDelegate::}{setEditorData()} implementation takes the data
153 referred to by the model index supplied and processes it according to
154 the presence of a \c currentIndex property in the editor widget:
155
156 \snippet examples/sql/sqlwidgetmapper/delegate.cpp setEditorData implementation
157
158 If, like QComboBox, the editor widget has this property, it is set using
159 the value from the model. Since we are passing around QVariant values,
160 the strings stored in the model are automatically converted to the integer
161 values needed for the \c currentIndex property.
162
163 As a result, instead of showing "0", "1" or "2" in the combo box, one of
164 its predefined set of items is shown. We call QItemDelegate::setEditorData()
165 for widgets without the \c currentIndex property.
166
167 The \l{QItemDelegate::}{setModelData()} implementation performs the reverse
168 process, taking the value stored in the widget's \c currentIndex property
169 and storing it back in the model:
170
171 \snippet examples/sql/sqlwidgetmapper/delegate.cpp setModelData implementation
172 \endomit
173
174 \section1 Summary and Further Reading
175
176 The use of a separate model for the combo box and a special delegate for the
177 widget mapper allows us to present a menu of choices to the user. Although
178 the choices are stored in the same database as the user's data, they are held
179 in a separate table. Using this approach, we can reconstructed complete records
180 at a later time while using database features appropriately.
181
182 If SQL models are not being used, it is still possible to use more than
183 one model to present choices to the user. This is covered by the
184 \l{Combo Widget Mapper Example}.
185*/
Note: See TracBrowser for help on using the repository browser.