QLinearGradient not working

Hi @ all

I tried to add a QLinearGradient in my qt-program, but after porting to QNX there is no gradient…
The color is displayed, but it is just switching from black to blue without changes in between.
So I am wondering: Is a Gradient from qt not possible in QNX? What is the requirement for using a gradient? (like some specific module, or a library?)

EDIT:

I played a bit around and this is the initialisation:

    gradient = new QLinearGradient(0,scene->sceneRect().top(), 0, scene->sceneRect().bottom());
    gradient->setColorAt(0, QColor(Qt::darkBlue));  
    gradient->setColorAt(0.3, QColor(Qt::black));
    gradient->setColorAt(0.7, QColor(Qt::black));
    gradient->setColorAt(1, QColor(Qt::darkBlue));
    brushBlue = new QBrush(*gradient);

    gradientRed = new QLinearGradient(0,scene->sceneRect().top(), 0, scene->sceneRect().bottom());
    gradientRed->setColorAt(0, QColor(Qt::darkRed)); 
    gradientRed->setColorAt(0.3, QColor(Qt::black));
    gradientRed->setColorAt(0.7, QColor(Qt::black));
    gradientRed->setColorAt(1, QColor(Qt::darkRed));
    brushRed = new QBrush(*gradientRed);

I set it on different times in my code with:

view->setBackgroundBrush(*brushBlue);

Now the interesting this is:
The Brsuh with the blue gradient is not working (clear cut between the colors), but the Red Brush is working.
Any idea why?

And how can I change the resolution for the gradient? Because I can see the lines from the gradient and this doesn´t look so good…

EDIT 2:

after some changes with the color (darkBlue to black, darkRed to black, darkGreen to black) I found some differences in the resolution or “steps” to change the color.
darkBlue → black: 1 step. either black or blue
darkRed → black: around 13 steps. you can still see the changes with some cuts
darkGreen → black: around 40 or 50 steps. you can still see the changes but looks better

What could be the reason for this? It looks like that it is possible for the BeagleBoard and QNX to make a gradient, but why so different for different colors???

I also tried with different colors and not only the “dark”-variants, but blue is still the looser (3 steps) and yellow, green and red have the most steps.

The QNX specific Qt code merely blits data from a Qt buffer to the hardware buffer. There could be a video mode issue, or a Qt problem. What version of Qt are you using? If it is the 4.7 QNX port, I’d be willing to try the code for you on 4.8.2 if you will post it.

I use Qt 4.7.1 for QNX.
I cannot post the code, because I make this program for my thesis.
And it is already too much code for posting (But thanks alot for the offer :slight_smile: )

On my win8-machine I use Qt 4.7.4 with MinGW and it is working. So does this hint to a video mode issue on the QNX machine?
If so I will try to contact Dennis on Foundry27 (he made the demo-OS I use as a basis on my beagleboard)

If you don’t want to post the entire code, I would try creating a small program that just shows the problem. If you contact Dennis, he will probably want something like this anyway.

True :smiley:
I will try to make one

EDIT: — deleted—

Ok, here is the minimal program with the basic architecture I am using. After building in Momentics and porting to BeagleBoard-xM I get the same problem → gradient is not working well/correct.

The kommunikation class is for the communication with the rs232 interface which I use to read data from my laptop. This class is running in a seperate thread.
For the communication I send first a value for the switch-loop (“100” in this case) and then the value (for design change “0” and “1” at the moment).
This value is then emitted via a signal to the main-thread and received from the function “setDesign()” in controller.cpp

main.cpp

#include "controller.h"

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    Controller *control = new Controller;
    control->view->show();
    return a.exec();
}

controller.h

#ifndef CONTROLLER_H
#define CONTROLLER_H

#include <QWidget>
#include <QtGui/QApplication>
#include <QtGui/QGraphicsView>
#include <QThread>
#include <QtCore>
#include "kommunikation.h"

class GraphicsView : public QGraphicsView
{
public:
    GraphicsView(QGraphicsScene *scene) : QGraphicsView(scene)
    {}
protected:
    virtual void resizeEvent(QResizeEvent *event)
    {}
};

