#include "Trigger.h"
#include "Gegenstand.h"


VarPointer::VarPointer( const char *name, Variable *var )
{
    this->name = name;
    this->var = var;
    ref = 1;
}

VarPointer::~VarPointer()
{
    if( var )
        var->release();
}

Text VarPointer::getName() const
{
    return name;
}

void VarPointer::setVariable( Variable *var )
{
    if( this->var )
        this->var->release();
    this->var = var;
}

Variable *VarPointer::getVariable() const
{
    return var ? var->getThis() : 0;
}

Variable *VarPointer::zVariable() const
{
    return var;
}

VarPointer::operator Variable *( ) const
{
    return var;
}

VarPointer *VarPointer::getThis()
{
    ref++;
    return this;
}

VarPointer *VarPointer::release()
{
    if( !--ref )
        delete this;
    return 0;
}

Bedingung::Bedingung( Aktion *expression )
{
    this->expression = expression;
    ref = 1;
}

Bedingung::~Bedingung()
{
    if( expression )
        expression->release();
}

void Bedingung::setExpression( Aktion *expr )
{
    if( expression )
        expression->release();
    expression = expr;
}

bool Bedingung::check( Spiel *zSpiel, Ereignis *zEreignis )
{
    if( !expression )
        return 1;
    double wait;
    ProgramCounter c;
    LocalMemory m;
    while( !expression->runNext( zSpiel, zEreignis, &m, &c, wait ) )
    {
        Variable *var = m.zVariable( "__return__" );
        if( !var )
            return 0;
        switch( var->getVariableTyp() )
        {
        case NICHTS:
            return 0;
        case INTEGER:
            return ( (Integer *)var )->getValue() != 0;
        case BOOLEAN:
            return ( (Boolean *)var )->getValue();
        case STRING:
            return ( (String *)var )->getValue().getLength();
        case FLOAT:
            return ( (Float *)var )->getValue() != 0;
        case TASTE:
            return ( (Integer *)var )->getValue() != 0;
        case GEGENSTAND_TYP:
            return ( (GegenstandTypVar *)var )->getValue() != KEIN_GEGENSTAND;
        default:
            return 1;
        }
    }
}

Bedingung *Bedingung::getThis()
{
    ref++;
    return this;
}

Bedingung *Bedingung::release()
{
    if( !--ref )
        delete this;
    return 0;
}