Salome HOME
New item (FontItem), allowing to show information about font setting and to select...
[modules/gui.git] / src / Qtx / QtxGroupBox.cxx
1 // File:      QtxGroupBox.cxx
2 // Author:    Sergey TELKOV
3
4 #include "QtxGroupBox.h"
5
6 #include <qhbox.h>
7 #include <qlayout.h>
8 #include <qtoolbutton.h>
9 #include <qapplication.h>
10 #include <qobjectlist.h>
11
12 QtxGroupBox::QtxGroupBox( QWidget* parent, const char* name )
13 : QGroupBox( parent, name ),
14 myContainer( 0 )
15 {
16 }
17
18 QtxGroupBox::QtxGroupBox( const QString& title, QWidget* parent, const char* name )
19 : QGroupBox( title, parent, name ),
20 myContainer( 0 )
21 {
22   initialize();
23 }
24
25 QtxGroupBox::QtxGroupBox( int strips, Orientation o, QWidget* parent, const char* name )
26 : QGroupBox( strips, o, parent, name ),
27 myContainer( 0 )
28 {
29   initialize();
30 }
31
32 QtxGroupBox::QtxGroupBox( int strips, Orientation o, const QString& title,
33                                           QWidget* parent, const char* name )
34 : QGroupBox( strips, o, title, parent, name ),
35 myContainer( 0 )
36 {
37   initialize();
38 }
39
40 QtxGroupBox::~QtxGroupBox()
41 {
42   delete myContainer;
43 }
44
45 void QtxGroupBox::initialize()
46 {
47   myContainer = new QHBox( this, 0, WStyle_Customize | WStyle_NoBorderEx | WStyle_Tool );
48
49   updateTitle();
50 }
51
52 #if QT_VER < 3
53
54 int QtxGroupBox::insideMargin() const
55 {
56   int m = 0;
57   if ( layout() )
58     m = layout()->margin();
59   return m;
60 }
61
62 int QtxGroupBox::insideSpacing() const
63 {
64   int s = 0;
65   if ( layout() )
66     s = layout()->spacing();
67   return s;
68 }
69
70 void QtxGroupBox::setInsideMargin( int m )
71 {
72   if ( layout() )
73     layout()->setMargin( m );
74 }
75
76 void QtxGroupBox::setInsideSpacing( int s )
77 {
78   if ( layout() )
79     layout()->setSpacing( s );
80 }
81
82 #endif
83
84 void QtxGroupBox::insertTitleWidget( QWidget* wid )
85 {
86   if ( !myContainer )
87     return;
88
89   wid->reparent( myContainer, QPoint( 0, 0 ), true );
90   wid->installEventFilter( this );
91
92   updateTitle();
93 }
94
95 void QtxGroupBox::removeTitleWidget( QWidget* wid )
96 {
97   if ( !myContainer || wid->parentWidget() != myContainer )
98     return;
99
100   wid->reparent( 0, QPoint( 0, 0 ), false );
101   wid->removeEventFilter( this );
102
103   updateTitle();
104 }
105
106 void QtxGroupBox::adjustInsideMargin()
107 {
108   QApplication::sendPostedEvents( myContainer, QEvent::ChildInserted );
109
110   myContainer->resize( myContainer->minimumSizeHint() );
111
112   setInsideMargin( myContainer->height() );
113 }
114
115 void QtxGroupBox::setAlignment( int align )
116 {
117   QGroupBox::setAlignment( align );
118
119   updateTitle();
120 }
121
122 void QtxGroupBox::setTitle( const QString& title )
123 {
124   QGroupBox::setTitle( title );
125
126   updateTitle();
127 }
128
129 void QtxGroupBox::setColumnLayout( int strips, Orientation o )
130 {
131   if ( myContainer )
132     myContainer->reparent( 0, QPoint( 0, 0 ), false );
133
134   QGroupBox::setColumnLayout( strips, o );
135
136   if ( myContainer )
137     myContainer->reparent( this, QPoint( 0, 0 ), false );
138
139   updateTitle();
140 }
141
142 void QtxGroupBox::show()
143 {
144   QGroupBox::show();
145
146   updateTitle();
147 }
148
149 void QtxGroupBox::update()
150 {
151   QGroupBox::update();
152
153   updateTitle();
154 }
155
156 QSize QtxGroupBox::sizeHint() const
157 {
158   QSize sz = QGroupBox::sizeHint();
159
160   int sw = titleSize().width();
161
162   if ( myContainer )
163   {
164     if ( alignment() == AlignCenter )
165       sw += 2 * ( myContainer->width() + 5 );
166     else
167       sw += 1 * ( myContainer->width() + 5 );
168   }
169
170   sw += frameRect().left();
171
172   return QSize( QMAX( sz.width(), sw ), sz.height() );
173 }
174
175 QSize QtxGroupBox::minimumSizeHint() const
176 {
177   QSize sz = QGroupBox::minimumSizeHint();
178
179   int sw = titleSize().width() + myContainer ? myContainer->width() + 5 : 0;
180
181   if ( myContainer )
182   {
183     if ( alignment() == AlignCenter )
184       sw += 2 * ( myContainer->width() + 5 );
185     else
186       sw += 1 * ( myContainer->width() + 5 );
187   }
188
189   sw += frameRect().left();
190
191   return QSize( QMAX( sz.width(), sw ), sz.height() );
192 }
193
194 bool QtxGroupBox::eventFilter( QObject* obj, QEvent* e )
195 {
196   QEvent::Type type = e->type();
197   if ( myContainer && obj->parent() == myContainer &&
198        ( type == QEvent::Show || type == QEvent::ShowToParent ||
199          type == QEvent::Hide || type == QEvent::HideToParent ) )
200     QApplication::postEvent( this, new QCustomEvent( QEvent::User ) );
201
202   return QGroupBox::eventFilter( obj, e );
203 }
204
205 void QtxGroupBox::resizeEvent( QResizeEvent* e )
206 {
207   QGroupBox::resizeEvent( e );
208
209   updateTitle();
210 }
211
212 void QtxGroupBox::childEvent( QChildEvent* e )
213 {
214   if ( e->type() == QEvent::ChildInserted && e->child() == myContainer )
215     return;
216
217   QGroupBox::childEvent( e );
218 }
219
220 void QtxGroupBox::customEvent( QCustomEvent* )
221 {
222   updateTitle();
223 }
224
225 void QtxGroupBox::frameChanged()
226 {
227   updateTitle();
228 }
229
230 QSize QtxGroupBox::titleSize() const
231 {
232   QSize sz( 0, 0 );
233
234   if ( layout() )
235   {
236     QSpacerItem* si = 0;
237     for ( QLayoutIterator it = layout()->iterator(); it.current() && !si; ++it )
238       si = it.current()->spacerItem();
239     if ( si )
240       sz = si->sizeHint();
241   }
242
243   int w = sz.width();
244   int h = sz.height() + insideMargin();
245
246   return QSize( w, h );
247 }
248
249 void QtxGroupBox::updateTitle()
250 {
251   if ( !myContainer )
252     return;
253
254   int align = alignment();
255   if ( align == AlignAuto )
256     align = QApplication::reverseLayout() ? AlignRight : AlignLeft;
257
258   if ( title().isEmpty() )
259     align = AlignRight;
260
261   QSize ts = titleSize();
262
263   int m = 5;
264
265   int w = frameRect().width() - ts.width();
266   if ( align == AlignCenter )
267     w = w / 2;
268
269   w -= m;
270
271   QApplication::sendPostedEvents( myContainer, QEvent::ChildInserted );
272   myContainer->resize( myContainer->minimumSizeHint() );
273
274   bool vis = false;
275   const QObjectList* list = myContainer->children();
276   if ( list )
277   {
278     for ( QObjectListIt it( *list ); it.current() && !vis; ++it )
279       vis = it.current()->isWidgetType() &&
280             ((QWidget*)it.current())->isVisibleTo( myContainer );
281   }
282
283   if ( myContainer->height() > ts.height() || myContainer->width() > w || !vis )
284     myContainer->hide();
285   else
286   {
287     int x = 0;
288     if ( align == AlignRight )
289       x = frameRect().left() + m;
290     else
291       x = frameRect().right() - myContainer->width() - m;
292
293     int y = frameRect().top() - ( myContainer->height() - frameWidth() ) / 2;
294
295     QPoint pos( x, QMAX( 0, y ) );
296     pos = mapToGlobal( pos );
297     if ( myContainer->parentWidget() )
298       pos = myContainer->parentWidget()->mapFromGlobal( pos );
299     myContainer->move( pos );
300     myContainer->show();
301   }
302
303   updateGeometry();
304 }