On Thu, 2013-08-08 at 16:40 +0200, Kjell Ahlstedt wrote:

> Templated get_*() methods can be added as overloaded methods, because
> the number of parameters will be different. Example:
> 
>         _WRAP_METHOD(Glib::VariantBase get_action_state(const
>         Glib::ustring& action_name) const,
>         g_action_group_get_action_state)
>         
>         template <typename T_Value>
>         void get_action_state(const Glib::ustring& action_name,
>         T_Value& value) const;
> It's also possible to deprecate the old get_action_state() and add a
> new get_action_state_variant(), identical except for its name.

Yes, thanks for the suggestion. I've done that.

> I'm not sure whether it's possible to overload other methods, e.g.
> 
>          _WRAP_METHOD(void change_action_state(const Glib::ustring&
>         action_name, const Glib::VariantBase& value),
>         g_action_group_change_action_state)
>         
>           template <typename T_Value>
>           void change_action_state(const Glib::ustring& action_name,
>         const T_Value& value);
> 
> Overload resolution prefers a non-template method to a template
> method, but perhaps that's true only when the parameter types exactly
> match those of the non-template method. The last parameter in a
> typical call would not be a Glib::VariantBase& but a
> Glib::Variant<T>&.

I tried. But you are right, the compiler calls the templated
change_state<>() with the Variant<>, trying to call
change_state_variant() with a Variant<Variant<int>>, for instance. At
least that would be an API change instead of an ABI change,
because existing already-compiled applications would be unaffected, but
it would be a hard one to detect.

So, in Action, I added
  template<typename T_Value>
  void change_state(const Glib::Variant<T_Value>& value)
to give the compiler something to call.
https://git.gnome.org/browse/glibmm/commit/?id=8acf6182ee6e54040cec1a049704c7563f67475a

Hopefully there's no case where someone would really want to call
change_state() with a Variant.

It seems to work. Does it seem OK to you? If so, I'll do it for similar
API.

-- 
Murray Cumming
murr...@murrayc.com
www.murrayc.com
www.openismus.com
diff --git a/gio/src/action.ccg b/gio/src/action.ccg
index 78cad2d..d3dd74a 100644
--- a/gio/src/action.ccg
+++ b/gio/src/action.ccg
@@ -24,11 +24,4 @@
 namespace Gio
 {
 
-void Action::change_state(bool value)
-{
-  g_return_if_fail(
-    g_variant_type_equal(g_action_get_state_type(const_cast<GAction*>(gobj())), G_VARIANT_TYPE_BOOLEAN));
-  change_state(Glib::Variant<bool>::create(value));
-}
-
 } // namespace Gio
diff --git a/gio/src/action.hg b/gio/src/action.hg
index 316631d..2b6db6d 100644
--- a/gio/src/action.hg
+++ b/gio/src/action.hg
@@ -92,27 +92,24 @@ public:
 
   _WRAP_METHOD(bool get_enabled() const, g_action_get_enabled)
 
-  //TODO: Do this when we can break ABI, removing change_state(const Glib::VariantBase& value) and change_state(bool)
-  //template <typename T_Value>
-  //void change_state(const T_Value& value);
-  //
-  //_WRAP_METHOD(void change_state_variant(const Glib::VariantBase& value), g_action_change_state)
-
-  _WRAP_METHOD(void change_state(const Glib::VariantBase& value), g_action_change_state)
-
   /** Request for the state of @a action to be changed to @a value,
-   * assuming that the state is boolean.
+   * assuming that the action has the expected state type.
    * 
-   * See g_action_get_state_type().
+   * See get_state_type().
    * 
    * This call merely requests a change.  The action may refuse to change
    * its state or may change its state to something other than @a value.
-   * See g_action_get_state_hint().
+   * See get_state_hint().
    * 
    * @newin{2,38}
    * @param value The new state.
    */
-  void change_state(bool value);
+  template <typename T_Value>
+  void change_state(const T_Value& value);
+
+  _WRAP_METHOD(void change_state_variant(const Glib::VariantBase& value), g_action_change_state)
+
+  _WRAP_METHOD(void change_state(const Glib::VariantBase& value), g_action_change_state, deprecated "Use the templated method instead, passing a normal C++ type.")
 
   //TODO: Docs
   template <typename T_Value>
@@ -120,13 +117,13 @@ public:
 
   _WRAP_METHOD(Glib::VariantBase get_state_variant() const, g_action_get_state)
 
-   //TODO: Do this when we can break ABI, removing activate_variant(const Glib::VariantBase& parameter);
-   //template <typename T_Value>
-   //void activate(const T_Value& parameter);
-   //
-   //_WRAP_METHOD(void activate_variant(const Glib::VariantBase& parameter), g_action_activate)
+  //TODO: Docs
+  template <typename T_Value>
+  void activate(const T_Value& parameter);
+
+  _WRAP_METHOD(void activate_variant(const Glib::VariantBase& parameter), g_action_activate)
 
-  _WRAP_METHOD(void activate(const Glib::VariantBase& parameter), g_action_activate)
+  _WRAP_METHOD(void activate(const Glib::VariantBase& parameter), g_action_activate, deprecated "Use the templated method instead, passing a normal C++ type.")
 
   _WRAP_METHOD(static bool name_is_valid(const Glib::ustring& action_name), g_action_name_is_valid )
 
@@ -208,7 +205,6 @@ Glib::ustring Action::print_detailed_name(const Glib::ustring& action_name, cons
   return print_detailed_name_variant(type_glib_variant::create(parameter));
 }
 
-/* See the TODOs above for when we can break ABI:
 template <typename T_Value>
 void Action::change_state(const T_Value& value)
 {
@@ -216,6 +212,7 @@ void Action::change_state(const T_Value& value)
 
   g_return_if_fail(
     g_variant_type_equal(g_action_get_state_type(const_cast<GAction*>(gobj())), type_glib_variant::variant_type().gobj()));
+
   change_state_variant(type_glib_variant::create(value));
 }
 
@@ -226,8 +223,8 @@ void Action::activate(const T_Value& parameter)
 
   g_return_if_fail(
     g_variant_type_equal(g_action_get_parameter_type(const_cast<GAction*>(gobj())), type_glib_variant::variant_type().gobj()));
+
   activate_variant(type_glib_variant::create(parameter));
 }
-*/
 
 } // namespace Gio
_______________________________________________
gtkmm-list mailing list
gtkmm-list@gnome.org
https://mail.gnome.org/mailman/listinfo/gtkmm-list

Reply via email to