00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include "kexiformscrollview.h"
00022
00023
00024 #include <formeditor/form.h>
00025 #include <formeditor/formmanager.h>
00026 #include <formeditor/objecttree.h>
00027 #include <formeditor/commands.h>
00028 #include <widget/utils/kexirecordmarker.h>
00029
00030 #include <kpopupmenu.h>
00031 #include <kdebug.h>
00032
00033 KexiFormScrollView::KexiFormScrollView(QWidget *parent, bool preview)
00034 : KexiScrollView(parent, preview)
00035 , KexiRecordNavigatorHandler()
00036 , KexiSharedActionClient()
00037 , KexiDataAwareObjectInterface()
00038 , KexiFormDataProvider()
00039 , KexiFormEventHandler()
00040 {
00041 m_currentLocalSortColumn = -1;
00042 m_localSortingOrder = -1;
00043 m_previousItem = 0;
00044 m_navPanel = m_scrollViewNavPanel;
00045 if (preview) {
00046 setRecordNavigatorVisible(true);
00047
00048
00049
00050 }
00051
00052 connect(this, SIGNAL(resizingStarted()), this, SLOT(slotResizingStarted()));
00053
00054 m_popupMenu = new KPopupMenu(this, "contextMenu");
00055
00056
00057 }
00058
00059 KexiFormScrollView::~KexiFormScrollView()
00060 {
00061 if (m_owner)
00062 delete m_data;
00063 m_data = 0;
00064 }
00065
00066 void
00067 KexiFormScrollView::show()
00068 {
00069 KexiScrollView::show();
00070
00071 #if 0 //moved to KexiFormView, OK?
00072
00073 if (m_preview) {
00074 KexiFormView* fv = dynamic_cast<KexiFormView*>(parent());
00075 int resizeMode = fv ? fv->resizeMode() : KexiFormView::ResizeAuto;
00076 if (resizeMode == KexiFormView::ResizeAuto)
00077 setResizePolicy(AutoOneFit);
00078 }
00079 #endif
00080 }
00081
00082 void
00083 KexiFormScrollView::slotResizingStarted()
00084 {
00085 if(m_form && KFormDesigner::FormManager::self())
00086 setSnapToGrid(KFormDesigner::FormManager::self()->snapWidgetsToGrid(), m_form->gridSize());
00087 else
00088 setSnapToGrid(false);
00089 }
00090
00091 int KexiFormScrollView::rowsPerPage() const
00092 {
00094 return 10;
00095 }
00096
00097 void KexiFormScrollView::selectCellInternal()
00098 {
00099
00100 if (m_currentItem) {
00101 if (m_currentItem!=m_previousItem) {
00102 fillDataItems(*m_currentItem, cursorAtNewRow());
00103 m_previousItem = m_currentItem;
00104 }
00105 }
00106 else {
00107 m_previousItem = 0;
00108 }
00109 }
00110
00111 void KexiFormScrollView::ensureCellVisible(int row, int col)
00112 {
00113 Q_UNUSED( row );
00114 Q_UNUSED( col );
00116
00117
00118
00119
00120
00121 }
00122
00123 void KexiFormScrollView::moveToRecordRequested(uint r)
00124 {
00126 selectRow(r);
00127 }
00128
00129 void KexiFormScrollView::moveToLastRecordRequested()
00130 {
00132 selectLastRow();
00133 }
00134
00135 void KexiFormScrollView::moveToPreviousRecordRequested()
00136 {
00138 selectPrevRow();
00139 }
00140
00141 void KexiFormScrollView::moveToNextRecordRequested()
00142 {
00144 selectNextRow();
00145 }
00146
00147 void KexiFormScrollView::moveToFirstRecordRequested()
00148 {
00150 selectFirstRow();
00151 }
00152
00153
00154
00155
00157
00158
00159 void KexiFormScrollView::clearColumnsInternal(bool repaint)
00160 {
00161 Q_UNUSED( repaint );
00163 }
00164
00165 void KexiFormScrollView::addHeaderColumn(const QString& caption, const QString& description,
00166 const QIconSet& icon, int width)
00167 {
00168 Q_UNUSED( caption );
00169 Q_UNUSED( description );
00170 Q_UNUSED( icon );
00171 Q_UNUSED( width );
00172
00174 }
00175
00176 int KexiFormScrollView::currentLocalSortingOrder() const
00177 {
00179 return m_localSortingOrder;
00180 }
00181
00182 int KexiFormScrollView::currentLocalSortColumn() const
00183 {
00184 return m_currentLocalSortColumn;
00185 }
00186
00187 void KexiFormScrollView::setLocalSortingOrder(int col, int order)
00188 {
00190 m_currentLocalSortColumn = col;
00191 m_localSortingOrder = order;
00192 }
00193
00194 void KexiFormScrollView::sortColumnInternal(int col, int order)
00195 {
00196 Q_UNUSED( col );
00197 Q_UNUSED( order );
00199 }
00200
00201 void KexiFormScrollView::updateGUIAfterSorting()
00202 {
00204 }
00205
00206 void KexiFormScrollView::createEditor(int row, int col, const QString& addText,
00207 bool removeOld)
00208 {
00209 Q_UNUSED( row );
00210 Q_UNUSED( addText );
00211 Q_UNUSED( removeOld );
00212
00213 if (isReadOnly()) {
00214 kexipluginsdbg << "KexiFormScrollView::createEditor(): DATA IS READ ONLY!"<<endl;
00215 return;
00216 }
00217 if (column( col )->isReadOnly()) {
00218 kexipluginsdbg << "KexiFormScrollView::createEditor(): COL IS READ ONLY!"<<endl;
00219 return;
00220 }
00221
00223 const bool startRowEdit = !m_rowEditing;
00224
00225 if (!m_rowEditing) {
00226
00227 m_data->clearRowEditBuffer();
00228
00229 m_rowEditing = true;
00230
00231 if (m_verticalHeader)
00232 m_verticalHeader->setEditRow(m_curRow);
00233 if (isInsertingEnabled() && m_currentItem==m_insertItem) {
00234
00235 m_newRowEditing = true;
00236
00237 m_data->append( m_insertItem );
00238
00239 m_insertItem = m_data->createItem();
00240
00241 if (m_verticalHeader)
00242 m_verticalHeader->addLabel();
00243
00244 updateWidgetContentsSize();
00245
00246
00247
00248
00249
00250
00251 }
00252 }
00253
00254 m_editor = editor(col);
00255 if (!m_editor)
00256 return;
00257
00258 if (startRowEdit) {
00259 recordNavigator()->showEditingIndicator(true);
00260
00261
00262 emit rowEditStarted(m_curRow);
00263 }
00264 }
00265
00266 KexiDataItemInterface *KexiFormScrollView::editor( int col, bool ignoreMissingEditor )
00267 {
00268 Q_UNUSED( ignoreMissingEditor );
00269
00270 if (!m_data || col<0 || col>=columns())
00271 return 0;
00272
00273 return dynamic_cast<KexiFormDataItemInterface*>(dbFormWidget()->orderedDataAwareWidgets()->at( col ));
00274
00275
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286
00287
00288
00289
00290
00291
00292
00293
00294
00295
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308 }
00309
00310 void KexiFormScrollView::editorShowFocus( int row, int col )
00311 {
00312 Q_UNUSED( row );
00313 Q_UNUSED( col );
00315
00316
00317 }
00318
00319 void KexiFormScrollView::updateCell(int row, int col)
00320 {
00321 Q_UNUSED( row );
00322 Q_UNUSED( col );
00324 }
00325
00326 void KexiFormScrollView::updateCurrentCell()
00327 {
00328 }
00329
00330 void KexiFormScrollView::updateRow(int row)
00331 {
00332 Q_UNUSED(row)
00334 }
00335
00336 void KexiFormScrollView::updateWidgetContents()
00337 {
00339 }
00340
00341 void KexiFormScrollView::updateWidgetContentsSize()
00342 {
00344 }
00345
00346 void KexiFormScrollView::updateWidgetScrollBars()
00347 {
00349 }
00350
00351 void KexiFormScrollView::slotRowRepaintRequested(KexiTableItem& item)
00352 {
00353 Q_UNUSED( item );
00355 }
00356
00357
00358
00359
00361
00362
00363
00364
00366
00367
00368 void KexiFormScrollView::slotRowInserted(KexiTableItem *item, bool repaint)
00369 {
00370 Q_UNUSED( item );
00371 Q_UNUSED( repaint );
00373 }
00374
00375 void KexiFormScrollView::slotRowInserted(KexiTableItem *item, uint row, bool repaint)
00376 {
00377 Q_UNUSED( item );
00378 Q_UNUSED( row );
00379 Q_UNUSED( repaint );
00381 }
00382
00383 void KexiFormScrollView::slotRowsDeleted( const QValueList<int> & )
00384 {
00386 }
00387
00388 KexiDBForm* KexiFormScrollView::dbFormWidget() const
00389 {
00390 return dynamic_cast<KexiDBForm*>(m_widget);
00391 }
00392
00393 int KexiFormScrollView::columns() const
00394 {
00395 return dbFormWidget()->orderedDataAwareWidgets()->count();
00396 }
00397
00398
00399
00400
00401
00402
00403
00404
00405
00406
00407 bool KexiFormScrollView::columnEditable(int col)
00408 {
00409 kexipluginsdbg << "KexiFormScrollView::columnEditable(" << col << ")" << endl;
00410 foreach_list (QPtrListIterator<KexiFormDataItemInterface>, it, m_dataItems) {
00411 kexipluginsdbg << (dynamic_cast<QWidget*>(it.current()) ? dynamic_cast<QWidget*>(it.current())->name() : "" )
00412 << " " << it.current()->dataSource() << endl;
00413 }
00414 kexipluginsdbg << "-- focus widgets --" << endl;
00415 foreach_list (QPtrListIterator<QWidget>, it, *dbFormWidget()->orderedFocusWidgets()) {
00416 kexipluginsdbg << it.current()->name() << endl;
00417 }
00418 kexipluginsdbg << "-- data-aware widgets --" << endl;
00419 foreach_list (QPtrListIterator<QWidget>, it, *dbFormWidget()->orderedDataAwareWidgets()) {
00420 kexipluginsdbg << it.current()->name() << endl;
00421 }
00422
00423
00424
00425 KexiFormDataItemInterface *item = dynamic_cast<KexiFormDataItemInterface*>(dbFormWidget()->orderedDataAwareWidgets()->at( col ));
00426
00427 if (!item || item->isReadOnly())
00428 return false;
00429
00430
00431
00432 return KexiDataAwareObjectInterface::columnEditable( col );
00433 }
00434
00435 void KexiFormScrollView::valueChanged(KexiDataItemInterface* item)
00436 {
00437 if (!item)
00438 return;
00439
00440 kexipluginsdbg << "** KexiFormScrollView::valueChanged(): editedItem="
00441 << (dbFormWidget()->editedItem ? dbFormWidget()->editedItem->value().toString() : QString::null)
00442 << ", "
00443 << (item ? item->value().toString() : QString::null)
00444 << endl;
00445 if (dbFormWidget()->editedItem!=item) {
00446 kexipluginsdbg << "**>>> dbFormWidget()->editedItem = dynamic_cast<KexiFormDataItemInterface*>(item)" << endl;
00447 dbFormWidget()->editedItem = dynamic_cast<KexiFormDataItemInterface*>(item);
00448 startEditCurrentCell();
00449 }
00450 fillDuplicatedDataItems(dynamic_cast<KexiFormDataItemInterface*>(item), item->value());
00451
00452
00453 dynamic_cast<KexiFormDataItemInterface*>(item)->setDisplayDefaultValue(dynamic_cast<QWidget*>(item), false);
00454 }
00455
00456 bool KexiFormScrollView::cursorAtNewRow() const
00457 {
00458 return isInsertingEnabled() && ( m_currentItem==m_insertItem || m_newRowEditing );
00459 }
00460
00461 void KexiFormScrollView::initDataContents()
00462 {
00463 KexiDataAwareObjectInterface::initDataContents();
00464
00465 if (m_preview) {
00467 setRecordNavigatorVisible(m_data);
00468 recordNavigator()->setEnabled(m_data);
00469 if (m_data) {
00470 recordNavigator()->setEditingIndicatorEnabled( !isReadOnly() );
00471 recordNavigator()->showEditingIndicator(false);
00472 }
00473
00474 dbFormWidget()->updateReadOnlyFlags();
00475 }
00476 }
00477
00478 KexiTableViewColumn* KexiFormScrollView::column(int col)
00479 {
00480 const int id = fieldNumberForColumn(col);
00481 return (id >= 0) ? m_data->column( id ) : 0;
00482 }
00483
00484 bool KexiFormScrollView::shouldDisplayDefaultValueForItem(KexiFormDataItemInterface* itemIface) const
00485 {
00486 return cursorAtNewRow()
00487 && !itemIface->columnInfo()->field->defaultValue().isNull()
00488
00489 && !itemIface->columnInfo()->field->isAutoIncrement();
00490 }
00491
00492 bool KexiFormScrollView::cancelEditor()
00493 {
00494 if (!dynamic_cast<KexiFormDataItemInterface*>(m_editor))
00495 return false;
00496
00497 if (m_errorMessagePopup)
00498 m_errorMessagePopup->close();
00499
00500 KexiFormDataItemInterface *itemIface = dynamic_cast<KexiFormDataItemInterface*>(m_editor);
00501 itemIface->undoChanges();
00502
00503 const bool displayDefaultValue = shouldDisplayDefaultValueForItem(itemIface);
00504
00505 if (itemIface->hasDisplayedDefaultValue() != displayDefaultValue)
00506 itemIface->setDisplayDefaultValue( dynamic_cast<QWidget*>(itemIface), displayDefaultValue );
00507
00508 fillDuplicatedDataItems(itemIface, m_editor->value());
00509
00510
00511 return KexiDataAwareObjectInterface::cancelEditor();
00512 }
00513
00514 void KexiFormScrollView::updateAfterCancelRowEdit()
00515 {
00516 for (QPtrListIterator<KexiFormDataItemInterface> it(m_dataItems); it.current(); ++it) {
00517 if (dynamic_cast<QWidget*>(it.current())) {
00518 kexipluginsdbg << "KexiFormScrollView::updateAfterCancelRowEdit(): "
00519 << dynamic_cast<QWidget*>(it.current())->className() << " "
00520 << dynamic_cast<QWidget*>(it.current())->name() << endl;
00521 }
00522 KexiFormDataItemInterface *itemIface = it.current();
00523 const bool displayDefaultValue = shouldDisplayDefaultValueForItem(itemIface);
00524 itemIface->undoChanges();
00525 if (itemIface->hasDisplayedDefaultValue() != displayDefaultValue)
00526 itemIface->setDisplayDefaultValue( dynamic_cast<QWidget*>(itemIface), displayDefaultValue );
00527 }
00528 recordNavigator()->showEditingIndicator(false);
00529 dbFormWidget()->editedItem = 0;
00530 }
00531
00532 void KexiFormScrollView::updateAfterAcceptRowEdit()
00533 {
00534 if (!m_currentItem)
00535 return;
00536 recordNavigator()->showEditingIndicator(false);
00537 dbFormWidget()->editedItem = 0;
00538
00539 fillDataItems(*m_currentItem, cursorAtNewRow());
00540 m_previousItem = m_currentItem;
00541 }
00542
00543 void KexiFormScrollView::beforeSwitchView()
00544 {
00545 m_editor = 0;
00546 }
00547
00548 void KexiFormScrollView::refreshContentsSize()
00549 {
00550 KexiScrollView::refreshContentsSize();
00551
00552 if (!m_preview && sender()==&m_delayedResize) {
00553 if (m_form)
00554 m_form->clearCommandHistory();
00555 }
00556 }
00557
00558 void KexiFormScrollView::handleDataWidgetAction(const QString& actionName)
00559 {
00560 QWidget *w = focusWidget();
00561 KexiFormDataItemInterface *item = 0;
00562 while (w) {
00563 item = dynamic_cast<KexiFormDataItemInterface*>(w);
00564 if (item)
00565 break;
00566 w = w->parentWidget();
00567 }
00568 if (item)
00569 item->handleAction(actionName);
00570 }
00571
00572 void KexiFormScrollView::copySelection()
00573 {
00574 handleDataWidgetAction("edit_copy");
00575 }
00576
00577 void KexiFormScrollView::cutSelection()
00578 {
00579 handleDataWidgetAction("edit_cut");
00580 }
00581
00582 void KexiFormScrollView::paste()
00583 {
00584 handleDataWidgetAction("edit_paste");
00585 }
00586
00587 int KexiFormScrollView::lastVisibleRow() const
00588 {
00590 return -1;
00591 }
00592
00593 #include "kexiformscrollview.moc"