#ifndef __OBJECT_FUNCTION_H__
#define __OBJECT_FUNCTION_H__

#include "Object.h"
#include "Expr.h"

namespace AScript {

//-----------------------------------------------------------------------------
// Class_Function / Object_Function
//-----------------------------------------------------------------------------
class DLLDECLARE Class_Function : public Class {
public:
	Class_Function(Environment *pEnvOuter);
	void Prepare();
	virtual bool CastFrom(Environment &env, Signal sig, Value &value);
	virtual Object *CreateDescendant(Environment &env, Signal sig, Class *pClass);
};

class DLLDECLARE Object_Function : public Object {
public:
	AScript_DeclareObjectAccessor(Function)
protected:
	Function *_pFunc;
	Value _valueSelf;
public:
	inline Object_Function(Environment &env, Function *pFunc, const Value &valueSelf) :
				Object(env.LookupClass(VTYPE_Function)), _pFunc(pFunc), _valueSelf(valueSelf) {}
	inline Object_Function(Class *pClass, Function *pFunc, const Value &valueSelf) :
				Object(pClass), _pFunc(pFunc), _valueSelf(valueSelf) {}
	inline Object_Function(const Object_Function &obj) :
				Object(obj), _pFunc(Function::Reference(obj._pFunc)), _valueSelf(obj._valueSelf) {}
	~Object_Function();
	virtual bool IsFunction() const;
	virtual Object *Clone() const;
	inline Function *GetFunction() { return _pFunc; }
	inline const Function *GetFunction() const { return _pFunc; }
	inline void SetSelf(const Value &valueSelf) { _valueSelf = valueSelf; }
	inline Value GetSelf() const { return _valueSelf; }
	inline String GetName() const { return _pFunc->GetName(); }
	virtual String GetFullName(Signal sig);
	virtual String ToString(Signal sig, bool exprFlag);
	virtual Value DoCall(Environment &env, Signal sig, Args &args);
	Value Eval(Environment &env, Signal sig, ValueList &valListArg) const;
	String MakePrefix(Signal sig) const;
};

}

#endif
