1 /*
2 SPDX-FileCopyrightText: 2020 Michail Vourlakos <mvourlakos@gmail.com>
3 SPDX-License-Identifier: GPL-2.0-or-later
4 */
5
6 // local
7 #include "generictable.h"
8 #include "activitydata.h"
9 #include "appletdata.h"
10 #include "errorinformationdata.h"
11 #include "layoutdata.h"
12 #include "screendata.h"
13 #include "viewdata.h"
14
15 // Qt
16 #include <QDebug>
17
18 namespace Latte {
19 namespace Data {
20
21 template <class T>
GenericTable()22 GenericTable<T>::GenericTable()
23 {
24 }
25
26 template <class T>
GenericTable(GenericTable<T> && o)27 GenericTable<T>::GenericTable(GenericTable<T> &&o)
28 : m_list(o.m_list)
29 {
30
31 }
32
33 template <class T>
GenericTable(const GenericTable<T> & o)34 GenericTable<T>::GenericTable(const GenericTable<T> &o)
35 : m_list(o.m_list)
36 {
37
38 }
39
40 //! Operators
41 template <class T>
operator =(const GenericTable<T> & rhs)42 GenericTable<T> &GenericTable<T>::operator=(const GenericTable<T> &rhs)
43 {
44 m_list = rhs.m_list;
45
46 return (*this);
47 }
48
49 template <class T>
operator =(GenericTable<T> && rhs)50 GenericTable<T> &GenericTable<T>::operator=(GenericTable<T> &&rhs)
51 {
52 m_list = rhs.m_list;
53 return (*this);
54 }
55
56 template <class T>
operator <<(const T & rhs)57 GenericTable<T> &GenericTable<T>::operator<<(const T &rhs)
58 {
59 if (!rhs.id.isEmpty()) {
60 m_list << rhs;
61 }
62
63 return (*this);
64 }
65
66 template <class T>
operator <<(const GenericTable<T> & rhs)67 GenericTable<T> &GenericTable<T>::operator<<(const GenericTable<T> &rhs)
68 {
69 m_list << rhs.m_list;
70 return (*this);
71 }
72
73 template <class T>
insert(const int & pos,const T & rhs)74 GenericTable<T> &GenericTable<T>::insert(const int &pos, const T &rhs)
75 {
76 m_list.insert(pos, rhs);
77 return (*this);
78 }
79
80 template <class T>
insertBasedOnName(const T & rhs)81 GenericTable<T> &GenericTable<T>::insertBasedOnName(const T &rhs)
82 {
83 return insert(sortedPosForName(rhs.name), rhs);
84 }
85
86 template <class T>
insertBasedOnId(const T & rhs)87 GenericTable<T> &GenericTable<T>::insertBasedOnId(const T &rhs)
88 {
89 return insert(sortedPosForId(rhs.id), rhs);
90 }
91
92 template <class T>
operator ==(const GenericTable<T> & rhs) const93 bool GenericTable<T>::operator==(const GenericTable<T> &rhs) const
94 {
95 if (m_list.count() == 0 && rhs.m_list.count() == 0) {
96 return true;
97 }
98
99 if (m_list.count() != rhs.m_list.count()) {
100 return false;
101 }
102
103 for(int i=0; i<m_list.count(); ++i) {
104 QString id = m_list[i].id;
105
106 if (!rhs.containsId(id) || (*this)[id] != rhs[id]){
107 return false;
108 }
109 }
110
111 return true;
112 }
113
114 template <class T>
operator !=(const GenericTable<T> & rhs) const115 bool GenericTable<T>::operator!=(const GenericTable<T> &rhs) const
116 {
117 return !(*this == rhs);
118 }
119
120 template <class T>
operator [](const QString & id)121 T &GenericTable<T>::operator[](const QString &id)
122 {
123 int pos{-1};
124
125 for(int i=0; i<m_list.count(); ++i) {
126 if (m_list[i].id == id){
127 pos = i;
128 break;
129 }
130 }
131
132 return m_list[pos];
133 }
134
135 template <class T>
operator [](const QString & id) const136 const T GenericTable<T>::operator[](const QString &id) const
137 {
138 int pos{-1};
139
140 for(int i=0; i<m_list.count(); ++i) {
141 if (m_list[i].id == id){
142 pos = i;
143 break;
144 }
145 }
146
147 return m_list[pos];
148 }
149
150 template <class T>
operator [](const uint & index)151 T &GenericTable<T>::operator[](const uint &index)
152 {
153 return m_list[index];
154 }
155
156 template <class T>
operator [](const uint & index) const157 const T GenericTable<T>::operator[](const uint &index) const
158 {
159 return m_list[index];
160 }
161
162 template <class T>
operator QString() const163 GenericTable<T>::operator QString() const
164 {
165 QString result;
166
167 for(int i=0; i<m_list.count(); ++i) {
168 result += m_list[i].id;
169 if (i<(m_list.count()-1)) {
170 result += ", ";
171 }
172 }
173
174 return result;
175 }
176
177 template <class T>
containsId(const QString & id) const178 bool GenericTable<T>::containsId(const QString &id) const
179 {
180 for(int i=0; i<m_list.count(); ++i) {
181 if (m_list[i].id == id){
182 return true;
183 }
184 }
185
186 return false;
187 }
188
189 template <class T>
containsName(const QString & name) const190 bool GenericTable<T>::containsName(const QString &name) const
191 {
192 for(int i=0; i<m_list.count(); ++i) {
193 if (m_list[i].name == name){
194 return true;
195 }
196 }
197
198 return false;
199 }
200
201 template <class T>
isEmpty() const202 bool GenericTable<T>::isEmpty() const
203 {
204 return m_list.count() <= 0;
205 }
206
207 template <class T>
rowExists(const int & row) const208 bool GenericTable<T>::rowExists(const int &row) const
209 {
210 return (m_list.count()>=0 && row>=0 && row<rowCount());
211 }
212
213 template <class T>
indexOf(const QString & id) const214 int GenericTable<T>::indexOf(const QString &id) const
215 {
216 for(int i=0; i<m_list.count(); ++i) {
217 if (m_list[i].id == id){
218 return i;
219 }
220 }
221
222 return -1;
223 }
224
225 template <class T>
rowCount() const226 int GenericTable<T>::rowCount() const
227 {
228 return m_list.count();
229 }
230
231 template <class T>
sortedPosForId(const QString & id) const232 int GenericTable<T>::sortedPosForId(const QString &id) const
233 {
234 int pos{0};
235
236 for(int i=0; i<m_list.count(); ++i) {
237 if (QString::compare(m_list[i].id, id, Qt::CaseInsensitive) <= 0) {
238 pos++;
239 } else {
240 break;
241 }
242 }
243
244 return pos;
245 }
246
247 template <class T>
sortedPosForName(const QString & name) const248 int GenericTable<T>::sortedPosForName(const QString &name) const
249 {
250 int pos{0};
251
252 for(int i=0; i<m_list.count(); ++i) {
253 if (QString::compare(m_list[i].name, name, Qt::CaseInsensitive) <= 0) {
254 pos++;
255 } else {
256 break;
257 }
258 }
259
260 return pos;
261 }
262
263 template <class T>
idForName(const QString & name) const264 QString GenericTable<T>::idForName(const QString &name) const
265 {
266 for(int i=0; i<m_list.count(); ++i) {
267 if (m_list[i].name == name) {
268 return m_list[i].id;
269 }
270 }
271
272 return QString();
273 }
274
275 template <class T>
ids() const276 QStringList GenericTable<T>::ids() const
277 {
278 QStringList idlist;
279
280 for(int i=0; i<m_list.count(); ++i) {
281 idlist << m_list[i].id;
282 }
283
284 return idlist;
285 }
286
287 template <class T>
names() const288 QStringList GenericTable<T>::names() const
289 {
290 QStringList nms;
291
292 for(int i=0; i<m_list.count(); ++i) {
293 nms << m_list[i].name;
294 }
295
296 return nms;
297 }
298
299 template <class T>
clear()300 void GenericTable<T>::clear()
301 {
302 m_list.clear();
303 }
304
305 template <class T>
remove(const QString & id)306 void GenericTable<T>::remove(const QString &id)
307 {
308 const int pos = indexOf(id);
309
310 if (pos >= 0) {
311 m_list.removeAt(pos);
312 }
313 }
314
315 template <class T>
remove(const int & row)316 void GenericTable<T>::remove(const int &row)
317 {
318 if (rowExists(row)) {
319 m_list.removeAt(row);
320 }
321 }
322
323 //! Make linker happy and provide which table instances will be used.
324 //! The alternative would be to move functions definitions in the header file
325 //! but that would drop readability
326 template class GenericTable<Data::Activity>;
327 template class GenericTable<Data::Applet>;
328 template class GenericTable<Data::ErrorInformation>;
329 template class GenericTable<Data::Generic>;
330 template class GenericTable<Data::Layout>;
331 template class GenericTable<Data::Screen>;
332 template class GenericTable<Data::View>;
333
334 }
335 }
336