Skip to content

Commit

Permalink
Use message bar for messages when performing actions to geopackages
Browse files Browse the repository at this point in the history
through browser instead of message boxes
  • Loading branch information
nyalldawson committed Nov 21, 2020
1 parent 13951b2 commit 5e7b500
Show file tree
Hide file tree
Showing 3 changed files with 104 additions and 79 deletions.
5 changes: 0 additions & 5 deletions src/core/providers/ogr/qgsgeopackagedataitems.cpp
Expand Up @@ -15,11 +15,6 @@
#include "qgsgeopackagedataitems.h"
///@cond PRIVATE

#include <QAction>
#include <QMessageBox>
#include <QFileDialog>
#include <QInputDialog>

#include "qgssqliteutils.h"
#include "qgsgeopackagedataitems.h"
#include "qgsogrdbconnection.h"
Expand Down
164 changes: 96 additions & 68 deletions src/gui/providers/ogr/qgsgeopackageitemguiprovider.cpp
Expand Up @@ -38,6 +38,7 @@
#include "qgsogrdataitems.h"
#include "qgsogrdbconnection.h"
#include "qgsgeopackageproviderconnection.h"
#include "qgsmessagebar.h"

void QgsGeoPackageItemGuiProvider::populateContextMenu( QgsDataItem *item, QMenu *menu,
const QList<QgsDataItem *> &,
Expand All @@ -50,13 +51,14 @@ void QgsGeoPackageItemGuiProvider::populateContextMenu( QgsDataItem *item, QMenu
{
QAction *actionRenameLayer = new QAction( tr( "Rename Layer '%1'…" ).arg( layerItem->name() ), this );
QVariantMap data;
data.insert( QStringLiteral( "uri" ), layerItem->uri() );
data.insert( QStringLiteral( "key" ), layerItem->providerKey() );
data.insert( QStringLiteral( "tableNames" ), layerItem->tableNames() );
data.insert( QStringLiteral( "item" ), QVariant::fromValue( QPointer< QgsDataItem >( layerItem ) ) );
data.insert( QStringLiteral( "context" ), QVariant::fromValue( context ) );
actionRenameLayer->setData( data );
connect( actionRenameLayer, &QAction::triggered, this, &QgsGeoPackageItemGuiProvider::renameVectorLayer );
const QString uri = layerItem->uri();
const QString providerKey = layerItem->providerKey();
const QStringList tableNames = layerItem->tableNames();
QPointer< QgsDataItem > itemPointer( layerItem );
connect( actionRenameLayer, &QAction::triggered, this, [this, uri, providerKey, tableNames, itemPointer, context ]
{
renameVectorLayer( uri, providerKey, tableNames, itemPointer, context );
} );
menu->addAction( actionRenameLayer );
}
}
Expand All @@ -68,10 +70,11 @@ void QgsGeoPackageItemGuiProvider::populateContextMenu( QgsDataItem *item, QMenu
menu->addAction( actionNew );

QAction *actionCreateDatabase = new QAction( tr( "Create Database…" ), rootItem->parent() );
QVariantMap data;
data.insert( QStringLiteral( "item" ), QVariant::fromValue( QPointer< QgsGeoPackageRootItem >( rootItem ) ) );
actionCreateDatabase->setData( data );
connect( actionCreateDatabase, &QAction::triggered, this, &QgsGeoPackageItemGuiProvider::createDatabase );
QPointer< QgsGeoPackageRootItem > rootItemPointer( rootItem );
connect( actionCreateDatabase, &QAction::triggered, this, [this, rootItemPointer ]
{
createDatabase( rootItemPointer );
} );
menu->addAction( actionCreateDatabase );
}

Expand All @@ -97,32 +100,33 @@ void QgsGeoPackageItemGuiProvider::populateContextMenu( QgsDataItem *item, QMenu

QString message = QObject::tr( "Delete %1…" ).arg( collectionItem->name() );
QAction *actionDelete = new QAction( message, collectionItem->parent() );
QVariantMap dataDelete;
dataDelete.insert( QStringLiteral( "path" ), collectionItem->path() );
dataDelete.insert( QStringLiteral( "name" ), collectionItem->name() );
dataDelete.insert( QStringLiteral( "parent" ), QVariant::fromValue( QPointer< QgsDataItem >( collectionItem->parent() ) ) );
actionDelete->setData( dataDelete );
connect( actionDelete, &QAction::triggered, this, &QgsGeoPackageItemGuiProvider::deleteGpkg );
QString collectionPath = collectionItem->path();
QString collectionName = collectionItem->name();
QPointer< QgsDataItem > parent( collectionItem->parent() );
connect( actionDelete, &QAction::triggered, this, [this, collectionPath, collectionName, parent, context ]()
{
deleteGpkg( collectionPath, collectionName, parent, context );
} );
menu->addAction( actionDelete );

// Run VACUUM
QAction *actionVacuumDb = new QAction( tr( "Compact Database (VACUUM)" ), collectionItem->parent() );
QVariantMap dataVacuum;
dataVacuum.insert( QStringLiteral( "name" ), collectionItem->name() );
dataVacuum.insert( QStringLiteral( "path" ), collectionItem->path() );
const QString name = collectionItem->name();
const QString path = collectionItem->path();
actionVacuumDb->setData( dataVacuum );
connect( actionVacuumDb, &QAction::triggered, this, &QgsGeoPackageItemGuiProvider::vacuum );
connect( actionVacuumDb, &QAction::triggered, this, [this, context, name, path]
{
vacuum( path, name, context );
} );
menu->addAction( actionVacuumDb );
}
}

