13 #include <qalgorithms.h> 18 #if QT_VERSION < 0x040601 19 #define qFabs(x) ::fabs(x) 20 #define qExp(x) ::exp(x) 23 static inline double qwtLog(
double base,
double value )
25 return log( value ) /
log( base );
44 static double qwtStepSize(
double intervalSize,
int maxSteps, uint base )
46 const double minStep =
52 const int numTicks = qCeil( qAbs( intervalSize / minStep ) ) - 1;
56 qAbs( intervalSize ), intervalSize ) > 0 )
59 return 0.5 * intervalSize;
68 static double qwtStepSize(
double intervalSize,
int maxSteps, uint base )
75 for (
int numSteps = maxSteps; numSteps > 1; numSteps-- )
77 const double stepSize = intervalSize / numSteps;
79 const double p = ::floor( ::
log( stepSize ) / ::
log( base ) );
80 const double fraction = qPow( base, p );
82 for ( uint
n = base;
n > 1;
n /= 2 )
84 if ( qFuzzyCompare( stepSize,
n * fraction ) )
87 if (
n == 3 && ( base % 2 ) == 0 )
89 if ( qFuzzyCompare( stepSize, 2 * fraction ) )
96 return intervalSize * 0.5;
101 static const double _eps = 1.0e-6;
114 double intervalSize )
116 const double eps =
_eps * intervalSize;
118 value = ( value - eps ) / intervalSize;
119 return ::ceil( value ) * intervalSize;
133 const double eps =
_eps * intervalSize;
135 value = ( value + eps ) / intervalSize;
136 return ::floor( value ) * intervalSize;
150 if ( numSteps == 0.0 || intervalSize == 0.0 )
153 return ( intervalSize - (
_eps * intervalSize ) ) / numSteps;
166 double intervalSize,
int numSteps, uint base )
176 const double p = ::floor( lx );
178 const double fraction = qPow( base, lx - p );
181 while ( ( n > 1 ) && ( fraction <= n / 2 ) )
184 double stepSize = n * qPow( base, p );
186 stepSize = -stepSize;
198 referenceValue( 0.0 ),
257 delete d_data->transform;
258 d_data->transform = transform;
273 if ( d_data->transform )
287 return d_data->lowerMargin;
298 return d_data->upperMargin;
319 d_data->lowerMargin = qMax( lower, 0.0 );
320 d_data->upperMargin = qMax( upper, 0.0 );
332 double intervalSize,
int numSteps )
const 335 intervalSize, numSteps, d_data->base );
372 if ( !interval.
isValid() || ticks.count() == 0 )
373 return QList<double>();
375 if ( contains( interval, ticks.first() )
376 && contains( interval, ticks.last() ) )
381 QList<double> strippedTicks;
382 for (
int i = 0;
i < ticks.count();
i++ )
384 if ( contains( interval, ticks[
i] ) )
385 strippedTicks += ticks[i];
387 return strippedTicks;
402 const double delta = ( value == 0.0 ) ? 0.5 : qAbs( 0.5 * value );
404 if ( DBL_MAX - delta < value )
407 if ( -DBL_MAX + delta > value )
410 return QwtInterval( value - delta, value + delta );
424 d_data->attributes |= attribute;
426 d_data->attributes &= ~attribute;
437 return ( d_data->attributes & attribute );
448 d_data->attributes = attributes;
457 return d_data->attributes;
471 d_data->referenceValue = r;
480 return d_data->referenceValue;
497 d_data->base = qMax( base, 2U );
536 double &x1,
double &x2,
double &stepSize )
const 550 if ( interval.
width() == 0.0 )
554 interval.
width(), qMax( maxNumSteps, 1 ),
base() );
557 interval =
align( interval, stepSize );
565 stepSize = -stepSize;
582 int maxMajorSteps,
int maxMinorSteps,
double stepSize )
const 586 if ( interval.
widthL() > std::numeric_limits<double>::max() )
588 qWarning() <<
"QwtLinearScaleEngine::divideScale: overflow";
592 if ( interval.
width() <= 0 )
595 stepSize = qAbs( stepSize );
596 if ( stepSize == 0.0 )
598 if ( maxMajorSteps < 1 )
602 interval.
width(), maxMajorSteps,
base() );
607 if ( stepSize != 0.0 )
610 buildTicks( interval, stepSize, maxMinorSteps, ticks );
632 const QwtInterval& interval,
double stepSize,
int maxMinorSteps,
640 if ( maxMinorSteps > 0 )
648 ticks[
i] =
strip( ticks[
i], interval );
653 for (
int j = 0; j < ticks[i].count(); j++ )
670 const QwtInterval &interval,
double stepSize )
const 672 int numTicks = qRound( interval.
width() / stepSize ) + 1;
673 if ( numTicks > 10000 )
677 #if QT_VERSION >= 0x040700 678 ticks.reserve( numTicks );
682 for (
int i = 1;
i < numTicks - 1;
i++ )
683 ticks += interval.
minValue() +
i * stepSize;
700 const QList<double>& majorTicks,
701 int maxMinorSteps,
double stepSize,
702 QList<double> &minorTicks,
703 QList<double> &mediumTicks )
const 706 if ( minStep == 0.0 )
710 const int numTicks = qCeil( qAbs( stepSize / minStep ) ) - 1;
714 medIndex = numTicks / 2;
718 for (
int i = 0;
i < majorTicks.count();
i++ )
720 double val = majorTicks[
i];
721 for (
int k = 0; k < numTicks; k++ )
725 double alignedValue = val;
730 mediumTicks += alignedValue;
732 minorTicks += alignedValue;
749 const QwtInterval &interval,
double stepSize )
const 757 const double eps = 0.000000000001;
758 if ( -DBL_MAX + stepSize <= x1 )
761 if ( qAbs(x) <= eps || !qFuzzyCompare( x1, x ) )
765 if ( DBL_MAX - stepSize >= x2 )
768 if ( qAbs(x) <= eps || !qFuzzyCompare( x2, x ) )
803 double &x1,
double &x2,
double &stepSize )
const 808 const double logBase =
base();
822 linearScaler.
autoScale( maxNumSteps, x1, x2, stepSize );
840 const double delta = qMax( interval.
maxValue() / logRef,
842 interval.
setInterval( logRef / delta, logRef * delta );
846 interval = interval.
extend( logRef );
850 if ( interval.
width() == 0.0 )
854 qMax( maxNumSteps, 1 ) );
855 if ( stepSize < 1.0 )
859 interval =
align( interval, stepSize );
867 stepSize = -stepSize;
884 int maxMajorSteps,
int maxMinorSteps,
double stepSize )
const 889 if ( interval.
width() <= 0 )
892 const double logBase =
base();
904 maxMajorSteps, maxMinorSteps, 0.0 );
907 stepSize = qAbs( stepSize );
908 if ( stepSize == 0.0 )
910 if ( maxMajorSteps < 1 )
915 if ( stepSize < 1.0 )
920 if ( stepSize != 0.0 )
923 buildTicks( interval, stepSize, maxMinorSteps, ticks );
945 const QwtInterval& interval,
double stepSize,
int maxMinorSteps,
953 if ( maxMinorSteps > 0 )
960 ticks[
i] =
strip( ticks[
i], interval );
972 const QwtInterval &interval,
double stepSize )
const 976 int numTicks = qRound( width / stepSize ) + 1;
977 if ( numTicks > 10000 )
980 const double lxmin = ::log( interval.
minValue() );
981 const double lxmax = ::log( interval.
maxValue() );
982 const double lstep = ( lxmax - lxmin ) /
double( numTicks - 1 );
985 #if QT_VERSION >= 0x040700 986 ticks.reserve( numTicks );
991 for (
int i = 1;
i < numTicks - 1;
i++ )
992 ticks +=
qExp( lxmin +
double(
i ) * lstep );
1009 const QList<double> &majorTicks,
1010 int maxMinorSteps,
double stepSize,
1011 QList<double> &minorTicks,
1012 QList<double> &mediumTicks )
const 1014 const double logBase =
base();
1016 if ( stepSize < 1.1 )
1019 if ( minStep == 0.0 )
1022 const int numSteps = qRound( stepSize / minStep );
1024 int mediumTickIndex = -1;
1025 if ( ( numSteps > 2 ) && ( numSteps % 2 == 0 ) )
1026 mediumTickIndex = numSteps / 2;
1028 for (
int i = 0;
i < majorTicks.count() - 1;
i++ )
1030 const double v = majorTicks[
i];
1031 const double s = logBase / numSteps;
1035 if ( !qFuzzyCompare( s, 1.0 ) )
1036 minorTicks += v * s;
1038 for (
int j = 2; j < numSteps; j++ )
1040 minorTicks += v * j * s;
1045 for (
int j = 1; j < numSteps; j++ )
1047 const double tick = v + j * v * ( logBase - 1 ) / numSteps;
1048 if ( j == mediumTickIndex )
1049 mediumTicks += tick;
1059 if ( minStep == 0.0 )
1062 if ( minStep < 1.0 )
1066 int numTicks = qRound( stepSize / minStep ) - 1;
1070 stepSize, stepSize ) > 0 )
1078 int mediumTickIndex = -1;
1079 if ( ( numTicks > 2 ) && ( numTicks % 2 ) )
1080 mediumTickIndex = numTicks / 2;
1083 const qreal minFactor = qMax( qPow( logBase, minStep ), qreal( logBase ) );
1085 for (
int i = 0;
i < majorTicks.count();
i++ )
1087 double tick = majorTicks[
i];
1088 for (
int j = 0; j < numTicks; j++ )
1092 if ( j == mediumTickIndex )
1093 mediumTicks += tick;
1113 const QwtInterval &interval,
double stepSize )
const
static QwtInterval qwtLogInterval(double base, const QwtInterval &interval)
void setTransformation(QwtTransform *)
QwtInterval limited(double minValue, double maxValue) const
QwtInterval normalized() const
Normalize the limits of the interval.
#define LOG_MAX
Maximum value for logarithmic scales.
QwtLinearScaleEngine(uint base=10)
int qwtFuzzyCompare(double value1, double value2, double intervalSize)
Compare 2 values, relative to an interval.
bool testAttribute(Attribute) const
bool contains(const QwtInterval &, double val) const
A class representing an interval.
#define LOG_MIN
Minimum value for logarithmic scales.
void setMargins(double lower, double upper)
Specify margins at the scale's endpoints.
void buildTicks(const QwtInterval &, double stepSize, int maxMinSteps, QList< double > ticks[QwtScaleDiv::NTickTypes]) const
Calculate ticks for an interval.
A class representing a scale division.
long double widthL() const
Return the width of an interval as long double.
QwtTransform * transformation() const
static double divideInterval(double interval, int numSteps, uint base)
double upperMargin() const
double lowerMargin() const
virtual QwtScaleDiv divideScale(double x1, double x2, int numMajorSteps, int numMinorSteps, double stepSize=0.0) const
Calculate a scale division for an interval.
virtual ~QwtLogScaleEngine()
Destructor.
QwtScaleEngine(uint base=10)
static double qwtLog(double base, double value)
virtual void autoScale(int maxSteps, double &x1, double &x2, double &stepSize) const
void setReference(double reference)
Specify a reference point.
void buildMinorTicks(const QList< double > &majorTicks, int maxMinorSteps, double stepSize, QList< double > &minorTicks, QList< double > &mediumTicks) const
Calculate minor/medium ticks for major ticks.
void buildTicks(const QwtInterval &, double stepSize, int maxMinSteps, QList< double > ticks[QwtScaleDiv::NTickTypes]) const
Calculate ticks for an interval.
void setInterval(double minValue, double maxValue, BorderFlags=IncludeBorders)
virtual ~QwtLinearScaleEngine()
Destructor.
virtual void autoScale(int maxSteps, double &x1, double &x2, double &stepSize) const
virtual QwtScaleDiv divideScale(double x1, double x2, int numMajorSteps, int numMinorSteps, double stepSize=0.0) const
Calculate a scale division for an interval.
static double divideEps(double interval, double steps)
Divide an interval into steps.
TFSIMD_FORCE_INLINE const tfScalar & x() const
Number of valid tick types.
Build a scale which is symmetric to the reference() value.
static double floorEps(double value, double intervalSize)
virtual ~QwtScaleEngine()
Destructor.
void buildMinorTicks(const QList< double > &majorTicks, int maxMinorSteps, double stepSize, QList< double > &minorTicks, QList< double > &mediumTicks) const
Calculate minor/medium ticks for major ticks.
QFlags< Attribute > Attributes
Layout attributes.
QwtInterval align(const QwtInterval &, double stepSize) const
Align an interval to a step size.
static double qwtStepSize(double intervalSize, int maxSteps, uint base)
QList< double > strip(const QList< double > &, const QwtInterval &) const
Turn the scale upside down.
static QwtInterval qwtPowInterval(double base, const QwtInterval &interval)
static double ceilEps(double value, double intervalSize)
Attributes attributes() const
double divideInterval(double interval, int numSteps) const
QList< double > buildMajorTicks(const QwtInterval &interval, double stepSize) const
Calculate major ticks for an interval.
A scale engine for linear scales.
QwtInterval extend(double value) const
Extend the interval.
QwtInterval buildInterval(double v) const
Build an interval around a value.
QwtInterval symmetrize(double value) const
QList< double > buildMajorTicks(const QwtInterval &interval, double stepSize) const
Calculate major ticks for an interval.
double width() const
Return the width of an interval.
Build a scale which includes the reference() value.
QwtScaleEngine::Attributes attributes
QwtLogScaleEngine(uint base=10)
void setAttributes(Attributes)
void setAttribute(Attribute, bool on=true)
QwtInterval align(const QwtInterval &, double stepSize) const
Align an interval to a step size.
Base class for scale engines.