[processing] Move recent algorithm log to c++ class

This commit is contained in:
Nyall Dawson 2018-07-04 16:03:49 +10:00
parent d66d1eec1b
commit d232cde514
10 changed files with 315 additions and 0 deletions

@ -0,0 +1,72 @@
/************************************************************************
* This file has been generated automatically from *
* *
* src/gui/processing/qgsprocessingrecentalgorithmlog.h *
* *
* Do not edit manually ! Edit header and run scripts/sipify.pl again *
************************************************************************/
class QgsProcessingRecentAlgorithmLog : QObject
{
%Docstring
A log for tracking recently used processing algorithms.
QgsProcessingRecentAlgorithmLog is not usually directly created, instead
use the instance accessible through :py:func:`QgsGui.processingRecentAlgorithmLog()`
The log contents are saved and restored via QgsSettings.
.. note::
Not stable API
.. versionadded:: 3.4
%End
%TypeHeaderCode
#include "qgsprocessingrecentalgorithmlog.h"
%End
public:
QgsProcessingRecentAlgorithmLog( QObject *parent = 0 );
%Docstring
Constructor for QgsProcessingRecentAlgorithmLog, with the specified
``parent`` object.
%End
QStringList recentAlgorithmIds() const;
%Docstring
Returns a list of the IDs of recently used processing algorithms, where the
first item in the list is the most recently used algorithm.
%End
void push( const QString &id );
%Docstring
Pushes the algorithm with matching ``id`` to the top of the recently used
algorithm list.
If this changes the list of recent algorithm IDs then the changed() signal
will be emitted.
%End
signals:
void changed();
%Docstring
Emitted when the list of recently used algorithms is changed, e.g. when
a new algorithm ID is pushed to the list (see push()).
%End
};
/************************************************************************
* This file has been generated automatically from *
* *
* src/gui/processing/qgsprocessingrecentalgorithmlog.h *
* *
* Do not edit manually ! Edit header and run scripts/sipify.pl again *
************************************************************************/

@ -67,6 +67,13 @@ Returns the global layout item GUI registry, used for registering the GUI behavi
Returns the global processing gui registry, used for registering the GUI behavior of processing algorithms. Returns the global processing gui registry, used for registering the GUI behavior of processing algorithms.
.. versionadded:: 3.2 .. versionadded:: 3.2
%End
static QgsProcessingRecentAlgorithmLog *processingRecentAlgorithmLog();
%Docstring
Returns the global processing recent algorithm log, used for tracking recently used processing algorithms.
.. versionadded:: 3.4
%End %End
static void enableAutoGeometryRestore( QWidget *widget, const QString &key = QString() ); static void enableAutoGeometryRestore( QWidget *widget, const QString &key = QString() );

@ -315,4 +315,5 @@
%Include auto_generated/locator/qgslocatorwidget.sip %Include auto_generated/locator/qgslocatorwidget.sip
%Include auto_generated/processing/qgsprocessingalgorithmconfigurationwidget.sip %Include auto_generated/processing/qgsprocessingalgorithmconfigurationwidget.sip
%Include auto_generated/processing/qgsprocessingalgorithmdialogbase.sip %Include auto_generated/processing/qgsprocessingalgorithmdialogbase.sip
%Include auto_generated/processing/qgsprocessingrecentalgorithmlog.sip
%Include auto_generated/qgsadvanceddigitizingcanvasitem.sip %Include auto_generated/qgsadvanceddigitizingcanvasitem.sip

@ -197,6 +197,7 @@ SET(QGIS_GUI_SRCS
processing/qgsprocessingalgorithmdialogbase.cpp processing/qgsprocessingalgorithmdialogbase.cpp
processing/qgsprocessingconfigurationwidgets.cpp processing/qgsprocessingconfigurationwidgets.cpp
processing/qgsprocessingguiregistry.cpp processing/qgsprocessingguiregistry.cpp
processing/qgsprocessingrecentalgorithmlog.cpp
qgisinterface.cpp qgisinterface.cpp
qgsactionmenu.cpp qgsactionmenu.cpp
@ -717,6 +718,7 @@ SET(QGIS_GUI_MOC_HDRS
processing/qgsprocessingalgorithmconfigurationwidget.h processing/qgsprocessingalgorithmconfigurationwidget.h
processing/qgsprocessingalgorithmdialogbase.h processing/qgsprocessingalgorithmdialogbase.h
processing/qgsprocessingconfigurationwidgets.h processing/qgsprocessingconfigurationwidgets.h
processing/qgsprocessingrecentalgorithmlog.h
) )
SET_PROPERTY(GLOBAL PROPERTY QGIS_GUI_MOC_HDRS ${QGIS_GUI_MOC_HDRS}) SET_PROPERTY(GLOBAL PROPERTY QGIS_GUI_MOC_HDRS ${QGIS_GUI_MOC_HDRS})

