00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012 #include <qpainter.h>
00013 #include <qpalette.h>
00014 #include <qmap.h>
00015 #include <qlocale.h>
00016 #include "qwt_math.h"
00017 #include "qwt_text.h"
00018 #include "qwt_painter.h"
00019 #include "qwt_scale_map.h"
00020 #include "qwt_scale_draw.h"
00021
00022 class QwtAbstractScaleDraw::PrivateData
00023 {
00024 public:
00025 PrivateData():
00026 components(Backbone | Ticks | Labels),
00027 spacing(4),
00028 minExtent(0)
00029 {
00030 tickLength[QwtScaleDiv::MinorTick] = 4;
00031 tickLength[QwtScaleDiv::MediumTick] = 6;
00032 tickLength[QwtScaleDiv::MajorTick] = 8;
00033 }
00034
00035 int components;
00036
00037 QwtScaleMap map;
00038 QwtScaleDiv scldiv;
00039
00040 int spacing;
00041 int tickLength[QwtScaleDiv::NTickTypes];
00042
00043 int minExtent;
00044
00045 QMap<double, QwtText> labelCache;
00046 };
00047
00055 QwtAbstractScaleDraw::QwtAbstractScaleDraw()
00056 {
00057 d_data = new QwtAbstractScaleDraw::PrivateData;
00058 }
00059
00061 QwtAbstractScaleDraw::QwtAbstractScaleDraw(const QwtAbstractScaleDraw &other)
00062 {
00063 d_data = new QwtAbstractScaleDraw::PrivateData(*other.d_data);
00064 }
00065
00067 QwtAbstractScaleDraw::~QwtAbstractScaleDraw()
00068 {
00069 delete d_data;
00070 }
00072 QwtAbstractScaleDraw &QwtAbstractScaleDraw::operator=(const QwtAbstractScaleDraw &other)
00073 {
00074 *d_data = *other.d_data;
00075 return *this;
00076 }
00077
00086 void QwtAbstractScaleDraw::enableComponent(
00087 ScaleComponent component, bool enable)
00088 {
00089 if ( enable )
00090 d_data->components |= component;
00091 else
00092 d_data->components &= ~component;
00093 }
00094
00099 bool QwtAbstractScaleDraw::hasComponent(ScaleComponent component) const
00100 {
00101 return (d_data->components & component);
00102 }
00103
00108 void QwtAbstractScaleDraw::setScaleDiv(const QwtScaleDiv &sd)
00109 {
00110 d_data->scldiv = sd;
00111 d_data->map.setScaleInterval(sd.lBound(), sd.hBound());
00112 d_data->labelCache.clear();
00113 }
00114
00119 void QwtAbstractScaleDraw::setTransformation(
00120 QwtScaleTransformation *transformation)
00121 {
00122 d_data->map.setTransformation(transformation);
00123 }
00124
00126 const QwtScaleMap &QwtAbstractScaleDraw::map() const
00127 {
00128 return d_data->map;
00129 }
00130
00132 QwtScaleMap &QwtAbstractScaleDraw::scaleMap()
00133 {
00134 return d_data->map;
00135 }
00136
00138 const QwtScaleDiv& QwtAbstractScaleDraw::scaleDiv() const
00139 {
00140 return d_data->scldiv;
00141 }
00142
00143 #if QT_VERSION < 0x040000
00144
00152 void QwtAbstractScaleDraw::draw(QPainter *painter,
00153 const QColorGroup& colorGroup) const
00154
00155 #else
00156
00165 void QwtAbstractScaleDraw::draw(QPainter *painter,
00166 const QPalette& palette) const
00167 #endif
00168 {
00169 if ( hasComponent(QwtAbstractScaleDraw::Labels) )
00170 {
00171 painter->save();
00172
00173 #if QT_VERSION < 0x040000
00174 painter->setPen(colorGroup.text());
00175 #else
00176 painter->setPen(palette.color(QPalette::Text));
00177 #endif
00178
00179 const QwtValueList &majorTicks =
00180 d_data->scldiv.ticks(QwtScaleDiv::MajorTick);
00181
00182 for (int i = 0; i < (int)majorTicks.count(); i++)
00183 {
00184 const double v = majorTicks[i];
00185 if ( d_data->scldiv.contains(v) )
00186 drawLabel(painter, majorTicks[i]);
00187 }
00188
00189 painter->restore();
00190 }
00191
00192 if ( hasComponent(QwtAbstractScaleDraw::Ticks) )
00193 {
00194 painter->save();
00195
00196 QPen pen = painter->pen();
00197 #if QT_VERSION < 0x040000
00198 pen.setColor(colorGroup.foreground());
00199 #else
00200 pen.setColor(palette.color(QPalette::Foreground));
00201 #endif
00202 painter->setPen(pen);
00203
00204 for ( int tickType = QwtScaleDiv::MinorTick;
00205 tickType < QwtScaleDiv::NTickTypes; tickType++ )
00206 {
00207 const QwtValueList &ticks = d_data->scldiv.ticks(tickType);
00208 for (int i = 0; i < (int)ticks.count(); i++)
00209 {
00210 const double v = ticks[i];
00211 if ( d_data->scldiv.contains(v) )
00212 drawTick(painter, v, d_data->tickLength[tickType]);
00213 }
00214 }
00215
00216 painter->restore();
00217 }
00218
00219 if ( hasComponent(QwtAbstractScaleDraw::Backbone) )
00220 {
00221 painter->save();
00222
00223 QPen pen = painter->pen();
00224 #if QT_VERSION < 0x040000
00225 pen.setColor(colorGroup.foreground());
00226 #else
00227 pen.setColor(palette.color(QPalette::Foreground));
00228 #endif
00229 painter->setPen(pen);
00230
00231 drawBackbone(painter);
00232
00233 painter->restore();
00234 }
00235 }
00236
00247 void QwtAbstractScaleDraw::setSpacing(int spacing)
00248 {
00249 if ( spacing < 0 )
00250 spacing = 0;
00251
00252 d_data->spacing = spacing;
00253 }
00254
00263 int QwtAbstractScaleDraw::spacing() const
00264 {
00265 return d_data->spacing;
00266 }
00267
00281 void QwtAbstractScaleDraw::setMinimumExtent(int minExtent)
00282 {
00283 if ( minExtent < 0 )
00284 minExtent = 0;
00285
00286 d_data->minExtent = minExtent;
00287 }
00288
00293 int QwtAbstractScaleDraw::minimumExtent() const
00294 {
00295 return d_data->minExtent;
00296 }
00297
00306 void QwtAbstractScaleDraw::setTickLength(
00307 QwtScaleDiv::TickType tickType, int length)
00308 {
00309 if ( tickType < QwtScaleDiv::MinorTick ||
00310 tickType > QwtScaleDiv::MajorTick )
00311 {
00312 return;
00313 }
00314
00315 if ( length < 0 )
00316 length = 0;
00317
00318 const int maxTickLen = 1000;
00319 if ( length > maxTickLen )
00320 length = 1000;
00321
00322 d_data->tickLength[tickType] = length;
00323 }
00324
00331 int QwtAbstractScaleDraw::tickLength(QwtScaleDiv::TickType tickType) const
00332 {
00333 if ( tickType < QwtScaleDiv::MinorTick ||
00334 tickType > QwtScaleDiv::MajorTick )
00335 {
00336 return 0;
00337 }
00338
00339 return d_data->tickLength[tickType];
00340 }
00341
00345 int QwtAbstractScaleDraw::majTickLength() const
00346 {
00347 return d_data->tickLength[QwtScaleDiv::MajorTick];
00348 }
00349
00361 QwtText QwtAbstractScaleDraw::label(double value) const
00362 {
00363 return QLocale::system().toString(value);
00364 }
00365
00379 const QwtText &QwtAbstractScaleDraw::tickLabel(
00380 const QFont &font, double value) const
00381 {
00382 QMap<double, QwtText>::const_iterator it = d_data->labelCache.find(value);
00383 if ( it == d_data->labelCache.end() )
00384 {
00385 QwtText lbl = label(value);
00386 lbl.setRenderFlags(0);
00387 lbl.setLayoutAttribute(QwtText::MinimumLayout);
00388
00389 (void)lbl.textSize(font);
00390
00391 it = d_data->labelCache.insert(value, lbl);
00392 }
00393
00394 return (*it);
00395 }
00396
00404 void QwtAbstractScaleDraw::invalidateCache()
00405 {
00406 d_data->labelCache.clear();
00407 }