Reputation: 1289
I'm trying to make a custom widget in Qt5 which is sort of like a QProgressBar but with 3 sliders and user movable: (slightly broken JS implementation: codepen, gist)
I'm having issues working out quite how to do this. My attempts have failed to either render all the parts of the widget correctly (making it very difficult to select and move different parts of it) or not working correctly with a VBoxLayout (doesn't expand to fit the horizontal space)
My latest attempt (you should be able to get the general idea from the constructor, nothing else was implemented)
UTrackSlider::UTrackSlider(QWidget *parent) : QWidget(parent)
{
this->setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::Minimum);
// CIRCLE_HEIGHT = 10
// BACKGROUND_HEIGHT = 30
/// @todo css should be in global stylesheet
background = new QLabel(this);
background->setMinimumHeight(this->BACKGROUND_HEIGHT);
background->setStyleSheet("QLabel{ border: 1px solid gray; background-color:white; border-radius:2px}");
background->setAttribute(Qt::WA_DeleteOnClose);
cue = new QLabel(this);
cue->setFixedSize(QSize(this->CIRCLE_HEIGHT, this->CIRCLE_HEIGHT));
cue->setStyleSheet("QLabel:hover{ border: 2px solid #d9534f; border-radius:5px}");
cue->setAttribute(Qt::WA_DeleteOnClose);
duration = new QLabel(this);
duration->setFixedSize(3, this->BACKGROUND_HEIGHT);
duration->setStyleSheet("QLabel{border: 3px solid #2376bb} QLabel:hover{border: 5px solid #2376bb}");
duration->setAttribute(Qt::WA_DeleteOnClose);
intro = new QLabel(this);
intro->setFixedSize(QSize(this->CIRCLE_HEIGHT, this->CIRCLE_HEIGHT));
intro->setStyleSheet("QLabel:hover{ border: 2px solid #5bc85c; border-radius:5px}");
intro->setAttribute(Qt::WA_DeleteOnClose);
QGridLayout *mainLayout = new QGridLayout(this);
mainLayout->addWidget(cue, 5, 0);
mainLayout->addWidget(background, 0, this->CIRCLE_HEIGHT);
mainLayout->addWidget(duration, 2, this->CIRCLE_HEIGHT);
mainLayout->addWidget(intro, 5, this->CIRCLE_HEIGHT + this->BACKGROUND_HEIGHT);
this->setLayout(mainLayout);
}
Basically, any pointers about how I should structure this composite widget such that it works in all these conditions?
EDIT: After discussing the issue with some people on #qt , i've come to the conclusion that I must override paintEvent. But this also means overriding some other functions to do the onClick and dragging effects, and I've got no idea where to start
Upvotes: 0
Views: 745
Reputation: 324
You're right, you have to re-implement
1.void paintEvent(QPaintEvent *)
2.void mouseMoveEvent(QMouseEvent *)
3.void mousePressEvent(QMouseEvent *)
4.void mouseReleaseEvent(QMouseEvent *)
of QWidget.
In order to handle the mouse event correctly, you may use QCoreApplication::sendEvent(QObject *, QEvent *)
to pass the event to the target widget.
Here's an example: https://github.com/Serge45/MultiSlider
In this example, I create three widgets(ColorSlider) in a container widget, and then use a linked list to propagate the mouse event correctly.
Upvotes: 1