QWidget::render() in custom QWidget
- 
Hello everyone, I made a custom QStackedWidget with the purpose of an animated transition from one widget to another - Slide in and out. I had issues with moving the QWidgets directly so I decided to make a screenshot of the new and old widget, show those, and move them with a QParallelAnimationGroup. I did this the following way: QPoint pNext = widget(slideTo)->pos(); pNow = widget(iCIndex)->pos(); QPixmap pmCurrent = QPixmap(widget(iCIndex)->size()); widget(iCIndex)->render(&pmCurrent); QPixmap pmSlideTo = QPixmap(widget(slideTo)->size()); widget(slideTo)->render(&pmSlideTo); QLabel *lblCurrent = new QLabel(this); QLabel *lblSlideTo = new QLabel(this); lblCurrent->resize(widget(iCIndex)->size()); lblSlideTo->resize(widget(slideTo)->size()); lblCurrent->show(); lblSlideTo->show(); lblCurrent->setPixmap(pmCurrent); lblSlideTo->setPixmap(pmSlideTo); lblCurrent->raise(); lblSlideTo->raise(); lblCurrent->move(0,0); lblSlideTo->move(pNext.x() - iOffsetX, pNext.y()-iOffsetY); QPropertyAnimation *anCurrent = new QPropertyAnimation(lblCurrent,"pos"); QPropertyAnimation *anSlideto = new QPropertyAnimation(lblSlideTo,"pos"); QParallelAnimationGroup *anGroup = new QParallelAnimationGroup; .... .... connect(anGroup, &QParallelAnimationGroup::finished, lblCurrent, &QLabel::deleteLater); connect(anGroup, &QParallelAnimationGroup::finished, lblSlideTo, &QLabel::deleteLater); connect(anGroup, &QParallelAnimationGroup::finished, [=]{ setCurrentIndex(iNext); widget(iNow)->hide(); widget(iNow)->move(pNow); bActive = false; emit AnimationFinished(); }); anGroup->start();The problem is, QWidget::render()completely ignores the stylesheet of the cStackedWidget. I applied it withui->cStackedMain->setStyleSheet("cStackedWidget{background-color:white;}");from the GUI-Class. The white background does not show in the QDesigner, but it is correctly painted when I start the program. If I set a global StyleSheet like centralWidget->setStyleSheet{background-color:white;}then render() accepts the white background. However I don't want to/can't use that , because it would overwrite the children of the whole ui. From the docu I know, that I have the overwrite the paintEvent in my custom widget class, which I did: void cStackedWidget::paintEvent(QPaintEvent *) { QStyleOption opt; opt.init(this); QPainter p(this); style()->drawPrimitive(QStyle::PE_Widget, &opt, &p, this); }So, I'm kinda lost and out of ideas, if anyone could help me, I would be very grateful. If needed/asked for, I'll look in uploading the class so it can be tested easily!? 
- 
Hello everyone, I made a custom QStackedWidget with the purpose of an animated transition from one widget to another - Slide in and out. I had issues with moving the QWidgets directly so I decided to make a screenshot of the new and old widget, show those, and move them with a QParallelAnimationGroup. I did this the following way: QPoint pNext = widget(slideTo)->pos(); pNow = widget(iCIndex)->pos(); QPixmap pmCurrent = QPixmap(widget(iCIndex)->size()); widget(iCIndex)->render(&pmCurrent); QPixmap pmSlideTo = QPixmap(widget(slideTo)->size()); widget(slideTo)->render(&pmSlideTo); QLabel *lblCurrent = new QLabel(this); QLabel *lblSlideTo = new QLabel(this); lblCurrent->resize(widget(iCIndex)->size()); lblSlideTo->resize(widget(slideTo)->size()); lblCurrent->show(); lblSlideTo->show(); lblCurrent->setPixmap(pmCurrent); lblSlideTo->setPixmap(pmSlideTo); lblCurrent->raise(); lblSlideTo->raise(); lblCurrent->move(0,0); lblSlideTo->move(pNext.x() - iOffsetX, pNext.y()-iOffsetY); QPropertyAnimation *anCurrent = new QPropertyAnimation(lblCurrent,"pos"); QPropertyAnimation *anSlideto = new QPropertyAnimation(lblSlideTo,"pos"); QParallelAnimationGroup *anGroup = new QParallelAnimationGroup; .... .... connect(anGroup, &QParallelAnimationGroup::finished, lblCurrent, &QLabel::deleteLater); connect(anGroup, &QParallelAnimationGroup::finished, lblSlideTo, &QLabel::deleteLater); connect(anGroup, &QParallelAnimationGroup::finished, [=]{ setCurrentIndex(iNext); widget(iNow)->hide(); widget(iNow)->move(pNow); bActive = false; emit AnimationFinished(); }); anGroup->start();The problem is, QWidget::render()completely ignores the stylesheet of the cStackedWidget. I applied it withui->cStackedMain->setStyleSheet("cStackedWidget{background-color:white;}");from the GUI-Class. The white background does not show in the QDesigner, but it is correctly painted when I start the program. If I set a global StyleSheet like centralWidget->setStyleSheet{background-color:white;}then render() accepts the white background. However I don't want to/can't use that , because it would overwrite the children of the whole ui. From the docu I know, that I have the overwrite the paintEvent in my custom widget class, which I did: void cStackedWidget::paintEvent(QPaintEvent *) { QStyleOption opt; opt.init(this); QPainter p(this); style()->drawPrimitive(QStyle::PE_Widget, &opt, &p, this); }So, I'm kinda lost and out of ideas, if anyone could help me, I would be very grateful. If needed/asked for, I'll look in uploading the class so it can be tested easily!? Hi 
 I think the issue is just who is parent ?
 The stylesheet will affect children so if it works with the custom widget when
 centralWidget->setStyleSheet{background-color:white;}
 has the style so to speak
 then it sounds like your custom is just owned by something not affected and hence its children will no either.I use only a single stylesheet on mainwindow. Not pr control as i think it becomes uncontrollable very fast. Maybe i misunderstand your issue and what works and what do not work. 
 Your paint looks correct :)
