// StackManager.C: bindable node stack Manager

#include "world.H"
#include "StackManager.H"
#include "xrmlP.H"

#include "Background.H"
#include "Fog.H"
#include "NavigationInfo.H"
#include "Viewpoint.H"
#ifdef PhBRML
#include "PhBAtmosphere.H"
#include "PhBTexturedBackground.H"
#include "PhBMonitorCalibration.H"
#endif

namespace xrml {

void StackManager::init(world *world)
{
  // push defaults for bindable nodes on their respective stacks 
  background.push(new Background); 		background[0]->world = world;
  fog.push(new Fog);				fog[0]->world = world;
  navigationInfo.push(new NavigationInfo); 	navigationInfo[0]->world = world;
  viewpoint.push(new Viewpoint);		viewpoint[0]->world = world;
#ifdef PhBRML
  phbAtmosphere.push(new PhBAtmosphere);	phbAtmosphere[0]->world = world;
  phbBackground.push(new PhBTexturedBackground);	phbBackground[0]->world = world;
  phbMonitorCalibration.push(new PhBMonitorCalibration); phbMonitorCalibration[0]->world = world;
#endif
}

void StackManager::checkin(class Bindable *node)
{
  bindable_stack *stack = 0;
  if (IsBackground(node))
    stack = (bindable_stack*)&background;
  else if (IsFog(node))
    stack = (bindable_stack*)&fog;
  else if (IsNavigationInfo(node))
    stack = (bindable_stack*)&navigationInfo;
  else if (IsViewpoint(node))
    stack = (bindable_stack*)&viewpoint;
#ifdef PhBRML
  else if (IsPhBAtmosphere(node))
    stack = (bindable_stack*)&phbAtmosphere;
  else if (IsPhBBackground(node))
    stack = (bindable_stack*)&phbBackground;
  else if (IsPhBMonitorCalibration(node))
    stack = (bindable_stack*)&phbMonitorCalibration;
#endif
  else {
    Fatal(-1, "StackManager::checkin", "unrecognized Bindable node type %s", node->typeId);
  }

  node->set_stack(stack);

  if (init_bind_bindables && node->stack->size == 1)
    // first encountered bindable node of this type -> bind it
    node->set_bind(true);
}

} // namespace xrml

