~indicator-applet-developers/qmenumodel/trunk

« back to all changes in this revision

Viewing changes to libqmenumodel/src/converter.cpp

  • Committer: Bileto Bot
  • Author(s): Marco Trevisan (Treviño)
  • Date: 2016-11-16 10:41:44 UTC
  • mfrom: (121.3.23 converter-improvements)
  • Revision ID: ci-train-bot@canonical.com-20161116104144-q1g8rtm2c5wvpa30
converter: cleanup and add support for more variant types

Approved by: Lukáš Tinkl

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
/*
2
 
 * Copyright 2012 Canonical Ltd.
 
2
 * Copyright 2012-2016 Canonical Ltd.
3
3
 *
4
4
 * This program is free software; you can redistribute it and/or modify
5
5
 * it under the terms of the GNU Lesser General Public License as published by
15
15
 *
16
16
 * Authors:
17
17
 *      Renato Araujo Oliveira Filho <renato@canonical.com>
 
18
 *      Marco Trevisan <marco.trevisan@canonical.com>
18
19
 */
19
20
 
20
21
extern "C" {
58
59
        gsize size = 0;
59
60
        const gchar *v = g_variant_get_string(value, &size);
60
61
        result.setValue(QString::fromUtf8(v, size));
 
62
    } else if (g_variant_type_equal(type, G_VARIANT_TYPE_STRING_ARRAY)) {
 
63
        gsize size = 0;
 
64
        const gchar **sa = g_variant_get_strv(value, &size);
 
65
        QStringList list;
 
66
        for (gsize i = 0; i < size; ++i) {
 
67
            list << QString::fromUtf8(sa[i]);
 
68
        }
 
69
        result.setValue(list);
 
70
        g_free(sa);
 
71
    } else if (g_variant_type_equal(type, G_VARIANT_TYPE_BYTESTRING)) {
 
72
        result.setValue(QByteArray(g_variant_get_bytestring(value)));
 
73
    } else if (g_variant_type_equal(type, G_VARIANT_TYPE_BYTESTRING_ARRAY)) {
 
74
        gsize size = 0;
 
75
        const gchar **bsa = g_variant_get_bytestring_array(value, &size);
 
76
        QByteArrayList list;
 
77
        for (gsize i = 0; i < size; ++i) {
 
78
            list << bsa[i];
 
79
        }
 
80
        result.setValue(list);
 
81
        g_free(bsa);
61
82
    } else if (g_variant_type_equal(type, G_VARIANT_TYPE_VARIANT)) {
62
83
        GVariant *var = g_variant_get_variant(value);
63
84
        result = toQVariant(var);
110
131
     * G_VARIANT_TYPE_UNIT
111
132
     * G_VARIANT_TYPE_DICT_ENTRY
112
133
     * G_VARIANT_TYPE_DICTIONARY
113
 
     * G_VARIANT_TYPE_STRING_ARRAY
114
 
     * G_VARIANT_TYPE_BYTESTRING
115
134
     * G_VARIANT_TYPE_OBJECT_PATH_ARRAY
116
 
     * G_VARIANT_TYPE_BYTESTRING_ARRAY
117
135
     */
118
136
 
119
137
    return result;
120
138
}
121
139
 
122
 
static GVariant* toGVariant(const QString &typeName, const QVariant &value)
123
 
{
124
 
    if (typeName == "uchar") {
125
 
        return g_variant_new_byte(value.value<uchar>());
126
 
    } else if (typeName == "short") {
127
 
        return g_variant_new_int16(value.value<short>());
128
 
    } else if (typeName == "ushort") {
129
 
        return g_variant_new_uint16(value.value<ushort>());
130
 
    } else if (typeName == "long") {
131
 
        return g_variant_new_int64(value.value<long>());
132
 
    } else if (typeName == "ulong") {
133
 
        return g_variant_new_uint64(value.value<ulong>());
134
 
    } else {
135
 
        qWarning() << "QVariant type not supported:" << typeName;
136
 
    }
137
 
 
138
 
    return NULL;
139
 
}
140
 
 
141
140
QVariant Converter::toQVariantFromVariantString(const QString &variantString)
142
141
{
143
142
    GVariant *gvariant;
147
146
        return QVariant();
148
147
    }
149
148
 
150
 
    gvariant = g_variant_parse (NULL, variantString.toUtf8().data(), NULL, NULL, &error);
 
149
    gvariant = g_variant_parse (NULL, qUtf8Printable(variantString), NULL, NULL, &error);
151
150
 
152
151
    if (error) {
153
152
        qWarning() << "Impossible to parse" << variantString << "as variant string:"<< error->message;
184
183
        result = g_variant_new_int64(value.toLongLong());
185
184
        break;
186
185
    case QVariant::String:
187
 
        result = g_variant_new_string(value.toString().toUtf8().data());
 
186
        result = g_variant_new_string(qUtf8Printable(value.toString()));
188
187
        break;
189
188
    case QVariant::UInt:
190
189
        result = g_variant_new_uint32(value.toUInt());
192
191
    case QVariant::ULongLong:
193
192
        result = g_variant_new_uint64(value.toULongLong());
194
193
        break;
 
194
    case QMetaType::UChar:
 
195
        result = g_variant_new_byte(value.value<uchar>());
 
196
        break;
 
197
    case QMetaType::Short:
 
198
        result = g_variant_new_int16(value.value<short>());
 
199
        break;
 
200
    case QMetaType::UShort:
 
201
        result = g_variant_new_uint16(value.value<ushort>());
 
202
        break;
 
203
    case QMetaType::Long:
 
204
        result = g_variant_new_int64(value.value<long>());
 
205
        break;
 
206
    case QMetaType::ULong:
 
207
        result = g_variant_new_uint64(value.value<ulong>());
 
208
        break;
195
209
    case QVariant::Map:
196
210
    {
197
211
        GVariantBuilder *b;
201
215
        QMapIterator<QString, QVariant> i(value.toMap());
202
216
        while (i.hasNext()) {
203
217
            i.next();
204
 
            g_variant_builder_add(b, "{sv}", i.key().toUtf8().data(), toGVariant(i.value()));
 
218
            g_variant_builder_add(b, "{sv}", qUtf8Printable(i.key()), toGVariant(i.value()));
 
219
        }
 
220
        result = g_variant_builder_end(b);
 
221
        g_variant_builder_unref(b);
 
222
        break;
 
223
    }
 
224
    case QMetaType::QByteArrayList:
 
225
    {
 
226
        const QByteArrayList &list = qvariant_cast<QByteArrayList>(value);
 
227
        GVariantBuilder *b = g_variant_builder_new(G_VARIANT_TYPE_BYTESTRING_ARRAY);
 
228
 
 
229
        for (const QByteArray &ba : list) {
 
230
            g_variant_builder_add_value(b, g_variant_new_bytestring(ba));
205
231
        }
206
232
        result = g_variant_builder_end(b);
207
233
        g_variant_builder_unref(b);
209
235
    }
210
236
    case QVariant::List:
211
237
    {
212
 
        QVariantList lst = value.toList();
213
 
        GVariant **vars = g_new(GVariant*, lst.size());
214
 
        for (int i=0; i < lst.size(); i++) {
215
 
            vars[i] = toGVariant(lst[i]);
216
 
        }
217
 
        result = g_variant_new_tuple(vars, lst.size());
218
 
        g_free(vars);
 
238
        GVariantBuilder *b = g_variant_builder_new(G_VARIANT_TYPE_TUPLE);
 
239
 
 
240
        for (const QVariant &v : value.toList()) {
 
241
            g_variant_builder_add_value(b, toGVariant(v));
 
242
        }
 
243
        result = g_variant_builder_end(b);
 
244
        g_variant_builder_unref(b);
 
245
        break;
 
246
    }
 
247
    case QVariant::StringList:
 
248
    {
 
249
        GVariantBuilder *b = g_variant_builder_new(G_VARIANT_TYPE_STRING_ARRAY);
 
250
 
 
251
        for (const QString &s : value.toStringList()) {
 
252
            g_variant_builder_add(b, "s", qUtf8Printable(s));
 
253
        }
 
254
        result = g_variant_builder_end(b);
 
255
        g_variant_builder_unref(b);
219
256
        break;
220
257
    }
221
258
    default:
222
 
        result = ::toGVariant(value.typeName(), value);
 
259
        qWarning() << "QVariant type not supported:" << value.type();
223
260
    }
224
261
 
225
262
    return result;
232
269
    }
233
270
 
234
271
    GVariant* result = NULL;
235
 
    const GVariantType* schema_type;
236
 
    schema_type = g_variant_type_new(schema);
 
272
    GVariantType* schema_type = g_variant_type_new(schema);
237
273
 
238
274
    if (g_variant_type_equal(schema_type, G_VARIANT_TYPE_BOOLEAN)) {
239
275
        if (value.canConvert<bool>()) {
273
309
        }
274
310
    } else if (g_variant_type_equal(schema_type, G_VARIANT_TYPE_STRING)) {
275
311
        if (value.canConvert<QString>()) {
276
 
            result = g_variant_new_string(value.toString().toUtf8().data());
 
312
            result = g_variant_new_string(qUtf8Printable(value.toString()));
277
313
        }
278
314
    } else if (g_variant_type_equal(schema_type, G_VARIANT_TYPE_VARIANT)) {
279
 
        result = Converter::toGVariant(value);
 
315
        result = g_variant_new_variant(Converter::toGVariant(value));
280
316
    } else if (g_variant_type_equal(schema_type, G_VARIANT_TYPE_VARDICT)) {
281
317
        if (value.canConvert(QVariant::Map)) {
282
318
            result = Converter::toGVariant(value.toMap());
283
319
        }
284
320
    } else if (g_variant_type_is_array(schema_type)) {
285
321
        if (value.canConvert(QVariant::List)) {
286
 
 
287
 
            const GVariantType* entry_type;
288
 
            GVariant* data;
289
 
            entry_type = g_variant_type_element(schema_type);
290
 
            gchar* entryTypeString = g_variant_type_dup_string(entry_type);
291
 
 
292
 
            QVariantList lst = value.toList();
293
 
            GVariant **vars = g_new(GVariant*, lst.size());
294
 
 
 
322
            const GVariantType* entryType = g_variant_type_element(schema_type);
 
323
            const gchar* entryTypeString = g_variant_type_peek_string(entryType);
 
324
 
 
325
            GVariantBuilder *b = g_variant_builder_new(G_VARIANT_TYPE_ARRAY);
295
326
            bool ok = true;
296
 
            for (int i=0; i < lst.size(); i++) {
297
 
                data = Converter::toGVariantWithSchema(lst[i], entryTypeString);
 
327
 
 
328
            for (const QVariant &v : value.toList()) {
 
329
                GVariant *data = toGVariantWithSchema(v, entryTypeString);
298
330
 
299
331
                if (data) {
300
 
                    vars[i] = data;
301
 
                }
302
 
                else {
 
332
                    g_variant_builder_add_value(b, data);
 
333
                } else {
303
334
                    ok = false;
304
335
                    qWarning() << "Failed to convert list to array with schema:" << schema;
305
336
                    break;
306
337
                }
307
338
            }
308
339
            if (ok) {
309
 
                result = g_variant_new_array(entry_type, vars, lst.size());
 
340
                result = g_variant_builder_end(b);
310
341
            }
311
 
            g_free(entryTypeString);
312
 
            g_free(vars);
 
342
            g_variant_builder_unref(b);
313
343
        }
314
344
    } else if (g_variant_type_is_tuple(schema_type)) {
315
345
        if (value.canConvert(QVariant::List)) {
316
 
            GVariant* data;
317
 
 
318
 
            QVariantList lst = value.toList();
319
 
            GVariant **vars = g_new(GVariant*, lst.size());
320
 
 
321
 
            const GVariantType* entry_type = g_variant_type_first(schema_type);
322
 
 
 
346
            const GVariantType* entryType = g_variant_type_first(schema_type);
 
347
 
 
348
            GVariantBuilder *b = g_variant_builder_new(G_VARIANT_TYPE_TUPLE);
323
349
            bool ok = true;
324
 
            for (int i=0; i < lst.size(); i++) {
325
 
 
326
 
                gchar* entryTypeString = g_variant_type_dup_string(entry_type);
327
 
 
328
 
                data = Converter::toGVariantWithSchema(lst[i], entryTypeString);
329
 
 
330
 
                if (data) {
331
 
                    vars[i] = data;
332
 
                }
333
 
                else {
334
 
                    ok = false;
335
 
                    qWarning() << "Failed to convert list to tuple with schema:" << schema;
336
 
                    g_free(entryTypeString);
337
 
                    break;
338
 
                }
 
350
 
 
351
            for (const QVariant &v : value.toList()) {
 
352
                gchar* entryTypeString = g_variant_type_dup_string(entryType);
 
353
                GVariant *data = toGVariantWithSchema(v, entryTypeString);
339
354
                g_free(entryTypeString);
340
355
 
341
 
                entry_type = g_variant_type_next(entry_type);
342
 
                if (!entry_type) {
 
356
                if (data) {
 
357
                    g_variant_builder_add_value(b, data);
 
358
                    entryType = g_variant_type_next(entryType);
 
359
                    if (!entryType)
 
360
                        break;
 
361
                } else {
 
362
                    ok = false;
 
363
                    qWarning() << "Failed to convert list to array with schema:" << schema;
343
364
                    break;
344
365
                }
345
366
            }
346
367
            if (ok) {
347
 
                result = g_variant_new_tuple(vars, lst.size());
 
368
                result = g_variant_builder_end(b);
348
369
            }
349
 
            g_free(vars);
 
370
            g_variant_builder_unref(b);
350
371
        }
351
372
    }
352
373
 
354
375
    if (!result) {
355
376
        result = Converter::toGVariant(value);
356
377
    }
 
378
 
 
379
    g_free(schema_type);
 
380
 
357
381
    return result;
358
382
}
359
383