- 
Hello everyone, I made a custom QStackedWidget with the purpose of an animated transition from one widget to another - Slide in and out. I had issues with moving the QWidgets directly so I decided to make a screenshot of the new and old widget, show those, and move them with a QParallelAnimationGroup. I did this the following way: QPoint pNext = widget(slideTo)->pos(); pNow = widget(iCIndex)->pos(); QPixmap pmCurrent = QPixmap(widget(iCIndex)->size()); widget(iCIndex)->render(&pmCurrent); QPixmap pmSlideTo = QPixmap(widget(slideTo)->size()); widget(slideTo)->render(&pmSlideTo); QLabel *lblCurrent = new QLabel(this); QLabel *lblSlideTo = new QLabel(this); lblCurrent->resize(widget(iCIndex)->size()); lblSlideTo->resize(widget(slideTo)->size()); lblCurrent->show(); lblSlideTo->show(); lblCurrent->setPixmap(pmCurrent); lblSlideTo->setPixmap(pmSlideTo); lblCurrent->raise(); lblSlideTo->raise(); lblCurrent->move(0,0); lblSlideTo->move(pNext.x() - iOffsetX, pNext.y()-iOffsetY); QPropertyAnimation *anCurrent = new QPropertyAnimation(lblCurrent,"pos"); QPropertyAnimation *anSlideto = new QPropertyAnimation(lblSlideTo,"pos"); QParallelAnimationGroup *anGroup = new QParallelAnimationGroup; .... .... connect(anGroup, &QParallelAnimationGroup::finished, lblCurrent, &QLabel::deleteLater); connect(anGroup, &QParallelAnimationGroup::finished, lblSlideTo, &QLabel::deleteLater); connect(anGroup, &QParallelAnimationGroup::finished, [=]{ setCurrentIndex(iNext); widget(iNow)->hide(); widget(iNow)->move(pNow); bActive = false; emit AnimationFinished(); }); anGroup->start();The problem is, QWidget::render()completely ignores the stylesheet of the cStackedWidget. I applied it withui->cStackedMain->setStyleSheet("cStackedWidget{background-color:white;}");from the GUI-Class. The white background does not show in the QDesigner, but it is correctly painted when I start the program. If I set a global StyleSheet like centralWidget->setStyleSheet{background-color:white;}then render() accepts the white background. However I don't want to/can't use that , because it would overwrite the children of the whole ui. From the docu I know, that I have the overwrite the paintEvent in my custom widget class, which I did: void cStackedWidget::paintEvent(QPaintEvent *) { QStyleOption opt; opt.init(this); QPainter p(this); style()->drawPrimitive(QStyle::PE_Widget, &opt, &p, this); }So, I'm kinda lost and out of ideas, if anyone could help me, I would be very grateful. If needed/asked for, I'll look in uploading the class so it can be tested easily!? wrote on 10 Mar 2017, 14:19 last edited byTo add to @mrjj @J.Hilk said in QWidget::render() in custom QWidget: However I don't want to/can't use that , because it would overwrite the children of the whole ui. You can use object name specific stylesheet see id selector in http://doc.qt.io/qt-5/stylesheet-syntax.html#selector-types I had issues with moving the QWidgets directly I implemented something similar here SelettoreImmagini.h SelettoreImmagini.cpp it's from one of the very first programs I wrote in Qt (a snake game) so it's VERY far from good (and the variable names are in italian) but gives you an idea, basically you keep 1 widget always visible then, you add the widgets that you want to scroll as its children but you never add them to a layout but instead manually resize them to the parent widget, at this point you are free to animate the "pos" property of the child widgets. In the linked example I move 2 QLabels 
- 
To add to @mrjj @J.Hilk said in QWidget::render() in custom QWidget: However I don't want to/can't use that , because it would overwrite the children of the whole ui. You can use object name specific stylesheet see id selector in http://doc.qt.io/qt-5/stylesheet-syntax.html#selector-types I had issues with moving the QWidgets directly I implemented something similar here SelettoreImmagini.h SelettoreImmagini.cpp it's from one of the very first programs I wrote in Qt (a snake game) so it's VERY far from good (and the variable names are in italian) but gives you an idea, basically you keep 1 widget always visible then, you add the widgets that you want to scroll as its children but you never add them to a layout but instead manually resize them to the parent widget, at this point you are free to animate the "pos" property of the child widgets. In the linked example I move 2 QLabels Hi, sorry for the delay, was a crazy weekend on my side. Thanks for the fast replies I think I'll have to be more precise with my description. First off, you may find a small example project here. So, let's say I set a single StyleSheet on the QMainWindow, like this: this->setStyleSheet("QMainWindow{background-color:white;}\ cStackedWidget{background-color:red;}\ QLabel{background-color:blue;}");I get a exactly what I want, white background/Mainwindow, red Stackedwidget and blue labels. 
 As soon as I use render() on the first QWidget of the QStackedWidget. the red is completly ignored, I get the default light grey for the stacked widget and blue QLabelsWhen I set the StyleSheet like this: this->setStyleSheet("background-color:red;");Everything is Red but, render() actually captures the QStackedWidget color correctly. LineBreakAs I'm writing this, I actually find the crux of the problem. this: this->setStyleSheet("QMainWindow{background-color:white;}\ cStackedWidget{background-color:red;}\ QLabel{background-color:blue;}");Paints the ui, like I whoud expect it to but its apparently not doing the job thoroughly enough. 
 Each "page" of the QStackedWidget is a QWidget, and using the above code paints the QWidgets red as well but not for the QWidget::render() function.Using this StyleSheet: this->setStyleSheet("QMainWindow{background-color:white;}\ cStackedWidget{background-color:red;}\ QWidget{background-color:red;}\ QLabel{background-color:blue;}");I see no difference for when the widget is painted, but now QWidget::render actually accepts the red background. So, is this a bug ot intended behaviour? 
