c++propertiesgetter-setterglibglibmm

glibmm/gtkmm custom property explanation/example request


i'm trying to reimplement a set of GLIB classes in C++ using GLIBMM. Most of them are buggy and need to be expanded a lot and since the entire project is done in C++ i preferred to port the code before correcting it.

Unfortunately i'm not a GLIB expert and even if i've spent many days around the official documentation i'm still in trouble in understanding some concepts, expecially around Properties.

As far as i have understood, properties are a full replacement (and maybe more) for setters and getters. Basically, instead of using specialized methods for each attribute, a common set/get_property method is used for all of them, accessing the property with a name (or ID) and using a container like GValue to hold multiple kind of data.

The only advantage i can see in this is the ability to access properties with names contained in strings (which may come for example from a configuration file) but i'm surely missing something. Moreover this seems to be true in GLIB but not in Glib::ObjectBase which says that you should prefer a specialized property_(*) getter/setter instead of property_set/get_value.

Reading the documentation about Glib::Property i'm not sure how a full properties implementation in C++ should like, i presume the lack of experience with GLIB is making it harder.

I'd like to move every property as an attribute with std get/set methods but i don't want to make a lot of changes discovering too late that the previous approch was times better :)

Can someone explain me what a property is (if compared with a C++ class attribute)? Can you provide me an example of a working property with signal/slots? Can someone put some light over the advantages of the two ways?

Thank you!


Solution

  • If we look under the hood of Glib properties GObject properties we see the c implementation at work. The above link also has a detailed explanation of the the code .

    Object properties

    "One of GObject's nice features is its generic get/set mechanism for object properties. When an object is instantiated, the object's class_init handler should be used to register the object's properties with g_object_class_install_properties.

    A more detail explanation in C++ and C can be found in both the links.

    The best way to understand how object properties work is by looking at a real example of how it is used:

    If we look at Glib Property details we can see

    A Glib::Object property.

    "This class wraps a GObject property, providing a C++ API to the GObject property system, for use with classes derived from Glib::Object or Glib::Interface.

    A property is a value associated with each instance of a type and some class data for each property:

    1. Its unique name, used to identify the property.
    2. A human-readable nick name.
    3. A short description.
    4. The default value and the minimum and maximum bounds (depending on the type of the property).
    5. Flags, defining, among other things, whether the property can be read or written."

    Example Ref GObject properties

    class MyCellRenderer : public Gtk::CellRenderer
    {
    public:
    MyCellRenderer()
    :
    Glib::ObjectBase (typeid(MyCellRenderer)),
    Gtk::CellRenderer(),
    

    The Equivalent of type definition in C or C++ (Constructor / Destructor)

    Template Glib::Property< T >::Property ( Glib::Object& object, const Glib::ustring& name )

    mybool is the name and true is the default value

    property_mybool (*this, "mybool", true),

    property_myint_ (*this, "myint", 42)

    {}
    virtual ~MyCellRenderer() {}
    

    // Glib::Property<> can be public,

    ** Declaration of type constructor / destructor Eg Public or private**

    Glib::Property<bool> property_mybool;
    // or private, and combined with Glib::PropertyProxy<>.
    Glib::PropertyProxy<int> property_myint() { return property_myint_.get_proxy(); }
    private:
    Glib::Property<int> property_myint_;
    };
    

    both g_object_set_property and class_init handler may be of use to you Ref GObject properties

    All the best