GNOME Bugzilla – Bug 620808
Implement getting and setting properties using introspection information.
Last modified: 2010-07-27 19:53:14 UTC
.
Created attachment 162908 [details] [review] Implement getting and setting properties using introspection information. This allows us to use information not present in GObject such as transfer and element types.
Created attachment 163059 [details] [review] Implement getting and setting properties using introspection information. This allows us to use information not present in GObject such as transfer and element types.
I'll take a look at this Friday if no one else gets to it first.
(In reply to comment #3) > I'll take a look at this Friday if no one else gets to it first. Or maybe we should address it once PyGI has been merged into PyGObject?
Review of attachment 163059 [details] [review]: Removing from the queue until we have merged with PyGObject (which seems uncontroversial).
Created attachment 166297 [details] [review] Implement getting and setting properties using introspection information. This allows us to use information not present in GObject such as transfer and element types.
Comment on attachment 166297 [details] [review] Implement getting and setting properties using introspection information. Accepted for commit after fixing up some white space issues git is complaining about and putting in some comments bellow: >+PyObject * >+pygi_get_property_value_real (PyGObject *instance, >+ const gchar *attr_name) >+{ >+ GType g_type; >+ GIPropertyInfo *property_info = NULL; >+ char *property_name = g_strdup (attr_name); >+ GParamSpec *pspec = NULL; >+ GValue value = { 0, }; >+ GArgument arg = { 0, }; >+ PyObject *py_value = NULL; >+ GITypeInfo *type_info = NULL; >+ GITransfer transfer; >+ >+ canonicalize_key (property_name); >+ >+ g_type = pyg_type_from_object ((PyObject *)instance); >+ property_info = _pygi_lookup_property_from_g_type (g_type, property_name); >+ >+ if (property_info == NULL) >+ goto out; >+ >+ pspec = g_object_class_find_property (G_OBJECT_GET_CLASS (instance->obj), >+ attr_name); >+ if (pspec == NULL) >+ goto out; >+ >+ g_value_init (&value, G_PARAM_SPEC_VALUE_TYPE (pspec)); >+ g_object_get_property (instance->obj, attr_name, &value); >+ >+ type_info = g_property_info_get_type (property_info); >+ transfer = g_property_info_get_ownership_transfer (property_info); >+ >+ if (g_type_info_is_pointer (type_info)) { >+ arg.v_pointer = g_value_peek_pointer (&value); >+ } else { >+ GITypeTag type_tag = g_type_info_get_tag (type_info); Need a FIXME on the switch statement indicating it is not complete >+ switch (type_tag) { >+ case GI_TYPE_TAG_INT32: >+ arg.v_int = g_value_get_int (&value); >+ break; >+ case GI_TYPE_TAG_UINT32: >+ arg.v_uint = g_value_get_uint (&value); >+ break; >+ case GI_TYPE_TAG_BOOLEAN: >+ arg.v_boolean = g_value_get_boolean (&value); >+ break; >+ case GI_TYPE_TAG_INTERFACE: >+ arg.v_pointer = g_value_get_object (&value); >+ break; >+ default: >+ PyErr_Format (PyExc_NotImplementedError, >+ "Retrieving properties of type %s is not implemented", >+ g_type_tag_to_string (g_type_info_get_tag (type_info))); >+ goto out; >+ } >+ } >+ >+ py_value = _pygi_argument_to_object (&arg, type_info, transfer); >+ >+out: >+ g_free (property_name); >+ if (property_info != NULL) >+ g_base_info_unref (property_info); >+ if (type_info != NULL) >+ g_base_info_unref (type_info); >+ >+ return py_value; >+} >+ >+gint >+pygi_set_property_value_real (PyGObject *instance, >+ const gchar *attr_name, >+ PyObject *py_value) >+{ >+ GType g_type; >+ GIPropertyInfo *property_info = NULL; >+ char *property_name = g_strdup (attr_name); >+ GITypeInfo *type_info = NULL; >+ GITypeTag type_tag; >+ GITransfer transfer; >+ GValue value = { 0, }; >+ GArgument arg = { 0, }; >+ GParamSpec *pspec = NULL; >+ gint ret_value = -1; >+ >+ canonicalize_key (property_name); >+ >+ g_type = pyg_type_from_object ((PyObject *)instance); >+ property_info = _pygi_lookup_property_from_g_type (g_type, property_name); >+ >+ if (property_info == NULL) >+ goto out; >+ >+ pspec = g_object_class_find_property (G_OBJECT_GET_CLASS (instance->obj), >+ attr_name); >+ if (pspec == NULL) >+ goto out; >+ >+ if (! (pspec->flags & G_PARAM_WRITABLE)) >+ goto out; >+ >+ type_info = g_property_info_get_type (property_info); >+ transfer = g_property_info_get_ownership_transfer (property_info); >+ arg = _pygi_argument_from_object (py_value, type_info, transfer); >+ >+ g_value_init (&value, G_PARAM_SPEC_VALUE_TYPE (pspec)); >+ >+ type_tag = g_type_info_get_tag (type_info); Need a FIXME on the switch statement indicating it is not complete >+ switch (type_tag) { >+ case GI_TYPE_TAG_GHASH: >+ g_value_set_boxed (&value, arg.v_pointer); >+ break; >+ case GI_TYPE_TAG_GLIST: >+ g_value_set_pointer (&value, arg.v_pointer); >+ break; >+ case GI_TYPE_TAG_INT32: >+ g_value_set_int (&value, arg.v_int); >+ break; >+ default: >+ PyErr_Format (PyExc_NotImplementedError, >+ "Setting properties of type %s is not implemented", >+ g_type_tag_to_string (g_type_info_get_tag (type_info))); >+ goto out; >+ } >+ >+ g_object_set_property (instance->obj, attr_name, &value); >+ >+ ret_value = 0; >+ >+out: >+ g_free (property_name); >+ if (property_info != NULL) >+ g_base_info_unref (property_info); >+ if (type_info != NULL) >+ g_base_info_unref (type_info); >+ >+ return ret_value; >+} >
Attachment 166297 [details] pushed as 6655a79 - Implement getting and setting properties using introspection information.