Embrace variadic templates

This commit is contained in:
TimePath
2025-01-21 12:36:33 +05:00
committed by Garux
parent de4ba78ad2
commit bb72714216
11 changed files with 456 additions and 797 deletions
+2 -2
View File
@@ -119,7 +119,7 @@ public: // public types
*/
template<typename ObjectClass, void (ObjectClass::*member)(float, float)>
class TexInfoCallbackMethod :
public BindFirstOpaque2<Member2<ObjectClass, float, float, void, member> >
public BindFirstOpaque<Member2<ObjectClass, float, float, void, member> >
{
public:
/**
@@ -128,7 +128,7 @@ public: // public types
* @param object The object on which to invoke the callback method.
*/
TexInfoCallbackMethod(ObjectClass& object) :
BindFirstOpaque2<Member2<ObjectClass, float, float, void, member> >(object) {}
BindFirstOpaque<Member2<ObjectClass, float, float, void, member> >(object) {}
};
public: // public methods
+157 -367
View File
@@ -88,131 +88,6 @@ public:
}
};
template<typename Caller>
class BindFirstOpaque
{
typedef typename Caller::first_argument_type FirstBound;
FirstBound firstBound;
public:
typedef typename Caller::result_type result_type;
explicit BindFirstOpaque( FirstBound firstBound ) : firstBound( firstBound ){
}
result_type operator()() const {
return Caller::call( firstBound );
}
FirstBound getBound() const {
return firstBound;
}
static result_type thunk( void* environment ){
return Caller::call( ConvertFromOpaque<FirstBound>::apply( environment ) );
}
void* getEnvironment() const {
return convertToOpaque( firstBound );
}
};
template<typename Caller>
class BindFirstOpaque1
{
typedef typename Caller::first_argument_type FirstBound;
FirstBound firstBound;
public:
typedef typename Caller::second_argument_type first_argument_type;
typedef typename Caller::result_type result_type;
explicit BindFirstOpaque1( FirstBound firstBound ) : firstBound( firstBound ){
}
result_type operator()( first_argument_type a1 ) const {
return Caller::call( firstBound, a1 );
}
FirstBound getBound() const {
return firstBound;
}
static result_type thunk( void* environment, first_argument_type a1 ){
return Caller::call( ConvertFromOpaque<FirstBound>::apply( environment ), a1 );
}
void* getEnvironment() const {
return convertToOpaque( firstBound );
}
};
template<typename Caller>
class BindFirstOpaque2
{
typedef typename Caller::first_argument_type FirstBound;
FirstBound firstBound;
public:
typedef typename Caller::second_argument_type first_argument_type;
typedef typename Caller::third_argument_type second_argument_type;
typedef typename Caller::result_type result_type;
explicit BindFirstOpaque2( FirstBound firstBound ) : firstBound( firstBound ){
}
result_type operator()( first_argument_type a1, second_argument_type a2 ) const {
return Caller::call( firstBound, a1, a2 );
}
FirstBound getBound() const {
return firstBound;
}
static result_type thunk( void* environment, first_argument_type a1, second_argument_type a2 ){
return Caller::call( ConvertFromOpaque<FirstBound>::apply( environment ), a1, a2 );
}
void* getEnvironment() const {
return convertToOpaque( firstBound );
}
};
template<typename Caller>
class BindFirstOpaque3
{
typedef typename Caller::first_argument_type FirstBound;
FirstBound firstBound;
public:
typedef typename Caller::second_argument_type first_argument_type;
typedef typename Caller::third_argument_type second_argument_type;
typedef typename Caller::fourth_argument_type third_argument_type;
typedef typename Caller::result_type result_type;
explicit BindFirstOpaque3( FirstBound firstBound ) : firstBound( firstBound ){
}
result_type operator()( first_argument_type a1, second_argument_type a2, third_argument_type a3 ) const {
return Caller::call( firstBound, a1, a2, a3 );
}
FirstBound getBound() const {
return firstBound;
}
static result_type thunk( void* environment, first_argument_type a1, second_argument_type a2, third_argument_type a3 ){
return Caller::call( ConvertFromOpaque<FirstBound>::apply( environment ), a1, a2, a3 );
}
void* getEnvironment() const {
return convertToOpaque( firstBound );
}
};
template<typename Caller>
class BindFirstOpaque4
{
typedef typename Caller::first_argument_type FirstBound;
FirstBound firstBound;
public:
typedef typename Caller::second_argument_type first_argument_type;
typedef typename Caller::third_argument_type second_argument_type;
typedef typename Caller::fourth_argument_type third_argument_type;
typedef typename Caller::fifth_argument_type fourth_argument_type;
typedef typename Caller::result_type result_type;
explicit BindFirstOpaque4( FirstBound firstBound ) : firstBound( firstBound ){
}
result_type operator()( first_argument_type a1, second_argument_type a2, third_argument_type a3, fourth_argument_type a4 ) const {
return Caller::call( firstBound, a1, a2, a3, a4 );
}
FirstBound getBound() const {
return firstBound;
}
static result_type thunk( void* environment, first_argument_type a1, second_argument_type a2, third_argument_type a3, fourth_argument_type a4 ){
return Caller::call( ConvertFromOpaque<FirstBound>::apply( environment ), a1, a2, a3, a4 );
}
void* getEnvironment() const {
return convertToOpaque( firstBound );
}
};
template<typename Thunk_>
class CallbackBase
{
@@ -244,38 +119,82 @@ inline bool operator<( const CallbackBase<Thunk>& self, const CallbackBase<Thunk
( !( other.getEnvironment() < self.getEnvironment() ) && self.getThunk() < other.getThunk() );
}
template<class Caller, class F>
class BindFirstOpaqueN;
template<class Caller, class R, class FirstBound, class... Ts>
class BindFirstOpaqueN<Caller, R(FirstBound, Ts...)>
{
FirstBound firstBound;
public:
explicit BindFirstOpaqueN( FirstBound firstBound ) : firstBound( firstBound ){
}
R operator()( Ts... args ) const {
return Caller::call( firstBound, args... );
}
FirstBound getBound() const {
return firstBound;
}
static R thunk( void *environment, Ts... args ){
return Caller::call( ConvertFromOpaque<FirstBound>::apply( environment ), args... );
}
void *getEnvironment() const {
return convertToOpaque( firstBound );
}
};
template<class Caller>
using BindFirstOpaque = BindFirstOpaqueN<Caller, typename Caller::func>;
template<class F>
class CallbackN;
template<class R, class... Ts>
class CallbackN<R(Ts...)> : public CallbackBase<R(*)(void *, Ts...)>
{
using Base = CallbackBase<R (*)(void *, Ts...)>;
static R nullThunk( void *, Ts... ){
}
public:
using func = R(Ts...);
CallbackN() : Base( 0, nullThunk ){
}
template<typename Caller>
CallbackN( const BindFirstOpaque<Caller>& caller ) : Base( caller.getEnvironment(), BindFirstOpaque<Caller>::thunk ){
}
CallbackN( void *environment, typename Base::Thunk function ) : Base( environment, function ){
}
R operator()( Ts... args ) const {
return Base::getThunk()( Base::getEnvironment(), args... );
}
};
/// \brief Combines a void pointer with a pointer to a function which operates on a void pointer.
///
/// Use with the callback constructors MemberCaller, ConstMemberCaller, ReferenceCaller, ConstReferenceCaller, PointerCaller, ConstPointerCaller and FreeCaller.
template<typename Result>
class Callback0 : public CallbackBase<Result ( * )( void* )>
template<class Result>
class Callback0 : public CallbackN<Result()>
{
typedef CallbackBase<Result ( * )( void* )> Base;
static Result nullThunk( void* ){
}
public:
typedef Result result_type;
Callback0() : Base( 0, nullThunk ){
}
template<typename Caller>
Callback0( const BindFirstOpaque<Caller>& caller ) : Base( caller.getEnvironment(), BindFirstOpaque<Caller>::thunk ){
}
Callback0( void* environment, typename Base::Thunk function ) : Base( environment, function ){
}
result_type operator()() const {
return Base::getThunk() ( Base::getEnvironment() );
}
using CallbackN<Result()>::CallbackN;
};
template<typename Caller>
inline Callback0<typename Caller::result_type> makeCallback0( const Caller& caller, typename Caller::first_argument_type callee ){
return Callback0<typename Caller::result_type>( BindFirstOpaque<Caller>( callee ) );
inline Callback0<get_result_type<Caller>> makeCallback0( const Caller& caller, get_argument<Caller, 0> callee ){
return Callback0<get_result_type<Caller>>( BindFirstOpaque<Caller>( callee ) );
}
template<typename Caller>
inline Callback0<typename Caller::result_type> makeStatelessCallback0( const Caller& caller ){
inline Callback0<get_result_type<Caller>> makeStatelessCallback0( const Caller& caller ){
return makeCallback0( Caller0To1<Caller>(), 0 );
}
@@ -286,35 +205,20 @@ typedef Callback0<void> Callback;
/// \brief Combines a void pointer with a pointer to a function which operates on a void pointer and one other argument.
///
/// Use with the callback constructors MemberCaller1, ConstMemberCaller1, ReferenceCaller1, ConstReferenceCaller1, PointerCaller1, ConstPointerCaller1 and FreeCaller1.
template<typename FirstArgument, typename Result>
class Callback1 : public CallbackBase<Result ( * )( void*, FirstArgument )>
template<class FirstArgument, class Result>
class Callback1 : public CallbackN<Result(FirstArgument)>
{
typedef CallbackBase<Result ( * )( void*, FirstArgument )> Base;
static Result nullThunk( void*, FirstArgument ){
}
public:
typedef FirstArgument first_argument_type;
typedef Result result_type;
Callback1() : Base( 0, nullThunk ){
}
template<typename Caller>
Callback1( const BindFirstOpaque1<Caller>& caller ) : Base( caller.getEnvironment(), BindFirstOpaque1<Caller>::thunk ){
}
Callback1( void* environment, typename Base::Thunk function ) : Base( environment, function ){
}
result_type operator()( FirstArgument firstArgument ) const {
return Base::getThunk() ( Base::getEnvironment(), firstArgument );
}
using CallbackN<Result(FirstArgument)>::CallbackN;
};
template<typename Caller>
inline Callback1<typename Caller::second_argument_type, typename Caller::result_type> makeCallback1( const Caller& caller, typename Caller::first_argument_type callee ){
return Callback1<typename Caller::second_argument_type, typename Caller::result_type>( BindFirstOpaque1<Caller>( callee ) );
inline Callback1<get_argument<Caller, 1>, get_result_type<Caller>>
makeCallback1( const Caller& caller, get_argument<Caller, 0> callee ){
return Callback1<get_argument<Caller, 1>, get_result_type<Caller>>( BindFirstOpaque<Caller>( callee ) );
}
template<typename Caller>
inline Callback1<typename Caller::second_argument_type, typename Caller::result_type> makeStatelessCallback1( const Caller& caller ){
inline Callback1<get_argument<Caller, 1>, get_result_type<Caller>> makeStatelessCallback1( const Caller& caller ){
return makeCallback1( Caller1To2<Caller>(), 0 );
}
@@ -322,47 +226,30 @@ inline Callback1<typename Caller::second_argument_type, typename Caller::result_
/// \brief Combines a void pointer with a pointer to a function which operates on a void pointer and two other arguments.
///
template<typename FirstArgument, typename SecondArgument, typename Result>
class Callback2 : public CallbackBase<Result ( * )( void*, FirstArgument, SecondArgument )>
class Callback2 : public CallbackN<Result(FirstArgument, SecondArgument)>
{
typedef CallbackBase<Result ( * )( void*, FirstArgument, SecondArgument )> Base;
static Result nullThunk( void*, FirstArgument, SecondArgument ){
}
public:
typedef FirstArgument first_argument_type;
typedef SecondArgument second_argument_type;
typedef Result result_type;
Callback2() : Base( 0, nullThunk ){
}
template<typename Caller>
Callback2( const BindFirstOpaque2<Caller>& caller ) : Base( caller.getEnvironment(), BindFirstOpaque2<Caller>::thunk ){
}
Callback2( void* environment, typename Base::Thunk function ) : Base( environment, function ){
}
result_type operator()( FirstArgument firstArgument, SecondArgument secondArgument ) const {
return Base::getThunk() ( Base::getEnvironment(), firstArgument, secondArgument );
}
using CallbackN<Result(FirstArgument, SecondArgument)>::CallbackN;
};
template<typename Caller>
inline Callback2<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::result_type
> makeCallback2( const Caller& caller, typename Caller::first_argument_type callee ){
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_result_type<Caller>
> makeCallback2( const Caller& caller, get_argument<Caller, 0> callee ){
return Callback2<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::result_type
>( BindFirstOpaque2<Caller>( callee ) );
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_result_type<Caller>
>( BindFirstOpaque<Caller>( callee ) );
}
template<typename Caller>
inline Callback2<
typename Caller::first_argument_type,
typename Caller::second_argument_type,
typename Caller::result_type
> makeStatelessCallback2( const Caller& caller ){
get_argument<Caller, 0>,
get_argument<Caller, 1>,
get_result_type<Caller>
> makeStatelessCallback2( const Caller& caller){
return makeCallback2( Caller2To3<Caller>(), 0 );
}
@@ -370,50 +257,32 @@ inline Callback2<
/// \brief Combines a void pointer with a pointer to a function which operates on a void pointer and three other arguments.
///
template<typename FirstArgument, typename SecondArgument, typename ThirdArgument, typename Result>
class Callback3 : public CallbackBase<Result ( * )( void*, FirstArgument, SecondArgument, ThirdArgument )>
class Callback3 : public CallbackN<Result(FirstArgument, SecondArgument, ThirdArgument)>
{
typedef CallbackBase<Result ( * )( void*, FirstArgument, SecondArgument, ThirdArgument )> Base;
static Result nullThunk( void*, FirstArgument, SecondArgument, ThirdArgument ){
}
public:
typedef FirstArgument first_argument_type;
typedef SecondArgument second_argument_type;
typedef ThirdArgument third_argument_type;
typedef Result result_type;
Callback3() : Base( 0, nullThunk ){
}
template<typename Caller>
Callback3( const BindFirstOpaque3<Caller>& caller ) : Base( caller.getEnvironment(), BindFirstOpaque3<Caller>::thunk ){
}
Callback3( void* environment, typename Base::Thunk function ) : Base( environment, function ){
}
result_type operator()( FirstArgument firstArgument, SecondArgument secondArgument, ThirdArgument thirdArgument ) const {
return Base::getThunk() ( Base::getEnvironment(), firstArgument, secondArgument, thirdArgument );
}
using CallbackN<Result(FirstArgument, SecondArgument, ThirdArgument)>::CallbackN;
};
template<typename Caller>
inline Callback3<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type,
typename Caller::result_type
> makeCallback3( const Caller& caller, typename Caller::first_argument_type callee ){
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>,
get_result_type<Caller>
> makeCallback3( const Caller& caller, get_argument<Caller, 0> callee ){
return Callback3<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type,
typename Caller::result_type
>( BindFirstOpaque3<Caller>( callee ) );
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>,
get_result_type<Caller>
>( BindFirstOpaque<Caller>( callee ) );
}
template<typename Caller>
inline Callback3<
typename Caller::first_argument_type,
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::result_type
get_argument<Caller, 0>,
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_result_type<Caller>
> makeStatelessCallback3( const Caller& caller ){
return makeCallback3( Caller3To4<Caller>(), 0 );
}
@@ -422,54 +291,35 @@ inline Callback3<
/// \brief Combines a void pointer with a pointer to a function which operates on a void pointer and four other arguments.
///
template<typename FirstArgument, typename SecondArgument, typename ThirdArgument, typename FourthArgument, typename Result>
class Callback4 : public CallbackBase<Result ( * )( void*, FirstArgument, SecondArgument, ThirdArgument, FourthArgument )>
class Callback4 : public CallbackN<Result(FirstArgument, SecondArgument, ThirdArgument, FourthArgument)>
{
typedef CallbackBase<Result ( * )( void*, FirstArgument, SecondArgument, ThirdArgument, FourthArgument )> Base;
static Result nullThunk( void*, FirstArgument, SecondArgument, ThirdArgument, FourthArgument ){
}
public:
typedef FirstArgument first_argument_type;
typedef SecondArgument second_argument_type;
typedef ThirdArgument third_argument_type;
typedef FourthArgument fourth_argument_type;
typedef Result result_type;
Callback4() : Base( 0, nullThunk ){
}
template<typename Caller>
Callback4( const BindFirstOpaque4<Caller>& caller ) : Base( caller.getEnvironment(), BindFirstOpaque4<Caller>::thunk ){
}
Callback4( void* environment, typename Base::Thunk function ) : Base( environment, function ){
}
result_type operator()( FirstArgument firstArgument, SecondArgument secondArgument, ThirdArgument thirdArgument, FourthArgument fourthArgument ) const {
return Base::getThunk() ( Base::getEnvironment(), firstArgument, secondArgument, thirdArgument, fourthArgument );
}
using CallbackN<Result(FirstArgument, SecondArgument, ThirdArgument, FourthArgument)>::CallbackN;
};
template<typename Caller>
inline Callback4<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type,
typename Caller::fifth_argument_type,
typename Caller::result_type
> makeCallback4( const Caller& caller, typename Caller::first_argument_type callee ){
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>,
get_argument<Caller, 4>,
get_result_type<Caller>
> makeCallback4( const Caller& caller, get_argument<Caller, 0> callee ){
return Callback4<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type,
typename Caller::fifth_argument_type,
typename Caller::result_type
>( BindFirstOpaque4<Caller>( callee ) );
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>,
get_argument<Caller, 4>,
get_result_type<Caller>
>( BindFirstOpaque<Caller>( callee ) );
}
template<typename Caller>
inline Callback4<
typename Caller::first_argument_type,
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type,
typename Caller::result_type
get_argument<Caller, 0>,
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>,
get_result_type<Caller>
> makeStatelessCallback4( const Caller& caller ){
return makeCallback4( Caller4To5<Caller>(), 0 );
}
@@ -480,140 +330,80 @@ inline Callback4<
/// \dontinclude generic/callback.cpp
/// \skipline MemberCaller example
/// \until end example
template<typename Environment, void( Environment::*member ) ( )>
class MemberCaller : public BindFirstOpaque< Member<Environment, void, member> >
{
public:
MemberCaller( Environment& environment ) : BindFirstOpaque< Member<Environment, void, member> >( environment ){
}
};
template<class Environment, void(Environment::*member)()>
using MemberCaller = BindFirstOpaque<Member<Environment, void, member>>;
/// \brief Forms a Callback from a const Environment reference and a const Environment member-function.
///
/// \dontinclude generic/callback.cpp
/// \skipline MemberCaller example
/// \until end example
template<typename Environment, void( Environment::*member ) ( ) const>
class ConstMemberCaller : public BindFirstOpaque< ConstMember<Environment, void, member> >
{
public:
ConstMemberCaller( const Environment& environment ) : BindFirstOpaque< ConstMember<Environment, void, member> >( environment ){
}
};
template<class Environment, void(Environment::*member)() const>
using ConstMemberCaller = BindFirstOpaque<ConstMember<Environment, void, member>>;
/// \brief Forms a Callback from a non-const Environment reference and a const Environment member-function which takes one argument.
template<typename Environment, typename FirstArgument, void( Environment::*member ) (FirstArgument)>
class MemberCaller1 : public BindFirstOpaque1< Member1<Environment, FirstArgument, void, member> >
{
public:
MemberCaller1( Environment& environment ) : BindFirstOpaque1< Member1<Environment, FirstArgument, void, member> >( environment ){
}
};
template<class Environment, class FirstArgument, void(Environment::*member)(FirstArgument)>
using MemberCaller1 = BindFirstOpaque<Member1<Environment, FirstArgument, void, member>>;
/// \brief Forms a Callback from a const Environment reference and a const Environment member-function which takes one argument.
template<typename Environment, typename FirstArgument, void( Environment::*member ) (FirstArgument) const>
class ConstMemberCaller1 : public BindFirstOpaque1< ConstMember1<Environment, FirstArgument, void, member> >
{
public:
ConstMemberCaller1( const Environment& environment ) : BindFirstOpaque1< ConstMember1<Environment, FirstArgument, void, member> >( environment ){
}
};
template<class Environment, class FirstArgument, void(Environment::*member)(FirstArgument) const>
using ConstMemberCaller1 = BindFirstOpaque<ConstMember1<Environment, FirstArgument, void, member>>;
/// \brief Forms a Callback from a non-const Environment reference and a free function which operates on a non-const Environment reference.
///
/// \dontinclude generic/callback.cpp
/// \skipline ReferenceCaller example
/// \until end example
template<typename Environment, void( *func ) (Environment&)>
class ReferenceCaller : public BindFirstOpaque< Function1<Environment&, void, func> >
{
public:
ReferenceCaller( Environment& environment ) : BindFirstOpaque< Function1<Environment&, void, func> >( environment ){
}
};
template<class Environment, void(*func)(Environment &)>
using ReferenceCaller = BindFirstOpaque<Function1<Environment &, void, func>>;
/// \brief Forms a Callback from a const Environment reference and a free function which operates on a const Environment reference.
///
/// \dontinclude generic/callback.cpp
/// \skipline ReferenceCaller example
/// \until end example
template<typename Environment, void( *func ) (const Environment&)>
class ConstReferenceCaller : public BindFirstOpaque< Function1<const Environment&, void, func> >
{
public:
ConstReferenceCaller( const Environment& environment ) : BindFirstOpaque< Function1<const Environment&, void, func> >( environment ){
}
};
template<class Environment, void(*func)(const Environment &)>
using ConstReferenceCaller = BindFirstOpaque<Function1<const Environment &, void, func>>;
/// \brief Forms a Callback from a non-const Environment reference and a free function which operates on a non-const Environment reference and one other argument.
template<typename Environment, typename FirstArgument, void( *func ) ( Environment&, FirstArgument )>
class ReferenceCaller1 : public BindFirstOpaque1< Function2<Environment&, FirstArgument, void, func> >
{
public:
ReferenceCaller1( Environment& environment ) : BindFirstOpaque1< Function2<Environment&, FirstArgument, void, func> >( environment ){
}
};
template<class Environment, class FirstArgument, void(*func)(Environment &, FirstArgument)>
using ReferenceCaller1 = BindFirstOpaque<Function2<Environment &, FirstArgument, void, func>>;
/// \brief Forms a Callback from a const Environment reference and a free function which operates on a const Environment reference and one other argument.
template<typename Environment, typename FirstArgument, void( *func ) ( const Environment&, FirstArgument )>
class ConstReferenceCaller1 : public BindFirstOpaque1< Function2<const Environment&, FirstArgument, void, func> >
{
public:
ConstReferenceCaller1( const Environment& environment ) : BindFirstOpaque1< Function2<const Environment&, FirstArgument, void, func> >( environment ){
}
};
template<class Environment, class FirstArgument, void(*func)(const Environment &, FirstArgument)>
using ConstReferenceCaller1 = BindFirstOpaque<Function2<const Environment &, FirstArgument, void, func>>;
/// \brief Forms a Callback from a non-const Environment pointer and a free function which operates on a non-const Environment pointer.
template<typename Environment, void( *func ) (Environment*)>
class PointerCaller : public BindFirstOpaque< Function1<Environment*, void, func> >
{
public:
PointerCaller( Environment* environment ) : BindFirstOpaque< Function1<Environment*, void, func> >( environment ){
}
};
template<class Environment, void(*func)(Environment *)>
using PointerCaller = BindFirstOpaque<Function1<Environment *, void, func>>;
/// \brief Forms a Callback from a const Environment pointer and a free function which operates on a const Environment pointer.
template<typename Environment, void( *func ) (const Environment*)>
class ConstPointerCaller : public BindFirstOpaque< Function1<const Environment*, void, func> >
{
public:
ConstPointerCaller( const Environment* environment ) : BindFirstOpaque< Function1<const Environment*, void, func> >( environment ){
}
};
template<class Environment, void(*func)(const Environment *)>
using ConstPointerCaller = BindFirstOpaque<Function1<const Environment *, void, func>>;
/// \brief Forms a Callback from a non-const Environment pointer and a free function which operates on a non-const Environment pointer and one other argument.
template<typename Environment, typename FirstArgument, void( *func ) ( Environment*, FirstArgument )>
class PointerCaller1 : public BindFirstOpaque1< Function2<Environment*, FirstArgument, void, func> >
{
public:
PointerCaller1( Environment* environment ) : BindFirstOpaque1< Function2<Environment*, FirstArgument, void, func> >( environment ){
}
};
template<class Environment, class FirstArgument, void(*func)(Environment *, FirstArgument)>
using PointerCaller1 = BindFirstOpaque<Function2<Environment *, FirstArgument, void, func>>;
/// \brief Forms a Callback from a const Environment pointer and a free function which operates on a const Environment pointer and one other argument.
template<typename Environment, typename FirstArgument, void( *func ) ( const Environment*, FirstArgument )>
class ConstPointerCaller1 : public BindFirstOpaque1< Function2<const Environment*, FirstArgument, void, func> >
{
public:
ConstPointerCaller1( const Environment* environment ) : BindFirstOpaque1< Function2<const Environment*, FirstArgument, void, func> >( environment ){
}
};
template<class Environment, class FirstArgument, void(*func)(const Environment *, FirstArgument)>
using ConstPointerCaller1 = BindFirstOpaque<Function2<const Environment *, FirstArgument, void, func>>;
/// \brief Forms a Callback from a free function which takes no arguments.
template<void( *func ) ( )>
class FreeCaller : public BindFirstOpaque< Caller0To1< Function0<void, func> > >
template<void(*func)()>
class FreeCaller : public BindFirstOpaque<Caller0To1<Function0<void, func>>>
{
public:
FreeCaller() : BindFirstOpaque< Caller0To1< Function0<void, func> > >( 0 ){
FreeCaller() : BindFirstOpaque<Caller0To1<Function0<void, func>>>( 0 ){
}
};
/// \brief Forms a Callback from a free function which takes a single argument.
template<typename FirstArgument, void( *func ) (FirstArgument)>
class FreeCaller1 : public BindFirstOpaque1< Caller1To2< Function1<FirstArgument, void, func> > >
template<class FirstArgument, void(*func)(FirstArgument)>
class FreeCaller1 : public BindFirstOpaque<Caller1To2<Function1<FirstArgument, void, func>>>
{
public:
FreeCaller1() : BindFirstOpaque1< Caller1To2< Function1<FirstArgument, void, func> > >( 0 ){
FreeCaller1() : BindFirstOpaque<Caller1To2<Function1<FirstArgument, void, func>>>( 0 ){
}
};
@@ -636,19 +426,19 @@ inline Callback makeCallback( const Functor& functor ){
/// \brief Constructs a Callback1 from a non-const \p functor with one argument.
///
/// \param Functor Must define \c first_argument_type and \c operator()(first_argument_type).
/// \param Functor Must define \c operator()(argument) and its signature as \c func.
template<typename Functor>
inline Callback1<typename Functor::first_argument_type> makeCallback1( Functor& functor ){
typedef typename Functor::first_argument_type FirstArgument;
inline Callback1<get_argument<Functor, 0>> makeCallback1( Functor& functor ){
typedef get_argument<Functor, 0> FirstArgument;
return Callback1<FirstArgument>( MemberCaller1<Functor, FirstArgument, &Functor::operator()>( functor ) );
}
/// \brief Constructs a Callback1 from a const \p functor with one argument.
///
/// \param Functor Must define \c first_argument_type and const \c operator()(first_argument_type).
/// \param Functor Must define const \c operator()(argument) and its signature as \c func.
template<typename Functor>
inline Callback1<typename Functor::first_argument_type> makeCallback1( const Functor& functor ){
typedef typename Functor::first_argument_type FirstArgument;
inline Callback1<get_argument<Functor, 0>> makeCallback1( const Functor& functor ){
typedef get_argument<Functor, 0> FirstArgument;
return Callback1<FirstArgument>( ConstMemberCaller1<Functor, FirstArgument, &Functor::operator()>( functor ) );
}
+193 -283
View File
@@ -1,315 +1,225 @@
#pragma once
template<typename Object, typename R, R( Object::*member ) ( )>
class Member
#include <tuple>
namespace detail {
template<class F>
struct Fn;
template<class R, class... Ts>
struct Fn<R(Ts...)>
{
using result_type = R;
template<int N>
using get = typename std::tuple_element<N, std::tuple<Ts...>>::type;
};
}
template<class Caller>
using get_result_type = typename detail::Fn<typename Caller::func>::result_type;
template<class Caller, int N>
using get_argument = typename detail::Fn<typename Caller::func>::template get<N>;
template<class Object, class F>
class MemberN;
template<class Object, class R, class... Ts>
class MemberN<Object, R(Ts...)>
{
public:
typedef Object& first_argument_type;
typedef R result_type;
static result_type call( first_argument_type object ){
return ( object.*member )();
template<R(Object::*f)(Ts...)>
class instance
{
public:
using func = R(Object &, Ts...);
static R call( Object& object, Ts... args ){
return ( object.*f )( args... );
}
};
};
template<class Object, class F>
class ConstMemberN;
template<class Object, class R, class... Ts>
class ConstMemberN<Object, R(Ts...)>
{
public:
template<R(Object::*f)(Ts...) const>
class instance
{
public:
using func = R(const Object &, Ts...);
static R call( const Object& object, Ts... args ){
return ( object.*f )( args... );
}
};
};
template<class F>
class FunctionN;
template<class R, class... Ts>
class FunctionN<R(Ts...)>
{
public:
template<R(*f)(Ts...)>
class instance
{
public:
using func = R(Ts...);
static R call( Ts... args ){
return ( f )( args... );
}
};
};
template<class Caller, class F>
class CallerShiftFirst;
template<class Caller, class R, class FirstArgument, class... Ts>
class CallerShiftFirst<Caller, R(FirstArgument, Ts...)>
{
public:
using func = R(FirstArgument, Ts...);
static R call( FirstArgument, Ts... args ){
return Caller::call( args... );
}
};
template<typename Object, typename R, R( Object::*member ) ( ) const>
class ConstMember
template<class Functor, class F>
class FunctorNInvoke;
namespace detail {
template<int ...>
struct seq
{
};
template<int N, int... S>
struct gens : gens<N - 1, N - 1, S...>
{
};
template<int... S>
struct gens<0, S...>
{
using type = seq<S...>;
};
template<int N>
using seq_new = typename gens<N>::type;
}
template<class Functor, class R, class... Ts>
class FunctorNInvoke<Functor, R(Ts...)>
{
std::tuple<Ts...> args;
template<class T>
struct caller;
template<int ...I>
struct caller<detail::seq<I...>>
{
static inline R call( FunctorNInvoke<Functor, R(Ts...)> *self, Functor functor ){
(void) self;
return functor( std::get<I>( self->args )... );
}
};
public:
typedef const Object& first_argument_type;
typedef R result_type;
static result_type call( first_argument_type object ){
return ( object.*member )();
FunctorNInvoke( Ts... args ) : args( args... ){
}
inline R operator()( Functor functor ) {
return caller<detail::seq_new<sizeof...(Ts)>>::call( this, functor );
}
};
template<typename Object, typename A1, typename R, R( Object::*member ) (A1)>
class Member1
{
public:
typedef Object& first_argument_type;
typedef A1 second_argument_type;
typedef R result_type;
static result_type call( first_argument_type object, second_argument_type a1 ){
return ( object.*member )( a1 );
}
};
template<class Functor>
using FunctorInvoke = FunctorNInvoke<Functor, typename Functor::func>;
template<typename Object, typename A1, typename R, R( Object::*member ) (A1) const>
class ConstMember1
{
public:
typedef const Object& first_argument_type;
typedef A1 second_argument_type;
typedef R result_type;
static result_type call( first_argument_type object, second_argument_type a1 ){
return ( object.*member )( a1 );
}
};
template<class Object, class R, R(Object::*member)()>
using Member = typename MemberN<Object, R()>::template instance<member>;
template<typename Object, typename A2, typename A3, typename R, R( Object::*member ) ( A2, A3 )>
class Member2
{
public:
typedef Object& first_argument_type;
typedef A2 second_argument_type;
typedef A3 third_argument_type;
typedef R result_type;
static result_type call( first_argument_type object, second_argument_type a2, third_argument_type a3 ){
return ( object.*member )( a2, a3 );
}
};
template<class Object, class R, R(Object::*member)() const>
using ConstMember = typename ConstMemberN<Object, R()>::template instance<member>;
template<typename Object, typename A2, typename A3, typename R, R( Object::*member ) ( A2, A3 ) const>
class ConstMember2
{
public:
typedef const Object& first_argument_type;
typedef A2 second_argument_type;
typedef A3 third_argument_type;
typedef R result_type;
static result_type call( first_argument_type object, second_argument_type a2, third_argument_type a3 ){
return ( object.*member )( a2, a3 );
}
};
template<class Object, class A1, class R, R(Object::*member)(A1)>
using Member1 = typename MemberN<Object, R(A1)>::template instance<member>;
template<typename Object, typename A2, typename A3, typename A4, typename R, R( Object::*member ) ( A2, A3, A4 )>
class Member3
{
public:
typedef Object& first_argument_type;
typedef A2 second_argument_type;
typedef A3 third_argument_type;
typedef A4 fourth_argument_type;
typedef R result_type;
static result_type call( first_argument_type object, second_argument_type a2, third_argument_type a3, fourth_argument_type a4 ){
return ( object.*member )( a2, a3, a4 );
}
};
template<class Object, class A1, class R, R(Object::*member)(A1) const>
using ConstMember1 = typename ConstMemberN<Object, R(A1)>::template instance<member>;
template<typename Object, typename A2, typename A3, typename A4, typename R, R( Object::*member ) ( A2, A3, A4 ) const>
class ConstMember3
{
public:
typedef const Object& first_argument_type;
typedef A2 second_argument_type;
typedef A3 third_argument_type;
typedef A4 fourth_argument_type;
typedef R result_type;
static result_type call( first_argument_type object, second_argument_type a2, third_argument_type a3, fourth_argument_type a4 ){
return ( object.*member )( a2, a3, a4 );
}
};
template<class Object, class A1, class A2, class R, R(Object::*member)(A1, A2)>
using Member2 = typename MemberN<Object, R(A1, A2)>::template instance<member>;
template<typename R, R( *func ) ( )>
class Function0
{
public:
typedef R result_type;
static result_type call(){
return (func)( );
}
};
template<class Object, class A1, class A2, class R, R(Object::*member)(A1, A2) const>
using ConstMember2 = typename ConstMemberN<Object, R(A1, A2)>::template instance<member>;
template<typename A1, typename R, R( *func ) (A1)>
class Function1
{
public:
typedef A1 first_argument_type;
typedef R result_type;
static result_type call( first_argument_type a1 ){
return (func)( a1 );
}
};
template<class Object, class A1, class A2, class A3, class R, R(Object::*member)(A1, A2, A3)>
using Member3 = typename MemberN<Object, R(A1, A2, A3)>::template instance<member>;
template<typename A1, typename A2, typename R, R( *func ) ( A1, A2 )>
class Function2
{
public:
typedef A1 first_argument_type;
typedef A2 second_argument_type;
typedef R result_type;
static result_type call( first_argument_type a1, second_argument_type a2 ){
return (func)( a1, a2 );
}
};
template<class Object, class A1, class A2, class A3, class R, R(Object::*member)(A1, A2, A3) const>
using ConstMember3 = typename ConstMemberN<Object, R(A1, A2, A3)>::template instance<member>;
template<typename A1, typename A2, typename A3, typename R, R( *func ) ( A1, A2, A3 )>
class Function3
{
public:
typedef A1 first_argument_type;
typedef A2 second_argument_type;
typedef A3 third_argument_type;
typedef R result_type;
static result_type call( first_argument_type a1, second_argument_type a2, third_argument_type a3 ){
return (func)( a1, a2, a3 );
}
};
template<class R, R(*func)()>
using Function0 = typename FunctionN<R()>::template instance<func>;
template<typename A1, typename A2, typename A3, typename A4, typename R, R( *func ) ( A1, A2, A3, A4 )>
class Function4
{
public:
typedef A1 first_argument_type;
typedef A2 second_argument_type;
typedef A3 third_argument_type;
typedef A4 fourth_argument_type;
typedef R result_type;
static result_type call( first_argument_type a1, second_argument_type a2, third_argument_type a3, fourth_argument_type a4 ){
return (func)( a1, a2, a3, a4 );
}
};
template<class A1, class R, R(*func)(A1)>
using Function1 = typename FunctionN<R(A1)>::template instance<func>;
template<typename A1, typename A2, typename A3, typename A4, typename A5, typename R, R( *func ) ( A1, A2, A3, A4, A5 )>
class Function5
{
public:
typedef A1 first_argument_type;
typedef A2 second_argument_type;
typedef A3 third_argument_type;
typedef A4 fourth_argument_type;
typedef A5 fifth_argument_type;
typedef R result_type;
static result_type call( first_argument_type a1, second_argument_type a2, third_argument_type a3, fourth_argument_type a4, fifth_argument_type a5 ){
return (func)( a1, a2, a3, a4, a5 );
}
};
template<class A1, class A2, class R, R(*func)(A1, A2)>
using Function2 = typename FunctionN<R(A1, A2)>::template instance<func>;
template<typename Caller, typename FirstArgument = void*>
class Caller0To1
{
public:
typedef FirstArgument first_argument_type;
typedef typename Caller::result_type result_type;
static result_type call( first_argument_type ){
return Caller::call();
}
};
template<class A1, class A2, class A3, class R, R(*func)(A1, A2, A3)>
using Function3 = typename FunctionN<R(A1, A2, A3)>::template instance<func>;
template<typename Caller, typename FirstArgument = void*>
class Caller1To2
{
public:
typedef FirstArgument first_argument_type;
typedef typename Caller::first_argument_type second_argument_type;
typedef typename Caller::result_type result_type;
static result_type call( first_argument_type, second_argument_type a2 ){
return Caller::call( a2 );
}
};
template<class A1, class A2, class A3, class A4, class R, R(*func)(A1, A2, A3, A4)>
using Function4 = typename FunctionN<R(A1, A2, A3, A4)>::template instance<func>;
template<typename Caller, typename FirstArgument = void*>
class Caller2To3
{
public:
typedef FirstArgument first_argument_type;
typedef typename Caller::first_argument_type second_argument_type;
typedef typename Caller::second_argument_type third_argument_type;
typedef typename Caller::result_type result_type;
static result_type call( first_argument_type, second_argument_type a2, third_argument_type a3 ){
return Caller::call( a2, a3 );
}
};
template<class A1, class A2, class A3, class A4, class A5, class R, R(*func)(A1, A2, A3, A4, A5)>
using Function5 = typename FunctionN<R(A1, A2, A3, A4, A5)>::template instance<func>;
template<typename Caller, typename FirstArgument = void*>
class Caller3To4
{
public:
typedef FirstArgument first_argument_type;
typedef typename Caller::first_argument_type second_argument_type;
typedef typename Caller::second_argument_type third_argument_type;
typedef typename Caller::third_argument_type fourth_argument_type;
typedef typename Caller::result_type result_type;
static result_type call( first_argument_type, second_argument_type a2, third_argument_type a3, fourth_argument_type a4 ){
return Caller::call( a2, a3, a4 );
}
};
template<class Caller, class FirstArgument = void *>
using Caller0To1 = CallerShiftFirst<Caller, get_result_type<Caller>(
FirstArgument
)>;
template<typename Caller, typename FirstArgument = void*>
class Caller4To5
{
public:
typedef FirstArgument first_argument_type;
typedef typename Caller::first_argument_type second_argument_type;
typedef typename Caller::second_argument_type third_argument_type;
typedef typename Caller::third_argument_type fourth_argument_type;
typedef typename Caller::fourth_argument_type fifth_argument_type;
typedef typename Caller::result_type result_type;
static result_type call( first_argument_type, second_argument_type a2, third_argument_type a3, fourth_argument_type a4, fifth_argument_type a5 ){
return Caller::call( a2, a3, a4, a5 );
}
};
template<class Caller, class FirstArgument = void *>
using Caller1To2 = CallerShiftFirst<Caller, get_result_type<Caller>(
FirstArgument,
get_argument<Caller, 0>
)>;
template<typename Functor>
class FunctorInvoke
{
public:
typedef typename Functor::result_type result_type;
inline result_type operator()( Functor functor ){
return functor();
}
};
template<class Caller, class FirstArgument = void *>
using Caller2To3 = CallerShiftFirst<Caller, get_result_type<Caller>(
FirstArgument,
get_argument<Caller, 0>,
get_argument<Caller, 1>
)>;
template<typename Functor>
class Functor1Invoke
{
typename Functor::first_argument_type a1;
public:
typedef typename Functor::first_argument_type first_argument_type;
typedef typename Functor::result_type result_type;
Functor1Invoke( first_argument_type a1 ) : a1( a1 ){
}
inline result_type operator()( Functor functor ){
return functor( a1 );
}
};
template<class Caller, class FirstArgument = void *>
using Caller3To4 = CallerShiftFirst<Caller, get_result_type<Caller>(
FirstArgument,
get_argument<Caller, 0>,
get_argument<Caller, 1>,
get_argument<Caller, 2>
)>;
template<typename Functor>
class Functor2Invoke
{
typename Functor::first_argument_type a1;
typename Functor::second_argument_type a2;
public:
typedef typename Functor::first_argument_type first_argument_type;
typedef typename Functor::second_argument_type second_argument_type;
typedef typename Functor::result_type result_type;
Functor2Invoke( first_argument_type a1, second_argument_type a2 )
: a1( a1 ), a2( a2 ){
}
inline result_type operator()( Functor functor ){
return functor( a1, a2 );
}
};
template<typename Functor>
class Functor3Invoke
{
typename Functor::first_argument_type a1;
typename Functor::second_argument_type a2;
typename Functor::third_argument_type a3;
public:
typedef typename Functor::first_argument_type first_argument_type;
typedef typename Functor::second_argument_type second_argument_type;
typedef typename Functor::third_argument_type third_argument_type;
typedef typename Functor::result_type result_type;
Functor3Invoke( first_argument_type a1, second_argument_type a2, third_argument_type a3 )
: a1( a1 ), a2( a2 ), a3( a3 ){
}
inline result_type operator()( Functor functor ){
return functor( a1, a2, a3 );
}
};
template<typename Other, typename True, typename False, typename Type>
class TypeEqual
{
public:
typedef False type;
};
template<typename Other, typename True, typename False>
class TypeEqual<Other, True, False, Other>
{
public:
typedef True type;
};
template<class Caller, class FirstArgument = void *>
using Caller4To5 = CallerShiftFirst<Caller, get_result_type<Caller>(
FirstArgument,
get_argument<Caller, 0>,
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>
)>;
+82 -115
View File
@@ -21,182 +21,149 @@ public:
const SignalHandlerResult SIGNAL_CONTINUE_EMISSION = SignalHandlerResult( false );
const SignalHandlerResult SIGNAL_STOP_EMISSION = SignalHandlerResult( true );
template<typename Caller>
class SignalHandlerCaller1
template<class Caller, class F>
class SignalHandlerCallerN;
template<class Caller, class R, class... Ts>
class SignalHandlerCallerN<Caller, R(Ts...)>
{
public:
typedef typename Caller::first_argument_type first_argument_type;
typedef SignalHandlerResult result_type;
static result_type call( first_argument_type a1 ){
Caller::call( a1 );
using func = SignalHandlerResult(Ts...);
static SignalHandlerResult call( Ts... args ) {
Caller::call( args... );
return SIGNAL_CONTINUE_EMISSION;
}
};
template<typename Caller>
class SignalHandlerCaller2
{
public:
typedef typename Caller::first_argument_type first_argument_type;
typedef typename Caller::second_argument_type second_argument_type;
typedef SignalHandlerResult result_type;
static result_type call( first_argument_type a1, second_argument_type a2 ){
Caller::call( a1, a2 );
return SIGNAL_CONTINUE_EMISSION;
}
};
template<class Caller>
using SignalHandlerCaller = SignalHandlerCallerN<Caller, typename Caller::func>;
template<class Caller>
using SignalHandlerCaller1 = SignalHandlerCaller<Caller>;
template<class Caller>
using SignalHandlerCaller2 = SignalHandlerCaller<Caller>;
template<typename Caller>
class SignalHandlerCaller3
{
public:
typedef typename Caller::first_argument_type first_argument_type;
typedef typename Caller::second_argument_type second_argument_type;
typedef typename Caller::third_argument_type third_argument_type;
typedef SignalHandlerResult result_type;
static result_type call( first_argument_type a1, second_argument_type a2, third_argument_type a3 ){
Caller::call( a1, a2, a3 );
return SIGNAL_CONTINUE_EMISSION;
}
};
using SignalHandlerCaller3 = SignalHandlerCaller<Caller>;
template<typename Caller>
class SignalHandlerCaller4
using SignalHandlerCaller4 = SignalHandlerCaller<Caller>;
template<typename Other, typename True, typename False, typename Type>
class TypeEqual
{
public:
typedef typename Caller::first_argument_type first_argument_type;
typedef typename Caller::second_argument_type second_argument_type;
typedef typename Caller::third_argument_type third_argument_type;
typedef typename Caller::fourth_argument_type fourth_argument_type;
typedef SignalHandlerResult result_type;
static result_type call( first_argument_type a1, second_argument_type a2, third_argument_type a3, fourth_argument_type a4 ){
Caller::call( a1, a2, a3, a4 );
return SIGNAL_CONTINUE_EMISSION;
}
using type = False;
};
class SignalHandler : public Callback0<SignalHandlerResult>
template<typename Other, typename True, typename False>
class TypeEqual<Other, True, False, Other>
{
public:
using type = True;
};
template<class CB, template<class T> class Wrapper>
class SignalHandlerN : public CB
{
public:
template<typename Caller>
SignalHandler( const BindFirstOpaque<Caller>& caller )
: Callback0<SignalHandlerResult>( BindFirstOpaque<typename TypeEqual<
SignalHandlerResult,
Caller,
SignalHandlerCaller1<Caller>,
typename Caller::result_type
>::type>( caller.getBound() ) ){
SignalHandlerN( const BindFirstOpaque<Caller>& caller )
: CB( BindFirstOpaque<typename TypeEqual<
SignalHandlerResult,
Caller,
Wrapper<Caller>,
get_result_type<Caller>
>::type>( caller.getBound() ) ){
}
};
class SignalHandler : public SignalHandlerN<Callback0<SignalHandlerResult>, SignalHandlerCaller1>
{
using SignalHandlerN<Callback0<SignalHandlerResult>, SignalHandlerCaller1>::SignalHandlerN;
};
template<typename Caller>
inline SignalHandler makeSignalHandler( const BindFirstOpaque<Caller>& caller ){
return SignalHandler( caller );
}
template<typename Caller>
inline SignalHandler makeSignalHandler( const Caller& caller, typename Caller::first_argument_type callee ){
inline SignalHandler makeSignalHandler( const Caller& caller, get_argument<Caller, 0> callee ){
return SignalHandler( BindFirstOpaque<Caller>( callee ) );
}
template<typename FirstArgument>
class SignalHandler1 : public Callback1<FirstArgument, SignalHandlerResult>
class SignalHandler1 : public SignalHandlerN<Callback1<FirstArgument, SignalHandlerResult>, SignalHandlerCaller2>
{
public:
template<typename Caller>
SignalHandler1( const BindFirstOpaque1<Caller>& caller )
: Callback1<FirstArgument, SignalHandlerResult>( BindFirstOpaque1<typename TypeEqual<
SignalHandlerResult,
Caller,
SignalHandlerCaller2<Caller>,
typename Caller::result_type
>::type>( caller.getBound() ) ){
}
using SignalHandlerN<Callback1<FirstArgument, SignalHandlerResult>, SignalHandlerCaller2>::SignalHandlerN;
};
template<typename Caller>
inline SignalHandler1<typename Caller::second_argument_type> makeSignalHandler1( const BindFirstOpaque1<Caller>& caller ){
return SignalHandler1<typename Caller::second_argument_type>( caller );
inline SignalHandler1<get_argument<Caller, 1>> makeSignalHandler1(const BindFirstOpaque<Caller>& caller){
return SignalHandler1<get_argument<Caller, 1>>( caller );
}
template<typename Caller>
inline SignalHandler1<typename Caller::second_argument_type> makeSignalHandler1( const Caller& caller, typename Caller::first_argument_type callee ){
return SignalHandler1<typename Caller::second_argument_type>( BindFirstOpaque1<Caller>( callee ) );
inline SignalHandler1<get_argument<Caller, 1>>
makeSignalHandler1(const Caller &caller, get_argument<Caller, 0> callee) {
return SignalHandler1<get_argument<Caller, 1>>(BindFirstOpaque<Caller>(callee));
}
template<typename FirstArgument, typename SecondArgument>
class SignalHandler2 : public Callback2<FirstArgument, SecondArgument, SignalHandlerResult>
class SignalHandler2 : public SignalHandlerN<Callback2<FirstArgument, SecondArgument, SignalHandlerResult>, SignalHandlerCaller3>
{
public:
template<typename Caller>
SignalHandler2( const BindFirstOpaque2<Caller>& caller )
: Callback2<FirstArgument, SecondArgument, SignalHandlerResult>( BindFirstOpaque2<typename TypeEqual<
SignalHandlerResult,
Caller,
SignalHandlerCaller3<Caller>,
typename Caller::result_type
>::type>( caller.getBound() ) ){
}
using SignalHandlerN<Callback2<FirstArgument, SecondArgument, SignalHandlerResult>, SignalHandlerCaller3>::SignalHandlerN;
};
template<typename Caller>
inline SignalHandler2<
typename Caller::second_argument_type,
typename Caller::third_argument_type
> makeSignalHandler2( const BindFirstOpaque2<Caller>& caller ){
get_argument<Caller, 1>,
get_argument<Caller, 2>
> makeSignalHandler2( const BindFirstOpaque<Caller>& caller ){
return SignalHandler2<
typename Caller::second_argument_type,
typename Caller::third_argument_type
get_argument<Caller, 1>,
get_argument<Caller, 2>
>( caller );
}
template<typename Caller>
inline SignalHandler2<
typename Caller::second_argument_type,
typename Caller::third_argument_type
> makeSignalHandler2( const Caller& caller, typename Caller::first_argument_type callee ){
get_argument<Caller, 1>,
get_argument<Caller, 2>
> makeSignalHandler2( const Caller& caller, get_argument<Caller, 0> callee ){
return SignalHandler2<
typename Caller::second_argument_type,
typename Caller::third_argument_type
>( BindFirstOpaque2<Caller>( callee ) );
get_argument<Caller, 1>,
get_argument<Caller, 2>
>( BindFirstOpaque<Caller>( callee ) );
}
template<typename FirstArgument, typename SecondArgument, typename ThirdArgument>
class SignalHandler3 : public Callback3<FirstArgument, SecondArgument, ThirdArgument, SignalHandlerResult>
class SignalHandler3 : public SignalHandlerN<Callback3<FirstArgument, SecondArgument, ThirdArgument, SignalHandlerResult>, SignalHandlerCaller4>
{
public:
template<typename Caller>
SignalHandler3( const BindFirstOpaque3<Caller>& caller )
: Callback3<FirstArgument, SecondArgument, ThirdArgument, SignalHandlerResult>( BindFirstOpaque3<typename TypeEqual<
SignalHandlerResult,
Caller,
SignalHandlerCaller4<Caller>,
typename Caller::result_type
>::type>( caller.getBound() ) ){
}
using SignalHandlerN<Callback3<FirstArgument, SecondArgument, ThirdArgument, SignalHandlerResult>, SignalHandlerCaller4>::SignalHandlerN;
};
template<typename Caller>
inline SignalHandler3<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type
> makeSignalHandler3( const BindFirstOpaque3<Caller>& caller ){
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>
> makeSignalHandler3( const BindFirstOpaque<Caller>& caller ){
return SignalHandler3<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>
>( caller );
}
template<typename Caller>
inline SignalHandler3<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type
> makeSignalHandler3( const Caller& caller, typename Caller::first_argument_type callee ){
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>
> makeSignalHandler3( const Caller& caller, get_argument<Caller, 0> callee ){
return SignalHandler3<
typename Caller::second_argument_type,
typename Caller::third_argument_type,
typename Caller::fourth_argument_type
>( BindFirstOpaque3<Caller>( callee ) );
get_argument<Caller, 1>,
get_argument<Caller, 2>,
get_argument<Caller, 3>
>( BindFirstOpaque<Caller>( callee ) );
}
+3 -3
View File
@@ -314,7 +314,7 @@ class Signal1 : public SignalBase< SignalHandler1<FirstArgument> >
typedef SignalBase< SignalHandler1<FirstArgument> > Base;
public:
void operator()( FirstArgument a1 ) const {
invokeSignalHandlers( Base::begin(), Base::end(), Functor1Invoke<typename Base::handler_type>( a1 ) );
invokeSignalHandlers( Base::begin(), Base::end(), FunctorInvoke<typename Base::handler_type>( a1 ) );
}
};
@@ -324,7 +324,7 @@ class Signal2 : public SignalBase< SignalHandler2<FirstArgument, SecondArgument>
typedef SignalBase< SignalHandler2<FirstArgument, SecondArgument> > Base;
public:
void operator()( FirstArgument a1, SecondArgument a2 ) const {
invokeSignalHandlers( Base::begin(), Base::end(), Functor2Invoke<typename Base::handler_type>( a1, a2 ) );
invokeSignalHandlers( Base::begin(), Base::end(), FunctorInvoke<typename Base::handler_type>( a1, a2 ) );
}
};
@@ -334,6 +334,6 @@ class Signal3 : public SignalBase< SignalHandler3<FirstArgument, SecondArgument,
typedef SignalBase< SignalHandler3<FirstArgument, SecondArgument, ThirdArgument> > Base;
public:
void operator()( FirstArgument a1, SecondArgument a2, ThirdArgument a3 ) const {
invokeSignalHandlers( Base::begin(), Base::end(), Functor3Invoke<typename Base::handler_type>( a1, a2, a3 ) );
invokeSignalHandlers( Base::begin(), Base::end(), FunctorInvoke<typename Base::handler_type>( a1, a2, a3 ) );
}
};
+8 -8
View File
@@ -398,12 +398,12 @@ typedef ConstReferenceCaller1<StringImportCallback, CopiedString, CopiedString_t
template<typename Caller>
inline StringImportCallback makeCopiedStringStringImportCallback( const Caller& caller ){
return StringImportCallback( caller.getEnvironment(), ImportConvert1<StringImportCallback::first_argument_type, Caller, CopiedStringFromString>::thunk );
return StringImportCallback( caller.getEnvironment(), ImportConvert1<get_argument<StringImportCallback, 0>, Caller, CopiedStringFromString>::thunk );
}
template<typename Caller>
inline StringExportCallback makeCopiedStringStringExportCallback( const Caller& caller ){
return StringExportCallback( caller.getEnvironment(), ImportConvert1<StringExportCallback::first_argument_type, Caller, CopiedStringToString>::thunk );
return StringExportCallback( caller.getEnvironment(), ImportConvert1<get_argument<StringExportCallback, 0>, Caller, CopiedStringToString>::thunk );
}
@@ -428,12 +428,12 @@ typedef ConstReferenceCaller1<StringImportCallback, bool, Bool_toString> BoolToS
template<typename Caller>
inline StringImportCallback makeBoolStringImportCallback( const Caller& caller ){
return StringImportCallback( caller.getEnvironment(), ImportConvert1<StringImportCallback::first_argument_type, Caller, BoolFromString>::thunk );
return StringImportCallback( caller.getEnvironment(), ImportConvert1<get_argument<StringImportCallback, 0>, Caller, BoolFromString>::thunk );
}
template<typename Caller>
inline StringExportCallback makeBoolStringExportCallback( const Caller& caller ){
return StringExportCallback( caller.getEnvironment(), ImportConvert1<StringExportCallback::first_argument_type, Caller, BoolToString>::thunk );
return StringExportCallback( caller.getEnvironment(), ImportConvert1<get_argument<StringExportCallback, 0>, Caller, BoolToString>::thunk );
}
@@ -458,12 +458,12 @@ typedef ConstReferenceCaller1<StringImportCallback, int, Int_toString> IntToStri
template<typename Caller>
inline StringImportCallback makeIntStringImportCallback( const Caller& caller ){
return StringImportCallback( caller.getEnvironment(), ImportConvert1<StringImportCallback::first_argument_type, Caller, IntFromString>::thunk );
return StringImportCallback( caller.getEnvironment(), ImportConvert1<get_argument<StringImportCallback, 0>, Caller, IntFromString>::thunk );
}
template<typename Caller>
inline StringExportCallback makeIntStringExportCallback( const Caller& caller ){
return StringExportCallback( caller.getEnvironment(), ImportConvert1<StringExportCallback::first_argument_type, Caller, IntToString>::thunk );
return StringExportCallback( caller.getEnvironment(), ImportConvert1<get_argument<StringExportCallback, 0>, Caller, IntToString>::thunk );
}
@@ -489,10 +489,10 @@ typedef ConstReferenceCaller1<StringImportCallback, std::size_t, Size_toString>
template<typename Caller>
inline StringImportCallback makeSizeStringImportCallback( const Caller& caller ){
return StringImportCallback( caller.getEnvironment(), ImportConvert1<StringImportCallback::first_argument_type, Caller, SizeFromString>::thunk );
return StringImportCallback( caller.getEnvironment(), ImportConvert1<get_argument<StringImportCallback, 0>, Caller, SizeFromString>::thunk );
}
template<typename Caller>
inline StringExportCallback makeSizeStringExportCallback( const Caller& caller ){
return StringExportCallback( caller.getEnvironment(), ImportConvert1<StringExportCallback::first_argument_type, Caller, SizeToString>::thunk );
return StringExportCallback( caller.getEnvironment(), ImportConvert1<get_argument<StringExportCallback, 0>, Caller, SizeToString>::thunk );
}
+6 -12
View File
@@ -473,11 +473,9 @@ class Dereference
{
const Functor& functor;
public:
typedef typename RemoveReference<typename Functor::first_argument_type>::type* first_argument_type;
typedef typename Functor::result_type result_type;
Dereference( const Functor& functor ) : functor( functor ){
}
result_type operator()( first_argument_type firstArgument ) const {
get_result_type<Functor> operator()( typename RemoveReference<get_argument<Functor, 0>>::type *firstArgument ) const {
return functor( *firstArgument );
}
};
@@ -499,15 +497,13 @@ Face* Brush_findIf( const Brush& brush, const Predicate& predicate ){
template<typename Caller>
class BindArguments1
{
typedef typename Caller::second_argument_type FirstBound;
typedef get_argument<Caller, 1> FirstBound;
FirstBound firstBound;
public:
typedef typename Caller::result_type result_type;
typedef typename Caller::first_argument_type first_argument_type;
BindArguments1( FirstBound firstBound )
: firstBound( firstBound ){
}
result_type operator()( first_argument_type firstArgument ) const {
get_result_type<Caller> operator()( get_argument<Caller, 0> firstArgument ) const {
return Caller::call( firstArgument, firstBound );
}
};
@@ -515,17 +511,15 @@ public:
template<typename Caller>
class BindArguments2
{
typedef typename Caller::second_argument_type FirstBound;
typedef typename Caller::third_argument_type SecondBound;
typedef get_argument<Caller, 1> FirstBound;
typedef get_argument<Caller, 2> SecondBound;
FirstBound firstBound;
SecondBound secondBound;
public:
typedef typename Caller::result_type result_type;
typedef typename Caller::first_argument_type first_argument_type;
BindArguments2( FirstBound firstBound, SecondBound secondBound )
: firstBound( firstBound ), secondBound( secondBound ){
}
result_type operator()( first_argument_type firstArgument ) const {
get_result_type<Caller> operator()( get_argument<Caller, 0> firstArgument ) const {
return Caller::call( firstArgument, firstBound, secondBound );
}
};
+1 -3
View File
@@ -23,13 +23,11 @@
#include <list>
#include "generic/callback.h"
#include "gtkutil/dialog.h"
#include "generic/callback.h"
#include "string/string.h"
template<typename Environment, typename FirstArgument, void( *func ) ( Environment&, FirstArgument )>
class ReferenceCaller1;
inline void BoolImport( bool& self, bool value ){
self = value;
}
+2 -2
View File
@@ -585,7 +585,7 @@ class OpenGLStateBucketAdd
const OpenGLRenderable& m_renderable;
const Matrix4& m_modelview;
public:
typedef const RendererLight& first_argument_type;
using func = void(const RendererLight&);
OpenGLStateBucketAdd( OpenGLStateBucket& bucket, const OpenGLRenderable& renderable, const Matrix4& modelview ) :
m_bucket( bucket ), m_renderable( renderable ), m_modelview( modelview ){
@@ -599,7 +599,7 @@ class CountLights
{
std::size_t m_count;
public:
typedef const RendererLight& first_argument_type;
using func = void(RendererLight&);
CountLights() : m_count( 0 ){
}
+1 -1
View File
@@ -3438,7 +3438,7 @@ class ResizeTranslatable : public Translatable
class SelectionCounter
{
public:
typedef const Selectable& first_argument_type;
using func = void(const Selectable &);
SelectionCounter( const SelectionChangeCallback& onchanged )
: m_count( 0 ), m_onchanged( onchanged ){
+1 -1
View File
@@ -656,7 +656,7 @@ class TextureCategoryLoadShader
const char* m_directory;
std::size_t& m_count;
public:
typedef const char* first_argument_type;
using func = void(const char *);
TextureCategoryLoadShader( const char* directory, std::size_t& count )
: m_directory( directory ), m_count( count ){