Skip to content

Commit

Permalink
Code dedup
Browse files Browse the repository at this point in the history
  • Loading branch information
m-kuhn committed Jul 8, 2017
1 parent 66d562a commit eb8eb59
Show file tree
Hide file tree
Showing 2 changed files with 37 additions and 18 deletions.
42 changes: 24 additions & 18 deletions src/core/expression/qgsexpressionfunction.cpp
Expand Up @@ -4302,20 +4302,17 @@ bool QgsWithVariableExpressionFunction::isStatic( const QgsExpressionNodeFunctio
if ( args->count() < 3 )
return false;

// We only need to check if the node evaluation is static, if both - name and value - are static.
if ( args->at( 0 )->isStatic( parent, context ) && args->at( 1 )->isStatic( parent, context ) )
{
QVariant name = args->at( 0 )->eval( parent, context );
QVariant value = args->at( 1 )->eval( parent, context );

QgsExpressionContextScope *scope = new QgsExpressionContextScope();
scope->setVariable( name.toString(), value );

QgsExpressionContext *updatedContext = const_cast<QgsExpressionContext *>( context );
updatedContext->appendScope( scope );

if ( args->at( 2 )->isStatic( parent, updatedContext ) )
// Temporarily append a new scope to provide the variable
appendTemporaryVariable( context, name.toString(), value );
if ( args->at( 2 )->isStatic( parent, context ) )
isStatic = true;
delete updatedContext->popScope();
popTemporaryVariable( context );
}

return false;
Expand All @@ -4332,15 +4329,13 @@ QVariant QgsWithVariableExpressionFunction::run( QgsExpressionNode::NodeList *ar
QVariant name = args->at( 0 )->eval( parent, context );
QVariant value = args->at( 1 )->eval( parent, context );

QgsExpressionContextScope *scope = new QgsExpressionContextScope();
scope->setVariable( name.toString(), value );

QgsExpressionContext *updatedContext = const_cast<QgsExpressionContext *>( context );
if ( !context )
updatedContext = new QgsExpressionContext();
updatedContext->appendScope( scope );

appendTemporaryVariable( updatedContext, name.toString(), value );
result = args->at( 2 )->eval( parent, updatedContext );
delete updatedContext->popScope();
popTemporaryVariable( updatedContext );
if ( !context )
delete updatedContext;

Expand Down Expand Up @@ -4369,13 +4364,24 @@ bool QgsWithVariableExpressionFunction::prepare( const QgsExpressionNodeFunction
QVariant name = args->at( 0 )->prepare( parent, context );
QVariant value = args->at( 1 )->prepare( parent, context );

QgsExpressionContextScope *scope = new QgsExpressionContextScope();
scope->setVariable( name.toString(), value );
appendTemporaryVariable( context, name.toString(), value );
args->at( 2 )->prepare( parent, context );
popTemporaryVariable( context );

return true;
}

void QgsWithVariableExpressionFunction::popTemporaryVariable( const QgsExpressionContext *context ) const
{
QgsExpressionContext *updatedContext = const_cast<QgsExpressionContext *>( context );
updatedContext->appendScope( scope );
args->at( 2 )->prepare( parent, updatedContext );
delete updatedContext->popScope();
}

return true;
void QgsWithVariableExpressionFunction::appendTemporaryVariable( const QgsExpressionContext *context, const QString &name, const QVariant &value ) const
{
QgsExpressionContextScope *scope = new QgsExpressionContextScope();
scope->setVariable( name, value );

QgsExpressionContext *updatedContext = const_cast<QgsExpressionContext *>( context );
updatedContext->appendScope( scope );
}
13 changes: 13 additions & 0 deletions src/core/expression/qgsexpressionfunction.h
Expand Up @@ -29,6 +29,7 @@
class QgsExpressionNodeFunction;
class QgsExpression;
class QgsExpressionContext;
class QgsExpressionContextScope;

/** \ingroup core
* A abstract base class for defining QgsExpression functions.
Expand Down Expand Up @@ -475,6 +476,18 @@ class QgsWithVariableExpressionFunction : public QgsExpressionFunction
QVariant func( const QVariantList &values, const QgsExpressionContext *context, QgsExpression *parent ) override;

bool prepare( const QgsExpressionNodeFunction *node, QgsExpression *parent, const QgsExpressionContext *context ) const override;

private:

/**
* Append a scope with a single variable definition (``name``=``value``)
*/
void appendTemporaryVariable( const QgsExpressionContext *context, const QString &name, const QVariant &value ) const;

/**
* Pop the temporary scope again
*/
void popTemporaryVariable( const QgsExpressionContext *context ) const;
};

#endif
Expand Down

0 comments on commit eb8eb59

Please sign in to comment.