void QgsGeoPackageItemGuiProvider::deleteGpkg()
void QgsGeoPackageItemGuiProvider::deleteGpkg( const QString &itemPath, const QString &name, QPointer< QgsDataItem > parent, const QgsDataItemGuiContext &context )
{
QAction *s = qobject_cast<QAction *>( sender() );
QVariantMap data = s->data().toMap();
const QString path = data[QStringLiteral( "path" )].toString().remove( QStringLiteral( "gpkg:/" ) );
const QString name = data[QStringLiteral( "name" )].toString();
QPointer< QgsDataItem > parent = data[QStringLiteral( "parent" )].value<QPointer< QgsDataItem >>();
QString path = itemPath;
path = path.remove( QStringLiteral( "gpkg:/" ) );
if ( parent )
{
const QString title = QObject::tr( "Delete GeoPackage" );
Expand All @@ -148,11 +152,17 @@ void QgsGeoPackageItemGuiProvider::deleteGpkg()

if ( !QFile::remove( path ) )
{
QMessageBox::warning( nullptr, title, tr( "Could not delete GeoPackage." ) );
if ( context.messageBar() )
context.messageBar()->pushMessage( title, tr( "Could not delete GeoPackage." ), Qgis::Critical );
else
QMessageBox::warning( nullptr, title, tr( "Could not delete GeoPackage." ) );
}
else
{
QMessageBox::information( nullptr, title, tr( "GeoPackage deleted successfully." ) );
if ( context.messageBar() )
context.messageBar()->pushMessage( title, tr( "GeoPackage deleted successfully." ), Qgis::Success );
else
QMessageBox::information( nullptr, title, tr( "GeoPackage deleted successfully." ) );
// If the deleted file was a stored connection, remove it too
if ( ! name.isEmpty() )
{
Expand All @@ -172,13 +182,17 @@ void QgsGeoPackageItemGuiProvider::deleteGpkg()
}
else
{
QMessageBox::warning( nullptr, title, QObject::tr( "The GeoPackage '%1' cannot be deleted because it is in the current project as '%2',"
" remove it from the project and retry." ).arg( path, projectLayer->name() ) );
if ( context.messageBar() )
context.messageBar()->pushMessage( title, QObject::tr( "The GeoPackage '%1' cannot be deleted because it is in the current project as '%2',"
" remove it from the project and retry." ).arg( path, projectLayer->name() ), Qgis::Critical );
else
QMessageBox::warning( nullptr, title, QObject::tr( "The GeoPackage '%1' cannot be deleted because it is in the current project as '%2',"
" remove it from the project and retry." ).arg( path, projectLayer->name() ) );
}
}
}

bool QgsGeoPackageItemGuiProvider::rename( QgsDataItem *item, const QString &newName, QgsDataItemGuiContext )
bool QgsGeoPackageItemGuiProvider::rename( QgsDataItem *item, const QString &newName, QgsDataItemGuiContext context )
{
if ( QgsGeoPackageVectorLayerItem *layerItem = qobject_cast< QgsGeoPackageVectorLayerItem * >( item ) )
{
Expand Down Expand Up @@ -243,30 +257,33 @@ bool QgsGeoPackageItemGuiProvider::rename( QgsDataItem *item, const QString &new
errCause = ex.what();
}
}
if ( errCause.isEmpty() && context.messageBar() )
{
context.messageBar()->pushMessage( tr( "Rename Layer" ), tr( "The layer <b>%1</b> was successfully renamed." ).arg( oldName ), Qgis::Success );
}
}

if ( ! errCause.isEmpty() )
QMessageBox::critical( nullptr, QObject::tr( "Error renaming layer" ), errCause );
{
if ( context.messageBar() )
context.messageBar()->pushMessage( QObject::tr( "Error renaming layer" ), errCause, Qgis::Critical );
else
QMessageBox::critical( nullptr, QObject::tr( "Error renaming layer" ), errCause );
}
else if ( layerItem->parent() )
{
layerItem->parent()->refreshConnections();
}

return errCause.isEmpty();
}

