~ubuntu-branches/ubuntu/maverick/datakiosk/maverick

« back to all changes in this revision

Viewing changes to src/src/datatableedit.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Jonathan Riddell
  • Date: 2005-06-27 22:48:06 UTC
  • Revision ID: james.westby@ubuntu.com-20050627224806-8farkci1dc2onhbs
Tags: upstream-0.7
ImportĀ upstreamĀ versionĀ 0.7

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/***************************************************************************
 
2
*   Copyright (C) 2005 by Adam Treat                                      *
 
3
*   treat@kde.org                                                         *
 
4
*                                                                         *
 
5
*   This program is free software; you can redistribute it and/or modify  *
 
6
*   it under the terms of the GNU General Public License as published by  *
 
7
*   the Free Software Foundation; either version 2 of the License, or     *
 
8
*   (at your option) any later version.                                   *
 
9
*                                                                         *
 
10
***************************************************************************/
 
11
 
 
12
#include "datatableedit.h"
 
13
#include "formlayout.h"
 
14
#include "datatableeditorfactory.h"
 
15
 
 
16
#include <qcolor.h>
 
17
#include <qpalette.h>
 
18
#include <qpushbutton.h>
 
19
 
 
20
#include <qlabel.h>
 
21
#include <qpainter.h>
 
22
#include <qsqlform.h>
 
23
#include <qdrawutil.h>
 
24
#include <qsqlpropertymap.h>
 
25
 
 
26
#include <kdebug.h>
 
27
#include <klocale.h>
 
28
#include <kmessagebox.h>
 
29
 
 
30
ScrollForm::ScrollForm( QWidget *parent, const char *name )
 
31
        : QScrollView( parent, name ),
 
32
        m_frameColor( Qt::green )
 
33
{
 
34
    setResizePolicy( QScrollView::AutoOneFit );
 
35
}
 
36
 
 
37
ScrollForm::~ScrollForm()
 
38
{}
 
39
 
 
40
void ScrollForm::drawFrame( QPainter* p )
 
41
{
 
42
    qDrawPlainRect( p, frameRect(), m_frameColor, 2 );
 
43
}
 
44
 
 
45
QColor ScrollForm::getFrameColor() const
 
46
{
 
47
    return m_frameColor;
 
48
}
 
49
 
 
50
void ScrollForm::setFrameColor( const QColor &color )
 
51
{
 
52
    m_frameColor = color;
 
53
}
 
54
 
 
55
DataTableEdit::DataTableEdit( QWidget *parent, const char *name )
 
56
        : QDataBrowser( parent, name ),
 
57
        m_map( 0L ),
 
58
        m_commit( 0L ),
 
59
        m_refreshing( false ),
 
60
        m_inserting( false ),
 
61
        m_currentRow( 0 )
 
62
{
 
63
 
 
64
    setConfirmInsert( true );
 
65
    setConfirmDelete( true );
 
66
 
 
67
    setAutoEdit( false );
 
68
    setForm( new QSqlForm() );
 
69
 
 
70
    QVBoxLayout *topLayout = new QVBoxLayout( this, 10, 10 );
 
71
 
 
72
    m_scroll = new ScrollForm( this );
 
73
    m_formBox = new QFrame( m_scroll->viewport() );
 
74
 
 
75
    QVBoxLayout *viewPortLayout = new QVBoxLayout( m_scroll->viewport(), 0, 0 );
 
76
    viewPortLayout->add(m_formBox);
 
77
 
 
78
    m_formLayout = new FormLayout( m_formBox, 20, 20 );
 
79
    m_scroll->addChild( m_formBox );
 
80
 
 
81
    QFrame *buttonBox = new QFrame(this);
 
82
    QHBoxLayout *buttonLayout = new QHBoxLayout( buttonBox, 0, 20 );
 
83
 
 
84
    QPushButton *f = new QPushButton( "|< First", buttonBox );
 
85
    QPushButton *p = new QPushButton( "<< Prev", buttonBox );
 
86
    QPushButton *n = new QPushButton( "Next >>", buttonBox );
 
87
    QPushButton *l = new QPushButton( "Last >|", buttonBox );
 
88
    m_commit = new QPushButton( "Commit", buttonBox );
 
89
    m_commit->setEnabled( false );
 
90
 
 
91
    f->setFocusPolicy( QWidget::ClickFocus );
 
92
    p->setFocusPolicy( QWidget::ClickFocus );
 
93
    n->setFocusPolicy( QWidget::ClickFocus );
 
94
    l->setFocusPolicy( QWidget::ClickFocus );
 
95
    m_commit->setFocusPolicy( QWidget::ClickFocus );
 
96
 
 
97
    QSpacerItem *hSpace = new QSpacerItem( 0, 0, QSizePolicy::Expanding, QSizePolicy::Minimum );
 
98
 
 
99
    buttonLayout->add( f );
 
100
    buttonLayout->add( p );
 
101
    buttonLayout->add( n );
 
102
    buttonLayout->add( l );
 
103
    buttonLayout->addItem( hSpace );
 
104
    buttonLayout->add( m_commit );
 
105
 
 
106
    topLayout->add( m_scroll );
 
107
    topLayout->add( buttonBox );
 
108
 
 
109
    QObject::connect( f, SIGNAL( clicked() ), this, SLOT( first() ) );
 
110
    QObject::connect( p, SIGNAL( clicked() ), this, SLOT( prev() ) );
 
111
    QObject::connect( n, SIGNAL( clicked() ), this, SLOT( next() ) );
 
112
    QObject::connect( l, SIGNAL( clicked() ), this, SLOT( last() ) );
 
113
    QObject::connect( m_commit, SIGNAL( clicked() ), this, SLOT( update() ) );
 
114
}
 
