2017-07-21 18:21:34 +02:00
|
|
|
/******************************************************************************
|
|
|
|
* QSkinny - Copyright (C) 2016 Uwe Rathmann
|
|
|
|
* This file may be used under the terms of the QSkinny License, Version 1.0
|
|
|
|
*****************************************************************************/
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
#include "QskBoundedValueControl.h"
|
2017-07-21 18:21:34 +02:00
|
|
|
#include "QskFunctions.h"
|
2020-07-22 11:49:28 +02:00
|
|
|
#include "QskIntervalF.h"
|
2017-07-21 18:21:34 +02:00
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
QSK_SYSTEM_STATE( QskBoundedValueControl, ReadOnly, ( QskAspect::FirstSystemState << 1 ) )
|
2019-09-27 07:34:25 +02:00
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
class QskBoundedValueControl::PrivateData
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
2018-08-03 08:15:28 +02:00
|
|
|
public:
|
|
|
|
PrivateData()
|
|
|
|
: minimum( 0.0 )
|
|
|
|
, maximum( 1.0 )
|
|
|
|
, value( 0.0 )
|
|
|
|
, stepSize( 0.1 )
|
|
|
|
, pageSize( 1 )
|
|
|
|
, snap( false )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
qreal minimum;
|
|
|
|
qreal maximum;
|
|
|
|
qreal value;
|
|
|
|
qreal stepSize;
|
|
|
|
int pageSize;
|
|
|
|
bool snap : 1;
|
|
|
|
};
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
QskBoundedValueControl::QskBoundedValueControl( QQuickItem* parent )
|
2018-08-03 08:15:28 +02:00
|
|
|
: QskControl( parent )
|
|
|
|
, m_data( new PrivateData() )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
2019-09-27 07:34:25 +02:00
|
|
|
setFocusPolicy( Qt::StrongFocus );
|
|
|
|
setAcceptedMouseButtons( Qt::LeftButton );
|
|
|
|
setWheelEnabled( true );
|
2017-07-21 18:21:34 +02:00
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
QskBoundedValueControl::~QskBoundedValueControl()
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setMinimum( qreal minimum )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
if ( m_data->minimum == minimum )
|
|
|
|
return;
|
|
|
|
|
|
|
|
m_data->minimum = minimum;
|
|
|
|
Q_EMIT minimumChanged( minimum );
|
|
|
|
|
|
|
|
if ( isComponentComplete() )
|
2020-07-25 12:50:26 +02:00
|
|
|
adjustBoundariesAndValue( false );
|
2017-07-21 18:21:34 +02:00
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
Q_EMIT boundariesChanged( boundaries() );
|
2017-07-21 18:21:34 +02:00
|
|
|
update();
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
qreal QskBoundedValueControl::minimum() const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
return m_data->minimum;
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setMaximum( qreal maximum )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
if ( m_data->maximum == maximum )
|
|
|
|
return;
|
|
|
|
|
|
|
|
m_data->maximum = maximum;
|
|
|
|
Q_EMIT maximumChanged( maximum );
|
|
|
|
|
|
|
|
if ( isComponentComplete() )
|
2020-07-25 12:50:26 +02:00
|
|
|
adjustBoundariesAndValue( true );
|
2017-07-21 18:21:34 +02:00
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
Q_EMIT boundariesChanged( boundaries() );
|
2017-07-21 18:21:34 +02:00
|
|
|
update();
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
qreal QskBoundedValueControl::maximum() const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
return m_data->maximum;
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setBoundaries( qreal min, qreal max )
|
2020-07-22 11:49:28 +02:00
|
|
|
{
|
|
|
|
if ( max < min )
|
|
|
|
max = min;
|
|
|
|
|
|
|
|
const auto oldMin = m_data->minimum;
|
|
|
|
const auto oldMax = m_data->maximum;
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
if ( min == oldMin && max == oldMax )
|
|
|
|
return;
|
|
|
|
|
2020-07-22 11:49:28 +02:00
|
|
|
m_data->minimum = min;
|
|
|
|
m_data->maximum = max;
|
|
|
|
|
|
|
|
if ( isComponentComplete() )
|
2020-07-25 12:50:26 +02:00
|
|
|
adjustBoundariesAndValue( false );
|
2020-07-22 11:49:28 +02:00
|
|
|
|
|
|
|
if ( m_data->minimum != oldMin )
|
|
|
|
Q_EMIT minimumChanged( m_data->minimum );
|
|
|
|
|
|
|
|
if ( m_data->maximum != oldMax )
|
|
|
|
Q_EMIT maximumChanged( m_data->maximum );
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
Q_EMIT boundariesChanged( boundaries() );
|
2020-07-22 11:49:28 +02:00
|
|
|
update();
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setBoundaries( const QskIntervalF& boundaries )
|
2020-07-22 11:49:28 +02:00
|
|
|
{
|
2020-07-25 12:50:26 +02:00
|
|
|
setBoundaries( boundaries.lowerBound(), boundaries.upperBound() );
|
2020-07-22 11:49:28 +02:00
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
QskIntervalF QskBoundedValueControl::boundaries() const
|
2020-07-22 11:49:28 +02:00
|
|
|
{
|
|
|
|
return QskIntervalF( m_data->minimum, m_data->maximum );
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::adjustBoundariesAndValue( bool increasing )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
if ( m_data->maximum < m_data->minimum )
|
|
|
|
{
|
|
|
|
if ( increasing )
|
|
|
|
{
|
|
|
|
m_data->minimum = m_data->maximum;
|
|
|
|
Q_EMIT minimumChanged( m_data->minimum );
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
m_data->maximum = m_data->minimum;
|
|
|
|
Q_EMIT maximumChanged( m_data->maximum );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
qreal newValue = m_data->value;
|
|
|
|
|
|
|
|
if ( m_data->snap && m_data->stepSize != 0.0 )
|
|
|
|
newValue = qRound( newValue / m_data->stepSize ) * m_data->stepSize;
|
|
|
|
|
|
|
|
newValue = qBound( m_data->minimum, newValue, m_data->maximum );
|
|
|
|
|
|
|
|
if ( newValue != m_data->value )
|
|
|
|
{
|
|
|
|
m_data->value = newValue;
|
|
|
|
Q_EMIT valueChanged( newValue );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
qreal QskBoundedValueControl::boundaryLength() const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
return m_data->maximum - m_data->minimum;
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
qreal QskBoundedValueControl::fixupValue( qreal value ) const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
2020-07-25 12:50:26 +02:00
|
|
|
return value;
|
2017-07-21 18:21:34 +02:00
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setValueAsRatio( qreal ratio )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
2020-07-25 12:50:26 +02:00
|
|
|
ratio = qBound( 0.0, ratio, 1.0 );
|
|
|
|
setValue( m_data->minimum + ratio * ( m_data->maximum - m_data->minimum ) );
|
|
|
|
}
|
|
|
|
|
|
|
|
qreal QskBoundedValueControl::valueAsRatio() const
|
|
|
|
{
|
|
|
|
return ( m_data->value - m_data->minimum ) / ( m_data->maximum - m_data->minimum );
|
2017-07-21 18:21:34 +02:00
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setValue( qreal value )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
if ( isComponentComplete() )
|
|
|
|
{
|
|
|
|
if ( m_data->snap && m_data->stepSize != 0.0 )
|
|
|
|
value = qRound( value / m_data->stepSize ) * m_data->stepSize;
|
|
|
|
|
|
|
|
value = qBound( m_data->minimum, value, m_data->maximum );
|
|
|
|
}
|
|
|
|
|
|
|
|
value = fixupValue( value );
|
|
|
|
|
|
|
|
if ( !qskFuzzyCompare( value, m_data->value ) )
|
|
|
|
{
|
|
|
|
m_data->value = value;
|
|
|
|
Q_EMIT valueChanged( value );
|
|
|
|
|
|
|
|
update();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
qreal QskBoundedValueControl::value() const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
return m_data->value;
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setStepSize( qreal stepSize )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
if ( qskFuzzyCompare( m_data->stepSize, stepSize ) )
|
|
|
|
return;
|
|
|
|
|
|
|
|
m_data->stepSize = stepSize;
|
|
|
|
Q_EMIT stepSizeChanged( stepSize );
|
|
|
|
|
|
|
|
update();
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
qreal QskBoundedValueControl::stepSize() const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
return m_data->stepSize;
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setPageSize( int pageSize )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
if ( m_data->pageSize == pageSize )
|
|
|
|
return;
|
|
|
|
|
|
|
|
m_data->pageSize = pageSize;
|
|
|
|
Q_EMIT pageSizeChanged( pageSize );
|
|
|
|
|
|
|
|
update();
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
int QskBoundedValueControl::pageSize() const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
return m_data->pageSize;
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setSnap( bool snap )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
if ( m_data->snap == snap )
|
|
|
|
return;
|
|
|
|
|
|
|
|
m_data->snap = snap;
|
|
|
|
Q_EMIT snapChanged( snap );
|
|
|
|
|
|
|
|
if ( snap )
|
|
|
|
{
|
|
|
|
// Re-align value
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
bool QskBoundedValueControl::snap() const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
return m_data->snap;
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::setReadOnly( bool readOnly )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
2019-09-27 07:34:25 +02:00
|
|
|
if ( readOnly == isReadOnly() )
|
2017-07-21 18:21:34 +02:00
|
|
|
return;
|
|
|
|
|
2019-09-27 07:34:25 +02:00
|
|
|
setSkinStateFlag( ReadOnly, readOnly );
|
2017-10-25 07:48:10 +02:00
|
|
|
|
2017-10-24 19:32:54 +02:00
|
|
|
// we are killing user settings here !!
|
2017-10-25 07:48:10 +02:00
|
|
|
setFocusPolicy( readOnly ? Qt::NoFocus : Qt::StrongFocus );
|
|
|
|
setAcceptedMouseButtons( readOnly ? Qt::NoButton : Qt::LeftButton );
|
2019-09-27 07:34:25 +02:00
|
|
|
setWheelEnabled( !readOnly );
|
2017-07-21 18:21:34 +02:00
|
|
|
|
|
|
|
Q_EMIT readOnlyChanged( readOnly );
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
bool QskBoundedValueControl::isReadOnly() const
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
2019-09-27 07:34:25 +02:00
|
|
|
return skinState() & ReadOnly;
|
2017-07-21 18:21:34 +02:00
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::stepUp()
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
setValue( m_data->value + m_data->stepSize );
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::stepDown()
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
setValue( m_data->value - m_data->stepSize );
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::pageUp()
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
setValue( m_data->value + m_data->stepSize * m_data->pageSize );
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::pageDown()
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
setValue( m_data->value - m_data->stepSize * m_data->pageSize );
|
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::keyPressEvent( QKeyEvent* event )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
if ( !isReadOnly() )
|
|
|
|
{
|
|
|
|
if ( event->key() == Qt::Key_Up || event->matches( QKeySequence::MoveToNextChar ) )
|
|
|
|
{
|
|
|
|
stepUp();
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
if ( event->key() == Qt::Key_Down || event->matches( QKeySequence::MoveToPreviousChar ) )
|
|
|
|
{
|
|
|
|
stepDown();
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
Inherited::keyPressEvent( event );
|
|
|
|
}
|
|
|
|
|
|
|
|
#ifndef QT_NO_WHEELEVENT
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::wheelEvent( QWheelEvent* event )
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
2018-08-03 08:15:28 +02:00
|
|
|
if ( isReadOnly() )
|
2017-12-22 14:15:24 +01:00
|
|
|
return;
|
|
|
|
|
2020-03-12 09:57:38 +01:00
|
|
|
#if QT_VERSION < 0x050e00
|
|
|
|
const int wheelDelta = event->delta();
|
|
|
|
#else
|
|
|
|
const auto delta = event->angleDelta();
|
|
|
|
const int wheelDelta = ( qAbs( delta.x() ) > qAbs( delta.y() ) )
|
|
|
|
? delta.x() : delta.y();
|
|
|
|
#endif
|
|
|
|
|
|
|
|
const int steps = wheelDelta / QWheelEvent::DefaultDeltasPerStep;
|
2017-07-21 18:21:34 +02:00
|
|
|
setValue( m_data->value + steps * m_data->stepSize );
|
|
|
|
}
|
|
|
|
|
|
|
|
#endif
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
void QskBoundedValueControl::componentComplete()
|
2017-07-21 18:21:34 +02:00
|
|
|
{
|
|
|
|
Inherited::componentComplete();
|
2020-07-25 12:50:26 +02:00
|
|
|
adjustBoundariesAndValue( true );
|
2017-07-21 18:21:34 +02:00
|
|
|
}
|
|
|
|
|
2020-07-25 12:50:26 +02:00
|
|
|
#include "moc_QskBoundedValueControl.cpp"
|