on f684183 help sign in
unity8/plugins/Unity/categories.cpp
141 lines 4.2 kB history raw
1/*
2 * Copyright (C) 2013 Canonical, Ltd.
3 *
4 * Authors:
5 * Michał Sawicz <michal.sawicz@canonical.com>
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; version 3.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <http://www.gnu.org/licenses/>.
18 */
20// self
21#include "categories.h"
22#include "categoryfilter.h"
24Categories::Categories(QObject* parent)
25 : DeeListModel(parent)
26 , m_resultModel(0)
28 // FIXME: need to clean up unused filters on countChanged
29 m_roles[Categories::RoleId] = "id";
30 m_roles[Categories::RoleName] = "name";
31 m_roles[Categories::RoleIcon] = "icon";
32 m_roles[Categories::RoleRenderer] = "renderer";
33 m_roles[Categories::RoleContentType] = "content_type";
34 m_roles[Categories::RoleHints] = "hints";
35 m_roles[Categories::RoleResults] = "results";
36 m_roles[Categories::RoleCount] = "count";
38 // TODO This should not be needed but accumulatting the count changes
39 // makes the visualization more stable and also makes crashes on fast
40 // change of the search term harder to reproduce
41 m_timer.setSingleShot(true);
42 m_timer.setInterval(50);
43 connect(&m_timer, SIGNAL(timeout()), this, SLOT(onEmitCountChanged()));
46Categories::~Categories()
48 qDeleteAll(m_filters);
51CategoryFilter*
52Categories::getFilter(int index) const
54 if (!m_filters.contains(index)) {
55 CategoryFilter* filter = new CategoryFilter();
56 connect(filter, SIGNAL(countChanged()), this, SLOT(onCountChanged()));
57 filter->setModel(m_resultModel);
58 filter->setIndex(index);
60 m_filters.insert(index, filter);
61 }
63 return m_filters[index];
66void
67Categories::setResultModel(DeeListModel* model)
69 if (model != m_resultModel) {
70 m_resultModel = model;
72 Q_FOREACH(CategoryFilter* filter, m_filters) {
73 filter->setModel(m_resultModel);
74 }
76 Q_EMIT resultModelChanged(m_resultModel);
77 }
80void
81Categories::onCountChanged()
83 CategoryFilter* filter = qobject_cast<CategoryFilter*>(sender());
84 if (filter) {
85 m_timerFilters << filter;
86 m_timer.start();
87 }
90void
91Categories::onEmitCountChanged()
93 QVector<int> roles;
94 roles.append(Categories::RoleCount);
95 Q_FOREACH(CategoryFilter* filter, m_timerFilters) {
96 QModelIndex changedIndex = index(filter->index());
97 Q_EMIT dataChanged(changedIndex, changedIndex, roles);
98 }
99 m_timerFilters.clear();
102QHash<int, QByteArray>
103Categories::roleNames() const
105 return m_roles;
108QVariant
109Categories::data(const QModelIndex& index, int role) const
111 if (!index.isValid()) {
112 return QVariant();
113 }
115 switch (role) {
116 case RoleId:
117 return QVariant::fromValue(index.row());
118 case RoleName:
119 return QVariant::fromValue(DeeListModel::data(index, 1)); //DISPLAY_NAME
120 case RoleIcon:
121 return QVariant::fromValue(DeeListModel::data(index, 2)); //ICON_HINT
122 case RoleRenderer:
123 return QVariant::fromValue(DeeListModel::data(index, 3)); //RENDERER_NAME
124 case RoleContentType:
125 {
126 auto hints = QVariant::fromValue(DeeListModel::data(index, 4)).toHash();
127 return hints.contains("content-type") ? hints["content-type"] : QVariant(QString("default"));
128 }
129 case RoleHints:
130 return QVariant::fromValue(DeeListModel::data(index, 4)); //HINTS
131 case RoleResults:
132 return QVariant::fromValue(getFilter(index.row()));
133 case RoleCount:
134 {
135 CategoryFilter* filter = getFilter(index.row());
136 return QVariant::fromValue(filter->rowCount());
137 }
138 default:
139 return QVariant();
140 }