#pragma once

namespace ros_bridge {
namespace traits {


//! @brief Checks if class T has a member function z.
//!
//! Checks if class T has a member function z. E.g if the class Point has a member function
//! z than HasMemberZ<Point>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberZ
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::z) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};
//! @brief Checks if class T has a member function SetZ.
//!
//! Checks if class T has a member function SetZ. E.g if the class Point has a member function
//! SetZ than HasMemberSetZ<Point>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberSetZ
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::SetZ) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Checks if class T has a member function labels.
//!
//! Checks if class T has a member function labels. E.g if the class T has a member function
//! labels than HasMemberLabels<T>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberLabels
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::labels) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Checks if class T has a member function SetLabels.
//!
//! Checks if class T has a member function SetLabels. E.g if the class T has a member function
//! SetLabels than HasMemberSetLabels<T>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberSetLabels
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::SetLabels) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Checks if class T has a member function labels.
//!
//! Checks if class T has a member function likelihood. E.g if the class T has a member function
//! likelihood than HasMemberLikelihood<T>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberLikelihood
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::likelihood) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Checks if class T has a member function setLikelihood.
//!
//! Checks if class T has a member function setLikelihood. E.g if the class T has a member function
//! setLikelihood than HasMemberSetLikelihood<T>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberSetLikelihood
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::setLikelihood) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Checks if class T has a member function header.
//!
//! Checks if class T has a member function header. E.g if the class T has a member function
//! header than HasMemberHeader<T>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberHeader
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::header) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Checks if class T has a member function setHeader.
//!
//! Checks if class T has a member function setHeader. E.g if the class T has a member function
//! setHeader than HasMemberSetHeader<T>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberSetHeader
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::setHeader) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Checks if class T has a member function altitude.
//!
//! Checks if class T has a member function altitude. E.g if the class T has a member function
//! altitude than HasMemberAltitude<T>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberAltitude
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::altitude) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Checks if class T has a member function setAltitude.
//!
//! Checks if class T has a member function setAltitude. E.g if the class T has a member function
//! setAltitude than HasMemberSetAltitude<T>::value is equal to 1 and 0 either.
template <typename T>
class HasMemberSetAltitude
{
    typedef char Small;
    struct Big { char x[2]; };

    template <typename C> static Small test( typeof(&C::setAltitude) ) ;
    template <typename C> static Big test(...);

public:
    enum { value = sizeof(test<T>(0)) == sizeof(Small) };
};

//! @brief Selects the Type T or U depending on flag and stores it inside Result.
template <int flag, typename T, typename U>
struct Select {typedef T Result;};
template <typename T, typename U>
struct Select<0, T, U> {typedef U Result;};

struct HasComponents {};
struct Has3Components : public HasComponents {};
struct Has2Components : public HasComponents {};



template <typename T>
struct Type2Type{
    typedef T OriginalType;
};


template <int k>
struct Int2Type{
    enum {value = k};
};

}
}
