CGII/framework/include/cgv/signal/abst_signal.h
2018-05-17 16:01:02 +02:00

224 lines
6.2 KiB
C++

#pragma once
#include <vector>
#include <map>
#include <cgv/type/invalid_type.h>
#include <cgv/type/func/make_argument.h>
#include <cgv/signal/lib_begin.h>
namespace cgv {
namespace signal {
class CGV_API functor_base;
class CGV_API tacker;
/// base functionality of all signals that allows connection and disconnection of abst_functors also to instances derived from the tacker class
class CGV_API signal_base
{
protected:
std::vector<functor_base*> functors;
void link(functor_base* fp);
void unlink(functor_base* fp);
void connect(functor_base* fp);
void disconnect(const functor_base* fp);
public:
/// return the number of connected functors
unsigned get_nr_functors() const;
/// only use this if you exactly know what to do!
void connect_abst(functor_base* fp);
/// virtual destructor
virtual ~signal_base();
/// disconnect all connections to the given tacker
void disconnect(const tacker* t);
/// disconnect all connections
void disconnect_all();
};
/// base class for all functor classes which provides access to the tacker interface of an involved instance
class CGV_API functor_base
{
protected:
/// place characteristic pointers into the two passed references, which serve as basis for the comparison of two functors
virtual void put_pointers(const void* &p1, const void* &p2) const = 0;
public:
/// virtual desctructor
virtual ~functor_base();
/// return the tacker interface of an involved instance or 0 if this is a function functor
virtual const tacker* get_tacker() const;
/// construct a copy of the functor on the heap
virtual functor_base* clone() const = 0;
/// compare this functor to another functor based on the pointers
bool operator == (const functor_base& f) const;
};
/** derive your classes that are attached to signals from this tacker class.
It will automatically disconnect from all signals on destruction such that
no signal can call a method of an instance of your class after the instance
has been destroyed. */
class CGV_API tacker
{
private:
typedef std::map<signal_base*, int> map_type;
mutable map_type signals;
public:
/// implement to allow reimplementation of copy constructor
tacker();
/// overload to avoid copying of signals
tacker(const tacker&);
/// keep track of the given signal
void tack(signal_base* s) const;
/// forget the given signal
void untack(signal_base* s) const;
/// forget all signals
void untack_all() const;
/// disconnect from all tacked signals on destruction
virtual ~tacker();
};
template <int i, typename T1 = type::invalid_type, typename T2 = type::invalid_type, typename T3 = type::invalid_type, typename T4 = type::invalid_type, typename T5 = type::invalid_type, typename T6 = type::invalid_type, typename T7 = type::invalid_type, typename T8 = type::invalid_type>
struct signature;
template <typename T1, typename T2, typename T3, typename T4, typename T5, typename T6, typename T7, typename T8>
struct signature<1,T1, T2, T3, T4, T5, T6, T7, T8>
{
typedef typename type::func::make_argument<T1>::type A1;
};
template <typename T1, typename T2, typename T3, typename T4, typename T5, typename T6, typename T7, typename T8>
struct signature<2,T1, T2, T3, T4, T5, T6, T7, T8>
{
typedef typename type::func::make_argument<T1>::type A1;
typedef typename type::func::make_argument<T2>::type A2;
};
template <typename T1, typename T2, typename T3, typename T4, typename T5, typename T6, typename T7, typename T8>
struct signature<3,T1, T2, T3, T4, T5, T6, T7, T8>
{
typedef typename type::func::make_argument<T1>::type A1;
typedef typename type::func::make_argument<T2>::type A2;
typedef typename type::func::make_argument<T3>::type A3;
};
template <typename T1, typename T2, typename T3, typename T4, typename T5, typename T6, typename T7, typename T8>
struct signature<4,T1, T2, T3, T4, T5, T6, T7, T8>
{
typedef typename type::func::make_argument<T1>::type A1;
typedef typename type::func::make_argument<T2>::type A2;
typedef typename type::func::make_argument<T3>::type A3;
typedef typename type::func::make_argument<T4>::type A4;
};
template <typename T1, typename T2, typename T3, typename T4, typename T5, typename T6, typename T7, typename T8>
struct signature<5,T1, T2, T3, T4, T5, T6, T7, T8>
{
typedef typename type::func::make_argument<T1>::type A1;
typedef typename type::func::make_argument<T2>::type A2;
typedef typename type::func::make_argument<T3>::type A3;
typedef typename type::func::make_argument<T4>::type A4;
typedef typename type::func::make_argument<T5>::type A5;
};
template <typename T1, typename T2, typename T3, typename T4, typename T5, typename T6, typename T7, typename T8>
struct signature<6,T1, T2, T3, T4, T5, T6, T7, T8>
{
typedef typename type::func::make_argument<T1>::type A1;
typedef typename type::func::make_argument<T2>::type A2;
typedef typename type::func::make_argument<T3>::type A3;
typedef typename type::func::make_argument<T4>::type A4;
typedef typename type::func::make_argument<T5>::type A5;
typedef typename type::func::make_argument<T6>::type A6;
};
template <typename T1, typename T2, typename T3, typename T4, typename T5, typename T6, typename T7, typename T8>
struct signature<7,T1, T2, T3, T4, T5, T6, T7, T8>
{
typedef typename type::func::make_argument<T1>::type A1;
typedef typename type::func::make_argument<T2>::type A2;
typedef typename type::func::make_argument<T3>::type A3;
typedef typename type::func::make_argument<T4>::type A4;
typedef typename type::func::make_argument<T5>::type A5;
typedef typename type::func::make_argument<T6>::type A6;
typedef typename type::func::make_argument<T7>::type A7;
};
template <typename T1, typename T2, typename T3, typename T4, typename T5, typename T6, typename T7, typename T8>
struct signature<8,T1, T2, T3, T4, T5, T6, T7, T8>
{
typedef typename type::func::make_argument<T1>::type A1;
typedef typename type::func::make_argument<T2>::type A2;
typedef typename type::func::make_argument<T3>::type A3;
typedef typename type::func::make_argument<T4>::type A4;
typedef typename type::func::make_argument<T5>::type A5;
typedef typename type::func::make_argument<T6>::type A6;
typedef typename type::func::make_argument<T7>::type A7;
typedef typename type::func::make_argument<T8>::type A8;
};
}
}
#include <cgv/config/lib_end.h>