QFrame with background image and otherwise transparent background

7.1k views Asked by At

I am making a desktop carousel app. There I need to show image widgets, which might contain other sub-widgets as well. For that I am using a QFrame with the required image as background. Here is the image I am trying to use: image link. What I want is that only the image shows up, no background image or anything shows up as well, so to the user it looks like just the image. Here is my code:

setGeometry(QRect(100, 20, 325,400));
setFrameStyle(QFrame::StyledPanel);
setStyleSheet("QFrame#ImageFrame { background-color: transparent; background: url(:icon/ipad-skin); }");
setAutoFillBackground(false);

However, I am getting this as a result:

enter image description here

I tried this as well (obtained from here) (and removing the stylesheet):

void MyWidget::paintEvent(QPaintEvent *p)
{
    QPainter* pPainter = new QPainter(this);
    pPainter->drawPixmap(rect(), QPixmap(":icon/newskin.png"));
    delete pPainter;
    QWidget::paintEvent(p);
}

Nothing different, the exact same result. The greyness of the background still shows.

How do I make the grey background of the QFrame go and display only the image (the dimensions I am setting are the same as the image)?

P.S I am aware that similar questions hve been answered here: QWidget transparent background (but not the children), and here: Frameless and transparent window qt5 but these doesn't solve my problem. The last solution makes my QFrame look like this:

enter image description here

The QFrame now comes with a title bar which is anything but what I wanted in the first place.

Edit - This solution works, but in my use-case, I need to display an image that is rendered via GL inside the QFrame (specifically, in the viewport within the iPad image we can see here). In Windows, setting the Qt::WA_TranslucentBackground property makes that GL-rendered image invisible. It works fine in Mac, though. So I am looking for a solution which will work in Windows as well.

2

There are 2 answers

7
Jeremy Friesner On BEST ANSWER

This code works for me (tested under MacOS/X 10.10.3, using Qt 5.5.0-beta; I'd expect it to work under any Qt version 4.5.0 or higher though):

main.h:

#ifndef main_h
#define main_h

#include <QFrame>
#include <QPixmap>

class MyFrame : public QFrame
{
public:
   MyFrame(QWidget * parent);

   virtual void paintEvent(QPaintEvent * e);

private:
   QPixmap _pixmap;
};

#endif

main.cpp:

#include <QApplication>
#include <QPainter>
#include "main.h"

MyFrame :: MyFrame(QWidget * parent) : QFrame(parent, Qt::Window|Qt::FramelessWindowHint)
{
   setAttribute(Qt::WA_TranslucentBackground);

   _pixmap.load("/Users/jaf/iPad_Vector.png");
   resize(_pixmap.size());
}

void MyFrame :: paintEvent(QPaintEvent * /*e*/)
{
   QPainter p(this);
   p.drawPixmap(0,0,width(),height(), _pixmap);
}

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

   MyFrame f(NULL);
   f.show();

   return app.exec();
}

Screenshot (showing the app's window in front of my desktop background):

screenshot

3
fjardon On

Can you try this light modification to your code ?

In case it doesn't work can you publish your compilable code on a public repository ? This would help reproduce in your exact context.

void MyWidget::paintEvent(QPaintEvent *p)
{
    QPainter* pPainter = new QPainter(this);
    pPainter->setBackgroundMode(Qt::TransparentMode);
    pPainter->drawPixmap(rect(), QPixmap(":icon/newskin.png"));
    delete pPainter;
    QWidget::paintEvent(p);
}