~ubuntu-branches/ubuntu/wily/sflphone/wily

« back to all changes in this revision

Viewing changes to kde/src/lib/contactmodel.cpp

  • Committer: Package Import Robot
  • Author(s): Jonathan Riddell
  • Date: 2015-01-07 14:51:16 UTC
  • mfrom: (4.3.5 sid)
  • Revision ID: package-import@ubuntu.com-20150107145116-yxnafinf4lrdvrmx
Tags: 1.4.1-0.1ubuntu1
* Merge with Debian, remaining changes:
 - Drop soprano, nepomuk build-dep
* Drop ubuntu patches, now upstream

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/****************************************************************************
 
2
 *   Copyright (C) 2014 by Savoir-Faire Linux                               *
 
3
 *   Author : Emmanuel Lepage Vallee <emmanuel.lepage@savoirfairelinux.com> *
 
4
 *                                                                          *
 
5
 *   This library is free software; you can redistribute it and/or          *
 
6
 *   modify it under the terms of the GNU Lesser General Public             *
 
7
 *   License as published by the Free Software Foundation; either           *
 
8
 *   version 2.1 of the License, or (at your option) any later version.     *
 
9
 *                                                                          *
 
10
 *   This library is distributed in the hope that it will be useful,        *
 
11
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of         *
 
12
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU      *
 
13
 *   Lesser General Public License for more details.                        *
 
14
 *                                                                          *
 
15
 *   You should have received a copy of the GNU General Public License      *
 
16
 *   along with this program.  If not, see <http://www.gnu.org/licenses/>.  *
 
17
 ***************************************************************************/
 
18
 
 
19
//Parent
 
20
#include "contactmodel.h"
 
21
 
 
22
//SFLPhone library
 
23
#include "contact.h"
 
24
#include "call.h"
 
25
#include "uri.h"
 
26
#include "phonenumber.h"
 
27
#include "abstractitembackend.h"
 
28
#include "itembackendmodel.h"
 
29
#include "visitors/itemmodelstateserializationvisitor.h"
 
30
 
 
31
//Qt
 
32
#include <QtCore/QHash>
 
33
#include <QtCore/QDebug>
 
34
#include <QtCore/QCoreApplication>
 
35
 
 
36
ContactModel* ContactModel::m_spInstance = nullptr;
 
37
 
 
38
///Constructor
 
39
ContactModel::ContactModel(QObject* par) : QAbstractItemModel(par?par:QCoreApplication::instance()),
 
40
m_pBackendModel(nullptr)
 
41
{
 
42
}
 
43
 
 
44
///Destructor
 
45
ContactModel::~ContactModel()
 
46
{
 
47
   m_hContactsByUid.clear();
 
48
   while (m_lContacts.size()) {
 
49
      Contact* c = m_lContacts[0];
 
50
      m_lContacts.remove(0);
 
51
      delete c;
 
52
   }
 
53
}
 
54
 
 
55
ContactModel* ContactModel::instance() {
 
56
   if (!m_spInstance)
 
57
      m_spInstance = new ContactModel(QCoreApplication::instance());
 
58
   return m_spInstance;
 
59
}
 
60
 
 
61
/*****************************************************************************
 
62
 *                                                                           *
 
63
 *                                   Model                                   *
 
64
 *                                                                           *
 
65
 ****************************************************************************/
 
66
 
 
67
 
 
68
bool ContactModel::setData( const QModelIndex& idx, const QVariant &value, int role)
 
69
{
 
70
   Q_UNUSED(idx)
 
71
   Q_UNUSED(value)
 
72
   Q_UNUSED(role)
 
73
   return false;
 
74
}
 
75
 
 
76
QVariant ContactModel::data( const QModelIndex& idx, int role) const
 
77
{
 
78
   if (!idx.isValid())
 
79
      return QVariant();
 
80
   if (!idx.parent().isValid() && (role == Qt::DisplayRole || role == Qt::EditRole)) {
 
81
      const Contact* c = m_lContacts[idx.row()];
 
82
      if (c)
 
83
         return QVariant(c->formattedName());
 
84
   }
 
85
   else if (idx.parent().isValid() && (role == Qt::DisplayRole || role == Qt::EditRole)) {
 
86
      const Contact* c = m_lContacts[idx.parent().row()];
 
87
      if (c)
 
88
         return QVariant(c->phoneNumbers()[idx.row()]->uri());
 
89
   }
 
90
   return QVariant();
 
91
}
 
