QGIS API Documentation  2.7.0-Master
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
qgsbrowsermodel.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsbrowsermodel.cpp
3  ---------------------
4  begin : July 2011
5  copyright : (C) 2011 by Martin Dobias
6  email : wonder dot sk at gmail dot 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 #include <QDir>
16 #include <QApplication>
17 #include <QStyle>
18 #include <QtConcurrentMap>
19 
20 #include "qgis.h"
21 #include "qgsapplication.h"
22 #include "qgsdataprovider.h"
23 #include "qgsmimedatautils.h"
24 #include "qgslogger.h"
25 #include "qgsproviderregistry.h"
26 
27 #include "qgsbrowsermodel.h"
28 #include "qgsproject.h"
29 
30 #include <QSettings>
31 
33  : mFinished( false )
34  , mItem( item )
35 {
36  connect( &mFutureWatcher, SIGNAL( finished() ), SLOT( finished() ) );
37 }
38 
40 {
41  mFutureWatcher.cancel();
42 }
43 
44 void QgsBrowserWatcher::setFuture( QFuture<QVector <QgsDataItem*> > future )
45 {
46  mFutureWatcher.setFuture( future );
47 }
48 
50 {
51  QgsDebugMsg( "Entered" );
52  emit finished( mItem, mFutureWatcher.result() );
53  mFinished = true;
54 }
55 
56 // sort function for QList<QgsDataItem*>, e.g. sorted/grouped provider listings
58 {
59  return QString::localeAwareCompare( a->name(), b->name() ) < 0;
60 }
61 
63  : QAbstractItemModel( parent )
64  , mFavourites( 0 )
65  , mProjectHome( 0 )
66 {
67  connect( QgsProject::instance(), SIGNAL( readProject( const QDomDocument & ) ), this, SLOT( updateProjectHome() ) );
68  connect( QgsProject::instance(), SIGNAL( writeProject( QDomDocument & ) ), this, SLOT( updateProjectHome() ) );
69  mLoadingMovie.setFileName( QgsApplication::iconPath( "/mIconLoading.gif" ) );
70  mLoadingMovie.setCacheMode( QMovie::CacheAll );
71  connect( &mLoadingMovie, SIGNAL( frameChanged( int ) ), SLOT( loadingFrameChanged() ) );
72  addRootItems();
73 }
74 
76 {
78 }
79 
81 {
82  QString home = QgsProject::instance()->homePath();
83  if ( mProjectHome && mProjectHome->path() == home )
84  return;
85 
86  int idx = mRootItems.indexOf( mProjectHome );
87 
88  // using layoutAboutToBeChanged() was messing expanded items
89  if ( idx >= 0 )
90  {
91  beginRemoveRows( QModelIndex(), idx, idx );
92  mRootItems.remove( idx );
93  endRemoveRows();
94  }
95  delete mProjectHome;
96  mProjectHome = home.isNull() ? 0 : new QgsDirectoryItem( NULL, tr( "Project home" ), home, "project:" + home );
97  if ( mProjectHome )
98  {
100 
101  beginInsertRows( QModelIndex(), 0, 0 );
102  mRootItems.insert( 0, mProjectHome );
103  endInsertRows();
104  }
105 }
106 
108 {
110 
111  // give the home directory a prominent second place
112  QgsDirectoryItem *item = new QgsDirectoryItem( NULL, tr( "Home" ), QDir::homePath(), "home:" + QDir::homePath() );
113  QStyle *style = QApplication::style();
114  QIcon homeIcon( style->standardPixmap( QStyle::SP_DirHomeIcon ) );
115  item->setIcon( homeIcon );
116  connectItem( item );
117  mRootItems << item;
118 
119  // add favourite directories
120  mFavourites = new QgsFavouritesItem( NULL, tr( "Favourites" ) );
121  if ( mFavourites )
122  {
125  }
126 
127  // add drives
128  foreach ( QFileInfo drive, QDir::drives() )
129  {
130  QString path = drive.absolutePath();
131  QgsDirectoryItem *item = new QgsDirectoryItem( NULL, path, path );
132 
133  connectItem( item );
134  mRootItems << item;
135  }
136 
137 #ifdef Q_WS_MAC
138  QString path = QString( "/Volumes" );
139  QgsDirectoryItem *vols = new QgsDirectoryItem( NULL, path, path );
140  connectItem( vols );
141  mRootItems << vols;
142 #endif
143 
144  // Add non file top level items
145  QStringList providersList = QgsProviderRegistry::instance()->providerList();
146 
147  // container for displaying providers as sorted groups (by QgsDataProvider::DataCapability enum)
148  QMap<int, QgsDataItem *> providerMap;
149 
150  foreach ( QString key, providersList )
151  {
152  QLibrary *library = QgsProviderRegistry::instance()->providerLibrary( key );
153  if ( !library )
154  continue;
155 
156  dataCapabilities_t * dataCapabilities = ( dataCapabilities_t * ) cast_to_fptr( library->resolve( "dataCapabilities" ) );
157  if ( !dataCapabilities )
158  {
159  QgsDebugMsg( library->fileName() + " does not have dataCapabilities" );
160  continue;
161  }
162 
163  int capabilities = dataCapabilities();
164  if ( capabilities == QgsDataProvider::NoDataCapabilities )
165  {
166  QgsDebugMsg( library->fileName() + " does not have any dataCapabilities" );
167  continue;
168  }
169 
170  dataItem_t *dataItem = ( dataItem_t * ) cast_to_fptr( library->resolve( "dataItem" ) );
171  if ( !dataItem )
172  {
173  QgsDebugMsg( library->fileName() + " does not have dataItem" );
174  continue;
175  }
176 
177  QgsDataItem *item = dataItem( "", NULL ); // empty path -> top level
178  if ( item )
179  {
180  QgsDebugMsg( "Add new top level item : " + item->name() );
181  connectItem( item );
182  providerMap.insertMulti( capabilities, item );
183  }
184  }
185 
186  // add as sorted groups by QgsDataProvider::DataCapability enum
187  foreach ( int key, providerMap.uniqueKeys() )
188  {
189  QList<QgsDataItem *> providerGroup = providerMap.values( key );
190  if ( providerGroup.size() > 1 )
191  {
192  qSort( providerGroup.begin(), providerGroup.end(), cmpByDataItemName_ );
193  }
194 
195  foreach ( QgsDataItem * ditem, providerGroup )
196  {
197  mRootItems << ditem;
198  }
199  }
200 }
201 
203 {
204  foreach ( QgsDataItem* item, mRootItems )
205  {
206  delete item;
207  }
208 
209  mRootItems.clear();
210 }
211 
212 
213 Qt::ItemFlags QgsBrowserModel::flags( const QModelIndex & index ) const
214 {
215  if ( !index.isValid() )
216  return 0;
217 
218  Qt::ItemFlags flags = Qt::ItemIsEnabled | Qt::ItemIsSelectable;
219 
220  QgsDataItem* ptr = ( QgsDataItem* ) index.internalPointer();
221  if ( ptr->type() == QgsDataItem::Layer )
222  {
223  flags |= Qt::ItemIsDragEnabled;
224  }
225  if ( ptr->acceptDrop() )
226  flags |= Qt::ItemIsDropEnabled;
227  return flags;
228 }
229 
230 QVariant QgsBrowserModel::data( const QModelIndex &index, int role ) const
231 {
232  if ( !index.isValid() )
233  return QVariant();
234 
235  QgsDataItem *item = dataItem( index );
236  if ( !item )
237  {
238  return QVariant();
239  }
240  else if ( role == Qt::DisplayRole )
241  {
242  return item->name();
243  }
244  else if ( role == Qt::ToolTipRole )
245  {
246  return item->toolTip();
247  }
248  else if ( role == Qt::DecorationRole && index.column() == 0 )
249  {
250  if ( fetching( item ) )
251  {
252  return mLoadingIcon;
253  }
254  return item->icon();
255  }
256  else
257  {
258  // unsupported role
259  return QVariant();
260  }
261 }
262 
263 QVariant QgsBrowserModel::headerData( int section, Qt::Orientation orientation, int role ) const
264 {
265  Q_UNUSED( section );
266  if ( orientation == Qt::Horizontal && role == Qt::DisplayRole )
267  {
268  return QVariant( "header" );
269  }
270 
271  return QVariant();
272 }
273 
274 int QgsBrowserModel::rowCount( const QModelIndex &parent ) const
275 {
276  //QgsDebugMsg(QString("isValid = %1 row = %2 column = %3").arg(parent.isValid()).arg(parent.row()).arg(parent.column()));
277 
278  if ( !parent.isValid() )
279  {
280  // root item: its children are top level items
281  return mRootItems.count(); // mRoot
282  }
283  else
284  {
285  // ordinary item: number of its children
286  QgsDataItem *item = dataItem( parent );
287  //if ( item ) QgsDebugMsg(QString("path = %1 rowCount = %2").arg(item->path()).arg(item->rowCount()) );
288  return item ? item->rowCount() : 0;
289  }
290 }
291 
292 bool QgsBrowserModel::hasChildren( const QModelIndex &parent ) const
293 {
294  if ( !parent.isValid() )
295  return true; // root item: its children are top level items
296 
297  QgsDataItem *item = dataItem( parent );
298  return item && item->hasChildren();
299 }
300 
301 int QgsBrowserModel::columnCount( const QModelIndex &parent ) const
302 {
303  Q_UNUSED( parent );
304  return 1;
305 }
306 
307 QModelIndex QgsBrowserModel::findPath( QString path, Qt::MatchFlag matchFlag )
308 {
309  QModelIndex theIndex; // starting from root
310  bool foundChild = true;
311 
312  while ( foundChild )
313  {
314  foundChild = false; // assume that the next child item will not be found
315 
316  for ( int i = 0; i < rowCount( theIndex ); i++ )
317  {
318  QModelIndex idx = index( i, 0, theIndex );
319  QgsDataItem *item = dataItem( idx );
320  if ( !item )
321  return QModelIndex(); // an error occurred
322 
323  if ( item->path() == path )
324  {
325  QgsDebugMsg( "Arrived " + item->path() );
326  return idx; // we have found the item we have been looking for
327  }
328 
329  // paths are slash separated identifier
330  if ( path.startsWith( item->path() + "/" ) )
331  {
332  foundChild = true;
333  theIndex = idx;
334  break;
335  }
336  }
337  }
338 
339  if ( matchFlag == Qt::MatchStartsWith )
340  return theIndex;
341 
342  QgsDebugMsg( "path not found" );
343  return QModelIndex(); // not found
344 }
345 
347 {
348  beginResetModel();
349  removeRootItems();
350  addRootItems();
351  endResetModel();
352 }
353 
354 QModelIndex QgsBrowserModel::index( int row, int column, const QModelIndex &parent ) const
355 {
356  QgsDataItem *p = dataItem( parent );
357  const QVector<QgsDataItem*> &items = p ? p->children() : mRootItems;
358  QgsDataItem *item = items.value( row, 0 );
359  return item ? createIndex( row, column, item ) : QModelIndex();
360 }
361 
362 QModelIndex QgsBrowserModel::parent( const QModelIndex &index ) const
363 {
364  QgsDataItem *item = dataItem( index );
365  if ( !item )
366  return QModelIndex();
367 
368  return findItem( item->parent() );
369 }
370 
371 QModelIndex QgsBrowserModel::findItem( QgsDataItem *item, QgsDataItem *parent ) const
372 {
373  const QVector<QgsDataItem*> &items = parent ? parent->children() : mRootItems;
374 
375  for ( int i = 0; i < items.size(); i++ )
376  {
377  if ( items[i] == item )
378  return createIndex( i, 0, item );
379 
380  QModelIndex childIndex = findItem( item, items[i] );
381  if ( childIndex.isValid() )
382  return childIndex;
383  }
384 
385  return QModelIndex();
386 }
387 
388 void QgsBrowserModel::beginInsertItems( QgsDataItem *parent, int first, int last )
389 {
390  QgsDebugMsgLevel( "parent mPath = " + parent->path(), 3 );
391  QModelIndex idx = findItem( parent );
392  if ( !idx.isValid() )
393  return;
394  QgsDebugMsgLevel( "valid", 3 );
395  beginInsertRows( idx, first, last );
396  QgsDebugMsgLevel( "end", 3 );
397 }
399 {
400  QgsDebugMsgLevel( "Entered", 3 );
401  endInsertRows();
402 }
403 void QgsBrowserModel::beginRemoveItems( QgsDataItem *parent, int first, int last )
404 {
405  QgsDebugMsgLevel( "parent mPath = " + parent->path(), 3 );
406  QModelIndex idx = findItem( parent );
407  if ( !idx.isValid() )
408  return;
409  beginRemoveRows( idx, first, last );
410 }
412 {
413  QgsDebugMsgLevel( "Entered", 3 );
414  endRemoveRows();
415 }
417 {
418  connect( item, SIGNAL( beginInsertItems( QgsDataItem*, int, int ) ),
419  this, SLOT( beginInsertItems( QgsDataItem*, int, int ) ) );
420  connect( item, SIGNAL( endInsertItems() ),
421  this, SLOT( endInsertItems() ) );
422  connect( item, SIGNAL( beginRemoveItems( QgsDataItem*, int, int ) ),
423  this, SLOT( beginRemoveItems( QgsDataItem*, int, int ) ) );
424  connect( item, SIGNAL( endRemoveItems() ),
425  this, SLOT( endRemoveItems() ) );
426 }
427 
428 QStringList QgsBrowserModel::mimeTypes() const
429 {
430  QStringList types;
431  // In theory the mime type convention is: application/x-vnd.<vendor>.<application>.<type>
432  // but it seems a bit over formalized. Would be an application/x-qgis-uri better?
433  types << "application/x-vnd.qgis.qgis.uri";
434  return types;
435 }
436 
437 QMimeData * QgsBrowserModel::mimeData( const QModelIndexList &indexes ) const
438 {
440  foreach ( const QModelIndex &index, indexes )
441  {
442  if ( index.isValid() )
443  {
444  QgsDataItem* ptr = ( QgsDataItem* ) index.internalPointer();
445  if ( ptr->type() != QgsDataItem::Layer ) continue;
446  QgsLayerItem *layer = ( QgsLayerItem* ) ptr;
447  lst.append( QgsMimeDataUtils::Uri( layer ) );
448  }
449  }
450  return QgsMimeDataUtils::encodeUriList( lst );
451 }
452 
453 bool QgsBrowserModel::dropMimeData( const QMimeData * data, Qt::DropAction action, int row, int column, const QModelIndex & parent )
454 {
455  Q_UNUSED( row );
456  Q_UNUSED( column );
457 
458  QgsDataItem* destItem = dataItem( parent );
459  if ( !destItem )
460  {
461  QgsDebugMsg( "DROP PROBLEM!" );
462  return false;
463  }
464 
465  return destItem->handleDrop( data, action );
466 }
467 
468 QgsDataItem *QgsBrowserModel::dataItem( const QModelIndex &idx ) const
469 {
470  void *v = idx.internalPointer();
471  QgsDataItem *d = reinterpret_cast<QgsDataItem*>( v );
472  Q_ASSERT( !v || d );
473  return d;
474 }
475 
476 bool QgsBrowserModel::canFetchMore( const QModelIndex & parent ) const
477 {
478  QgsDataItem* item = dataItem( parent );
479  // if ( item )
480  // QgsDebugMsg( QString( "path = %1 canFetchMore = %2" ).arg( item->path() ).arg( item && ! item->isPopulated() ) );
481  return ( item && ! item->isPopulated() );
482 }
483 
484 void QgsBrowserModel::fetchMore( const QModelIndex & parent )
485 {
486  QgsDebugMsg( "Entered" );
487  QgsDataItem* item = dataItem( parent );
488 
489  if ( !item || fetching( item ) )
490  return;
491 
492  QgsDebugMsg( "path = " + item->path() );
493 
494  if ( item->isPopulated() )
495  return;
496 
497  QList<QgsDataItem*> itemList;
498  itemList << item;
499  QgsBrowserWatcher * watcher = new QgsBrowserWatcher( item );
500  connect( watcher, SIGNAL( finished( QgsDataItem*, QVector <QgsDataItem*> ) ), SLOT( childrenCreated( QgsDataItem*, QVector <QgsDataItem*> ) ) );
501  watcher->setFuture( QtConcurrent::mapped( itemList, QgsBrowserModel::createChildren ) );
502  mWatchers.append( watcher );
503  mLoadingMovie.setPaused( false );
504  emit dataChanged( parent, parent );
505 }
506 
507 /* Refresh dir path */
508 void QgsBrowserModel::refresh( QString path )
509 {
510  QModelIndex index = findPath( path );
511  refresh( index );
512 }
513 
514 /* Refresh item */
515 void QgsBrowserModel::refresh( const QModelIndex& theIndex )
516 {
517  QgsDataItem *item = dataItem( theIndex );
518  if ( !item )
519  return;
520 
521  QgsDebugMsg( "Refresh " + item->path() );
522 
523  QList<QgsDataItem*> itemList;
524  itemList << item;
525  QgsBrowserWatcher * watcher = new QgsBrowserWatcher( item );
526  connect( watcher, SIGNAL( finished( QgsDataItem*, QVector <QgsDataItem*> ) ), SLOT( refreshChildrenCreated( QgsDataItem*, QVector <QgsDataItem*> ) ) );
527  watcher->setFuture( QtConcurrent::mapped( itemList, QgsBrowserModel::createChildren ) );
528  mWatchers.append( watcher );
529  mLoadingMovie.setPaused( false );
530  emit dataChanged( theIndex, theIndex );
531 }
532 
533 // This is expected to be run in a separate thread
534 QVector<QgsDataItem*> QgsBrowserModel::createChildren( QgsDataItem* item )
535 {
536  QgsDebugMsg( "Entered" );
537  QTime time;
538  time.start();
539  QVector <QgsDataItem*> children = item->createChildren();
540  QgsDebugMsg( QString( "%1 children created in %2 ms" ).arg( children.size() ).arg( time.elapsed() ) );
541  // Children objects must be pushed to main thread.
542  foreach ( QgsDataItem* child, children )
543  {
544  if ( !child ) // should not happen
545  continue;
546  // However it seems to work without resetting parent, the Qt doc says that
547  // "The object cannot be moved if it has a parent."
548  QgsDebugMsg( "moveToThread child" + child->path() );
549  child->setParent( 0 );
550  child->moveToThread( QApplication::instance()->thread() );
551  child->setParent( item );
552  }
553  return children;
554 }
555 
556 void QgsBrowserModel::childrenCreated( QgsDataItem* item, QVector <QgsDataItem*> children )
557 {
558  QgsDebugMsg( QString( "children.size() = %1" ).arg( children.size() ) );
559  QModelIndex index = findItem( item );
560  if ( !index.isValid() ) // check if item still exists
561  return;
562  item->populate( children );
563  emit dataChanged( index, index );
564  emit fetchFinished( index );
565 }
566 
567 void QgsBrowserModel::refreshChildrenCreated( QgsDataItem* item, QVector <QgsDataItem*> children )
568 {
569  QgsDebugMsg( QString( "path = %1 children.size() = %2" ).arg( item->path() ).arg( children.size() ) );
570  QModelIndex index = findItem( item );
571  if ( !index.isValid() ) // check if item still exists
572  return;
573  item->refresh( children );
574  emit dataChanged( index, index );
575 }
576 
578 {
579  foreach ( QgsBrowserWatcher * watcher, mWatchers )
580  {
581  if ( !watcher->isFinished() && watcher->item() == item )
582  return true;
583  }
584  return false;
585 }
586 
588 {
589  mLoadingIcon = QIcon( mLoadingMovie.currentPixmap() );
590  int notFinished = 0;
591  foreach ( QgsBrowserWatcher * watcher, mWatchers )
592  {
593  if ( watcher->isFinished() )
594  {
595  delete watcher;
596  mWatchers.removeOne( watcher );
597  continue;
598  }
599  QModelIndex index = findItem( watcher->item() );
600  QgsDebugMsg( QString( "path = %1 not finished" ).arg( watcher->item()->path() ) );
601  emit dataChanged( index, index );
602  notFinished++;
603  }
604  if ( notFinished == 0 )
605  mLoadingMovie.setPaused( true );
606 }
607 
609 {
610  Q_ASSERT( mFavourites );
611  mFavourites->addDirectory( favDir );
612 }
613 
614 void QgsBrowserModel::removeFavourite( const QModelIndex &index )
615 {
616  QgsDirectoryItem *item = dynamic_cast<QgsDirectoryItem *>( dataItem( index ) );
617  if ( !item )
618  return;
619 
620  mFavourites->removeDirectory( item );
621 }
void childrenCreated(QgsDataItem *item, QVector< QgsDataItem * > items)
virtual Qt::ItemFlags flags(const QModelIndex &index) const
Used by other components to obtain information about each item provided by the model.
Contains various Favourites directories.
Definition: qgsdataitem.h:319
static unsigned index
bool hasChildren(const QModelIndex &parent=QModelIndex()) const
void removeDirectory(QgsDirectoryItem *item)
static bool cmpByDataItemName_(QgsDataItem *a, QgsDataItem *b)
virtual int columnCount(const QModelIndex &parent=QModelIndex()) const
Provides the number of columns of data exposed by the model.
virtual void refresh()
QVector< QgsDataItem * > children() const
Definition: qgsdataitem.h:131
QString name() const
Definition: qgsdataitem.h:133
QgsDataItem * parent() const
Definition: qgsdataitem.h:129
virtual void populate()
static QgsProviderRegistry * instance(QString pluginPath=QString::null)
means of accessing canonical single instance
#define QgsDebugMsg(str)
Definition: qgslogger.h:33
static QString iconPath(QString iconFile)
Returns path to the desired icon file.
void addDirectory(QString favIcon)
void removeFavourite(const QModelIndex &index)
virtual bool handleDrop(const QMimeData *, Qt::DropAction)
Definition: qgsdataitem.h:99
QgsFavouritesItem * mFavourites
void beginRemoveItems(QgsDataItem *parent, int first, int last)
virtual QIcon icon()
void fetchMore(const QModelIndex &parent)
void connectItem(QgsDataItem *item)
virtual QVariant headerData(int section, Qt::Orientation orientation, int role=Qt::DisplayRole) const
Provides views with information to show in their headers.
virtual int rowCount(const QModelIndex &parent=QModelIndex()) const
Provides the number of rows of data exposed by the model.
QgsDataItem * item() const
QString homePath() const
Return project's home path.
void setIcon(QIcon icon)
Definition: qgsdataitem.h:140
QStringList providerList() const
Return list of available providers by their keys.
QgsDirectoryItem * mProjectHome
bool isPopulated()
Definition: qgsdataitem.h:72
virtual bool dropMimeData(const QMimeData *data, Qt::DropAction action, int row, int column, const QModelIndex &parent)
Handles the data supplied by a drag and drop operation that ended with the given action.
QgsBrowserModel(QObject *parent=0)
#define QgsDebugMsgLevel(str, level)
Definition: qgslogger.h:34
static QVector< QgsDataItem * > createChildren(QgsDataItem *item)
QgsDataItem * dataItem(const QModelIndex &idx) const
QModelIndex findPath(QString path, Qt::MatchFlag matchFlag=Qt::MatchExactly)
Return index of item with given path.
bool canFetchMore(const QModelIndex &parent) const
QString path() const
Definition: qgsdataitem.h:134
Type type() const
Definition: qgsdataitem.h:128
QgsBrowserWatcher(QgsDataItem *item)
bool hasChildren()
virtual QModelIndex parent(const QModelIndex &index) const
Returns the parent of the model item with the given index.
virtual QModelIndex index(int row, int column, const QModelIndex &parent=QModelIndex()) const
Returns the index of the item in the model specified by the given row, column and parent index...
A directory: contains subdirectories and layers.
Definition: qgsdataitem.h:247
QModelIndex findItem(QgsDataItem *item, QgsDataItem *parent=0) const
static QMimeData * encodeUriList(UriList layers)
base class for all items in the model
Definition: qgsdataitem.h:39
QLibrary * providerLibrary(const QString &providerKey) const
void beginInsertItems(QgsDataItem *parent, int first, int last)
void refreshChildrenCreated(QgsDataItem *item, QVector< QgsDataItem * > items)
virtual QStringList mimeTypes() const
Returns a list of mime that can describe model indexes.
void refresh(QString path)
static QgsProject * instance()
access to canonical QgsProject instance
Definition: qgsproject.cpp:362
void setParent(QgsDataItem *parent)
Definition: qgsdataitem.h:130
virtual QMimeData * mimeData(const QModelIndexList &indexes) const
Returns an object that contains serialized items of data corresponding to the list of indexes specifi...
bool fetching(QgsDataItem *item) const
virtual QVector< QgsDataItem * > createChildren()
Item that represents a layer that can be opened with one of the providers.
Definition: qgsdataitem.h:180
void fetchFinished(const QModelIndex &index)
Emitted when item children fetch was finished.
QgsDataItem * dataItem_t(QString, QgsDataItem *)
Definition: qgsdataitem.h:35
void(*)() cast_to_fptr(void *p)
Definition: qgis.h:298
QString toolTip() const
Definition: qgsdataitem.h:144
virtual bool acceptDrop()
Definition: qgsdataitem.h:96
int dataCapabilities_t()
QList< Uri > UriList
virtual QVariant data(const QModelIndex &index, int role=Qt::DisplayRole) const
Used to supply item data to views and delegates.
void setFuture(QFuture< QVector< QgsDataItem * > > future)
#define tr(sourceText)
QVector< QgsDataItem * > mRootItems
void addFavouriteDirectory(QString favDir)