Appendix A. The RefPtr smartpointer
Prev |  | Next

## Appendix A. The RefPtr smartpointer

Glib::RefPtr is a smartpointer. Specifically, it is a reference-counting smartpointer. You might be familiar with `std::auto_ptr<>`, which is also a smartpointer, but `Glib::RefPtr<>` is much simpler, and more useful. We expect a future version of the C++ Standard Library to contain a reference-counting shared smartpointer, so a future version of gtkmm will probably use that instead.

Reference

A smartpointer acts much like a normal pointer. Here are a few examples.

#### Copying

You can copy RefPtrs, just like normal pointers. But unlike normal pointers, you don't need to worry about deleting the underlying instance

    Glib::RefPtr<Gdk::Bitmap> refBitmap = Gdk::Bitmap::create(window,
    data, width, height);
    Glib::RefPtr<Gdk::Bitmap> refBitmap2 = refBitmap;

Of course this means that you can store RefPtrs in standard containers, such as std::vector or std::list.

    std::list< Glib::RefPtr<Gdk::Pixmap> > listPixmaps;
    Glib::RefPtr<Gdk::Pixmap> refPixmap = Gdk::Pixmap::create(window,
    width, height, depth);
    listPixmaps.push_back(refPixmap);

#### Dereferencing

You can dereference a smartpointer with the -> operator, to call the methods of the underlying instance, just like a normal pointer.

    Glib::RefPtr<Gdk::Bitmap> refBitmap = Gdk::Bitmap::create(window,
    data, width, height);
    int depth = refBitmap->get_depth();

But unlike most smartpointers, you can't use the * operator to access the underlying instance.

    Glib::RefPtr<Gdk::Bitmap> refBitmap = Gdk::Bitmap::create(window,
    data, width, height);
    Gdk::Bitmap* underlying = *refBitmap; //Syntax error - will not compile.

#### Casting

You can cast RefPtrs to base types, just like normal pointers.

    Glib::RefPtr<Gtk::TreeStore> refStore = Gdk::TreeStore::create(columns);
    Glib::RefPtr<Gtk::TreeModel> refModel = refStore;

This means that any method which takes a `const Glib::RefPtr<BaseType>` argument can also take a `const Glib::RefPtr<DerivedType>`. The cast is implicit, just as it would be for a normal pointer.

You can also cast to a derived type, but the syntax is a little different than with a normal pointer.

    Glib::RefPtr<Gtk::TreeStore> refStore =
    Glib::RefPtr<Gtk::TreeStore>::cast_dynamic(refModel);
    Glib::RefPtr<Gtk::TreeStore> refStore2 =
    Glib::RefPtr<Gtk::TreeStore>::cast_static(refModel);

#### Checking for null

Just like normal pointers, you can check whether a RefPtr points to anything.

    Glib::RefPtr<Gtk::TreeModel> refModel = m_TreeView.get_model();
    if(refModel)
    {
      int cols_count = refModel->get_n_columns();
      ...
    }

But unlike normal pointers, RefPtrs are automatically initialized to null so you don't need to remember to do that yourself.

#### Constness

The use of the const keyword in C++ is not always clear. You might not realise that `const Something*` declares a pointer to a const Something, The pointer can be changed, but not the Something that it points to.

Therefore, the RefPtr equivalent of `Something*` for a method parameter is `const Glib::RefPtr<Something>&`, and the equivalent of `const Something*` is `const Glib::RefPtr<const Something>&`.

The `const ... &` around both is just for efficiency, like using `const std::string&` instead of `std::string` for a method parameter to avoid unnecessary copying.

Prev | Up | Next
Chapter 22. Copyright and Permissions Notice | Home | Appendix B. Signals