QGIS API Documentation  3.26.3-Buenos Aires (65e4edfdad)
qgsexpressioncontextutils.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  qgsexpressioncontextutils.cpp
3  ------------------------
4  Date : April 2015
5  Copyright : (C) 2015 by Nyall Dawson
6  Email : nyall dot dawson at gmail dot com
7  ***************************************************************************
8  * *
9  * This program is free software; you can redistribute it and/or modify *
10  * it under the terms of the GNU General Public License as published by *
11  * the Free Software Foundation; either version 2 of the License, or *
12  * (at your option) any later version. *
13  * *
14  ***************************************************************************/
15 
17 #include "qgsapplication.h"
18 #include "qgsvectorlayer.h"
19 #include "qgsproject.h"
20 #include "qgsexpression.h"
21 #include "qgsprocessingcontext.h"
23 #include "qgsprocessingalgorithm.h"
24 #include "qgsmapsettings.h"
25 #include "qgssymbollayerutils.h"
26 #include "qgslayout.h"
27 #include "qgslayoutitem.h"
28 #include "qgsexpressionutils.h"
30 #include "qgslayoutatlas.h"
31 #include "qgslayoutmultiframe.h"
32 #include "qgsfeatureid.h"
33 #include "qgslayoutitemmap.h"
34 #include "qgsmaplayerlistutils_p.h"
35 #include "qgsprojoperation.h"
36 #include "qgsmarkersymbol.h"
37 #include "qgstriangularmesh.h"
38 #include "qgsvectortileutils.h"
39 
41 {
42  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Global" ) );
43 
44  const QVariantMap customVariables = QgsApplication::customVariables();
45 
46  for ( QVariantMap::const_iterator it = customVariables.constBegin(); it != customVariables.constEnd(); ++it )
47  {
48  scope->setVariable( it.key(), it.value(), true );
49  }
50 
51  //add some extra global variables
52  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "qgis_version" ), Qgis::version(), true, true ) );
53  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "qgis_version_no" ), Qgis::versionInt(), true, true ) );
54  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "qgis_short_version" ), QStringLiteral( "%1.%2" ).arg( Qgis::versionInt() / 10000 ).arg( Qgis::versionInt() / 100 % 100 ), true, true ) );
55  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "qgis_release_name" ), Qgis::releaseName(), true, true ) );
56  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "qgis_platform" ), QgsApplication::platform(), true, true ) );
57  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "qgis_os_name" ), QgsApplication::osName(), true, true ) );
58  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "qgis_locale" ), QgsApplication::locale(), true, true ) );
59  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "user_account_name" ), QgsApplication::userLoginName(), true, true ) );
60  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "user_full_name" ), QgsApplication::userFullName(), true, true ) );
61 
62  return scope;
63 }
64 
65 void QgsExpressionContextUtils::setGlobalVariable( const QString &name, const QVariant &value )
66 {
67  QgsApplication::setCustomVariable( name, value );
68 }
69 
70 void QgsExpressionContextUtils::setGlobalVariables( const QVariantMap &variables )
71 {
73 }
74 
76 {
77  QVariantMap vars = QgsApplication::customVariables();
78  if ( vars.remove( name ) )
80 }
81 
83 
84 class GetLayoutItemVariables : public QgsScopedExpressionFunction
85 {
86  public:
87  GetLayoutItemVariables( const QgsLayout *c )
88  : QgsScopedExpressionFunction( QStringLiteral( "item_variables" ), QgsExpressionFunction::ParameterList() << QgsExpressionFunction::Parameter( QStringLiteral( "id" ) ), QStringLiteral( "Layout" ) )
89  , mLayout( c )
90  {}
91 
92  QVariant func( const QVariantList &values, const QgsExpressionContext *, QgsExpression *, const QgsExpressionNodeFunction * ) override
93  {
94  if ( !mLayout )
95  return QVariant();
96 
97  const QString id = values.at( 0 ).toString();
98 
99  const QgsLayoutItem *item = mLayout->itemById( id );
100  if ( !item )
101  return QVariant();
102 
104 
105  return c.variablesToMap();
106  }
107 
108  QgsScopedExpressionFunction *clone() const override
109  {
110  return new GetLayoutItemVariables( mLayout );
111  }
112 
113  private:
114 
115  const QgsLayout *mLayout = nullptr;
116 
117 };
118 
119 
120 class GetLayoutMapLayerCredits : public QgsScopedExpressionFunction
121 {
122  public:
123  GetLayoutMapLayerCredits( const QgsLayout *c )
124  : QgsScopedExpressionFunction( QStringLiteral( "map_credits" ),
125  QgsExpressionFunction::ParameterList() << QgsExpressionFunction::Parameter( QStringLiteral( "id" ) )
126  << QgsExpressionFunction::Parameter( QStringLiteral( "include_layer_names" ), true, false )
127  << QgsExpressionFunction::Parameter( QStringLiteral( "layer_name_separator" ), true, QStringLiteral( ": " ) ), QStringLiteral( "Layout" ) )
128  , mLayout( c )
129  {}
130 
131  QVariant func( const QVariantList &values, const QgsExpressionContext *, QgsExpression *, const QgsExpressionNodeFunction * ) override
132  {
133  if ( !mLayout )
134  return QVariant();
135 
136  const QString id = values.value( 0 ).toString();
137 
138  if ( QgsLayoutItemMap *map = qobject_cast< QgsLayoutItemMap * >( mLayout->itemById( id ) ) )
139  {
140  const QgsExpressionContext c = map->createExpressionContext();
141  const QVariantList mapLayers = c.variable( QStringLiteral( "map_layers" ) ).toList();
142 
143  const bool includeLayerNames = values.value( 1 ).toBool();
144  const QString layerNameSeparator = values.value( 2 ).toString();
145 
146  QVariantList res;
147  for ( const QVariant &value : mapLayers )
148  {
149  if ( const QgsMapLayer *layer = qobject_cast< const QgsMapLayer * >( value.value< QObject * >() ) )
150  {
151  const QStringList credits = !layer->metadata().rights().isEmpty() ? layer->metadata().rights() : QStringList() << layer->attribution();
152  for ( const QString &credit : credits )
153  {
154  if ( credit.trimmed().isEmpty() )
155  continue;
156 
157  const QString creditString = includeLayerNames ? layer->name() + layerNameSeparator + credit
158  : credit;
159 
160  if ( !res.contains( creditString ) )
161  res << creditString;
162  }
163  }
164  }
165 
166  return res;
167  }
168  return QVariant();
169  }
170 
171  QgsScopedExpressionFunction *clone() const override
172  {
173  return new GetLayoutMapLayerCredits( mLayout );
174  }
175 
176  private:
177 
178  const QgsLayout *mLayout = nullptr;
179 
180 };
181 
182 class GetCurrentFormFieldValue : public QgsScopedExpressionFunction
183 {
184  public:
185  GetCurrentFormFieldValue( )
186  : QgsScopedExpressionFunction( QStringLiteral( "current_value" ), QgsExpressionFunction::ParameterList() << QStringLiteral( "field_name" ), QStringLiteral( "Form" ) )
187  {}
188 
189  QVariant func( const QVariantList &values, const QgsExpressionContext *context, QgsExpression *, const QgsExpressionNodeFunction * ) override
190  {
191  const QString fieldName( values.at( 0 ).toString() );
192  const QgsFeature feat( context->variable( QStringLiteral( "current_feature" ) ).value<QgsFeature>() );
193  if ( fieldName.isEmpty() || ! feat.isValid( ) )
194  {
195  return QVariant();
196  }
197  return feat.attribute( fieldName ) ;
198  }
199 
200  QgsScopedExpressionFunction *clone() const override
201  {
202  return new GetCurrentFormFieldValue( );
203  }
204 
205  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
206  {
207  return false;
208  };
209 
210 };
211 
212 class GetCurrentParentFormFieldValue : public QgsScopedExpressionFunction
213 {
214  public:
215  GetCurrentParentFormFieldValue( )
216  : QgsScopedExpressionFunction( QStringLiteral( "current_parent_value" ), QgsExpressionFunction::ParameterList() << QStringLiteral( "field_name" ), QStringLiteral( "Form" ) )
217  {}
218 
219  QVariant func( const QVariantList &values, const QgsExpressionContext *context, QgsExpression *, const QgsExpressionNodeFunction * ) override
220  {
221  const QString fieldName( values.at( 0 ).toString() );
222  const QgsFeature feat( context->variable( QStringLiteral( "current_parent_feature" ) ).value<QgsFeature>() );
223  if ( fieldName.isEmpty() || ! feat.isValid( ) )
224  {
225  return QVariant();
226  }
227  return feat.attribute( fieldName ) ;
228  }
229 
230  QgsScopedExpressionFunction *clone() const override
231  {
232  return new GetCurrentParentFormFieldValue( );
233  }
234 
235  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
236  {
237  return false;
238  };
239 
240 };
241 
242 
243 class GetProcessingParameterValue : public QgsScopedExpressionFunction
244 {
245  public:
246  GetProcessingParameterValue( const QVariantMap &params )
247  : QgsScopedExpressionFunction( QStringLiteral( "parameter" ), QgsExpressionFunction::ParameterList() << QgsExpressionFunction::Parameter( QStringLiteral( "name" ) ), QStringLiteral( "Processing" ) )
248  , mParams( params )
249  {}
250 
251  QVariant func( const QVariantList &values, const QgsExpressionContext *, QgsExpression *, const QgsExpressionNodeFunction * ) override
252  {
253  return mParams.value( values.at( 0 ).toString() );
254  }
255 
256  QgsScopedExpressionFunction *clone() const override
257  {
258  return new GetProcessingParameterValue( mParams );
259  }
260 
261  private:
262 
263  const QVariantMap mParams;
264 
265 };
266 
268 
269 
270 QgsExpressionContextScope *QgsExpressionContextUtils::formScope( const QgsFeature &formFeature, const QString &formMode )
271 {
272  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Form" ) );
273  scope->addFunction( QStringLiteral( "current_value" ), new GetCurrentFormFieldValue( ) );
274  scope->setVariable( QStringLiteral( "current_geometry" ), formFeature.geometry( ), true );
275  scope->setVariable( QStringLiteral( "current_feature" ), formFeature, true );
276  scope->setVariable( QStringLiteral( "form_mode" ), formMode, true );
277  return scope;
278 }
279 
280 
281 QgsExpressionContextScope *QgsExpressionContextUtils::parentFormScope( const QgsFeature &parentFormFeature, const QString &parentFormMode )
282 {
283  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Parent Form" ) );
284  scope->addFunction( QStringLiteral( "current_parent_value" ), new GetCurrentParentFormFieldValue( ) );
285  scope->setVariable( QStringLiteral( "current_parent_geometry" ), parentFormFeature.geometry( ), true );
286  scope->setVariable( QStringLiteral( "current_parent_feature" ), parentFormFeature, true );
287  scope->setVariable( QStringLiteral( "parent_form_mode" ), parentFormMode, true );
288  return scope;
289 }
290 
292 {
293  if ( !project )
294  {
295  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Project" ) );
296  return scope;
297  }
298  else
299  return project->createExpressionContextScope();
300 }
301 
302 void QgsExpressionContextUtils::setProjectVariable( QgsProject *project, const QString &name, const QVariant &value )
303 {
304  if ( !project )
305  return;
306 
307  QVariantMap vars = project->customVariables();
308 
309  vars.insert( name, value );
310 
311  project->setCustomVariables( vars );
312 }
313 
314 void QgsExpressionContextUtils::setProjectVariables( QgsProject *project, const QVariantMap &variables )
315 {
316  if ( !project )
317  return;
318 
319  project->setCustomVariables( variables );
320 }
321 
323 {
324  if ( !project )
325  {
326  return;
327  }
328 
329  QVariantMap vars = project->customVariables();
330  if ( vars.remove( name ) )
331  project->setCustomVariables( vars );
332 }
333 
335 {
336  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Layer" ) );
337 
338  if ( !layer )
339  return scope;
340 
341  //add variables defined in layer properties
342  const QStringList variableNames = layer->customProperty( QStringLiteral( "variableNames" ) ).toStringList();
343  const QStringList variableValues = layer->customProperty( QStringLiteral( "variableValues" ) ).toStringList();
344 
345  int varIndex = 0;
346  for ( const QString &variableName : variableNames )
347  {
348  if ( varIndex >= variableValues.length() )
349  {
350  break;
351  }
352 
353  const QVariant varValue = variableValues.at( varIndex );
354  varIndex++;
355  scope->setVariable( variableName, varValue, true );
356  }
357 
358  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layer_name" ), layer->name(), true, true ) );
359  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layer_id" ), layer->id(), true, true ) );
360  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "_layer_crs" ), QVariant::fromValue<QgsCoordinateReferenceSystem>( layer->crs() ), true, true ) );
361  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layer_crs" ), layer->crs().authid(), true, true ) );
362  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layer" ), QVariant::fromValue<QgsWeakMapLayerPointer >( QgsWeakMapLayerPointer( const_cast<QgsMapLayer *>( layer ) ) ), true, true ) );
363 
364  const QgsVectorLayer *vLayer = qobject_cast< const QgsVectorLayer * >( layer );
365  if ( vLayer )
366  {
367  scope->setFields( vLayer->fields() );
368  }
369 
370  //TODO - add functions. Possibilities include:
371  //is_selected
372  //field summary stats
373 
374  return scope;
375 }
376 
377 QList<QgsExpressionContextScope *> QgsExpressionContextUtils::globalProjectLayerScopes( const QgsMapLayer *layer )
378 {
379  QList<QgsExpressionContextScope *> scopes;
380  scopes << globalScope();
381 
382  QgsProject *project = QgsProject::instance(); // TODO: use project associated with layer
383  if ( project )
384  scopes << projectScope( project );
385 
386  if ( layer )
387  scopes << layerScope( layer );
388  return scopes;
389 }
390 
391 
392 void QgsExpressionContextUtils::setLayerVariable( QgsMapLayer *layer, const QString &name, const QVariant &value )
393 {
394  if ( !layer )
395  return;
396 
397  //write variable to layer
398  QStringList variableNames = layer->customProperty( QStringLiteral( "variableNames" ) ).toStringList();
399  QStringList variableValues = layer->customProperty( QStringLiteral( "variableValues" ) ).toStringList();
400 
401  variableNames << name;
402  variableValues << value.toString();
403 
404  layer->setCustomProperty( QStringLiteral( "variableNames" ), variableNames );
405  layer->setCustomProperty( QStringLiteral( "variableValues" ), variableValues );
406 }
407 
408 void QgsExpressionContextUtils::setLayerVariables( QgsMapLayer *layer, const QVariantMap &variables )
409 {
410  if ( !layer )
411  return;
412 
413  QStringList variableNames;
414  QStringList variableValues;
415 
416  QVariantMap::const_iterator it = variables.constBegin();
417  for ( ; it != variables.constEnd(); ++it )
418  {
419  variableNames << it.key();
420  variableValues << it.value().toString();
421  }
422 
423  layer->setCustomProperty( QStringLiteral( "variableNames" ), variableNames );
424  layer->setCustomProperty( QStringLiteral( "variableValues" ), variableValues );
425 }
426 
428 {
429  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
430  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
431 
432  // and because people don't read that ^^, I'm going to blast it all over this function
433 
434  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Map Settings" ) );
435 
436  //add known map settings context variables
437  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_id" ), "canvas", true ) );
438  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_rotation" ), mapSettings.rotation(), true ) );
439  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_scale" ), mapSettings.scale(), true ) );
440 
441  scope->setVariable( QStringLiteral( "zoom_level" ), QgsVectorTileUtils::scaleToZoomLevel( mapSettings.scale(), 0, 99999 ), true );
442  scope->setVariable( QStringLiteral( "vector_tile_zoom" ), QgsVectorTileUtils::scaleToZoom( mapSettings.scale() ), true );
443 
444  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
445  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
446 
447  const QgsGeometry extent = QgsGeometry::fromRect( mapSettings.visibleExtent() );
448  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_extent" ), QVariant::fromValue( extent ), true ) );
449  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_extent_width" ), mapSettings.visibleExtent().width(), true ) );
450  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_extent_height" ), mapSettings.visibleExtent().height(), true ) );
451 
452  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
453  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
454 
455  const QgsGeometry centerPoint = QgsGeometry::fromPointXY( mapSettings.visibleExtent().center() );
456  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_extent_center" ), QVariant::fromValue( centerPoint ), true ) );
457 
458  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
459  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
460 
461  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_crs" ), mapSettings.destinationCrs().authid(), true ) );
462  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_crs_definition" ), mapSettings.destinationCrs().toProj(), true ) );
463  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_units" ), QgsUnitTypes::toString( mapSettings.mapUnits() ), true ) );
464  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_crs_description" ), mapSettings.destinationCrs().description(), true ) );
465  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_crs_acronym" ), mapSettings.destinationCrs().projectionAcronym(), true ) );
466  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_crs_projection" ), mapSettings.destinationCrs().operation().description(), true ) );
467  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_crs_ellipsoid" ), mapSettings.destinationCrs().ellipsoidAcronym(), true ) );
468  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_crs_proj4" ), mapSettings.destinationCrs().toProj(), true ) );
469  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_crs_wkt" ), mapSettings.destinationCrs().toWkt( QgsCoordinateReferenceSystem::WKT_PREFERRED ), true ) );
470 
471  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
472  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
473 
474  QVariantList layersIds;
475  QVariantList layers;
476  const QList<QgsMapLayer *> layersInMap = mapSettings.layers( true );
477  layersIds.reserve( layersInMap.count() );
478  layers.reserve( layersInMap.count() );
479  for ( QgsMapLayer *layer : layersInMap )
480  {
481  layersIds << layer->id();
482  layers << QVariant::fromValue<QgsWeakMapLayerPointer>( QgsWeakMapLayerPointer( layer ) );
483  }
484 
485  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
486  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
487 
488  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_layer_ids" ), layersIds, true ) );
489  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_layers" ), layers, true ) );
490 
491  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
492  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
493 
494  scope->addFunction( QStringLiteral( "is_layer_visible" ), new GetLayerVisibility( mapSettings.layers( true ), mapSettings.scale() ) );
495 
496  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
497  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
498 
499  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_start_time" ), mapSettings.isTemporal() ? mapSettings.temporalRange().begin() : QVariant(), true ) );
500  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_end_time" ), mapSettings.isTemporal() ? mapSettings.temporalRange().end() : QVariant(), true ) );
501  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "map_interval" ), mapSettings.isTemporal() ? ( mapSettings.temporalRange().end() - mapSettings.temporalRange().begin() ) : QVariant(), true ) );
502 
503  // IMPORTANT: ANY CHANGES HERE ALSO NEED TO BE MADE TO QgsLayoutItemMap::createExpressionContext()
504  // (rationale is described in QgsLayoutItemMap::createExpressionContext() )
505 
506  if ( mapSettings.frameRate() >= 0 )
507  scope->setVariable( QStringLiteral( "frame_rate" ), mapSettings.frameRate(), true );
508  if ( mapSettings.currentFrame() >= 0 )
509  scope->setVariable( QStringLiteral( "frame_number" ), mapSettings.currentFrame(), true );
510 
511  return scope;
512 }
513 
514 QgsExpressionContextScope *QgsExpressionContextUtils::mapToolCaptureScope( const QList<QgsPointLocator::Match> &matches )
515 {
516  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Map Tool Capture" ) );
517 
518  QVariantList matchList;
519 
520  for ( const QgsPointLocator::Match &match : matches )
521  {
522  QVariantMap matchMap;
523 
524  matchMap.insert( QStringLiteral( "valid" ), match.isValid() );
525  matchMap.insert( QStringLiteral( "layer" ), QVariant::fromValue<QgsWeakMapLayerPointer>( QgsWeakMapLayerPointer( match.layer() ) ) );
526  matchMap.insert( QStringLiteral( "feature_id" ), match.featureId() );
527  matchMap.insert( QStringLiteral( "vertex_index" ), match.vertexIndex() );
528  matchMap.insert( QStringLiteral( "distance" ), match.distance() );
529 
530  matchList.append( matchMap );
531  }
532 
533  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "snapping_results" ), matchList ) );
534 
535  return scope;
536 }
537 
539 {
540  if ( !symbolScope )
541  return nullptr;
542 
543  symbolScope->addVariable( QgsExpressionContextScope::StaticVariable( QgsExpressionContext::EXPR_SYMBOL_COLOR, symbol ? symbol->color() : QColor(), true ) );
544 
545  double angle = 0.0;
546  const QgsMarkerSymbol *markerSymbol = dynamic_cast< const QgsMarkerSymbol * >( symbol );
547  if ( markerSymbol )
548  {
549  angle = markerSymbol->angle();
550  }
552 
553  return symbolScope;
554 }
555 
557 {
558  std::unique_ptr< QgsExpressionContextScope > scope( new QgsExpressionContextScope( QObject::tr( "Layout" ) ) );
559  if ( !layout )
560  return scope.release();
561 
562  //add variables defined in layout properties
563  const QStringList variableNames = layout->customProperty( QStringLiteral( "variableNames" ) ).toStringList();
564  const QStringList variableValues = layout->customProperty( QStringLiteral( "variableValues" ) ).toStringList();
565 
566  int varIndex = 0;
567 
568  for ( const QString &variableName : variableNames )
569  {
570  if ( varIndex >= variableValues.length() )
571  {
572  break;
573  }
574 
575  const QVariant varValue = variableValues.at( varIndex );
576  varIndex++;
577  scope->setVariable( variableName, varValue );
578  }
579 
580  //add known layout context variables
581  if ( const QgsMasterLayoutInterface *l = dynamic_cast< const QgsMasterLayoutInterface * >( layout ) )
582  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_name" ), l->name(), true ) );
583 
584  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_numpages" ), layout->pageCollection()->pageCount(), true ) );
585  if ( layout->pageCollection()->pageCount() > 0 )
586  {
587  // just take first page size
588  const QSizeF s = layout->pageCollection()->page( 0 )->sizeWithUnits().toQSizeF();
589  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_pageheight" ), s.height(), true ) );
590  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_pagewidth" ), s.width(), true ) );
591  }
592 
593  QVariantList offsets;
594  for ( int i = 0; i < layout->pageCollection()->pageCount(); i++ )
595  {
596  const QPointF p = layout->pageCollection()->pagePositionToLayoutPosition( i, QgsLayoutPoint( 0, 0 ) );
597  offsets << p.y();
598  }
599  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_pageoffsets" ), offsets, true ) );
600 
601  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_dpi" ), layout->renderContext().dpi(), true ) );
602 
603  scope->addFunction( QStringLiteral( "item_variables" ), new GetLayoutItemVariables( layout ) );
604  scope->addFunction( QStringLiteral( "map_credits" ), new GetLayoutMapLayerCredits( layout ) );
605 
606  if ( layout->reportContext().layer() )
607  {
608  scope->setFields( layout->reportContext().layer()->fields() );
609  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_layerid" ), layout->reportContext().layer()->id(), true ) );
610  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_layername" ), layout->reportContext().layer()->name(), true ) );
611  }
612 
613  if ( layout->reportContext().feature().isValid() )
614  {
615  const QgsFeature atlasFeature = layout->reportContext().feature();
616  scope->setFeature( atlasFeature );
617  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_feature" ), QVariant::fromValue( atlasFeature ), true ) );
618  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_featureid" ), FID_IS_NULL( atlasFeature.id() ) ? QVariant() : atlasFeature.id(), true ) );
619  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_geometry" ), QVariant::fromValue( atlasFeature.geometry() ), true ) );
620  }
621 
622  return scope.release();
623 }
624 
625 void QgsExpressionContextUtils::setLayoutVariable( QgsLayout *layout, const QString &name, const QVariant &value )
626 {
627  if ( !layout )
628  return;
629 
630  //write variable to layout
631  QStringList variableNames = layout->customProperty( QStringLiteral( "variableNames" ) ).toStringList();
632  QStringList variableValues = layout->customProperty( QStringLiteral( "variableValues" ) ).toStringList();
633 
634  variableNames << name;
635  variableValues << value.toString();
636 
637  layout->setCustomProperty( QStringLiteral( "variableNames" ), variableNames );
638  layout->setCustomProperty( QStringLiteral( "variableValues" ), variableValues );
639 }
640 
641 void QgsExpressionContextUtils::setLayoutVariables( QgsLayout *layout, const QVariantMap &variables )
642 {
643  if ( !layout )
644  return;
645 
646  QStringList variableNames;
647  QStringList variableValues;
648 
649  QVariantMap::const_iterator it = variables.constBegin();
650  for ( ; it != variables.constEnd(); ++it )
651  {
652  variableNames << it.key();
653  variableValues << it.value().toString();
654  }
655 
656  layout->setCustomProperty( QStringLiteral( "variableNames" ), variableNames );
657  layout->setCustomProperty( QStringLiteral( "variableValues" ), variableValues );
658 }
659 
661 {
662  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Atlas" ) );
663  if ( !atlas )
664  {
665  //add some dummy atlas variables. This is done so that as in certain contexts we want to show
666  //users that these variables are available even if they have no current value
667  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_pagename" ), QString(), true, true ) );
668  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_feature" ), QVariant::fromValue( QgsFeature() ), true, true ) );
669  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_featureid" ), QVariant(), true, true ) );
670  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_geometry" ), QVariant::fromValue( QgsGeometry() ), true, true ) );
671  return scope;
672  }
673 
674  //add known atlas variables
675  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_totalfeatures" ), atlas->count(), true, true ) );
676  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_featurenumber" ), atlas->currentFeatureNumber() + 1, true, true ) );
677  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_filename" ), atlas->currentFilename(), true, true ) );
678  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_pagename" ), atlas->nameForPage( atlas->currentFeatureNumber() ), true, true ) );
679 
680  if ( atlas->enabled() && atlas->coverageLayer() )
681  {
682  scope->setFields( atlas->coverageLayer()->fields() );
683  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_layerid" ), atlas->coverageLayer()->id(), true ) );
684  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_layername" ), atlas->coverageLayer()->name(), true ) );
685  }
686 
687  if ( atlas->enabled() )
688  {
689  const QgsFeature atlasFeature = atlas->layout()->reportContext().feature();
690  scope->setFeature( atlasFeature );
691  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_feature" ), QVariant::fromValue( atlasFeature ), true ) );
692  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_featureid" ), FID_IS_NULL( atlasFeature.id() ) ? QVariant() : atlasFeature.id(), true ) );
693  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "atlas_geometry" ), QVariant::fromValue( atlasFeature.geometry() ), true ) );
694  }
695 
696  return scope;
697 }
698 
700 {
701  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Layout Item" ) );
702  if ( !item )
703  return scope;
704 
705  //add variables defined in layout item properties
706  const QStringList variableNames = item->customProperty( QStringLiteral( "variableNames" ) ).toStringList();
707  const QStringList variableValues = item->customProperty( QStringLiteral( "variableValues" ) ).toStringList();
708 
709  int varIndex = 0;
710  for ( const QString &variableName : variableNames )
711  {
712  if ( varIndex >= variableValues.length() )
713  {
714  break;
715  }
716 
717  const QVariant varValue = variableValues.at( varIndex );
718  varIndex++;
719  scope->setVariable( variableName, varValue );
720  }
721 
722  //add known layout item context variables
723  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "item_id" ), item->id(), true ) );
724  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "item_uuid" ), item->uuid(), true ) );
725  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_page" ), item->page() + 1, true ) );
726 
727  if ( item->layout() )
728  {
729  const QgsLayoutItemPage *page = item->layout()->pageCollection()->page( item->page() );
730  if ( page )
731  {
732  const QSizeF s = page->sizeWithUnits().toQSizeF();
733  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_pageheight" ), s.height(), true ) );
734  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_pagewidth" ), s.width(), true ) );
735  }
736  else
737  {
738  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_pageheight" ), QVariant(), true ) );
739  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "layout_pagewidth" ), QVariant(), true ) );
740  }
741  }
742 
743  return scope;
744 }
745 
746 void QgsExpressionContextUtils::setLayoutItemVariable( QgsLayoutItem *item, const QString &name, const QVariant &value )
747 {
748  if ( !item )
749  return;
750 
751  //write variable to layout item
752  QStringList variableNames = item->customProperty( QStringLiteral( "variableNames" ) ).toStringList();
753  QStringList variableValues = item->customProperty( QStringLiteral( "variableValues" ) ).toStringList();
754 
755  variableNames << name;
756  variableValues << value.toString();
757 
758  item->setCustomProperty( QStringLiteral( "variableNames" ), variableNames );
759  item->setCustomProperty( QStringLiteral( "variableValues" ), variableValues );
760 }
761 
762 void QgsExpressionContextUtils::setLayoutItemVariables( QgsLayoutItem *item, const QVariantMap &variables )
763 {
764  if ( !item )
765  return;
766 
767  QStringList variableNames;
768  QStringList variableValues;
769 
770  QVariantMap::const_iterator it = variables.constBegin();
771  for ( ; it != variables.constEnd(); ++it )
772  {
773  variableNames << it.key();
774  variableValues << it.value().toString();
775  }
776 
777  item->setCustomProperty( QStringLiteral( "variableNames" ), variableNames );
778  item->setCustomProperty( QStringLiteral( "variableValues" ), variableValues );
779 }
780 
782 {
783  QgsExpressionContextScope *scope = new QgsExpressionContextScope( QObject::tr( "Multiframe Item" ) );
784  if ( !frame )
785  return scope;
786 
787  //add variables defined in layout item properties
788  const QStringList variableNames = frame->customProperty( QStringLiteral( "variableNames" ) ).toStringList();
789  const QStringList variableValues = frame->customProperty( QStringLiteral( "variableValues" ) ).toStringList();
790 
791  int varIndex = 0;
792  for ( const QString &variableName : variableNames )
793  {
794  if ( varIndex >= variableValues.length() )
795  {
796  break;
797  }
798 
799  const QVariant varValue = variableValues.at( varIndex );
800  varIndex++;
801  scope->setVariable( variableName, varValue );
802  }
803 
804  return scope;
805 }
806 
807 void QgsExpressionContextUtils::setLayoutMultiFrameVariable( QgsLayoutMultiFrame *frame, const QString &name, const QVariant &value )
808 {
809  if ( !frame )
810  return;
811 
812  //write variable to layout multiframe
813  QStringList variableNames = frame->customProperty( QStringLiteral( "variableNames" ) ).toStringList();
814  QStringList variableValues = frame->customProperty( QStringLiteral( "variableValues" ) ).toStringList();
815 
816  variableNames << name;
817  variableValues << value.toString();
818 
819  frame->setCustomProperty( QStringLiteral( "variableNames" ), variableNames );
820  frame->setCustomProperty( QStringLiteral( "variableValues" ), variableValues );
821 }
822 
824 {
825  if ( !frame )
826  return;
827 
828  QStringList variableNames;
829  QStringList variableValues;
830 
831  QVariantMap::const_iterator it = variables.constBegin();
832  for ( ; it != variables.constEnd(); ++it )
833  {
834  variableNames << it.key();
835  variableValues << it.value().toString();
836  }
837 
838  frame->setCustomProperty( QStringLiteral( "variableNames" ), variableNames );
839  frame->setCustomProperty( QStringLiteral( "variableValues" ), variableValues );
840 }
841 
843 {
845  scope->setFeature( feature );
846  scope->setFields( fields );
847  return QgsExpressionContext() << scope;
848 }
849 
851 {
852  // set aside for future use
853  Q_UNUSED( context )
854 
855  std::unique_ptr< QgsExpressionContextScope > scope( new QgsExpressionContextScope( QObject::tr( "Algorithm" ) ) );
856  scope->addFunction( QStringLiteral( "parameter" ), new GetProcessingParameterValue( parameters ) );
857 
858  if ( !algorithm )
859  return scope.release();
860 
861  //add standard algorithm variables
862  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "algorithm_id" ), algorithm->id(), true ) );
863 
864  return scope.release();
865 }
866 
867 QgsExpressionContextScope *QgsExpressionContextUtils::processingModelAlgorithmScope( const QgsProcessingModelAlgorithm *model, const QVariantMap &, QgsProcessingContext &context )
868 {
869  std::unique_ptr< QgsExpressionContextScope > modelScope( new QgsExpressionContextScope( QObject::tr( "Model" ) ) );
870  QString modelPath;
871  if ( !model->sourceFilePath().isEmpty() )
872  {
873  modelPath = model->sourceFilePath();
874  }
875  else if ( context.project() )
876  {
877  // fallback to project path -- the model may be embedded in a project, OR an unsaved model. In either case the
878  // project path is a logical value to fall back to
879  modelPath = context.project()->projectStorage() ? context.project()->fileName() : context.project()->absoluteFilePath();
880  }
881 
882  const QString modelFolder = !modelPath.isEmpty() ? QFileInfo( modelPath ).path() : QString();
883  modelScope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "model_path" ), QDir::toNativeSeparators( modelPath ), true ) );
884  modelScope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "model_folder" ), QDir::toNativeSeparators( modelFolder ), true, true ) );
885  modelScope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "model_name" ), model->displayName(), true ) );
886  modelScope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "model_group" ), model->group(), true ) );
887 
888  // custom variables
889  const QVariantMap customVariables = model->variables();
890  for ( auto it = customVariables.constBegin(); it != customVariables.constEnd(); ++it )
891  {
892  modelScope->addVariable( QgsExpressionContextScope::StaticVariable( it.key(), it.value(), true ) );
893  }
894 
895  return modelScope.release();
896 }
897 
899 {
900  std::unique_ptr< QgsExpressionContextScope > scope( new QgsExpressionContextScope() );
901  scope->addVariable( QgsExpressionContextScope::StaticVariable( QStringLiteral( "notification_message" ), message, true ) );
902  return scope.release();
903 }
904 
906 {
907  QgsExpression::registerFunction( new GetNamedProjectColor( nullptr ) );
908  QgsExpression::registerFunction( new GetLayoutItemVariables( nullptr ) );
909  QgsExpression::registerFunction( new GetLayoutMapLayerCredits( nullptr ) );
910  QgsExpression::registerFunction( new GetLayerVisibility( QList<QgsMapLayer *>(), 0.0 ) );
911  QgsExpression::registerFunction( new GetProcessingParameterValue( QVariantMap() ) );
912  QgsExpression::registerFunction( new GetCurrentFormFieldValue( ) );
913  QgsExpression::registerFunction( new GetCurrentParentFormFieldValue( ) );
914 }
915 
917 {
918  Q_UNUSED( node )
919  return mUsesGeometry;
920 }
921 
923 {
924  Q_UNUSED( node )
925  return mReferencedColumns;
926 }
927 
929 {
930  return allParamsStatic( node, parent, context );
931 }
932 
933 //
934 // GetLayerVisibility
935 //
936 
937 QgsExpressionContextUtils::GetLayerVisibility::GetLayerVisibility( const QList<QgsMapLayer *> &layers, double scale )
938  : QgsScopedExpressionFunction( QStringLiteral( "is_layer_visible" ), QgsExpressionFunction::ParameterList() << QgsExpressionFunction::Parameter( QStringLiteral( "id" ) ), QStringLiteral( "General" ) )
939  , mLayers( _qgis_listRawToQPointer( layers ) )
940  , mScale( scale )
941 {
942  for ( const auto &layer : mLayers )
943  {
944  if ( layer->hasScaleBasedVisibility() )
945  {
946  mScaleBasedVisibilityDetails[ layer ] = qMakePair( layer->minimumScale(), layer->maximumScale() );
947  }
948  }
949 }
950 
951 QgsExpressionContextUtils::GetLayerVisibility::GetLayerVisibility()
952  : QgsScopedExpressionFunction( QStringLiteral( "is_layer_visible" ), QgsExpressionFunction::ParameterList() << QgsExpressionFunction::Parameter( QStringLiteral( "id" ) ), QStringLiteral( "General" ) )
953 {}
954 
955 QVariant QgsExpressionContextUtils::GetLayerVisibility::func( const QVariantList &values, const QgsExpressionContext *, QgsExpression *parent, const QgsExpressionNodeFunction * )
956 {
957  if ( mLayers.isEmpty() )
958  {
959  return false;
960  }
961 
962  bool isVisible = false;
963  QgsMapLayer *layer = QgsExpressionUtils::getMapLayer( values.at( 0 ), parent );
964  if ( layer && mLayers.contains( layer ) )
965  {
966  isVisible = true;
967  if ( mScaleBasedVisibilityDetails.contains( layer ) && !qgsDoubleNear( mScale, 0.0 ) )
968  {
969  if ( ( !qgsDoubleNear( mScaleBasedVisibilityDetails[ layer ].first, 0.0 ) && mScale > mScaleBasedVisibilityDetails[ layer ].first ) ||
970  ( !qgsDoubleNear( mScaleBasedVisibilityDetails[ layer ].second, 0.0 ) && mScale < mScaleBasedVisibilityDetails[ layer ].second ) )
971  {
972  isVisible = false;
973  }
974  }
975  }
976 
977  return isVisible;
978 }
979 
980 QgsScopedExpressionFunction *QgsExpressionContextUtils::GetLayerVisibility::clone() const
981 {
982  GetLayerVisibility *func = new GetLayerVisibility();
983  func->mLayers = mLayers;
984  func->mScale = mScale;
985  func->mScaleBasedVisibilityDetails = mScaleBasedVisibilityDetails;
986  return func;
987 }
988 
989 //
990 // mesh expression context
991 //
992 
994 class CurrentVertexZValueExpressionFunction: public QgsScopedExpressionFunction
995 {
996  public:
997  CurrentVertexZValueExpressionFunction():
998  QgsScopedExpressionFunction( "$vertex_z",
999  0,
1000  QStringLiteral( "Meshes" ) )
1001  {}
1002 
1003  QgsScopedExpressionFunction *clone() const override {return new CurrentVertexZValueExpressionFunction();}
1004 
1005  QVariant func( const QVariantList &, const QgsExpressionContext *context, QgsExpression *, const QgsExpressionNodeFunction * ) override
1006  {
1007  if ( !context )
1008  return QVariant();
1009 
1010  if ( !context->hasVariable( QStringLiteral( "_mesh_vertex_index" ) ) || !context->hasVariable( QStringLiteral( "_mesh_layer" ) ) )
1011  return QVariant();
1012 
1013  int vertexIndex = context->variable( QStringLiteral( "_mesh_vertex_index" ) ).toInt();
1014 
1015  QgsMeshLayer *layer = qobject_cast<QgsMeshLayer *>( qvariant_cast<QgsMapLayer *>( context->variable( QStringLiteral( "_mesh_layer" ) ) ) );
1016  if ( !layer || !layer->nativeMesh() || layer->nativeMesh()->vertexCount() <= vertexIndex )
1017  return QVariant();
1018 
1019  const QgsMeshVertex &vertex = layer->nativeMesh()->vertex( vertexIndex );
1020  if ( !vertex.isEmpty() )
1021  return vertex.z();
1022  else
1023  return QVariant();
1024  }
1025 
1026  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
1027  {
1028  return false;
1029  }
1030 };
1031 
1032 class CurrentVertexXValueExpressionFunction: public QgsScopedExpressionFunction
1033 {
1034  public:
1035  CurrentVertexXValueExpressionFunction():
1036  QgsScopedExpressionFunction( "$vertex_x",
1037  0,
1038  QStringLiteral( "Meshes" ) )
1039  {}
1040 
1041  QgsScopedExpressionFunction *clone() const override {return new CurrentVertexXValueExpressionFunction();}
1042 
1043  QVariant func( const QVariantList &, const QgsExpressionContext *context, QgsExpression *, const QgsExpressionNodeFunction * ) override
1044  {
1045  if ( !context )
1046  return QVariant();
1047 
1048  if ( !context->hasVariable( QStringLiteral( "_mesh_vertex_index" ) ) || !context->hasVariable( QStringLiteral( "_mesh_layer" ) ) )
1049  return QVariant();
1050 
1051  int vertexIndex = context->variable( QStringLiteral( "_mesh_vertex_index" ) ).toInt();
1052 
1053  QgsMeshLayer *layer = qobject_cast<QgsMeshLayer *>( qvariant_cast<QgsMapLayer *>( context->variable( QStringLiteral( "_mesh_layer" ) ) ) );
1054  if ( !layer || !layer->nativeMesh() || layer->nativeMesh()->vertexCount() <= vertexIndex )
1055  return QVariant();
1056 
1057  const QgsMeshVertex &vertex = layer->nativeMesh()->vertex( vertexIndex );
1058  if ( !vertex.isEmpty() )
1059  return vertex.x();
1060  else
1061  return QVariant();
1062  }
1063 
1064  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
1065  {
1066  return false;
1067  }
1068 };
1069 
1070 class CurrentVertexYValueExpressionFunction: public QgsScopedExpressionFunction
1071 {
1072  public:
1073  CurrentVertexYValueExpressionFunction():
1074  QgsScopedExpressionFunction( "$vertex_y",
1075  0,
1076  QStringLiteral( "Meshes" ) )
1077  {}
1078 
1079  QgsScopedExpressionFunction *clone() const override {return new CurrentVertexYValueExpressionFunction();}
1080 
1081  QVariant func( const QVariantList &, const QgsExpressionContext *context, QgsExpression *, const QgsExpressionNodeFunction * ) override
1082  {
1083  if ( !context )
1084  return QVariant();
1085 
1086  if ( !context->hasVariable( QStringLiteral( "_mesh_vertex_index" ) ) || !context->hasVariable( QStringLiteral( "_mesh_layer" ) ) )
1087  return QVariant();
1088 
1089  int vertexIndex = context->variable( QStringLiteral( "_mesh_vertex_index" ) ).toInt();
1090 
1091  QgsMeshLayer *layer = qobject_cast<QgsMeshLayer *>( qvariant_cast<QgsMapLayer *>( context->variable( QStringLiteral( "_mesh_layer" ) ) ) );
1092  if ( !layer || !layer->nativeMesh() || layer->nativeMesh()->vertexCount() <= vertexIndex )
1093  return QVariant();
1094 
1095  const QgsMeshVertex &vertex = layer->nativeMesh()->vertex( vertexIndex );
1096  if ( !vertex.isEmpty() )
1097  return vertex.y();
1098  else
1099  return QVariant();
1100  }
1101 
1102  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
1103  {
1104  return false;
1105  }
1106 };
1107 
1108 class CurrentVertexExpressionFunction: public QgsScopedExpressionFunction
1109 {
1110  public:
1111  CurrentVertexExpressionFunction():
1112  QgsScopedExpressionFunction( "$vertex_as_point",
1113  0,
1114  QStringLiteral( "Meshes" ) )
1115  {}
1116 
1117  QgsScopedExpressionFunction *clone() const override {return new CurrentVertexExpressionFunction();}
1118 
1119  QVariant func( const QVariantList &, const QgsExpressionContext *context, QgsExpression *, const QgsExpressionNodeFunction * ) override
1120  {
1121  if ( !context )
1122  return QVariant();
1123 
1124  if ( !context->hasVariable( QStringLiteral( "_mesh_vertex_index" ) ) || !context->hasVariable( QStringLiteral( "_mesh_layer" ) ) )
1125  return QVariant();
1126 
1127  int vertexIndex = context->variable( QStringLiteral( "_mesh_vertex_index" ) ).toInt();
1128 
1129  QgsMeshLayer *layer = qobject_cast<QgsMeshLayer *>( qvariant_cast<QgsMapLayer *>( context->variable( QStringLiteral( "_mesh_layer" ) ) ) );
1130  if ( !layer || !layer->nativeMesh() || layer->nativeMesh()->vertexCount() <= vertexIndex )
1131  return QVariant();
1132 
1133  const QgsMeshVertex &vertex = layer->nativeMesh()->vertex( vertexIndex );
1134  if ( !vertex.isEmpty() )
1135  return QVariant::fromValue( QgsGeometry( new QgsPoint( vertex ) ) );
1136  else
1137  return QVariant();
1138  }
1139 
1140  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
1141  {
1142  return false;
1143  }
1144 };
1145 
1146 class CurrentVertexIndexExpressionFunction: public QgsScopedExpressionFunction
1147 {
1148  public:
1149  CurrentVertexIndexExpressionFunction():
1150  QgsScopedExpressionFunction( "$vertex_index",
1151  0,
1152  QStringLiteral( "Meshes" ) )
1153  {}
1154 
1155  QgsScopedExpressionFunction *clone() const override {return new CurrentVertexIndexExpressionFunction();}
1156 
1157  QVariant func( const QVariantList &, const QgsExpressionContext *context, QgsExpression *, const QgsExpressionNodeFunction * ) override
1158  {
1159  if ( !context )
1160  return QVariant();
1161 
1162  if ( !context->hasVariable( QStringLiteral( "_mesh_vertex_index" ) ) || !context->hasVariable( QStringLiteral( "_mesh_layer" ) ) )
1163  return QVariant();
1164 
1165  return context->variable( QStringLiteral( "_mesh_vertex_index" ) );
1166  }
1167 
1168 
1169  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
1170  {
1171  return false;
1172  }
1173 };
1174 
1175 class CurrentFaceAreaExpressionFunction: public QgsScopedExpressionFunction
1176 {
1177  public:
1178  CurrentFaceAreaExpressionFunction():
1179  QgsScopedExpressionFunction( "$face_area",
1180  0,
1181  QStringLiteral( "Meshes" ) )
1182  {}
1183 
1184  QgsScopedExpressionFunction *clone() const override {return new CurrentFaceAreaExpressionFunction();}
1185 
1186  QVariant func( const QVariantList &, const QgsExpressionContext *context, QgsExpression *parent, const QgsExpressionNodeFunction * ) override
1187  {
1188  if ( !context )
1189  return QVariant();
1190 
1191  if ( !context->hasVariable( QStringLiteral( "_mesh_face_index" ) ) || !context->hasVariable( QStringLiteral( "_mesh_layer" ) ) )
1192  return QVariant();
1193 
1194  int faceIndex = context->variable( QStringLiteral( "_mesh_face_index" ) ).toInt();
1195 
1196  QgsMeshLayer *layer = qobject_cast<QgsMeshLayer *>( qvariant_cast<QgsMapLayer *>( context->variable( QStringLiteral( "_mesh_layer" ) ) ) );
1197  if ( !layer || !layer->nativeMesh() || layer->nativeMesh()->faceCount() <= faceIndex )
1198  return QVariant();
1199 
1200  const QgsMeshFace &face = layer->nativeMesh()->face( faceIndex );
1201  if ( !face.isEmpty() )
1202  {
1203  QgsDistanceArea *calc = parent->geomCalculator();
1204  QgsGeometry geom = QgsMeshUtils::toGeometry( layer->nativeMesh()->face( faceIndex ), layer->nativeMesh()->vertices );
1205  if ( calc )
1206  {
1207  double area = calc->measureArea( geom );
1208  area = calc->convertAreaMeasurement( area, parent->areaUnits() );
1209  return QVariant( area );
1210  }
1211  else
1212  {
1213  return QVariant( geom.area() );
1214  }
1215  }
1216  else
1217  return QVariant();
1218  }
1219 
1220  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
1221  {
1222  return false;
1223  }
1224 };
1225 
1226 class CurrentFaceIndexExpressionFunction: public QgsScopedExpressionFunction
1227 {
1228  public:
1229  CurrentFaceIndexExpressionFunction():
1230  QgsScopedExpressionFunction( "$face_index",
1231  0,
1232  QStringLiteral( "Meshes" ) )
1233  {}
1234 
1235  QgsScopedExpressionFunction *clone() const override {return new CurrentFaceIndexExpressionFunction();}
1236 
1237  QVariant func( const QVariantList &, const QgsExpressionContext *context, QgsExpression *, const QgsExpressionNodeFunction * ) override
1238  {
1239  if ( !context )
1240  return QVariant();
1241 
1242  if ( !context->hasVariable( QStringLiteral( "_mesh_face_index" ) ) || !context->hasVariable( QStringLiteral( "_mesh_layer" ) ) )
1243  return QVariant();
1244 
1245  return context->variable( QStringLiteral( "_mesh_face_index" ) ).toInt();
1246 
1247  }
1248 
1249  bool isStatic( const QgsExpressionNodeFunction *, QgsExpression *, const QgsExpressionContext * ) const override
1250  {
1251  return false;
1252  }
1253 };
1254 
1255 
1256 
1258 {
1259  std::unique_ptr<QgsExpressionContextScope> scope = std::make_unique<QgsExpressionContextScope>();
1260 
1261  switch ( elementType )
1262  {
1263  case QgsMesh::Vertex:
1264  {
1265  QgsExpression::registerFunction( new CurrentVertexExpressionFunction, true );
1266  QgsExpression::registerFunction( new CurrentVertexXValueExpressionFunction, true );
1267  QgsExpression::registerFunction( new CurrentVertexYValueExpressionFunction, true );
1268  QgsExpression::registerFunction( new CurrentVertexZValueExpressionFunction, true );
1269  QgsExpression::registerFunction( new CurrentVertexIndexExpressionFunction, true );
1270  scope->addFunction( "$vertex_as_point", new CurrentVertexExpressionFunction );
1271  scope->addFunction( "$vertex_x", new CurrentVertexXValueExpressionFunction );
1272  scope->addFunction( "$vertex_y", new CurrentVertexYValueExpressionFunction );
1273  scope->addFunction( "$vertex_z", new CurrentVertexZValueExpressionFunction );
1274  scope->addFunction( "$vertex_index", new CurrentVertexIndexExpressionFunction );
1275  }
1276  break;
1277  case QgsMesh::Face:
1278  {
1279  QgsExpression::registerFunction( new CurrentFaceAreaExpressionFunction, true );
1280  QgsExpression::registerFunction( new CurrentFaceIndexExpressionFunction, true );
1281  scope->addFunction( "$face_area", new CurrentFaceAreaExpressionFunction );
1282  scope->addFunction( "$face_index", new CurrentFaceIndexExpressionFunction );
1283  }
1284  break;
1285  case QgsMesh::Edge:
1286  break;
1287  }
1288 
1289  return scope.release();
1290 }
QgsExpressionContext
Expression contexts are used to encapsulate the parameters around which a QgsExpression should be eva...
Definition: qgsexpressioncontext.h:406
QgsLayoutObject::customProperty
QVariant customProperty(const QString &key, const QVariant &defaultValue=QVariant()) const
Read a custom property from the object.
Definition: qgslayoutobject.cpp:231
QgsMapLayer::crs
QgsCoordinateReferenceSystem crs
Definition: qgsmaplayer.h:79
QgsApplication::osName
static QString osName()
Returns a string name of the operating system QGIS is running on.
Definition: qgsapplication.cpp:1280
QgsLayoutItem::id
QString id() const
Returns the item's ID name.
Definition: qgslayoutitem.h:359
QgsExpressionContextScope::addFunction
void addFunction(const QString &name, QgsScopedExpressionFunction *function)
Adds a function to the scope.
Definition: qgsexpressioncontext.cpp:193
QgsLayoutObject::layout
const QgsLayout * layout() const
Returns the layout the object is attached to.
Definition: qgslayoutobject.cpp:216
QgsExpressionContextScope::setFeature
void setFeature(const QgsFeature &feature)
Convenience function for setting a feature for the scope.
Definition: qgsexpressioncontext.h:319
qgsexpressioncontextutils.h
QgsSymbol::color
QColor color() const
Returns the symbol's color.
Definition: qgssymbol.cpp:877
QgsRectangle::height
double height() const SIP_HOLDGIL
Returns the height of the rectangle.
Definition: qgsrectangle.h:230
QgsProject::customVariables
QVariantMap customVariables() const
A map of custom project variables.
Definition: qgsproject.cpp:2139
QgsProject::projectStorage
QgsProjectStorage * projectStorage() const
Returns pointer to project storage implementation that handles read/write of the project file.
Definition: qgsproject.cpp:793
Qgis::version
static QString version()
Version string.
Definition: qgis.cpp:277
QgsLayoutItemPage
Item representing the paper in a layout.
Definition: qgslayoutitempage.h:58
QgsExpressionContextScope::setVariable
void setVariable(const QString &name, const QVariant &value, bool isStatic=false)
Convenience method for setting a variable in the context scope by name name and value.
Definition: qgsexpressioncontext.cpp:83
QgsExpressionContextUtils::globalScope
static QgsExpressionContextScope * globalScope()
Creates a new scope which contains variables and functions relating to the global QGIS context.
Definition: qgsexpressioncontextutils.cpp:40
QgsCoordinateReferenceSystem::projectionAcronym
QString projectionAcronym() const
Returns the projection acronym for the projection used by the CRS.
Definition: qgscoordinatereferencesystem.cpp:1239
QgsProcessingContext::project
QgsProject * project() const
Returns the project in which the algorithm is being executed.
Definition: qgsprocessingcontext.h:121
QgsExpressionContextScope::addVariable
void addVariable(const QgsExpressionContextScope::StaticVariable &variable)
Adds a variable into the context scope.
Definition: qgsexpressioncontext.cpp:97
QgsPoint
Point geometry type, with support for z-dimension and m-values.
Definition: qgspoint.h:48
QgsExpressionContextUtils::mapToolCaptureScope
static QgsExpressionContextScope * mapToolCaptureScope(const QList< QgsPointLocator::Match > &matches)
Sets the expression context variables which are available for expressions triggered by a map tool cap...
Definition: qgsexpressioncontextutils.cpp:514
qgsexpression.h
QgsLayout::renderContext
QgsLayoutRenderContext & renderContext()
Returns a reference to the layout's render context, which stores information relating to the current ...
Definition: qgslayout.cpp:359
QgsMapLayer::setCustomProperty
Q_INVOKABLE void setCustomProperty(const QString &key, const QVariant &value)
Set a custom property for layer.
Definition: qgsmaplayer.cpp:1976
algorithm
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 allowing algorithms to be written in pure substantial changes are required in order to port existing x Processing algorithms for QGIS x The most significant changes are outlined not GeoAlgorithm For algorithms which operate on features one by consider subclassing the QgsProcessingFeatureBasedAlgorithm class This class allows much of the boilerplate code for looping over features from a vector layer to be bypassed and instead requires implementation of a processFeature method Ensure that your algorithm(or algorithm 's parent class) implements the new pure virtual createInstance(self) call
QgsCoordinateReferenceSystem::WKT_PREFERRED
@ WKT_PREFERRED
Preferred format, matching the most recent WKT ISO standard. Currently an alias to WKT2_2019,...
Definition: qgscoordinatereferencesystem.h:680
QgsTemporalRangeObject::isTemporal
bool isTemporal() const
Returns true if the object's temporal range is enabled, and the object will be filtered when renderin...
Definition: qgstemporalrangeobject.cpp:30
QgsExpressionContextUtils::notificationScope
static QgsExpressionContextScope * notificationScope(const QString &message=QString())
Creates a new scope which contains variables and functions relating to provider notifications.
Definition: qgsexpressioncontextutils.cpp:898
QgsMesh::Face
@ Face
Definition: qgsmeshdataprovider.h:69
QgsExpression::geomCalculator
QgsDistanceArea * geomCalculator()
Returns calculator used for distance and area calculations (used by $length, $area and $perimeter fun...
Definition: qgsexpression.cpp:401
QgsLayoutAtlas::count
int count() const override
Returns the number of features to iterate over.
Definition: qgslayoutatlas.cpp:401
QgsRectangle::center
QgsPointXY center() const SIP_HOLDGIL
Returns the center point of the rectangle.
Definition: qgsrectangle.h:251
QgsExpressionContextUtils::formScope
static QgsExpressionContextScope * formScope(const QgsFeature &formFeature=QgsFeature(), const QString &formMode=QString())
Creates a new scope which contains functions and variables from the current attribute form/table form...
Definition: qgsexpressioncontextutils.cpp:270
QgsApplication::setCustomVariables
static void setCustomVariables(const QVariantMap &customVariables)
Custom expression variables for this application.
Definition: qgsapplication.cpp:1955
QgsExpressionContextUtils::registerContextFunctions
static void registerContextFunctions()
Registers all known core functions provided by QgsExpressionContextScope objects.
Definition: qgsexpressioncontextutils.cpp:905
qgssymbollayerutils.h
QgsCoordinateReferenceSystem::description
QString description
Definition: qgscoordinatereferencesystem.h:218
QgsFields
Container of fields for a vector layer.
Definition: qgsfields.h:44
QgsExpressionContextUtils::setProjectVariable
static void setProjectVariable(QgsProject *project, const QString &name, const QVariant &value)
Sets a project context variable.
Definition: qgsexpressioncontextutils.cpp:302
QgsGeometry::fromPointXY
static QgsGeometry fromPointXY(const QgsPointXY &point) SIP_HOLDGIL
Creates a new geometry from a QgsPointXY object.
Definition: qgsgeometry.cpp:176
QgsExpressionContextUtils::layerScope
static QgsExpressionContextScope * layerScope(const QgsMapLayer *layer)
Creates a new scope which contains variables and functions relating to a QgsMapLayer.
Definition: qgsexpressioncontextutils.cpp:334
QgsExpressionContextUtils::setLayerVariables
static void setLayerVariables(QgsMapLayer *layer, const QVariantMap &variables)
Sets all layer context variables.
Definition: qgsexpressioncontextutils.cpp:408
qgslayoutmultiframe.h
qgsprocessingmodelalgorithm.h
QgsFeature::geometry
QgsGeometry geometry
Definition: qgsfeature.h:71
QgsTemporalRangeObject::temporalRange
const QgsDateTimeRange & temporalRange() const
Returns the datetime range for the object.
Definition: qgstemporalrangeobject.cpp:43
QgsPoint::z
double z
Definition: qgspoint.h:71
QgsExpressionContextUtils::mapSettingsScope
static QgsExpressionContextScope * mapSettingsScope(const QgsMapSettings &mapSettings)
Creates a new scope which contains variables and functions relating to a QgsMapSettings object.
Definition: qgsexpressioncontextutils.cpp:427
QgsDistanceArea::measureArea
double measureArea(const QgsGeometry &geometry) const
Measures the area of a geometry.
Definition: qgsdistancearea.cpp:208
QgsProject::setCustomVariables
void setCustomVariables(const QVariantMap &customVariables)
A map of custom project variables.
Definition: qgsproject.cpp:2144
QgsProject::instance
static QgsProject * instance()
Returns the QgsProject singleton instance.
Definition: qgsproject.cpp:480
QgsExpressionContextUtils::globalProjectLayerScopes
static QList< QgsExpressionContextScope * > globalProjectLayerScopes(const QgsMapLayer *layer)
Creates a list of three scopes: global, layer's project and layer.
Definition: qgsexpressioncontextutils.cpp:377
qgsprojoperation.h
QgsExpressionContextUtils::layoutScope
static QgsExpressionContextScope * layoutScope(const QgsLayout *layout)
Creates a new scope which contains variables and functions relating to a QgsLayout layout.
Definition: qgsexpressioncontextutils.cpp:556
QgsProjOperation::description
QString description() const
Description.
Definition: qgsprojoperation.h:61
QgsExpressionContextUtils::layoutItemScope
static QgsExpressionContextScope * layoutItemScope(const QgsLayoutItem *item)
Creates a new scope which contains variables and functions relating to a QgsLayoutItem.
Definition: qgsexpressioncontextutils.cpp:699
qgsfeatureid.h
QgsLayoutItem::page
int page() const
Returns the page the item is currently on, with the first page returning 0.
Definition: qgslayoutitem.cpp:542
QgsExpressionContextUtils::multiFrameScope
static QgsExpressionContextScope * multiFrameScope(const QgsLayoutMultiFrame *frame)
Creates a new scope which contains variables and functions relating to a QgsLayoutMultiFrame.
Definition: qgsexpressioncontextutils.cpp:781
QgsSymbol
Abstract base class for all rendered symbols.
Definition: qgssymbol.h:92
QgsExpressionContextScope::setFields
void setFields(const QgsFields &fields)
Convenience function for setting a fields for the scope.
Definition: qgsexpressioncontext.cpp:199
QgsLayoutMultiFrame
Abstract base class for layout items with the ability to distribute the content to several frames (Qg...
Definition: qgslayoutmultiframe.h:48
qgsmapsettings.h
QgsExpressionContextUtils::setLayerVariable
static void setLayerVariable(QgsMapLayer *layer, const QString &name, const QVariant &value)
Sets a layer context variable.
Definition: qgsexpressioncontextutils.cpp:392
QgsMarkerSymbol::angle
double angle() const
Returns the marker angle for the whole symbol.
Definition: qgsmarkersymbol.cpp:53
QgsMapSettings::frameRate
double frameRate() const
Returns the frame rate of the map (in frames per second), for maps which are part of an animation.
Definition: qgsmapsettings.cpp:868
QgsExpressionContextUtils::removeProjectVariable
static void removeProjectVariable(QgsProject *project, const QString &name)
Remove project context variable.
Definition: qgsexpressioncontextutils.cpp:322
QgsExpressionContext::EXPR_SYMBOL_COLOR
static const QString EXPR_SYMBOL_COLOR
Inbuilt variable name for symbol color variable.
Definition: qgsexpressioncontext.h:807
QgsExpressionContext::variable
QVariant variable(const QString &name) const
Fetches a matching variable from the context.
Definition: qgsexpressioncontext.cpp:300
QgsLayout::pageCollection
QgsLayoutPageCollection * pageCollection()
Returns a pointer to the layout's page collection, which stores and manages page items in the layout.
Definition: qgslayout.cpp:459
QgsLayoutAtlas::layout
QgsLayout * layout() override
Returns the layout associated with the iterator.
Definition: qgslayoutatlas.cpp:47
QgsLayoutItem::sizeWithUnits
QgsLayoutSize sizeWithUnits() const
Returns the item's current size, including units.
Definition: qgslayoutitem.h:673
FID_IS_NULL
#define FID_IS_NULL(fid)
Definition: qgsfeatureid.h:30
QgsProject
Encapsulates a QGIS project, including sets of map layers and their styles, layouts,...
Definition: qgsproject.h:103
qgsmaplayerlistutils_p.h
QgsApplication::platform
static QString platform()
Returns the QGIS platform name, e.g., "desktop", "server", "qgis_process" or "external" (for external...
Definition: qgsapplication.cpp:1339
QgsExpressionContext::EXPR_SYMBOL_ANGLE
static const QString EXPR_SYMBOL_ANGLE
Inbuilt variable name for symbol angle variable.
Definition: qgsexpressioncontext.h:809
QgsDistanceArea::convertAreaMeasurement
double convertAreaMeasurement(double area, QgsUnitTypes::AreaUnit toUnits) const
Takes an area measurement calculated by this QgsDistanceArea object and converts it to a different ar...
Definition: qgsdistancearea.cpp:992
QgsApplication::locale
static QString locale()
Returns the QGIS locale.
Definition: qgsapplication.cpp:1344
qgsapplication.h
qgstriangularmesh.h
QgsVectorLayer::fields
QgsFields fields() const FINAL
Returns the list of fields of this layer.
Definition: qgsvectorlayer.cpp:3436
QgsFeature::id
QgsFeatureId id
Definition: qgsfeature.h:68
QgsPoint::y
double y
Definition: qgspoint.h:70
QgsVectorTileUtils::scaleToZoomLevel
static int scaleToZoomLevel(double mapScale, int sourceMinZoom, int sourceMaxZoom, double z0Scale=559082264.0287178)
Finds the best fitting zoom level given a map scale denominator and allowed zoom level range.
Definition: qgsvectortileutils.cpp:71
QgsExpressionContextUtils::projectScope
static QgsExpressionContextScope * projectScope(const QgsProject *project)
Creates a new scope which contains variables and functions relating to a QGIS project.
Definition: qgsexpressioncontextutils.cpp:291
QgsExpressionContextUtils::setLayoutVariable
static void setLayoutVariable(QgsLayout *layout, const QString &name, const QVariant &value)
Sets a layout context variable.
Definition: qgsexpressioncontextutils.cpp:625
QgsMesh::faceCount
int faceCount() const
Returns number of faces.
Definition: qgsmeshdataprovider.cpp:205
QgsMapSettings::rotation
double rotation() const
Returns the rotation of the resulting map image, in degrees clockwise.
Definition: qgsmapsettings.cpp:102
QgsMesh::vertexCount
int vertexCount() const
Returns number of vertices.
Definition: qgsmeshdataprovider.cpp:200
QgsProcessingAlgorithm::id
QString id() const
Returns the unique ID for the algorithm, which is a combination of the algorithm provider's ID and th...
Definition: qgsprocessingalgorithm.cpp:52
QgsLayoutSize::toQSizeF
QSizeF toQSizeF() const
Converts the layout size to a QSizeF.
Definition: qgslayoutsize.cpp:47
QgsLayout::customProperty
QVariant customProperty(const QString &key, const QVariant &defaultValue=QVariant()) const
Read a custom property from the layout.
Definition: qgslayout.cpp:415
QgsMesh::ElementType
ElementType
Defines type of mesh elements.
Definition: qgsmeshdataprovider.h:65
QgsLayoutAtlas::enabled
bool enabled() const
Returns whether the atlas generation is enabled.
Definition: qgslayoutatlas.h:67
QgsExpressionContextUtils::setLayoutMultiFrameVariables
static void setLayoutMultiFrameVariables(QgsLayoutMultiFrame *frame, const QVariantMap &variables)
Sets all layout multiframe context variables for an frame.
Definition: qgsexpressioncontextutils.cpp:823
qgslayoutitem.h
QgsFeature::isValid
bool isValid() const
Returns the validity of this feature.
Definition: qgsfeature.cpp:216
QgsProcessingContext
Contains information about the context in which a processing algorithm is executed.
Definition: qgsprocessingcontext.h:46
QgsMarkerSymbol
A marker symbol type, for rendering Point and MultiPoint geometries.
Definition: qgsmarkersymbol.h:30
QgsUnitTypes::toString
static Q_INVOKABLE QString toString(QgsUnitTypes::DistanceUnit unit)
Returns a translated string representing a distance unit.
Definition: qgsunittypes.cpp:199
qgsDoubleNear
bool qgsDoubleNear(double a, double b, double epsilon=4 *std::numeric_limits< double >::epsilon())
Compare two doubles (but allow some difference)
Definition: qgis.h:2265
qgsprocessingalgorithm.h
QgsMapSettings::mapUnits
QgsUnitTypes::DistanceUnit mapUnits() const
Returns the units of the map's geographical coordinates - used for scale calculation.
Definition: qgsmapsettings.cpp:400
QgsMeshLayer
Represents a mesh layer supporting display of data on structured or unstructured meshes.
Definition: qgsmeshlayer.h:98
QgsLayoutReportContext::feature
QgsFeature feature() const
Returns the current feature for evaluating the layout.
Definition: qgslayoutreportcontext.h:62
QgsLayoutAtlas::coverageLayer
QgsVectorLayer * coverageLayer() const
Returns the coverage layer used for the atlas features.
Definition: qgslayoutatlas.h:116
QgsExpressionContextUtils::parentFormScope
static QgsExpressionContextScope * parentFormScope(const QgsFeature &formFeature=QgsFeature(), const QString &formMode=QString())
Creates a new scope which contains functions and variables from the current parent attribute form/tab...
Definition: qgsexpressioncontextutils.cpp:281
qgsexpressionutils.h
QgsExpressionContextUtils::processingAlgorithmScope
static QgsExpressionContextScope * processingAlgorithmScope(const QgsProcessingAlgorithm *algorithm, const QVariantMap &parameters, QgsProcessingContext &context)
Creates a new scope which contains variables and functions relating to a processing algorithm,...
Definition: qgsexpressioncontextutils.cpp:850
QgsLayout::reportContext
QgsLayoutReportContext & reportContext()
Returns a reference to the layout's report context, which stores information relating to the current ...
Definition: qgslayout.cpp:369
QgsExpressionContextUtils::setGlobalVariable
static void setGlobalVariable(const QString &name, const QVariant &value)
Sets a global context variable.
Definition: qgsexpressioncontextutils.cpp:65
QgsCoordinateReferenceSystem::toWkt
QString toWkt(WktVariant variant=WKT1_GDAL, bool multiline=false, int indentationWidth=4) const
Returns a WKT representation of this CRS.
Definition: qgscoordinatereferencesystem.cpp:1810
QgsMesh::Edge
@ Edge
Definition: qgsmeshdataprovider.h:68
QgsExpressionContextUtils::setLayoutItemVariable
static void setLayoutItemVariable(QgsLayoutItem *item, const QString &name, const QVariant &value)
Sets a layout item context variable, with the given name and value.
Definition: qgsexpressioncontextutils.cpp:746
QgsMesh::face
QgsMeshFace face(int index) const
Returns a face at the index.
Definition: qgsmeshdataprovider.cpp:145
QgsMeshLayer::nativeMesh
QgsMesh * nativeMesh()
Returns native mesh (nullptr before rendering or calling to updateMesh)
Definition: qgsmeshlayer.cpp:275
QgsExpressionContextUtils::processingModelAlgorithmScope
static QgsExpressionContextScope * processingModelAlgorithmScope(const QgsProcessingModelAlgorithm *model, const QVariantMap &parameters, QgsProcessingContext &context)
Creates a new scope which contains variables and functions relating to a processing model algorithm,...
Definition: qgsexpressioncontextutils.cpp:867
QgsExpressionContextUtils::setLayoutItemVariables
static void setLayoutItemVariables(QgsLayoutItem *item, const QVariantMap &variables)
Sets all layout item context variables for an item.
Definition: qgsexpressioncontextutils.cpp:762
QgsScopedExpressionFunction::referencedColumns
QSet< QString > referencedColumns(const QgsExpressionNodeFunction *node) const override
Returns a set of field names which are required for this function.
Definition: qgsexpressioncontextutils.cpp:922
QgsMapLayer::id
QString id() const
Returns the layer's unique ID, which is used to access this layer from QgsProject.
Definition: qgsmaplayer.cpp:169
QgsLayoutPageCollection::page
QgsLayoutItemPage * page(int pageNumber)
Returns a specific page (by pageNumber) from the collection.
Definition: qgslayoutpagecollection.cpp:472
QgsApplication::setCustomVariable
static void setCustomVariable(const QString &name, const QVariant &value)
Set a single custom expression variable.
Definition: qgsapplication.cpp:1970
QgsWeakMapLayerPointer
QPointer< QgsMapLayer > QgsWeakMapLayerPointer
Weak pointer for QgsMapLayer.
Definition: qgsmaplayer.h:2146
QgsMapSettings::scale
double scale() const
Returns the calculated map scale.
Definition: qgsmapsettings.cpp:458
QgsLayoutItem
Base class for graphical items within a QgsLayout.
Definition: qgslayoutitem.h:112
QgsProject::fileName
QString fileName
Definition: qgsproject.h:107
QgsCoordinateReferenceSystem::toProj
QString toProj() const
Returns a Proj string representation of this CRS.
Definition: qgscoordinatereferencesystem.cpp:1293
QgsExpressionNodeFunction
An expression node for expression functions.
Definition: qgsexpressionnodeimpl.h:395
QgsMeshFace
QVector< int > QgsMeshFace
List of vertex indexes.
Definition: qgsmeshdataprovider.h:42
QgsCoordinateReferenceSystem::operation
QgsProjOperation operation() const
Returns information about the PROJ operation associated with the coordinate reference system,...
Definition: qgscoordinatereferencesystem.cpp:1440
qgslayout.h
QgsLayoutObject::setCustomProperty
void setCustomProperty(const QString &key, const QVariant &value)
Set a custom property for the object.
Definition: qgslayoutobject.cpp:226
QgsExpressionContextScope
Single scope for storing variables and functions for use within a QgsExpressionContext....
Definition: qgsexpressioncontext.h:113
QgsExpressionContextUtils::setGlobalVariables
static void setGlobalVariables(const QVariantMap &variables)
Sets all global context variables.
Definition: qgsexpressioncontextutils.cpp:70
QgsLayoutAtlas::currentFeatureNumber
int currentFeatureNumber() const
Returns the current feature number, where a value of 0 corresponds to the first feature.
Definition: qgslayoutatlas.h:254
QgsProject::absoluteFilePath
QString absoluteFilePath() const
Returns full absolute path to the project file if the project is stored in a file system - derived fr...
Definition: qgsproject.cpp:823
QgsPointLocator::Match
Definition: qgspointlocator.h:187
qgsvectorlayer.h
QgsMapSettings::destinationCrs
QgsCoordinateReferenceSystem destinationCrs() const
Returns the destination coordinate reference system for the map render.
Definition: qgsmapsettings.cpp:358
QgsLayoutItemMap
Layout graphical items for displaying a map.
Definition: qgslayoutitemmap.h:317
QgsExpression::areaUnits
QgsUnitTypes::AreaUnit areaUnits() const
Returns the desired areal units for calculations involving geomCalculator(), e.g.,...
Definition: qgsexpression.cpp:424
QgsExpressionContextUtils::createFeatureBasedContext
static QgsExpressionContext createFeatureBasedContext(const QgsFeature &feature, const QgsFields &fields)
Helper function for creating an expression context which contains just a feature and fields collectio...
Definition: qgsexpressioncontextutils.cpp:842
QgsApplication::userLoginName
static QString userLoginName()
Returns the user's operating system login account name.
Definition: qgsapplication.cpp:1211
QgsLayoutItem::uuid
virtual QString uuid() const
Returns the item identification string.
Definition: qgslayoutitem.h:345
QgsMapLayer::customProperty
Q_INVOKABLE QVariant customProperty(const QString &value, const QVariant &defaultValue=QVariant()) const
Read a custom property from layer.
Definition: qgsmaplayer.cpp:1999
QgsExpressionContextUtils::updateSymbolScope
static QgsExpressionContextScope * updateSymbolScope(const QgsSymbol *symbol, QgsExpressionContextScope *symbolScope=nullptr)
Updates a symbol scope related to a QgsSymbol to an expression context.
Definition: qgsexpressioncontextutils.cpp:538
QgsExpressionContextUtils::meshExpressionScope
static QgsExpressionContextScope * meshExpressionScope(QgsMesh::ElementType elementType)
Creates a new scope which contains functions relating to mesh layer element elementType.
QgsProcessingAlgorithm
Abstract base class for processing algorithms.
Definition: qgsprocessingalgorithm.h:52
c
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
Definition: porting_processing.dox:1
QgsGeometry
A geometry is the spatial representation of a feature.
Definition: qgsgeometry.h:124
QgsExpressionFunction
A abstract base class for defining QgsExpression functions.
Definition: qgsexpressionfunction.h:40
QgsLayoutAtlas::currentFilename
QString currentFilename() const
Returns the current feature filename.
Definition: qgslayoutatlas.cpp:503
QgsLayout
Base class for layouts, which can contain items such as maps, labels, scalebars, etc.
Definition: qgslayout.h:50
QgsVectorLayer
Represents a vector layer which manages a vector based data sets.
Definition: qgsvectorlayer.h:391
QgsRectangle::width
double width() const SIP_HOLDGIL
Returns the width of the rectangle.
Definition: qgsrectangle.h:223
QgsScopedExpressionFunction::clone
virtual QgsScopedExpressionFunction * clone() const =0
Returns a clone of the function.
QgsMapLayer
Base class for all map layer types. This is the base class for all map layer types (vector,...
Definition: qgsmaplayer.h:72
qgsmarkersymbol.h
QgsGeometry::fromRect
static QgsGeometry fromRect(const QgsRectangle &rect) SIP_HOLDGIL
Creates a new geometry from a QgsRectangle.
Definition: qgsgeometry.cpp:241
QgsMesh::vertices
QVector< QgsMeshVertex > vertices
Definition: qgsmeshdataprovider.h:112
QgsMapLayer::name
QString name
Definition: qgsmaplayer.h:76
QgsExpressionContextUtils::removeGlobalVariable
static void removeGlobalVariable(const QString &name)
Remove a global context variable.
Definition: qgsexpressioncontextutils.cpp:75
QgsProject::createExpressionContextScope
QgsExpressionContextScope * createExpressionContextScope() const override
This method needs to be reimplemented in all classes which implement this interface and return an exp...
Definition: qgsproject.cpp:2224
QgsScopedExpressionFunction::isStatic
bool isStatic(const QgsExpressionNodeFunction *node, QgsExpression *parent, const QgsExpressionContext *context) const override
Will be called during prepare to determine if the function is static.
Definition: qgsexpressioncontextutils.cpp:928
QgsVectorTileUtils::scaleToZoom
static double scaleToZoom(double mapScale, double z0Scale=559082264.0287178)
Finds zoom level given map scale denominator.
Definition: qgsvectortileutils.cpp:63
QgsExpressionContextUtils::atlasScope
static QgsExpressionContextScope * atlasScope(const QgsLayoutAtlas *atlas)
Creates a new scope which contains variables and functions relating to a QgsLayoutAtlas.
Definition: qgsexpressioncontextutils.cpp:660
qgsprocessingcontext.h
QgsCoordinateReferenceSystem::authid
QString authid
Definition: qgscoordinatereferencesystem.h:217
qgslayoutpagecollection.h
QgsExpressionFunction::allParamsStatic
static bool allParamsStatic(const QgsExpressionNodeFunction *node, QgsExpression *parent, const QgsExpressionContext *context)
This will return true if all the params for the provided function node are static within the constrai...
Definition: qgsexpressionfunction.cpp:244
Qgis::releaseName
static QString releaseName()
Release name.
Definition: qgis.cpp:289
QgsApplication::customVariables
static QVariantMap customVariables()
Custom expression variables for this application.
Definition: qgsapplication.cpp:1936
QgsExpression::registerFunction
static bool registerFunction(QgsExpressionFunction *function, bool transferOwnership=false)
Registers a function to the expression engine.
Definition: qgsexpressionfunction.cpp:8427
QgsDistanceArea
A general purpose distance and area calculator, capable of performing ellipsoid based calculations.
Definition: qgsdistancearea.h:52
QgsLayoutRenderContext::dpi
double dpi() const
Returns the dpi for outputting the layout.
Definition: qgslayoutrendercontext.cpp:89
QgsCoordinateReferenceSystem::ellipsoidAcronym
QString ellipsoidAcronym() const
Returns the ellipsoid acronym for the ellipsoid used by the CRS.
Definition: qgscoordinatereferencesystem.cpp:1251
QgsFeature
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
Definition: qgsfeature.h:55
QgsPoint::isEmpty
bool isEmpty() const override SIP_HOLDGIL
Returns true if the geometry is empty.
Definition: qgspoint.cpp:767
QgsMeshUtils::toGeometry
CORE_EXPORT QgsGeometry toGeometry(const QgsMeshFace &face, const QVector< QgsMeshVertex > &vertices)
Returns face as polygon geometry.
Definition: qgstriangularmesh.cpp:638
QgsMasterLayoutInterface
Interface for master layout type objects, such as print layouts and reports.
Definition: qgsmasterlayoutinterface.h:42
QgsLayout::setCustomProperty
void setCustomProperty(const QString &key, const QVariant &value)
Set a custom property for the layout.
Definition: qgslayout.cpp:407
QgsScopedExpressionFunction::usesGeometry
bool usesGeometry(const QgsExpressionNodeFunction *node) const override
Does this function use a geometry object.
Definition: qgsexpressioncontextutils.cpp:916
qgsvectortileutils.h
QgsExpressionContextScope::StaticVariable
Single variable definition for use within a QgsExpressionContextScope.
Definition: qgsexpressioncontext.h:120
QgsLayoutPageCollection::pageCount
int pageCount() const
Returns the number of pages in the collection.
Definition: qgslayoutpagecollection.cpp:467
QgsExpression
Class for parsing and evaluation of expressions (formerly called "search strings")....
Definition: qgsexpression.h:102
QgsMapSettings
The QgsMapSettings class contains configuration for rendering of the map. The rendering itself is don...
Definition: qgsmapsettings.h:88
QgsMapSettings::visibleExtent
QgsRectangle visibleExtent() const
Returns the actual extent derived from requested extent that takes output image size into account.
Definition: qgsmapsettings.cpp:411
QgsExpressionContextUtils::setLayoutMultiFrameVariable
static void setLayoutMultiFrameVariable(QgsLayoutMultiFrame *frame, const QString &name, const QVariant &value)
Sets a layout multi frame context variable, with the given name and value.
Definition: qgsexpressioncontextutils.cpp:807
QgsLayoutPoint
This class provides a method of storing points, consisting of an x and y coordinate,...
Definition: qgslayoutpoint.h:39
QgsMesh::vertex
QgsMeshVertex vertex(int index) const
Returns a vertex at the index.
Definition: qgsmeshdataprovider.cpp:138
QgsMapSettings::currentFrame
long long currentFrame() const
Returns the current frame number of the map, for maps which are part of an animation.
Definition: qgsmapsettings.cpp:878
QgsScopedExpressionFunction
Expression function for use within a QgsExpressionContextScope. This differs from a standard QgsExpre...
Definition: qgsexpressioncontext.h:39
MathUtils::angle
double ANALYSIS_EXPORT angle(QgsPoint *p1, QgsPoint *p2, QgsPoint *p3, QgsPoint *p4)
Calculates the angle between two segments (in 2 dimension, z-values are ignored)
Definition: MathUtils.cpp:786
QgsGeometry::area
double area() const
Returns the planar, 2-dimensional area of the geometry.
Definition: qgsgeometry.cpp:1880
Qgis::versionInt
static int versionInt()
Version number used for comparing versions using the "Check QGIS Version" function.
Definition: qgis.cpp:282
QgsLayoutAtlas
Class used to render QgsLayout as an atlas, by iterating over the features from an associated vector ...
Definition: qgslayoutatlas.h:41
QgsLayoutItem::createExpressionContext
QgsExpressionContext createExpressionContext() const override
This method needs to be reimplemented in all classes which implement this interface and return an exp...
Definition: qgslayoutitem.cpp:1159
QgsPoint::x
double x
Definition: qgspoint.h:69
QgsScopedExpressionFunction::func
QVariant func(const QVariantList &values, const QgsExpressionContext *context, QgsExpression *parent, const QgsExpressionNodeFunction *node) override=0
Returns result of evaluating the function.
qgsproject.h
QgsLayoutReportContext::layer
QgsVectorLayer * layer() const
Returns the vector layer associated with the layout's context.
Definition: qgslayoutreportcontext.cpp:66
QgsExpressionContextUtils::setProjectVariables
static void setProjectVariables(QgsProject *project, const QVariantMap &variables)
Sets all project context variables.
Definition: qgsexpressioncontextutils.cpp:314
QgsMapSettings::layers
QList< QgsMapLayer * > layers(bool expandGroupLayers=false) const
Returns the list of layers which will be rendered in the map.
Definition: qgsmapsettings.cpp:299
QgsExpressionContextUtils::setLayoutVariables
static void setLayoutVariables(QgsLayout *layout, const QVariantMap &variables)
Sets all layout context variables.
Definition: qgsexpressioncontextutils.cpp:641
QgsLayoutPageCollection::pagePositionToLayoutPosition
QPointF pagePositionToLayoutPosition(int page, const QgsLayoutPoint &position) const
Converts a position on a page to an absolute position in layout coordinates.
Definition: qgslayoutpagecollection.cpp:234
QgsExpressionContext::hasVariable
bool hasVariable(const QString &name) const
Check whether a variable is specified by any scope within the context.
Definition: qgsexpressioncontext.cpp:289
QgsApplication::userFullName
static QString userFullName()
Returns the user's operating system login account full display name.
Definition: qgsapplication.cpp:1246
qgslayoutitemmap.h
QgsMesh::Vertex
@ Vertex
Definition: qgsmeshdataprovider.h:67
qgslayoutatlas.h
QgsLayoutAtlas::nameForPage
QString nameForPage(int page) const
Returns the calculated name for a specified atlas page number.
Definition: qgslayoutatlas.cpp:177