diff --git a/python/core/auto_generated/qgsdataitemproviderregistry.sip.in b/python/core/auto_generated/qgsdataitemproviderregistry.sip.in index 4ee4e537971..96c81ec5fd4 100644 --- a/python/core/auto_generated/qgsdataitemproviderregistry.sip.in +++ b/python/core/auto_generated/qgsdataitemproviderregistry.sip.in @@ -34,17 +34,19 @@ QgsDataItemProviderRegistry is not usually directly created, but rather accessed QList providers() const; %Docstring -Gets list of available providers +Returns the list of available providers. %End void addProvider( QgsDataItemProvider *provider /Transfer/ ); %Docstring -Add a provider implementation. Takes ownership of the object. +Adds a ``provider`` implementation to the registry. Ownership of the provider +is transferred to the registry. %End void removeProvider( QgsDataItemProvider *provider ); %Docstring -Remove provider implementation from the list (provider object is deleted) +Removes a ``provider`` implementation from the registry. +The provider object is automatically deleted. %End private: diff --git a/python/gui/auto_generated/qgsdataitemguiprovider.sip.in b/python/gui/auto_generated/qgsdataitemguiprovider.sip.in new file mode 100644 index 00000000000..192295ec32e --- /dev/null +++ b/python/gui/auto_generated/qgsdataitemguiprovider.sip.in @@ -0,0 +1,44 @@ +/************************************************************************ + * This file has been generated automatically from * + * * + * src/gui/qgsdataitemguiprovider.h * + * * + * Do not edit manually ! Edit header and run scripts/sipify.pl again * + ************************************************************************/ + + + + +class QgsDataItemGuiProvider +{ +%Docstring + +Abstract base class for providers which affect how QgsDataItem items behave +within the application GUI. + +Providers must be registered via QgsDataItemGuiProviderRegistry. + +.. versionadded:: 3.6 +%End + +%TypeHeaderCode +#include "qgsdataitemguiprovider.h" +%End + public: + + virtual ~QgsDataItemGuiProvider(); + + virtual QString name() = 0; +%Docstring +Returns the provider's name. +%End + +}; + +/************************************************************************ + * This file has been generated automatically from * + * * + * src/gui/qgsdataitemguiprovider.h * + * * + * Do not edit manually ! Edit header and run scripts/sipify.pl again * + ************************************************************************/ diff --git a/python/gui/auto_generated/qgsdataitemguiproviderregistry.sip.in b/python/gui/auto_generated/qgsdataitemguiproviderregistry.sip.in new file mode 100644 index 00000000000..3c54c0d8846 --- /dev/null +++ b/python/gui/auto_generated/qgsdataitemguiproviderregistry.sip.in @@ -0,0 +1,61 @@ +/************************************************************************ + * This file has been generated automatically from * + * * + * src/gui/qgsdataitemguiproviderregistry.h * + * * + * Do not edit manually ! Edit header and run scripts/sipify.pl again * + ************************************************************************/ + + + + +class QgsDataItemGuiProviderRegistry +{ +%Docstring +This class keeps a list of data item GUI providers that may affect how QgsDataItems +behave within the application GUI. + +QgsDataItemGuiProviderRegistry is not usually directly created, but rather accessed through +QgsGui.instance()->dataItemGuiProviderRegistry(). + +.. versionadded:: 3.6 +%End + +%TypeHeaderCode +#include "qgsdataitemguiproviderregistry.h" +%End + public: + + QgsDataItemGuiProviderRegistry(); + + ~QgsDataItemGuiProviderRegistry(); + + + QList providers() const; +%Docstring +Returns the list of available providers. +%End + + void addProvider( QgsDataItemGuiProvider *provider /Transfer/ ); +%Docstring +Adds a ``provider`` implementation to the registry. Ownership of the provider +is transferred to the registry. +%End + + void removeProvider( QgsDataItemGuiProvider *provider ); +%Docstring +Removes a ``provider`` implementation from the registry. +The provider object is automatically deleted. +%End + + private: + QgsDataItemGuiProviderRegistry( const QgsDataItemGuiProviderRegistry &rh ); +}; + +/************************************************************************ + * This file has been generated automatically from * + * * + * src/gui/qgsdataitemguiproviderregistry.h * + * * + * Do not edit manually ! Edit header and run scripts/sipify.pl again * + ************************************************************************/ diff --git a/python/gui/auto_generated/qgsgui.sip.in b/python/gui/auto_generated/qgsgui.sip.in index 1ac8edd1fb4..6e310187382 100644 --- a/python/gui/auto_generated/qgsgui.sip.in +++ b/python/gui/auto_generated/qgsgui.sip.in @@ -74,6 +74,14 @@ Returns the global processing gui registry, used for registering the GUI behavio Returns the global processing recent algorithm log, used for tracking recently used processing algorithms. .. versionadded:: 3.4 +%End + + static QgsDataItemGuiProviderRegistry *dataItemGuiProviderRegistry(); +%Docstring +Returns the global data item GUI provider registry, used for tracking providers which affect the browser +GUI. + +.. versionadded:: 3.6 %End static void enableAutoGeometryRestore( QWidget *widget, const QString &key = QString() ); diff --git a/python/gui/gui_auto.sip b/python/gui/gui_auto.sip index fed01fb6f7c..1e952467c33 100644 --- a/python/gui/gui_auto.sip +++ b/python/gui/gui_auto.sip @@ -1,5 +1,7 @@ // Include auto-generated SIP files %Include auto_generated/qgsattributeforminterface.sip +%Include auto_generated/qgsdataitemguiprovider.sip +%Include auto_generated/qgsdataitemguiproviderregistry.sip %Include auto_generated/qgsdetaileditemdata.sip %Include auto_generated/qgsexpressionbuilderdialog.sip %Include auto_generated/qgsgeometryrubberband.sip diff --git a/src/core/qgsdataitemproviderregistry.h b/src/core/qgsdataitemproviderregistry.h index 270225dceac..538cdf491c0 100644 --- a/src/core/qgsdataitemproviderregistry.h +++ b/src/core/qgsdataitemproviderregistry.h @@ -46,13 +46,21 @@ class CORE_EXPORT QgsDataItemProviderRegistry //! QgsDataItemProviderRegistry cannot be copied. QgsDataItemProviderRegistry &operator=( const QgsDataItemProviderRegistry &rh ) = delete; - //! Gets list of available providers + /** + * Returns the list of available providers. + */ QList providers() const { return mProviders; } - //! Add a provider implementation. Takes ownership of the object. + /** + * Adds a \a provider implementation to the registry. Ownership of the provider + * is transferred to the registry. + */ void addProvider( QgsDataItemProvider *provider SIP_TRANSFER ); - //! Remove provider implementation from the list (provider object is deleted) + /** + * Removes a \a provider implementation from the registry. + * The provider object is automatically deleted. + */ void removeProvider( QgsDataItemProvider *provider ); private: @@ -60,7 +68,7 @@ class CORE_EXPORT QgsDataItemProviderRegistry QgsDataItemProviderRegistry( const QgsDataItemProviderRegistry &rh ); #endif - //! available providers. this class owns the pointers + //! Available providers, owned by this class QList mProviders; }; diff --git a/src/gui/CMakeLists.txt b/src/gui/CMakeLists.txt index 7d006bc59c0..3602090d004 100644 --- a/src/gui/CMakeLists.txt +++ b/src/gui/CMakeLists.txt @@ -243,6 +243,8 @@ SET(QGIS_GUI_SRCS qgscredentialdialog.cpp qgscustomdrophandler.cpp qgscurveeditorwidget.cpp + qgsdataitemguiprovider.cpp + qgsdataitemguiproviderregistry.cpp qgsdatumtransformdialog.cpp qgsdatasourceselectdialog.cpp qgsdetaileditemdata.cpp @@ -767,6 +769,8 @@ ENDIF(MSVC) SET(QGIS_GUI_HDRS qgsattributeforminterface.h qgsattributeformlegacyinterface.h + qgsdataitemguiprovider.h + qgsdataitemguiproviderregistry.h qgsdetaileditemdata.h qgsexpressionbuilderdialog.h qgsgeometryrubberband.h diff --git a/src/gui/qgsdataitemguiprovider.cpp b/src/gui/qgsdataitemguiprovider.cpp new file mode 100644 index 00000000000..c4afbe9a2fa --- /dev/null +++ b/src/gui/qgsdataitemguiprovider.cpp @@ -0,0 +1,18 @@ +/*************************************************************************** + qgsdataitemguiprovider.cpp + -------------------------------------- + Date : October 2018 + Copyright : (C) 2018 by Nyall Dawson + Email : nyall dot dawson at gmail dot com + *************************************************************************** + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + ***************************************************************************/ + +#include "qgsdataitemguiprovider.h" + +// no implementation currently diff --git a/src/gui/qgsdataitemguiprovider.h b/src/gui/qgsdataitemguiprovider.h new file mode 100644 index 00000000000..18ab8b4e927 --- /dev/null +++ b/src/gui/qgsdataitemguiprovider.h @@ -0,0 +1,47 @@ +/*************************************************************************** + qgsdataitemguiprovider.h + -------------------------------------- + Date : October 2018 + Copyright : (C) 2018 by Nyall Dawson + Email : nyall dot dawson at gmail dot com + *************************************************************************** + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + ***************************************************************************/ + +#ifndef QGSDATAITEMGUIPROVIDER_H +#define QGSDATAITEMGUIPROVIDER_H + +#include "qgis_gui.h" + +class QString; + +/** + * \class QgsDataItemGuiProvider + * \ingroup gui + * + * Abstract base class for providers which affect how QgsDataItem items behave + * within the application GUI. + * + * Providers must be registered via QgsDataItemGuiProviderRegistry. + * + * \since QGIS 3.6 + */ +class GUI_EXPORT QgsDataItemGuiProvider +{ + public: + + virtual ~QgsDataItemGuiProvider() = default; + + /** + * Returns the provider's name. + */ + virtual QString name() = 0; + +}; + +#endif // QGSDATAITEMGUIPROVIDER_H diff --git a/src/gui/qgsdataitemguiproviderregistry.cpp b/src/gui/qgsdataitemguiproviderregistry.cpp new file mode 100644 index 00000000000..f12dc568b90 --- /dev/null +++ b/src/gui/qgsdataitemguiproviderregistry.cpp @@ -0,0 +1,38 @@ +/*************************************************************************** + qgsdataitemguiproviderregistry.cpp + -------------------------------------- + Date : October 2018 + Copyright : (C) 2018 by Nyall Dawson + Email : nyall dot dawson at gmail dot com + *************************************************************************** + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + ***************************************************************************/ + +#include "qgsdataitemguiproviderregistry.h" +#include "qgsdataitemguiprovider.h" + +QgsDataItemGuiProviderRegistry::QgsDataItemGuiProviderRegistry() +{ +} + +QgsDataItemGuiProviderRegistry::~QgsDataItemGuiProviderRegistry() +{ + qDeleteAll( mProviders ); +} + +void QgsDataItemGuiProviderRegistry::addProvider( QgsDataItemGuiProvider *provider ) +{ + mProviders.append( provider ); +} + +void QgsDataItemGuiProviderRegistry::removeProvider( QgsDataItemGuiProvider *provider ) +{ + int index = mProviders.indexOf( provider ); + if ( index >= 0 ) + delete mProviders.takeAt( index ); +} diff --git a/src/gui/qgsdataitemguiproviderregistry.h b/src/gui/qgsdataitemguiproviderregistry.h new file mode 100644 index 00000000000..f8b2ff62415 --- /dev/null +++ b/src/gui/qgsdataitemguiproviderregistry.h @@ -0,0 +1,76 @@ +/*************************************************************************** + qgsdataitemguiproviderregistry.h + -------------------------------------- + Date : October 2018 + Copyright : (C) 2018 by Nyall Dawson + Email : nyall dot dawson at gmail dot com + *************************************************************************** + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + ***************************************************************************/ + +#ifndef QGSDATAITEMGUIPROVIDERREGISTRY_H +#define QGSDATAITEMGUIPROVIDERREGISTRY_H + +#include "qgis_gui.h" +#include "qgis_sip.h" +#include + +class QgsDataItemGuiProvider; + +/** + * \class QgsDataItemGuiProviderRegistry + * \ingroup gui + * This class keeps a list of data item GUI providers that may affect how QgsDataItems + * behave within the application GUI. + * + * QgsDataItemGuiProviderRegistry is not usually directly created, but rather accessed through + * QgsGui::instance()->dataItemGuiProviderRegistry(). + * + * \since QGIS 3.6 + */ +class GUI_EXPORT QgsDataItemGuiProviderRegistry +{ + public: + + QgsDataItemGuiProviderRegistry(); + + ~QgsDataItemGuiProviderRegistry(); + + //! QgsDataItemGuiProviderRegistry cannot be copied. + QgsDataItemGuiProviderRegistry( const QgsDataItemGuiProviderRegistry &rh ) = delete; + //! QgsDataItemGuiProviderRegistry cannot be copied. + QgsDataItemGuiProviderRegistry &operator=( const QgsDataItemGuiProviderRegistry &rh ) = delete; + + /** + * Returns the list of available providers. + */ + QList providers() const { return mProviders; } + + /** + * Adds a \a provider implementation to the registry. Ownership of the provider + * is transferred to the registry. + */ + void addProvider( QgsDataItemGuiProvider *provider SIP_TRANSFER ); + + /** + * Removes a \a provider implementation from the registry. + * The provider object is automatically deleted. + */ + void removeProvider( QgsDataItemGuiProvider *provider ); + + private: +#ifdef SIP_RUN + QgsDataItemGuiProviderRegistry( const QgsDataItemGuiProviderRegistry &rh ); +#endif + + //! Available providers, owned by this class + QList mProviders; + +}; + +#endif // QGSDATAITEMGUIPROVIDERREGISTRY_H diff --git a/src/gui/qgsgui.cpp b/src/gui/qgsgui.cpp index d9cb507d824..1c792518097 100644 --- a/src/gui/qgsgui.cpp +++ b/src/gui/qgsgui.cpp @@ -43,6 +43,7 @@ #include "qgsprocessingrecentalgorithmlog.h" #include "qgswindowmanagerinterface.h" #include "qgssettings.h" +#include "qgsdataitemguiproviderregistry.h" QgsGui *QgsGui::instance() { @@ -95,6 +96,11 @@ QgsProcessingRecentAlgorithmLog *QgsGui::processingRecentAlgorithmLog() return instance()->mProcessingRecentAlgorithmLog; } +QgsDataItemGuiProviderRegistry *QgsGui::dataItemGuiProviderRegistry() +{ + return instance()->mDataItemGuiProviderRegistry; +} + void QgsGui::enableAutoGeometryRestore( QWidget *widget, const QString &key ) { if ( widget->objectName().isEmpty() ) @@ -130,6 +136,7 @@ QgsGui::HigFlags QgsGui::higFlags() QgsGui::~QgsGui() { delete mProcessingGuiRegistry; + delete mDataItemGuiProviderRegistry; delete mProcessingRecentAlgorithmLog; delete mLayoutItemGuiRegistry; delete mLayerTreeEmbeddedWidgetRegistry; @@ -168,4 +175,5 @@ QgsGui::QgsGui() mWidgetStateHelper = new QgsWidgetStateHelper(); mProcessingRecentAlgorithmLog = new QgsProcessingRecentAlgorithmLog(); mProcessingGuiRegistry = new QgsProcessingGuiRegistry(); + mDataItemGuiProviderRegistry = new QgsDataItemGuiProviderRegistry(); } diff --git a/src/gui/qgsgui.h b/src/gui/qgsgui.h index 779339f66dd..7206116c77d 100644 --- a/src/gui/qgsgui.h +++ b/src/gui/qgsgui.h @@ -34,6 +34,7 @@ class QgsWidgetStateHelper; class QgsProcessingGuiRegistry; class QgsProcessingRecentAlgorithmLog; class QgsWindowManagerInterface; +class QgsDataItemGuiProviderRegistry; /** * \ingroup gui @@ -105,6 +106,13 @@ class GUI_EXPORT QgsGui */ static QgsProcessingRecentAlgorithmLog *processingRecentAlgorithmLog(); + /** + * Returns the global data item GUI provider registry, used for tracking providers which affect the browser + * GUI. + * \since QGIS 3.6 + */ + static QgsDataItemGuiProviderRegistry *dataItemGuiProviderRegistry(); + /** * Register the widget to allow its position to be automatically saved and restored when open and closed. * Use this to avoid needing to call saveGeometry() and restoreGeometry() on your widget. @@ -158,6 +166,7 @@ class GUI_EXPORT QgsGui QgsLayoutItemGuiRegistry *mLayoutItemGuiRegistry = nullptr; QgsProcessingGuiRegistry *mProcessingGuiRegistry = nullptr; QgsProcessingRecentAlgorithmLog *mProcessingRecentAlgorithmLog = nullptr; + QgsDataItemGuiProviderRegistry *mDataItemGuiProviderRegistry = nullptr; std::unique_ptr< QgsWindowManagerInterface > mWindowManager; #ifdef SIP_RUN diff --git a/tests/src/python/CMakeLists.txt b/tests/src/python/CMakeLists.txt index 1d78fe816da..de110c46e42 100644 --- a/tests/src/python/CMakeLists.txt +++ b/tests/src/python/CMakeLists.txt @@ -34,6 +34,7 @@ ADD_PYTHON_TEST(PyQgsCoordinateTransformContext test_qgscoordinatetransformconte ADD_PYTHON_TEST(PyQgsDefaultValue test_qgsdefaultvalue.py) ADD_PYTHON_TEST(PyQgsXmlUtils test_qgsxmlutils.py) ADD_PYTHON_TEST(PyQgsCoordinateTransform test_qgscoordinatetransform.py) +ADD_PYTHON_TEST(PyQgsDataItemGuiProviderRegistry test_qgsdataitemguiproviderregistry.py) ADD_PYTHON_TEST(PyQgsDataItemProviderRegistry test_qgsdataitemproviderregistry.py) ADD_PYTHON_TEST(PyQgsDateTimeEdit test_qgsdatetimeedit.py) ADD_PYTHON_TEST(PyQgsDateTimeStatisticalSummary test_qgsdatetimestatisticalsummary.py) diff --git a/tests/src/python/test_qgsdataitemguiproviderregistry.py b/tests/src/python/test_qgsdataitemguiproviderregistry.py new file mode 100644 index 00000000000..eff0158984b --- /dev/null +++ b/tests/src/python/test_qgsdataitemguiproviderregistry.py @@ -0,0 +1,70 @@ +# -*- coding: utf-8 -*- +"""QGIS Unit tests for QgsDataItemGuiProviderRegistry + +.. note:: This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. +""" +__author__ = 'Nyall Dawson' +__date__ = '27/10/2018' +__copyright__ = 'Copyright 2018, The QGIS Project' +# This will get replaced with a git SHA1 when you do a git archive +__revision__ = '$Format:%H$' + +import qgis # NOQA + +from qgis.gui import (QgsGui, + QgsDataItemGuiProvider, + QgsDataItemGuiProviderRegistry) +from qgis.testing import start_app, unittest + +app = start_app() + + +class TestProvider(QgsDataItemGuiProvider): + + def __init__(self, name): + super().__init__() + self._name = name + + def name(self): + return self._name + + +class TestQgsDataItemGuiProviderRegistry(unittest.TestCase): + + def testAppRegistry(self): + # ensure there is an application instance + self.assertIsNotNone(QgsGui.dataItemGuiProviderRegistry()) + + def testRegistry(self): + registry = QgsDataItemGuiProviderRegistry() + initial_providers = registry.providers() + + # add a new provider + p1 = TestProvider('p1') + registry.addProvider(p1) + self.assertIn(p1, registry.providers()) + + p2 = TestProvider('p2') + registry.addProvider(p2) + self.assertIn(p1, registry.providers()) + self.assertIn(p2, registry.providers()) + + registry.removeProvider(None) + p3 = TestProvider('p3') + # not in registry yet + registry.removeProvider(p3) + + registry.removeProvider(p1) + self.assertNotIn('p1', [p.name() for p in registry.providers()]) + self.assertIn(p2, registry.providers()) + + registry.removeProvider(p2) + self.assertNotIn('p2', [p.name() for p in registry.providers()]) + self.assertEqual(registry.providers(), initial_providers) + + +if __name__ == '__main__': + unittest.main() diff --git a/tests/src/python/test_qgsdataitemproviderregistry.py b/tests/src/python/test_qgsdataitemproviderregistry.py index f476c297422..f65f6d62ac9 100644 --- a/tests/src/python/test_qgsdataitemproviderregistry.py +++ b/tests/src/python/test_qgsdataitemproviderregistry.py @@ -73,7 +73,7 @@ class TestQgsDataItemProviderRegistry(unittest.TestCase): registry.removeProvider(p2) self.assertNotIn('p2', [p.name() for p in registry.providers()]) self.assertEqual(registry.providers(), initial_providers) - + if __name__ == '__main__': unittest.main()