//------------------------------------------------------------------
//------------------------------------------------------------------
class Controller  : public QWidget
{
    Q_OBJECT
public:
    explicit Controller(QWidget *parent = 0);
    GraphicsView *view;
    Kommunikation *worker;

public slots:
	void setDesign(int);

private:
    QGraphicsScene *scene;
    QThread *thread;
    int design;
    QLinearGradient *gradient;
    QBrush *brushBlue;
    QLinearGradient *gradientRed;
    QBrush *brushRed;
};
#endif // CONTROLLER_H

controller.cpp

#include "controller.h"

Controller::Controller(QWidget *parent) :
    QWidget(parent), design(0)
{
    scene = new QGraphicsScene(-400, -300, 800, 600);
    view = new GraphicsView(scene);
    thread = new QThread();
    worker = new Kommunikation();

    view->setRenderHint(QPainter::Antialiasing);
    view->setBackgroundBrush(QBrush(Qt::black));
    view->setFrameStyle(QFrame::NoFrame);
    view->showFullScreen();

    gradient = new QLinearGradient(0,scene->sceneRect().top(), 0, scene->sceneRect().bottom());
    gradient->setColorAt(0, QColor(Qt::darkBlue));
    gradient->setColorAt(0.3, QColor(Qt::black));
    gradient->setColorAt(0.7, QColor(Qt::black));
    gradient->setColorAt(1, QColor(Qt::darkBlue));
    brushBlue = new QBrush(*gradient);

    gradientRed = new QLinearGradient(0,scene->sceneRect().top(), 0, scene->sceneRect().bottom());
    gradientRed->setColorAt(0, QColor(Qt::darkRed));
    gradientRed->setColorAt(0.3, QColor(Qt::black));
    gradientRed->setColorAt(0.7, QColor(Qt::black));
    gradientRed->setColorAt(1, QColor(Qt::darkRed));
    brushRed = new QBrush(*gradientRed);

    setDesign(0);

    worker->moveToThread(thread);

        QObject::connect(thread, SIGNAL(started()), worker, SLOT(process()));
        QObject::connect(worker, SIGNAL(finished()), thread, SLOT(quit()));
        QObject::connect(worker, SIGNAL(finished()), worker, SLOT(deleteLater()));
        QObject::connect(thread, SIGNAL(finished()), thread, SLOT(deleteLater()));
        QObject::connect(worker, SIGNAL(setDesign(int)), this, SLOT(setDesign(int)));

    thread->start();
}

void Controller::setDesign(int b)
{
		design = b;
		    switch(design)
		    {
		      case 0:
		    	  view->setBackgroundBrush(*brushBlue);
		         break;
		      case 1:
		    	  view->setBackgroundBrush(*brushRed);
		         break;
		    }
		     scene->update();
}

kommunikation.h

#ifndef KOMMUNIKATION_H
#define KOMMUNIKATION_H

#include <QObject>
#include <QDebug>
#include <termios.h>
#include <fcntl.h>
#include <string.h>
#include <process.h>
#include <stddef.h>
#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/neutrino.h>

class Kommunikation : public QObject
{
    Q_OBJECT
public:

    Kommunikation();
    ~Kommunikation();

public slots:
    int portInit();
    void process();

signals:
    void finished();
    void eror(QString er);
    void setDesign(int);

private:
    int choice;
    int value;
    int count;
    int speed;
    int fd; 
    char data[3];  
    char intArr[4]; 
    int intData;
    struct termios raw;
};

#endif // KOMMUNIKATION_H

kommunikation.cpp

#include "kommunikation.h"

Kommunikation::Kommunikation()
{}

Kommunikation::~Kommunikation()
{}

int Kommunikation::portInit()
{
        //---------------------------------------------------
        //---------------------------------------------------
            // Open the port
            if ((fd = open ("/dev/ser1", O_RDWR)) == -1)
            {
                   fprintf(stderr, "Error with open() on /dev/ser1. Make sure exists.\n");
                   perror (NULL);
                   exit(EXIT_FAILURE);
            }

            // Get the attributes
            if (tcgetattr( fd, &raw))
            {
                   close( fd );
                   return -1;
            }

            // Set input baud rate
            speed = B115200;
            cfsetispeed(&raw, speed);//inputspeed
            cfsetospeed(&raw, speed);//outputspeed

            raw.c_iflag &= ~(BRKINT | ICRNL | INPCK | ISTRIP | IXON );
	    raw.c_oflag &= ~(OPOST);
            raw.c_cflag &= ~(CSIZE|IHFLOW|OHFLOW);
            raw.c_cflag |= CS8 | CREAD | CLOCAL;
            raw.c_cflag &= ~CSTOPB;
            raw.c_cflag &= ~PARENB;

            raw.c_lflag &= ~(ECHO | ICANON | ISIG | ECHOE | ECHOK | ECHONL | IEXTEN);

            raw.c_cc[VMIN] =  1;
            raw.c_cc[VTIME] = 0;

            if ( tcsetattr( fd, TCSADRAIN, &raw ) == -1 )   // CHECK FOR -1 failure here - this is the actual "set" and it must succeed on nothing may have changed
            {
                   fprintf(stderr, "Error with tcsetattr() on /dev/ser1.\n");
                   perror (NULL);
                   exit(EXIT_FAILURE);
            }
            return fd;
}

