// Copyright (c) 2012-2023 Wojciech Figat. All rights reserved.
#pragma once
#include "Engine/Scripting/SerializableScriptingObject.h"
#include "BehaviorTypes.h"
///
/// Base class for Behavior Tree nodes.
///
API_CLASS(Abstract) class FLAXENGINE_API BehaviorTreeNode : public SerializableScriptingObject
{
DECLARE_SCRIPTING_TYPE_WITH_CONSTRUCTOR_IMPL(BehaviorTreeNode, SerializableScriptingObject);
friend class BehaviorTreeGraph;
protected:
// Raw memory byte offset from the start of the behavior memory block.
API_FIELD(ReadOnly) int32 _memoryOffset = 0;
public:
///
/// Node user name (eg. Follow Enemy, or Pick up Weapon).
///
API_FIELD() String Name;
///
/// Initializes node state. Called after whole tree is loaded and nodes hierarchy is setup.
///
/// Node owner asset.
API_FUNCTION() virtual void Init(BehaviorTree* tree)
{
}
///
/// Gets the node instance state size. A chunk of the valid memory is passed via InitState to setup that memory chunk (one per-behavior).
///
API_FUNCTION() virtual int32 GetStateSize() const
{
return 0;
}
///
/// Initializes node instance state. Called when starting logic simulation for a given behavior.
///
/// Behavior to simulate.
/// Pointer to pre-allocated memory for this node to use (call constructor of the state container).
API_FUNCTION() virtual void InitState(Behavior* behavior, void* memory)
{
}
///
/// Cleanups node instance state. Called when stopping logic simulation for a given behavior.
///
/// Behavior to simulate.
/// Pointer to pre-allocated memory for this node to use (call destructor of the state container).
API_FUNCTION() virtual void ReleaseState(Behavior* behavior, void* memory)
{
}
///
/// Updates node logic.
///
/// Behavior update context data.
/// Operation result enum.
API_FUNCTION() virtual BehaviorUpdateResult Update(BehaviorUpdateContext context)
{
return BehaviorUpdateResult::Success;
}
// [SerializableScriptingObject]
void Serialize(SerializeStream& stream, const void* otherObj) override;
void Deserialize(DeserializeStream& stream, ISerializeModifier* modifier) override;
public:
// Returns the typed node state at the given memory address.
template
T* GetState(void* memory) const
{
ASSERT((int32)sizeof(T) <= GetStateSize());
return reinterpret_cast((byte*)memory + _memoryOffset);
}
};