Qt 4.8: Chapter 5: Using List Property Types

Qt Reference Documentation

# Chapter 5: Using List Property Types

Files:

- declarative/tutorials/extending/chapter5-listproperties/app.qml
- declarative/tutorials/extending/chapter5-listproperties/piechart.cpp
- declarative/tutorials/extending/chapter5-listproperties/piechart.h
- declarative/tutorials/extending/chapter5-listproperties/pieslice.cpp
- declarative/tutorials/extending/chapter5-listproperties/pieslice.h
- declarative/tutorials/extending/chapter5-listproperties/main.cpp
- declarative/tutorials/extending/chapter5-listproperties/chapter5-listproperties.pro

Right now, a `PieChart` can only have one `PieSlice`. Ideally a chart would have multiple slices, with different colors and sizes. To do this, we could have a `slices` property that accepts a list of `PieSlice` items:

     import Charts 1.0
     import QtQuick 1.0

     Item {
         width: 300; height: 200

         PieChart {
             anchors.centerIn: parent
             width: 100; height: 100

             slices: [
                 PieSlice {
                     anchors.fill: parent
                     color: "red"
                     fromAngle: 0; angleSpan: 110
                 },
                 PieSlice {
                     anchors.fill: parent
                     color: "black"
                     fromAngle: 110; angleSpan: 50
                 },
                 PieSlice {
                     anchors.fill: parent
                     color: "blue"
                     fromAngle: 160; angleSpan: 100
                 }
             ]
         }
     }

To do this, we replace the `pieSlice` property in `PieChart` with a `slices` property, declared as a QDeclarativeListProperty type. The QDeclarativeListProperty class enables the creation of list properties in QML extensions. We replace the `pieSlice()` function with a `slices()` function that returns a list of slices, and add an internal `append_slice()` function (discussed below). We also use a QList to store the internal list of slices as `m_slices`:

     class PieChart : public QDeclarativeItem
     {
         Q_OBJECT
         Q_PROPERTY(QDeclarativeListProperty<PieSlice> slices READ slices)
         ...
     public:
         ...
         QDeclarativeListProperty<PieSlice> slices();

     private:
         static void append_slice(QDeclarativeListProperty<PieSlice> *list, PieSlice *slice);

         QString m_name;
         QList<PieSlice *> m_slices;
     };

Although the `slices` property does not have an associated `WRITE` function, it is still modifiable because of the way QDeclarativeListProperty works. In the `PieChart` implementation, we implement `PieChart::slices()` to return a QDeclarativeListProperty value and indicate that the internal `PieChart::append_slice()` function is to be called whenever a request is made from QML to add items to the list:

     QDeclarativeListProperty<PieSlice> PieChart::slices()
     {
         return QDeclarativeListProperty<PieSlice>(this, 0, &PieChart::append_slice);
     }

     void PieChart::append_slice(QDeclarativeListProperty<PieSlice> *list, PieSlice *slice)
     {
         PieChart *chart = qobject_cast<PieChart *>(list->object);
         if (chart) {
             slice->setParentItem(chart);
             chart->m_slices.append(slice);
         }
     }

The `append_slice()` function simply sets the parent item as before, and adds the new item to the `m_slices` list. As you can see, the append function for a QDeclarativeListProperty is called with two arguments: the list property, and the item that is to be appended.

The `PieSlice` class has also been modified to include `fromAngle` and `angleSpan` properties and to draw the slice according to these values. This is a straightforward modification if you have read the previous pages in this tutorial, so the code is not shown here.

The complete code can be seen in the updated `examples/tutorials/extending/chapter5-listproperties` directory.