115
 
 
116
DataTableEdit::~DataTableEdit()
 
117
{}
 
118
 
 
119
void DataTableEdit::addEditorBase( DataEditorBase *editor, bool isVirtual )
 
120
{
 
121
    m_formLayout->add( editor );
 
122
    if ( !isVirtual )
 
123
    {
 
124
        form()->insert( editor->getEditor(), editor->getField()->name() );
 
125
        QObject::connect( editor, SIGNAL( editBufferChanged( QVariant, bool ) ),
 
126
                          this, SLOT( toggleColorBox() ) );
 
127
        QObject::connect( editor, SIGNAL( addConstraint( DataEditorBase *, const QString & ) ),
 
128
                          this, SLOT( constrainEditor( DataEditorBase *, const QString & ) ) );
 
129
    }
 
130
    editor->show();
 
131
}
 
132
 
 
133
void DataTableEdit::removeEditors()
 
134
{
 
135
    form()->clear();
 
136
    QLayoutIterator it = m_formLayout->iterator();
 
137
    QLayoutItem *item;
 
138
    while ( (item = it.takeCurrent()) )
 
139
    {
 
140
        DataEditorBase *editor = ::qt_cast<DataEditorBase*>( item->widget() );
 
141
        delete editor;
 
142
        delete item;
 
143
    }
 
144
}
 
145
 
 
146
void DataTableEdit::installPropertyMap( QSqlPropertyMap *map )
 
147
{
 
148
    m_map = map;
 
149
    form()->installPropertyMap( map );
 
150
}
 
151
 
 
152
FormLayout* DataTableEdit::getFormLayout() const
 
153
{
 
154
    return m_formLayout;
 
155
}
 
156
 
 
157
ScrollForm* DataTableEdit::getScrollView() const
 
158
{
 
159
    return m_scroll;
 
160
}
 
161
 
 
162
QFrame* DataTableEdit::getFormBox() const
 
163
{
 
164
    return m_formBox;
 
165
}
 
166
 
 
167
QVariant DataTableEdit::currentValue( const QString &field )
 
168
{
 
169
    QSqlField *f = sqlCursor()->editBuffer()->field( field );
 
170
    if ( f )
 
171
    {
 
172
        QWidget *w = form()->fieldToWidget( f );
 
173
        if ( w && m_map )
 
174
        {
 
175
            QVariant v = m_map->property( w );
 
176
            if ( !v.isNull() )
 
177
                return v;
 
178
        }
 
179
 
 
180
        return f->value();
 
181
    }
 
182
 
 
183
    return QVariant();
 
184
}
 
185
 
 
186
void DataTableEdit::setCurrentRow( int row )
 
187
{
 
188
    if ( row == -1 )
 
189
    {
 
190
        form()->clearValues( true );
 
191
        setEnabled( false );
 
192
        m_scroll->viewport()->hide();
 
193
    }
 
194
    else if ( !isEnabled() )
 
195
    {
 
196
        setEnabled( true );
 
197
        m_scroll->viewport()->show();
 
198
    }
 
199
 
 
200
    seek( row, false );
 
201
}
 
202
 
 
203
bool DataTableEdit::seek( int i, bool relative )
 
