QGIS API Documentation  2.8.2-Wien
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
qgscptcitycolorrampv2dialog.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgscptcitycolorrampv2dialog.cpp
3  ---------------------
4  begin : July 2012
5  copyright : (C) 2012 by Etienne Tourigny
6  email : etourigny dot dev at gmail.com
7  ***************************************************************************
8  * *
9  * This program is free software; you can redistribute it and/or modify *
10  * it under the terms of the GNU General Public License as published by *
11  * the Free Software Foundation; either version 2 of the License, or *
12  * (at your option) any later version. *
13  * *
14  ***************************************************************************/
15 
17 
18 #include "qgscptcityarchive.h"
19 #include "qgsvectorcolorrampv2.h"
20 #include "qgslogger.h"
21 #include "qgsapplication.h"
22 #include "qgsdialog.h"
23 
24 #include <QPushButton>
25 #include <QTextEdit>
26 #include <QTime>
27 #include <QMessageBox>
28 #include <QSortFilterProxyModel>
29 
31 
32 // TODO
33 // - fix Diverging children when first show Selections
34 // - fix crash on Diverging?
35 
36 class TreeFilterProxyModel : public QSortFilterProxyModel
37 {
38  // Q_OBJECT
39 
40  public:
41  TreeFilterProxyModel( QObject *parent, QgsCptCityBrowserModel* model )
42  : QSortFilterProxyModel( parent ), mModel( model )
43  { setSourceModel( mModel ); }
44 
45  protected:
46  bool filterAcceptsRow( int sourceRow, const QModelIndex &sourceParent ) const override
47  {
48  QgsCptCityDataItem* item = mModel->dataItem( mModel->index( sourceRow, 0, sourceParent ) );
49  return ( item && !( item->type() == QgsCptCityDataItem::ColorRamp ) );
50  }
51  // bool lessThan(const QModelIndex &left, const QModelIndex &right) const;
52 
53  private:
54  QgsCptCityBrowserModel* mModel;
55 };
56 
57 
58 // ----------------------
59 
61  : QDialog( parent )
62  , mRamp( 0 )
63  , mArchiveViewType( QgsCptCityBrowserModel::Selections )
64 {
65  setupUi( this );
66 
67  buttonBox->button( QDialogButtonBox::Ok )->setEnabled( false );
68 
69  QSettings settings;
70  restoreGeometry( settings.value( "/Windows/CptCityColorRampV2Dialog/geometry" ).toByteArray() );
71  mSplitter->setSizes( QList<int>() << 250 << 550 );
72  mSplitter->restoreState( settings.value( "/Windows/CptCityColorRampV2Dialog/splitter" ).toByteArray() );
73 
74  mModel = mAuthorsModel = mSelectionsModel = 0; //mListModel = 0;
75  mTreeFilter = 0;
76 
79 
80  // show information on how to install cpt-city files if none are found
81  if ( ! mArchive || mArchive->isEmpty() )
82  {
83  // QgsDialog dlg( this );
84  // dlg.setWindowTitle( tr( "cpt-city gradient files not found" ) );
85  QTextEdit *edit = new QTextEdit( 0 );
86  edit->setReadOnly( true );
87  // not sure if we want this long string to be translated
88  QString helpText = tr( "Error - cpt-city gradient files not found.\n\n"
89  "You have two means of installing them:\n\n"
90  "1) Install the \"Color Ramp Manager\" python plugin "
91  "(you must enable Experimental plugins in the plugin manager) "
92  "and use it to download latest cpt-city package.\n"
93  "You can install the entire cpt-city archive or a selection for QGIS.\n\n"
94  "2) Download the complete archive (in svg format) "
95  "and unzip it to your QGIS settings directory [%1] .\n\n"
96  "This file can be found at [%2]\nand current file is [%3]"
98  ).arg( "http://soliton.vm.bytemark.co.uk/pub/cpt-city/pkg/"
99  ).arg( "http://soliton.vm.bytemark.co.uk/pub/cpt-city/pkg/cpt-city-svg-2.07.zip" );
100  edit->setText( helpText );
101  mStackedWidget->addWidget( edit );
102  mStackedWidget->setCurrentIndex( 1 );
103  tabBar->setVisible( false );
104  // dlg.layout()->addWidget( edit );
105  // dlg.resize(500,400);
106  // dlg.exec();
107  return;
108  }
109 
110  if ( ! mArchive )
111  return;
112  QgsDebugMsg( "archive: " + mArchive->archiveName() );
113 
114  if ( ramp )
115  {
116  mRamp = ramp;
117  }
118  else
119  {
120  mRamp = new QgsCptCityColorRampV2( "", "", false );
121  ramp = mRamp;
122  }
123  QgsDebugMsg( QString( "ramp name= %1 variant= %2 - %3 variants" ).arg( ramp->schemeName() ).arg( ramp->variantName() ).arg( ramp->variantList().count() ) );
124 
125  // model / view
126  QgsDebugMsg( "loading model/view objects" );
127  if ( mAuthorsModel )
128  delete mAuthorsModel;
130  if ( mSelectionsModel )
131  delete mSelectionsModel;
134 
135  mTreeView->setSelectionMode( QAbstractItemView::SingleSelection );
136  mTreeView->setColumnHidden( 1, true );
137  QgsDebugMsg( "done loading model/view objects" );
138 
139  // setup ui
140  tabBar->blockSignals( true );
141  tabBar->addTab( tr( "Selections by theme" ) );
142  tabBar->addTab( tr( "All by author" ) );
143  cboVariantName->setIconSize( QSize( 100, 15 ) );
144  lblPreview->installEventFilter( this ); // mouse click on preview label shows svg render
145 
146  // look for item, if not found in selections archive, look for in authors
147  QgsDebugMsg( "looking for ramp " + mRamp->schemeName() );
148  if ( mRamp->schemeName() != "" )
149  {
150  bool found = updateRamp();
151  if ( ! found )
152  {
153  tabBar->setCurrentIndex( 1 );
155  found = updateRamp();
156  // if not found, go back to selections model
157  if ( ! found )
158  {
159  tabBar->setCurrentIndex( 0 );
161  }
162  }
163  if ( found )
164  buttonBox->button( QDialogButtonBox::Ok )->setEnabled( true );
165  }
166  else
167  {
168  updateRamp();
169  }
170 
171  tabBar->blockSignals( false );
172 
173  connect( this, SIGNAL( finished( int ) ), this, SLOT( onFinished() ) );
174 
175 }
176 
178 {
179 }
180 
182 {
183  QStringList variantList = mRamp->variantList();
184 
185  QgsDebugMsg( QString( "ramp %1%2 has %3 variants" ).arg( mRamp->schemeName() ).arg( mRamp->variantName() ).arg( variantList.count() ) );
186 
187  cboVariantName->blockSignals( true );
188  cboVariantName->clear();
189 
190  if ( variantList.isEmpty() )
191  {
192  cboVariantName->setEnabled( false );
193  cboVariantName->setVisible( false );
195  }
196  else
197  {
198  // populate variant combobox
199  QString oldVariant = cboVariantName->currentText();
200  QgsCptCityColorRampV2 ramp( mRamp->schemeName(), mRamp->variantList(), QString() );
201  QPixmap blankPixmap( cboVariantName->iconSize() );
202  blankPixmap.fill( Qt::white );
203  QIcon blankIcon( blankPixmap );
204  int index;
205 
206  foreach ( QString variant, variantList )
207  {
208  QString variantStr = variant;
209  if ( variantStr.startsWith( "-" ) || variantStr.startsWith( "_" ) )
210  variantStr.remove( 0, 1 );
211  cboVariantName->addItem( " " + variantStr );
212  index = cboVariantName->count() - 1;
213  cboVariantName->setItemData( index, variant, Qt::UserRole );
214 
215  ramp.setVariantName( variant );
216  if ( ramp.loadFile() )
217  cboVariantName->setItemIcon( index,
218  QgsSymbolLayerV2Utils::colorRampPreviewIcon( &ramp, cboVariantName->iconSize() ) );
219  else
220  cboVariantName->setItemIcon( index, blankIcon );
221  cboVariantName->setItemData( index, Qt::AlignHCenter, Qt::TextAlignmentRole );
222  }
223 
224  cboVariantName->blockSignals( false );
225 
226  // try to set the original variant again (if exists)
227  int idx = -1;
228  QString newVariant = mRamp->variantName();
229  QgsDebugMsg( QString( "variant= %1 - %2 variants" ).arg( mRamp->variantName() ).arg( mRamp->variantList().count() ) );
230  if ( newVariant != QString() )
231  {
232  if ( newVariant.startsWith( "-" ) || newVariant.startsWith( "_" ) )
233  newVariant.remove( 0, 1 );
234  newVariant = " " + newVariant;
235  idx = cboVariantName->findText( newVariant );
236  }
237  else
238  idx = cboVariantName->findText( oldVariant );
239 
240  // if not found use the item in the middle
241  if ( idx == -1 )
242  {
243  idx = cboVariantName->count() / 2;
244  }
245  cboVariantName->setCurrentIndex( idx );
246  // updatePreview();
247 
248  cboVariantName->setEnabled( true );
249  cboVariantName->setVisible( true );
250  }
251 
252 }
253 
255 {
256  const QModelIndex &sourceIndex = mTreeFilter->mapToSource( index );
257  QgsCptCityDataItem *item = mModel->dataItem( sourceIndex );
258  if ( ! item )
259  return;
260  QgsDebugMsg( QString( "item %1 clicked" ).arg( item->name() ) );
261  buttonBox->button( QDialogButtonBox::Ok )->setEnabled( false );
262  updateTreeView( item );
263 }
264 
266 {
267  if ( ! item )
268  {
269  QgsDebugMsg( "invalid item" );
270  return;
271  }
272  if ( item->type() == QgsCptCityDataItem::Directory )
273  {
274  if ( resetRamp )
275  {
276  mRamp->setName( "", "" );
277  QgsDebugMsg( QString( "variant= %1 - %2 variants" ).arg( mRamp->variantName() ).arg( mRamp->variantList().count() ) );
278  lblSchemeName->setText( "" );
280  }
281  updateListWidget( item );
282  lblSchemePath->setText( item->path() );
283  lblCollectionInfo->setText( QString( "%1 (%2)" ).arg( item->info() ).arg( item->leafCount() ) );
285  }
286  else if ( item->type() == QgsCptCityDataItem::Selection )
287  {
288  lblSchemePath->setText( "" );
290  updateListWidget( item );
291  lblCollectionInfo->setText( QString( "%1 (%2)" ).arg( item->info() ).arg( item->leafCount() ) );
292  }
293  else if ( item->type() == QgsCptCityDataItem::AllRamps )
294  {
295  lblSchemePath->setText( "" );
297  updateListWidget( item );
298  lblCollectionInfo->setText( tr( "All Ramps (%1)" ).arg( item->leafCount() ) );
299  }
300  else
301  {
302  QgsDebugMsg( QString( "item %1 has invalid type %2" ).arg( item->path() ).arg(( int )item->type() ) );
303  }
304 }
305 
307 {
308  QgsCptCityColorRampItem *rampItem = mListRamps.at( item->data( Qt::UserRole ).toInt() );
309  if ( rampItem )
310  {
311  buttonBox->button( QDialogButtonBox::Ok )->setEnabled( true );
312  lblSchemeName->setText( QFileInfo( rampItem->name() ).fileName() );
313  mRamp->copy( &rampItem->ramp() );
314  QgsDebugMsg( QString( "variant= %1 - %2 variants" ).arg( mRamp->variantName() ).arg( mRamp->variantList().count() ) );
316  }
317  else
318  {
319  QgsDebugMsg( "invalid item" );
320  }
321 }
322 
324 {
325  if ( mListWidget->selectedItems().count() == 0 )
326  {
327  mRamp->setName( "", "" );
328  }
329 }
330 
332 {
333  QgsDebugMsg( "Entered" );
334  if ( index == 0 )
335  {
338  }
339  else if ( index == 1 )
340  {
343  }
344  else
345  {
346  QgsDebugMsg( QString( "invalid index %1" ).arg( index ) );
349  }
350 
351  mListWidget->blockSignals( true );
352  updateRamp();
353  mListWidget->blockSignals( false );
354 }
355 
356 
358 {
359  QString path, title, copyFile, descFile;
360 
361  // get basic information, depending on if is color ramp or directory
362  QgsCptCityDataItem *item =
363  dynamic_cast< QgsCptCityDataItem* >( mModel->dataItem( mTreeFilter->mapToSource( mTreeView->currentIndex() ) ) );
364  if ( ! item )
365  return;
366 
367  path = item->path();
368  if ( item->type() == QgsCptCityDataItem::Directory )
369  {
370  title = tr( "%1 directory details" ).arg( item->path() );
371  }
372  else if ( item->type() == QgsCptCityColorRampItem::Directory )
373  {
374  title = tr( "%1 gradient details" ).arg( path );
375  }
376  else
377  {
378  return;
379  }
380  copyFile = mArchive->copyingFileName( path );
381  descFile = mArchive->descFileName( path );
382 
383  // prepare dialog
384  QgsDialog dlg( this, 0, QDialogButtonBox::Close );
385  QVBoxLayout *layout = dlg.layout();
386  dlg.setWindowTitle( title );
387  QTextEdit *textEdit = new QTextEdit( &dlg );
388  textEdit->setReadOnly( true );
389  layout->addWidget( textEdit );
390 
391  // add contents of DESC.xml and COPYING.xml
392  QString copyText;
393  if ( ! copyFile.isNull() )
394  {
395  QFile file( copyFile );
396  if ( file.open( QIODevice::ReadOnly | QIODevice::Text ) )
397  {
398  copyText = QString( file.readAll() );
399  file.close();
400  }
401  }
402  QString descText;
403  if ( ! descFile.isNull() )
404  {
405  QFile file( descFile );
406  if ( file.open( QIODevice::ReadOnly | QIODevice::Text ) )
407  {
408  descText = QString( file.readAll() );
409  file.close();
410  }
411  }
412  textEdit->insertPlainText( title + "\n\n" );
413  textEdit->insertPlainText( "===================" );
414  textEdit->insertPlainText( " copying " );
415  textEdit->insertPlainText( "===================\n" );
416  textEdit->insertPlainText( copyText );
417  textEdit->insertPlainText( "\n" );
418  textEdit->insertPlainText( "==================" );
419  textEdit->insertPlainText( " description " );
420  textEdit->insertPlainText( "==================\n" );
421  textEdit->insertPlainText( descText );
422  textEdit->moveCursor( QTextCursor::Start );
423 
424  dlg.resize( 600, 600 );
425  dlg.exec();
426 }
427 
429 {
430  QSize size = lblPreview->size();
431 
432  if ( clear || mRamp->schemeName() == "" )
433  {
434  lblSchemeName->setText( "" );
435  lblSchemePath->setText( "" );
436  lblLicensePreview->setText( "" );
437  QPixmap blankPixmap( size );
438  blankPixmap.fill( Qt::transparent );
439  lblPreview->setPixmap( blankPixmap );
440  return;
441  }
442 
443  mRamp->loadFile();
444 
445  lblSchemePath->setText( mRamp->schemeName() + mRamp->variantName() );
446 
447  // update pixmap
448  // TODO draw checker-board/transparent background
449  // for transparent, add [ pixmap.fill( Qt::transparent ); ] to QgsSymbolLayerV2Utils::colorRampPreviewPixmap
450  QPixmap pixmap = QgsSymbolLayerV2Utils::colorRampPreviewPixmap( mRamp, size );
451  lblPreview->setPixmap( pixmap );
452 
453  // add copyright information from COPYING.xml file
455 }
456 
458 {
459  updateCopyingInfo( QMap< QString, QString >() );
460 }
461 
462 void QgsCptCityColorRampV2Dialog::updateCopyingInfo( const QMap< QString, QString >& copyingMap )
463 {
464  QString authorStr = copyingMap.value( "authors" );
465  if ( authorStr.length() > 80 )
466  authorStr.replace( authorStr.indexOf( " ", 80 ), 1, "\n" );
467  lblAuthorName->setText( authorStr );
468  QString licenseStr = copyingMap.value( "license/informal" );
469  if ( copyingMap.contains( "license/year" ) )
470  licenseStr += " (" + copyingMap.value( "license/year" ) + ")";
471  if ( licenseStr.length() > 80 )
472  licenseStr.replace( licenseStr.indexOf( " ", 80 ), 1, "\n" );
473  if ( copyingMap.contains( "license/url" ) )
474  licenseStr += "\n[ " + copyingMap.value( "license/url" ) + " ]";
475  else
476  licenseStr += "\n";
477  lblLicenseName->setText( licenseStr );
478  licenseStr.replace( "\n", " " );
479  lblLicensePreview->setText( licenseStr );
480  lblLicensePreview->setCursorPosition( 0 );
481  if ( copyingMap.contains( "src/link" ) )
482  lblSrcLink->setText( copyingMap.value( "src/link" ) );
483  else
484  lblSrcLink->setText( "" );
485 }
486 
488 {
489  Q_UNUSED( index );
490  if ( cboVariantName->currentIndex() != -1 )
491  mRamp->setVariantName( cboVariantName->itemData( cboVariantName->currentIndex(), Qt::UserRole ).toString() );
492  QgsDebugMsg( QString( "variant= %1 - %2 variants" ).arg( mRamp->variantName() ).arg( mRamp->variantList().count() ) );
493  updatePreview();
494 }
495 
497 {
498  // save settings
499  QSettings settings;
500  settings.setValue( "/Windows/CptCityColorRampV2Dialog/geometry", saveGeometry() );
501  settings.setValue( "/Windows/CptCityColorRampV2Dialog/splitter", mSplitter->saveState() );
502 }
503 
505 {
506  // show error message to use color ramp manager to get more gradients
507  QString helpText = tr( "You can download a more complete set of cpt-city gradients "
508  "by installing the \"Color Ramp Manager\" plugin "
509  "(you must enable Experimental plugins in the plugin manager).\n\n"
510  );
511  QMessageBox* msg = new QMessageBox( this );
512  msg->setText( helpText );
513  msg->exec();
514 }
515 
517 {
518  QgsDebugMsg( QString( "result: %1 checked: %2" ).arg( result() ).arg( cboConvertStandard->isChecked() ) );
519  // if "save as standard gradient" is checked, convert to QgsVectorGradientColorRampV2
520  return ( result() == Accepted && cboConvertStandard->isChecked() );
521 }
522 
524 {
525  mListWidget->blockSignals( true );
526  mListWidget->clear();
527  mListRamps.clear();
528  QgsCptCityCollectionItem* colItem = dynamic_cast<QgsCptCityCollectionItem*>( item );
529  if ( colItem )
530  {
531  QgsDebugMsg( "path= " + item->path() );
532  // recursively get children ramps
533  QVector<QgsCptCityDataItem*> childrenRamps = colItem->childrenRamps( true );
534  for ( int i = 0; i < childrenRamps.count(); i++ )
535  {
536  QgsCptCityColorRampItem* rampItem = dynamic_cast<QgsCptCityColorRampItem*>( childrenRamps[i] );
537  if ( ! rampItem )
538  {
539  QgsDebugMsg( "invalid item " + childrenRamps[i]->path() );
540  continue;
541  }
542  QListWidgetItem* listItem = new QListWidgetItem();
543  listItem->setText( rampItem->shortInfo() );
544  listItem->setIcon( rampItem->icon( QSize( 75, 50 ) ) );
545  listItem->setToolTip( rampItem->path() + "\n" + rampItem->info() );
546  listItem->setData( Qt::UserRole, QVariant( i ) );
547  mListWidget->addItem( listItem );
548  mListRamps << rampItem;
549  }
550  }
551  else
552  {
553  QgsDebugMsg( "invalid item" );
554  }
555  mListWidget->blockSignals( false );
556 }
557 
558 // this function is for a svg preview, available if the svg files have been processed with svgx
559 // e.g. for f in `ls */*/*/*/*.svg`; do echo $f ; svgx -p -t svg $f > tmp1.svg; mv tmp1.svg $f; done
560 // perhaps a future version of the cpt-city svg gradients will have them by default
561 bool QgsCptCityColorRampV2Dialog::eventFilter( QObject *obj, QEvent *event )
562 {
563  QSize size = lblPreview->size();
564 
565  if ( event->type() == QEvent::MouseButtonPress )
566  {
567  // create preview from svg file if supported - depends on file versions
568  QPixmap pixmap( mRamp->fileName() );
569  if ( ! pixmap.isNull() )
570  lblPreview->setPixmap( pixmap.scaled( size ) );
571  return true;
572  }
573  else if ( event->type() == QEvent::MouseButtonRelease )
574  {
575  // restore preview
576  QPixmap pixmap = QgsSymbolLayerV2Utils::colorRampPreviewPixmap( mRamp, size );
577  lblPreview->setPixmap( pixmap );
578  return true;
579  }
580  else
581  {
582  // standard event processing
583  return QObject::eventFilter( obj, event );
584  }
585 }
586 
588 {
589  QgsDebugMsg( "Entered" );
590  mListWidget->clear();
591  mListRamps.clear();
592  cboVariantName->clear();
594  lblCollectionInfo->clear();
595 
596  buttonBox->button( QDialogButtonBox::Ok )->setEnabled( false );
597  updatePreview( true );
598 
599  QgsDebugMsg( "schemeName= " + mRamp->schemeName() );
600  if ( mRamp->schemeName() == "" )
601  {
602  showAll();
603  return false;
604  }
605 
606  // search for item in model
607  QModelIndex modelIndex = mModel->findPath( mRamp->schemeName() );
608  if ( modelIndex == QModelIndex() )
609  {
610  return false;
611  }
612  QgsCptCityColorRampItem* childItem =
613  dynamic_cast<QgsCptCityColorRampItem*>( mModel->dataItem( modelIndex ) );
614  if ( ! childItem )
615  return false;
616  if ( mRamp->schemeName() != childItem->ramp().schemeName() )
617  return false;
618 
619  // found child, set mRamp variantList
620  // mRamp->copy( &childItem->ramp() );
621  mRamp->setVariantList( childItem->ramp().variantList() );
622 
623  // found child, update tree
624  QgsDebugMsg( QString( "found item %1" ).arg( mRamp->schemeName() ) );
625  lblSchemeName->setText( QFileInfo( mRamp->schemeName() ).fileName() );
626  QModelIndex parentIndex = modelIndex.parent();
627  QModelIndex selIndex = mTreeFilter->mapFromSource( parentIndex );
628 
629  // QgsDebugMsg(QString("parent row=%1 path=%2 parentRow=%3").arg(parentIndex.row()).arg(mModel->dataItem( parentIndex )->path()).arg(parentIndex.parent().row()));
630  mTreeView->setCurrentIndex( selIndex );
631  mTreeView->setExpanded( selIndex, true );
632  mTreeView->scrollTo( selIndex, QAbstractItemView::PositionAtCenter );
633  updateTreeView( mModel->dataItem( parentIndex ), false );
634 
635  // update listWidget, find appropriate item in mListRamps
636  for ( int i = 0; i < mListRamps.count(); i++ )
637  {
638  if ( mListRamps[i] == childItem )
639  {
640  QgsDebugMsg( QString( "found matching item %1 target=%2" ).arg( mListRamps[i]->path() ).arg( childItem->path() ) );
641  QListWidgetItem* listItem = mListWidget->item( i );
642  mListWidget->setCurrentItem( listItem );
643  // on_mListWidget_itemClicked( listItem );
645  mListWidget->scrollToItem( listItem, QAbstractItemView::EnsureVisible );
646  // mListView->selectionModel()->select( childIndex, QItemSelectionModel::Select );
647  buttonBox->button( QDialogButtonBox::Ok )->setEnabled( true );
648  return true;
649  }
650  }
651 
652  return false;
653 }
654 
656 {
657  QModelIndex modelIndex = mModel->findPath( "" );
658  if ( modelIndex != QModelIndex() )
659  {
660  QModelIndex selIndex = mTreeFilter->mapFromSource( modelIndex );
661  mTreeView->setCurrentIndex( selIndex );
662  mTreeView->setExpanded( selIndex, true );
663  mTreeView->scrollTo( selIndex, QAbstractItemView::PositionAtCenter );
664  updateTreeView( mModel->dataItem( modelIndex ), false );
665  }
666 }
667 
669 {
670  QgsDebugMsg( "Entered" );
671  mModel = model;
672 
673  if ( mTreeFilter )
674  delete mTreeFilter;
675  mTreeFilter = new TreeFilterProxyModel( this, mModel );
676  mTreeView->setModel( mTreeFilter );
677 }
678 
679 #if 0
680 void QgsCptCityColorRampV2Dialog::refresh()
681 {
682  QApplication::setOverrideCursor( Qt::WaitCursor );
683  refreshModel( QModelIndex() );
684  QApplication::restoreOverrideCursor();
685 }
686 
687 void QgsCptCityColorRampV2Dialog::refreshModel( const QModelIndex& index )
688 {
689  if ( index.isValid() )
690  {
691  QgsCptCityDataItem *item = mModel->dataItem( index );
692  if ( item )
693  {
694  QgsDebugMsg( "path = " + item->path() );
695  }
696  else
697  {
698  QgsDebugMsg( "invalid item" );
699  }
700  }
701 
702  mModel->refresh( index );
703 
704  for ( int i = 0 ; i < mModel->rowCount( index ); i++ )
705  {
706  QModelIndex idx = mModel->index( i, 0, index );
707  if ( mTreeView->isExpanded( idx ) || !mModel->hasChildren( idx ) )
708  {
709  refreshModel( idx );
710  }
711  }
712 }
713 #endif