summaryrefslogtreecommitdiffabout
path: root/qtcompat/qcombotableitem.cpp
Unidiff
Diffstat (limited to 'qtcompat/qcombotableitem.cpp') (more/less context) (ignore whitespace changes)
-rw-r--r--qtcompat/qcombotableitem.cpp481
1 files changed, 481 insertions, 0 deletions
diff --git a/qtcompat/qcombotableitem.cpp b/qtcompat/qcombotableitem.cpp
new file mode 100644
index 0000000..348ea24
--- a/dev/null
+++ b/qtcompat/qcombotableitem.cpp
@@ -0,0 +1,481 @@
1/****************************************************************************
2**
3** Implementation of QTable widget class
4**
5** Created : 000607
6**
7** Copyright (C) 1992-2002 Trolltech AS. All rights reserved.
8**
9** This file is part of the table module of the Qt GUI Toolkit.
10**
11** This file may be distributed under the terms of the Q Public License
12** as defined by Trolltech AS of Norway and appearing in the file
13** LICENSE.QPL included in the packaging of this file.
14**
15** This file may be distributed and/or modified under the terms of the
16** GNU General Public License version 2 as published by the Free Software
17** Foundation and appearing in the file LICENSE.GPL included in the
18** packaging of this file.
19**
20** Licensees holding valid Qt Enterprise Edition licenses may use this
21** file in accordance with the Qt Commercial License Agreement provided
22** with the Software.
23**
24** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
25** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
26**
27** See http://www.trolltech.com/pricing.html or email sales@trolltech.com for
28** information about Qt Commercial License Agreements.
29** See http://www.trolltech.com/qpl/ for QPL licensing information.
30** See http://www.trolltech.com/gpl/ for GPL licensing information.
31**
32** Contact info@trolltech.com if any conditions of this licensing are
33** not clear to you.
34**
35**********************************************************************/
36/*US
37#include "qglobal.h"
38#if defined(Q_CC_BOR)
39// needed for qsort() because of a std namespace problem on Borland
40#include "qplatformdefs.h"
41#endif
42*/
43#include "qcombotableitem.h"
44
45#include "qcombobox.h"
46#include "qstyle.h"
47
48/*US
49
50#ifndef QT_NO_TABLE
51
52#include "qpainter.h"
53#include "qlineedit.h"
54#include "qcursor.h"
55#include "qapplication.h"
56#include "qtimer.h"
57#include "qobjectlist.h"
58#include "qiconset.h"
59#include "qcombobox.h"
60#include "qcheckbox.h"
61#include "qdragobject.h"
62#include "qevent.h"
63#include "qlistbox.h"
64#include "qstyle.h"
65
66#include <stdlib.h>
67#include <limits.h>
68
69static bool qt_update_cell_widget = TRUE;
70
71class QM_EXPORT_TABLE QTableHeader : public QHeader
72{
73 friend class QTable;
74 Q_OBJECT
75
76public:
77 enum SectionState {
78 Normal,
79 Bold,
80 Selected
81 };
82
83 QTableHeader( int, QTable *t, QWidget* parent=0, const char* name=0 );
84 ~QTableHeader() {};
85 void addLabel( const QString &s, int size );
86 void setLabel( int section, const QString & s, int size = -1 );
87 void setLabel( int section, const QIconSet & iconset, const QString & s,
88 int size = -1 );
89 void removeLabel( int section );
90
91 void setSectionState( int s, SectionState state );
92 void setSectionStateToAll( SectionState state );
93 SectionState sectionState( int s ) const;
94
95 int sectionSize( int section ) const;
96 int sectionPos( int section ) const;
97 int sectionAt( int section ) const;
98
99 void setSectionStretchable( int s, bool b );
100 bool isSectionStretchable( int s ) const;
101
102 void updateCache();
103
104signals:
105 void sectionSizeChanged( int s );
106
107protected:
108 void paintEvent( QPaintEvent *e );
109 void paintSection( QPainter *p, int index, const QRect& fr );
110 void mousePressEvent( QMouseEvent *e );
111 void mouseMoveEvent( QMouseEvent *e );
112 void mouseReleaseEvent( QMouseEvent *e );
113 void mouseDoubleClickEvent( QMouseEvent *e );
114 void resizeEvent( QResizeEvent *e );
115
116private slots:
117 void doAutoScroll();
118 void sectionWidthChanged( int col, int os, int ns );
119 void indexChanged( int sec, int oldIdx, int newIdx );
120 void updateStretches();
121 void updateWidgetStretches();
122
123private:
124 void updateSelections();
125 void saveStates();
126 void setCaching( bool b );
127 void swapSections( int oldIdx, int newIdx, bool swapTable = TRUE );
128 bool doSelection( QMouseEvent *e );
129 void sectionLabelChanged( int section );
130 void resizeArrays( int n );
131
132private:
133 QMemArray<int> states, oldStates;
134 QMemArray<bool> stretchable;
135 QMemArray<int> sectionSizes, sectionPoses;
136 bool mousePressed;
137 int pressPos, startPos, endPos;
138 QTable *table;
139 QTimer *autoScrollTimer;
140 QWidget *line1, *line2;
141 bool caching;
142 int resizedSection;
143 bool isResizing;
144 int numStretches;
145 QTimer *stretchTimer, *widgetStretchTimer;
146 QTableHeaderPrivate *d;
147
148};
149
150#ifdef _WS_QWS_
151# define NO_LINE_WIDGET
152#endif
153
154
155
156struct QTablePrivate
157{
158 QTablePrivate() : hasRowSpan( FALSE ), hasColSpan( FALSE ),
159 redirectMouseEvent( FALSE )
160 {
161 hiddenRows.setAutoDelete( TRUE );
162 hiddenCols.setAutoDelete( TRUE );
163 }
164 uint hasRowSpan : 1;
165 uint hasColSpan : 1;
166 uint redirectMouseEvent : 1;
167 QIntDict<int> hiddenRows, hiddenCols;
168 QTimer *geomTimer;
169};
170
171struct QTableHeaderPrivate
172{
173#ifdef NO_LINE_WIDGET
174 int oldLinePos;
175#endif
176};
177
178static bool isRowSelection( QTable::SelectionMode selMode )
179{
180 return selMode == QTable::SingleRow || selMode == QTable::MultiRow;
181}
182*/
183
184
185/*!
186 \class QComboTableItem
187 \brief The QComboTableItem class provides a means of using
188 comboboxes in QTables.
189
190 \ingroup advanced
191 \module table
192
193 A QComboTableItem is a table item which looks and behaves like a
194 combobox. The advantage of using QComboTableItems rather than real
195 comboboxes is that a QComboTableItem uses far less resources than
196 real comboboxes in \l{QTable}s. When the cell has the focus it
197 displays a real combobox which the user can interact with. When
198 the cell does not have the focus the cell \e looks like a
199 combobox. Only text items (i.e. no pixmaps) may be used in
200 QComboTableItems.
201
202 QComboTableItem items have the edit type \c WhenCurrent (see
203 \l{EditType}). The QComboTableItem's list of items is provided by
204 a QStringList passed to the constructor.
205
206 The list of items may be changed using setStringList(). The
207 current item can be set with setCurrentItem() and retrieved with
208 currentItem(). The text of the current item can be obtained with
209 currentText(), and the text of a particular item can be retrieved
210 with text().
211
212 If isEditable() is TRUE the QComboTableItem will permit the user
213 to either choose an existing list item, or create a new list item
214 by entering their own text; otherwise the user may only choose one
215 of the existing list items.
216
217 To populate a table cell with a QComboTableItem use
218 QTable::setItem().
219
220 QComboTableItems may be deleted with QTable::clearCell().
221
222 QComboTableItems can be distinguished from \l{QTableItem}s and
223 \l{QCheckTableItem}s using their Run Time Type Identification
224 number (see rtti()).
225
226 \img qtableitems.png Table Items
227
228 \sa QCheckTableItem QTableItem QComboBox
229*/
230
231QComboBox *QComboTableItem::fakeCombo = 0;
232QWidget *fakeComboWidget = 0;
233
234/*!
235 Creates a combo table item for the table \a table. The combobox's
236 list of items is passed in the \a list argument. If \a editable is
237 TRUE the user may type in new list items; if \a editable is FALSE
238 the user may only select from the list of items provided.
239
240 By default QComboTableItems cannot be replaced by other table
241 items since isReplaceable() returns FALSE by default.
242
243 \sa QTable::clearCell() EditType
244*/
245
246QComboTableItem::QComboTableItem( QTable *table, const QStringList &list, bool editable )
247 : QTableItem( table, WhenCurrent, "" ), entries( list ), current( 0 ), edit( editable )
248{
249 setReplaceable( FALSE );
250 if ( !fakeCombo ) {
251 fakeComboWidget = new QWidget( 0, 0 );
252 fakeCombo = new QComboBox( FALSE, fakeComboWidget, 0 );
253 fakeCombo->hide();
254 }
255}
256
257/*!
258 Sets the list items of this QComboTableItem to the strings in the
259 string list \a l.
260*/
261
262void QComboTableItem::setStringList( const QStringList &l )
263{
264 entries = l;
265 current = 0;
266 if ( table()->cellWidget( row(), col() ) ) {
267 cb->clear();
268 cb->insertStringList( entries );
269 }
270 table()->updateCell( row(), col() );
271}
272
273/*! \reimp */
274
275QWidget *QComboTableItem::createEditor() const
276{
277 // create an editor - a combobox in our case
278 ( (QComboTableItem*)this )->cb = new QComboBox( edit, table()->viewport(), "qt_editor_cb" );
279 cb->insertStringList( entries );
280 cb->setCurrentItem( current );
281 QObject::connect( cb, SIGNAL( activated( int ) ), table(), SLOT( doValueChanged() ) );
282 return cb;
283}
284
285/*! \reimp */
286
287void QComboTableItem::setContentFromEditor( QWidget *w )
288{
289 if ( w->inherits( "QComboBox" ) ) {
290 QComboBox *cb = (QComboBox*)w;
291 entries.clear();
292 for ( int i = 0; i < cb->count(); ++i )
293 entries << cb->text( i );
294 current = cb->currentItem();
295 setText( *entries.at( current ) );
296 }
297}
298
299/*! \reimp */
300
301void QComboTableItem::paint( QPainter *p, const QColorGroup &cg,
302 const QRect &cr, bool selected )
303{
304 fakeCombo->resize( cr.width(), cr.height() );
305
306 QColorGroup c( cg );
307 if ( selected ) {
308 c.setBrush( QColorGroup::Base, cg.brush( QColorGroup::Highlight ) );
309 c.setColor( QColorGroup::Text, cg.highlightedText() );
310 }
311
312/*US QStyle::SFlags flags = QStyle::Style_Default;
313 if(isEnabled() && table()->isEnabled())
314 flags |= QStyle::Style_Enabled;
315*/
316//US table()->style().drawComplexControl( QStyle::CC_ComboBox, p, fakeCombo, fakeCombo->rect(), c, flags );
317
318 table()->style().drawComboButton(p, fakeCombo->x(), fakeCombo->y(), fakeCombo->width(), fakeCombo->height(), c, FALSE, FALSE, (/*US isEnabled() && */table()->isEnabled()), 0);
319 p->save();
320/*US
321 QRect textR = table()->style().querySubControlMetrics(QStyle::CC_ComboBox, fakeCombo,
322 QStyle::SC_ComboBoxEditField);
323
324*/
325 int align = alignment(); // alignment() changes entries
326//US p->drawText( textR, wordWrap() ? ( align | WordBreak ) : align, *entries.at( current ) );
327 QRect textR = QRect( fakeCombo->x()+2, fakeCombo->y(), fakeCombo->width()- 17, fakeCombo->height() );
328 //qDebug("x %d -- %d wid %d -- %d ", cr.x(),fakeCombo->x(), cr.width(), fakeCombo->width() );
329 p->drawText( textR, wordWrap() ? ( align | WordBreak ) : align, *entries.at( current ) );
330 p->restore();
331}
332
333/*!
334 Sets the list item \a i to be the combo table item's current list
335 item.
336
337 \sa currentItem()
338*/
339
340void QComboTableItem::setCurrentItem( int i )
341{
342 QWidget *w = table()->cellWidget( row(), col() );
343 if ( w && w->inherits( "QComboBox" ) ) {
344 ( (QComboBox*)w )->setCurrentItem( i );
345 current = i;
346 setText( ( (QComboBox*)w )->currentText() );
347 } else {
348 current = i;
349 setText( *entries.at( i ) );
350 table()->updateCell( row(), col() );
351 }
352}
353
354/*!
355 \overload
356
357 Sets the list item whose text is \a s to be the combo table item's
358 current list item. Does nothing if no list item has the text \a s.
359
360 \sa currentItem()
361*/
362
363void QComboTableItem::setCurrentItem( const QString &s )
364{
365 int i = entries.findIndex( s );
366 if ( i != -1 )
367 setCurrentItem( i );
368}
369
370/*!
371 Returns the index of the combo table item's current list item.
372
373 \sa setCurrentItem()
374*/
375
376int QComboTableItem::currentItem() const
377{
378 QWidget *w = table()->cellWidget( row(), col() );
379 if ( w && w->inherits( "QComboBox" ) )
380 return ( (QComboBox*)w )->currentItem();
381 return current;
382}
383
384/*!
385 Returns the text of the combo table item's current list item.
386
387 \sa currentItem() text()
388*/
389
390QString QComboTableItem::currentText() const
391{
392 QWidget *w = table()->cellWidget( row(), col() );
393 if ( w && w->inherits( "QComboBox" ) )
394 return ( (QComboBox*)w )->currentText();
395 return *entries.at( current );
396}
397
398/*!
399 Returns the total number of list items in the combo table item.
400*/
401
402int QComboTableItem::count() const
403{
404 QWidget *w = table()->cellWidget( row(), col() );
405 if ( w && w->inherits( "QComboBox" ) )
406 return ( (QComboBox*)w )->count();
407 return (int)entries.count(); //### size_t/int cast
408}
409
410/*!
411 Returns the text of the combo's list item at index \a i.
412
413 \sa currentText()
414*/
415
416QString QComboTableItem::text( int i ) const
417{
418 QWidget *w = table()->cellWidget( row(), col() );
419 if ( w && w->inherits( "QComboBox" ) )
420 return ( (QComboBox*)w )->text( i );
421 return *entries.at( i );
422}
423
424/*!
425 If \a b is TRUE the combo table item can be edited, i.e. the user
426 may enter a new text item themselves. If \a b is FALSE the user may
427 may only choose one of the existing items.
428
429 \sa isEditable()
430*/
431
432void QComboTableItem::setEditable( bool b )
433{
434 edit = b;
435}
436
437/*!
438 Returns TRUE if the user can add their own list items to the
439 combobox's list of items; otherwise returns FALSE.
440
441 \sa setEditable()
442*/
443
444bool QComboTableItem::isEditable() const
445{
446 return edit;
447}
448
449int QComboTableItem::RTTI = 1;
450
451/*!
452 \fn int QComboTableItem::rtti() const
453
454 Returns 1.
455
456 Make your derived classes return their own values for rtti()to
457 distinguish between different table item subclasses. You should
458 use values greater than 1000, preferably a large random number, to
459 allow for extensions to this class.
460
461
462 \sa QTableItem::rtti()
463*/
464
465int QComboTableItem::rtti() const
466{
467 return RTTI;
468}
469
470/*! \reimp */
471
472QSize QComboTableItem::sizeHint() const
473{
474 fakeCombo->insertItem( currentText() );
475 fakeCombo->setCurrentItem( fakeCombo->count() - 1 );
476 QSize sh = fakeCombo->sizeHint();
477 fakeCombo->removeItem( fakeCombo->count() - 1 );
478//US return sh.expandedTo( QApplication::globalStrut() );
479 return sh;
480}
481