Salome HOME
Join modifications from BR_Dev_For_4_0 tag V4_1_1.
[modules/gui.git] / src / Qtx / QtxPopupMenu.cxx
1 // Copyright (C) 2005  OPEN CASCADE, CEA/DEN, EDF R&D, PRINCIPIA R&D
2 // 
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either 
6 // version 2.1 of the License.
7 // 
8 // This library is distributed in the hope that it will be useful 
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of 
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
11 // Lesser General Public License for more details.
12 //
13 // You should have received a copy of the GNU Lesser General Public  
14 // License along with this library; if not, write to the Free Software 
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19 #include "QtxPopupMenu.h"
20
21 #include <qpainter.h>
22
23 /*!
24     Class: QtxPopupMenu::TitleMenuItem [Internal]
25     Descr: Custom menu item for popup title.
26 */
27
28 class QtxPopupMenu::TitleMenuItem : public QCustomMenuItem
29 {
30 public:
31   TitleMenuItem( const QString&, const QIconSet&, const int );
32   virtual ~TitleMenuItem();
33
34   virtual bool  fullSpan() const;
35   virtual bool  isSeparator() const;
36   virtual void  setFont( const QFont& );
37
38   virtual void  paint( QPainter*, const QColorGroup&, bool, bool, int, int, int, int );
39   virtual QSize sizeHint();
40
41 private:
42   QString       myText;
43   QIconSet      myIcon;
44   QFont         myFont;
45   int           myAlign;
46 };
47
48 /*!
49   Constructor
50 */
51 QtxPopupMenu::TitleMenuItem::TitleMenuItem( const QString& txt, const QIconSet& ico, const int align )
52 : QCustomMenuItem(),
53 myText( txt ),
54 myIcon( ico ),
55 myAlign( align )
56 {
57 }
58
59 /*!
60   Destructor
61 */
62 QtxPopupMenu::TitleMenuItem::~TitleMenuItem()
63 {
64 }
65
66 /*!
67   \return  TRUE if this item wants to span the entire popup menu width  
68 */
69 bool QtxPopupMenu::TitleMenuItem::fullSpan() const
70 {
71   return true;
72 }
73
74 /*!
75   \return TRUE if this item is just a separator
76 */
77 bool QtxPopupMenu::TitleMenuItem::isSeparator() const
78 {
79   return false;
80 }
81
82 /*!
83   Changes font of item
84   \param font - new font
85 */
86 void QtxPopupMenu::TitleMenuItem::setFont( const QFont& font )
87 {
88   myFont = font;
89   myFont.setBold( true );
90 }
91
92 /*!
93   Draws item
94 */
95 void QtxPopupMenu::TitleMenuItem::paint( QPainter* p, const QColorGroup& cg,
96                                          bool act, bool enabled, int x, int y, int w, int h )
97 {
98   QFont f = p->font();
99   p->setFont( myFont );
100
101   p->fillRect( x, y, w, h, cg.brush( QColorGroup::Dark ) );
102
103   p->setPen( cg.shadow() );
104   p->drawRect( x, y, w, h );
105
106   int m = 3;
107   int s = 3;
108   int iw = p->fontMetrics().width( myText ) + ( myIcon.isNull() ? 0 : myIcon.pixmap().width() + s );
109   int ih = QMAX( ( myIcon.isNull() ? 0 : myIcon.pixmap().height() ), p->fontMetrics().height() );
110
111   int ix = x;
112   int iy = y + m;
113
114   if ( myAlign & AlignLeft )
115     ix = x;
116   else if ( myAlign & AlignRight )
117     ix = x + ( w - iw );
118   else if ( myAlign & AlignHCenter )
119     ix = x + ( w - iw ) / 2;
120
121   if ( myAlign & AlignTop )
122     iy = y;
123   else if ( myAlign & AlignBottom )
124     iy = y + ( h - ih - m );
125   else if ( myAlign & AlignVCenter )
126     iy = y + ( h - ih ) / 2;
127
128   if ( !myIcon.isNull() )
129   {
130     p->drawPixmap( ix, iy + ( ih - myIcon.pixmap().height() ) / 2, myIcon.pixmap() );
131     ix += myIcon.pixmap().width() + s;
132   }
133
134   p->setPen( cg.brightText() );
135   p->drawText( ix, iy + ( ih - p->fontMetrics().height() ) / 2 +
136                p->fontMetrics().ascent(), myText, 0, -1 );
137
138   p->setFont( f );
139 }
140
141 /*!
142   \return the recommended size for item
143 */
144 QSize QtxPopupMenu::TitleMenuItem::sizeHint()
145 {
146   QFontMetrics fM( myFont );
147
148   int m = 3;
149   int s = 3;
150   int w = fM.width( myText ) + ( myIcon.isNull() ? 0 : myIcon.pixmap().width() + s );
151   int h = QMAX( ( myIcon.isNull() ? 0 : myIcon.pixmap().height() ), fM.height() ) + 2 * m;
152
153   return QSize( w, h );
154 }
155
156 /*!
157   Constructor
158 */
159 QtxPopupMenu::QtxPopupMenu( QWidget* parent, const char* name )
160 : QPopupMenu( parent, name ),
161 myId( -1 ),
162 myPolicy( TitleAuto ),
163 myAlign( AlignCenter )
164 {
165 }
166
167 /*!
168   Destructor
169 */
170 QtxPopupMenu::~QtxPopupMenu()
171 {
172 }
173
174 /*!
175   \return popup menu title
176 */
177 QString QtxPopupMenu::titleText() const
178 {
179   return myText;
180 }
181
182 /*!
183   \return popup menu icon
184 */
185 QIconSet QtxPopupMenu::titleIcon() const
186 {
187   return myIcon;
188 }
189
190 /*!
191   \return popup menu title policy
192 */
193 int QtxPopupMenu::titlePolicy() const
194 {
195   return myPolicy;
196 }
197
198 /*!
199   \return popup menu title alignment
200 */
201 int QtxPopupMenu::titleAlignment() const
202 {
203   return myAlign;
204 }
205
206 /*!
207   Changes title text
208   \param txt - new text
209 */
210 void QtxPopupMenu::setTitleText( const QString& txt )
211 {
212   if ( myText == txt )
213     return;
214
215   myText = txt;
216
217   updateTitle();
218 }
219
220 /*!
221   Changes title icon
222   \param icon - new icon
223 */
224 void QtxPopupMenu::setTitleIcon( const QIconSet& ico )
225 {
226   myIcon = ico;
227
228   updateTitle();
229 }
230
231 /*!
232   Changes title policy
233   \param p - new policy
234 */
235 void QtxPopupMenu::setTitlePolicy( const int p )
236 {
237   if ( myPolicy == p )
238     return;
239
240   myPolicy = p;
241
242   updateTitle();
243 }
244
245 /*!
246   Changes title alignment
247   \param a - new alignment
248 */
249 void QtxPopupMenu::setTitleAlignment( const int a )
250 {
251   if ( myAlign == a )
252     return;
253
254   myAlign = a;
255
256   updateTitle();
257 }
258
259 /*!
260   Shows menu
261 */
262 void QtxPopupMenu::show()
263 {
264   insertTitle();
265
266   QPopupMenu::show();
267 }
268
269 /*!
270   Hides menu
271 */
272 void QtxPopupMenu::hide()
273 {
274   QPopupMenu::hide();
275
276   removeTitle();
277 }
278
279 /*!
280   Creates title item
281   \param txt - item text
282   \param icon - item icon
283   \param align - item alignment
284 */
285 QtxPopupMenu::TitleMenuItem* QtxPopupMenu::createTitleItem( const QString& txt, const QIconSet& ico,
286                                                             const int align ) const
287 {
288   return new TitleMenuItem( txt, ico, align );
289 }
290
291 /*!
292   Inserts title item to popup menu
293 */
294 void QtxPopupMenu::insertTitle()
295 {
296   if ( myId != -1 || titlePolicy() == TitleOff ||
297        ( titlePolicy() == TitleAuto && titleText().stripWhiteSpace().isEmpty() ) )
298     return;
299
300   TitleMenuItem* item = createTitleItem( titleText(), titleIcon(), titleAlignment() );
301
302   myId = insertItem( item, -1, 0 );
303   setItemEnabled( myId, false );
304 }
305
306 /*!
307   Removes title item from popup menu
308 */
309 void QtxPopupMenu::removeTitle()
310 {
311   if ( myId == -1 )
312     return;
313
314   removeItem( myId );
315   myId = -1;
316 }
317
318 /*!
319   Updates title item
320 */
321 void QtxPopupMenu::updateTitle()
322 {
323   if ( myId != -1 )
324   {
325     removeTitle();
326     insertTitle();
327   }
328 }