QML और C++ इमेज इंटरऑपरेबिलिटी



image qt (1)

QtQuick1 में करना संभव था लेकिन QtQuick2 में उस कार्यक्षमता को हटा दिया गया था।

समाधान मैं QML और C ++ में समान छवि के साथ QQuickImageProvider को लागू करने की अनुमति देता है जो मूल रूप से QQuickImageProvider QPixmap * साथ काम करता है जो स्ट्रिंग में परिवर्तित हो जाता है और फिर एक पॉइंटर प्रकार में वापस आ जाता है (यह थोड़ा असुरक्षित ध्वनि करता है लेकिन साबित हुआ है काफी अच्छा काम करने के लिए)।

class Pixmap : public QObject {
    Q_OBJECT
    Q_PROPERTY(QString data READ data NOTIFY dataChanged)
public:
    Pixmap(QObject * p = 0) : QObject(p), pix(0) {}
    ~Pixmap() { if (pix) delete pix; }

    QString data() {
        if (pix) return "image://pixmap/" + QString::number((qulonglong)pix);
        else return QString();
    }

public slots:
    void load(QString url) {
        QPixmap * old = 0;
        if (pix) old = pix;
        pix = new QPixmap(url);
        emit dataChanged();
        if (old) delete old;
    }

    void clear() {
        if (pix) delete pix;
        pix = 0;
        emit dataChanged();
    }

signals:
    void dataChanged();

private:
    QPixmap * pix;
};

Pixmap तत्व का कार्यान्वयन बहुत सीधा है, हालाँकि प्रारंभिक थोड़ा सीमित था, क्योंकि नए पिक्समैप को एक ही मेमोरी पते पर आवंटित किया जाना था क्योंकि data स्ट्रिंग अलग-अलग छवियों के लिए समान थी, जिससे QML छवि घटक अपडेट नहीं होता था , लेकिन यह समाधान उतना ही सरल था जितना कि पुराने Pixmap को डिलीट करने के बाद ही नया आवंटित किया गया था। यहां वास्तविक छवि प्रदाता है:

class PixmapProvider : public QQuickImageProvider {
public:
    PixmapProvider() : QQuickImageProvider(QQuickImageProvider::Pixmap) {}
    QPixmap requestPixmap(const QString &id, QSize *size, const QSize &requestedSize) {
        qulonglong d = id.toULongLong();
        if (d) {
            QPixmap * p = reinterpret_cast<QPixmap *>(d);
            return *p;
        } else {
            return QPixmap();
        }
    }
};

पंजीकरण:

//in main()
engine.addImageProvider("pixmap", new PixmapProvider);
qmlRegisterType<Pixmap>("Test", 1, 0, "Pixmap");

और यह है कि आप इसे QML में कैसे उपयोग करते हैं:

Pixmap {
    id: pix
}

Image {
    source: pix.data
}

// and then pix.load(path)

ALSO ध्यान दें कि मेरे मामले में पिक्समैप का कोई वास्तविक संशोधन नहीं था जिसे QML में अद्यतन करने की आवश्यकता थी। यह समाधान QML में छवि को ऑटो-अपडेट नहीं करेगा यदि इसे C ++ में बदल दिया जाए, क्योंकि मेमोरी में पता वही रहेगा। लेकिन इसके लिए समाधान बस उतना ही सीधा है - एक update() पद्धति लागू करें जो एक new QPixmap(oldPixmap) आवंटित करता है - यह एक ही आंतरिक डेटा का उपयोग करेगा लेकिन आपको एक नया मेमोरी एड्रेस के साथ एक नया new QPixmap(oldPixmap) देगा, जो ट्रिगर होगा परिवर्तन पर अद्यतन करने के लिए QML छवि। इसका मतलब यह है कि Pixmap को एक्सेस करने के लिए प्रोफ़ेड विधि Pixmap वर्ग के माध्यम से होगी, सीधे QPixmap * से नहीं क्योंकि आपको data परिवर्तन को ट्रिगर करने के लिए Pixmap क्लास की आवश्यकता होगी, इसलिए बस pix लिए एक pix जोड़ें, और बस इस स्थिति में जटिल करें या थ्रेडेड सामान, आप इसके बजाय QImage का उपयोग करना चाहते हैं और एक म्यूटेक्स जोड़ सकते हैं ताकि अंतर्निहित डेटा को QML में परिवर्तित नहीं किया जा सके, जबकि C ++ या आसपास के अन्य तरीके से बदला जा सके।

मैंने दस्तावेज़ीकरण के माध्यम से देखा है और जो कुछ भी मुझे इंटरनेट पर मिल सकता है, लेकिन ऐसा नहीं लगता है कि सी ++ से क्यूएमएल छवि तक पहुंचना संभव है।

क्या उसके आसपास काम करने का कोई तरीका है?





qtquick2