Introduce intermediate base class QgsAbstractVectorLayer3DRenderer

This will be useful as we start adding more properties that are common
among all vector layer 3D renderers (such as tiling configuration)
This commit is contained in:
Martin Dobias 2020-01-10 13:50:05 +01:00
parent 932cd65c78
commit 89829c5191
10 changed files with 130 additions and 87 deletions

View File

@ -39,7 +39,7 @@ Creates an instance of a 3D renderer based on a DOM element with renderer config
};
class QgsRuleBased3DRenderer : QgsAbstract3DRenderer
class QgsRuleBased3DRenderer : QgsAbstractVectorLayer3DRenderer
{
%Docstring
Rule-based 3D renderer.
@ -244,15 +244,6 @@ Construct renderer with the given root rule (takes ownership)
%End
~QgsRuleBased3DRenderer();
void setLayer( QgsVectorLayer *layer );
%Docstring
Sets vector layer associated with the renderer
%End
QgsVectorLayer *layer() const;
%Docstring
Returns vector layer associated with the renderer
%End
QgsRuleBased3DRenderer::Rule *rootRule();
%Docstring
Returns pointer to the root rule
@ -266,8 +257,6 @@ Returns pointer to the root rule
virtual void readXml( const QDomElement &elem, const QgsReadWriteContext &context );
virtual void resolveReferences( const QgsProject &project );
};

View File