204
{
 
205
    m_currentRow = i;
 
206
 
 
207
    //If we are currently inserting, but the cursor
 
208
    //is valid then we've aborted the insert before the
 
209
    //commit.
 
210
    if ( m_inserting && sqlCursor()->at() == i )
 
211
        emit insertAborted();
 
212
 
 
213
    //The DataTableView sends us this extra signal
 
214
    //so we make sure the cursor is still invalid during
 
215
    //our commit.
 
216
    if ( m_inserting )
 
217
        m_inserting = sqlCursor()->at() != i;
 
218
 
 
219
    if ( !m_inserting )
 
220
    {
 
221
        changeColorBox( Qt::green );
 
222
        m_commit->setEnabled( false );
 
223
    }
 
224
 
 
225
    bool temp = QDataBrowser::seek( i, relative );
 
226
 
 
227
    return temp;
 
228
}
 
229
 
 
230
void DataTableEdit::first()
 
231
{
 
232
    emit selectedFirst();
 
233
}
 
234
 
 
235
void DataTableEdit::prev()
 
236
{
 
237
    emit selectedPrev();
 
238
}
 
239
 
 
240
void DataTableEdit::next()
 
241
{
 
242
    emit selectedNext();
 
243
}
 
244
 
 
245
void DataTableEdit::last()
 
246
{
 
247
    emit selectedLast();
 
248
}
 
249
 
 
250
void DataTableEdit::update()
 
251
{
 
252
    if ( !m_commit->isEnabled() )
 
253
        return;
 
254
 
 
255
    m_inserting = false;
 
256
    ///TODO Write own version of update to get rid of unnecessary seeks
 
257
    /// and invalidated updates.
 
258
    QDataBrowser::update();
 
259
    seek( m_currentRow, false );
 
260
    changeColorBox( Qt::green );
 
261
    m_commit->setEnabled( false );
 
262
    emit selectedRow( m_currentRow );
 
263
}
 
264
 
 
265
bool DataTableEdit::insertRecord()
 
266
{
 
267
    if ( confirmInsert() )
 
268
        if ( KMessageBox::Continue !=
 
269
             KMessageBox::warningContinueCancel( this, i18n( "You are about to insert a record. Are you sure?" ) ) )
 
270
                return false;
 
271
 
 
272
    m_inserting = true;
 
273
    QDataBrowser::insert();
 
274
    changeColorBox( Qt::red );
 
275
    m_commit->setEnabled( true );
 
276
    return true;
 
277
}
 
278
 
 
279
bool DataTableEdit::deleteRecord()
 
280
{
 
281
    if ( confirmDelete() )
 
282
        if ( KMessageBox::Continue !=
 
283
             KMessageBox::warningContinueCancel( this, i18n( "You are about to delete a record. Are you sure?" ) ) )
 
284
            return false;
 
285
 
 
286
    bool success = QDataBrowser::deleteCurrent();
 
287
    if ( success )
 
288
    {
 
289
        changeColorBox( Qt::green );
 
290
        m_commit->setEnabled( false );
 
291
    }
 
292
    return success;
 
293
}
 
294
 
 
295
void DataTableEdit::refresh()
 
296
{
 
297
    m_refreshing = true;
 
298
    QDataBrowser::refresh();
 
299
    m_refreshing = false;
 
300
}
 
301
 
 
302
void DataTableEdit::readFields()
 
303
{
 
304
    m_refreshing = true;
 
305
    QDataBrowser::readFields();
 
306
 
 
307
    QLayoutIterator it = m_formLayout->iterator();
 
308
    QLayoutItem *item;
 
309
    while ( (item = it.current()) != 0 )
 
310
    {
 
311
        DataEditorBase *editor = ::qt_cast<DataEditorBase*>( item->widget() );
 
312
        if ( !editor->getField() )
 
313
        {
 
314
            editor->calculateEditor(); //This editor points to a virtual field
 
315
            ++it;
 
316
            continue;
 
317
        }
 
318
 
 
319
        if ( editor->getField()->isNull() )
 
320
        {
 
321
            editor->setNullValue( "" ); //needs to sync with QDataTable::nullText
 
322
        }
 
323
        ++it;
 
324
    }
 
325
 
 
326
    m_refreshing = false;
 
327
}
 
328
 
 
329
void DataTableEdit::calculateFields()
 
330
{
 
331
    QLayoutIterator it = m_formLayout->iterator();
 
332
    QLayoutItem *item;
 
333
    while ( (item = it.current()) != 0 )
 
334
    {
 
335
        DataEditorBase *editor = ::qt_cast<DataEditorBase*>( item->widget() );
 
336
        if ( !editor->getField() )
 
337
            editor->calculateEditor(); //This editor points to a virtual field
 
338
        ++it;
 
339
    }
 
340
}
 
