PDA

View Full Version : A very difficult animation problem...can Qt4 solve it?



nupul
1st April 2006, 16:04
Does Qt have a solution for THIS!!!

Say i have a widget window that displays an image of a butterfly. When

the user clicks on this butterfly, it dipatches it self from its

position and moves all over the screen being, sheared/scales/rotated in

a predefined/random path - could be as simple as just moving along the

borders of the screen, or diagonally across and back, like a slash '/'

Thus, the butterfly "leaves" its parent window and moves over other

windows/desktop etc before settling back in its parent window.

Is this possible using the very robust Paint Engine of Qt?!?!?!

Will this solution be platform dependent? If so, I'd prefer to know how

to achieve the same in Linux/X and windows!!

Thanks.

Nupul.

God bless the one to help me with this...

jacek
1st April 2006, 16:07
Try painting on QApplication::desktop().

wysota
1st April 2006, 16:30
Or animate a widget without background over your desktop. Qt Quarterly issue 16 shows how to achieve widgets with transparent background (http://doc.trolltech.com/qq/qq16-background.html).

BTW. Painting on the desktop widget in Qt4 may not be possible (or at least easy) due to the nature of the paint engine present since Qt 4.1.

jacek
1st April 2006, 16:36
BTW. Painting on the desktop widget in Qt4 may not be possible (or at least easy) due to the nature of the paint engine present since Qt 4.1.
Why should painting on QDesktopWidget be different than painting on QWidget? It just might not work on all systems.

wysota
1st April 2006, 16:51
Qt 4.1 introduces the "backing store" which holds a copy of the widget in memory. It would require to hold a copy of the desktop itself to do it (do window managers allow painting outside windows?). But I think the backing store can be disabled.

I've been trying to get a transparent widget, but I can't manage to do it. Either my system doesn't support it (which it should) or I simply don't know how to do it.

jacek
1st April 2006, 16:52
I've been trying to get a transparent widget, but I can't manage to do it. Either my system doesn't support it (which it should) or I simply don't know how to do it.
But it doesn't mean that painting on a particular widget should be harder than on other widgets.

wysota
1st April 2006, 17:10
Well, I seem not to be able to paint on it using such a test program:


#include <QApplication>
#include <QDesktopWidget>
#include <QPainter>

int main(int argc, char **argv){
QApplication app(argc, argv);
QDesktopWidget *dw = app.desktop();
dw->setAttribute(Qt::WA_PaintOutsidePaintEvent);
QPainter p(dw);
p.drawLine(0,0,dw->width(), dw->height());
return app.exec();
}

An alternative would be to catch a paintEvent for it, but I doubt it gets any paint events :)

I managed to get a transparent top-level widget using the Qt::WA_PaintOnScreen attribute combined with other attributes but the drawback is that the background under the widget is not refreshed if it changes, so one would have to do that manually (somehow).

Chicken Blood Machine
1st April 2006, 22:08
Well, I seem not to be able to paint on it using such a test program:


#include <QApplication>
#include <QDesktopWidget>
#include <QPainter>

int main(int argc, char **argv){
QApplication app(argc, argv);
QDesktopWidget *dw = app.desktop();
dw->setAttribute(Qt::WA_PaintOutsidePaintEvent);
QPainter p(dw);
p.drawLine(0,0,dw->width(), dw->height());
return app.exec();
}

An alternative would be to catch a paintEvent for it, but I doubt it gets any paint events :)

I managed to get a transparent top-level widget using the Qt::WA_PaintOnScreen attribute combined with other attributes but the drawback is that the background under the widget is not refreshed if it changes, so one would have to do that manually (somehow).


You can always use the old setMask() trick, which may not be as fast/elegant, but it certainly works everywhere!

wysota
1st April 2006, 23:11
You can always use the old setMask() trick, which may not be as fast/elegant, but it certainly works everywhere!

The thing is I tried and it didn't work and I don't know why. Does it work in Qt4 with top-level widgets? Could you provide a sample code which does that? I tried something like that and it didn't work:


QBitmap bitmap;
bitmap.clear(); // does it set bits to 0 or 1?
setMask(bitmap);

I could still paint the widget.

Chicken Blood Machine
1st April 2006, 23:21
I can confirm that this works on Suse 10and Windows XP (Qt 4.1.1):


sms::PhoneWidget::PhoneWidget(QWidget* parent) :
QWidget(parent, Qt::Window | Qt::FramelessWindowHint)
{
QPixmap pixmap(":/john_phone.png");
resize(pixmap.size());

QPalette p(palette());
p.setBrush(QPalette::Window, QBrush(pixmap));
setPalette(p);
setMask(pixmap.mask());
}

wysota
2nd April 2006, 00:51
Works for me too, although the pixmap is very aliased. I must have set wrong flags before or in a wrong place.

nupul
3rd April 2006, 05:25
what are the above codes by wysota and CBM are achieving?

How does it help in answering the query i put forth??

(not being rude...i am not able to comprehend the fact, that's all

Thanks

Nupul

Chicken Blood Machine
3rd April 2006, 06:11
what are the above codes by wysota and CBM are achieving?

How does it help in answering the query i put forth??

(not being rude...i am not able to comprehend the fact, that's all

Thanks

Nupul

It achieves displaying an irregular (non-square) widget on the desktop - like the butterfy that you described. Why don't you try it and see for yourself?