@@ -24,11 +24,20 @@
2424
2525#define CATEGORY_COLUMN 2
2626
27+// TODO: use something from libunity once it's public
28+enum CategoryColumn {
29+ ID,
30+ DISPLAY_NAME,
31+ ICON_HINT,
32+ RENDERER_NAME,
33+ HINTS
34+};
35+
2736Categories::Categories(QObject* parent)
2837 : DeeListModel(parent)
2938{
3039 // FIXME: need to clean up unused filters on countChanged
31− m_roles[Categories::RoleId] = "id";
40+ m_roles[Categories::RoleCategoryId] = "categoryId";
3241 m_roles[Categories::RoleName] = "name";
3342 m_roles[Categories::RoleIcon] = "icon";
3443 m_roles[Categories::RoleRenderer] = "renderer";
@@ -73,6 +82,25 @@ Categories::onCountChanged()
7382 }
7483}
7584
85+void Categories::onRowCountChanged()
86+{
87+ QAbstractItemModel* model = qobject_cast<QAbstractItemModel*>(sender());
88+ // find the corresponding category index
89+ for (auto iter = m_overriddenCategories.begin(); iter != m_overriddenCategories.end(); ++iter) {
90+ if (iter.value() == model) {
91+ for (int i = 0; i < rowCount(); i++) {
92+ auto id = data(index(i), RoleCategoryId).toString();
93+ if (id != iter.key()) continue;
94+ QVector<int> roles;
95+ roles.append(RoleCount);
96+ QModelIndex changedIndex = index(i);
97+ Q_EMIT dataChanged(changedIndex, changedIndex, roles);
98+ break;
99+ }
100+ }
101+ }
102+}
103+
76104void
77105Categories::onEmitCountChanged()
78106{
@@ -92,6 +120,41 @@ Categories::roleNames() const
92120 return m_roles;
93121}
94122
123+void Categories::onOverrideModelDestroyed()
124+{
125+ QObject* model = sender();
126+ auto iter = m_overriddenCategories.begin();
127+ while (iter != m_overriddenCategories.end()) {
128+ if (iter.value() == model) {
129+ iter = m_overriddenCategories.erase(iter);
130+ continue;
131+ }
132+ ++iter;
133+ }
134+}
135+
136+void Categories::overrideResults(const QString& categoryId, QAbstractItemModel* model)
137+{
138+ m_overriddenCategories[categoryId] = model;
139+ // watch the model
140+ connect(model, &QObject::destroyed, this, &Categories::onOverrideModelDestroyed);
141+ connect(model, &QAbstractItemModel::rowsInserted, this, &Categories::onRowCountChanged);
142+ connect(model, &QAbstractItemModel::rowsRemoved, this, &Categories::onRowCountChanged);
143+ connect(model, &QAbstractItemModel::modelReset, this, &Categories::onRowCountChanged);
144+
145+ // emit the dataChanged signal if the category is already in the model
146+ for (int i = 0; i < rowCount(); i++) {
147+ auto id = data(index(i), RoleCategoryId).toString();
148+ if (id != categoryId) continue;
149+ QVector<int> roles;
150+ roles.append(RoleCount);
151+ roles.append(RoleResults);
152+ QModelIndex changedIndex = index(i);
153+ Q_EMIT dataChanged(changedIndex, changedIndex, roles);
154+ break;
155+ }
156+}
157+
95158void Categories::setResultModel(DeeModel* model)
96159{
97160 // FIXME: should ref it
@@ -153,24 +216,36 @@ Categories::data(const QModelIndex& index, int role) const
153216 }
154217
155218 switch (role) {
156− case RoleId:
157− return DeeListModel::data(index, 0); //ID
219+ case RoleCategoryId:
220+ return DeeListModel::data(index, CategoryColumn::ID);
158221 case RoleName:
159− return DeeListModel::data(index, 1); //DISPLAY_NAME
222+ return DeeListModel::data(index, CategoryColumn::DISPLAY_NAME);
160223 case RoleIcon:
161− return DeeListModel::data(index, 2); //ICON_HINT
224+ return DeeListModel::data(index, CategoryColumn::ICON_HINT);
162225 case RoleRenderer:
163− return DeeListModel::data(index, 3); //RENDERER_NAME
226+ return DeeListModel::data(index, CategoryColumn::RENDERER_NAME);
164227 case RoleContentType:
165228 {
166− auto hints = DeeListModel::data(index, 4).toHash();
167− return hints.contains("content-type") ? hints["content-type"] : QVariant(QString("default"));
229+ auto hints = DeeListModel::data(index, CategoryColumn::HINTS).toHash();
230+ return hints.contains("content-type") ? hints["content-type"] : QVariant(QString("default"));
168231 }
169232 case RoleHints:
170− return DeeListModel::data(index, 4); //HINTS
233+ return DeeListModel::data(index, CategoryColumn::HINTS);
171234 case RoleResults:
235+ if (m_overriddenCategories.size() > 0)
236+ {
237+ auto id = DeeListModel::data(index, CategoryColumn::ID).toString();
238+ if (m_overriddenCategories.find(id) != m_overriddenCategories.end())
239+ return QVariant::fromValue(m_overriddenCategories[id]);
240+ }
172241 return QVariant::fromValue(getFilter(index.row()));
173242 case RoleCount:
243+ if (m_overriddenCategories.size() > 0)
244+ {
245+ auto id = DeeListModel::data(index, CategoryColumn::ID).toString();
246+ if (m_overriddenCategories.find(id) != m_overriddenCategories.end())
247+ return QVariant::fromValue(m_overriddenCategories[id]->rowCount());
248+ }
174249 return QVariant::fromValue(getFilter(index.row())->rowCount());
175250 default:
176251 return QVariant();