#include "LagrangianFiniteElementBasis.hpp"

template<class ToolBasisFunctionType> 
bool 
LagrangianFiniteElementBasis<ToolBasisFunctionType>::
is_hierarchical() 
{
  return false;
}

template<class ToolBasisFunctionType> 
unsigned int 
LagrangianFiniteElementBasis<ToolBasisFunctionType>::
nbShapeFunction(const unsigned int order, const ElemType itemType) 
{
  switch (itemType)
  {
    case NODEELEM:
    {
      return 1;
    }
    case EDGE2:
    case EDGE3:
    {
      return order+1;
    }
    case TRI3:
    case TRI6:
    {
      return (order+1)*(order+2)/2;
    }
    case QUAD4:
    case QUAD9:
    {
      return (order+1)*(order+1);
    }
    case QUAD8:
    {
      switch (order)
      {
        case 1:  
          return 4;
        case 2:
          return 8;
        default:
        {
          std::cerr<< "LagrangianBasis: Unsupported order "<<itemType<<std::endl;
          std::logic_error("halt");
          return 0;
        }
      }
    }
    case TET4:
    case TET10:
    {
      return (order+1)*(order+2)*(order+3)/6;
    }
    case HEX8:
    case HEX27:
    {
      return (order+1)*(order+1)*(order+1);
    }
    case HEX20:
    {
      switch (order)
      {
        case 1:  
          return 8;
        case 2:
          return 20;
        default:
        {
          std::cerr<< "LagrangianBasis: Unsupported order "<<itemType<<std::endl;
          std::logic_error("halt");
          return 0;
        }
      }
    }
    case PRISM6:
    {
      return 6;
    }
    case PRISM15:
    {
      switch (order)
      {
        case 1:  
          return 6;
        case 2:
          return 15;
        default:
        {
          std::cerr<< "LagrangianBasis: Unsupported order "<<itemType<<std::endl;
          std::logic_error("halt");
          return 0;
        }
      }
    }
    case PYRAMID5:
    {
      return 5;
    }
    case PYRAMID13:
    {
      switch (order)
      {
        case 1:  
          return 5;
        case 2:
          return 13;
        default:
        {
          std::cerr<< "LagrangianBasis: Unsupported order "<<itemType<<std::endl;
          std::logic_error("halt");
          return 0;
        }
      }
    }
    default:
    {
      std::cerr<< "LagrangianBasis: Unsupported Itemtype "<<itemType<<std::endl;
      std::logic_error("halt");
      return 0;
    }
  }
}