@ -41,7 +41,7 @@ Creates an instance of a 3D renderer based on a DOM element with renderer config
};
class QgsVectorLayer3DRenderer : QgsAbstract3DRenderer
class QgsVectorLayer3DRenderer : QgsAbstractVectorLayer3DRenderer
{
%Docstring
3D renderer that renders all features of a vector layer with the same 3D symbol.
@ -57,15 +57,6 @@ The appearance is completely defined by the symbol.
explicit QgsVectorLayer3DRenderer( QgsAbstract3DSymbol *s /Transfer/ = 0 );
%Docstring
Takes ownership of the symbol object
%End
void setLayer( QgsVectorLayer *layer );
%Docstring
Sets vector layer associated with the renderer
%End
QgsVectorLayer *layer() const;
%Docstring
Returns vector layer associated with the renderer
%End
void setSymbol( QgsAbstract3DSymbol *symbol /Transfer/ );
@ -85,8 +76,6 @@ Returns 3D symbol associated with the renderer
virtual void readXml( const QDomElement &elem, const QgsReadWriteContext &context );
virtual void resolveReferences( const QgsProject &project );
private:
QgsVectorLayer3DRenderer( const QgsVectorLayer3DRenderer & );

View File

@ -4,6 +4,7 @@
SET(QGIS_3D_SRCS
qgsaabb.cpp
qgsabstract3dengine.cpp
qgsabstractvectorlayer3drenderer.cpp
qgs3danimationsettings.cpp
qgs3dmapscene.cpp
qgs3dmapsettings.cpp
@ -72,6 +73,7 @@ SET(QGIS_3D_HDRS
qgs3dutils.h
qgsaabb.h
qgsabstract3dengine.h
qgsabstractvectorlayer3drenderer.h
qgscameracontroller.h
qgscamerapose.h
qgslayoutitem3dmap.h

View File

@ -536,15 +536,11 @@ void Qgs3DMapScene::addLayerEntity( QgsMapLayer *layer )
// Fix vector layer's renderer to make sure the renderer is pointing to its layer.
// It has happened before that renderer pointed to a different layer (probably after copying a style).
// This is a bit of a hack and it should be handled in QgsMapLayer::setRenderer3D() but in qgis_core
// the vector layer 3D renderer class is not available. Maybe we need an intermediate map layer 3D renderer
// class in qgis_core that can be used to handle this case nicely.
if ( layer->type() == QgsMapLayerType::VectorLayer && renderer->type() == QLatin1String( "vector" ) )
// the vector layer 3D renderer classes are not available.
if ( layer->type() == QgsMapLayerType::VectorLayer &&
( renderer->type() == QLatin1String( "vector" ) || renderer->type() == QLatin1String( "rulebased" ) ) )
{
static_cast<QgsVectorLayer3DRenderer *>( renderer )->setLayer( static_cast<QgsVectorLayer *>( layer ) );
}
else if ( layer->type() == QgsMapLayerType::VectorLayer && renderer->type() == QLatin1String( "rulebased" ) )
{
static_cast<QgsRuleBased3DRenderer *>( renderer )->setLayer( static_cast<QgsVectorLayer *>( layer ) );
static_cast<QgsAbstractVectorLayer3DRenderer *>( renderer )->setLayer( static_cast<QgsVectorLayer *>( layer ) );
}
else if ( layer->type() == QgsMapLayerType::MeshLayer && renderer->type() == QLatin1String( "mesh" ) )
{

View File

@ -0,0 +1,55 @@
/***************************************************************************
qgsabstractvectorlayer3drenderer.cpp
--------------------------------------
Date : January 2020
Copyright : (C) 2020 by Martin Dobias
Email : wonder dot sk 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 "qgsabstractvectorlayer3drenderer.h"
#include "qgsvectorlayer.h"
QgsAbstractVectorLayer3DRenderer::QgsAbstractVectorLayer3DRenderer()
{
}
void QgsAbstractVectorLayer3DRenderer::setLayer( QgsVectorLayer *layer )
{
mLayerRef = QgsMapLayerRef( layer );
}
QgsVectorLayer *QgsAbstractVectorLayer3DRenderer::layer() const
{
return qobject_cast<QgsVectorLayer *>( mLayerRef.layer );
}
void QgsAbstractVectorLayer3DRenderer::copyBaseProperties( QgsAbstractVectorLayer3DRenderer *r ) const
{
r->mLayerRef = mLayerRef;
}
void QgsAbstractVectorLayer3DRenderer::writeXmlBaseProperties( QDomElement &elem, const QgsReadWriteContext &context ) const
{
Q_UNUSED( context )
elem.setAttribute( QStringLiteral( "layer" ), mLayerRef.layerId );
}
void QgsAbstractVectorLayer3DRenderer::readXmlBaseProperties( const QDomElement &elem, const QgsReadWriteContext &context )
{
Q_UNUSED( context )
mLayerRef = QgsMapLayerRef( elem.attribute( QStringLiteral( "layer" ) ) );
}
void QgsAbstractVectorLayer3DRenderer::resolveReferences( const QgsProject &project )
{
mLayerRef.setLayer( project.mapLayer( mLayerRef.layerId ) );
}

View File

@ -0,0 +1,57 @@
/***************************************************************************
qgsabstractvectorlayer3drenderer.h
--------------------------------------
Date : January 2020
Copyright : (C) 2020 by Martin Dobias
Email : wonder dot sk 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 QGSABSTRACTVECTORLAYER3DRENDERER_H
#define QGSABSTRACTVECTORLAYER3DRENDERER_H
#include "qgis_3d.h"
#include "qgsabstract3drenderer.h"
#include "qgsmaplayerref.h"
class QgsVectorLayer;
/**
* \ingroup 3d
* Base class for 3D renderers that are based on vector layers.
*
* \since QGIS 3.12
*/
class _3D_EXPORT QgsAbstractVectorLayer3DRenderer : public QgsAbstract3DRenderer
{
public:
QgsAbstractVectorLayer3DRenderer();
//! Sets vector layer associated with the renderer
void setLayer( QgsVectorLayer *layer );
//! Returns vector layer associated with the renderer
QgsVectorLayer *layer() const;
void resolveReferences( const QgsProject &project ) override;
protected:
//! copy common properties of this object to another object
void copyBaseProperties( QgsAbstractVectorLayer3DRenderer *r ) const;
//! write common properties of this object to DOM element
void writeXmlBaseProperties( QDomElement &elem, const QgsReadWriteContext &context ) const;
//! read common properties of this object from DOM element
void readXmlBaseProperties( const QDomElement &elem, const QgsReadWriteContext &context );
private:
QgsMapLayerRef mLayerRef; //!< Layer used to extract polygons from
};
#endif // QGSABSTRACTVECTORLAYER3DRENDERER_H

View File

@ -395,20 +395,10 @@ QgsRuleBased3DRenderer *QgsRuleBased3DRenderer::clone() const
clonedDescendants[i]->setRuleKey( origDescendants[i]->ruleKey() );
QgsRuleBased3DRenderer *r = new QgsRuleBased3DRenderer( rootRule );
r->mLayerRef = mLayerRef;
copyBaseProperties( r );
return r;
}
void QgsRuleBased3DRenderer::setLayer( QgsVectorLayer *layer )
{
mLayerRef = QgsMapLayerRef( layer );
}
QgsVectorLayer *QgsRuleBased3DRenderer::layer() const
{
return qobject_cast<QgsVectorLayer *>( mLayerRef.layer );
}
Qt3DCore::QEntity *QgsRuleBased3DRenderer::createEntity( const Qgs3DMapSettings &map ) const
{
QgsVectorLayer *vl = layer();
@ -423,7 +413,7 @@ void QgsRuleBased3DRenderer::writeXml( QDomElement &elem, const QgsReadWriteCont
{
QDomDocument doc = elem.ownerDocument();
elem.setAttribute( QStringLiteral( "layer" ), mLayerRef.layerId );
writeXmlBaseProperties( elem, context );
QDomElement rulesElem = mRootRule->save( doc, context );
rulesElem.setTagName( QStringLiteral( "rules" ) ); // instead of just "rule"
@ -432,13 +422,7 @@ void QgsRuleBased3DRenderer::writeXml( QDomElement &elem, const QgsReadWriteCont
void QgsRuleBased3DRenderer::readXml( const QDomElement &elem, const QgsReadWriteContext &context )
{
Q_UNUSED( context )
mLayerRef = QgsMapLayerRef( elem.attribute( QStringLiteral( "layer" ) ) );
readXmlBaseProperties( elem, context );
// root rule is read before class constructed
}
void QgsRuleBased3DRenderer::resolveReferences( const QgsProject &project )
{
mLayerRef.setLayer( project.mapLayer( mLayerRef.layerId ) );
}

View File

@ -19,7 +19,7 @@
#include "qgis_3d.h"
#include "qgs3drendererregistry.h"
#include "qgsabstract3drenderer.h"
#include "qgsabstractvectorlayer3drenderer.h"
#include "qgsabstract3dsymbol.h"
#include "qgsmaplayerref.h"
@ -58,7 +58,7 @@ class _3D_EXPORT QgsRuleBased3DRendererMetadata : public Qgs3DRendererAbstractMe
*
* \since QGIS 3.6
*/
class _3D_EXPORT QgsRuleBased3DRenderer : public QgsAbstract3DRenderer
class _3D_EXPORT QgsRuleBased3DRenderer : public QgsAbstractVectorLayer3DRenderer
{
public:
@ -296,11 +296,6 @@ class _3D_EXPORT QgsRuleBased3DRenderer : public QgsAbstract3DRenderer
QgsRuleBased3DRenderer( QgsRuleBased3DRenderer::Rule *root SIP_TRANSFER );
~QgsRuleBased3DRenderer() override;
//! Sets vector layer associated with the renderer
void setLayer( QgsVectorLayer *layer );
//! Returns vector layer associated with the renderer
QgsVectorLayer *layer() const;
//! Returns pointer to the root rule
QgsRuleBased3DRenderer::Rule *rootRule() { return mRootRule; }
//! Returns pointer to the root rule
@ -312,10 +307,8 @@ class _3D_EXPORT QgsRuleBased3DRenderer : public QgsAbstract3DRenderer
void writeXml( QDomElement &elem, const QgsReadWriteContext &context ) const override;
void readXml( const QDomElement &elem, const QgsReadWriteContext &context ) override;
void resolveReferences( const QgsProject &project ) override;
private:
QgsMapLayerRef mLayerRef; //!< Layer used to extract polygons from
Rule *mRootRule = nullptr;
};

View File

@ -49,20 +49,10 @@ QgsVectorLayer3DRenderer::QgsVectorLayer3DRenderer( QgsAbstract3DSymbol *s )
QgsVectorLayer3DRenderer *QgsVectorLayer3DRenderer::clone() const
{
QgsVectorLayer3DRenderer *r = new QgsVectorLayer3DRenderer( mSymbol ? mSymbol->clone() : nullptr );
r->mLayerRef = mLayerRef;
copyBaseProperties( r );
return r;
}
void QgsVectorLayer3DRenderer::setLayer( QgsVectorLayer *layer )
{
mLayerRef = QgsMapLayerRef( layer );
}
QgsVectorLayer *QgsVectorLayer3DRenderer::layer() const
{
return qobject_cast<QgsVectorLayer *>( mLayerRef.layer );
}
void QgsVectorLayer3DRenderer::setSymbol( QgsAbstract3DSymbol *symbol )
{
mSymbol.reset( symbol );
@ -87,7 +77,7 @@ void QgsVectorLayer3DRenderer::writeXml( QDomElement &elem, const QgsReadWriteCo
{
QDomDocument doc = elem.ownerDocument();
elem.setAttribute( QStringLiteral( "layer" ), mLayerRef.layerId );
writeXmlBaseProperties( elem, context );
QDomElement elemSymbol = doc.createElement( QStringLiteral( "symbol" ) );
if ( mSymbol )
@ -100,7 +90,7 @@ void QgsVectorLayer3DRenderer::writeXml( QDomElement &elem, const QgsReadWriteCo
void QgsVectorLayer3DRenderer::readXml( const QDomElement &elem, const QgsReadWriteContext &context )
{
mLayerRef = QgsMapLayerRef( elem.attribute( QStringLiteral( "layer" ) ) );
readXmlBaseProperties( elem, context );
QDomElement elemSymbol = elem.firstChildElement( QStringLiteral( "symbol" ) );
QString symbolType = elemSymbol.attribute( QStringLiteral( "type" ) );
@ -116,8 +106,3 @@ void QgsVectorLayer3DRenderer::readXml( const QDomElement &elem, const QgsReadWr
symbol->readXml( elemSymbol, context );
mSymbol.reset( symbol );
}
void QgsVectorLayer3DRenderer::resolveReferences( const QgsProject &project )
{
mLayerRef.setLayer( project.mapLayer( mLayerRef.layerId ) );
}

View File

@ -20,7 +20,7 @@
#include "qgis_sip.h"
#include "qgs3drendererregistry.h"
#include "qgsabstract3drenderer.h"
#include "qgsabstractvectorlayer3drenderer.h"
#include "qgsabstract3dsymbol.h"
#include "qgsphongmaterialsettings.h"
@ -57,17 +57,12 @@ class _3D_EXPORT QgsVectorLayer3DRendererMetadata : public Qgs3DRendererAbstract
* The appearance is completely defined by the symbol.
* \since QGIS 3.0
*/
class _3D_EXPORT QgsVectorLayer3DRenderer : public QgsAbstract3DRenderer
class _3D_EXPORT QgsVectorLayer3DRenderer : public QgsAbstractVectorLayer3DRenderer
{
public:
//! Takes ownership of the symbol object
explicit QgsVectorLayer3DRenderer( QgsAbstract3DSymbol *s SIP_TRANSFER = nullptr );
//! Sets vector layer associated with the renderer
void setLayer( QgsVectorLayer *layer );
//! Returns vector layer associated with the renderer
QgsVectorLayer *layer() const;
//! Sets 3D symbol associated with the renderer. Takes ownership of the symbol
void setSymbol( QgsAbstract3DSymbol *symbol SIP_TRANSFER );
//! Returns 3D symbol associated with the renderer
@ -79,10 +74,8 @@ class _3D_EXPORT QgsVectorLayer3DRenderer : public QgsAbstract3DRenderer
void writeXml( QDomElement &elem, const QgsReadWriteContext &context ) const override;
void readXml( const QDomElement &elem, const QgsReadWriteContext &context ) override;
void resolveReferences( const QgsProject &project ) override;
private:
QgsMapLayerRef mLayerRef; //!< Layer used to extract polygons from
std::unique_ptr<QgsAbstract3DSymbol> mSymbol; //!< 3D symbol that defines appearance
private: