fix: make volume/progress sliders draggable

ClickableSlider previously accepted the mouse press without forwarding
to QSlider, so the drag mechanism never started. Now setSliderPosition
is called first (jumping the handle to the click point) and the event
is always forwarded so Qt enters normal drag mode. mouseMoveEvent is
also overridden to keep snapping to the cursor during a drag.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
joren
2026-03-24 00:40:29 +01:00
parent 35ae649fc9
commit 157d0f9ffe

View File

@@ -16,17 +16,34 @@ protected:
void mousePressEvent(QMouseEvent *event) override
{
if (event->button() == Qt::LeftButton) {
int val;
if (orientation() == Qt::Horizontal) {
val = minimum() + (maximum() - minimum()) * event->pos().x() / width();
} else {
val = minimum() + (maximum() - minimum()) * (height() - event->pos().y()) / height();
}
setValue(val);
// Jump the handle to the clicked position first so Qt's own
// press handler sees the click "on" the handle and starts drag.
const int val = posToValue(event->pos());
setSliderPosition(val);
emit sliderMoved(val);
event->accept();
} else {
QSlider::mousePressEvent(event);
}
// Always forward so the slider enters drag mode normally.
QSlider::mousePressEvent(event);
}
void mouseMoveEvent(QMouseEvent *event) override
{
// During a drag, keep snapping to cursor position.
if (event->buttons() & Qt::LeftButton) {
const int val = posToValue(event->pos());
setSliderPosition(val);
emit sliderMoved(val);
}
QSlider::mouseMoveEvent(event);
}
private:
int posToValue(const QPoint &pos) const
{
const int span = orientation() == Qt::Horizontal ? width() : height();
const int pixel = orientation() == Qt::Horizontal ? pos.x() : (height() - pos.y());
if (span <= 0) return minimum();
const int val = minimum() + (maximum() - minimum()) * pixel / span;
return qBound(minimum(), val, maximum());
}
};