92
 
 
93
QVariant ContactModel::headerData(int section, Qt::Orientation orientation, int role) const
 
94
{
 
95
   Q_UNUSED(section)
 
96
   if (orientation == Qt::Horizontal && role == Qt::DisplayRole)
 
97
      return QVariant(tr("Contacts"));
 
98
   return QVariant();
 
99
}
 
100
 
 
101
int ContactModel::rowCount( const QModelIndex& par ) const
 
102
{
 
103
   if (!par.isValid()) {
 
104
      return m_lContacts.size();
 
105
   }
 
106
   else if (!par.parent().isValid() && par.row() < m_lContacts.size()) {
 
107
      const Contact* c = m_lContacts[par.row()];
 
108
      if (c) {
 
109
         const int size = c->phoneNumbers().size();
 
110
         return size==1?0:size;
 
111
      }
 
112
   }
 
113
   return 0;
 
114
}
 
115
 
 
116
Qt::ItemFlags ContactModel::flags( const QModelIndex& idx ) const
 
117
{
 
118
   if (!idx.isValid())
 
119
      return Qt::NoItemFlags;
 
120
   return Qt::ItemIsEnabled | ((idx.parent().isValid())?Qt::ItemIsSelectable:Qt::ItemIsEnabled);
 
121
}
 
122
 
 
123
int ContactModel::columnCount ( const QModelIndex& par) const
 
124
{
 
125
   Q_UNUSED(par)
 
126
   return 1;
 
127
}
 
128
 
 
129
QModelIndex ContactModel::parent( const QModelIndex& idx) const
 
130
{
 
131
   if (!idx.isValid())
 
132
      return QModelIndex();
 
133
   CategorizedCompositeNode* modelItem = (CategorizedCompositeNode*)idx.internalPointer();
 
134
   if (modelItem && modelItem->type() == CategorizedCompositeNode::Type::NUMBER) {
 
135
      int idx2 = m_lContacts.indexOf(((Contact::PhoneNumbers*)modelItem)->contact());
 
136
      if (idx2 != -1) {
 
137
         return ContactModel::index(idx2,0,QModelIndex());
 
138
      }
 
139
   }
 
140
   return QModelIndex();
 
141
}
 
142
 
 
143
QModelIndex ContactModel::index( int row, int column, const QModelIndex& par) const
 
144
{
 
145
   if (!par.isValid() && m_lContacts.size() > row) {
 
146
      return createIndex(row,column,m_lContacts[row]);
 
147
   }
 
148
   else if (par.isValid() && m_lContacts[par.row()]->phoneNumbers().size() > row) {
 
149
      return createIndex(row,column,(CategorizedCompositeNode*)(&(m_lContacts[par.row()]->phoneNumbers())));
 
150
   }
 
151
   return QModelIndex();
 
152
}
 
153
 
 
154
/*****************************************************************************
 
155
 *                                                                           *
 
156
 *                                  Mutator                                  *
 
157
 *                                                                           *
 
158
 ****************************************************************************/
 
159
 
 
160
 
 
161
///Find contact by UID
 
162
Contact* ContactModel::getContactByUid(const QByteArray& uid)
 
163
{
 
164
   return m_hContactsByUid[uid];
 
165
}
 
166
 
 
167
/**
 
168
 * Create a temporary contact or return the existing one for an UID
 
169
 * This temporary contact should eventually be merged into the real one
 
170
 */
 
171
Contact* ContactModel::getPlaceHolder(const QByteArray& uid )
 
172
{
 
173
   Contact* ct = m_hContactsByUid[uid];
 
174
 
 
175
   //Do not create a placeholder if the real deal exist
 
176
   if (ct) {
 
177
      return ct;
 
178
   }
 
179
 
 
180
   //Do not re-create if it already exist
 
181
   ct = m_hPlaceholders[uid];
 
182
   if (ct)
 
183
      return ct;
 
184
 
 
185
   ContactPlaceHolder* ct2 = new ContactPlaceHolder(uid);
 
186
 
 
187
   m_hPlaceholders[ct2->uid()] = ct2;
 
188
   return ct2;
 
189
}
 
