Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. QImageIOPlugin doesn't work
Qt 6.11 is out! See what's new in the release blog

QImageIOPlugin doesn't work

Scheduled Pinned Locked Moved Unsolved General and Desktop
15 Posts 4 Posters 3.0k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • S Offline
    S Offline
    sandro4912
    wrote on last edited by
    #1

    I tryed to write a plugin which introduces a new file format .ti which enables reading and writing files in ascii art.

    When I try out the plugin in it doesn't seem to work.

    My plugin files look like this:

    TEMPLATE = lib
    TARGET = textimage
    CONFIG += plugin release
    VERSION = 1.0.0
    
    HEADERS += \
        textimagehandler.h \
        textimageplugin.h
    
    SOURCES += \
        textimagehandler.cpp \
        textimageplugin.cpp
    
    target.path += $$[QT_INSTALL_PLUGINS]/imageformats
    INSTALLS += target
    
    DISTFILES += \
        textimageplugin.json
    
    #ifndef TEXTIMAGEHANDLER_H
    #define TEXTIMAGEHANDLER_H
    
    #include <QImageIOHandler>
    
    class TextImageHandler : public QImageIOHandler
    {
    public:
        bool read(QImage *image) override;
        bool write(const QImage &image) override;
    
        bool canRead() const override;
        static bool canRead(QIODevice *device);
    };
    
    #endif // TEXTIMAGEHANDLER_H
    
    #ifndef TEXTIMAGEPLUGIN_H
    #define TEXTIMAGEPLUGIN_H
    
    #include <QImageIOPlugin>
    
    class TextImagePlugin : public QImageIOPlugin
    {
        Q_OBJECT
        Q_PLUGIN_METADATA(
            IID "org.qt-project.Qt.QImageIOFactoryInterface" FILE "textimageplugin.json")
    public:
        QStringList keys() const;
    
        Capabilities capabilities(
            QIODevice *device, const QByteArray &format) const override;
        QImageIOHandler *create(
            QIODevice *device,
            const QByteArray &format = QByteArray{}) const override;
    };
    
    #endif // TEXTIMAGEPLUGIN_H
    
    #include "textimagehandler.h"
    
    #include <QTextStream>
    #include <QRegExp>
    #include <QImage>
    
    const char map[] =  " .:ilNAM";
    
    bool TextImageHandler::read(QImage *image)
    {
        QTextStream stream{device()};
        QString line = stream.readLine();
    
        if(line !=  "TEXT" || stream.status() != QTextStream::Ok) {
            return false;
        }
    
        line = stream.readLine();
    
         QRegExp re( R"(\d+)x(\d+)" );
         int width;
         int height;
         if(re.exactMatch(line)) {
    
             bool ok;
    
             width = re.cap(1).toInt(&ok);
             if(!ok) {
                 return false;
             }
    
             height = re.cap(2).toInt(&ok);
             if(!ok) {
                 return false;
             }
         }
         else{
             return false;
         }
    
    
         QImage result{width, height, QImage::Format_ARGB32};
         for( int y=0; y<height; ++y )
         {
             line = stream.readLine();
             if( line.length() != width )
                 return false;
    
             for( int x=0; x<width; ++x )
             {
                 switch( QString(map).indexOf(line[x]) )
                 {
                 case 0:
                     result.setPixel( x, y, 0xffffffff );
                     break;
                 case 1:
                     result.setPixel( x, y, 0xffdfdfdf );
                     break;
                 case 2:
                     result.setPixel( x, y, 0xffbfbfbf );
                     break;
                 case 3:
                     result.setPixel( x, y, 0xff9f9f9f );
                     break;
                 case 4:
                     result.setPixel( x, y, 0xff7f7f7f );
                     break;
                 case 5:
                     result.setPixel( x, y, 0xff5f5f5f );
                     break;
                 case 6:
                     result.setPixel( x, y, 0xff3f3f3f );
                     break;
                 case 7:
                     result.setPixel( x, y, 0xff000000 );
                     break;
                 default:
                     return false;
                 }
             }
         }
    
         if(stream.status() != QTextStream::Ok) {
             return false;
         }
         *image  = result;
         return true;
    }
    
    bool TextImageHandler::write(const QImage &image)
    {
        QTextStream stream{device()};
    
        stream << "TEXT\n";
        stream << image.width() << "x" << image.height() << "\n";
    
        for( int y=0; y<image.height(); ++y )
        {
            for( int x=0; x<image.width(); ++x )
            {
                QRgb rgb = image.pixel( x, y );
                int r = rgb & 0xff;
                int g = (rgb >> 8) & 0xff;
                int b = (rgb >> 16) & 0xff;
    
                stream << map[ 7 - (((r+g+b)/3)>>5) & 0x7 ];
            }
            stream << "\n";
        }
    
        if( stream.status() != QTextStream::Ok ) {
            return false;
        }
        return true;
    }
    
    bool TextImageHandler::canRead() const
    {
          return canRead( device() );
    }
    
    bool TextImageHandler::canRead(QIODevice *device)
    {
        if( device->peek(4) == "TEXT" ) {
            return true;
        }
    
        return false;
    }
    
    #include "textimageplugin.h"
    
    #include "textimagehandler.h"
    
    QStringList TextImagePlugin::keys() const
    {
        return QStringList{"ti"};
    }
    
    QImageIOPlugin::Capabilities TextImagePlugin::capabilities(
        QIODevice *device, const QByteArray &format) const
    {
        if(format == "ti") {
            return (QImageIOPlugin::CanRead | QImageIOPlugin::CanWrite);
        }
    
        if(!format.isEmpty()) {
            return nullptr;
        }
    
        if(!device->isOpen()) {
            return  nullptr;
        }
    
        QImageIOPlugin::Capabilities result;
    
        if(device->isReadable() && TextImageHandler::canRead(device)) {
            result |= QImageIOPlugin::CanRead;
        }
    
        if(device->isWritable()) {
            result |= QImageIOPlugin::CanWrite;
        }
        return result;
    }
    
    QImageIOHandler *TextImagePlugin::create(
        QIODevice *device, const QByteArray &format) const
    {
        auto result = new TextImageHandler{};
    
        result->setDevice(device);
        result->setFormat(format);
        return result;
    }
    
    {
      "Keys": [ "ti" ],
      "MimeTypes": [ "image/ti", "image/ti" ]
    }
    

    I generate a plugin file with adding install to make. It looks like this:

    Bibliothek "release\textimage1.lib" und Objekt "release\textimage1.exp" werden erstellt.
     copy /y release\textimage1.dll E:\Qt\5.12.2\msvc2017\plugins\imageformats\textimage1.dll
         1 Datei(en) kopiert.
    18:55:39: The process "E:\Qt\Tools\QtCreator\bin\jom.exe" exited normally.
    18:55:39: Elapsed time: 00:02.
    

    When i try to run a small sample programm the new ti format does not show up:

    #include <QApplication>
    
    #include <QImage>
    #include <QImageReader>
    #include <QByteArray>
    
    #include <QtDebug>
    
    int main( int argc, char **argv )
    { 
        QApplication app( argc, argv );
    
        for(const auto& supported : QImageReader::supportedImageFormats ()) {
            qDebug() << supported;
        }
    }
    
    18:51:03: Starting E:\Cpp_Projekte\QT\Foundations_of_QT\CH11_image_plugin\read\build-read-Desktop_Qt_5_12_2_MSVC2017_32bit-Debug\debug\read.exe ...
    "bmp"
    "cur"
    "gif"
    "icns"
    "ico"
    "jpeg"
    "jpg"
    "pbm"
    "pgm"
    "png"
    "ppm"
    "svg"
    "svgz"
    "tga"
    "tif"
    "tiff"
    "wbmp"
    "webp"
    "xbm"
    "xpm"
    18:51:04: E:/Cpp_Projekte/QT/Foundations_of_QT/CH11_image_plugin/read/build-read-Desktop_Qt_5_12_2_MSVC2017_32bit-Debug/debug/read.exe exited with code 0
    

    What can be wrong. I assumed generating the file under "Qt\5.12.2\msvc2017\plugins\imageformats" is correct?

    1 Reply Last reply
    0
    • SGaistS Offline
      SGaistS Offline
      SGaist
      Lifetime Qt Champion
      wrote on last edited by aha_1980
      #2

      Hi,

      Start your application with the QT_DEBUG_PLUGINS environment variable set to 1 to see what happens with your plugin.

      Interested in AI ? www.idiap.ch
      Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

      1 Reply Last reply
      3
      • Christian EhrlicherC Offline
        Christian EhrlicherC Offline
        Christian Ehrlicher
        Lifetime Qt Champion
        wrote on last edited by
        #3

        Apart from @SGaist 's answer - you can't mix debug and release plugins on windows. So either compile your testapp in release mode or your plugin as debug.

        Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
        Visit the Qt Academy at https://academy.qt.io/catalog

        1 Reply Last reply
        3
        • S Offline
          S Offline
          sandro4912
          wrote on last edited by
          #4

          I compiled both now as debug and enabled QT_DEBUG_PLUGINS. It gives me this output:

          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/styles/qwindowsvistastyled.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qgifd.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qicnsd.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qicod.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qjpegd.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qsvgd.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qtgad.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qtiffd.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qwbmpd.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qwebpd.dll" 
          QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/platforms/qwindowsd.dll" 
          

          It looks like my dll doesn't even get loaded but why is that so?

          The folder contains the file textimage1.dll which is supposed to be the plugin:

          0_1561233369247_ba7c8c52-5122-4725-9510-7c56d588b661-image.png

          1 Reply Last reply
          0
          • Christian EhrlicherC Offline
            Christian EhrlicherC Offline
            Christian Ehrlicher
            Lifetime Qt Champion
            wrote on last edited by
            #5

            There must be also an output during startup - you only pasted the stuff during shutdown...

            Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
            Visit the Qt Academy at https://academy.qt.io/catalog

            1 Reply Last reply
            1
            • S Offline
              S Offline
              sandro4912
              wrote on last edited by sandro4912
              #6

              I get this error on startup:

              
              "The plugin 'E:/Qt/5.12.2/msvc2017/plugins/imageformats/textimage1.dll' uses incompatible Qt library. (Cannot mix debug and release libraries.)" 
                       not a plugin
              QFactoryLoader::QFactoryLoader() checking directory path "E:/Cpp_Projekte/QT/Foundations_of_QT/CH11_image_plugin/read/build-read-Desktop_Qt_5_12_2_MSVC2017_32bit-Debug/debug/imageformats" ...
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qgifd.dll"
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qicnsd.dll"
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qicod.dll"
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qjpegd.dll"
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qsvgd.dll"
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qtgad.dll"
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qtiffd.dll"
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qwbmpd.dll"
              loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qwebpd.dll"
              

              I build the plugin and the project with MSVC2017 32 Bit Debug to get the Debug Output. There should not be a mix?

              The output of the plugin file looks like this:

              22:57:44: Running steps for project image_plugin...
              22:57:44: Configuration unchanged, skipping qmake step.
              22:57:44: Starting: "E:\Qt\Tools\QtCreator\bin\jom.exe" install
              	E:\Qt\Tools\QtCreator\bin\jom.exe -f Makefile.Release install
              	copy /y release\textimage1.dll E:\Qt\5.12.2\msvc2017\plugins\imageformats\textimage1.dll
                      1 Datei(en) kopiert.
              22:57:44: The process "E:\Qt\Tools\QtCreator\bin\jom.exe" exited normally.
              22:57:44: Elapsed time: 00:00.
              
              1 Reply Last reply
              0
              • Christian EhrlicherC Offline
                Christian EhrlicherC Offline
                Christian Ehrlicher
                Lifetime Qt Champion
                wrote on last edited by
                #7

                @sandro4912 said in QImageIOPlugin doesn't work:

                copy /y release\textimage1.dll E:\Qt\5.12.2\msvc2017\plugins\imageformats\textimage1.dll

                This does not look like a debug build.

                Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
                Visit the Qt Academy at https://academy.qt.io/catalog

                1 Reply Last reply
                3
                • SGaistS Offline
                  SGaistS Offline
                  SGaist
                  Lifetime Qt Champion
                  wrote on last edited by
                  #8

                  Your plugin is named: textimage1.dll It is missing the d suffix for your debug build.

                  You can use TARGET = $$qtLibraryTarget(textimage)

                  Interested in AI ? www.idiap.ch
                  Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                  1 Reply Last reply
                  2
                  • S Offline
                    S Offline
                    sandro4912
                    wrote on last edited by
                    #9

                    Than i wonder why it is not build as debug.

                    I clearly select debug and then build:

                    0_1561275497852_958750a2-35c8-4131-bb00-c2b24a1eb0fb-image.png

                    The build settings for debug:

                    0_1561275704127_5d06df1a-fa93-4f74-b158-600fdf3aff97-image.png

                    I already removed the release flag from CONFIG so it should not get forced into release or should it?

                    TEMPLATE = lib
                    CONFIG += plugin
                    TARGET = $$qtLibraryTarget(textimage)
                    VERSION = 1.0.0
                    
                    HEADERS += \
                        textimagehandler.h \
                        textimageplugin.h
                    
                    SOURCES += \
                        textimagehandler.cpp \
                        textimageplugin.cpp
                    
                    target.path += $$[QT_INSTALL_PLUGINS]/imageformats
                    INSTALLS += target
                    
                    DISTFILES += \
                        textimageplugin.json
                    

                    What does TARGET = $$qtLibraryTarget(textimage) do? why is it needed?

                    aha_1980A 1 Reply Last reply
                    0
                    • S sandro4912

                      Than i wonder why it is not build as debug.

                      I clearly select debug and then build:

                      0_1561275497852_958750a2-35c8-4131-bb00-c2b24a1eb0fb-image.png

                      The build settings for debug:

                      0_1561275704127_5d06df1a-fa93-4f74-b158-600fdf3aff97-image.png

                      I already removed the release flag from CONFIG so it should not get forced into release or should it?

                      TEMPLATE = lib
                      CONFIG += plugin
                      TARGET = $$qtLibraryTarget(textimage)
                      VERSION = 1.0.0
                      
                      HEADERS += \
                          textimagehandler.h \
                          textimageplugin.h
                      
                      SOURCES += \
                          textimagehandler.cpp \
                          textimageplugin.cpp
                      
                      target.path += $$[QT_INSTALL_PLUGINS]/imageformats
                      INSTALLS += target
                      
                      DISTFILES += \
                          textimageplugin.json
                      

                      What does TARGET = $$qtLibraryTarget(textimage) do? why is it needed?

                      aha_1980A Offline
                      aha_1980A Offline
                      aha_1980
                      Lifetime Qt Champion
                      wrote on last edited by
                      #10

                      @sandro4912

                      Your plugin is named: textimage1.dll It is missing the d suffix for your debug build.

                      On Windows, the library must be called textimage1d.dll if it is a debug version. The reason was already explained above: On Windows, you cannot mix debug and release objects.

                      Qt has to stay free or it will die.

                      1 Reply Last reply
                      2
                      • S Offline
                        S Offline
                        sandro4912
                        wrote on last edited by
                        #11

                        Ok but were do i change the name with the d suffix? In the pro file? Or can i just rename it manually?

                        1 Reply Last reply
                        0
                        • Christian EhrlicherC Offline
                          Christian EhrlicherC Offline
                          Christian Ehrlicher
                          Lifetime Qt Champion
                          wrote on last edited by
                          #12

                          @sandro4912 said in QImageIOPlugin doesn't work:

                          Ok but were do i change the name with the d suffix? In the pro file? Or can i just rename it manually?

                          Simply read @SGaist 's answer: 'You can use TARGET = $$qtLibraryTarget(textimage)'

                          Qt Online Installer direct download: https://download.qt.io/official_releases/online_installers/
                          Visit the Qt Academy at https://academy.qt.io/catalog

                          1 Reply Last reply
                          2
                          • S Offline
                            S Offline
                            sandro4912
                            wrote on last edited by
                            #13

                            I added the target but it doesn't seem to add the d suffix to make it debug:

                            TEMPLATE = lib
                            CONFIG += plugin
                            VERSION = 1.0.0
                            
                            HEADERS += \
                                textimagehandler.h \
                                textimageplugin.h
                            
                            SOURCES += \
                                textimagehandler.cpp \
                                textimageplugin.cpp
                            
                            TARGET = $$qtLibraryTarget(textimage)
                            target.path += $$[QT_INSTALL_PLUGINS]/imageformats
                            INSTALLS += target
                            
                            DISTFILES += \
                                textimageplugin.json
                            
                            1 Reply Last reply
                            0
                            • SGaistS Offline
                              SGaistS Offline
                              SGaist
                              Lifetime Qt Champion
                              wrote on last edited by
                              #14

                              Did you re-run qmake after changing the TARGET value ?

                              Interested in AI ? www.idiap.ch
                              Please read the Qt Code of Conduct - https://forum.qt.io/topic/113070/qt-code-of-conduct

                              1 Reply Last reply
                              1
                              • S Offline
                                S Offline
                                sandro4912
                                wrote on last edited by sandro4912
                                #15

                                Ok i guess i forgot to rerun it. Now i could generate the debug files.

                                When running my testprogram with debug it stills fails but the message is different

                                Got keys from plugin meta data ()
                                QFactoryLoader::QFactoryLoader() checking directory path "E:/Cpp_Projekte/QT/Foundations_of_QT/CH11_image_plugin/read/build-read-Desktop_Qt_5_12_2_MSVC2017_32bit-Debug/debug/imageformats" ...
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qgifd.dll"
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qicnsd.dll"
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qicod.dll"
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qjpegd.dll"
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qsvgd.dll"
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qtgad.dll"
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qtiffd.dll"
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qwbmpd.dll"
                                loaded library "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qwebpd.dll"
                                "bmp"
                                "cur"
                                "gif"
                                "icns"
                                "ico"
                                "jpeg"
                                "jpg"
                                "pbm"
                                "pgm"
                                "png"
                                "ppm"
                                "svg"
                                "svgz"
                                "tga"
                                "tif"
                                "tiff"
                                "wbmp"
                                "webp"
                                "xbm"
                                "xpm"
                                Failed to load.
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/styles/qwindowsvistastyled.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qgifd.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qicnsd.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qicod.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qjpegd.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qsvgd.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qtgad.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qtiffd.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qwbmpd.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/imageformats/qwebpd.dll" 
                                QLibraryPrivate::unload succeeded on "E:/Qt/5.12.2/msvc2017/plugins/platforms/qwindowsd.dll"
                                

                                let me know if you need more information...

                                1 Reply Last reply
                                0

                                • Login

                                • Login or register to search.
                                • First post
                                  Last post
                                0
                                • Categories
                                • Recent
                                • Tags
                                • Popular
                                • Users
                                • Groups
                                • Search
                                • Get Qt Extensions
                                • Unsolved