Having accomplished something similar for a QSlider, I thought it'd be simple. However, I've overriden drawComplexControl, subControlRect, hitTestComplexControl and pixelMetric, and I still encouter two related bugs: when dragging the handle, the handle moves to other places than what the mouse cursor points to, and the handle, instead of being confined to the slider groove, manages to escape the QScrollBar and overwrite its arrows.
I'm guessing both of these is because somehow I've screwed up the calculation of pixel position to slider position to value to screen position, but I can't figure out where. Below are cleaned up code snippets.
void PictureScrollbarStyle
::drawComplexControl(ComplexControl control,
const QStyleOptionComplex* option,
{
-snip-
//drawing the handle
QRect Pos
= subControlRect
(CC_ScrollBar, option, SC_ScrollBarSlider, widget
);
painter->drawPixmap(Pos , *handlePicture);
-snip-
}
void PictureScrollbarStyle::drawComplexControl(ComplexControl control, const QStyleOptionComplex* option,
QPainter* painter, const QWidget* widget) const
{
-snip-
//drawing the handle
QRect Pos = subControlRect(CC_ScrollBar, option, SC_ScrollBarSlider, widget);
painter->drawPixmap(Pos , *handlePicture);
-snip-
}
To copy to clipboard, switch view to plain text mode
SubControl subControl,
const QWidget* widget
) const{
-snip-
if (SC_ScrollBarSlider == subControl)
{
int h = handlePicture->height() / 2;
int span = StyleOptions->maximum - StyleOptions->minimum;
float ratio = (float)StyleOptions->rect.height() / (float)span;
int position = (int)(StyleOptions->sliderPosition * ratio);
QRect result
(0, position
- h, handlePicture
->width
(), handlePicture
->height
());
return result.
isValid() ? result
: QRect(0,
0,
0,
0);
}
-snip-
}
QRect PictureScrollbarStyle::subControlRect(ComplexControl control, const QStyleOptionComplex* option,
SubControl subControl, const QWidget* widget) const
{
-snip-
if (SC_ScrollBarSlider == subControl)
{
int h = handlePicture->height() / 2;
int span = StyleOptions->maximum - StyleOptions->minimum;
float ratio = (float)StyleOptions->rect.height() / (float)span;
int position = (int)(StyleOptions->sliderPosition * ratio);
QRect result(0, position - h, handlePicture->width(), handlePicture->height());
return result.isValid() ? result : QRect(0, 0, 0, 0);
}
-snip-
}
To copy to clipboard, switch view to plain text mode
const QPoint
& pos,
const QWidget* widget
) const {
-snip-
r = subControlRect(CC_ScrollBar, option, SC_ScrollBarSlider, widget);
if (r.isValid() && r.contains(pos))
{
return SC_ScrollBarSlider;
}
return SC_ScrollBarGroove;
}
QStyle::SubControl PictureScrollbarStyle::hitTestComplexControl(ComplexControl control, const QStyleOptionComplex* option,
const QPoint& pos, const QWidget* widget) const
{
-snip-
r = subControlRect(CC_ScrollBar, option, SC_ScrollBarSlider, widget);
if (r.isValid() && r.contains(pos))
{
return SC_ScrollBarSlider;
}
return SC_ScrollBarGroove;
}
To copy to clipboard, switch view to plain text mode
pixelMetric code isn't attached because debug prints show it's not used.
Thanks in advance.
Bookmarks