animation of widget
-
I am a beginner in qt
and I want to create a animation of a widget. like when the mouse press on widget show some animation(change the pic)
using timer or propertyAnimation to do with that and workbut i want to make the widget not a part of mainwindow(a new window).
so i do something like this//ignore the memory leak, it just a sample AnimateWidget aniWidget = new AnimateWidget(); aniWidget.show();
if dont set the parent widget, the animation lag,and the whole desktop being lag too.
and I want to know what happen and whyany suggestion?
forgive for bad English~~
-
Hi and welcome to devnet,
Which version of Qt ?
On which OS ?
Can you provide a minimal compilable example that shows this behaviour ? -
Hi and welcome to devnet,
Which version of Qt ?
On which OS ?
Can you provide a minimal compilable example that shows this behaviour ?is Qt 5.9 on linux
what i do is:
1.create a widget with only a QLabel(use to load a .png file)
2.use QTimer or propertyAnimation to change the .png in a high frequently(30ms)
there is a sample code below:AnimateWidget::AnimateWidget (QWidget *parent) : QWidget(parent) { setWindowFlags(Qt::FramelessWindowHint); setAttribute(Qt::WA_TranslucentBackground); picTotal = 50; picLabel = new QLabel(this); layout = new QStackedLayout(this); layout->addWidget(picLabel); setLayout(layout); initPicList(); initPic(); initAnimation(); } void AnimateWidget::initPicList() { //load all pic for(int i = 0; i < picTotal; i++){ //QList<QPixmap*> picList in header //all png named pic01.png,pic02.png... in qrc file picList.push_back(new QPixmap(QString(":/res/pic%1.png").arg(i,2,10,QChar('0')))); } } //load the first png void AnimateWidget::initPic() { //QPixmap *pix in header pix = new QPixmap(); pix->load(":/res/pic00.png",0,Qt::AvoidDither | Qt::ThresholdAlphaDither | Qt::ThresholdDither); resize(pix->size()); picLabel->resize(pix->size()); setMask(QBitmap(pix->mask())); pcLabel->setPixmap(*pix); } void AnimateWidget::initAnimation() { ani = new QPropertyAnimation(this); ani->setStartValue(0); ani->setEndValue(picTotal); ani->setDuration(picTotal * 30); ani->setLoopCount(-1); ani->setTargetObject() connect(ani,&QPropertyAnimation::valueChanged,this,&AnimateWidget::picChange); ani->start(); } void AnimateWidget::picChange(const QVariant &index); { int i = index.toInt(); pix = picList.at(i); resize(pix->size()); setMask(QBitmap(pix->mask())); picLabel->setPixmap(*pix); //repaint(); //update(); } void AnimateWidget::mousePressEvent(QMouseEvent *event) { if(event->button() == Qt::LeftButton){ //QPoint relativePos; in header relativePos = this->pos() - event->globalPos(); } } void AnimateWidget::mouseMoveEvent(QMouseEvent *event) { this->move(event->globalPos() + relativePos); } ## use in mainwindow## void MainWindow()::showWidget() { //I want to make the widget independent. if new with this is work perfectly //AnimateWidget aniWidget = new AnimateWidget(this); AnimateWidget aniWidget = new AnimateWidget(); aniWidget.show(); }
and I want to know why it become lag even the whole desktop become lag too
and how to fix the lag -
Profile that method.
I am guessing that recreating the bitmap and the mask is going to cost you the most.
Also, there's no real reason to allocate your QPixmap objects on the heap.
What kind of ui are you trying to build with that widget ?
-
the ui of widget just showing picture(sequence,like a gif. but gif has some sawtooth,so i want to make it with pngs).
I want to make it a desktop tool like a floating ball on the desktop.so I need to make the widget independent that can moving in desktop everywhere.
why I allocate the QPixmap on the heap is I think create a pixmap object with take time if do in the method(picChange)in particular when I create the animateWidget with parent. it work perfectly.
//AnimateWidget aniWidget = new AnimateWidget(this); //it work AnimateWidget aniWidget = new AnimateWidget(); //lag
so I am confused what difference between with and without parent widget.it seems to when without parent the paint event did not respond immediately.
and i try something like this:
//in the widget constructor setWindowFlags(Qt::FramelessWindowHint | Qt::Window); //use in mainwindow AnimateWidget aniWidget = new AnimateWidget(this)
it also being lag
what makes that too different behavior happen:
- create widget part of mainwindow is working perfect
- create widget not part of mainwindow is lagging
-
the ui of widget just showing picture(sequence,like a gif. but gif has some sawtooth,so i want to make it with pngs).
I want to make it a desktop tool like a floating ball on the desktop.so I need to make the widget independent that can moving in desktop everywhere.
why I allocate the QPixmap on the heap is I think create a pixmap object with take time if do in the method(picChange)in particular when I create the animateWidget with parent. it work perfectly.
//AnimateWidget aniWidget = new AnimateWidget(this); //it work AnimateWidget aniWidget = new AnimateWidget(); //lag
so I am confused what difference between with and without parent widget.it seems to when without parent the paint event did not respond immediately.
and i try something like this:
//in the widget constructor setWindowFlags(Qt::FramelessWindowHint | Qt::Window); //use in mainwindow AnimateWidget aniWidget = new AnimateWidget(this)
it also being lag
what makes that too different behavior happen:
- create widget part of mainwindow is working perfect
- create widget not part of mainwindow is lagging
@chimppppp said in animation of widget:
the ui of widget just showing picture(sequence,like a gif. but gif has some sawtooth,so i want to make it with pngs).
I want to make it a desktop tool like a floating ball on the desktop.so I need to make the widget independent that can moving in desktop everywhere.
why I allocate the QPixmap on the heap is I think create a pixmap object with take time if do in the method(picChange)in particular when I create the animateWidget with parent. it work perfectly.
//AnimateWidget aniWidget = new AnimateWidget(this); //it work AnimateWidget aniWidget = new AnimateWidget(); //lag
so I am confused what difference between with and without parent widget.it seems to when without parent the paint event did not respond immediately.
and i try something like this:
//in the widget constructor setWindowFlags(Qt::FramelessWindowHint | Qt::Window); //use in mainwindow AnimateWidget aniWidget = new AnimateWidget(this)
it also being lag
what makes that too different behavior happen:
- create widget part of mainwindow is working perfect
- create widget not part of mainwindow is lagging
the reason of lagging is as you said(recreating the bitmap and the mask), so i move it outsize the callback of animation. it work perfectly!
but i also want to know the reason of two different behavior happen. like the underlying logic of Qt painting? or eventloop? -
Top level VS embedded widget: the former is backed by a real window while the later is an "alien" that is handled by Qt.
-
Top level VS embedded widget: the former is backed by a real window while the later is an "alien" that is handled by Qt.
@SGaist I don't quite understand. It seems that the event loop of top level and embedded widget is different?
such as top level widget event loop handled by system so if do something take time makes desktop lag. and embedded widget event loop handled by Qt that have a high efficiency processing so if do something take time if ok?