1
/* This file is part of the KDE project
2
Copyright (C) 2004-2012 JarosÅaw Staniek <staniek@kde.org>
4
This library is free software; you can redistribute it and/or
5
modify it under the terms of the GNU Library General Public
6
License as published by the Free Software Foundation; either
7
version 2 of the License, or (at your option) any later version.
9
This library is distributed in the hope that it will be useful,
10
but WITHOUT ANY WARRANTY; without even the implied warranty of
11
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12
Library General Public License for more details.
14
You should have received a copy of the GNU Library General Public License
15
along with this library; see the file COPYING.LIB. If not, write to
16
the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17
* Boston, MA 02110-1301, USA.
25
#include <QCloseEvent>
27
#include "kexiactionproxy.h"
33
//! Base class for single view embeddable in KexiWindow.
34
/*! This class automatically works as a proxy for shared (application-wide) actions.
35
KexiView has 'dirty' flag to indicate that view's data has changed.
36
This flag's state is reused by KexiWindow object that contain the view.
37
KexiView objects can be also nested, using addChildView(): any actions and 'dirty' flag
38
are transmited to parent view in this case.
40
KexiView objects are usually allocated within KexiWindow objects by implementing
41
KexiPart::createView() method. See query or table part code for examples.
43
KexiView object can be also allocated without attaching it KexiWindow,
44
especially within dock window. see KexiMainWindow::initNavigator() to see example
45
how KexiBrowser does this.
47
@todo add some protected access methods
49
class KEXICORE_EXPORT KexiView : public QWidget, public KexiActionProxy
54
explicit KexiView(QWidget *parent);
57
//! \return parent KexiWindow that containing this view,
58
//! or 0 if no window contain this view
59
KexiWindow* window() const;
61
/*! Added for convenience.
62
\return KexiPart object that was used to create this view (with a window)
63
or 0 if this view is not created using KexiPart. \sa window() */
64
KexiPart::Part* part() const;
66
/*! \return preferred size hint, that can be used to resize the view.
67
It is computed using maximum of (a) \a otherSize and (b) current dock area's size,
68
so the view won't exceed this maximum size. The method is used e.g. in KexiWindow::sizeHint().
69
If you reimplement this method, do not forget to return value of
70
yoursize.boundedTo( KexiView::preferredSizeHint(otherSize) ). */
71
virtual QSize preferredSizeHint(const QSize& otherSize);
73
void addChildView(KexiView* childView);
75
void removeView(Kexi::ViewMode mode);
77
/*! True if contents (data) of the view is dirty and need to be saved
78
This may or not be used, depending if changes in the window
79
are saved immediately (e.g. like in datatableview) or saved by hand (by user)
80
(e.g. like in alter-table window).
81
"Dirty" flag is reused by KexiWindow::dirty().
82
Default implementation just uses internal dirty flag, that is false by default.
83
Reimplement this if you e.g. want reuse other "dirty"
84
flag from internal structures that may be changed. */
85
virtual bool isDirty() const;
87
/*! @return true if data editing is in progress. This is useful to indicate
88
* to the master window that the view should save the before switching to
89
* other view. This information is used in KexiWindow::switchToViewMode().
90
* Implement this in view that supports data editing, typically
91
* of mode Kexi::DataViewMode. If you do this, also implement
92
* saveDataChanges() and cancelDataChanges().
93
* Default implementation just returns false. */
94
virtual bool isDataEditingInProgress() const;
96
/*! Saves changes that are currently made to the associated data.
97
* Implement this in view that supports data editing, typically
98
* of mode Kexi::DataViewMode. If you do this, also implement
99
* isDataEditingInProgress() and cancelDataChanges().
100
* This method is used by KexiWindow::switchToViewMode().
101
* Default implementation just returns true.
102
* @return true on success, false on failure and cancelled if the operation
103
* has been cancelled. */
104
virtual tristate saveDataChanges();
106
/*! Cancel changes that are currently made to the associated data.
107
* Implement this in view that supports data editing, typically
108
* of mode Kexi::DataViewMode. If you do this, also implement
109
* isDataEditingInProgress() and saveDataChanges().
110
* This method is used by KexiWindow::switchToViewMode().
111
* Default implementation just returns true.
112
* @return true on success, false on failure and cancelled if the operation
113
* has been cancelled. */
114
virtual tristate cancelDataChanges();
116
/*! \return the view mode for this view. */
117
Kexi::ViewMode viewMode() const;
119
/*! Reimplemented from KexiActionProxy.
120
\return shared action with name \a action_name for this view.
121
If there's no such action declared in Kexi Part (part()),
122
global shared action is returned (if exists). */
123
virtual QAction* sharedAction(const QString& action_name);
125
/*! Enables or disables shared action declared in Kexi Part (part()).
126
If there's no such action, global shared action is enabled or disabled (if exists). */
127
virtual void setAvailable(const QString& action_name, bool set);
129
enum StoreNewDataOption {
130
OverwriteExistingData = 1 //!< Overwerite existing object in storeNewData()
132
Q_DECLARE_FLAGS(StoreNewDataOptions, StoreNewDataOption)
134
QString defaultIconName() const;
136
void setDefaultIconName(const QString& iconName);
138
/*! For KexiQueryView */
139
virtual QList<QVariant> currentParameters() const;
142
virtual void setFocus();
144
/*! Call this in your view's implementation whenever current property set
145
(returned by propertySet()) is switched to other,
146
so property editor contents need to be completely replaced. */
147
virtual void propertySetSwitched();
149
/*! Saves settings for the view. Default implementation does nothing and returns true.
150
Implement this if there are settings to save. */
151
virtual bool saveSettings();
153
/*! Sets dirty flag on or off. It the flag changes,
154
dirty(bool) signal is emitted by the parent window (KexiWindow),
155
to inform the world about that. If this view has a parent view, setDirty()
156
is called also on parent view.
157
Always use this function to update 'dirty' flag information. */
158
void setDirty(bool set);
160
/*! Equal to setDirty(true). */
164
//! emitted when the view is about to close
165
void closing(bool *cancel);
170
virtual bool eventFilter(QObject *o, QEvent *e);
172
/*! called by KexiWindow::switchToViewMode() right before window is switched to new mode
173
By default does nothing. Reimplement this if you need to do something
174
before switching to this view.
175
\return true if you accept or false if a error occupied and view shouldn't change
176
If there is no error but switching should be just cancelled
177
(probably after showing some info messages), you need to return cancelled.
178
Set \a dontStore to true (it's false by default) if you want to avoid data storing
179
by storeData() or storeNewData(). */
180
virtual tristate beforeSwitchTo(Kexi::ViewMode mode, bool *dontStore);
182
/*! called by KexiWindow::switchToViewMode() right after window is switched to new mode
183
By default does nothing. Reimplement this if you need to do something
184
after switching to this view.
185
\return true if you accept or false if a error occupied and view shouldn't change
186
If there is no error but switching should be just cancelled
187
(probably after showing some info messages), you need to return cancelled. */
188
virtual tristate afterSwitchFrom(Kexi::ViewMode mode);
190
virtual void closeEvent(QCloseEvent * e);
192
/*! \return a property set for this view. For reimplementation. By default returns NULL. */
193
virtual KPropertySet *propertySet();
195
/*! Call this in your view's implementation whenever current property set
196
is changed that few properties are now visible and/or few other are invisible,
197
so property editor operating on this property set should be completely reloaded.
198
If \a preservePrevSelection is true and there was a property set
199
assigned before call, previously selected item will be preselected
200
in the editor (if found). */
201
void propertySetReloaded(bool preservePrevSelection = false,
202
const QByteArray& propertyToSelect = QByteArray());
204
/*! Tells this view to create and store data of the new object
205
pointed by \a object on the backend.
206
Called by KexiWindow::storeNewData() and KexiWindow::storeDataAs().
207
Default implementation:
208
- makes a deep copy of \a object
209
- stores object data \a object in 'kexi__objects' internal table
210
using KDbConnection::storeNewObjectData().
211
Reimplement this for your needs.
213
- deep copy of \a object should be made
214
- object data should be created at the backend
215
(by calling KexiView::storeNewData(const KDbObject&, KexiView::StoreNewDataOptions,bool*))
216
or using KDbConnection::storeNewObjectData() or more specialized method.
217
For example KexiTableDesignerView uses KDbConnection::createTable(KDbTableSchema) for this
218
(KDbTableSchema inherits KDbObject) to store more information than
219
just the object data. You should use such subclasses if needed.
221
Should return newly created object data object on success.
222
In this case, do not store schema object yourself (make a deep copy if needed). */
223
virtual KDbObject* storeNewData(const KDbObject& object,
224
KexiView::StoreNewDataOptions options,
227
/*! Tells this view to fully copy existing object's data pointed by \a object on the backend.
228
For example, for database tables it whould copy metadata, copy \a object, so the copy will
229
have different name, caption and description, and physically copy the table (possibly on
231
Called by KexiWindow::storeDataAs().
232
Default implementation:
233
- makes a deep copy of \a object
234
- stores object data \a object in 'kexi__objects' internal table
235
using KDbConnection::storeNewObjectData()
236
- makes a full copy of data and user data.
237
Reimplement this for your needs.
239
- deep copy of \a object should be made
240
- object data should be created at the backend
241
(by calling KexiView::copyData(const KDbObject&, KexiView::StoreNewDataOptions,bool*))
242
or using KDbConnection::storeNewObjectData() or more specialized method.
243
For example KexiTableDesignerView uses KDbConnection::createTable(KDbTableSchema) for this
244
(KDbTableSchema inherits KDbObject) to store more information than
245
just object data. Then it copies data table on the server side.
246
You should use such subclasses if needed.
248
Should return newly created object data object on success.
249
In this case, do not store schema object yourself (make deep copy if needed). */
250
virtual KDbObject* copyData(const KDbObject& object,
251
KexiView::StoreNewDataOptions options,
254
/*! Loads large string data \a dataString block (e.g. xml form's representation),
255
indexed with optional \a dataID, from the database backend.
256
If \a canBeEmpty is true and there is no data block for dataID, true is returned
257
and \a dataString is set to null string. The default is false.
258
\return true on success
259
\sa storeDataBlock(). */
260
bool loadDataBlock(QString *dataString, const QString& dataID = QString(),
261
bool canBeEmpty = false);
263
/*! Tells this view to store data changes on the backend.
264
Called by KexiWindow::storeData().
265
Default implementation:
266
- stores object data \a object in 'kexi__objects' internal table
267
using KDbConnection::storeObjectData().
268
If \a dontAsk is true, no question dialog will
269
be shown to the user. The default is false.
271
Reimplement this for your needs. Should return true on success, false on failure
272
and cancelled when the task should be cancelled.
273
\sa storeNewData() */
274
virtual tristate storeData(bool dontAsk = false);
276
/*! Stores (potentially large) string data \a dataString, block (e.g. xml form's representation),
277
at the database backend. Block will be stored in "kexi__objectdata" table pointed by
278
this object's id and an optional \a dataID identifier.
280
If window's id is not available (KexiWindow::id()),
281
then ID that was just created in storeNewData() is used
282
(see description of newlyAssignedID()).
283
If there is already such record in the table, it's simply overwritten.
284
\return true on success
286
bool storeDataBlock(const QString &dataString, const QString &dataID = QString());
288
/*! Removes (potentially large) string data (e.g. xml form's representation),
289
pointed by optional \a dataID, from the database backend.
290
\return true on success. Does not fail if the block doe not exists.
291
Note that if \a dataID is not specified, all data blocks for this view will be removed.
292
\sa storeDataBlock(). */
293
bool removeDataBlock(const QString& dataID = QString());
295
void setViewWidget(QWidget* w, bool focusProxy = false);
297
/*! Updates actions (e.g. availability). Reimplement it, if needed (you must
298
call superclass impelmentation at the end!).
299
This implementation does nothing for this view but calls updateActions()
300
for every child-view of this view.
301
called by KexiWindow on window's activation (\a activated is true)
303
virtual void updateActions(bool activated);
305
virtual void setFocusInternal() {
309
/*! Allows to react on parent window's detaching.
310
@todo it should be called by KexiWindow::youAreDetached().
311
Default implementation does nothing.
312
Implement it if you want to perform some appropriate actions. */
313
virtual void windowDetached() {}
315
/*! Allows to react on parent window's attaching.
316
@todo it should be called by KexiWindow::youAreAttached().
317
Default implementation does nothing.
318
Implement it if you want to perform some appropriate actions. */
319
virtual void windowAttached() {}
321
/*! Assigns a list of view-level actions. Used by KexiView ctor. */
322
void setViewActions(const QList<QAction*>& actions);
324
/*! Assigns a list of main-menu-level actions. Used by KexiView ctor. */
325
void setMainMenuActions(const QList<QAction*>& actions);
327
/*! @return a list of view-level actions. */
328
QList<QAction*> viewActions() const;
330
/*! @return view-level action for name @a name or 0 if there is no such action. */
331
QAction* viewAction(const char* name) const;
333
void initViewActions();
334
void initMainMenuActions();
336
void toggleViewModeButtonBack();
338
//! Sets properties in the Property Editor to be sorted if @a set is true.
339
void setSortedProperties(bool set);
342
void slotSwitchToViewModeInternal(Kexi::ViewMode mode);
343
void slotSwitchToDataViewModeInternal(bool);
344
void slotSwitchToDesignViewModeInternal(bool);
345
void slotSwitchToTextViewModeInternal(bool);
348
void createViewModeToggleButtons();
352
friend class KexiWindow;
355
Q_DECLARE_OPERATORS_FOR_FLAGS(KexiView::StoreNewDataOptions)