return false;
}

void QgsGeoPackageItemGuiProvider::renameVectorLayer()
void QgsGeoPackageItemGuiProvider::renameVectorLayer( const QString &uri, const QString &key, const QStringList &tableNames,
QPointer< QgsDataItem > item, const QgsDataItemGuiContext &context )
{
QAction *s = qobject_cast<QAction *>( sender() );
QVariantMap data = s->data().toMap();
const QString uri = data[QStringLiteral( "uri" )].toString();
const QString key = data[QStringLiteral( "key" )].toString();
// Collect existing table names
const QStringList tableNames = data[QStringLiteral( "tableNames" )].toStringList();
QPointer< QgsDataItem > item = data[QStringLiteral( "item" )].value<QPointer< QgsDataItem >>();
QgsDataItemGuiContext context = data[QStringLiteral( "context" )].value< QgsDataItemGuiContext >();

// Get layer name from layer URI
QVariantMap pieces( QgsProviderRegistry::instance()->decodeUri( key, uri ) );
QString layerName = pieces[QStringLiteral( "layerName" )].toString();
Expand All @@ -285,7 +302,7 @@ void QgsGeoPackageItemGuiProvider::renameVectorLayer()
}


bool QgsGeoPackageItemGuiProvider::deleteLayer( QgsLayerItem *layerItem, QgsDataItemGuiContext )
bool QgsGeoPackageItemGuiProvider::deleteLayer( QgsLayerItem *layerItem, QgsDataItemGuiContext context )
{
if ( QgsGeoPackageAbstractLayerItem *item = qobject_cast< QgsGeoPackageAbstractLayerItem * >( layerItem ) )
{
Expand Down Expand Up @@ -316,7 +333,10 @@ bool QgsGeoPackageItemGuiProvider::deleteLayer( QgsLayerItem *layerItem, QgsData
bool res = item->executeDeleteLayer( errCause );
if ( !res )
{
QMessageBox::warning( nullptr, tr( "Delete Layer" ), errCause );
if ( context.messageBar() )
context.messageBar()->pushMessage( tr( "Delete Layer" ), errCause, Qgis::Critical );
else
QMessageBox::warning( nullptr, tr( "Delete Layer" ), errCause );
}
else
{
Expand All @@ -327,12 +347,15 @@ bool QgsGeoPackageItemGuiProvider::deleteLayer( QgsLayerItem *layerItem, QgsData
if ( QMessageBox::question( nullptr, QObject::tr( "Delete Layer" ), QObject::tr( "The layer <b>%1</b> was successfully deleted."
" Compact database (VACUUM) <b>%2</b> now?" ).arg( item->name(), connectionParentItem->name() ), QMessageBox::Yes | QMessageBox::No, QMessageBox::No ) == QMessageBox::Yes )
{
vacuumGeoPackageDbAction( connectionParentItem->path(), connectionParentItem->name() );
vacuumGeoPackageDbAction( connectionParentItem->path(), connectionParentItem->name(), context );
}
}
else
{
QMessageBox::information( nullptr, tr( "Delete Layer" ), tr( "The layer <b>%1</b> was successfully deleted." ).arg( item->name() ) );
if ( context.messageBar() )
context.messageBar()->pushMessage( tr( "Delete Layer" ), tr( "The layer <b>%1</b> was successfully deleted." ).arg( item->name() ), Qgis::Success );
else
QMessageBox::information( nullptr, tr( "Delete Layer" ), tr( "The layer <b>%1</b> was successfully deleted." ).arg( item->name() ) );
}
if ( item->parent() )
item->parent()->refreshConnections();
Expand All @@ -346,31 +369,29 @@ bool QgsGeoPackageItemGuiProvider::deleteLayer( QgsLayerItem *layerItem, QgsData
}
}

void QgsGeoPackageItemGuiProvider::vacuumGeoPackageDbAction( const QString &path, const QString &name )
void QgsGeoPackageItemGuiProvider::vacuumGeoPackageDbAction( const QString &path, const QString &name, const QgsDataItemGuiContext &context )
{
Q_UNUSED( path )
QString errCause;
bool result = QgsGeoPackageCollectionItem::vacuumGeoPackageDb( name, path, errCause );
if ( !result || !errCause.isEmpty() )
{
QMessageBox::warning( nullptr, tr( "Database compact (VACUUM)" ), errCause );
if ( context.messageBar() )
context.messageBar()->pushMessage( tr( "Database compact (VACUUM)" ), errCause, Qgis::Critical );
else
QMessageBox::warning( nullptr, tr( "Database compact (VACUUM)" ), errCause );
}
}

void QgsGeoPackageItemGuiProvider::vacuum()
void QgsGeoPackageItemGuiProvider::vacuum( const QString &itemPath, const QString &name, const QgsDataItemGuiContext &context )
{
QAction *s = qobject_cast<QAction *>( sender() );
QVariantMap data = s->data().toMap();
const QString path = data[QStringLiteral( "path" )].toString().remove( QStringLiteral( "gpkg:/" ) );
const QString name = data[QStringLiteral( "name" )].toString();
vacuumGeoPackageDbAction( path, name );
QString path = itemPath;
path = path.remove( QStringLiteral( "gpkg:/" ) );
vacuumGeoPackageDbAction( path, name, context );
}

void QgsGeoPackageItemGuiProvider::createDatabase()
void QgsGeoPackageItemGuiProvider::createDatabase( QPointer< QgsGeoPackageRootItem > item )
{
QAction *s = qobject_cast<QAction *>( sender() );
QVariantMap data = s->data().toMap();
QPointer< QgsGeoPackageRootItem > item = data[QStringLiteral( "item" )].value<QPointer< QgsGeoPackageRootItem >>();
if ( item )
{
QgsNewGeoPackageLayerDialog dialog( nullptr );
Expand All @@ -395,18 +416,17 @@ bool QgsGeoPackageItemGuiProvider::acceptDrop( QgsDataItem *item, QgsDataItemGui
return false;
}

bool QgsGeoPackageItemGuiProvider::handleDrop( QgsDataItem *item, QgsDataItemGuiContext, const QMimeData *data, Qt::DropAction )
bool QgsGeoPackageItemGuiProvider::handleDrop( QgsDataItem *item, QgsDataItemGuiContext context, const QMimeData *data, Qt::DropAction )
{
if ( QgsGeoPackageCollectionItem *collectionItem = qobject_cast< QgsGeoPackageCollectionItem * >( item ) )
{
return handleDropGeopackage( collectionItem, data );
return handleDropGeopackage( collectionItem, data, context );
}
return false;
}

bool QgsGeoPackageItemGuiProvider::handleDropGeopackage( QgsGeoPackageCollectionItem *item, const QMimeData *data )
bool QgsGeoPackageItemGuiProvider::handleDropGeopackage( QgsGeoPackageCollectionItem *item, const QMimeData *data, const QgsDataItemGuiContext &context )
{

if ( !QgsMimeDataUtils::isUriList( data ) )
return false;

Expand Down Expand Up @@ -478,8 +498,12 @@ bool QgsGeoPackageItemGuiProvider::handleDropGeopackage( QgsGeoPackageCollection

if ( exists && !isVector )
{
QMessageBox::warning( nullptr, tr( "Cannot Overwrite Layer" ),
tr( "Destination layer <b>%1</b> already exists. Overwriting with raster layers is not currently supported." ).arg( dropUri.name ) );
if ( context.messageBar() )
context.messageBar()->pushMessage( tr( "Cannot Overwrite Layer" ),
tr( "Destination layer <b>%1</b> already exists. Overwriting with raster layers is not currently supported." ).arg( dropUri.name ), Qgis::Critical );
else
QMessageBox::warning( nullptr, tr( "Cannot Overwrite Layer" ),
tr( "Destination layer <b>%1</b> already exists. Overwriting with raster layers is not currently supported." ).arg( dropUri.name ) );
}
else if ( ! exists || QMessageBox::question( nullptr, tr( "Overwrite Layer" ),
tr( "Destination layer <b>%1</b> already exists. Do you want to overwrite it?" ).arg( dropUri.name ), QMessageBox::Yes | QMessageBox::No ) == QMessageBox::Yes )
Expand All @@ -498,8 +522,10 @@ bool QgsGeoPackageItemGuiProvider::handleDropGeopackage( QgsGeoPackageCollection
// when export is successful:
connect( exportTask, &QgsVectorLayerExporterTask::exportComplete, item, [ = ]()
{
// this is gross - TODO - find a way to get access to messageBar from data items
QMessageBox::information( nullptr, tr( "Import to GeoPackage database" ), tr( "Import was successful." ) );
if ( context.messageBar() )
context.messageBar()->pushMessage( tr( "Import to GeoPackage database" ), tr( "Import was successful." ), Qgis::Success );
else
QMessageBox::information( nullptr, tr( "Import to GeoPackage database" ), tr( "Import was successful." ) );
item->refreshConnections();
} );

Expand All @@ -524,8 +550,10 @@ bool QgsGeoPackageItemGuiProvider::handleDropGeopackage( QgsGeoPackageCollection
// when export is successful:
connect( exportTask, &QgsGeoPackageRasterWriterTask::writeComplete, item, [ = ]()
{
// this is gross - TODO - find a way to get access to messageBar from data items
QMessageBox::information( nullptr, tr( "Import to GeoPackage database" ), tr( "Import was successful." ) );
if ( context.messageBar() )
context.messageBar()->pushMessage( tr( "Import to GeoPackage database" ), tr( "Import was successful." ), Qgis::Success );
else
QMessageBox::information( nullptr, tr( "Import to GeoPackage database" ), tr( "Import was successful." ) );
item->refreshConnections();
} );

Expand Down
14 changes: 8 additions & 6 deletions src/gui/providers/ogr/qgsgeopackageitemguiprovider.h
Expand Up @@ -26,6 +26,7 @@
#define SIP_NO_FILE

class QgsGeoPackageCollectionItem;
class QgsGeoPackageRootItem;

class QgsGeoPackageItemGuiProvider : public QObject, public QgsDataItemGuiProvider
{
Expand All @@ -49,15 +50,16 @@ class QgsGeoPackageItemGuiProvider : public QObject, public QgsDataItemGuiProvid
const QMimeData *data,
Qt::DropAction action ) override;
private:
bool handleDropGeopackage( QgsGeoPackageCollectionItem *item, const QMimeData *data );
bool handleDropGeopackage( QgsGeoPackageCollectionItem *item, const QMimeData *data, const QgsDataItemGuiContext &context );
//! Compacts (VACUUM) a geopackage database
void vacuumGeoPackageDbAction( const QString &path, const QString &name );
void createDatabase( );
void vacuumGeoPackageDbAction( const QString &path, const QString &name, const QgsDataItemGuiContext &context );
void createDatabase( QPointer< QgsGeoPackageRootItem > item );

protected slots:
void vacuum();
void renameVectorLayer();
void deleteGpkg();
void vacuum( const QString &path, const QString &name, const QgsDataItemGuiContext &context );
void renameVectorLayer( const QString &uri, const QString &key, const QStringList &tableNames,
QPointer< QgsDataItem > item, const QgsDataItemGuiContext &context );
void deleteGpkg( const QString &itemPath, const QString &name, QPointer<QgsDataItem> parent, const QgsDataItemGuiContext &context );
};

///@endcond
Expand Down

0 comments on commit 5e7b500

Please sign in to comment.