mirror of
https://github.com/qgis/QGIS.git
synced 2025-10-06 00:07:29 -04:00
Use an edit operation for annotation item translation, instead of
transform Will make it easier to add undo/redo support in future
This commit is contained in:
parent
f76b262ac0
commit
a7d299df92
@ -2,5 +2,6 @@
|
||||
# monkey patching scoped based enum
|
||||
QgsAbstractAnnotationItemEditOperation.Type.MoveNode.__doc__ = "Move a node"
|
||||
QgsAbstractAnnotationItemEditOperation.Type.DeleteNode.__doc__ = "Delete a node"
|
||||
QgsAbstractAnnotationItemEditOperation.Type.__doc__ = 'Operation type\n\n' + '* ``MoveNode``: ' + QgsAbstractAnnotationItemEditOperation.Type.MoveNode.__doc__ + '\n' + '* ``DeleteNode``: ' + QgsAbstractAnnotationItemEditOperation.Type.DeleteNode.__doc__
|
||||
QgsAbstractAnnotationItemEditOperation.Type.TranslateItem.__doc__ = "Translate (move) an item"
|
||||
QgsAbstractAnnotationItemEditOperation.Type.__doc__ = 'Operation type\n\n' + '* ``MoveNode``: ' + QgsAbstractAnnotationItemEditOperation.Type.MoveNode.__doc__ + '\n' + '* ``DeleteNode``: ' + QgsAbstractAnnotationItemEditOperation.Type.DeleteNode.__doc__ + '\n' + '* ``TranslateItem``: ' + QgsAbstractAnnotationItemEditOperation.Type.TranslateItem.__doc__
|
||||
# --
|
||||
|
@ -82,15 +82,6 @@ Returns the bounding box of the item's geographic location, in the parent layer'
|
||||
virtual QgsRectangle boundingBox( QgsRenderContext &context ) const;
|
||||
%Docstring
|
||||
Returns the bounding box of the item's geographic location, in the parent layer's coordinate reference system.
|
||||
%End
|
||||
|
||||
virtual bool transform( const QTransform &transform ) = 0;
|
||||
%Docstring
|
||||
Transforms the item's geometry using the specified ``transform``.
|
||||
|
||||
Returns ``True`` if the transformation was successful.
|
||||
|
||||
.. versionadded:: 3.22
|
||||
%End
|
||||
|
||||
virtual void render( QgsRenderContext &context, QgsFeedback *feedback ) = 0;
|
||||
@ -212,16 +203,6 @@ exactly 2mm thick when a map is rendered at 1:1000, or 1mm thick when rendered a
|
||||
.. seealso:: :py:func:`symbologyReferenceScale`
|
||||
|
||||
.. seealso:: :py:func:`setUseSymbologyReferenceScale`
|
||||
%End
|
||||
|
||||
virtual QgsGeometry rubberBandGeometry() const;
|
||||
%Docstring
|
||||
Returns the geometry to use as a rubber band for map tools which manipulate the item.
|
||||
|
||||
The default implementation returns a null geometry, which indicates that the item bounds should
|
||||
be used as the rubber band.
|
||||
|
||||
.. versionadded:: 3.22
|
||||
%End
|
||||
|
||||
protected:
|
||||
|
@ -26,6 +26,7 @@ Abstract base class for annotation item edit operations
|
||||
{
|
||||
MoveNode,
|
||||
DeleteNode,
|
||||
TranslateItem,
|
||||
};
|
||||
|
||||
QgsAbstractAnnotationItemEditOperation( const QString &itemId );
|
||||
@ -128,6 +129,50 @@ Returns the node position before the delete occurred (in layer coordinates).
|
||||
|
||||
};
|
||||
|
||||
|
||||
class QgsAnnotationItemEditOperationTranslateItem : QgsAbstractAnnotationItemEditOperation
|
||||
{
|
||||
%Docstring(signature="appended")
|
||||
Annotation item edit operation consisting of translating (moving) an item
|
||||
|
||||
.. versionadded:: 3.22
|
||||
%End
|
||||
|
||||
%TypeHeaderCode
|
||||
#include "qgsannotationitemeditoperation.h"
|
||||
%End
|
||||
public:
|
||||
|
||||
QgsAnnotationItemEditOperationTranslateItem( const QString &itemId, double translateX, double translateY );
|
||||
%Docstring
|
||||
Constructor for QgsAnnotationItemEditOperationTranslateItem, where the node with the specified ``id`` and translation
|
||||
(in map units)
|
||||
%End
|
||||
|
||||
virtual Type type() const;
|
||||
|
||||
|
||||
QgsVertexId nodeId() const;
|
||||
%Docstring
|
||||
Returns the deleted node ID.
|
||||
%End
|
||||
|
||||
double translationX() const;
|
||||
%Docstring
|
||||
Returns the x-axis translation, in layer units.
|
||||
|
||||
\since :py:func:`~QgsAnnotationItemEditOperationTranslateItem.translationY`
|
||||
%End
|
||||
|
||||
double translationY() const;
|
||||
%Docstring
|
||||
Returns the y-axis translation, in layer units.
|
||||
|
||||
\since :py:func:`~QgsAnnotationItemEditOperationTranslateItem.translationX`
|
||||
%End
|
||||
|
||||
};
|
||||
|
||||
class QgsAnnotationItemEditOperationTransientResults
|
||||
{
|
||||
%Docstring(signature="appended")
|
||||
|
@ -37,10 +37,6 @@ Constructor for QgsAnnotationLineItem, with the specified ``linestring``.
|
||||
|
||||
virtual QList< QgsAnnotationItemNode > nodes() const;
|
||||
|
||||
virtual QgsGeometry rubberBandGeometry() const;
|
||||
|
||||
virtual bool transform( const QTransform &transform );
|
||||
|
||||
virtual Qgis::AnnotationItemEditOperationResult applyEdit( QgsAbstractAnnotationItemEditOperation *operation );
|
||||
|
||||
virtual QgsAnnotationItemEditOperationTransientResults *transientEditResults( QgsAbstractAnnotationItemEditOperation *operation ) /Factory/;
|
||||
|
@ -57,8 +57,6 @@ Creates a new marker annotation item.
|
||||
|
||||
virtual QgsRectangle boundingBox( QgsRenderContext &context ) const;
|
||||
|
||||
virtual bool transform( const QTransform &transform );
|
||||
|
||||
|
||||
QgsPointXY geometry() const;
|
||||
%Docstring
|
||||
|
@ -53,8 +53,6 @@ Creates a new text at point annotation item.
|
||||
|
||||
virtual QList< QgsAnnotationItemNode > nodes() const;
|
||||
|
||||
virtual bool transform( const QTransform &transform );
|
||||
|
||||
virtual Qgis::AnnotationItemEditOperationResult applyEdit( QgsAbstractAnnotationItemEditOperation *operation );
|
||||
|
||||
virtual QgsAnnotationItemEditOperationTransientResults *transientEditResults( QgsAbstractAnnotationItemEditOperation *operation ) /Factory/;
|
||||
|
@ -37,10 +37,6 @@ Constructor for QgsAnnotationPolygonItem, with the specified ``polygon`` geometr
|
||||
|
||||
virtual QList< QgsAnnotationItemNode > nodes() const;
|
||||
|
||||
virtual QgsGeometry rubberBandGeometry() const;
|
||||
|
||||
virtual bool transform( const QTransform &transform );
|
||||
|
||||
virtual Qgis::AnnotationItemEditOperationResult applyEdit( QgsAbstractAnnotationItemEditOperation *operation );
|
||||
|
||||
virtual QgsAnnotationItemEditOperationTransientResults *transientEditResults( QgsAbstractAnnotationItemEditOperation *operation ) /Factory/;
|
||||
|
@ -60,8 +60,3 @@ bool QgsAnnotationItem::readCommonProperties( const QDomElement &element, const
|
||||
setSymbologyReferenceScale( element.attribute( QStringLiteral( "referenceScale" ) ).toDouble() );
|
||||
return true;
|
||||
}
|
||||
|
||||
QgsGeometry QgsAnnotationItem::rubberBandGeometry() const
|
||||
{
|
||||
return QgsGeometry();
|
||||
}
|
||||
|
@ -113,15 +113,6 @@ class CORE_EXPORT QgsAnnotationItem
|
||||
*/
|
||||
virtual QgsRectangle boundingBox( QgsRenderContext &context ) const { Q_UNUSED( context ) return boundingBox();}
|
||||
|
||||
/**
|
||||
* Transforms the item's geometry using the specified \a transform.
|
||||
*
|
||||
* Returns TRUE if the transformation was successful.
|
||||
*
|
||||
* \since QGIS 3.22
|
||||
*/
|
||||
virtual bool transform( const QTransform &transform ) = 0;
|
||||
|
||||
/**
|
||||
* Renders the item to the specified render \a context.
|
||||
*
|
||||
@ -237,16 +228,6 @@ class CORE_EXPORT QgsAnnotationItem
|
||||
*/
|
||||
void setSymbologyReferenceScale( double scale ) { mReferenceScale = scale; }
|
||||
|
||||
/**
|
||||
* Returns the geometry to use as a rubber band for map tools which manipulate the item.
|
||||
*
|
||||
* The default implementation returns a null geometry, which indicates that the item bounds should
|
||||
* be used as the rubber band.
|
||||
*
|
||||
* \since QGIS 3.22
|
||||
*/
|
||||
virtual QgsGeometry rubberBandGeometry() const;
|
||||
|
||||
protected:
|
||||
|
||||
/**
|
||||
|
@ -62,3 +62,20 @@ QgsAbstractAnnotationItemEditOperation::Type QgsAnnotationItemEditOperationDelet
|
||||
{
|
||||
return Type::DeleteNode;
|
||||
}
|
||||
|
||||
//
|
||||
// QgsAnnotationItemEditOperationTranslateItem
|
||||
//
|
||||
|
||||
QgsAnnotationItemEditOperationTranslateItem::QgsAnnotationItemEditOperationTranslateItem( const QString &itemId, double translateX, double translateY )
|
||||
: QgsAbstractAnnotationItemEditOperation( itemId )
|
||||
, mTranslateX( translateX )
|
||||
, mTranslateY( translateY )
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
QgsAbstractAnnotationItemEditOperation::Type QgsAnnotationItemEditOperationTranslateItem::type() const
|
||||
{
|
||||
return Type::TranslateItem;
|
||||
}
|
||||
|
@ -40,6 +40,7 @@ class CORE_EXPORT QgsAbstractAnnotationItemEditOperation
|
||||
{
|
||||
MoveNode, //!< Move a node
|
||||
DeleteNode, //!< Delete a node
|
||||
TranslateItem, //!< Translate (move) an item
|
||||
};
|
||||
|
||||
/**
|
||||
@ -144,6 +145,52 @@ class CORE_EXPORT QgsAnnotationItemEditOperationDeleteNode : public QgsAbstractA
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* \ingroup core
|
||||
* \brief Annotation item edit operation consisting of translating (moving) an item
|
||||
* \since QGIS 3.22
|
||||
*/
|
||||
class CORE_EXPORT QgsAnnotationItemEditOperationTranslateItem : public QgsAbstractAnnotationItemEditOperation
|
||||
{
|
||||
public:
|
||||
|
||||
/**
|
||||
* Constructor for QgsAnnotationItemEditOperationTranslateItem, where the node with the specified \a id and translation
|
||||
* (in map units)
|
||||
*/
|
||||
QgsAnnotationItemEditOperationTranslateItem( const QString &itemId, double translateX, double translateY );
|
||||
|
||||
Type type() const override;
|
||||
|
||||
/**
|
||||
* Returns the deleted node ID.
|
||||
*/
|
||||
QgsVertexId nodeId() const { return mNodeId; }
|
||||
|
||||
/**
|
||||
* Returns the x-axis translation, in layer units.
|
||||
*
|
||||
* \since translationY()
|
||||
*/
|
||||
double translationX() const { return mTranslateX; }
|
||||
|
||||
/**
|
||||
* Returns the y-axis translation, in layer units.
|
||||
*
|
||||
* \since translationX()
|
||||
*/
|
||||
double translationY() const { return mTranslateY; }
|
||||
|
||||
private:
|
||||
|
||||
QgsVertexId mNodeId;
|
||||
double mTranslateX = 0;
|
||||
double mTranslateY = 0;
|
||||
|
||||
|
||||
};
|
||||
|
||||
/**
|
||||
* \ingroup core
|
||||
* \brief Encapsulates the transient results of an in-progress annotation edit operation.
|
||||
|
@ -92,17 +92,6 @@ QList<QgsAnnotationItemNode> QgsAnnotationLineItem::nodes() const
|
||||
return res;
|
||||
}
|
||||
|
||||
QgsGeometry QgsAnnotationLineItem::rubberBandGeometry() const
|
||||
{
|
||||
return QgsGeometry( mCurve->clone() );
|
||||
}
|
||||
|
||||
bool QgsAnnotationLineItem::transform( const QTransform &transform )
|
||||
{
|
||||
mCurve->transform( transform );
|
||||
return true;
|
||||
}
|
||||
|
||||
Qgis::AnnotationItemEditOperationResult QgsAnnotationLineItem::applyEdit( QgsAbstractAnnotationItemEditOperation *operation )
|
||||
{
|
||||
switch ( operation->type() )
|
||||
@ -122,6 +111,14 @@ Qgis::AnnotationItemEditOperationResult QgsAnnotationLineItem::applyEdit( QgsAbs
|
||||
return mCurve->isEmpty() ? Qgis::AnnotationItemEditOperationResult::ItemCleared : Qgis::AnnotationItemEditOperationResult::Success;
|
||||
break;
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::TranslateItem:
|
||||
{
|
||||
QgsAnnotationItemEditOperationTranslateItem *moveOperation = qgis::down_cast< QgsAnnotationItemEditOperationTranslateItem * >( operation );
|
||||
const QTransform transform = QTransform::fromTranslate( moveOperation->translationX(), moveOperation->translationY() );
|
||||
mCurve->transform( transform );
|
||||
return Qgis::AnnotationItemEditOperationResult::Success;
|
||||
}
|
||||
}
|
||||
|
||||
return Qgis::AnnotationItemEditOperationResult::Invalid;
|
||||
@ -142,6 +139,15 @@ QgsAnnotationItemEditOperationTransientResults *QgsAnnotationLineItem::transient
|
||||
break;
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::TranslateItem:
|
||||
{
|
||||
QgsAnnotationItemEditOperationTranslateItem *moveOperation = qgis::down_cast< QgsAnnotationItemEditOperationTranslateItem * >( operation );
|
||||
const QTransform transform = QTransform::fromTranslate( moveOperation->translationX(), moveOperation->translationY() );
|
||||
std::unique_ptr< QgsCurve > modifiedCurve( mCurve->clone() );
|
||||
modifiedCurve->transform( transform );
|
||||
return new QgsAnnotationItemEditOperationTransientResults( QgsGeometry( std::move( modifiedCurve ) ) );
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::DeleteNode:
|
||||
break;
|
||||
}
|
||||
|
@ -44,8 +44,6 @@ class CORE_EXPORT QgsAnnotationLineItem : public QgsAnnotationItem
|
||||
void render( QgsRenderContext &context, QgsFeedback *feedback ) override;
|
||||
bool writeXml( QDomElement &element, QDomDocument &document, const QgsReadWriteContext &context ) const override;
|
||||
QList< QgsAnnotationItemNode > nodes() const override;
|
||||
QgsGeometry rubberBandGeometry() const override;
|
||||
bool transform( const QTransform &transform ) override;
|
||||
Qgis::AnnotationItemEditOperationResult applyEdit( QgsAbstractAnnotationItemEditOperation *operation ) override;
|
||||
QgsAnnotationItemEditOperationTransientResults *transientEditResults( QgsAbstractAnnotationItemEditOperation *operation ) override SIP_FACTORY;
|
||||
|
||||
|
@ -95,6 +95,14 @@ Qgis::AnnotationItemEditOperationResult QgsAnnotationMarkerItem::applyEdit( QgsA
|
||||
{
|
||||
return Qgis::AnnotationItemEditOperationResult::ItemCleared;
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::TranslateItem:
|
||||
{
|
||||
QgsAnnotationItemEditOperationTranslateItem *moveOperation = qgis::down_cast< QgsAnnotationItemEditOperationTranslateItem * >( operation );
|
||||
mPoint.setX( mPoint.x() + moveOperation->translationX() );
|
||||
mPoint.setY( mPoint.y() + moveOperation->translationY() );
|
||||
return Qgis::AnnotationItemEditOperationResult::Success;
|
||||
}
|
||||
}
|
||||
|
||||
return Qgis::AnnotationItemEditOperationResult::Invalid;
|
||||
@ -110,6 +118,12 @@ QgsAnnotationItemEditOperationTransientResults *QgsAnnotationMarkerItem::transie
|
||||
return new QgsAnnotationItemEditOperationTransientResults( QgsGeometry( moveOperation->after().clone() ) );
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::TranslateItem:
|
||||
{
|
||||
QgsAnnotationItemEditOperationTranslateItem *moveOperation = qgis::down_cast< QgsAnnotationItemEditOperationTranslateItem * >( operation );
|
||||
return new QgsAnnotationItemEditOperationTransientResults( QgsGeometry( new QgsPoint( mPoint.x() + moveOperation->translationX(), mPoint.y() + moveOperation->translationY() ) ) );
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::DeleteNode:
|
||||
break;
|
||||
}
|
||||
@ -177,12 +191,6 @@ QgsRectangle QgsAnnotationMarkerItem::boundingBox( QgsRenderContext &context ) c
|
||||
return context.coordinateTransform().transformBoundingBox( boundsMapUnits, QgsCoordinateTransform::ReverseTransform );
|
||||
}
|
||||
|
||||
bool QgsAnnotationMarkerItem::transform( const QTransform &transform )
|
||||
{
|
||||
mPoint.transform( transform );
|
||||
return true;
|
||||
}
|
||||
|
||||
const QgsMarkerSymbol *QgsAnnotationMarkerItem::symbol() const
|
||||
{
|
||||
return mSymbol.get();
|
||||
|
@ -56,7 +56,6 @@ class CORE_EXPORT QgsAnnotationMarkerItem : public QgsAnnotationItem
|
||||
QgsAnnotationMarkerItem *clone() override SIP_FACTORY;
|
||||
QgsRectangle boundingBox() const override;
|
||||
QgsRectangle boundingBox( QgsRenderContext &context ) const override;
|
||||
bool transform( const QTransform &transform ) override;
|
||||
|
||||
/**
|
||||
* Returns the point geometry of the marker.
|
||||
|
@ -138,15 +138,6 @@ QList<QgsAnnotationItemNode> QgsAnnotationPointTextItem::nodes() const
|
||||
return { QgsAnnotationItemNode( QgsVertexId( 0, 0, 0 ), mPoint, Qgis::AnnotationItemNodeType::VertexHandle )};
|
||||
}
|
||||
|
||||
bool QgsAnnotationPointTextItem::transform( const QTransform &transform )
|
||||
{
|
||||
double x = mPoint.x();
|
||||
double y = mPoint.y();
|
||||
transform.map( mPoint.x(), mPoint.y(), &x, &y );
|
||||
mPoint.set( x, y );
|
||||
return true;
|
||||
}
|
||||
|
||||
Qgis::AnnotationItemEditOperationResult QgsAnnotationPointTextItem::applyEdit( QgsAbstractAnnotationItemEditOperation *operation )
|
||||
{
|
||||
switch ( operation->type() )
|
||||
@ -162,6 +153,14 @@ Qgis::AnnotationItemEditOperationResult QgsAnnotationPointTextItem::applyEdit( Q
|
||||
{
|
||||
return Qgis::AnnotationItemEditOperationResult::ItemCleared;
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::TranslateItem:
|
||||
{
|
||||
QgsAnnotationItemEditOperationTranslateItem *moveOperation = qgis::down_cast< QgsAnnotationItemEditOperationTranslateItem * >( operation );
|
||||
mPoint.setX( mPoint.x() + moveOperation->translationX() );
|
||||
mPoint.setY( mPoint.y() + moveOperation->translationY() );
|
||||
return Qgis::AnnotationItemEditOperationResult::Success;
|
||||
}
|
||||
}
|
||||
|
||||
return Qgis::AnnotationItemEditOperationResult::Invalid;
|
||||
@ -177,6 +176,12 @@ QgsAnnotationItemEditOperationTransientResults *QgsAnnotationPointTextItem::tran
|
||||
return new QgsAnnotationItemEditOperationTransientResults( QgsGeometry( moveOperation->after().clone() ) );
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::TranslateItem:
|
||||
{
|
||||
QgsAnnotationItemEditOperationTranslateItem *moveOperation = qgis::down_cast< QgsAnnotationItemEditOperationTranslateItem * >( operation );
|
||||
return new QgsAnnotationItemEditOperationTransientResults( QgsGeometry( new QgsPoint( mPoint.x() + moveOperation->translationX(), mPoint.y() + moveOperation->translationY() ) ) );
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::DeleteNode:
|
||||
break;
|
||||
}
|
||||
|
@ -55,7 +55,6 @@ class CORE_EXPORT QgsAnnotationPointTextItem : public QgsAnnotationItem
|
||||
QgsRectangle boundingBox() const override;
|
||||
QgsRectangle boundingBox( QgsRenderContext &context ) const override;
|
||||
QList< QgsAnnotationItemNode > nodes() const override;
|
||||
bool transform( const QTransform &transform ) override;
|
||||
Qgis::AnnotationItemEditOperationResult applyEdit( QgsAbstractAnnotationItemEditOperation *operation ) override;
|
||||
QgsAnnotationItemEditOperationTransientResults *transientEditResults( QgsAbstractAnnotationItemEditOperation *operation ) override SIP_FACTORY;
|
||||
|
||||
|
@ -122,17 +122,6 @@ QList<QgsAnnotationItemNode> QgsAnnotationPolygonItem::nodes() const
|
||||
return res;
|
||||
}
|
||||
|
||||
QgsGeometry QgsAnnotationPolygonItem::rubberBandGeometry() const
|
||||
{
|
||||
return QgsGeometry( mPolygon->clone() );
|
||||
}
|
||||
|
||||
bool QgsAnnotationPolygonItem::transform( const QTransform &transform )
|
||||
{
|
||||
mPolygon->transform( transform );
|
||||
return true;
|
||||
}
|
||||
|
||||
Qgis::AnnotationItemEditOperationResult QgsAnnotationPolygonItem::applyEdit( QgsAbstractAnnotationItemEditOperation *operation )
|
||||
{
|
||||
switch ( operation->type() )
|
||||
@ -152,6 +141,14 @@ Qgis::AnnotationItemEditOperationResult QgsAnnotationPolygonItem::applyEdit( Qgs
|
||||
return mPolygon->isEmpty() ? Qgis::AnnotationItemEditOperationResult::ItemCleared : Qgis::AnnotationItemEditOperationResult::Success;
|
||||
break;
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::TranslateItem:
|
||||
{
|
||||
QgsAnnotationItemEditOperationTranslateItem *moveOperation = qgis::down_cast< QgsAnnotationItemEditOperationTranslateItem * >( operation );
|
||||
const QTransform transform = QTransform::fromTranslate( moveOperation->translationX(), moveOperation->translationY() );
|
||||
mPolygon->transform( transform );
|
||||
return Qgis::AnnotationItemEditOperationResult::Success;
|
||||
}
|
||||
}
|
||||
|
||||
return Qgis::AnnotationItemEditOperationResult::Invalid;
|
||||
@ -172,6 +169,15 @@ QgsAnnotationItemEditOperationTransientResults *QgsAnnotationPolygonItem::transi
|
||||
break;
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::TranslateItem:
|
||||
{
|
||||
QgsAnnotationItemEditOperationTranslateItem *moveOperation = qgis::down_cast< QgsAnnotationItemEditOperationTranslateItem * >( operation );
|
||||
const QTransform transform = QTransform::fromTranslate( moveOperation->translationX(), moveOperation->translationY() );
|
||||
std::unique_ptr< QgsCurvePolygon > modifiedPolygon( mPolygon->clone() );
|
||||
modifiedPolygon->transform( transform );
|
||||
return new QgsAnnotationItemEditOperationTransientResults( QgsGeometry( std::move( modifiedPolygon ) ) );
|
||||
}
|
||||
|
||||
case QgsAbstractAnnotationItemEditOperation::Type::DeleteNode:
|
||||
break;
|
||||
}
|
||||
|
@ -43,8 +43,6 @@ class CORE_EXPORT QgsAnnotationPolygonItem : public QgsAnnotationItem
|
||||
void render( QgsRenderContext &context, QgsFeedback *feedback ) override;
|
||||
bool writeXml( QDomElement &element, QDomDocument &document, const QgsReadWriteContext &context ) const override;
|
||||
QList< QgsAnnotationItemNode > nodes() const override;
|
||||
QgsGeometry rubberBandGeometry() const override;
|
||||
bool transform( const QTransform &transform ) override;
|
||||
Qgis::AnnotationItemEditOperationResult applyEdit( QgsAbstractAnnotationItemEditOperation *operation ) override;
|
||||
QgsAnnotationItemEditOperationTransientResults *transientEditResults( QgsAbstractAnnotationItemEditOperation *operation ) override SIP_FACTORY;
|
||||
|
||||
|
@ -197,18 +197,28 @@ void QgsMapToolModifyAnnotation::cadCanvasMoveEvent( QgsMapMouseEvent *event )
|
||||
|
||||
case Action::MoveItem:
|
||||
{
|
||||
#if 0
|
||||
const QgsVector delta = event->mapPoint() - mMoveStartPointCanvasCrs;
|
||||
if ( mTemporaryRubberBand )
|
||||
#endif
|
||||
|
||||
if ( QgsAnnotationItem *item = annotationItemFromId( mSelectedItemLayerId, mSelectedItemId ) )
|
||||
{
|
||||
mTemporaryRubberBand->setTranslationOffset( delta.x(), delta.y() );
|
||||
mTemporaryRubberBand->updatePosition();
|
||||
mTemporaryRubberBand->update();
|
||||
}
|
||||
for ( QgsRubberBand *band : mHoveredItemNodeRubberBands )
|
||||
{
|
||||
band->setTranslationOffset( delta.x(), delta.y() );
|
||||
band->updatePosition();
|
||||
band->update();
|
||||
QgsAnnotationLayer *layer = annotationLayerFromId( mSelectedItemLayerId );
|
||||
const QgsVector delta = toLayerCoordinates( layer, event->mapPoint() ) - mMoveStartPointLayerCrs;
|
||||
|
||||
QgsAnnotationItemEditOperationTranslateItem operation( mSelectedItemId, delta.x(), delta.y() );
|
||||
std::unique_ptr< QgsAnnotationItemEditOperationTransientResults > operationResults( item->transientEditResults( &operation ) );
|
||||
if ( operationResults )
|
||||
{
|
||||
mTemporaryRubberBand.reset( new QgsRubberBand( mCanvas, operationResults->representativeGeometry().type() ) );
|
||||
const double scaleFactor = canvas()->fontMetrics().xHeight() * .2;
|
||||
mTemporaryRubberBand->setWidth( scaleFactor );
|
||||
mTemporaryRubberBand->setToGeometry( operationResults->representativeGeometry(), layer->crs() );
|
||||
}
|
||||
else
|
||||
{
|
||||
mTemporaryRubberBand.reset();
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
@ -285,16 +295,6 @@ void QgsMapToolModifyAnnotation::cadCanvasPressEvent( QgsMapMouseEvent *event )
|
||||
if ( hoveredNode.point().isEmpty() )
|
||||
{
|
||||
mCurrentAction = Action::MoveItem;
|
||||
|
||||
QgsAnnotationItem *item = annotationItemFromId( mSelectedItemLayerId, mSelectedItemId );
|
||||
QgsGeometry rubberBandGeom = item->rubberBandGeometry();
|
||||
if ( rubberBandGeom.isNull() )
|
||||
rubberBandGeom = mSelectedRubberBand->asGeometry();
|
||||
|
||||
mTemporaryRubberBand.reset( new QgsRubberBand( mCanvas, rubberBandGeom.type() ) );
|
||||
const double scaleFactor = canvas()->fontMetrics().xHeight() * .2;
|
||||
mTemporaryRubberBand->setWidth( scaleFactor );
|
||||
mTemporaryRubberBand->setToGeometry( rubberBandGeom, layer->crs() );
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -339,16 +339,21 @@ void QgsMapToolModifyAnnotation::cadCanvasPressEvent( QgsMapMouseEvent *event )
|
||||
else if ( event->button() == Qt::LeftButton )
|
||||
{
|
||||
// apply move
|
||||
if ( QgsAnnotationItem *item = annotationItemFromId( mSelectedItemLayerId, mSelectedItemId ) )
|
||||
if ( QgsAnnotationLayer *layer = annotationLayerFromId( mSelectedItemLayerId ) )
|
||||
{
|
||||
QgsAnnotationLayer *layer = annotationLayerFromId( mSelectedItemLayerId );
|
||||
const QgsVector delta = toLayerCoordinates( layer, event->mapPoint() ) - mMoveStartPointLayerCrs;
|
||||
const QTransform transform = QTransform::fromTranslate( delta.x(), delta.y() );
|
||||
|
||||
std::unique_ptr< QgsAnnotationItem > transformedItem( item->clone() );
|
||||
transformedItem->transform( transform );
|
||||
layer->replaceItem( mSelectedItemId, transformedItem.release() );
|
||||
mRefreshSelectedItemAfterRedraw = true;
|
||||
QgsAnnotationItemEditOperationTranslateItem operation( mSelectedItemId, delta.x(), delta.y() );
|
||||
switch ( layer->applyEdit( &operation ) )
|
||||
{
|
||||
case Qgis::AnnotationItemEditOperationResult::Success:
|
||||
QgsProject::instance()->setDirty( true );
|
||||
mRefreshSelectedItemAfterRedraw = true;
|
||||
break;
|
||||
case Qgis::AnnotationItemEditOperationResult::Invalid:
|
||||
case Qgis::AnnotationItemEditOperationResult::ItemCleared:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
mTemporaryRubberBand.reset();
|
||||
@ -422,18 +427,22 @@ void QgsMapToolModifyAnnotation::keyPressEvent( QKeyEvent *event )
|
||||
|| event->key() == Qt::Key_Down )
|
||||
{
|
||||
QgsAnnotationLayer *layer = annotationLayerFromId( mSelectedItemLayerId );
|
||||
QgsAnnotationItem *annotationItem = annotationItemFromId( mSelectedItemLayerId, mSelectedItemId );
|
||||
if ( !layer || !annotationItem )
|
||||
if ( !layer )
|
||||
return;
|
||||
|
||||
const QSizeF deltaLayerCoordinates = deltaForKeyEvent( layer, mSelectedRubberBand->asGeometry().centroid().asPoint(), event );
|
||||
const QTransform transform = QTransform::fromTranslate( deltaLayerCoordinates.width(), deltaLayerCoordinates.height() );
|
||||
|
||||
std::unique_ptr< QgsAnnotationItem > transformedItem( annotationItem->clone() );
|
||||
transformedItem->transform( transform );
|
||||
layer->replaceItem( mSelectedItemId, transformedItem.release() );
|
||||
mRefreshSelectedItemAfterRedraw = true;
|
||||
|
||||
QgsAnnotationItemEditOperationTranslateItem operation( mSelectedItemId, deltaLayerCoordinates.width(), deltaLayerCoordinates.height() );
|
||||
switch ( layer->applyEdit( &operation ) )
|
||||
{
|
||||
case Qgis::AnnotationItemEditOperationResult::Success:
|
||||
QgsProject::instance()->setDirty( true );
|
||||
mRefreshSelectedItemAfterRedraw = true;
|
||||
break;
|
||||
case Qgis::AnnotationItemEditOperationResult::Invalid:
|
||||
case Qgis::AnnotationItemEditOperationResult::ItemCleared:
|
||||
break;
|
||||
}
|
||||
event->ignore(); // disable default shortcut handling (move map)
|
||||
}
|
||||
break;
|
||||
|
@ -52,11 +52,6 @@ class TestItem : public QgsAnnotationItem
|
||||
return new TestItem();
|
||||
}
|
||||
|
||||
bool transform( const QTransform & ) override
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool writeXml( QDomElement &, QDomDocument &, const QgsReadWriteContext & ) const override
|
||||
{
|
||||
return true;
|
||||
|
@ -68,7 +68,6 @@ class TestItem : public QgsAnnotationItem // clazy:exclude=missing-qobject-macro
|
||||
void render( QgsRenderContext &, QgsFeedback * ) override {}
|
||||
bool writeXml( QDomElement &, QDomDocument &, const QgsReadWriteContext & ) const override { return true; }
|
||||
bool readXml( const QDomElement &, const QgsReadWriteContext & ) override { return true; }
|
||||
bool transform( const QTransform & ) override { return true; }
|
||||
};
|
||||
|
||||
class TestItemWidget: public QgsAnnotationItemBaseWidget
|
||||
|
@ -38,7 +38,8 @@ from qgis.core import (QgsMapSettings,
|
||||
Qgis,
|
||||
QgsVertexId,
|
||||
QgsAnnotationItemEditOperationMoveNode,
|
||||
QgsAnnotationItemEditOperationDeleteNode
|
||||
QgsAnnotationItemEditOperationDeleteNode,
|
||||
QgsAnnotationItemEditOperationTranslateItem
|
||||
)
|
||||
from qgis.PyQt.QtXml import QDomDocument
|
||||
|
||||
@ -87,8 +88,7 @@ class TestQgsAnnotationLineItem(unittest.TestCase):
|
||||
item = QgsAnnotationLineItem(QgsLineString([QgsPoint(12, 13), QgsPoint(14, 13), QgsPoint(14, 15)]))
|
||||
self.assertEqual(item.geometry().asWkt(), 'LineString (12 13, 14 13, 14 15)')
|
||||
|
||||
transform = QTransform.fromTranslate(100, 200)
|
||||
item.transform(transform)
|
||||
self.assertEqual(item.applyEdit(QgsAnnotationItemEditOperationTranslateItem('', 100, 200)), Qgis.AnnotationItemEditOperationResult.Success)
|
||||
self.assertEqual(item.geometry().asWkt(), 'LineString (112 213, 114 213, 114 215)')
|
||||
|
||||
def test_apply_move_node_edit(self):
|
||||
@ -122,13 +122,12 @@ class TestQgsAnnotationLineItem(unittest.TestCase):
|
||||
res = item.transientEditResults(QgsAnnotationItemEditOperationMoveNode('', QgsVertexId(0, 0, 1), QgsPoint(14, 13), QgsPoint(17, 18)))
|
||||
self.assertEqual(res.representativeGeometry().asWkt(), 'LineString (12 13, 17 18, 14 15)')
|
||||
|
||||
def test_rubberbandgeometry(self):
|
||||
"""
|
||||
Test creating rubber band geometry
|
||||
"""
|
||||
def test_transient_translate_operation(self):
|
||||
item = QgsAnnotationLineItem(QgsLineString([QgsPoint(12, 13), QgsPoint(14, 13), QgsPoint(14, 15)]))
|
||||
band = item.rubberBandGeometry()
|
||||
self.assertEqual(band.asWkt(), 'LineString (12 13, 14 13, 14 15)')
|
||||
self.assertEqual(item.geometry().asWkt(), 'LineString (12 13, 14 13, 14 15)')
|
||||
|
||||
res = item.transientEditResults(QgsAnnotationItemEditOperationTranslateItem('', 100, 200))
|
||||
self.assertEqual(res.representativeGeometry().asWkt(), 'LineString (112 213, 114 213, 114 215)')
|
||||
|
||||
def testReadWriteXml(self):
|
||||
doc = QDomDocument("testdoc")
|
||||
|
@ -36,7 +36,8 @@ from qgis.core import (QgsMapSettings,
|
||||
QgsPointXY,
|
||||
QgsVertexId,
|
||||
QgsAnnotationItemEditOperationMoveNode,
|
||||
QgsAnnotationItemEditOperationDeleteNode
|
||||
QgsAnnotationItemEditOperationDeleteNode,
|
||||
QgsAnnotationItemEditOperationTranslateItem
|
||||
)
|
||||
from qgis.PyQt.QtXml import QDomDocument
|
||||
|
||||
@ -85,8 +86,7 @@ class TestQgsAnnotationMarkerItem(unittest.TestCase):
|
||||
item = QgsAnnotationMarkerItem(QgsPoint(12, 13))
|
||||
self.assertEqual(item.geometry().asWkt(), 'POINT(12 13)')
|
||||
|
||||
transform = QTransform.fromTranslate(100, 200)
|
||||
item.transform(transform)
|
||||
self.assertEqual(item.applyEdit(QgsAnnotationItemEditOperationTranslateItem('', 100, 200)), Qgis.AnnotationItemEditOperationResult.Success)
|
||||
self.assertEqual(item.geometry().asWkt(), 'POINT(112 213)')
|
||||
|
||||
def test_apply_move_node_edit(self):
|
||||
@ -109,6 +109,13 @@ class TestQgsAnnotationMarkerItem(unittest.TestCase):
|
||||
res = item.transientEditResults(QgsAnnotationItemEditOperationMoveNode('', QgsVertexId(0, 0, 0), QgsPoint(12, 13), QgsPoint(17, 18)))
|
||||
self.assertEqual(res.representativeGeometry().asWkt(), 'Point (17 18)')
|
||||
|
||||
def test_transient_translate_operation(self):
|
||||
item = QgsAnnotationMarkerItem(QgsPoint(12, 13))
|
||||
self.assertEqual(item.geometry().asWkt(), 'POINT(12 13)')
|
||||
|
||||
res = item.transientEditResults(QgsAnnotationItemEditOperationTranslateItem('', 100, 200))
|
||||
self.assertEqual(res.representativeGeometry().asWkt(), 'Point (112 213)')
|
||||
|
||||
def testReadWriteXml(self):
|
||||
doc = QDomDocument("testdoc")
|
||||
elem = doc.createElement('test')
|
||||
|
@ -38,6 +38,7 @@ from qgis.core import (QgsMapSettings,
|
||||
QgsVertexId,
|
||||
QgsAnnotationItemEditOperationMoveNode,
|
||||
QgsAnnotationItemEditOperationDeleteNode,
|
||||
QgsAnnotationItemEditOperationTranslateItem,
|
||||
QgsPoint
|
||||
)
|
||||
from qgis.PyQt.QtXml import QDomDocument
|
||||
@ -97,8 +98,7 @@ class TestQgsAnnotationPointTextItem(unittest.TestCase):
|
||||
item = QgsAnnotationPointTextItem('my text', QgsPointXY(12, 13))
|
||||
self.assertEqual(item.point().asWkt(), 'POINT(12 13)')
|
||||
|
||||
transform = QTransform.fromTranslate(100, 200)
|
||||
item.transform(transform)
|
||||
self.assertEqual(item.applyEdit(QgsAnnotationItemEditOperationTranslateItem('', 100, 200)), Qgis.AnnotationItemEditOperationResult.Success)
|
||||
self.assertEqual(item.point().asWkt(), 'POINT(112 213)')
|
||||
|
||||
def test_apply_move_node_edit(self):
|
||||
@ -115,6 +115,13 @@ class TestQgsAnnotationPointTextItem(unittest.TestCase):
|
||||
res = item.transientEditResults(QgsAnnotationItemEditOperationMoveNode('', QgsVertexId(0, 0, 0), QgsPoint(12, 13), QgsPoint(17, 18)))
|
||||
self.assertEqual(res.representativeGeometry().asWkt(), 'Point (17 18)')
|
||||
|
||||
def test_transient_translate_operation(self):
|
||||
item = QgsAnnotationPointTextItem('my text', QgsPointXY(12, 13))
|
||||
self.assertEqual(item.point().asWkt(), 'POINT(12 13)')
|
||||
|
||||
res = item.transientEditResults(QgsAnnotationItemEditOperationTranslateItem('', 100, 200))
|
||||
self.assertEqual(res.representativeGeometry().asWkt(), 'Point (112 213)')
|
||||
|
||||
def test_apply_delete_node_edit(self):
|
||||
item = QgsAnnotationPointTextItem('my text', QgsPointXY(12, 13))
|
||||
self.assertEqual(item.point().asWkt(), 'POINT(12 13)')
|
||||
|
@ -40,7 +40,8 @@ from qgis.core import (QgsMapSettings,
|
||||
QgsPointXY,
|
||||
QgsVertexId,
|
||||
QgsAnnotationItemEditOperationMoveNode,
|
||||
QgsAnnotationItemEditOperationDeleteNode
|
||||
QgsAnnotationItemEditOperationDeleteNode,
|
||||
QgsAnnotationItemEditOperationTranslateItem
|
||||
)
|
||||
from qgis.PyQt.QtXml import QDomDocument
|
||||
|
||||
@ -86,20 +87,11 @@ class TestQgsAnnotationPolygonItem(unittest.TestCase):
|
||||
QgsAnnotationItemNode(QgsVertexId(0, 0, 1), QgsPointXY(14, 13), Qgis.AnnotationItemNodeType.VertexHandle),
|
||||
QgsAnnotationItemNode(QgsVertexId(0, 0, 2), QgsPointXY(14, 15), Qgis.AnnotationItemNodeType.VertexHandle)])
|
||||
|
||||
def test_rubberbandgeometry(self):
|
||||
"""
|
||||
Test creating rubber band geometry
|
||||
"""
|
||||
item = QgsAnnotationPolygonItem(QgsPolygon(QgsLineString([QgsPoint(12, 13), QgsPoint(14, 13), QgsPoint(14, 15), QgsPoint(12, 13)])))
|
||||
band = item.rubberBandGeometry()
|
||||
self.assertEqual(band.asWkt(), 'Polygon ((12 13, 14 13, 14 15, 12 13))')
|
||||
|
||||
def test_transform(self):
|
||||
item = QgsAnnotationPolygonItem(QgsPolygon(QgsLineString([QgsPoint(12, 13), QgsPoint(14, 13), QgsPoint(14, 15), QgsPoint(12, 13)])))
|
||||
self.assertEqual(item.geometry().asWkt(), 'Polygon ((12 13, 14 13, 14 15, 12 13))')
|
||||
|
||||
transform = QTransform.fromTranslate(100, 200)
|
||||
item.transform(transform)
|
||||
self.assertEqual(item.applyEdit(QgsAnnotationItemEditOperationTranslateItem('', 100, 200)), Qgis.AnnotationItemEditOperationResult.Success)
|
||||
self.assertEqual(item.geometry().asWkt(), 'Polygon ((112 213, 114 213, 114 215, 112 213))')
|
||||
|
||||
def test_apply_move_node_edit(self):
|
||||
@ -137,6 +129,14 @@ class TestQgsAnnotationPolygonItem(unittest.TestCase):
|
||||
res = item.transientEditResults(QgsAnnotationItemEditOperationMoveNode('', QgsVertexId(0, 0, 1), QgsPoint(14, 13), QgsPoint(17, 18)))
|
||||
self.assertEqual(res.representativeGeometry().asWkt(), 'Polygon ((12 13, 17 18, 14 15, 12 13))')
|
||||
|
||||
def test_transient_translate_operation(self):
|
||||
item = QgsAnnotationPolygonItem(
|
||||
QgsPolygon(QgsLineString([QgsPoint(12, 13), QgsPoint(14, 13), QgsPoint(14, 15), QgsPoint(12, 13)])))
|
||||
self.assertEqual(item.geometry().asWkt(), 'Polygon ((12 13, 14 13, 14 15, 12 13))')
|
||||
|
||||
res = item.transientEditResults(QgsAnnotationItemEditOperationTranslateItem('', 100, 200))
|
||||
self.assertEqual(res.representativeGeometry().asWkt(), 'Polygon ((112 213, 114 213, 114 215, 112 213))')
|
||||
|
||||
def testReadWriteXml(self):
|
||||
doc = QDomDocument("testdoc")
|
||||
elem = doc.createElement('test')
|
||||
|
Loading…
x
Reference in New Issue
Block a user