Page 1 of 1

[SOLVED] Converting Magick::Image <-> QImage (Qt4).

Posted: 2008-12-28T06:18:52-07:00
by adrian5632
Hi!
I need to convert an image from and to YUV (YCbCr) color space to use it with the ogg theora library. But before I pass the YUV image to theora I need to do some operations on image in form of a QImage object. I found an example class: http://lists.trolltech.com/qt-interest/ ... 494-0.html and transformed two its methods to a global functions: QImage* toQImage() and Image* toImage(). Everything works until I use the "YCbCr" magick. But without using the magick it is useless - because I need a YUV data. If I read a yuv image from file directly to the Image object and use the "YCbCr" magick - it works fine. I'm very confused... Here is the code of the main.cpp and the Qt's project file:

main.cpp:

Code: Select all

#include <QtGui>
#include <Magick++.h>

using namespace Magick;

QImage* toQImage(Image &image);
Image*  toImage(QImage &qimage);

void test1();
void test2();
void test3();

QImage* toQImage(Image &image)
{
    qDebug() << "toQImage:" << image.columns() << image.rows();

    QImage *newQImage = new QImage(image.columns(), image.rows(), QImage::Format_RGB32);
    const Magick::PixelPacket *pixels;
    Magick::ColorRGB rgb;
    for (int y = 0; y < newQImage->height(); y++) {
        pixels = image.getConstPixels(0, y, newQImage->width(), 1);
        for (int x = 0; x < newQImage->width(); x++) {
            rgb = (*(pixels + x));
            newQImage->setPixel(x, y, QColor((int) (255 * rgb.red())
                                             , (int) (255 * rgb.green())
                                             , (int) (255 * rgb.blue())).rgb());
        }
    }
    return newQImage;
}


Image* toImage(QImage& qimage)
{
    qDebug() << "toImage:" << qimage.width() << qimage.height();

    Image *newImage = new Image(Magick::Geometry(qimage.width(), qimage.height()), Magick::ColorRGB(0.5, 0.2, 0.3));

    double scale = 1 / 256.0;
    newImage->modifyImage();
    Magick::PixelPacket *pixels;
    Magick::ColorRGB mgc;
    for (int y = 0; y < qimage.height(); y++) {
        pixels = newImage->setPixels(0, y, newImage->columns(), 1);
        for (int x = 0; x < qimage.width(); x++) {
            QColor pix = qimage.pixel(x, y);
            //      *pixels++ = Magick::ColorRGB(256 * pix.red(), 256 * pix.green(), 256 * pix.blue());
            mgc.red(scale *pix.red());
            mgc.green(scale *pix.green());
            mgc.blue(scale *pix.blue());
            //      *pixels++ = Magick::ColorRGB(scale *pix.red(), scale * pix.green(), scale * pix.blue());
            *pixels++ = mgc;
        }
        newImage->syncPixels();
    }

    return newImage;
}

void test1() //works fine
{
    Image aMagickImage("/home/adrian/zrzut.png"); //it's a 1280x800 image
    QImage *aQImage = toQImage(aMagickImage);

    QLabel label;
    label.setPixmap(QPixmap::fromImage(*aQImage)); //set pixmap from image;
    label.show();

    qApp->exec();//loop is exited after closing the label's window
    delete aQImage;
}

void test2()//also works fine
{
    QImage aQImage("/home/adrian/zrzut.png");
    Image *aMagickImage = toImage(aQImage);

    QImage *anotherQImage = toQImage(*aMagickImage);
    delete aMagickImage;

    QLabel label;
    label.setPixmap(QPixmap::fromImage(*anotherQImage)); //set pixmap from image;
    label.show();

    qApp->exec();//loop is exited after closing the label's window
    delete anotherQImage;
}

void test3()//works not so fine...
{
    QImage aQImage("/home/adrian/zrzut.png");
    Image *aMagickImage = toImage(aQImage);
    aMagickImage->magick("YCbCr");//because I need to process a YUV data in my app

    Blob aBlob;
    aMagickImage->write(&aBlob);
    //I'm gonna use the blob's data in theora

    delete aMagickImage;
    aMagickImage = new Image(aBlob, Geometry(aQImage.width(), aQImage.height()), "RGB");

    QImage *anotherQImage = toQImage(*aMagickImage);//new QImage is a plain blue image :/
    delete aMagickImage;                            //I don't know what magic should I use


    QLabel label;
    label.setPixmap(QPixmap::fromImage(*anotherQImage)); //set pixmap from image;
    label.show();

    qApp->exec();//loop is exited after closing the label's window
    delete anotherQImage;
}

int main(int argc, char *argv[])
{
    QApplication app(argc, argv);

    test1();
    test2();
    test3();

    return 0;
}
ImageTest.pro:

Code: Select all

TARGET = ImageTest
CONFIG   += console
CONFIG   -= app_bundle
TEMPLATE = app
SOURCES += main.cpp
LIBS += -L/usr/lib \
    -lMagick++ \
    -lWand \
    -lMagick

Re: Converting Magick::Image <-> QImage (Qt4).

Posted: 2008-12-28T11:31:41-07:00
by adrian5632
UPDATE
This version of the test3() function works but writing three times to a blob is veeeery slow. I don't know what's the problem.

Code: Select all

void test3()
{
    QImage aQImage("/home/adrian/zrzut.png");
    Image *aMagickImage = toImage(aQImage);

    Blob aBlob;
    aMagickImage->write(&aBlob, "PNG");
    delete aMagickImage;

    aMagickImage = new Image(aBlob, Geometry(aQImage.width(), aQImage.height()), "PNG");
    aMagickImage->write(&aBlob, "YCbCr");
    delete aMagickImage;

    aMagickImage = new Image(aBlob, Geometry(aQImage.width(), aQImage.height()), "YCbCr");
    aMagickImage->write(&aBlob, "PNG");
    delete aMagickImage;

    aMagickImage = new Image(aBlob, Geometry(aQImage.width(), aQImage.height()), "PNG");


    QImage *anotherQImage = toQImage(*aMagickImage);
    delete aMagickImage;

    QLabel label;
    label.setPixmap(QPixmap::fromImage(*anotherQImage)); //set pixmap from image;
    label.show();

    qApp->exec();//loop is exited after closing the label's window
    delete anotherQImage;
}

Re: Converting Magick::Image <-> QImage (Qt4).

Posted: 2008-12-28T13:52:22-07:00
by adrian5632
Solved! The problem was in the image's depth and type which I had to set to 8 and TrueColorMatteType.