felipealmeida pushed a commit to branch master. http://git.enlightenment.org/core/efl.git/commit/?id=96d3af10bf199c4a8f563503a663a0890fa1ec84
commit 96d3af10bf199c4a8f563503a663a0890fa1ec84 Author: Felipe Magno de Almeida <fel...@expertisesolutions.com.br> Date: Thu Sep 28 17:48:04 2017 -0300 eolian-cxx: Add optional parameter to lambda for unnamed proxy instantiation --- src/bindings/cxx/eo_cxx/eo_cxx_interop.hh | 34 ++++++++++++++++++++----- src/lib/eolian_cxx/grammar/class_definition.hpp | 8 +++--- src/tests/eolian_cxx/eolian_cxx_test_binding.cc | 6 ++++- 3 files changed, 36 insertions(+), 12 deletions(-) diff --git a/src/bindings/cxx/eo_cxx/eo_cxx_interop.hh b/src/bindings/cxx/eo_cxx/eo_cxx_interop.hh index 2f9b6382b3..d77bcf21e0 100644 --- a/src/bindings/cxx/eo_cxx/eo_cxx_interop.hh +++ b/src/bindings/cxx/eo_cxx/eo_cxx_interop.hh @@ -830,10 +830,12 @@ T convert_to_return(U& object) } /// Miscellaneous -template <typename T, typename Enable = void> -struct is_callable : std::false_type {}; -template <typename T> -struct is_callable<T, decltype(std::declval<T>() ())> : std::true_type {}; +template <typename T, typename U, typename Enable = void> +struct is_constructor_lambda : std::false_type {}; +template <typename T, typename U> +struct is_constructor_lambda<T, U, decltype(std::declval<T>() ())> : std::true_type {}; +template <typename T, typename U> +struct is_constructor_lambda<T, U, decltype(std::declval<T>() (std::declval<U>()))> : std::true_type {}; template <typename P> inline void do_eo_add(Eo*& object, P const& parent @@ -843,12 +845,30 @@ inline void do_eo_add(Eo*& object, P const& parent object = ::_efl_add_internal_start(__FILE__, __LINE__, klass, parent._eo_ptr(), EINA_TRUE, EINA_FALSE); object = ::_efl_add_end(object, EINA_FALSE, EINA_FALSE); } -template <typename P, typename F> -void do_eo_add(Eo*& object, P const& parent, Efl_Class const* klass, F f + +template <typename T> +struct void_t { typedef void type; }; + +template <typename F, typename U> +auto call_lambda(F&& f, U&) -> typename void_t<decltype(f())>::type +{ + f(); +} + +template <typename F, typename U> +auto call_lambda(F&& f, U& object) -> typename void_t<decltype(f(object))>::type +{ + f(object); +} + +template <typename P, typename F, typename U> +void do_eo_add(Eo*& object, P const& parent, Efl_Class const* klass + , U& proxy + , F&& f , typename std::enable_if< eo::is_eolian_object<P>::value>::type* = 0) { object = ::_efl_add_internal_start(__FILE__, __LINE__, klass, parent._eo_ptr(), EINA_TRUE, EINA_FALSE); - f(); + ::efl::eolian::call_lambda(std::forward<F>(f), proxy); object = ::_efl_add_end(object, EINA_FALSE, EINA_FALSE); } diff --git a/src/lib/eolian_cxx/grammar/class_definition.hpp b/src/lib/eolian_cxx/grammar/class_definition.hpp index 71808a3a48..326ef23578 100644 --- a/src/lib/eolian_cxx/grammar/class_definition.hpp +++ b/src/lib/eolian_cxx/grammar/class_definition.hpp @@ -69,13 +69,13 @@ struct class_definition_generator << scope_tab << "{\n" << scope_tab << scope_tab << "::efl::eolian::do_eo_add( ::efl::eo::concrete::_eo_raw, parent, _eo_class());\n" << scope_tab << "}\n" - << scope_tab << "template <typename F> " << string << "( ::efl::eo::instantiate_t, F f, typename ::std::enable_if< ::efl::eolian::is_callable<F>::value>::type* = 0)\n" + << scope_tab << "template <typename F> " << string << "( ::efl::eo::instantiate_t, F&& f, typename ::std::enable_if< ::efl::eolian::is_constructor_lambda<F, " << string << " >::value>::type* = 0)\n" << scope_tab << "{\n" - << scope_tab << scope_tab << "::efl::eolian::do_eo_add( ::efl::eo::concrete::_eo_raw, ::efl::eo::concrete{nullptr}, _eo_class(), f);\n" + << scope_tab << scope_tab << "::efl::eolian::do_eo_add( ::efl::eo::concrete::_eo_raw, ::efl::eo::concrete{nullptr}, _eo_class(), *this, std::forward<F>(f));\n" << scope_tab << "}\n" - << scope_tab << "template <typename T, typename F> " << string << "( ::efl::eo::instantiate_t, T&& parent, F f, typename ::std::enable_if< ::efl::eolian::is_callable<F>::value && ::efl::eo::is_eolian_object<T>::value>::type* = 0)\n" + << scope_tab << "template <typename T, typename F> " << string << "( ::efl::eo::instantiate_t, T&& parent, F&& f, typename ::std::enable_if< ::efl::eolian::is_constructor_lambda<F, " << string << " >::value && ::efl::eo::is_eolian_object<T>::value>::type* = 0)\n" << scope_tab << "{\n" - << scope_tab << scope_tab << "::efl::eolian::do_eo_add( ::efl::eo::concrete::_eo_raw, parent, _eo_class(), f);\n" + << scope_tab << scope_tab << "::efl::eolian::do_eo_add( ::efl::eo::concrete::_eo_raw, parent, _eo_class(), *this, std::forward<F>(f));\n" << scope_tab << "}\n" // << scope_tab << "explicit " << string << "( ::efl::eo::concrete const& parent)\n" // << scope_tab << scope_tab << ": ::efl::eo::concrete( ::efl::eo::do_eo_add(parent)) {}\n" diff --git a/src/tests/eolian_cxx/eolian_cxx_test_binding.cc b/src/tests/eolian_cxx/eolian_cxx_test_binding.cc index 90f880e319..ead856268d 100644 --- a/src/tests/eolian_cxx/eolian_cxx_test_binding.cc +++ b/src/tests/eolian_cxx/eolian_cxx_test_binding.cc @@ -66,7 +66,11 @@ START_TEST(eolian_cxx_test_type_generation) { efl::eo::eo_init eo_init; - name1::name2::Type_Generation g(efl::eo::instantiate); + name1::name2::Type_Generation g1(efl::eo::instantiate); + name1::name2::Type_Generation g2(efl::eo::instantiate + , [] {}); + name1::name2::Type_Generation g3(efl::eo::instantiate + , [] (name1::name2::Type_Generation) {}); } END_TEST --