AxisRepBase.cxx
Go to the documentation of this file.
00001 
00012 // for tex
00013 #ifdef HAVE_CONFIG_H
00014 #include "config.h"
00015 #endif
00016 
00017 // for truncation warning
00018 #ifdef _MSC_VER
00019 #include "msdevstudio/MSconfig.h"
00020 #define finite _finite
00021 #endif
00022 
00023 #include "AxisRepBase.h"
00024 
00025 #include "axes/AxisModelBase.h"
00026 #include "graphics/Color.h"
00027 #include "graphics/DataView.h"
00028 #include "pattern/string_convert.h"
00029 #include "transforms/PeriodicBinaryTransform.h"
00030 
00031 #include <cmath>
00032 #include <cassert>
00033 #include <cstdio>
00034 
00035 using std::max;
00036 using std::min;
00037 using std::string;
00038 using std::vector;
00039 using std::sprintf;
00040 #ifdef __USE_ISOC99
00041 using std::isfinite;
00042 #endif
00043 
00044 using namespace hippodraw;
00045 
00046 AxisRepBase::AxisRepBase()
00047   : m_sci_note_x(false), 
00048     m_sci_note_y(false),
00049     m_axis_x_origin (0.),
00050     m_axis_y_origin ( 0.0),
00051     m_axis_width ( 0.0 ),
00052     m_axis_height ( 0.0 ),
00053     m_font_size( 1.0 ), 
00054     m_x_tick_font_size ( 1.0 ),
00055     m_y_tick_font_size ( 1.0 ),
00056     m_x_font_size( 1.0 ), 
00057     m_y_font_size( 1.0 ),
00058     m_xLabelFont( 0 ),
00059     m_yLabelFont( 0 ),
00060     m_zLabelFont( 0 ),
00061     m_titleFont( 0 ),
00062     m_draw_titles( true )
00063 {
00064 }
00065 
00066 AxisRepBase::AxisRepBase( const AxisRepBase & axis_rep )
00067   : m_sci_note_x(axis_rep.m_sci_note_x),
00068     m_sci_note_y(axis_rep.m_sci_note_y),
00069     m_axis_x_origin( axis_rep.m_axis_x_origin ),
00070     m_axis_y_origin( axis_rep.m_axis_y_origin ),
00071     m_axis_width( axis_rep.m_axis_width ),
00072     m_axis_height( axis_rep.m_axis_height ),
00073     m_font_size( axis_rep.m_font_size ),
00074     m_x_font_size( axis_rep.m_x_font_size ),
00075     m_y_font_size( axis_rep.m_y_font_size ),
00076     m_xLabelFont( axis_rep.m_xLabelFont ),
00077     m_yLabelFont( axis_rep.m_yLabelFont ),
00078     m_zLabelFont( axis_rep.m_zLabelFont ),
00079     m_titleFont( axis_rep.m_titleFont ),
00080     m_draw_titles( axis_rep.m_draw_titles )
00081 {
00082 }
00083 
00084 AxisRepBase::~AxisRepBase()
00085 {
00086   delete m_xLabelFont;
00087   delete m_yLabelFont;
00088   delete m_zLabelFont;
00089   delete m_titleFont;
00090 }
00091 
00092 void
00093 AxisRepBase::
00094 initAxisRect( ViewBase & view )
00095 {
00096   const Rect & rect = view.getUserRect();
00097 
00098   m_axis_x_origin = rect.getX();
00099   m_axis_y_origin = rect.getY();
00100   m_axis_width = rect.getWidth();
00101   m_axis_height = rect.getHeight();
00102 }
00103 
00104 void
00105 AxisRepBase::
00106 beginPlot( ViewBase & view )
00107 {
00108   initAxisRect( view );
00109 }
00110 
00111 void AxisRepBase::setDrawTitles( bool set )
00112 {
00113   m_draw_titles = set;
00114 }
00115 
00116 void
00117 AxisRepBase::
00118 drawTitle ( ViewBase & base, const std::string & title )
00119 {
00120 
00121   DataView & view = dynamic_cast < DataView & > ( base );
00122 
00123   // Draw Latex at the top of the plotter if in Latex format
00124 #ifdef HAVE_TEX_UTILS
00125   if (String::ci_find(title, "tex:")==0) {
00126     string tex_snippet = title.substr(4);
00127     view.drawLatex ( tex_snippet, 1 );
00128   }
00129 
00130   else {
00131 #endif
00132     const Rect & marginRect = view.getMarginRect();
00133     float mx = marginRect.getX();
00134     Rect rect = view.getDrawRect ();
00135     float mw = rect.getWidth();
00136     
00137     double x_font_size = ( 1.3 * mw ) / title.size();
00138     m_font_size = min(x_font_size,12.0);
00139     
00140     double one = 1.0;
00141     m_font_size = max ( m_font_size, one );
00142     
00143     float x = mx + 0.5 * marginRect.getWidth ();
00144     float y = 2.0;
00145     
00146     if ( m_titleFont != 0 ) {
00147       view.drawText ( title, x, y, 0.0, 0.0, 'c', 't', false,
00148                       m_titleFont );
00149     } else {
00150       view.drawText ( title, x, y, m_font_size, 0.0, 'c', 't', false );
00151     }
00152 
00153 #ifdef HAVE_TEX_UTILS
00154   }
00155 #endif
00156 }
00157 
00158 void
00159 AxisRepBase::
00160 setXFontSize ( const AxisModelBase & axisModel,
00161                ViewBase & view )
00162 {
00163   Rect draw_rect = view.getDrawRect();
00164   m_x_tick_font_size = min( ( draw_rect.getWidth() ) * 0.040, 12.0 );
00165   double one = 1.0;
00166   m_x_tick_font_size = max ( m_x_tick_font_size, one );
00167 
00168   AxisLoc location = axisModel.getScaleLocation();
00169   
00170   if ( location == PLOTBOTTOM )
00171     {
00172       m_x_font_size = min( (double)m_x_tick_font_size,
00173                            ( m_axis_y_origin -
00174                              draw_rect.getY() ) / 2.0 );
00175     }
00176   else if ( location == PLOTTOP )
00177     {
00178       m_x_font_size = min( (double)m_x_tick_font_size,
00179                            ( draw_rect.getHeight() -
00180                              m_axis_height -
00181                              ( m_axis_y_origin
00182                                - draw_rect.getY() ) ) /2.0 );
00183     }
00184 }
00185 
00186 void
00187 AxisRepBase::
00188 setYFontSize ( const AxisModelBase & axisModel,
00189                ViewBase & view )
00190 {
00191   assert ( m_y_tick_font_size > 0 );
00192 
00193   Rect draw_rect = view.getDrawRect();
00194   double height = draw_rect.getHeight ();
00195   double size = height * 0.040;
00196   size = std::min ( size, 11.0 );
00197   double one = 1.0;
00198   m_y_tick_font_size = std::max ( size, one );
00199   
00200   assert ( m_y_tick_font_size > 0 );
00201   const vector<AxisTick> & labels = axisModel.getTicks ( );
00202   if ( labels.empty () == true ) return;
00203 
00204   if ( axisModel.getScaleLocation() & PLOTLEFT )
00205     {
00206       float yr;
00207       
00208       if ( m_draw_titles && 
00209            axisModel.getLabelLocation() & PLOTLEFT ) {
00210         yr = 14;
00211       } 
00212       else {
00213         yr = 0;
00214       }
00215       const AxisTick & tick = labels.back ( );
00216       m_y_font_size = min ( m_y_tick_font_size, 
00217                            ( m_axis_x_origin -
00218                              draw_rect.getX() - yr )
00219                            / tick.content().size() );
00220     }
00221   else if ( axisModel.getScaleLocation() & PLOTRIGHT )
00222     {
00223       // Estimates the space needed for the Y axis label.
00224       float yr;
00225       if ( m_draw_titles && 
00226            axisModel.getLabelLocation() & PLOTRIGHT ) {
00227         yr = 14;
00228       } else {
00229         yr = 0;
00230       }
00231 
00232       m_y_font_size = min( m_y_tick_font_size, 
00233                    ( draw_rect.getWidth() - 
00234                      m_axis_width - 
00235                      ( m_axis_x_origin - 
00236                        draw_rect.getX() ) - yr )
00237                    / labels[labels.size() - 1].content().size() );
00238     }
00239 }
00240 
00241 void
00242 AxisRepBase::
00243 setZFontSize ( const AxisModelBase & axisModel,
00244                ViewBase & view )
00245 {
00246   AxisLoc location = axisModel.getScaleLocation();
00247   Rect draw_rect = view.getDrawRect();
00248   if ( location == PLOTBOTTOM )
00249     {
00250       m_z_font_size = min( (double)m_font_size,
00251                            ( m_axis_y_origin -
00252                              draw_rect.getY() ) / 2.0 );
00253     }
00254   else if ( location == PLOTTOP )
00255     {
00256       m_z_font_size = min( (double)m_font_size,
00257                            ( draw_rect.getHeight() -
00258                              m_axis_height -
00259                              ( m_axis_y_origin
00260                                - draw_rect.getY() ) ) /2.0 );
00261     }
00262 }
00263 
00264 void
00265 AxisRepBase::
00266 drawXLabels ( const AxisModelBase & axisModel,
00267               ViewBase & base, const std::string & x_label )
00268 {
00269   DataView & view = dynamic_cast < DataView & > ( base );
00270 
00271   // Calculate the ratio of range(rmag) and value(pmag) to decide
00272   // where scientific notation is needed.
00273   const vector< AxisTick > & ticks = axisModel.getTicks();
00274   m_sci_note_x=false;
00275   int mid = ticks.size()/2;
00276   double ref = ticks[mid].value();
00277   double range = ticks[mid+1].value()-ref;
00278   if (fabs(ref/range)>1e6) m_sci_note_x=true;
00279   
00280   // Draw Latex at the bottom of the plotter if in Latex format
00281 #ifdef HAVE_TEX_UTILS
00282   if (String::ci_find(x_label, "tex:")==0) {
00283     string tex_snippet = x_label.substr(4);
00284     if (m_sci_note_x) {
00285       tex_snippet+="-"+ticks[mid].content();
00286       if (axisModel.needPMag()) {
00287         // Use LaTeX to generate: label-mid*10^Pmag
00288         tex_snippet+="\\times 10^"+String::convert ( static_cast <int> (axisModel.getPMag()) );
00289       }
00290     }
00291     view.drawLatex ( tex_snippet, 2 );
00292   }
00293 
00294   else {    
00295 #endif
00296     std::string label;
00297     if (m_sci_note_x) {
00298       label = x_label+" - "+ticks[mid].content();
00299     }
00300     else {
00301       label = x_label;
00302     }
00303     
00304     float x = 0., y = 0.;
00305     Rect draw_rect = view.getDrawRect ();
00306     float draw_h = draw_rect.getHeight ();
00307     float draw_w = draw_rect.getWidth ();
00308     
00309     const Rect & margin_rect = view.getMarginRect ();
00310     float margin_x = margin_rect.getX ();
00311     float margin_w = margin_rect.getWidth ();
00312     
00313     x = margin_x + 0.5 * margin_w;
00314     
00315     float tmp = 0.045 * draw_w;
00316     tmp = max ( tmp, 1.0f );
00317     m_x_font_size = min ( tmp, static_cast<float>( 18.0 ) );
00318     assert ( m_x_font_size > 0 );    
00319     
00320     double ratio = draw_w / ( label.size() ) * 2;
00321     m_x_font_size = std::min ( m_x_font_size, ratio );
00322     assert ( m_x_font_size > 0 );    
00323     double one = 2.0;
00324     m_x_font_size = std::max ( m_x_font_size, one );
00325 
00326     assert ( m_x_font_size > 0 );    
00327     if ( axisModel.getLabelLocation() & PLOTBOTTOM )
00328       {
00329         if ( m_xLabelFont != 0 ) {
00330           y = draw_h - 1.5*m_xLabelFont->pointSize()-6.0; // experimental
00331           view.drawText ( label, x, y, 0., 0.0, 'c', 't',
00332                           false, m_xLabelFont );
00333         } else {
00334           y = draw_h - m_x_font_size - 6.0; // take into account descenders
00335           view.drawText ( label, x, y, m_x_font_size, 0.0, 'c', 't', false );
00336         }
00337       }
00338     else if ( axisModel.getLabelLocation() & PLOTTOP )
00339       {
00340         y = 1.0;
00341         if ( m_xLabelFont != 0 ) {
00342           
00343           view.drawText ( label, x, y, 0.0, 0.0, 'c', 't',
00344                           false, m_xLabelFont );
00345         } else {
00346           
00347           view.drawText ( label, x, y, m_x_font_size, 0.0, 'c', 't', false );
00348         }
00349       }
00350     
00351     
00352     // Draw the mag when both pmag and small range sci_note are needed.
00353     // TODO: handle (location & PLOTTOP)
00354     if ( (m_sci_note_x) && (axisModel.needPMag() ) ){
00355       if ( m_xLabelFont == NULL ) {
00356         x = x+0.27 * m_x_font_size * label.size();
00357         y = y+0.2 * m_x_font_size;
00358         view.drawText ( " x10", x, y, m_x_font_size*0.8, 0.0, 'c', 't', false );
00359         
00360         double pmag = axisModel.getPMag();
00361         int i = static_cast < int > ( pmag );
00362         const string text = String::convert ( i );
00363         x += 1.0 * m_x_font_size ;
00364         y -= 0.4 * m_x_font_size;  
00365         view.drawText ( text, x, y, m_x_font_size*0.8, 0.0, 'c', 't', false );
00366       } else {
00367         x = x+0.4 * m_xLabelFont->pointSize() * label.size();
00368         view.drawText ( " x10", x, y, 0.0, 0.0, 'c', 't', false, m_xLabelFont );
00369         
00370         double pmag = axisModel.getPMag();
00371         int i = static_cast < int > ( pmag );
00372         const string text = String::convert ( i );
00373         x += 1.6 * m_xLabelFont->pointSize() ;
00374         y -= 0.4 * m_xLabelFont->pointSize();
00375         view.drawText ( text, x, y, 0.0, 0.0, 'c', 't', false, m_xLabelFont );
00376       }
00377     }
00378 #ifdef HAVE_TEX_UTILS
00379   }
00380 #endif
00381   
00382 }
00383 void
00384 AxisRepBase::
00385 drawYLabels ( const AxisModelBase & axisModel,
00386               ViewBase & base, const std::string & y_label )
00387 {
00388   DataView & view = dynamic_cast < DataView & > ( base );
00389 
00390   // Calculate the ratio of range(rmag) and value(pmag) to decide
00391   // where scientific notation is needed.
00392   const vector< AxisTick > & ticks = axisModel.getTicks();
00393   m_sci_note_y=false;
00394   int mid = ticks.size()/2;
00395   double ref = ticks[mid].value();
00396   double range = ticks[mid+1].value()-ref;
00397   if (fabs(ref/range)>1e6) m_sci_note_y=true;
00398   
00399   
00400 #ifdef HAVE_TEX_UTILS
00401   // Draw Latex at the left of the plotter if in Latex format
00402   if (String::ci_find(y_label, "tex:")==0) {
00403     string tex_snippet = y_label.substr(4);
00404    
00405     if (m_sci_note_y) {
00406       tex_snippet+="-"+ticks[mid].content();
00407       if (axisModel.needPMag()) {
00408         // Use LaTeX to generate: label-mid*10^Pmag
00409         tex_snippet+="\\times 10^"+String::convert ( static_cast <int> (axisModel.getPMag()) );
00410       }
00411     }
00412 
00413 
00414     view.drawLatex ( tex_snippet, 3 );
00415   }
00416 
00417   else {
00418 #endif
00419 
00420     
00421     std::string label;
00422     if (m_sci_note_y) {
00423       label = y_label+" - "+ticks[mid].content();
00424     }
00425     else {
00426       label = y_label;
00427     }
00428     
00429     Rect draw_rect = view.getDrawRect ();
00430 
00431     float x = 0., y = 0.;
00432     AxisLoc location = axisModel.getLabelLocation();
00433     
00434     //float tmp = min ( view.getDrawRect().getWidth() * 0.05,
00435     //      view.getDrawRect().getHeight() * 0.05 );
00436     float tmp = draw_rect.getHeight() * 0.05;
00437     m_y_font_size = min( tmp, static_cast<float>( 18.0 ) );
00438     m_y_font_size = min( m_y_font_size, draw_rect.getHeight()
00439                          / ( label.size() ) * 2 );
00440     double one = 1.0;
00441     m_y_font_size = max ( m_y_font_size, one );
00442     y = view.getMarginRect().getY() + 
00443       view.getMarginRect().getHeight() *0.5;
00444     
00445     if ( location & PLOTLEFT )
00446       {
00447         x = 2.0;
00448         if ( m_yLabelFont != 0 ) {
00449           view.drawText ( label, x, y, 0.0, 90.0, 'c', 't',
00450                           false, m_yLabelFont );
00451         } else {
00452           view.drawText ( label, x, y, m_y_font_size, 90.0, 'c', 't', false );
00453         }
00454       }
00455     else if ( location & PLOTRIGHT )
00456       {
00457         x = draw_rect.getWidth() - 2.0;
00458         if ( m_yLabelFont != 0 ) {
00459           view.drawText ( label, x, y, 0.0, -90.0, 'c', 't',
00460                           false, m_yLabelFont );
00461         } else {
00462           view.drawText ( label, x, y, m_y_font_size, -90.0, 'c', 't', false );
00463         }
00464       }
00465     
00466     
00467     // Draw the mag when both pmag and small range sci_note are needed.
00468     // TODO: handle (location & PLOTTOP)
00469     if ( (m_sci_note_y) && (axisModel.needPMag() ) ){
00470       if ( m_yLabelFont == NULL ) {
00471         y = y-0.27 * m_y_font_size * label.size();
00472         x = x+0.2 * m_y_font_size;
00473         view.drawText ( " x10", x, y, m_y_font_size*0.8, 90.0, 'c', 't', false );
00474         
00475         double pmag = axisModel.getPMag();
00476         int i = static_cast < int > ( pmag );
00477         const string text = String::convert ( i );
00478         x -= 0.4 * m_y_font_size ;
00479         y -= 1.0 * m_y_font_size;  
00480         view.drawText ( text, x, y, m_y_font_size*0.8, 90.0, 'c', 't', false );
00481       } else {
00482         y = y-0.4 * m_yLabelFont->pointSize() * label.size();
00483         view.drawText ( " x10", x, y, 0.0, 90.0, 'c', 't', false, m_yLabelFont );
00484         
00485         double pmag = axisModel.getPMag();
00486         int i = static_cast < int > ( pmag );
00487         const string text = String::convert ( i );
00488         x -= 0.4 * m_yLabelFont->pointSize() ;
00489         y -= 1.6 * m_yLabelFont->pointSize();
00490         view.drawText ( text, x, y, 0.0, 90.0, 'c', 't', false, m_yLabelFont );
00491       }
00492     }
00493 #ifdef HAVE_TEX_UTILS
00494   }
00495 #endif
00496 }
00497 
00498 void
00499 AxisRepBase::
00500 drawReferencePoint( const AxisModelBase & axisModel, 
00501                     ViewBase & base,
00502                     const std::string & ref)
00503 {
00504   if ( axisModel.getScaleLocation() & PLOTBOTTOM )
00505     {
00506       DataView & view = dynamic_cast < DataView & > ( base );
00507       
00508       const Rect & margin_rect = view.getMarginRect ();
00509       float x = margin_rect.getX() + margin_rect.getWidth ();
00510       
00511       x -= 1 * m_x_tick_font_size * ref.size();
00512       
00513       Rect view_rect = view.getDrawRect ();
00514       float y = + view_rect.getHeight ();
00515       
00516       view.drawText ( "X Ref:"+ref, x, y, m_x_tick_font_size, 0., 'l', 'b' );
00517     }
00518   else if (axisModel.getScaleLocation() & PLOTLEFT)
00519     {
00520       DataView & view = dynamic_cast < DataView & > ( base );
00521 
00522       float x = 2.;
00523       x += m_y_tick_font_size;
00524       
00525       const Rect & margin_rect = view.getMarginRect ();
00526       float y = margin_rect.getY() + 0.2 * m_y_tick_font_size;
00527       
00528       view.drawText ( "Y Ref:"+ref, x, y, m_y_tick_font_size, 0., 'l', 'b' );
00529     }
00530       
00531 }
00532 
00533 
00534 void
00535 AxisRepBase::
00536 drawXMag ( const AxisModelBase & axisModel,
00537            ViewBase & base , const std::string & mag )
00538 {
00539   DataView & view = dynamic_cast < DataView & > ( base );
00540 
00541   const Rect & margin_rect = view.getMarginRect ();
00542   float x = margin_rect.getX() + margin_rect.getWidth ();
00543 
00544   double pmag = axisModel.getPMag();
00545   int i = static_cast<int> (pmag);
00546   const string text = String::convert ( i );
00547   x -= 0.8 * m_x_tick_font_size * text.size();
00548 
00549   Rect view_rect = view.getDrawRect ();
00550   float y = + view_rect.getHeight ();
00551 
00552   view.drawText ( "x10", x, y, 0.75 * m_x_tick_font_size, 0., 'l', 'b' );
00553 
00554   x += 1.25 * m_x_tick_font_size ;
00555   y -= 0.5 * m_x_tick_font_size;
00556 
00557   if (m_sci_note_x) {
00558     view.drawText( mag, x, y, 0.75 * m_x_tick_font_size, 0., 'l', 'b' );
00559   } else {
00560     view.drawText ( text, x, y, 0.75 * m_x_tick_font_size, 0., 'l', 'b' );
00561   }
00562 }
00563 
00564 void
00565 AxisRepBase::
00566 drawYMag ( const AxisModelBase & axisModel,
00567            ViewBase & base, const std::string & mag )
00568 {
00569   DataView & view = dynamic_cast < DataView & > ( base );
00570 
00571   float x = 2.;
00572   if ( axisModel.getScaleLocation() & PLOTLEFT ) {
00573     x += m_y_tick_font_size;
00574   }
00575   else {
00576     x -= m_y_tick_font_size;
00577   }
00578 
00579   const Rect & margin_rect = view.getMarginRect ();
00580   float y = margin_rect.getY() + 0.5 * m_y_tick_font_size;
00581 
00582   view.drawText ( "x10", x, y, m_y_tick_font_size, 0., 'l', 'b' );
00583 
00584   double pmag = axisModel.getPMag();
00585   int i = static_cast < int > ( pmag );
00586   const string text = String::convert ( i );
00587   x += 1.75 * m_y_tick_font_size ;
00588   y -= 0.5 * m_y_tick_font_size;
00589 
00590   if (m_sci_note_y) {
00591     view.drawText ( mag, x, y, m_y_tick_font_size, 0., 'l', 'b' );
00592   } else {
00593     view.drawText ( text, x, y, m_y_tick_font_size, 0., 'l', 'b' );
00594   }
00595 
00596 }
00597 
00598 void
00599 AxisRepBase::
00600 drawAxesLines ( TransformBase & transform, 
00601                 ViewBase & view, 
00602                 const Range & x_range,
00603                 const Range & y_range)
00604 {
00605   const BinaryTransform & t
00606     = dynamic_cast< const BinaryTransform & > ( transform );
00607   vector< double > xv ( 100 );
00608   vector< double > yv ( 100 );
00609   Color black ( 0, 0, 0 );
00610 
00611   xv[0] = x_range.low( );
00612   yv[0] = y_range.low( );
00613   for( int i = 1; i < 100; i++)
00614     {
00615       xv[i] = xv[i-1] + ( x_range.high() - x_range.low() )/99; 
00616       yv[i] = yv[i-1];
00617     }
00618   t.transform( xv, yv );
00619   view.drawPolyLine ( xv, yv, Line::Solid, black, 1 );
00620 
00621   
00622   xv[0] = x_range.high( );
00623   yv[0] = y_range.low( );
00624   for( int i = 1; i < 100; i++)
00625     {
00626       xv[i] = xv[i-1]; 
00627       yv[i] = yv[i-1] + ( y_range.high() - y_range.low() )/99; ;
00628     }
00629   t.transform( xv, yv );
00630   view.drawPolyLine ( xv, yv, Line::Solid, black, 1 );
00631 
00632 
00633   xv[0] = x_range.low( );
00634   yv[0] = y_range.high( );
00635   for( int i = 1; i < 100; i++)
00636     {
00637       xv[i] = xv[i-1] + ( x_range.high() - x_range.low() )/99;  
00638       yv[i] = yv[i-1];
00639     }
00640   
00641   t.transform( xv, yv );
00642   view.drawPolyLine ( xv, yv, Line::Solid, black, 1 );
00643 
00644 
00645   xv[0] = x_range.low( );
00646   yv[0] = y_range.low( );
00647   for( int i = 1; i < 100; i++)
00648     {
00649       xv[i] = xv[i-1];
00650       yv[i] = yv[i-1]  + ( y_range.high() - y_range.low() )/99;  
00651     }
00652   
00653   t.transform( xv, yv );
00654   view.drawPolyLine ( xv, yv, Line::Solid, black, 1 );
00655 
00656   
00657 }
00658 
00659 
00660 
00661 void AxisRepBase::drawGridLines( const AxisModelBase & axisModelX,
00662                                  const AxisModelBase & axisModelY,
00663                                  TransformBase & transform,
00664                                  ViewBase & view )
00665 {
00666   Range x_range = axisModelX.getRange( false );
00667   Range y_range = axisModelY.getRange( false );
00668   
00669     
00670   const vector< AxisTick > & x_ticks = axisModelX.getTicks();
00671   const vector< AxisTick > & y_ticks = axisModelY.getTicks();
00672   
00673   unsigned int nxpoints = 100;
00674   unsigned int nypoints = 100;
00675   vector< double > xv(100), yv(100);
00676   
00677   double user_x, user_y;
00678   Color grey( 180, 180, 180 );
00679     
00680   BinaryTransform & t
00681     = dynamic_cast< BinaryTransform & > ( transform );
00682 
00683   t.validate( x_range, y_range );
00684 
00685   if ( x_ticks.empty () == true || y_ticks.empty () == true ) 
00686     return;
00687 
00688   
00689   double dx = ( x_range.high() - x_range.low() ) / ( nxpoints - 1 );
00690   double dy = ( y_range.high() - y_range.low() ) / ( nypoints - 1 ) ;
00691   
00692     
00693   // Drawing the   coordinates of the aligned along y-Axis 
00694   // i.e.curves for which  x = const
00695   // Don't draw first tick if it will cover the left edge.
00696   for ( unsigned int i = ( x_range.low() == x_ticks[0].value() )?1:0; 
00697         i < x_ticks.size(); i++ )
00698     {
00699       user_x = x_ticks[ i ].value();
00700       
00701       for ( unsigned int j = 0; j < nypoints; j++ )
00702         {
00703           user_y = y_range.low() + j * dy;
00704                   
00705           xv[ j ] = user_x;
00706           yv[ j ] = user_y;
00707           
00708         }
00709       
00710       t.transform( xv, yv );
00711       view.drawPolyLine ( xv, yv, Line::Dot, grey, 0 );
00712       
00713     }
00714   
00715   
00716   // Drawing the   coordinates of the aligned along x-Axis 
00717   // i.e.curves for which  y = const
00718   // Don't draw first tick if it will cover the bottom edge.
00719   for ( unsigned int j = ( y_range.low() == y_ticks[0].value() )?1:0; 
00720         j < y_ticks.size(); j++ )
00721     {
00722       user_y = y_ticks[ j ].value();
00723       
00724       for ( unsigned int i = 0; i < nxpoints; i++ )
00725         {
00726           user_x = x_range.low() + i * dx;
00727         
00728           xv[ i ] = user_x ;
00729           yv[ i ] = user_y ;
00730         }
00731 
00732       t.transform( xv, yv ); 
00733       view.drawPolyLine( xv, yv, Line::Dot, grey, 0 );
00734     }
00735    
00736    return;
00737 }
00738 
00739 void
00740 AxisRepBase::
00741 drawXTickLines( const AxisModelBase & axisModelX,
00742                 const AxisModelBase & axisModelY,
00743                 const TransformBase & transform,
00744                 ViewBase & base )
00745 {
00746   DataView & view = dynamic_cast < DataView & > ( base );
00747   AxisLoc loc = axisModelX.getLabelLocation();
00748   assert( loc == PLOTBOTTOM || PLOTTOP );
00749   
00750   const vector< AxisTick > & ticks = axisModelX.getTicks();
00751   if ( ticks.empty() == true ) return;
00752   
00753   vector< double > xv;
00754   vector< double > yv;
00755 
00756   unsigned int size = 4 * ticks.size();
00757   xv.reserve( size );
00758   yv.reserve( size );
00759 
00760   const BinaryTransform & t
00761     = dynamic_cast< const BinaryTransform & > ( transform );
00762 
00763   const Rect & view_rect = view.getMarginRect();
00764   double tick_length = 0.05 * view_rect.getHeight();
00765   tick_length = min ( tick_length, 8. );  
00766   Range yrange = axisModelY.getRange( false );
00767   
00768   for ( unsigned int i = 0; i < ticks.size(); i++ )
00769     {
00770       double user_x_start = ticks[i].value ();
00771       double user_x_temp = user_x_start;
00772 
00773       double user_by_start = yrange.low();
00774       double user_ty_start = yrange.high();
00775       
00776       // transform will change the x value, so we need the temp
00777       t.transform ( user_x_start, user_by_start );
00778       t.transform ( user_x_temp, user_ty_start );
00779       
00780       double view_x_start = view.userToDrawXAutoInv ( user_x_start );
00781       double view_by_start = view.userToDrawY ( user_by_start );
00782       double view_ty_start = view.userToDrawY ( user_ty_start );
00783       
00784       double view_x_end = view_x_start;
00785       double view_by_end = view_by_start - tick_length;
00786       double view_ty_end = view_ty_start + tick_length;
00787 
00788 #ifdef __USE_ISOC99
00789       if( isfinite( view_x_start ) &&
00790           isfinite( view_by_start ) &&
00791           isfinite( view_ty_start ) &&
00792           isfinite( view_x_start ) &&
00793           isfinite( view_by_end   ) )
00794 #else
00795       if( finite( view_x_start ) &&
00796           finite( view_by_start ) &&
00797           finite( view_ty_start ) &&
00798           finite( view_x_start ) &&
00799           finite( view_by_end   ) )
00800 #endif
00801         {
00802           xv.push_back( view_x_start );
00803           yv.push_back( view_by_start );
00804           xv.push_back( view_x_end );
00805           yv.push_back( view_by_end );
00806 
00807           xv.push_back( view_x_start );
00808           yv.push_back( view_ty_start );
00809           xv.push_back( view_x_end );
00810           yv.push_back( view_ty_end );
00811         }
00812     }
00813   
00814   view.drawViewLines ( xv, yv, Line::Solid, false, 1 );
00815 }
00816 
00817 void 
00818 AxisRepBase::
00819 drawYTickLines ( const AxisModelBase & axisModelX,
00820                  const AxisModelBase & axisModelY,
00821                  const TransformBase & transform,
00822                  ViewBase & base )
00823 {
00824   AxisLoc loc = axisModelY.getLabelLocation ();
00825   assert ( loc == PLOTLEFT || loc == PLOTRIGHT );
00826 
00827   DataView & view = dynamic_cast < DataView & > ( base );
00828   const Rect & draw_rect = view.getMarginRect ();
00829 
00830   double tick_length = 0.05 * draw_rect.getWidth ();
00831   tick_length = min ( tick_length, 8. );
00832 
00833   vector< double > xv;
00834   vector< double > yv; 
00835 
00836   const vector< AxisTick > & ticks = axisModelY.getTicks ();
00837   unsigned int size = ticks.size ();
00838 
00839   if ( size == 0 ) return;
00840 
00841   size *= 4;
00842 
00843   xv.reserve ( size );
00844   yv.reserve ( size );
00845 
00846   const BinaryTransform & t 
00847     = dynamic_cast< const BinaryTransform & > ( transform );
00848 
00849   Range xrange = axisModelX.getRange( false );
00850   
00851   for ( unsigned int i = 0; i < ticks.size(); i++ )
00852     {
00853       double user_lx_start = xrange.low();
00854       double user_rx_start = xrange.high();
00855       double user_y_start = ticks[i].value();
00856       double user_y_temp = user_y_start; // for second call to transform
00857 
00858       // transform modifies its argument, thus we need 2 separate y's
00859       t.transform( user_lx_start, user_y_start );
00860       t.transform( user_rx_start, user_y_temp );
00861       
00862       double view_lx_start = view.userToDrawX( user_lx_start );
00863       double view_rx_start = view.userToDrawX( user_rx_start );
00864       double view_y_start = view.userToDrawY( user_y_start );
00865 
00866       double view_lx_end = view_lx_start + tick_length;
00867       double view_rx_end = view_rx_start - tick_length;
00868       double view_y_end = view_y_start;
00869 
00870 #ifdef __USE_ISOC99
00871       if( isfinite( view_lx_start ) &&
00872           isfinite( view_y_start ) &&
00873           isfinite( view_lx_start ) &&
00874           isfinite( view_y_end   ) )
00875 #else
00876       if( finite( view_lx_start ) &&
00877           finite( view_y_start ) &&
00878           finite( view_lx_start ) &&
00879           finite( view_y_end   ) )
00880 #endif
00881         {
00882           xv.push_back( view_lx_start );
00883           yv.push_back( view_y_start );
00884           xv.push_back( view_lx_end );
00885           yv.push_back( view_y_end );
00886 
00887           xv.push_back( view_rx_start );
00888           yv.push_back( view_y_start );
00889           xv.push_back( view_rx_end );
00890           yv.push_back( view_y_end );
00891         }
00892     }
00893   
00894   view.drawViewLines ( xv, yv, Line::Solid, false, 1 );
00895 }
00896 
00897 void
00898 AxisRepBase::
00899 setFontSize( const AxisModelBase * xAxisModel,
00900              const AxisModelBase * yAxisModel,
00901              const AxisModelBase * zAxisModel,
00902              ViewBase & view )
00903 {
00904   Rect draw_rect = view.getDrawRect();
00905 
00906   m_font_size = min( ( draw_rect.getWidth() ) * 0.040, 12.0 );
00907   m_font_size = min (m_font_size, 12.0);
00908   double one = 1.0;
00909   m_font_size = max ( m_font_size, one );
00910   setXFontSize ( *xAxisModel, view );
00911   setYFontSize ( *yAxisModel, view );
00912   if ( zAxisModel != 0 ) setZFontSize ( *zAxisModel, view );
00913 }
00914 
00915 void
00916 AxisRepBase::
00917 drawXTickLabels ( const AxisModelBase & axisModelX,
00918                   const AxisModelBase & axisModelY,
00919                   const TransformBase & transform, 
00920                   ViewBase & base )
00921 {
00922   double padding  = 1.0;
00923   
00924   vector < double > xv;  
00925   vector < double > yv;  
00926   
00927   const vector < AxisTick > & ticks = axisModelX.getTicks ();
00928   unsigned int size = ticks.size ();
00929   if ( size == 0 ) return;
00930   
00931   xv.reserve ( size );
00932   yv.reserve ( size );
00933   
00934   Range yrange = axisModelY.getRange( false );
00935 
00936   for ( unsigned int i = 0; i < size; i++ ){
00937     xv.push_back ( ticks[i].value () );
00938     yv.push_back ( yrange.low() ); 
00939   }
00940   
00941   const BinaryTransform & t 
00942     = dynamic_cast< const BinaryTransform & > ( transform );
00943   t.transform ( xv, yv );
00944   
00945   // Calculate the Y position in view coordinates.
00946   DataView & view = dynamic_cast < DataView & > ( base );
00947   const Rect & margin = view.getMarginRect ();
00948   float y = margin.getY ();
00949   float x;
00950   char yp = 'b';
00951   
00952   if ( axisModelX.getScaleLocation() & PLOTBOTTOM ) {
00953     y = margin.getY () + margin.getHeight ();
00954     yp = 't';
00955   }
00956 
00957   // If scientific notation is needed, calculate mag.
00958   string mag="";
00959   double ref = 0.;
00960   if (m_sci_note_x) {
00961     int mid = ticks.size()/2;
00962     ref = ticks[mid].value();
00963     double range = ticks[mid+1].value()-ref;
00964     char cstr[8]; 
00965     sprintf(cstr, "%.0e", range);
00966     string str(cstr);
00967     string::size_type pos = str.find ( 'e' );
00968     mag=string( str, pos + 1 ); // exponent
00969   }
00970 
00971   for ( unsigned int i = 0; i < ticks.size(); i++ )
00972     {
00973       // In first stage we calculate the tick. This shall help us get
00974       // the direction of the tick and using it we shall locate where
00975       // to draw the tick labels.
00976       double user_x_start = ticks[i].value();
00977       double user_y_start = yrange.low();
00978             
00979       t.transform( user_x_start, user_y_start );
00980       
00981       double view_x_start = view.userToDrawXAutoInv( user_x_start );
00982       double view_y_start = view.userToDrawY( user_y_start );
00983       
00984       double user_x_end = ticks[i].value ();
00985       double user_y_end = 
00986         yrange.low() + .05 * ( yrange.high() - yrange.low() );
00987       
00988       t.transform( user_x_end, user_y_end );
00989       
00990       double view_x_end = view.userToDrawXAutoInv( user_x_end );
00991       double view_y_end = view.userToDrawY( user_y_end );
00992       
00993       // Calculating the unit vector (ux,uy) in the direction of the tick
00994       double dx = view_x_end - view_x_start;
00995       double dy = view_y_end - view_y_start;
00996       
00997       double ux = dx / sqrt( dx * dx + dy * dy );
00998       double uy = dy / sqrt ( dx * dx + dy * dy );
00999       
01000       // Now calculate the x coord of the end point of the tick by 
01001       // moving a distance "tick_length" starting from view_x_start 
01002      // in the direction of ux. Similarly for y coordinate.
01003       x = view_x_start - ux * padding;
01004       y = view_y_start - uy * padding;
01005       
01006       // Plot the labels now. ( Handle two mode. )
01007       if (m_sci_note_x){
01008         // Draw the difference from reference tick value.
01009         double diff=ticks[i].value()-ref;
01010         // 6 byte should be enough, as small as -1e-99
01011         char pstr[8];    
01012         sprintf(pstr, "%.0e", diff);
01013         const std::string str(pstr);
01014         string::size_type pos = str.find ( 'e' );
01015         string m ( str, 0, pos ); // mantessa
01016         string e ( str, pos + 1 ); // exponent
01017         // Is this safe ?
01018         if (e!=mag && m!="0") m+="0";
01019         drawXTickLabel ( m, x, y,  view );
01020       }
01021       else {
01022         // Draw the content of the ticks.
01023         drawXTickLabel ( ticks[i].content(), x, y, view );
01024       }
01025     }
01026   
01027   // Draw sct_note reference point or pmag.
01028   if (m_sci_note_x) {
01029     drawXMag( axisModelX, view, mag );
01030     //drawXLabels(axisModelX, view, "X="+ticks[mid].content());
01031     //drawReferencePoint( axisModelX, view, ticks[mid].content());
01032   }
01033     
01034     else if ( axisModelX.needPMag () )
01035     {
01036       // Logarithmic graphs do not need the magnitude written.
01037       if ( axisModelX.isLog () == false ) {
01038         drawXMag ( axisModelX, view );
01039       }
01040     }
01041 }
01042 
01043 void
01044 AxisRepBase::
01045 drawYTickLabels ( const AxisModelBase & axisModelX,
01046                   const AxisModelBase & axisModelY,
01047                   const TransformBase & transform,
01048                   ViewBase & view )
01049 {
01050   double padding  = 2.0;
01051 
01052   const vector< AxisTick > & ticks = axisModelY.getTicks ();
01053   unsigned int size = ticks.size ();
01054   if ( size == 0 ) return;
01055 
01056   const BinaryTransform & t 
01057     = dynamic_cast< const BinaryTransform & > ( transform );
01058 
01059   Range xrange = axisModelX.getRange( false );
01060 
01061   // If scientific notation is needed, calculate mag.
01062   string mag="";
01063   double ref = 0.;
01064   if (m_sci_note_y) {
01065     int mid = ticks.size()/2;
01066     ref = ticks[mid].value();
01067     double range = ticks[mid+1].value()-ref;
01068     char cstr[8]; 
01069     sprintf(cstr, "%.0e", range);
01070     string str(cstr);
01071     string::size_type pos = str.find ( 'e' );
01072     mag=string( str, pos + 1 ); // exponent
01073   }
01074 
01075   for ( unsigned int i = 0; i < ticks.size(); i++ )
01076     {
01077       // In first stage we calculate the tick. This shall help us get
01078       // the direction of the tick and using it we shall locate where
01079       // to draw the tick labels.
01080       double user_x_start = xrange.low();
01081       double user_y_start = ticks[i].value();
01082             
01083       t.transform( user_x_start, user_y_start );
01084       
01085       double view_x_start = view.userToDrawX( user_x_start );
01086       double view_y_start = view.userToDrawY( user_y_start );
01087       
01088       double user_x_end 
01089         = xrange.low() + .05 * ( xrange.high() - xrange.low() );
01090       double user_y_end = ticks[i].value ();
01091       
01092       t.transform( user_x_end, user_y_end );
01093       
01094       double view_x_end = view.userToDrawX( user_x_end );
01095       double view_y_end = view.userToDrawY( user_y_end );
01096 
01097       // Calculating the unit vector (ux,uy) in the direction of the tick
01098       double dx = view_x_end - view_x_start;
01099       double dy = view_y_end - view_y_start;
01100       
01101       double ux = dx / sqrt( dx * dx + dy * dy );
01102       double uy = dy / sqrt ( dx * dx + dy * dy );
01103 
01104       // Now calculate the x coord of the end point of the tick by 
01105       // moving a distance "tick_length" starting from view_x_start 
01106       // in the direction of ux. Similarly for y coordinate.
01107       float x = view_x_start - ux * padding;
01108       float y = view_y_start - uy * 1.5;
01109 
01110       // Plot the labels now. ( Handle two mode. )
01111       if (m_sci_note_y){
01112         // Draw the difference from reference tick value.
01113         double diff=ticks[i].value()-ref;
01114         // 6 byte should be enough, as small as -1e-99
01115         char pstr[8];    
01116         sprintf(pstr, "%.0e", diff);
01117         const std::string str(pstr);
01118         string::size_type pos = str.find ( 'e' );
01119         string m ( str, 0, pos ); // mantessa
01120         string e ( str, pos + 1 ); // exponent
01121         // Is this safe?
01122         if (e!=mag && m!="0") m+="0";
01123         drawYTickLabel ( m, x, y,  view );
01124       }
01125       else {
01126         // Draw the content of the ticks.
01127         drawYTickLabel ( ticks[i].content(), x, y, view );
01128       }
01129     } 
01130 
01131   
01132   // Draw pmag.
01133   if (m_sci_note_y) {
01134     drawYMag( axisModelY, view, mag );
01135   }
01136     
01137   else if ( axisModelY.needPMag () ){
01138     // Logarithmic graphs do not need the magnitude written.
01139     if ( axisModelY.isLog () == false ) {
01140       drawYMag ( axisModelY, view );
01141     }
01142   }
01143 }
01144 
01145 void
01146 AxisRepBase::
01147 drawXTickLabel ( const std::string & label, float x, float y, ViewBase & view )
01148 {
01149   char xalign = 'c';
01150   char yalign = 't';
01151   float angle = 0.;
01152   double & font_size = m_x_tick_font_size;
01153 
01154   string::size_type pos = label.find ( 'e' );
01155   if ( pos == string::npos ) {
01156     view.drawText ( label, x, y, m_x_tick_font_size, angle, xalign, yalign );
01157   }
01158   else {  // need superscript
01159     double ss_size = 0.9 * font_size;
01160     string m ( label, 0, pos ); // mantessa
01161     string e ( label, pos + 1 ); // exponent
01162     if ( m == "1" ) { 
01163       m += "0";
01164       x += 0.25 * font_size; // don't know why this is needed.
01165       y += 0.25 * ss_size;
01166       view.drawText ( m, x, y, font_size, angle, 'r', yalign );
01167 
01168       if ( e[0] == '-' ) {
01169         x -= 0.10 * font_size;
01170       }
01171       y -= 0.5 * ss_size;
01172       view.drawText ( e, x, y, ss_size, angle, 'l', yalign );
01173     }
01174     else { // m != 1
01175       m += "x10";
01176       x += 0.25 * font_size;
01177       y += 0.25 * ss_size;
01178       view.drawText ( m, x, y, font_size, angle, 'r', yalign );
01179 
01180       if ( e[0] == '-' ) {
01181         x -= 0.10 * font_size;
01182       }
01183       y -= 0.5 * ss_size;
01184       view.drawText ( e, x, y, ss_size, angle, 'l', yalign );
01185     }
01186   }
01187 }
01188 
01189 
01190 void 
01191 AxisRepBase::
01192 drawYTickLabel ( const std::string & label,
01193                  float x, float y,
01194                  ViewBase & view )
01195 {
01196   char xalign = 'r';
01197   char yalign = 'c';
01198   float angle = 0.;
01199   double font_size = m_y_tick_font_size;
01200 
01201   string::size_type pos = label.find ( 'e' );  
01202   if ( pos == string::npos ) {
01203       view.drawText ( label, x, y, font_size, angle, xalign, yalign );
01204     }
01205 
01206   else {  // need superscript
01207     string m ( label, 0, pos ); // mantessa
01208     string e ( label, pos + 1 ); // exponent
01209  
01210     if ( m == "1" ) { 
01211       m += "0";
01212       x = x - 0.40 * font_size * e.size();
01213       view.drawText ( m, x, y, font_size, angle, xalign, yalign );
01214       
01215       if ( e[0] == '-' ) {
01216         x -= 0.20 * font_size;
01217       }
01218       y = y - 0.625 * font_size;
01219       view.drawText ( e, x, y, 0.9 * font_size, angle, 'l', yalign );
01220     }
01221     else { // m != '1' and need to leave room for label
01222       m += "x10";
01223       x = x - 0.40 * font_size * e.size();
01224       view.drawText (m, x, y, font_size, angle, xalign, yalign );
01225       
01226       if ( e[0] == '-' ) {
01227         x -= 0.20 * font_size;
01228       }
01229       y = y - 0.625 * font_size;
01230       view.drawText ( e, x, y, 0.9 * font_size, angle, 'l', yalign );
01231     } 
01232   }
01233 }
01234 
01235 
01236 void
01237 AxisRepBase::
01238 drawYTickLabels ( const std::vector < AxisTick > & ticks,
01239                   const std::vector < float > & xv,
01240                   const std::vector < float> & yv,
01241                   ViewBase & view)
01242 {
01243   char xalign = 'r';
01244   char yalign = 'c';
01245   float angle = 0.;
01246   double font_size = m_y_tick_font_size;
01247 
01248   const string & alabel = ticks[0].content();
01249   string::size_type pos = alabel.find ( 'e' );
01250   bool sci_notate = pos != string::npos;
01251 
01252   if ( sci_notate == false ) {
01253     for ( unsigned int i = 0; i < ticks.size(); i++ ) {
01254       view.drawText ( ticks[i].content(), xv[i], yv[i],
01255                       font_size, angle, xalign, yalign );
01256     }
01257   }
01258   else {  // need superscript
01259     bool mixed_m = false;
01260     for ( unsigned int i = 0; i < ticks.size (); i++ ) {
01261       const string & label = ticks[i].content ();
01262       string m ( label, 0, pos ); // mantessa
01263       string e ( label, pos + 1 ); // exponent
01264       mixed_m |= m != "1";
01265     }
01266     if ( mixed_m == true ) {
01267       font_size *= 0.90;
01268     }
01269     for ( unsigned int i = 0; i < ticks.size (); i++ ) {
01270       const string & label = ticks[i].content();
01271       string::size_type pos = alabel.find ( 'e' );
01272       string m ( label, 0, pos );
01273       string e ( label, pos + 1 );
01274       if ( m == "1" ) { 
01275         m += "0";
01276         float x = xv[i] - 0.40 * font_size * e.size();
01277         view.drawText ( m, x, yv[i], font_size, angle, xalign, yalign );
01278 
01279         if ( e[0] == '-' ) {
01280           x -= 0.20 * font_size;
01281         }
01282         float y = yv[i] - 0.625 * font_size;
01283         view.drawText ( e, x, y, 0.9 * font_size, angle, 'l', yalign );
01284       }
01285       else { // m != '1' and need to leave room for label
01286         m += "x10";
01287         float x = xv[i] - 0.40 * font_size * e.size();
01288         view.drawText (m, x, yv[i], font_size, angle, xalign, yalign );
01289 
01290         if ( e[0] == '-' ) {
01291           x -= 0.20 * font_size;
01292         }
01293         float y = yv[i] - 0.625 * font_size;
01294         view.drawText ( e, x, y, 0.9 * font_size, angle, 'l', yalign );
01295       }
01296     }
01297   }
01298 }
01299 
01300 void
01301 AxisRepBase::
01302 drawCrossHairs ( double x, double y,
01303                  TransformBase & tb,
01304                  ViewBase & view )
01305 {
01306 
01307   vector < double > xv ( 4 );
01308   vector < double > yv ( 4 );
01309   
01310 
01311    const BinaryTransform & tf
01312     = dynamic_cast< const BinaryTransform & > ( tb );
01313 
01314   if ( tf.isPeriodic() )
01315     {
01316       const PeriodicBinaryTransform & tp 
01317         = dynamic_cast < const PeriodicBinaryTransform & > ( tb );
01318       
01319       double xoffset = tp.xOffset();
01320       double yoffset = tp.yOffset();
01321       
01322       x   = tp.moduloSubX( x, xoffset );
01323       y   = tp.moduloSubY( y, yoffset );
01324     }
01325   
01326   tf.transform ( x,y );
01327   
01328   xv[0] = m_axis_x_origin;
01329   yv[0] = y;
01330   
01331   xv[1] = m_axis_width + m_axis_x_origin;
01332   yv[1] = y;
01333 
01334   xv[2] = x;
01335   yv[2] = m_axis_height + m_axis_y_origin;
01336 
01337   xv[3] = x;
01338   yv[3] = m_axis_y_origin;
01339 
01340   // Note: m_axis_* is already in the transformed system.
01341   Color grey ( 180, 180, 180 );
01342   view.drawLines ( xv, yv, Line::Solid, grey, 0 );
01343 
01344 }
01345 
01350 void
01351 AxisRepBase::
01352 drawAllXTicks ( const AxisModelBase & axisModelX,
01353                 const AxisModelBase & axisModelY,
01354                 const TransformBase & transform,
01355                 ViewBase & view )
01356 {
01357   drawXTickLines ( axisModelX, axisModelY, transform, view );
01358   drawXTickLabels ( axisModelX, axisModelY, transform, view );
01359 }
01360 
01361 void
01362 AxisRepBase::
01363 drawAllYTicks ( const AxisModelBase & axisModelX,
01364                 const AxisModelBase & axisModelY,
01365                 const TransformBase & transform,
01366                                    ViewBase & view )
01367 {
01368   drawYTickLines ( axisModelX, axisModelY, transform, view );
01369   drawYTickLabels ( axisModelX, axisModelY, transform, view );
01370 }
01371 
01372 
01373 void AxisRepBase::setXLabelFont( FontBase* font )
01374 {
01375   assert( font != 0 );
01376   if( m_xLabelFont == NULL )
01377     m_xLabelFont = font;
01378   else
01379     {
01380       delete m_xLabelFont;
01381       m_xLabelFont = font;
01382     }
01383 }
01384 
01385 FontBase* AxisRepBase::xLabelFont( )
01386 {
01387   return m_xLabelFont;
01388 }
01389 
01390 
01391 void AxisRepBase::setYLabelFont( FontBase* font )
01392 {
01393   assert( font != 0 );
01394   if( m_yLabelFont == NULL )
01395     m_yLabelFont = font;
01396   else
01397     {
01398       delete m_yLabelFont;
01399       m_yLabelFont = font;
01400     }
01401 }
01402 
01403 FontBase* AxisRepBase::yLabelFont( )
01404 {
01405   return m_yLabelFont;
01406 }
01407 
01408 
01409 void AxisRepBase::setZLabelFont( FontBase* font )
01410 {
01411   assert( font != 0 );
01412   if( m_zLabelFont == NULL )
01413     m_zLabelFont = font;
01414   else
01415     {
01416       delete m_zLabelFont;
01417       m_zLabelFont = font;
01418     }
01419 }
01420 
01421 FontBase* AxisRepBase::zLabelFont( )
01422 {
01423   return m_zLabelFont;
01424 }
01425 
01426 void AxisRepBase::setTitleFont( FontBase* font )
01427 {
01428   assert( font != 0 );
01429   if( m_titleFont == NULL )
01430     m_titleFont = font;
01431   else
01432     {
01433       delete m_titleFont;
01434       m_titleFont = font;
01435     }
01436 }
01437 
01438 FontBase* AxisRepBase::titleFont( )
01439 {
01440   return m_titleFont;
01441 }
01442 
01443 void
01444 AxisRepBase::drawColorScale ( const BinToColor &, ViewBase & )
01445 {
01446   assert ( false );
01447 }

Generated for HippoDraw Class Library by doxygen