2 * Copyright (C) 2012, 2013 Canonical, Ltd.
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; version 3.
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
18#include "qlimitproxymodelqml.h"
23QLimitProxyModelQML::QLimitProxyModelQML(QObject *parent)
24 : QIdentityProxyModel(parent)
26 , m_sourceInserting(false)
27 , m_sourceRemoving(false)
28 , m_dataChangedBegin(-1)
29 , m_dataChangedEnd(-1)
31 connect(this, SIGNAL(modelReset()), SIGNAL(countChanged()));
32 connect(this, SIGNAL(rowsInserted(QModelIndex,int,int)), SIGNAL(countChanged()));
33 connect(this, SIGNAL(rowsRemoved(QModelIndex,int,int)), SIGNAL(countChanged()));
36QHash<int, QByteArray> QLimitProxyModelQML::roleNames() const
38 return sourceModel() ? sourceModel()->roleNames() : QHash<int, QByteArray>();
42QLimitProxyModelQML::setModel(QAbstractItemModel *itemModel)
44 if (itemModel != sourceModel()) {
45 if (sourceModel() != NULL) {
46 sourceModel()->disconnect(this);
49 setSourceModel(itemModel);
51 if (sourceModel() != NULL) {
52 // Disconnect the QIdentityProxyModel handling for rows removed/added...
53 disconnect(sourceModel(), SIGNAL(rowsAboutToBeInserted(QModelIndex,int,int)), this, NULL);
54 disconnect(sourceModel(), SIGNAL(rowsInserted(QModelIndex,int,int)), this, NULL);
55 disconnect(sourceModel(), SIGNAL(rowsAboutToBeRemoved(QModelIndex,int,int)), this, NULL);
56 disconnect(sourceModel(), SIGNAL(rowsRemoved(QModelIndex,int,int)), this, NULL);
58 // ... and use our own
59 connect(sourceModel(), SIGNAL(rowsAboutToBeInserted(QModelIndex,int,int)),
60 this, SLOT(sourceRowsAboutToBeInserted(QModelIndex,int,int)));
61 connect(sourceModel(), SIGNAL(rowsInserted(QModelIndex,int,int)),
62 this, SLOT(sourceRowsInserted(QModelIndex,int,int)));
63 connect(sourceModel(), SIGNAL(rowsAboutToBeRemoved(QModelIndex,int,int)),
64 this, SLOT(sourceRowsAboutToBeRemoved(QModelIndex,int,int)));
65 connect(sourceModel(), SIGNAL(rowsRemoved(QModelIndex,int,int)),
66 this, SLOT(sourceRowsRemoved(QModelIndex,int,int)));
68 Q_EMIT modelChanged();
73QLimitProxyModelQML::rowCount(const QModelIndex &parent) const
75 if (parent.isValid()) // We are not a tree
78 const int unlimitedCount = QIdentityProxyModel::rowCount(parent);
79 return m_limit < 0 ? unlimitedCount : qMin(m_limit, unlimitedCount);
83QLimitProxyModelQML::limit() const
89QLimitProxyModelQML::setLimit(int limit)
91 if (limit != m_limit) {
92 bool inserting = false;
93 bool removing = false;
94 const int oldCount = rowCount();
95 const int unlimitedCount = QIdentityProxyModel::rowCount();
97 if (limit < oldCount) {
99 beginRemoveRows(QModelIndex(), limit, oldCount - 1);
101 } else if (limit < 0) {
102 if (m_limit < unlimitedCount) {
104 beginInsertRows(QModelIndex(), m_limit, unlimitedCount - 1);
107 if (limit > m_limit && unlimitedCount > m_limit) {
109 beginInsertRows(QModelIndex(), m_limit, qMin(limit, unlimitedCount) - 1);
110 } else if (limit < m_limit && limit < oldCount) {
112 beginRemoveRows(QModelIndex(), limit, oldCount - 1);
120 } else if (removing) {
124 Q_EMIT limitChanged();
129QLimitProxyModelQML::sourceRowsAboutToBeInserted(const QModelIndex &parent, int start, int end)
132 beginInsertRows(mapFromSource(parent), start, end);
133 m_sourceInserting = true;
134 } else if (start < m_limit) {
135 const int nSourceAddedItems = end - start + 1;
136 const int currentCount = QIdentityProxyModel::rowCount();
137 if (currentCount + nSourceAddedItems <= m_limit) {
138 beginInsertRows(mapFromSource(parent), start, end);
139 m_sourceInserting = true;
140 } else if (currentCount < m_limit) {
141 const int nItemsToInsert = m_limit - currentCount;
142 beginInsertRows(mapFromSource(parent), start, start + nItemsToInsert - 1);
143 m_sourceInserting = true;
144 m_dataChangedBegin = start + nItemsToInsert;
145 m_dataChangedEnd = m_limit - 1;
146 if (m_dataChangedBegin > m_dataChangedEnd) {
147 m_dataChangedBegin = -1;
148 m_dataChangedEnd = -1;
151 m_dataChangedBegin = start;
152 m_dataChangedEnd = m_limit - 1;
158QLimitProxyModelQML::sourceRowsAboutToBeRemoved(const QModelIndex &parent, int start, int end)
161 beginRemoveRows(mapFromSource(parent), start, end);
162 m_sourceRemoving = true;
163 } else if (start < m_limit) {
164 const int nSourceRemovedItems = end - start + 1;
165 const int currentCount = QIdentityProxyModel::rowCount();
166 if (currentCount <= m_limit) {
167 beginRemoveRows(mapFromSource(parent), start, end);
168 m_sourceRemoving = true;
169 } else if (currentCount - nSourceRemovedItems < m_limit) {
170 const int nItemsToRemove = m_limit - (currentCount - nSourceRemovedItems);
171 beginRemoveRows(mapFromSource(parent), m_limit - nItemsToRemove, m_limit - 1);
172 m_sourceRemoving = true;
173 m_dataChangedBegin = start;
174 m_dataChangedEnd = m_limit - nItemsToRemove - 1;
175 if (m_dataChangedBegin > m_dataChangedEnd) {
176 m_dataChangedBegin = -1;
177 m_dataChangedEnd = -1;
180 m_dataChangedBegin = start;
181 m_dataChangedEnd = m_limit - 1;
187QLimitProxyModelQML::sourceRowsInserted(const QModelIndex & /*parent*/, int /*start*/, int /*end*/)
189 if (m_sourceInserting) {
191 m_sourceInserting = false;
193 if (m_dataChangedBegin != -1 && m_dataChangedEnd != -1) {
194 dataChanged(index(m_dataChangedBegin, 0), index(m_dataChangedEnd, 0));
195 m_dataChangedBegin = -1;
196 m_dataChangedEnd = -1;
201QLimitProxyModelQML::sourceRowsRemoved(const QModelIndex & /*parent*/, int /*start*/, int /*end*/)
203 if (m_sourceRemoving) {
205 m_sourceRemoving = false;
207 if (m_dataChangedBegin != -1 && m_dataChangedEnd != -1) {
208 dataChanged(index(m_dataChangedBegin, 0), index(m_dataChangedEnd, 0));
209 m_dataChangedBegin = -1;
210 m_dataChangedEnd = -1;
keysesc to close
- j k
- move down, up
- enter
- open
- esc
- back, or up a level
- 1 2 3 4
- readme, files, commits, refs
- /
- filter
- y
- copy the clone command
- c
- compare the chosen commit with another (or shift-click both)
- ?
- show or hide this list