@ -0,0 +1,50 @@
/***************************************************************************
qgsprocessingrecentalgorithmlog.cpp
------------------------------------
Date : July 2018
Copyright : (C) 2018 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 "qgsprocessingrecentalgorithmlog.h"
#include "qgssettings.h"
///@cond PRIVATE
const int MAX_LOG_LENGTH = 5;
QgsProcessingRecentAlgorithmLog::QgsProcessingRecentAlgorithmLog( QObject *parent )
: QObject( parent )
{
QgsSettings settings;
mRecentAlgorithmIds = settings.value( QStringLiteral( "processing/recentAlgorithms" ), QVariant(), QgsSettings::Gui ).toStringList();
}
QStringList QgsProcessingRecentAlgorithmLog::recentAlgorithmIds() const
{
return mRecentAlgorithmIds;
}
void QgsProcessingRecentAlgorithmLog::push( const QString &id )
{
const QStringList previous = mRecentAlgorithmIds;
mRecentAlgorithmIds.removeAll( id );
mRecentAlgorithmIds.insert( 0, id );
if ( mRecentAlgorithmIds.length() > MAX_LOG_LENGTH )
mRecentAlgorithmIds = mRecentAlgorithmIds.mid( 0, MAX_LOG_LENGTH );
QgsSettings settings;
settings.setValue( QStringLiteral( "processing/recentAlgorithms" ), mRecentAlgorithmIds, QgsSettings::Gui );
if ( previous != mRecentAlgorithmIds )
emit changed();
}
///@endcond

@ -0,0 +1,79 @@
/***************************************************************************
qgsprocessingrecentalgorithmlog.h
----------------------------------
Date : July 2018
Copyright : (C) 2018 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 QGSPROCESSINGRECENTALGORITHMLOG_H
#define QGSPROCESSINGRECENTALGORITHMLOG_H
#include "qgis.h"
#include "qgis_gui.h"
///@cond NOT_STABLE
/**
* \ingroup gui
* \brief A log for tracking recently used processing algorithms.
*
* QgsProcessingRecentAlgorithmLog is not usually directly created, instead
* use the instance accessible through QgsGui::processingRecentAlgorithmLog().
*
* The log contents are saved and restored via QgsSettings.
*
* \note Not stable API
* \since QGIS 3.4
*/
class GUI_EXPORT QgsProcessingRecentAlgorithmLog : public QObject
{
Q_OBJECT
public:
/**
* Constructor for QgsProcessingRecentAlgorithmLog, with the specified
* \a parent object.
*/
QgsProcessingRecentAlgorithmLog( QObject *parent = nullptr );
/**
* Returns a list of the IDs of recently used processing algorithms, where the
* first item in the list is the most recently used algorithm.
*/
QStringList recentAlgorithmIds() const;
/**
* Pushes the algorithm with matching \a id to the top of the recently used
* algorithm list.
*
* If this changes the list of recent algorithm IDs then the changed() signal
* will be emitted.
*/
void push( const QString &id );
signals:
/**
* Emitted when the list of recently used algorithms is changed, e.g. when
* a new algorithm ID is pushed to the list (see push()).
*/
void changed();
private:
QStringList mRecentAlgorithmIds;
};
///@endcond
#endif // QGSPROCESSINGRECENTALGORITHMLOG_H