190
 
 
191
///Return if there is backends
 
192
bool ContactModel::hasBackends() const
 
193
{
 
194
   return m_lBackends.size();
 
195
}
 
196
 
 
197
 
 
198
const QVector<AbstractContactBackend*> ContactModel::enabledBackends() const
 
199
{
 
200
   return m_lBackends;
 
201
}
 
202
 
 
203
bool ContactModel::hasEnabledBackends() const
 
204
{
 
205
   return m_lBackends.size()>0;
 
206
}
 
207
 
 
208
CommonItemBackendModel* ContactModel::backendModel() const
 
209
{
 
210
   if (!m_pBackendModel) {
 
211
      const_cast<ContactModel*>(this)->m_pBackendModel = new CommonItemBackendModel(const_cast<ContactModel*>(this));
 
212
   }
 
213
   return m_pBackendModel; //TODO
 
214
}
 
215
 
 
216
const QVector<AbstractContactBackend*> ContactModel::backends() const
 
217
{
 
218
   return m_lBackends;
 
219
}
 
220
 
 
221
bool ContactModel::enableBackend(AbstractContactBackend* backend, bool enabled)
 
222
{
 
223
   Q_UNUSED(backend)
 
224
   Q_UNUSED(enabled)
 
225
   //TODO;
 
226
   return false;
 
227
}
 
228
 
 
229
bool ContactModel::addContact(Contact* c)
 
230
{
 
231
   if (!c)
 
232
      return false;
 
233
   beginInsertRows(QModelIndex(),m_lContacts.size()-1,m_lContacts.size());
 
234
   m_lContacts << c;
 
235
   m_hContactsByUid[c->uid()] = c;
 
236
 
 
237
   //Deprecate the placeholder
 
238
   if (m_hPlaceholders.contains(c->uid())) {
 
239
      ContactPlaceHolder* c2 = m_hPlaceholders[c->uid()];
 
240
      if (c2) {
 
241
         c2->merge(c);
 
242
         m_hPlaceholders[c->uid()] = nullptr;
 
243
      }
 
244
   }
 
245
   endInsertRows();
 
246
   emit layoutChanged();
 
247
   emit newContactAdded(c);
 
248
   return true;
 
249
}
 
250
 
 
251
 
 
252
void ContactModel::disableContact(Contact* c)
 
253
{
 
254
   if (c)
 
255
      c->setActive(false);
 
256
}
 
257
 
 
258
const ContactList ContactModel::contacts() const
 
259
{
 
260
   return m_lContacts;
 
261
}
 
262
 
 
263
void ContactModel::addBackend(AbstractContactBackend* backend, LoadOptions options)
 
264
{
 
265
   m_lBackends << backend;
 
266
   connect(backend,SIGNAL(reloaded()),this,SLOT(slotReloaded()));
 
267
   connect(backend,SIGNAL(newContactAdded(Contact*)),this,SLOT(slotContactAdded(Contact*)));
 
268
   if (options & LoadOptions::FORCE_ENABLED || ItemModelStateSerializationVisitor::instance()->isChecked(backend))
 
269
      backend->load();
 
270
   emit newBackendAdded(backend);
 
271
}
 
272
 
 
273
bool ContactModel::addNewContact(Contact* c, AbstractContactBackend* backend)
 
274
{
 
275
   Q_UNUSED(backend);
 
276
   return m_lBackends[0]->addNew(c);
 
277
}
 
278
 
 
279
 
 
280
/*****************************************************************************
 
281
 *                                                                           *
 
282
 *                                    Slot                                   *
 
283
 *                                                                           *
 
284
 ****************************************************************************/
 
285
 
 
286
void ContactModel::slotReloaded()
 
287
{
 
288
   emit reloaded();
 
289
}
 
290
 
 
291
void ContactModel::slotContactAdded(Contact* c)
 
292
{
 
293
   addContact(c);
 
294
}