//#####################################################################
// Copyright 2021, Craig Schroeder.
// This file is part of PhysBAM whose distribution is governed by the license contained in the accompanying file PHYSBAM_COPYRIGHT.txt.
//#####################################################################
#ifndef __GENERAL_INTERPOLATION_CELL_DEFINITION__
#define __GENERAL_INTERPOLATION_CELL_DEFINITION__

#include <Core/Arrays/ARRAY.h>
#include <Core/Arrays/ARRAYS_ND.h>
#include <Core/Arrays/FACE_ARRAYS.h>
#include <Core/Interpolation/GENERAL_INTERPOLATION_CELL.h>
#include <Core/Interpolation/GENERAL_INTERPOLATION_HELPERS.h>
#include <Core/Interpolation/INTERPOLATION_CELL.h>
#include <Core/Interpolation/INTERPOLATION_HELPERS.h>
#include <Core/Log/DEBUG_UTILITIES.h>
namespace PhysBAM{

//#####################################################################
// Function Interpolate_Cell
//#####################################################################
template<class TV,class T2,class STENCIL,bool const_extrap> auto
GENERAL_INTERPOLATION_CELL<TV,T2,STENCIL,const_extrap>::
Interpolate_Cell(const GRID<TV>& grid,const ARRAYS_ND_BASE<T2,IV>& u,const TV& X) const -> T2
{
    auto p=INTERPOLATION_HELPERS::Clamped_Index<ss,const_extrap>(grid,at_cells,u.domain,X);
    return Interpolate<-1>(stencil,grid,u,p);
}
//#####################################################################
// Function Extrema_Cell
//#####################################################################
template<class TV,class T2,class STENCIL,bool const_extrap> auto
GENERAL_INTERPOLATION_CELL<TV,T2,STENCIL,const_extrap>::
Extrema_Cell(const GRID<TV>& grid,const ARRAYS_ND_BASE<T2,IV>& u0,const ARRAYS_ND_BASE<T2,IV>& u1,const TV& X) const -> VECTOR<T2,2>
{
    auto p=INTERPOLATION_HELPERS::Clamped_Index<ss,const_extrap>(grid,at_cells,u0.domain,X);
    return Extrema<ss,-1>(grid,u0,u1,p);
}
//#####################################################################
// Function Gradient_Cell
//#####################################################################
template<class TV,class T2,class STENCIL,bool const_extrap> auto
GENERAL_INTERPOLATION_CELL<TV,T2,STENCIL,const_extrap>::
Gradient_Cell(const GRID<TV>& grid,const ARRAYS_ND_BASE<T2,IV>& u,const TV& X) const -> TV2
{
    auto p=INTERPOLATION_HELPERS::Clamped_Index<ss,const_extrap>(grid,at_cells,u.domain,X);
    return Gradient<-1>(stencil,grid,u,p);
}
//#####################################################################
// Function Hessian_Cell
//#####################################################################
template<class TV,class T2,class STENCIL,bool const_extrap> auto
GENERAL_INTERPOLATION_CELL<TV,T2,STENCIL,const_extrap>::
Hessian_Cell(const GRID<TV>& grid,const ARRAYS_ND_BASE<T2,IV>& u,const TV& X) const -> SM2
{
    auto p=INTERPOLATION_HELPERS::Clamped_Index<ss,const_extrap>(grid,at_cells,u.domain,X);
    return Hessian<-1>(stencil,grid,u,p);
}
//#####################################################################
// Function Interpolate_Cell_V
//#####################################################################
template<class TV,class T2,class STENCIL,bool const_extrap> auto
GENERAL_INTERPOLATION_CELL<TV,T2,STENCIL,const_extrap>::
Interpolate_Cell_V(const GRID<TV>& grid,const ARRAYS_ND_BASE<T2,IV>& u,const TV& X) const -> T2
{
    return Interpolate_Cell(grid,u,X);
}
//#####################################################################
// Function Extrema_Cell_V
//#####################################################################
template<class TV,class T2,class STENCIL,bool const_extrap> auto
GENERAL_INTERPOLATION_CELL<TV,T2,STENCIL,const_extrap>::
Extrema_Cell_V(const GRID<TV>& grid,const ARRAYS_ND_BASE<T2,IV>& u0,const ARRAYS_ND_BASE<T2,IV>& u1,const TV& X) const -> VECTOR<T2,2>
{
    return Extrema_Cell(grid,u0,u1,X);
}
//#####################################################################
// Function Gradient_Cell_V
//#####################################################################
template<class TV,class T2,class STENCIL,bool const_extrap> auto
GENERAL_INTERPOLATION_CELL<TV,T2,STENCIL,const_extrap>::
Gradient_Cell_V(const GRID<TV>& grid,const ARRAYS_ND_BASE<T2,IV>& u,const TV& X) const -> TV2
{
    return Gradient_Cell(grid,u,X);
}
//#####################################################################
// Function Hessian_Cell_V
//#####################################################################
template<class TV,class T2,class STENCIL,bool const_extrap> auto
GENERAL_INTERPOLATION_CELL<TV,T2,STENCIL,const_extrap>::
Hessian_Cell_V(const GRID<TV>& grid,const ARRAYS_ND_BASE<T2,IV>& u,const TV& X) const -> SM2
{
    return Hessian_Cell(grid,u,X);
}
}
#endif
