Skip to content

Commit

Permalink
[annotations] Add framework for map tools for creating new annotation
Browse files Browse the repository at this point in the history
items
  • Loading branch information
nyalldawson committed Sep 8, 2021
1 parent 3a082f5 commit 01226a3
Show file tree
Hide file tree
Showing 10 changed files with 298 additions and 16 deletions.
Expand Up @@ -68,6 +68,13 @@ Returns an icon representing creation of the annotation item type.
virtual QgsAnnotationItemBaseWidget *createItemWidget( QgsAnnotationItem *item ) /TransferBack/;
%Docstring
Creates a configuration widget for an ``item`` of this type. Can return ``None`` if no configuration GUI is required.
%End

virtual QgsCreateAnnotationItemMapTool *createMapTool( QgsMapCanvas *canvas, QgsAdvancedDigitizingDockWidget *cadDockWidget ) /TransferBack/;
%Docstring
Creates a map tool for a creating a new item of this type.

May return ``None`` if no map tool is available for creating the item.
%End

virtual QgsAnnotationItem *createItem() /TransferBack/;
Expand All @@ -88,6 +95,7 @@ called for items added programmatically.




class QgsAnnotationItemGuiGroup
{
%Docstring(signature="appended")
Expand Down
@@ -0,0 +1,60 @@
/************************************************************************
* This file has been generated automatically from *
* *
* src/gui/annotations/qgscreateannotationitemmaptool.h *
* *
* Do not edit manually ! Edit header and run scripts/sipify.pl again *
************************************************************************/



class QgsCreateAnnotationItemMapTool: QgsMapToolAdvancedDigitizing
{
%Docstring(signature="appended")

A base class for map tools which create annotation items.

Clients should connect to the map tool's :py:func:`~itemCreated` signal, and call the
:py:func:`~takeCreatedItem` implementation to take ownership of the newly created item
whenever this signal is emitted.

.. versionadded:: 3.22
%End

%TypeHeaderCode
#include "qgscreateannotationitemmaptool.h"
%End
public:

QgsCreateAnnotationItemMapTool( QgsMapCanvas *canvas, QgsAdvancedDigitizingDockWidget *cadDockWidget );
%Docstring
Constructor for QgsCreateAnnotationItemMapTool.
%End

virtual QgsAnnotationItem *takeCreatedItem() = 0 /TransferBack/;
%Docstring
Takes the newly created item from the tool, transferring ownership to the caller.

Subclasses must implement this method, and ensure that they emit the :py:func:`~QgsCreateAnnotationItemMapTool.itemCreated` signal whenever
they have a created item ready for clients to take.
%End

signals:

void itemCreated();
%Docstring
Emitted by the tool when a new annotation item has been created.

Clients should connect to this signal and call :py:func:`~QgsCreateAnnotationItemMapTool.takeCreatedItem` to take the newly created item from the map tool.
%End


};

/************************************************************************
* This file has been generated automatically from *
* *
* src/gui/annotations/qgscreateannotationitemmaptool.h *
* *
* Do not edit manually ! Edit header and run scripts/sipify.pl again *
************************************************************************/
1 change: 1 addition & 0 deletions python/gui/gui_auto.sip
Expand Up @@ -227,6 +227,7 @@
%Include auto_generated/annotations/qgsannotationitemcommonpropertieswidget.sip
%Include auto_generated/annotations/qgsannotationitemguiregistry.sip
%Include auto_generated/annotations/qgsannotationitemwidget.sip
%Include auto_generated/annotations/qgscreateannotationitemmaptool.sip
%Include auto_generated/annotations/qgsmaptoolmodifyannotation.sip
%Include auto_generated/attributetable/qgsattributetabledelegate.sip
%Include auto_generated/attributetable/qgsattributetablefiltermodel.sip
Expand Down
3 changes: 3 additions & 0 deletions src/gui/CMakeLists.txt
Expand Up @@ -98,6 +98,8 @@ set(QGIS_GUI_SRCS
annotations/qgsannotationitemguiregistry.cpp
annotations/qgsannotationitemwidget.cpp
annotations/qgsannotationitemwidget_impl.cpp
annotations/qgscreateannotationitemmaptool.cpp
annotations/qgscreateannotationitemmaptool_impl.cpp
annotations/qgsmaptoolmodifyannotation.cpp

auth/qgsauthauthoritieseditor.cpp
Expand Down Expand Up @@ -887,6 +889,7 @@ set(QGIS_GUI_HDRS
annotations/qgsannotationitemcommonpropertieswidget.h
annotations/qgsannotationitemguiregistry.h
annotations/qgsannotationitemwidget.h
annotations/qgscreateannotationitemmaptool.h
annotations/qgsmaptoolmodifyannotation.h

attributeformconfig/qgsattributeformcontaineredit.h
Expand Down
65 changes: 54 additions & 11 deletions src/gui/annotations/qgsannotationitemguiregistry.cpp
Expand Up @@ -20,6 +20,25 @@

#include "qgsannotationitemwidget_impl.h"

//
// QgsAnnotationItemAbstractGuiMetadata
//

QIcon QgsAnnotationItemAbstractGuiMetadata::creationIcon() const
{
return QgsApplication::getThemeIcon( QStringLiteral( "/mActionAddBasicRectangle.svg" ) );
}

QgsAnnotationItemBaseWidget *QgsAnnotationItemAbstractGuiMetadata::createItemWidget( QgsAnnotationItem * )
{
return nullptr;
}

QgsCreateAnnotationItemMapTool *QgsAnnotationItemAbstractGuiMetadata::createMapTool( QgsMapCanvas *, QgsAdvancedDigitizingDockWidget * )
{
return nullptr;
}

QgsAnnotationItem *QgsAnnotationItemAbstractGuiMetadata::createItem()
{
return nullptr;
Expand All @@ -30,6 +49,41 @@ void QgsAnnotationItemAbstractGuiMetadata::newItemAddedToLayer( QgsAnnotationIte

}

//
// QgsAnnotationItemGuiMetadata
//

QIcon QgsAnnotationItemGuiMetadata::creationIcon() const
{
return mIcon.isNull() ? QgsAnnotationItemAbstractGuiMetadata::creationIcon() : mIcon;
}

QgsAnnotationItemBaseWidget *QgsAnnotationItemGuiMetadata::createItemWidget( QgsAnnotationItem *item )
{
return mWidgetFunc ? mWidgetFunc( item ) : nullptr;
}

QgsAnnotationItem *QgsAnnotationItemGuiMetadata::createItem()
{
return mCreateFunc ? mCreateFunc() : QgsAnnotationItemAbstractGuiMetadata::createItem();
}

void QgsAnnotationItemGuiMetadata::newItemAddedToLayer( QgsAnnotationItem *item, QgsAnnotationLayer *layer )
{
if ( mAddedToLayerFunc )
mAddedToLayerFunc( item, layer );
}

QgsCreateAnnotationItemMapTool *QgsAnnotationItemGuiMetadata::createMapTool( QgsMapCanvas *canvas, QgsAdvancedDigitizingDockWidget *cadDockWidget )
{
return mCreateMapToolFunc ? mCreateMapToolFunc( canvas, cadDockWidget ) : nullptr;
}


//
// QgsAnnotationItemGuiRegistry
//

QgsAnnotationItemGuiRegistry::QgsAnnotationItemGuiRegistry( QObject *parent )
: QObject( parent )
{
Expand Down Expand Up @@ -164,14 +218,3 @@ void QgsAnnotationItemGuiRegistry::addDefaultItems()
return widget;
} ) );
}

QgsAnnotationItem *QgsAnnotationItemGuiMetadata::createItem()
{
return mCreateFunc ? mCreateFunc() : QgsAnnotationItemAbstractGuiMetadata::createItem();
}

void QgsAnnotationItemGuiMetadata::newItemAddedToLayer( QgsAnnotationItem *item, QgsAnnotationLayer *layer )
{
if ( mAddedToLayerFunc )
mAddedToLayerFunc( item, layer );
}
39 changes: 34 additions & 5 deletions src/gui/annotations/qgsannotationitemguiregistry.h
Expand Up @@ -28,6 +28,9 @@
class QgsAnnotationLayer;
class QgsAnnotationItem;
class QgsAnnotationItemBaseWidget;
class QgsCreateAnnotationItemMapTool;
class QgsMapCanvas;
class QgsAdvancedDigitizingDockWidget;

/**
* \ingroup gui
Expand Down Expand Up @@ -82,7 +85,7 @@ class GUI_EXPORT QgsAnnotationItemAbstractGuiMetadata
/**
* Returns an icon representing creation of the annotation item type.
*/
virtual QIcon creationIcon() const { return QgsApplication::getThemeIcon( QStringLiteral( "/mActionAddBasicRectangle.svg" ) ); }
virtual QIcon creationIcon() const;

/*
* IMPORTANT: While it seems like /Factory/ would be the correct annotations here, that's not
Expand All @@ -102,7 +105,14 @@ class GUI_EXPORT QgsAnnotationItemAbstractGuiMetadata
/**
* Creates a configuration widget for an \a item of this type. Can return NULLPTR if no configuration GUI is required.
*/
virtual QgsAnnotationItemBaseWidget *createItemWidget( QgsAnnotationItem *item ) SIP_TRANSFERBACK { Q_UNUSED( item ) return nullptr; }
virtual QgsAnnotationItemBaseWidget *createItemWidget( QgsAnnotationItem *item ) SIP_TRANSFERBACK;

/**
* Creates a map tool for a creating a new item of this type.
*
* May return NULLPTR if no map tool is available for creating the item.
*/
virtual QgsCreateAnnotationItemMapTool *createMapTool( QgsMapCanvas *canvas, QgsAdvancedDigitizingDockWidget *cadDockWidget ) SIP_TRANSFERBACK;

/**
* Creates an instance of the corresponding item type.
Expand All @@ -129,6 +139,9 @@ class GUI_EXPORT QgsAnnotationItemAbstractGuiMetadata
//! Annotation item configuration widget creation function
typedef std::function<QgsAnnotationItemBaseWidget *( QgsAnnotationItem * )> QgsAnnotationItemWidgetFunc SIP_SKIP;

//! Create annotation map tool creation function
typedef std::function<QgsCreateAnnotationItemMapTool *( QgsMapCanvas *, QgsAdvancedDigitizingDockWidget * )> QgsCreateAnnotationItemMapToolFunc SIP_SKIP;

//! Annotation item added to layer callback
typedef std::function<void ( QgsAnnotationItem *, QgsAnnotationLayer *layer )> QgsAnnotationItemAddedToLayerFunc SIP_SKIP;

Expand Down Expand Up @@ -157,11 +170,13 @@ class GUI_EXPORT QgsAnnotationItemGuiMetadata : public QgsAnnotationItemAbstract
const QgsAnnotationItemWidgetFunc &pfWidget = nullptr,
const QString &groupId = QString(),
Qgis::AnnotationItemGuiFlags flags = Qgis::AnnotationItemGuiFlags(),
const QgsAnnotationItemCreateFunc &pfCreateFunc = nullptr )
const QgsAnnotationItemCreateFunc &pfCreateFunc = nullptr,
const QgsCreateAnnotationItemMapToolFunc &pfCreateMapToolFunc = nullptr )
: QgsAnnotationItemAbstractGuiMetadata( type, visibleName, groupId, flags )
, mIcon( creationIcon )
, mWidgetFunc( pfWidget )
, mCreateFunc( pfCreateFunc )
, mCreateMapToolFunc( pfCreateMapToolFunc )
{}

/**
Expand All @@ -176,6 +191,18 @@ class GUI_EXPORT QgsAnnotationItemGuiMetadata : public QgsAnnotationItemAbstract
*/
void setWidgetFunction( const QgsAnnotationItemWidgetFunc &function ) { mWidgetFunc = function; }

/**
* Returns the classes' create new item map tool creation function.
* \see setCreateMapToolFunction()
*/
QgsCreateAnnotationItemMapToolFunc createMapToolFunction() const { return mCreateMapToolFunc; }

/**
* Sets the classes' create new item map tool creation \a function.
* \see createMapToolFunction()
*/
void setCreateMapToolFunction( const QgsCreateAnnotationItemMapToolFunc &function ) { mCreateMapToolFunc = function; }

/**
* Returns the classes' item creation function.
* \see setItemCreationFunction()
Expand All @@ -200,16 +227,18 @@ class GUI_EXPORT QgsAnnotationItemGuiMetadata : public QgsAnnotationItemAbstract
*/
void setItemAddedToLayerFunction( const QgsAnnotationItemAddedToLayerFunc &function ) { mAddedToLayerFunc = function; }

QIcon creationIcon() const override { return mIcon.isNull() ? QgsAnnotationItemAbstractGuiMetadata::creationIcon() : mIcon; }
QgsAnnotationItemBaseWidget *createItemWidget( QgsAnnotationItem *item ) override { return mWidgetFunc ? mWidgetFunc( item ) : nullptr; }
QIcon creationIcon() const override;
QgsAnnotationItemBaseWidget *createItemWidget( QgsAnnotationItem *item ) override;

QgsAnnotationItem *createItem() override;
void newItemAddedToLayer( QgsAnnotationItem *item, QgsAnnotationLayer *layer ) override;
QgsCreateAnnotationItemMapTool *createMapTool( QgsMapCanvas *canvas, QgsAdvancedDigitizingDockWidget *cadDockWidget ) override;

protected:
QIcon mIcon;
QgsAnnotationItemWidgetFunc mWidgetFunc = nullptr;
QgsAnnotationItemCreateFunc mCreateFunc = nullptr;
QgsCreateAnnotationItemMapToolFunc mCreateMapToolFunc = nullptr;
QgsAnnotationItemAddedToLayerFunc mAddedToLayerFunc = nullptr;

};
Expand Down
22 changes: 22 additions & 0 deletions src/gui/annotations/qgscreateannotationitemmaptool.cpp
@@ -0,0 +1,22 @@
/***************************************************************************
qgscreateannotationitemmaptool.cpp
------------------------
Date : September 2021
Copyright : (C) 2021 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 "qgscreateannotationitemmaptool.h"

QgsCreateAnnotationItemMapTool::QgsCreateAnnotationItemMapTool( QgsMapCanvas *canvas, QgsAdvancedDigitizingDockWidget *cadDockWidget )
: QgsMapToolAdvancedDigitizing( canvas, cadDockWidget )
{

}
67 changes: 67 additions & 0 deletions src/gui/annotations/qgscreateannotationitemmaptool.h
@@ -0,0 +1,67 @@
/***************************************************************************
qgscreateannotationitemmaptool.h
------------------------
Date : September 2021
Copyright : (C) 2021 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 QGSCREATEANNOTATIONITEMMAPTOOL_H
#define QGSCREATEANNOTATIONITEMMAPTOOL_H

#include "qgis_gui.h"
#include "qgis_sip.h"
#include "qgsmaptooladvanceddigitizing.h"

class QgsAnnotationItem;

/**
* \class QgsCreateAnnotationItemMapTool
* \ingroup gui
*
* \brief A base class for map tools which create annotation items.
*
* Clients should connect to the map tool's itemCreated() signal, and call the
* takeCreatedItem() implementation to take ownership of the newly created item
* whenever this signal is emitted.
*
* \since QGIS 3.22
*/
class GUI_EXPORT QgsCreateAnnotationItemMapTool: public QgsMapToolAdvancedDigitizing
{
Q_OBJECT

public:

/**
* Constructor for QgsCreateAnnotationItemMapTool.
*/
QgsCreateAnnotationItemMapTool( QgsMapCanvas *canvas, QgsAdvancedDigitizingDockWidget *cadDockWidget );

/**
* Takes the newly created item from the tool, transferring ownership to the caller.
*
* Subclasses must implement this method, and ensure that they emit the itemCreated() signal whenever
* they have a created item ready for clients to take.
*/
virtual QgsAnnotationItem *takeCreatedItem() = 0 SIP_TRANSFERBACK;

signals:

/**
* Emitted by the tool when a new annotation item has been created.
*
* Clients should connect to this signal and call takeCreatedItem() to take the newly created item from the map tool.
*/
void itemCreated();


};

#endif // QGSCREATEANNOTATIONITEMMAPTOOL_H

0 comments on commit 01226a3

Please sign in to comment.