// Copyright (C) 2019 by Joseph Mirabel, LAAS-CNRS.
//
// This file is part of the hpp-corbaserver.
//
// This software is provided "as is" without warranty of any kind,
// either expressed or implied, including but not limited to the
// implied warranties of fitness for a particular purpose.
//
// See the COPYING file for more information.

#ifndef HPP_CORE_CONSTRAINTS_IDL
#define HPP_CORE_CONSTRAINTS_IDL
#include <hpp/common.idl>

#include <hpp/constraints_idl/constraints.idl>

module hpp
{
  module constraints_idl {
    interface Implicit;
    typedef sequence <Implicit> Implicits;
  };

  module core_idl {

  interface Constraint
  {
    HPP_EXPOSE_MEMORY_DEALLOCATION(Error)

    boolean apply (inout floatSeq config) raises (Error);

    string name () raises (Error);
    string str () raises (Error);
    boolean isSatisfied (in floatSeq config) raises (Error);

    Constraint copy() raises (Error);
  }; // interface Constraint

  interface ConfigProjector : Constraint
  {
    void setRightHandSideFromConfig             (in floatSeq config) raises (Error);
    //-> rightHandSideFromConfig
    void setRightHandSideOfConstraintFromConfig (in constraints_idl::Implicit nm, in floatSeq config) raises (Error);
    //-> rightHandSideFromConfig
    void setRightHandSide             (in floatSeq param) raises (Error);
    //-> rightHandSide
    void setRightHandSideOfConstraint (in constraints_idl::Implicit nm, in floatSeq rhs) raises (Error);
    //-> rightHandSide
    floatSeq getRightHandSide () raises (Error);
    //-> rightHandSide
    void setRightHandSideAt (in value_type s) raises (Error);
    //-> rightHandSideAt
    boolean isConstraintSatisfied (in constraints_idl::Implicit nm,
                                   in floatSeq arg, out floatSeq err,
                                   out boolean constraintFound) raises (Error);
    //* hpp::core::vector_t _arg = hpp::corbaServer::floatSeqToVector (arg);
    //* hpp::constraints::ImplicitPtr_t _nm = hpp::corbaServer::reference_to_servant_base<hpp::constraints::Implicit>(server_, nm)->get();
    //* hpp::core::vector_t errorOut (_nm->function ().outputSpace ()->nv ());
    //* bool res = getT ()->solver ().isConstraintSatisfied
    //*    (_nm, _arg,errorOut, constraintFound);
    //* err = hpp::corbaServer::vectorToFloatSeq (errorOut);
    //* return res;

    constraints_idl::Implicits numericalConstraints() raises(Error);

    boolean add (in constraints_idl::Implicit numconstraint, in unsigned long priority);

    void setLastIsOptional (in boolean optional);
    //-> lastIsOptional

    boolean getLastIsOptional ();
    //-> lastIsOptional

    void setErrorThreshold (in value_type threshold) raises(Error);
    //-> errorThreshold
    value_type getErrorThreshold () raises(Error);
    //-> errorThreshold
  }; // interface ConfigProjector

  interface ConstraintSet : Constraint
  {
    /// The return type should be ConfigProjector. At the moment, this causes a bug
    /// because because the implementation does not know this inherits from Constraint.
    /// The CORBA object below \b is a ConfigProjector
    Constraint getConfigProjector () raises (Error);
    //-> configProjector

    void addConstraint(in Constraint a_constraint) raises (Error);
  }; // interface ConstraintSet

  }; // module core
}; // module hpp
//* #include <hpp/core/constraint.hh>
//* #include <hpp/core/constraint-set.hh>
//* #include <hpp/core/config-projector.hh>
//* #include <hpp/constraints_idl/constraints.hh>
//* #include <hpp/constraints/solver/by-substitution.hh>

#endif // HPP_CORE_CONSTRAINTS_IDL
