23QgsReportSectionFieldGroup::QgsReportSectionFieldGroup( QgsAbstractReportSection *parent )
24 : QgsAbstractReportSection( parent )
29QString QgsReportSectionFieldGroup::description()
const
32 return QObject::tr(
"Group: %1 - %2" ).arg( mCoverageLayer->name(), mField );
34 return QObject::tr(
"Group" );
37QIcon QgsReportSectionFieldGroup::icon()
const
42QgsReportSectionFieldGroup *QgsReportSectionFieldGroup::clone()
const
44 auto copy = std::make_unique< QgsReportSectionFieldGroup >(
nullptr );
45 copyCommonProperties( copy.get() );
49 copy->mBody.reset( mBody->clone() );
54 copy->setLayer( mCoverageLayer.get() );
55 copy->setField( mField );
56 copy->setSortAscending( mSortAscending );
57 copy->setBodyEnabled( mBodyEnabled );
59 return copy.release();
62bool QgsReportSectionFieldGroup::beginRender()
64 if ( !mCoverageLayer )
67 if ( !mField.isEmpty() )
69 mFieldIndex = mCoverageLayer->fields().lookupField( mField );
70 if ( mFieldIndex < 0 )
74 mBody->reportContext().setLayer( mCoverageLayer.get() );
78 return QgsAbstractReportSection::beginRender();
81bool QgsReportSectionFieldGroup::prepareHeader()
86 if ( !mFeatures.isValid() )
88 mFeatures = mCoverageLayer->getFeatures( buildFeatureRequest() );
91 mHeaderFeature = getNextFeature();
92 header()->reportContext().blockSignals(
true );
93 header()->reportContext().setLayer( mCoverageLayer.get() );
94 header()->reportContext().blockSignals(
false );
95 header()->reportContext().setFeature( mHeaderFeature );
96 mSkipNextRequest =
true;
97 mNoFeatures = !mHeaderFeature.isValid();
98 return mHeaderVisibility == AlwaysInclude || !mNoFeatures;
101bool QgsReportSectionFieldGroup::prepareFooter()
103 return mFooterVisibility == AlwaysInclude || !mNoFeatures;
106QgsLayout *QgsReportSectionFieldGroup::nextBody(
bool &ok )
108 if ( !mFeatures.isValid() )
110 mFeatures = mCoverageLayer->getFeatures( buildFeatureRequest() );
114 if ( !mSkipNextRequest )
116 f = getNextFeature();
121 mSkipNextRequest =
false;
129 if (
auto *lFooter = footer() )
131 lFooter->reportContext().blockSignals(
true );
132 lFooter->reportContext().setLayer( mCoverageLayer.get() );
133 lFooter->reportContext().blockSignals(
false );
134 lFooter->reportContext().setFeature( mLastFeature );
142 updateChildContexts( f );
145 if ( mBody && mBodyEnabled )
147 mBody->reportContext().blockSignals(
true );
148 mBody->reportContext().setLayer( mCoverageLayer.get() );
149 mBody->reportContext().blockSignals(
false );
150 mBody->reportContext().setFeature( f );
153 return mBodyEnabled ? mBody.get() :
nullptr;
156void QgsReportSectionFieldGroup::reset()
158 QgsAbstractReportSection::reset();
159 mEncounteredValues.clear();
160 mSkipNextRequest =
false;
167void QgsReportSectionFieldGroup::setParentSection( QgsAbstractReportSection *parent )
169 QgsAbstractReportSection::setParentSection( parent );
170 if ( !mCoverageLayer )
171 mCoverageLayer.resolveWeakly( project() );
174void QgsReportSectionFieldGroup::reloadSettings()
176 QgsAbstractReportSection::reloadSettings();
178 mBody->reloadSettings();
181bool QgsReportSectionFieldGroup::writePropertiesToElement( QDomElement &element, QDomDocument &doc,
const QgsReadWriteContext &context )
const
183 element.setAttribute( QStringLiteral(
"headerVisibility" ),
static_cast< int >( mHeaderVisibility ) );
184 element.setAttribute( QStringLiteral(
"footerVisibility" ),
static_cast< int >( mFooterVisibility ) );
185 element.setAttribute( QStringLiteral(
"field" ), mField );
186 element.setAttribute( QStringLiteral(
"ascending" ), mSortAscending ? QStringLiteral(
"1" ) : QStringLiteral(
"0" ) );
187 element.setAttribute( QStringLiteral(
"bodyEnabled" ), mBodyEnabled ? QStringLiteral(
"1" ) : QStringLiteral(
"0" ) );
188 if ( mCoverageLayer )
190 element.setAttribute( QStringLiteral(
"coverageLayer" ), mCoverageLayer.layerId );
191 element.setAttribute( QStringLiteral(
"coverageLayerName" ), mCoverageLayer.name );
192 element.setAttribute( QStringLiteral(
"coverageLayerSource" ), mCoverageLayer.source );
193 element.setAttribute( QStringLiteral(
"coverageLayerProvider" ), mCoverageLayer.provider );
198 QDomElement bodyElement = doc.createElement( QStringLiteral(
"body" ) );
199 bodyElement.appendChild( mBody->writeXml( doc, context ) );
200 element.appendChild( bodyElement );
205bool QgsReportSectionFieldGroup::readPropertiesFromElement(
const QDomElement &element,
const QDomDocument &doc,
const QgsReadWriteContext &context )
207 mHeaderVisibility =
static_cast< SectionVisibility
>( element.attribute( QStringLiteral(
"headerVisibility" ) ).toInt() );
208 mFooterVisibility =
static_cast< SectionVisibility
>( element.attribute( QStringLiteral(
"footerVisibility" ) ).toInt() );
209 mField = element.attribute( QStringLiteral(
"field" ) );
210 mSortAscending = element.attribute( QStringLiteral(
"ascending" ) ).toInt();
211 mBodyEnabled = element.attribute( QStringLiteral(
"bodyEnabled" ) ).toInt();
212 QString layerId = element.attribute( QStringLiteral(
"coverageLayer" ) );
213 QString layerName = element.attribute( QStringLiteral(
"coverageLayerName" ) );
214 QString layerSource = element.attribute( QStringLiteral(
"coverageLayerSource" ) );
215 QString layerProvider = element.attribute( QStringLiteral(
"coverageLayerProvider" ) );
216 mCoverageLayer =
QgsVectorLayerRef( layerId, layerName, layerSource, layerProvider );
217 mCoverageLayer.resolveWeakly( project() );
219 const QDomElement bodyElement = element.firstChildElement( QStringLiteral(
"body" ) );
220 if ( !bodyElement.isNull() )
222 const QDomElement bodyLayoutElem = bodyElement.firstChild().toElement();
223 auto body = std::make_unique< QgsLayout >( project() );
224 body->readXml( bodyLayoutElem, doc, context );
225 mBody = std::move( body );
230bool QgsReportSectionFieldGroup::sortAscending()
const
232 return mSortAscending;
235void QgsReportSectionFieldGroup::setSortAscending(
bool sortAscending )
237 mSortAscending = sortAscending;
243 QVariantMap filter = context().fieldFilters;
245 QStringList filterParts;
246 for (
auto filterIt = filter.constBegin(); filterIt != filter.constEnd(); ++filterIt )
249 int fieldIndex = mCoverageLayer->fields().lookupField( filterIt.key() );
250 if ( fieldIndex >= 0 )
256 if ( !filterParts.empty() )
258 QString filterString = QStringLiteral(
"(%1)" ).arg( filterParts.join( QLatin1String(
") AND (" ) ) );
266QgsFeature QgsReportSectionFieldGroup::getNextFeature()
269 QVariant currentValue;
271 while ( first || ( ( !mBody || !mBodyEnabled ) && mEncounteredValues.contains( currentValue ) ) )
273 if ( !mFeatures.nextFeature( f ) )
279 currentValue = f.
attribute( mFieldIndex );
282 mEncounteredValues.insert( currentValue );
286void QgsReportSectionFieldGroup::updateChildContexts(
const QgsFeature &feature )
288 QgsReportSectionContext
c = context();
290 if ( mCoverageLayer )
291 c.currentLayer = mCoverageLayer.get();
293 QVariantMap currentFilter =
c.fieldFilters;
294 currentFilter.insert( mField, feature.
attribute( mFieldIndex ) );
295 c.fieldFilters = currentFilter;
297 const QList< QgsAbstractReportSection * > sections = childSections();
298 for ( QgsAbstractReportSection *section : std::as_const( sections ) )
300 section->setContext(
c );
static QIcon getThemeIcon(const QString &name, const QColor &fillColor=QColor(), const QColor &strokeColor=QColor())
Helper to get a theme icon.
static QString createFieldEqualityExpression(const QString &fieldName, const QVariant &value, QMetaType::Type fieldType=QMetaType::Type::UnknownType)
Create an expression allowing to evaluate if a field is equal to a value.
Wrapper for iterator of features from vector data provider or vector layer.
Wraps a request for features to a vector layer (or directly its vector data provider).
QgsFeatureRequest & addOrderBy(const QString &expression, bool ascending=true)
Adds a new OrderByClause, appending it as the least important one.
QgsFeatureRequest & setFilterExpression(const QString &expression)
Set the filter expression.
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
bool isValid() const
Returns the validity of this feature.
Q_INVOKABLE QVariant attribute(const QString &name) const
Lookup attribute value by attribute name.
Base class for layouts, which can contain items such as maps, labels, scalebars, etc.
A container for the context for various read/write operations on objects.
As part of the API refactoring and improvements which landed in the Processing API was substantially reworked from the x version This was done in order to allow much of the underlying Processing framework to be ported into c
_LayerRef< QgsVectorLayer > QgsVectorLayerRef