mirror of
https://github.com/GoldenCheetah/GoldenCheetah.git
synced 2026-02-14 00:28:42 +00:00
185 lines
4.0 KiB
C++
185 lines
4.0 KiB
C++
#include <qstyle.h>
|
|
#if QT_VERSION >= 0x040000
|
|
#include <qstyleoption.h>
|
|
#endif
|
|
#include "scrollbar.h"
|
|
|
|
ScrollBar::ScrollBar(QWidget * parent):
|
|
QScrollBar(parent)
|
|
{
|
|
init();
|
|
}
|
|
|
|
ScrollBar::ScrollBar(Qt::Orientation o,
|
|
QWidget *parent):
|
|
QScrollBar(o, parent)
|
|
{
|
|
init();
|
|
}
|
|
|
|
ScrollBar::ScrollBar(double minBase, double maxBase,
|
|
Qt::Orientation o, QWidget *parent):
|
|
QScrollBar(o, parent)
|
|
{
|
|
init();
|
|
setBase(minBase, maxBase);
|
|
moveSlider(minBase, maxBase);
|
|
}
|
|
|
|
void ScrollBar::init()
|
|
{
|
|
d_inverted = orientation() == Qt::Vertical;
|
|
d_baseTicks = 1000000;
|
|
d_minBase = 0.0;
|
|
d_maxBase = 1.0;
|
|
moveSlider(d_minBase, d_maxBase);
|
|
|
|
connect(this, SIGNAL(sliderMoved(int)), SLOT(catchSliderMoved(int)));
|
|
connect(this, SIGNAL(valueChanged(int)), SLOT(catchValueChanged(int)));
|
|
}
|
|
|
|
void ScrollBar::setInverted(bool inverted)
|
|
{
|
|
if ( d_inverted != inverted )
|
|
{
|
|
d_inverted = inverted;
|
|
moveSlider(minSliderValue(), maxSliderValue());
|
|
}
|
|
}
|
|
|
|
bool ScrollBar::isInverted() const
|
|
{
|
|
return d_inverted;
|
|
}
|
|
|
|
void ScrollBar::setBase(double min, double max)
|
|
{
|
|
if ( min != d_minBase || max != d_maxBase )
|
|
{
|
|
d_minBase = min;
|
|
d_maxBase = max;
|
|
|
|
moveSlider(minSliderValue(), maxSliderValue());
|
|
}
|
|
}
|
|
|
|
void ScrollBar::moveSlider(double min, double max)
|
|
{
|
|
const int sliderTicks = qRound((max - min) /
|
|
(d_maxBase - d_minBase) * d_baseTicks);
|
|
|
|
// setRange initiates a valueChanged of the scrollbars
|
|
// in some situations. So we block
|
|
// and unblock the signals.
|
|
|
|
blockSignals(true);
|
|
|
|
setRange(sliderTicks / 2, d_baseTicks - sliderTicks / 2);
|
|
int steps = sliderTicks / 200;
|
|
if ( steps <= 0 )
|
|
steps = 1;
|
|
|
|
#if QT_VERSION < 0x040000
|
|
setSteps(steps, sliderTicks);
|
|
#else
|
|
setSingleStep(steps);
|
|
setPageStep(sliderTicks);
|
|
#endif
|
|
|
|
int tick = mapToTick(min + (max - min) / 2);
|
|
if ( isInverted() )
|
|
tick = d_baseTicks - tick;
|
|
|
|
#if QT_VERSION < 0x040000
|
|
directSetValue(tick);
|
|
rangeChange();
|
|
#else
|
|
setSliderPosition(tick);
|
|
#endif
|
|
blockSignals(false);
|
|
}
|
|
|
|
double ScrollBar::minBaseValue() const
|
|
{
|
|
return d_minBase;
|
|
}
|
|
|
|
double ScrollBar::maxBaseValue() const
|
|
{
|
|
return d_maxBase;
|
|
}
|
|
|
|
void ScrollBar::sliderRange(int value, double &min, double &max) const
|
|
{
|
|
if ( isInverted() )
|
|
value = d_baseTicks - value;
|
|
|
|
const int visibleTicks = pageStep();
|
|
|
|
min = mapFromTick(value - visibleTicks / 2);
|
|
max = mapFromTick(value + visibleTicks / 2);
|
|
}
|
|
|
|
double ScrollBar::minSliderValue() const
|
|
{
|
|
double min, dummy;
|
|
sliderRange(value(), min, dummy);
|
|
|
|
return min;
|
|
}
|
|
|
|
double ScrollBar::maxSliderValue() const
|
|
{
|
|
double max, dummy;
|
|
sliderRange(value(), dummy, max);
|
|
|
|
return max;
|
|
}
|
|
|
|
int ScrollBar::mapToTick(double v) const
|
|
{
|
|
return (int) ( ( v - d_minBase) / (d_maxBase - d_minBase ) * d_baseTicks );
|
|
}
|
|
|
|
double ScrollBar::mapFromTick(int tick) const
|
|
{
|
|
return d_minBase + ( d_maxBase - d_minBase ) * tick / d_baseTicks;
|
|
}
|
|
|
|
void ScrollBar::catchValueChanged(int value)
|
|
{
|
|
double min, max;
|
|
sliderRange(value, min, max);
|
|
emit valueChanged(orientation(), min, max);
|
|
}
|
|
|
|
void ScrollBar::catchSliderMoved(int value)
|
|
{
|
|
double min, max;
|
|
sliderRange(value, min, max);
|
|
emit sliderMoved(orientation(), min, max);
|
|
}
|
|
|
|
int ScrollBar::extent() const
|
|
{
|
|
#if QT_VERSION < 0x040000
|
|
return style().pixelMetric(QStyle::PM_ScrollBarExtent, this);
|
|
#else
|
|
QStyleOptionSlider opt;
|
|
opt.init(this);
|
|
opt.subControls = QStyle::SC_None;
|
|
opt.activeSubControls = QStyle::SC_None;
|
|
opt.orientation = orientation();
|
|
opt.minimum = minimum();
|
|
opt.maximum = maximum();
|
|
opt.sliderPosition = sliderPosition();
|
|
opt.sliderValue = value();
|
|
opt.singleStep = singleStep();
|
|
opt.pageStep = pageStep();
|
|
opt.upsideDown = invertedAppearance();
|
|
if (orientation() == Qt::Horizontal)
|
|
opt.state |= QStyle::State_Horizontal;
|
|
return style()->pixelMetric(QStyle::PM_ScrollBarExtent, &opt, this);
|
|
#endif
|
|
}
|