- 
Hi, sorry for the delay, was a crazy weekend on my side. Thanks for the fast replies I think I'll have to be more precise with my description. First off, you may find a small example project here. So, let's say I set a single StyleSheet on the QMainWindow, like this: this->setStyleSheet("QMainWindow{background-color:white;}\ cStackedWidget{background-color:red;}\ QLabel{background-color:blue;}");I get a exactly what I want, white background/Mainwindow, red Stackedwidget and blue labels. 
 As soon as I use render() on the first QWidget of the QStackedWidget. the red is completly ignored, I get the default light grey for the stacked widget and blue QLabelsWhen I set the StyleSheet like this: this->setStyleSheet("background-color:red;");Everything is Red but, render() actually captures the QStackedWidget color correctly. LineBreakAs I'm writing this, I actually find the crux of the problem. this: this->setStyleSheet("QMainWindow{background-color:white;}\ cStackedWidget{background-color:red;}\ QLabel{background-color:blue;}");Paints the ui, like I whoud expect it to but its apparently not doing the job thoroughly enough. 
 Each "page" of the QStackedWidget is a QWidget, and using the above code paints the QWidgets red as well but not for the QWidget::render() function.Using this StyleSheet: this->setStyleSheet("QMainWindow{background-color:white;}\ cStackedWidget{background-color:red;}\ QWidget{background-color:red;}\ QLabel{background-color:blue;}");I see no difference for when the widget is painted, but now QWidget::render actually accepts the red background. So, is this a bug ot intended behaviour? @J.Hilk 
 Super with a sample. +5
 I see what you mean.
 Its a bit odd. So first it accepts the stylesheet but when
 you render an image for slide animation it is
 not applied. I thought it would be exactly the
 same in and render() would just call paint.Interesting :) 
- 
Just realized, that I had still thread still open. I'll share how I managed to circumvent the problem. Sadly I haven't found a realsolution as of now.In the function that makes the screenshot, I added this line just before calling QWidget::renderthis->setStyleSheet("cStackedWidget {background-color:white;}" "QWidget#LiveStatus{background-color:white;}" ... //List of all QStackedwidget Pages ... "QWidget#FanThreshhold{background-color:white;}");For some reason I have to set the stylesheet new for each time. Simply setting this once will not work. Anyway, I'll mark it as solved, 
 unless someone else has a new idea !?
