1 /*=========================================================================
2 
3   Library:   CTK
4 
5   Copyright (c) Kitware Inc.
6 
7   Licensed under the Apache License, Version 2.0 (the "License");
8   you may not use this file except in compliance with the License.
9   You may obtain a copy of the License at
10 
11       http://www.apache.org/licenses/LICENSE-2.0.txt
12 
13   Unless required by applicable law or agreed to in writing, software
14   distributed under the License is distributed on an "AS IS" BASIS,
15   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16   See the License for the specific language governing permissions and
17   limitations under the License.
18 
19 =========================================================================*/
20 
21 #ifndef __ctkMenuComboBox_h
22 #define __ctkMenuComboBox_h
23 
24 // Qt includes
25 #include <QMenu>
26 #include <QMetaType>
27 #include <QWidget>
28 class QComboBox;
29 class QToolButton;
30 
31 // CTK includes
32 #include "ctkWidgetsExport.h"
33 class ctkCompleter;
34 class ctkMenuComboBoxPrivate;
35 
36 /// \ingroup Widgets
37 /// QComboBox linked with a QMenu. See ctkMenuComboBox::setMenu()
38 /// ctkMenuComboBox can be editable, disable,
39 /// editable on focus or editable on double click.
40 ///   if it is editable :
41 /// the comboBox is always editable, you can filter the Menu or show it.
42 ///   if it is editable on focus - on double click:
43 /// the combobox become editable when it has the focus in.
44 /// So ctkMenuComboBox's purpose is to filter a menu, if you edit the current text
45 /// or show the menu, if you click on the arrow.
46 ///   if it is disabled :
47 /// the ctkMenuComboBox has the same behavior as a QPushButton. You can't filter the menu.
48 
49 /// By default ctkMenuComboBox is not editable with the search icon visible.
50 /// See ctkmenuComboBox::setEditableType() to change the default behavior.
51 /// and setIconSearchVisible() to show/hide the icon.
52 
53 class CTK_WIDGETS_EXPORT ctkMenuComboBox : public QWidget
54 {
55   Q_OBJECT
56   Q_ENUMS(EditableBehavior)
57   /// This property holds the text shown on the combobox when there is no
58   /// selected item.
59   /// Empty by default.
60   Q_PROPERTY(QString defaultText READ defaultText WRITE setDefaultText)
61   /// This property holds the icon shown on the combobox when the current item
62   /// (QAction) doesn't have any icon associated.
63   /// Empty by default
64   Q_PROPERTY(QIcon defaultIcon READ defaultIcon WRITE setDefaultIcon)
65   /// This property holds the edit behavior of the combobox, it defines what
66   /// action is needed to turn the combobox into a search mode where the user
67   /// can type the name of the item to select using the combobox line edit.
68   /// ctkMenuComboBox::NotEditable by default
69   /// \sa EditableType
70   Q_PROPERTY(EditableBehavior editBehavior READ editableBehavior WRITE setEditableBehavior)
71   /// This property controls whether the search tool button is visible or hidden.
72   /// True by default
73   Q_PROPERTY(bool searchIconVisible READ isSearchIconVisible WRITE setSearchIconVisible)
74   /// This property holds whether the search tool button displays an icon only,
75   /// text only, or text beside/below the icon.
76   /// The default is Qt::ToolButtonIconOnly.
77   /// \sa QToolButton::toolButtonStyle
78   Q_PROPERTY(Qt::ToolButtonStyle toolButtonStyle READ toolButtonStyle WRITE setToolButtonStyle)
79 public:
80   enum EditableBehavior{
81     NotEditable = 0,
82     Editable,
83     EditableOnFocus,
84     EditableOnPopup
85   };
86 
87   /// Superclass typedef
88   typedef QWidget Superclass;
89 
90   ///
91   ctkMenuComboBox(QWidget* parent = 0);
92   virtual ~ctkMenuComboBox();
93 
94   /// Add a menu to the QcomboBox and set a QCompleter
95   void setMenu(QMenu* menu);
96   QMenu* menu()const;
97 
98   void setDefaultText(const QString&);
99   QString defaultText()const;
100 
101   void setDefaultIcon(const QIcon&);
102   QIcon defaultIcon()const;
103 
104   void setEditableBehavior(EditableBehavior editBehavior);
105   EditableBehavior editableBehavior()const;
106 
107   void setSearchIconVisible(bool state);
108   bool isSearchIconVisible() const;
109 
110   Qt::ToolButtonStyle toolButtonStyle() const;
111 
112   /// Set the minimum width of the combobox.
113   /// \sa QComboBox::setMinimumContentsLength()
114   void setMinimumContentsLength(int characters);
115 
116   /// Return the internal combo box
117   QComboBox* menuComboBoxInternal() const;
118 
119   /// Return the internal tool button
120   QToolButton* toolButtonInternal() const;
121 
122   /// Return the internal completer
123   ctkCompleter* searchCompleter() const;
124 
125 protected:
126   virtual bool eventFilter(QObject* target, QEvent* event);
127 
128 public Q_SLOTS:
129   void clearActiveAction();
130   void setToolButtonStyle(Qt::ToolButtonStyle style);
131 
132 Q_SIGNALS:
133   void actionChanged(QAction* action);
134   void popupShown();
135 
136 protected Q_SLOTS:
137   /// Change the current text/icon on the QComboBox
138   /// And trigger the action.
139   /// action selected from the menu.
140   void onActionSelected(QAction* action);
141   /// action selected from the line edit or the completer.
142   void onEditingFinished();
143 
144 protected:
145   QScopedPointer<ctkMenuComboBoxPrivate> d_ptr;
146 
147 private:
148   Q_DECLARE_PRIVATE(ctkMenuComboBox);
149   Q_DISABLE_COPY(ctkMenuComboBox);
150 };
151 
152 Q_DECLARE_METATYPE(ctkMenuComboBox::EditableBehavior)
153 
154 #endif
155