Changes: Consider display name settings in unit tests
[qtcontacts-tracker:hasselmms-qtcontacts-tracker.git] / src / engine / displaylabelgenerator.cpp
1 /*********************************************************************************
2  ** This file is part of QtContacts tracker storage plugin
3  **
4  ** Copyright (c) 2009-2011 Nokia Corporation and/or its subsidiary(-ies).
5  **
6  ** Contact:  Nokia Corporation (info@qt.nokia.com)
7  **
8  ** GNU Lesser General Public License Usage
9  ** This file may be used under the terms of the GNU Lesser General Public License
10  ** version 2.1 as published by the Free Software Foundation and appearing in the
11  ** file LICENSE.LGPL included in the packaging of this file.  Please review the
12  ** following information to ensure the GNU Lesser General Public License version
13  ** 2.1 requirements will be met:
14  ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
15  **
16  ** In addition, as a special exception, Nokia gives you certain additional rights.
17  ** These rights are described in the Nokia Qt LGPL Exception version 1.1, included
18  ** in the file LGPL_EXCEPTION.txt in this package.
19  **
20  ** Other Usage
21  ** Alternatively, this file may be used in accordance with the terms and
22  ** conditions contained in a signed written agreement between you and Nokia.
23  *********************************************************************************/
24
25 #include "displaylabelgenerator.h"
26
27 #include <qcontactdetails.h>
28
29 ////////////////////////////////////////////////////////////////////////////////////////////////////
30
31 class QctDisplayLabelGeneratorData : public QSharedData
32 {
33 protected:
34     explicit QctDisplayLabelGeneratorData(const QString &detailName);
35
36 public:
37     virtual ~QctDisplayLabelGeneratorData();
38
39 public: // API to be implemented
40     virtual QString createDisplayLabel(const QContact &contact) const = 0;
41
42 public:
43     const QString &requiredDetailName() const;
44
45 protected:
46     const QString m_detailName;
47 };
48
49 class SimpleDetailFieldDisplayLabelGeneratorData : public QctDisplayLabelGeneratorData
50 {
51 public:
52     SimpleDetailFieldDisplayLabelGeneratorData(const QString &detailName, const QString &fieldName);
53
54 public: // AbstractDisplayLabelGeneratorData API
55     virtual QString createDisplayLabel(const QContact &contact) const;
56
57 protected:
58     const QString m_fieldName;
59 };
60
61 class FirstNameLastNameDisplayLabelGeneratorData : public QctDisplayLabelGeneratorData
62 {
63 public:
64     FirstNameLastNameDisplayLabelGeneratorData();
65
66 public: // AbstractDisplayLabelGeneratorData API
67     virtual QString createDisplayLabel(const QContact &contact) const;
68 };
69
70 class LastNameFirstNameDisplayLabelGeneratorData : public QctDisplayLabelGeneratorData
71 {
72 public:
73     LastNameFirstNameDisplayLabelGeneratorData();
74
75 public: // AbstractDisplayLabelGeneratorData API
76     virtual QString createDisplayLabel(const QContact &contact) const;
77 };
78
79 ////////////////////////////////////////////////////////////////////////////////////////////////////
80
81 QctDisplayLabelGeneratorData::QctDisplayLabelGeneratorData(const QString &detailName)
82     : m_detailName(detailName)
83 {
84 }
85 QctDisplayLabelGeneratorData::~QctDisplayLabelGeneratorData()
86 {
87 }
88
89 inline const QString &
90 QctDisplayLabelGeneratorData::requiredDetailName() const
91 {
92     return m_detailName;
93 }
94
95 SimpleDetailFieldDisplayLabelGeneratorData::SimpleDetailFieldDisplayLabelGeneratorData(const QString &detailName,
96                                                                                        const QString &fieldName)
97     : QctDisplayLabelGeneratorData(detailName)
98     , m_fieldName(fieldName)
99 {
100 }
101
102 QString
103 SimpleDetailFieldDisplayLabelGeneratorData::createDisplayLabel(const QContact &contact) const
104 {
105     return contact.detail(m_detailName).value(m_fieldName);
106 }
107
108 FirstNameLastNameDisplayLabelGeneratorData::FirstNameLastNameDisplayLabelGeneratorData()
109     : QctDisplayLabelGeneratorData(QContactName::DefinitionName)
110 {
111 }
112
113 QString
114 FirstNameLastNameDisplayLabelGeneratorData::createDisplayLabel(const QContact &contact) const
115 {
116     const QContactDetail nameDetail = contact.detail(QContactName::DefinitionName);
117
118     QString result = nameDetail.value(QContactName::FieldFirstName);
119
120     const QString lastName = nameDetail.value(QContactName::FieldLastName);
121     if (not lastName.isEmpty()) {
122         if (not result.isEmpty()) {
123             result.append(QLatin1Char(' '));
124         }
125
126         result.append(lastName);
127     }
128     return result;
129 }
130
131 LastNameFirstNameDisplayLabelGeneratorData::LastNameFirstNameDisplayLabelGeneratorData()
132     : QctDisplayLabelGeneratorData(QContactName::DefinitionName)
133 {
134 }
135
136 QString
137 LastNameFirstNameDisplayLabelGeneratorData::createDisplayLabel(const QContact &contact) const
138 {
139     const QContactDetail nameDetail = contact.detail(QContactName::DefinitionName);
140
141     QString result = nameDetail.value(QContactName::FieldLastName);
142
143     const QString lastName = nameDetail.value(QContactName::FieldFirstName);
144     if (not lastName.isEmpty()) {
145         if (not result.isEmpty()) {
146             result.append(QLatin1String(" "));
147         }
148
149         result.append(lastName);
150     }
151     return result;
152 }
153
154 ////////////////////////////////////////////////////////////////////////////////////////////////////
155
156 QctDisplayLabelGenerator::QctDisplayLabelGenerator(QctDisplayLabelGeneratorData *data)
157     : d(data)
158 {
159 }
160
161 QctDisplayLabelGenerator::QctDisplayLabelGenerator(const QctDisplayLabelGenerator &other)
162     : d(other.d)
163 {
164 }
165
166 QctDisplayLabelGenerator::~QctDisplayLabelGenerator()
167 {
168 }
169
170 QctDisplayLabelGenerator & QctDisplayLabelGenerator::operator=(const QctDisplayLabelGenerator &other)
171 {
172     d = other.d;
173     return *this;
174 }
175
176 QString QctDisplayLabelGenerator::createDisplayLabel(const QContact& contact) const
177 {
178     return d->createDisplayLabel(contact);
179 }
180
181 const QString& QctDisplayLabelGenerator::requiredDetailName() const
182 {
183     return d->requiredDetailName();
184 }
185
186 QctDisplayLabelGenerator
187 QctDisplayLabelGenerator::simpleDetailFieldGenerator(const QString &detailName,
188                                                      const QString &detailFieldName)
189 {
190     return QctDisplayLabelGenerator(new SimpleDetailFieldDisplayLabelGeneratorData(detailName, detailFieldName));
191 }
192
193 QctDisplayLabelGenerator
194 QctDisplayLabelGenerator::firstNameLastNameGenerator()
195 {
196     return QctDisplayLabelGenerator(new FirstNameLastNameDisplayLabelGeneratorData);
197 }
198
199 QctDisplayLabelGenerator
200 QctDisplayLabelGenerator::lastNameFirstNameGenerator()
201 {
202     return QctDisplayLabelGenerator(new LastNameFirstNameDisplayLabelGeneratorData);
203 }
204
205 const QList<QctDisplayLabelGenerator> &
206 QctDisplayLabelGenerator::getList(ListOptions options)
207 {
208     typedef QList<QctDisplayLabelGenerator> GeneratorList;
209     typedef QHash<ListOptions, GeneratorList> GeneratorListMap;
210
211     static GeneratorListMap generators;
212
213     GeneratorListMap::Iterator it = generators.find(options);
214
215     if (it == generators.constEnd()) {
216         it = generators.insert(options, createList(options));
217     }
218
219     return it.value();
220 }
221
222 QList<QctDisplayLabelGenerator>
223 QctDisplayLabelGenerator::createList(ListOptions options)
224 {
225     QList<QctDisplayLabelGenerator> generators;
226
227     // Prefer nickname first/last name when requested (NB#283142, NB#287273)
228     if (options & PreferNickname) {
229         generators += simpleDetailFieldGenerator(QContactNickname::DefinitionName,
230                                                  QContactNickname::FieldNickname);
231     }
232
233     // Choose among "FirstName LastName" and "LastName FirstName" according settings
234     switch(options & RealNameOptions) {
235     case PreferFirstName:
236         generators += firstNameLastNameGenerator();
237         break;
238     case PreferLastName:
239         generators += lastNameFirstNameGenerator();
240         break;
241     }
242
243     // If CustomLabel is set it dominates all other rules, but detailed name fields (NB#200059)
244     generators += simpleDetailFieldGenerator(QContactName::DefinitionName,
245                                              QContactName::FieldCustomLabel);
246
247     // Take "any available name information" - nickname, unless configured to dominate
248     if (not(options & PreferNickname)) {
249         generators += simpleDetailFieldGenerator(QContactNickname::DefinitionName,
250                                                  QContactNickname::FieldNickname);
251     }
252
253     // Take "any available name information" - middle name
254     generators += simpleDetailFieldGenerator(QContactName::DefinitionName,
255                                              QContactName::FieldMiddleName);
256
257     // The company name, e.g. "Nokia"
258     generators += simpleDetailFieldGenerator(QContactOrganization::DefinitionName,
259                                              QContactOrganization::FieldName);
260
261     // "IM username", first the most available IM nickname (e.g "The Dude")
262     generators += simpleDetailFieldGenerator(QContactGlobalPresence::DefinitionName,
263                                              QContactGlobalPresence::FieldNickname);
264
265     // IM address as desparate fallback, this could be a long incomprehensible URI.
266     // Usually it should be something like "thedude@ovi.com".
267     generators += simpleDetailFieldGenerator(QContactOnlineAccount::DefinitionName,
268                                              QContactOnlineAccount::FieldAccountUri);
269
270     // The email address, e.g. "hans.wurst@nokia.com"
271     generators += simpleDetailFieldGenerator(QContactEmailAddress::DefinitionName,
272                                              QContactEmailAddress::FieldEmailAddress);
273
274     // The phone number, e.g. "+3581122334455
275     generators += simpleDetailFieldGenerator(QContactPhoneNumber::DefinitionName,
276                                              QContactPhoneNumber::FieldNumber);
277
278     // The contact's homepage URL, e.g. "http://www.nokia.com/"
279     generators += simpleDetailFieldGenerator(QContactUrl::DefinitionName,
280                                              QContactUrl::FieldUrl);
281
282     return generators;
283 }