22QgsReportSectionFieldGroup::QgsReportSectionFieldGroup( QgsAbstractReportSection *parent )
 
   23  : QgsAbstractReportSection( parent )
 
   28QString QgsReportSectionFieldGroup::description()
 const 
   30  if ( mCoverageLayer.get() )
 
   31    return QObject::tr( 
"Group: %1 - %2" ).arg( mCoverageLayer->name(), mField );
 
   33    return QObject::tr( 
"Group" );
 
   36QIcon QgsReportSectionFieldGroup::icon()
 const 
   41QgsReportSectionFieldGroup *QgsReportSectionFieldGroup::clone()
 const 
   43  std::unique_ptr< QgsReportSectionFieldGroup > copy = std::make_unique< QgsReportSectionFieldGroup >( 
nullptr );
 
   44  copyCommonProperties( copy.get() );
 
   48    copy->mBody.reset( mBody->clone() );
 
   53  copy->setLayer( mCoverageLayer.get() );
 
   54  copy->setField( mField );
 
   55  copy->setSortAscending( mSortAscending );
 
   56  copy->setBodyEnabled( mBodyEnabled );
 
   58  return copy.release();
 
   61bool QgsReportSectionFieldGroup::beginRender()
 
   63  if ( !mCoverageLayer.get() )
 
   66  if ( !mField.isEmpty() )
 
   68    mFieldIndex = mCoverageLayer->fields().lookupField( mField );
 
   69    if ( mFieldIndex < 0 )
 
   73      mBody->reportContext().setLayer( mCoverageLayer.get() );
 
   77  return QgsAbstractReportSection::beginRender();
 
   80bool QgsReportSectionFieldGroup::prepareHeader()
 
   85  if ( !mFeatures.isValid() )
 
   87    mFeatures = mCoverageLayer->getFeatures( buildFeatureRequest() );
 
   90  mHeaderFeature = getNextFeature();
 
   91  header()->reportContext().blockSignals( 
true );
 
   92  header()->reportContext().setLayer( mCoverageLayer.get() );
 
   93  header()->reportContext().blockSignals( 
false );
 
   94  header()->reportContext().setFeature( mHeaderFeature );
 
   95  mSkipNextRequest = 
true;
 
   96  mNoFeatures = !mHeaderFeature.isValid();
 
   97  return mHeaderVisibility == AlwaysInclude || !mNoFeatures;
 
  100bool QgsReportSectionFieldGroup::prepareFooter()
 
  102  return mFooterVisibility == AlwaysInclude || !mNoFeatures;
 
  105QgsLayout *QgsReportSectionFieldGroup::nextBody( 
bool &ok )
 
  107  if ( !mFeatures.isValid() )
 
  109    mFeatures = mCoverageLayer->getFeatures( buildFeatureRequest() );
 
  113  if ( !mSkipNextRequest )
 
  115    f = getNextFeature();
 
  120    mSkipNextRequest = 
false;
 
  128    if ( 
auto *lFooter = footer() )
 
  130      lFooter->reportContext().blockSignals( 
true );
 
  131      lFooter->reportContext().setLayer( mCoverageLayer.get() );
 
  132      lFooter->reportContext().blockSignals( 
false );
 
  133      lFooter->reportContext().setFeature( mLastFeature );
 
  141  updateChildContexts( f );
 
  144  if ( mBody && mBodyEnabled )
 
  146    mBody->reportContext().blockSignals( 
true );
 
  147    mBody->reportContext().setLayer( mCoverageLayer.get() );
 
  148    mBody->reportContext().blockSignals( 
false );
 
  149    mBody->reportContext().setFeature( f );
 
  152  return mBodyEnabled ? mBody.get() : 
nullptr;
 
  155void QgsReportSectionFieldGroup::reset()
 
  157  QgsAbstractReportSection::reset();
 
  158  mEncounteredValues.clear();
 
  159  mSkipNextRequest = 