@ -32,6 +32,7 @@
#include "qgsshortcutsmanager.h" #include "qgsshortcutsmanager.h"
#include "qgswidgetstatehelper_p.h" #include "qgswidgetstatehelper_p.h"
#include "qgslogger.h" #include "qgslogger.h"
#include "qgsprocessingrecentalgorithmlog.h"
QgsGui *QgsGui::instance() QgsGui *QgsGui::instance()
{ {
@ -79,6 +80,11 @@ QgsProcessingGuiRegistry *QgsGui::processingGuiRegistry()
return instance()->mProcessingGuiRegistry; return instance()->mProcessingGuiRegistry;
} }
QgsProcessingRecentAlgorithmLog *QgsGui::processingRecentAlgorithmLog()
{
return instance()->mProcessingRecentAlgorithmLog;
}
void QgsGui::enableAutoGeometryRestore( QWidget *widget, const QString &key ) void QgsGui::enableAutoGeometryRestore( QWidget *widget, const QString &key )
{ {
if ( widget->objectName().isEmpty() ) if ( widget->objectName().isEmpty() )
@ -91,6 +97,7 @@ void QgsGui::enableAutoGeometryRestore( QWidget *widget, const QString &key )
QgsGui::~QgsGui() QgsGui::~QgsGui()
{ {
delete mProcessingGuiRegistry; delete mProcessingGuiRegistry;
delete mProcessingRecentAlgorithmLog;
delete mLayoutItemGuiRegistry; delete mLayoutItemGuiRegistry;
delete mLayerTreeEmbeddedWidgetRegistry; delete mLayerTreeEmbeddedWidgetRegistry;
delete mEditorWidgetRegistry; delete mEditorWidgetRegistry;
@ -116,5 +123,6 @@ QgsGui::QgsGui()
mSourceSelectProviderRegistry = new QgsSourceSelectProviderRegistry(); mSourceSelectProviderRegistry = new QgsSourceSelectProviderRegistry();
mLayoutItemGuiRegistry = new QgsLayoutItemGuiRegistry(); mLayoutItemGuiRegistry = new QgsLayoutItemGuiRegistry();
mWidgetStateHelper = new QgsWidgetStateHelper(); mWidgetStateHelper = new QgsWidgetStateHelper();
mProcessingRecentAlgorithmLog = new QgsProcessingRecentAlgorithmLog();
mProcessingGuiRegistry = new QgsProcessingGuiRegistry(); mProcessingGuiRegistry = new QgsProcessingGuiRegistry();
} }

@ -31,6 +31,7 @@ class QgsNative;
class QgsLayoutItemGuiRegistry; class QgsLayoutItemGuiRegistry;
class QgsWidgetStateHelper; class QgsWidgetStateHelper;
class QgsProcessingGuiRegistry; class QgsProcessingGuiRegistry;
class QgsProcessingRecentAlgorithmLog;
/** /**
* \ingroup gui * \ingroup gui
@ -96,6 +97,12 @@ class GUI_EXPORT QgsGui
*/ */
static QgsProcessingGuiRegistry *processingGuiRegistry(); static QgsProcessingGuiRegistry *processingGuiRegistry();
/**
* Returns the global processing recent algorithm log, used for tracking recently used processing algorithms.
* \since QGIS 3.4
*/
static QgsProcessingRecentAlgorithmLog *processingRecentAlgorithmLog();
/** /**
* Register the widget to allow its position to be automatically saved and restored when open and closed. * 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. * Use this to avoid needing to call saveGeometry() and restoreGeometry() on your widget.
@ -117,6 +124,7 @@ class GUI_EXPORT QgsGui
QgsMapLayerActionRegistry *mMapLayerActionRegistry = nullptr; QgsMapLayerActionRegistry *mMapLayerActionRegistry = nullptr;
QgsLayoutItemGuiRegistry *mLayoutItemGuiRegistry = nullptr; QgsLayoutItemGuiRegistry *mLayoutItemGuiRegistry = nullptr;
QgsProcessingGuiRegistry *mProcessingGuiRegistry = nullptr; QgsProcessingGuiRegistry *mProcessingGuiRegistry = nullptr;
QgsProcessingRecentAlgorithmLog *mProcessingRecentAlgorithmLog = nullptr;
#ifdef SIP_RUN #ifdef SIP_RUN
QgsGui( const QgsGui &other ); QgsGui( const QgsGui &other );

@ -140,6 +140,7 @@ ADD_PYTHON_TEST(PyQgsPoint test_qgspoint.py)
ADD_PYTHON_TEST(PyQgsPointClusterRenderer test_qgspointclusterrenderer.py) ADD_PYTHON_TEST(PyQgsPointClusterRenderer test_qgspointclusterrenderer.py)
ADD_PYTHON_TEST(PyQgsPointDisplacementRenderer test_qgspointdisplacementrenderer.py) ADD_PYTHON_TEST(PyQgsPointDisplacementRenderer test_qgspointdisplacementrenderer.py)
ADD_PYTHON_TEST(PyQgsPostgresDomain test_qgspostgresdomain.py) ADD_PYTHON_TEST(PyQgsPostgresDomain test_qgspostgresdomain.py)
ADD_PYTHON_TEST(PyQgsProcessingRecentAlgorithmLog test_qgsprocessingrecentalgorithmslog.py)
ADD_PYTHON_TEST(PyQgsProjectionSelectionWidgets test_qgsprojectionselectionwidgets.py) ADD_PYTHON_TEST(PyQgsProjectionSelectionWidgets test_qgsprojectionselectionwidgets.py)
ADD_PYTHON_TEST(PyQgsProjectMetadata test_qgsprojectmetadata.py) ADD_PYTHON_TEST(PyQgsProjectMetadata test_qgsprojectmetadata.py)
ADD_PYTHON_TEST(PyQgsRange test_qgsrange.py) ADD_PYTHON_TEST(PyQgsRange test_qgsrange.py)

@ -0,0 +1,87 @@
# -*- coding: utf-8 -*-
"""QGIS Unit tests for QgsProcessingRecentAlgorithmLog.
.. 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__ = '2018-07'
__copyright__ = 'Copyright 2018, The QGIS Project'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
from qgis.PyQt.QtCore import QCoreApplication
from qgis.core import QgsSettings
from qgis.gui import QgsProcessingRecentAlgorithmLog, QgsGui
from qgis.testing import start_app, unittest
from qgis.PyQt.QtTest import QSignalSpy
start_app()
class TestQgsProcessingRecentAlgorithmLog(unittest.TestCase):
@classmethod
def setUpClass(cls):
"""Run before all tests"""
QCoreApplication.setOrganizationName("QGIS_Test")
QCoreApplication.setOrganizationDomain("QGIS_TestPyQgsNewGeoPackageLayerDialog.com")
QCoreApplication.setApplicationName("QGIS_TestPyQgsNewGeoPackageLayerDialog")
QgsSettings().clear()
def test_log(self):
log = QgsProcessingRecentAlgorithmLog()
self.assertFalse(log.recentAlgorithmIds())
spy = QSignalSpy(log.changed)
log.push('test')
self.assertEqual(log.recentAlgorithmIds(), ['test'])
self.assertEqual(len(spy), 1)
log.push('test')
self.assertEqual(log.recentAlgorithmIds(), ['test'])
self.assertEqual(len(spy), 1)
log.push('test2')
self.assertEqual(log.recentAlgorithmIds(), ['test2', 'test'])
self.assertEqual(len(spy), 2)
log.push('test')
self.assertEqual(log.recentAlgorithmIds(), ['test', 'test2'])
self.assertEqual(len(spy), 3)
log.push('test3')
self.assertEqual(log.recentAlgorithmIds(), ['test3', 'test', 'test2'])
self.assertEqual(len(spy), 4)
log.push('test4')
self.assertEqual(log.recentAlgorithmIds(), ['test4', 'test3', 'test', 'test2'])
self.assertEqual(len(spy), 5)
log.push('test5')
self.assertEqual(log.recentAlgorithmIds(), ['test5', 'test4', 'test3', 'test', 'test2'])
self.assertEqual(len(spy), 6)
log.push('test6')
self.assertEqual(log.recentAlgorithmIds(), ['test6', 'test5', 'test4', 'test3', 'test'])
self.assertEqual(len(spy), 7)
log.push('test3')
self.assertEqual(log.recentAlgorithmIds(), ['test3', 'test6', 'test5', 'test4', 'test'])
self.assertEqual(len(spy), 8)
log.push('test3')
self.assertEqual(log.recentAlgorithmIds(), ['test3', 'test6', 'test5', 'test4', 'test'])
self.assertEqual(len(spy), 8)
# test that log has been saved to QgsSettings
log2 = QgsProcessingRecentAlgorithmLog()
self.assertEqual(log2.recentAlgorithmIds(), ['test3', 'test6', 'test5', 'test4', 'test'])
def test_gui_instance(self):
self.assertIsNotNone(QgsGui.instance().processingRecentAlgorithmLog())
if __name__ == '__main__':
unittest.main()