void Kommunikation::process()
{

    choice = 0;
    value = 0;
    count = 0;
    fd = 0;

	  fd = portInit();

    while(1)
    {
        for(int i = 0; i < sizeof(data); i++)
        {data[i] = 0;}

        for(int i = 0; i < sizeof(intArr); i++)
        {intArr[i] = 0;}

        count = read(fd, data, 3);

        if(data[1] == 0){value = ((int)data[2]);}
        if(data[1] == 1){value = ((int)data[2]) + 127;}
        if(data[1] == 2){value = ((int)data[2]) + 254;}
        if(data[1] == 3){value = ((int)data[2]) + 381;}
        if(data[1] == 4){value = ((int)data[2]) + 508;}
        if(data[1] == 5){value = ((int)data[2]) + 635;}
        if(data[1] == 6){value = ((int)data[2]) + 762;}
        if(data[1] == 7){value = ((int)data[2]) + 889;}
        if(data[1] == 8){value = ((int)data[2]) + 1016;}

        switch(value)
        {
        case 100:
        	count = read(fd, intArr, 2);
            if(intArr[0] == 0){intData = ((int)intArr[1]);}
            if(intArr[0] == 1){intData = ((int)intArr[1]) + 127;}
        	emit setDesign(intData);
        	break;
        }
    }
}

Disclaimer, I did not look at the details of your code.

I compiled it on my 6.5 system using Qt 4.8.2. I ran the code in two modes,

  1. Natively without Photon running
  2. With Photon running using my phqt program

In both cases I saw a blank screen with a gradient that started on the top dark blue, became black in the center and then became dark blue on the bottom again.
I’ve attached a .jpg with a screen dump.

Assuming that this is what you wanted, there are two possible explainations.

  1. There’s been a bug fix since 4.7.
  2. Our hardware is different, and Qt works properly on mine, but not yours.

Could the “failure” be to lack of color depth? Mitchell’s desktop 24bit RGB, beagleXM 16bit RGB?

Dennis,

You got me curious about this.   The original version of my phqt program had 32 bit hard coded.   I tried running the program with Photon in a 16 bit mode.   This worked, but all it proved was that Photon properly blits a 32 bit image to a 16 bit graphic mode.     So I upgraded the rest of the software so I could run the Qt program in 16 bit also.   It appears to continue to work.   I'm uploading the screen dump.   If you look very carefully, you can see that the color changes are a little bit coarser than they were in 32 bit mode.

So if there is a problem with 16 bit, it was fixed by 4.8.2.

Mitchell

the color changes are a little bit coarser than they were in 32 bit mode.
Good. So its working as expected.

Let me add, if you’d like to try 4.8.2, I can provide the changes to allow it to compile under 6.5 for x86.

Mitchell

Thx for the tests :slight_smile:
It is indeed what I wanted to display.

I already have a library for 4.8.2 armv7

and some other binaries from
http://community.qnx.com/sf/discussion/do/listPosts/projects.qt/discussion.general.topc21389;jsessionid=E3FA15D8974480409CD820E640DC7374?pageSize=-1#post_post91093
but I am still a beginner with QNX and I don´t know what to do with these files…

What I already tried:

  • copy files an binaries to \QNX650\target\qnx6\armle-v7\usr\lib and compile a qt4.8 program → “make” command is not working because of some missing references
  • copy only the lib-files to the path → makefile after “make”-command indicates that it is still qt4.7
    (“make” command with the provided qmake_qnx-file found on foundry27)