341
 
 
342
void DataTableEdit::toggleColorBox()
 
343
{
 
344
    if ( m_refreshing )
 
345
        return;
 
346
 
 
347
    QColor color = m_scroll->getFrameColor();
 
348
 
 
349
    if ( color == Qt::green && currentEdited() )
 
350
    {
 
351
        changeColorBox( Qt::red );
 
352
        m_commit->setEnabled( true );
 
353
    }
 
354
    else if ( color == Qt::red && !currentEdited() )
 
355
    {
 
356
        changeColorBox( Qt::green );
 
357
        m_commit->setEnabled( false );
 
358
    }
 
359
}
 
360
 
 
361
void DataTableEdit::constrainEditor( DataEditorBase *editor, const QString &field )
 
362
{
 
363
    DataEditorBase *constraint = 0;
 
364
    QLayoutIterator it = m_formLayout->iterator();
 
365
    QLayoutItem *item;
 
366
    while ( (item = it.current()) != 0 )
 
367
    {
 
368
        DataEditorBase *eb = ::qt_cast<DataEditorBase*>( item->widget() );
 
369
        if ( !eb->getField() )
 
370
        {
 
371
            ++it;
 
372
            continue;
 
373
        }
 
374
 
 
375
        if ( eb->getField()->name() == field )
 
376
        {
 
377
            constraint = eb;
 
378
            break;
 
379
        }
 
380
        ++it;
 
381
    }
 
382
 
 
383
    if ( constraint )
 
384
    {
 
385
        QObject::connect( constraint, SIGNAL( editBufferChanged( QVariant, bool ) ),
 
386
                          editor, SLOT( resetEditBuffer( QVariant, bool ) ) );
 
387
    }
 
388
}
 
389
 
 
390
QSql::Confirm DataTableEdit::confirmEdit( QSql::Op /*m*/ )
 
391
{
 
392
    return QSql::Yes;
 
393
}
 
394
 
 
395
void DataTableEdit::showEvent( QShowEvent *ev )
 
396
{
 
397
    QDataBrowser::showEvent( ev );
 
398
    if ( !m_formLayout )
 
399
        return;
 
400
 
 
401
    QLayoutIterator it = m_formLayout->iterator();
 
402
    QLayoutItem *item = it.current();
 
403
 
 
404
    if ( !item )
 
405
        return;
 
406
 
 
407
    if ( DataEditorBase *editor = ::qt_cast<DataEditorBase*>( item->widget() ) )
 
408
        editor->setFocus();
 
409
}
 
410
 
 
411
bool DataTableEdit::currentEdited()
 
412
{
 
413
    bool edited = false;
 
414
    QLayoutIterator it = m_formLayout->iterator();
 
415
    QLayoutItem *item;
 
416
    while ( (item = it.current()) != 0 )
 
417
    {
 
418
        DataEditorBase *editor = ::qt_cast<DataEditorBase*>( item->widget() );
 
419
        if ( editor->currentEdited() )
 
420
        {
 
421
            edited = true;
 
422
        }
 
423
        ++it;
 
424
    }
 
425
    return edited;
 
426
}
 
427
 
 
428
void DataTableEdit::handleError( const QSqlError &error )
 
429
{
 
430
    QSqlError err;
 
431
    //If currentEdited() != QDataBrowser::currentEdited()
 
432
    //we know that the user put an incorrect string in a
 
433
    //relation combo.  Eventually should track the combo and highlight it
 
434
    if ( currentEdited() && !QDataBrowser::currentEdited() )
 
435
        err = QSqlError ( error.driverText(),
 
436
            "Data Relation Error!\nCheck your dropdown boxes...",
 
437
            error.type(), error.number() );
 
438
    else
 
439
        err = error;
 
440
 
 
441
    kdDebug() << "Error in query = " << sqlCursor()->lastQuery() << endl;
 
442
    QDataBrowser::handleError( error );
 
443
}
 
444
 
 
445
void DataTableEdit::changeColorBox( QColor color )
 
446
{
 
447
    QColor cur = m_scroll->getFrameColor();
 
448
    if ( cur == color)
 
449
        return;
 
450
 
 
451
    m_scroll->setFrameColor( color );
 
452
    m_scroll->repaint();
 
453
    emit colorBoxChanged( color );
 
454
}
 
455
 
 
456
#include "datatableedit.moc"