false;
 
  166void QgsReportSectionFieldGroup::setParentSection( QgsAbstractReportSection *parent )
 
  168  QgsAbstractReportSection::setParentSection( parent );
 
  169  if ( !mCoverageLayer )
 
  170    mCoverageLayer.resolveWeakly( project() );
 
  173void QgsReportSectionFieldGroup::reloadSettings()
 
  175  QgsAbstractReportSection::reloadSettings();
 
  177    mBody->reloadSettings();
 
  180bool QgsReportSectionFieldGroup::writePropertiesToElement( QDomElement &element, QDomDocument &doc, 
const QgsReadWriteContext &context )
 const 
  182  element.setAttribute( QStringLiteral( 
"headerVisibility" ), 
static_cast< int >( mHeaderVisibility ) );
 
  183  element.setAttribute( QStringLiteral( 
"footerVisibility" ), 
static_cast< int >( mFooterVisibility ) );
 
  184  element.setAttribute( QStringLiteral( 
"field" ), mField );
 
  185  element.setAttribute( QStringLiteral( 
"ascending" ), mSortAscending ? QStringLiteral( 
"1" ) : QStringLiteral( 
"0" ) );
 
  186  element.setAttribute( QStringLiteral( 
"bodyEnabled" ), mBodyEnabled ? QStringLiteral( 
"1" ) : QStringLiteral( 
"0" ) );
 
  187  if ( mCoverageLayer )
 
  189    element.setAttribute( QStringLiteral( 
"coverageLayer" ), mCoverageLayer.layerId );
 
  190    element.setAttribute( QStringLiteral( 
"coverageLayerName" ), mCoverageLayer.name );
 
  191    element.setAttribute( QStringLiteral( 
"coverageLayerSource" ), mCoverageLayer.source );
 
  192    element.setAttribute( QStringLiteral( 
"coverageLayerProvider" ), mCoverageLayer.provider );
 
  197    QDomElement bodyElement = doc.createElement( QStringLiteral( 
"body" ) );
 
  198    bodyElement.appendChild( mBody->writeXml( doc, context ) );
 
  199    element.appendChild( bodyElement );
 
  204bool QgsReportSectionFieldGroup::readPropertiesFromElement( 
const QDomElement &element, 
const QDomDocument &doc, 
const QgsReadWriteContext &context )
 
  206  mHeaderVisibility = 
static_cast< SectionVisibility 
>( element.attribute( QStringLiteral( 
"headerVisibility" ) ).toInt() );
 
  207  mFooterVisibility = 
static_cast< SectionVisibility 
>( element.attribute( QStringLiteral( 
"footerVisibility" ) ).toInt() );
 
  208  mField = element.attribute( QStringLiteral( 
"field" ) );
 
  209  mSortAscending = element.attribute( QStringLiteral( 
"ascending" ) ).toInt();
 
  210  mBodyEnabled = element.attribute( QStringLiteral( 
"bodyEnabled" ) ).toInt();
 
  211  QString layerId = element.attribute( QStringLiteral( 
"coverageLayer" ) );
 
  212  QString layerName = element.attribute( QStringLiteral( 
"coverageLayerName" ) );
 
  213  QString layerSource = element.attribute( QStringLiteral( 
"coverageLayerSource" ) );
 
  214  QString layerProvider = element.attribute( QStringLiteral( 
"coverageLayerProvider" ) );
 
  215  mCoverageLayer = 
QgsVectorLayerRef( layerId, layerName, layerSource, layerProvider );
 
  216  mCoverageLayer.resolveWeakly( project() );
 
  218  const QDomElement bodyElement = element.firstChildElement( QStringLiteral( 
"body" ) );
 
  219  if ( !bodyElement.isNull() )
 
  221    const QDomElement bodyLayoutElem = bodyElement.firstChild().toElement();
 
  222    std::unique_ptr< QgsLayout > body = std::make_unique< QgsLayout >( project() );
 
  223    body->readXml( bodyLayoutElem, doc, context );
 
  224    mBody = std::move( body );
 
  229bool QgsReportSectionFieldGroup::sortAscending()
 const 
  231  return mSortAscending;
 
  234void QgsReportSectionFieldGroup::setSortAscending( 
bool sortAscending )
 
  236  mSortAscending = sortAscending;
 
  242  QVariantMap filter = context().fieldFilters;
 
  244  QStringList filterParts;
 
  245  for ( 
auto filterIt = filter.constBegin(); filterIt != filter.constEnd(); ++filterIt )
 
  248    int fieldIndex = mCoverageLayer->fields().lookupField( filterIt.key() );
 
  249    if ( fieldIndex >= 0 )
 
  255  if ( !filterParts.empty() )
 
  257    QString filterString = QStringLiteral( 
"(%1)" ).arg( filterParts.join( QLatin1String( 
") AND (" ) ) );
 
  265QgsFeature QgsReportSectionFieldGroup::getNextFeature()
 
  268  QVariant currentValue;
 
  270  while ( first || ( ( !mBody || !mBodyEnabled ) && mEncounteredValues.contains( currentValue ) ) )
 
  272    if ( !mFeatures.nextFeature( f ) )
 
  278    currentValue = f.
attribute( mFieldIndex );
 
  281  mEncounteredValues.insert( currentValue );
 
  285void QgsReportSectionFieldGroup::updateChildContexts( 
const QgsFeature &feature )
 
  287  QgsReportSectionContext 
c = context();
 
  289  if ( mCoverageLayer )
 
  290    c.currentLayer = mCoverageLayer.get();
 
  292  QVariantMap currentFilter = 
c.fieldFilters;
 
  293  currentFilter.insert( mField, feature.
attribute( mFieldIndex ) );
 
  294  c.fieldFilters = currentFilter;
 
  296  const QList< QgsAbstractReportSection * > sections = childSections();
 
  297  for ( QgsAbstractReportSection *section : std::as_const( sections ) )
 
  299    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, QVariant::Type fieldType=QVariant::Type::Invalid)
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.
 
This class 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.
 
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.
 
The class is used as a container of context for various read/write operations on other 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