File indexing completed on 2024-05-12 16:39:36

0001 /* This file is part of the KDE project
0002    Copyright (C) 2005-2012 Jarosław Staniek <staniek@kde.org>
0003 
0004    This program is free software; you can redistribute it and/or
0005    modify it under the terms of the GNU Library General Public
0006    License as published by the Free Software Foundation; either
0007    version 2 of the License, or (at your option) any later version.
0008 
0009    This program is distributed in the hope that it will be useful,
0010    but WITHOUT ANY WARRANTY; without even the implied warranty of
0011    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
0012    Library General Public License for more details.
0013 
0014    You should have received a copy of the GNU Library General Public License
0015    along with this program; see the file COPYING.  If not, write to
0016    the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
0017  * Boston, MA 02110-1301, USA.
0018 */
0019 
0020 #ifndef KEXIDATAITEMINTERFACE_H
0021 #define KEXIDATAITEMINTERFACE_H
0022 
0023 #include <QVariant>
0024 #include <QWidget>
0025 
0026 #include "kexicore_export.h"
0027 
0028 class KexiDataItemInterface;
0029 class KDbConnection;
0030 class KDbField;
0031 class KDbQueryColumnInfo;
0032 
0033 //! An helper class used to react on KexiDataItemInterface objects' changes.
0034 class KEXICORE_EXPORT KexiDataItemChangesListener
0035 {
0036 public:
0037     KexiDataItemChangesListener();
0038     virtual ~KexiDataItemChangesListener();
0039 
0040     /*! Implement this to react for change of \a item.
0041      Called by KexiDataItemInterface::valueChanged() */
0042     virtual void valueChanged(KexiDataItemInterface* item) = 0;
0043 
0044     /*! Implement this to return information whether we're currently at new record or not.
0045      This can be used e.g. by data-aware widgets to determine if "(auto)"
0046      label should be displayed. */
0047     virtual bool cursorAtNewRecord() const = 0;
0048 
0049     /*! Implement this to react when length of data has been exceeded. */
0050     virtual void lengthExceeded(KexiDataItemInterface *item, bool lengthExceeded) = 0;
0051 
0052     /*! Implement this to react when "length of data has been exceeded" message need updating. */
0053     virtual void updateLengthExceededMessage(KexiDataItemInterface *item) = 0;
0054 };
0055 
0056 //! An interface for declaring widgets to be data-aware.
0057 class KEXICORE_EXPORT KexiDataItemInterface
0058 {
0059 public:
0060     KexiDataItemInterface();
0061     virtual ~KexiDataItemInterface();
0062 
0063     /*! Just initializes \a value, and calls setValueInternal(const QString& add, bool removeOld).
0064      If \a removeOld is true, current value is set up as \a add.
0065      If \a removeOld if false, current value is set up as \a value + \a add.
0066      \a value is stored as 'old value' -it'd be usable in the future
0067      (e.g. Combo Box editor can use old value if current value does not
0068      match any item on the list).
0069 
0070      \a visibleValue (if not NULL) is passed to provide visible value to display instead of \a value.
0071      This is currently used only in case of the combo box form widget, where displayed content
0072      (usually a text of image) differs from the value of the widget (a numeric index).
0073 
0074      This method is called by table view's and form's editors. */
0075     void setValue(const QVariant& value, const QVariant& add = QVariant(), bool removeOld = false,
0076                   const QVariant* visibleValue = 0);
0077 
0078     //! \return field information for this item
0079     virtual KDbField *field() = 0;
0080 
0081     //! \return column information for this item
0082     virtual KDbQueryColumnInfo* columnInfo() = 0;
0083 
0084     //! Used internally to set column information.
0085     virtual void setColumnInfo(KDbConnection *conn, KDbQueryColumnInfo* cinfo) = 0;
0086 
0087     //! Sets listener. No need to reimplement this.
0088     virtual void installListener(KexiDataItemChangesListener* listener);
0089 
0090     //! \return value currently represented by this item.
0091     virtual QVariant value() = 0;
0092 
0093     //! \return true if editor's value is valid for a given type
0094     //! Used for checking if an entered value is valid,
0095     //! E.g. a part of time value can be entered: "12:8" and this is invalid, not only null.
0096     //! Null time or date is valid in Kexi, so it is not enough to test value().isValid().
0097     //! Default implementation just returns true.
0098     virtual bool valueIsValid();
0099 
0100     //! \return true if editor's value is null (not empty)
0101     //! Used for checking if a given constraint within table or form is met.
0102     virtual bool valueIsNull() = 0;
0103 
0104     //! \return true if editor's value is empty (not necessary null).
0105     //! Only few data types can accept "EMPTY" property
0106     //! (use KDbField::hasEmptyProperty() to check this).
0107     //! Used for checking if a given constraint within table of form is met.
0108     virtual bool valueIsEmpty() = 0;
0109 
0110     //! \return value that should be displayed for this item.
0111     //! Only used for items like combo box, where real value is an integer while
0112     //! displayed value is usually a text. For other item types this method should be empty.
0113     virtual QVariant visibleValue();
0114 
0115     /*! \return 'readOnly' flag for this item. The flag is usually taken from
0116      the item's widget, e.g. QLineEdit::isReadOnly().
0117      By default, always returns false. */
0118     virtual bool isReadOnly() const;
0119 
0120     /*! \return the view widget of this item, e.g. line edit widget. */
0121     virtual QWidget* widget() = 0;
0122 
0123     /*! Hides item's widget, if available. */
0124     virtual void hideWidget();
0125 
0126     /*! Shows item's widget, if available. */
0127     virtual void showWidget();
0128 
0129     //! \return true if editor's value is changed (compared to original value)
0130     virtual bool valueChanged();
0131 
0132     /*! \return true if the item widget's cursor (whatever that means, eg. line edit cursor)
0133      is at the beginning of editor's contents. This can inform table/form view that
0134      after pressing "left arrow" key should stop editing and move to a field on the left hand. */
0135     virtual bool cursorAtStart() = 0;
0136 
0137     /*! \return true if the item widget's cursor (whatever that means, eg. line edit cursor)
0138      is at the end of editor's contents. This can inform table/form view that
0139      after pressing "right arrow" key should stop editing and move to a field on the right hand. */
0140     virtual bool cursorAtEnd() = 0;
0141 
0142     /*! Moves cursor after the last character (or element).
0143      For implementation in items supporting text cursor's movement; by default does nothing. */
0144     virtual void moveCursorToEnd() {}
0145 
0146     /*! Moves cursor before the first character (or element).
0147      For implementation in items supporting text cursor's movement; by default does nothing. */
0148     virtual void moveCursorToStart() {}
0149 
0150     /*! Selects all characters (or elements) of the item.
0151      For implementation in items supporting text or elements; by default does nothing. */
0152     virtual void selectAll() {}
0153 
0154     //! clears item's data, so the data will contain NULL data
0155     virtual void clear() = 0;
0156 
0157     /*! \return true if this editor offers a widget (e.g. line edit) that we can move focus to.
0158      Editor for boolean values has this set to false (see KexiBoolTableEdit).
0159      This is true by default. You can override this flag by changing
0160      hasFocusableWidget in your subclass' constructor. */
0161     bool hasFocusableWidget() const;
0162 
0163     void setHasFocusableWidget(bool set) const;
0164 
0165     /*! Displays additional elements that are needed for indicating that the current cell
0166      is selected. For example, combobox editor (KexiComboBoxTableEdit) moves and shows
0167      dropdown button. \a r is the rectangle for the cell.
0168      If \a readOnly is true, additional elements should be visually disabled,
0169      e.g. dropdown button of the combobox editor should be disabled.
0170      For reimplementation. By default does nothing. */
0171     virtual void showFocus(const QRect& r, bool readOnly);
0172 
0173     /*! Hides additional elements that are needed for indicating that the current cell
0174      is selected.
0175      For reimplementation. By default does nothing. */
0176     virtual void hideFocus();
0177 
0178     /*! Allows to define reaction for clicking on cell's contents.
0179      Currently it's used for editor of type boolean, where we want to toggle true/false
0180      on single mouse click. \sa hasFocusableWidget(), KexiBoolTableEdit.
0181      Default implementation does nothing. */
0182     virtual void clickedOnContents();
0183 
0184     /*! \return true if editing should be accepted immediately after
0185      deleting contents for the cell (usually using Delete key).
0186      This flag is false by default, and is true e.g. for date, time and datetime types. */
0187     bool acceptEditorAfterDeleteContents() const;
0188 
0189     void setAcceptEditorAfterDeleteContents(bool set) const;
0190 
0191     virtual void setFocus();
0192 
0193     bool cursorAtNewRecord();
0194 
0195     /*! Sets a pointer to a Parent Data Item Interface. This pointer is 0 by default,
0196      but can be set by parent widget if this interface is a building block of a larger data widget.
0197      It is the case for KexiDBFieldEdit widget (see KexiDBFieldEdit::createEditor()). Use with care.
0198      signalValueChanged() method will check this pointer, and if it's not 0,
0199      parentDataItemInterface()->signalValueChanged() is called, so a changes can be signalled at higher level. */
0200     void setParentDataItemInterface(KexiDataItemInterface* parentDataItemInterface);
0201 
0202     /*! \return a pointer to a Parent Data Item Interface.
0203      @see setParentDataItemInterface() */
0204     KexiDataItemInterface* parentDataItemInterface() const;
0205 
0206     /*! Handles action having standard name \a actionName.
0207      Action could be: "edit_cut", "edit_paste", etc.
0208      For reimplementation. */
0209     virtual void handleAction(const QString& actionName);
0210 
0211     virtual bool isComboBox() const;
0212 
0213     virtual QWidget* internalEditor() const;
0214 
0215     //! Called (e.g. by KexiDataItemInterface) to change invalid value so it is valid.
0216     //! @return true on successful fixing
0217     //! Default implementation just returns true.
0218     virtual bool fixup();
0219 
0220     bool lengthExceededEmittedAtPreviousChange() const;
0221 
0222     void setLengthExceededEmittedAtPreviousChange(bool set);
0223 
0224 protected:
0225     /*! Initializes this editor with \a add value, which should be somewhat added to the current
0226      value (see originalValue()).
0227      If \a removeOld is true, a value should be set to \a add, otherwise
0228      -it should be set to current \a originalValue() + \a add, if possible.
0229      Implement this. */
0230     virtual void setValueInternal(const QVariant& add, bool removeOld) = 0;
0231 
0232     QVariant originalValue() const;
0233 
0234     /*! Initializes this editor with \a value visible value.
0235      This is currently used only in case of the combo box form widget, where displayed content
0236      (usually a text of image) differs from the value of the widget (a numeric index).
0237      For implementation in the combo box widget, by default does nothing. */
0238     virtual void setVisibleValueInternal(const QVariant& value);
0239 
0240     /*! Call this in your implementation when value changes,
0241      so installed listener can react on this change. If there is a parent data item defined
0242      (see setParentDataItemInterface()), parent's signalValueChanged() method will be called instead. */
0243     virtual void signalValueChanged();
0244 
0245     /*! Used to perform some actions before signalValueChanged() call.
0246      We need this because the interface is not QObject and thus has got no real signals.
0247      Used in KexiDBComboBox. */
0248     virtual void beforeSignalValueChanged() {}
0249 
0250     /*! Used to indicate that length of data has been exceeded. */
0251     virtual void signalLengthExceeded(bool lengthExceeded);
0252 
0253     /*! Used to request update for "length has been exceeded" message. */
0254     virtual void signalUpdateLengthExceededMessage();
0255 
0256     /*! Emits request for showing or hiding the "Length exceeded" warning, if needed. */
0257     void emitLengthExceededIfNeeded(bool lengthExceeded);
0258 
0259     KexiDataItemChangesListener* listener();
0260 
0261     void setFocusableWidget(bool set);
0262 
0263     class Private;
0264     Private* const d;
0265 };
0266 
0267 #endif