Salome HOME
82d1721766fdf80c85495ad62794494e0b016810
[modules/gui.git] / src / Plot2d / Plot2d_ViewFrame.cxx
1 #include "Plot2d_ViewFrame.h"
2
3 #include "Plot2d_Prs.h"
4 #include "Plot2d_Curve.h"
5 #include "Plot2d_FitDataDlg.h"
6 #include "Plot2d_ViewWindow.h"
7 #include "Plot2d_SetupViewDlg.h"
8
9 #include "SUIT_Tools.h"
10 #include "SUIT_Session.h"
11 #include "SUIT_MessageBox.h"
12 #include "SUIT_ResourceMgr.h"
13 #include "SUIT_Application.h"
14
15 #include "qapplication.h"
16 #include <qtoolbar.h>
17 #include <qtoolbutton.h>
18 #include <qcursor.h>
19 #include <qcolordialog.h>
20 #include <qptrlist.h>
21 #include <qlayout.h>
22 #include <qmap.h>
23
24 #include <qwt_math.h>
25 #include <qwt_plot_canvas.h>
26 #include <iostream>
27 #include <stdlib.h>
28
29 #include <qwt_legend.h>
30
31 #define DEFAULT_LINE_WIDTH     0     // (default) line width
32 #define DEFAULT_MARKER_SIZE    9     // default marker size
33 #define MIN_RECT_SIZE          11    // min sensibility area size
34
35 const char* imageZoomCursor[] = { 
36 "32 32 3 1",
37 ". c None",
38 "a c #000000",
39 "# c #ffffff",
40 "................................",
41 "................................",
42 ".#######........................",
43 "..aaaaaaa.......................",
44 "................................",
45 ".............#####..............",
46 "...........##.aaaa##............",
47 "..........#.aa.....a#...........",
48 ".........#.a.........#..........",
49 ".........#a..........#a.........",
50 "........#.a...........#.........",
51 "........#a............#a........",
52 "........#a............#a........",
53 "........#a............#a........",
54 "........#a............#a........",
55 ".........#...........#.a........",
56 ".........#a..........#a.........",
57 ".........##.........#.a.........",
58 "........#####.....##.a..........",
59 ".......###aaa#####.aa...........",
60 "......###aa...aaaaa.......#.....",
61 ".....###aa................#a....",
62 "....###aa.................#a....",
63 "...###aa...............#######..",
64 "....#aa.................aa#aaaa.",
65 ".....a....................#a....",
66 "..........................#a....",
67 "...........................a....",
68 "................................",
69 "................................",
70 "................................",
71 "................................"};
72
73 const char* imageCrossCursor[] = { 
74   "32 32 3 1",
75   ". c None",
76   "a c #000000",
77   "# c #ffffff",
78   "................................",
79   "................................",
80   "................................",
81   "................................",
82   "................................",
83   "................................",
84   "................................",
85   "...............#................",
86   "...............#a...............",
87   "...............#a...............",
88   "...............#a...............",
89   "...............#a...............",
90   "...............#a...............",
91   "...............#a...............",
92   "...............#a...............",
93   ".......#################........",
94   "........aaaaaaa#aaaaaaaaa.......",
95   "...............#a...............",
96   "...............#a...............",
97   "...............#a...............",
98   "...............#a...............",
99   "...............#a...............",
100   "...............#a...............",
101   "...............#a...............",
102   "................a...............",
103   "................................",
104   "................................",
105   "................................",
106   "................................",
107   "................................",
108   "................................",
109   "................................"};
110   
111
112 QPixmap zoomPixmap(imageZoomCursor);
113 QPixmap globalPanPixmap(imageCrossCursor);
114
115 QCursor panCursor(Qt::SizeAllCursor);
116 QCursor zoomCursor(zoomPixmap);
117 QCursor glPanCursor(globalPanPixmap);
118
119 //=================================================================================
120 // Plot2d_ViewFrame implementation
121 //=================================================================================
122
123 /*!
124   Constructor
125 */
126 Plot2d_ViewFrame::Plot2d_ViewFrame( QWidget* parent, const QString& title )
127      : QWidget (parent, title, 0),
128        myOperation( NoOpId ), 
129        myCurveType( 1 ), 
130        myShowLegend( true ), myLegendPos( 1 ),
131        myMarkerSize( DEFAULT_MARKER_SIZE ),
132        myTitle( "" ), myXTitle( "" ), myYTitle( "" ), myY2Title( "" ),
133        myBackground( white ),
134        myTitleEnabled( true ), myXTitleEnabled( true ),
135        myYTitleEnabled( true ), myY2TitleEnabled (true),
136        myXGridMajorEnabled( true ), myYGridMajorEnabled( true ), myY2GridMajorEnabled( true ), 
137        myXGridMinorEnabled( false ), myYGridMinorEnabled( false ), myY2GridMinorEnabled( false ),
138        myXGridMaxMajor( 8 ), myYGridMaxMajor( 8 ), myY2GridMaxMajor( 8 ),
139        myXGridMaxMinor( 5 ), myYGridMaxMinor( 5 ), myY2GridMaxMinor( 5 ),
140        myXMode( 0 ), myYMode( 0 ), mySecondY( false )
141 {
142   /* Plot 2d View */
143   QVBoxLayout* aLayout = new QVBoxLayout( this ); 
144   myPlot = new Plot2d_Plot2d( this );
145   aLayout->addWidget( myPlot );
146
147 //  createActions();
148
149   connect( myPlot, SIGNAL( plotMouseMoved( const QMouseEvent& ) ),
150      this,   SLOT( plotMouseMoved( const QMouseEvent& ) ) );
151   connect( myPlot, SIGNAL( plotMousePressed( const QMouseEvent& ) ),
152      this,   SLOT( plotMousePressed( const QMouseEvent& ) ) );
153   connect( myPlot, SIGNAL( plotMouseReleased( const QMouseEvent& ) ),
154      this,   SLOT( plotMouseReleased( const QMouseEvent& ) ) );
155   //connect( myPlot, SIGNAL( legendClicked( long ) ),
156   //   this,   SLOT( onLegendClicked( long ) ) );
157
158   /* Initial Setup - get from the preferences */
159   readPreferences();
160
161   myPlot->setMargin( 5 );
162   setCurveType( myCurveType, false );
163   setXGrid( myXGridMajorEnabled, myXGridMaxMajor, myXGridMinorEnabled, myXGridMaxMinor, false );
164   setYGrid( myYGridMajorEnabled, myYGridMaxMajor, myYGridMinorEnabled, myYGridMaxMinor,
165             myY2GridMajorEnabled, myY2GridMaxMajor, myY2GridMinorEnabled, myY2GridMaxMinor, false );
166
167   setTitle( myTitleEnabled,  myTitle,  MainTitle, false );
168   setTitle( myXTitleEnabled, myXTitle, XTitle, false );
169   setTitle( myYTitleEnabled, myYTitle, YTitle, false );
170
171   if (mySecondY)
172     setTitle( myY2TitleEnabled, myY2Title, Y2Title, false );
173   setHorScaleMode( myXMode, false );
174   setVerScaleMode( myYMode, false );
175   setBackgroundColor( myBackground );
176   setLegendPos( myLegendPos );
177   showLegend( myShowLegend, false );
178   myPlot->replot();
179
180   if ( parent ) {
181     resize( (int)(0.8 * parent->width()), (int)(0.8 * parent->height()) );
182   }
183   QwtDiMap xMap = myPlot->canvasMap( QwtPlot::xBottom );
184   QwtDiMap yMap = myPlot->canvasMap( QwtPlot::yLeft );
185   myXDistance = xMap.d2() - xMap.d1();
186   myYDistance = yMap.d2() - yMap.d1();
187   myYDistance2 = 0;
188   if (mySecondY) {
189     QwtDiMap yMap2 = myPlot->canvasMap( QwtPlot::yRight );
190     myYDistance2 = yMap2.d2() - yMap2.d1();
191   }
192 }
193 /*!
194   Destructor
195 */
196 Plot2d_ViewFrame::~Plot2d_ViewFrame()
197 {
198 }
199 /*!
200   Gets window's central widget
201 */
202 QWidget* Plot2d_ViewFrame::getViewWidget()
203 {
204   return (QWidget*)myPlot;
205 }
206 /*!
207   Actually this method just re-displays all curves which are presented in the viewer
208 */
209 void Plot2d_ViewFrame::DisplayAll()
210 {
211   QList<Plot2d_Curve> clist;
212   getCurves( clist );
213   for ( int i = 0; i < (int)clist.count(); i++ ) {
214     updateCurve( clist.at( i ), false );
215   }
216   myPlot->replot();
217 }
218 /*!
219    Removes all curves from the view
220 */
221 void Plot2d_ViewFrame::EraseAll() 
222 {
223   myPlot->clear();
224   myCurves.clear();
225   myPlot->replot();
226 }
227 /*!
228   Redraws viewframe contents
229 */
230 void Plot2d_ViewFrame::Repaint()
231 {
232   myPlot->replot();
233 }
234 /*!
235   Display presentation
236 */
237 void Plot2d_ViewFrame::Display( const Plot2d_Prs* prs )
238 {
239   if ( !prs || prs->IsNull() )
240     return;
241
242   if (prs->isSecondY()) {
243     myPlot->enableAxis(QwtPlot::yRight, true);
244     mySecondY = true;
245   }
246   else {
247     myPlot->enableAxis(QwtPlot::yRight, false);
248     mySecondY = false;
249   }
250
251   // display all curves from presentation
252   curveList aCurves = prs->getCurves();
253   displayCurves( aCurves );
254   setXGrid( myXGridMajorEnabled, myXGridMaxMajor, myXGridMinorEnabled, myXGridMaxMinor, true );
255   setYGrid( myYGridMajorEnabled, myYGridMaxMajor, myYGridMinorEnabled, myYGridMaxMinor,
256             myY2GridMajorEnabled, myY2GridMaxMajor, myY2GridMinorEnabled, myY2GridMaxMinor, true );
257 }
258
259 /*!
260   Erase presentation
261 */
262 void Plot2d_ViewFrame::Erase( const Plot2d_Prs* prs, const bool )
263 {
264   if ( !prs || prs->IsNull() )
265     return;
266
267   // erase all curves from presentation
268   curveList aCurves = prs->getCurves();
269   eraseCurves( aCurves );
270 }
271
272 /*!
273   Sets title
274 */
275 void Plot2d_ViewFrame::setTitle( const QString& title )
276 {
277   setTitle( myTitleEnabled, title, MainTitle, true );
278 }
279
280 /*!
281   Reads Plot2d view settings from the preferences
282 */
283 void Plot2d_ViewFrame::readPreferences()
284 {
285   SUIT_ResourceMgr* resMgr = SUIT_Session::session()->resourceMgr();
286
287   myCurveType = resMgr->integerValue( "Plot2d", "CurveType", myCurveType );
288   if ( myCurveType < 1 || myCurveType > 2 )
289     myCurveType = 1;
290   myShowLegend = resMgr->booleanValue( "Plot2d", "ShowLegend", myShowLegend );
291   myLegendPos = resMgr->integerValue( "Plot2d", "LegendPos", myLegendPos );
292   myMarkerSize = resMgr->integerValue( "Plot2d", "MarkerSize", myMarkerSize );
293   myBackground = resMgr->colorValue( "Plot2d", "Background", myBackground );
294
295   myTitleEnabled = resMgr->booleanValue( "Plot2d", "ShowTitle", myTitleEnabled );
296   myXTitleEnabled = resMgr->booleanValue( "Plot2d", "ShowHorTitle", myXTitleEnabled );
297   myYTitleEnabled = resMgr->booleanValue( "Plot2d", "ShowVerLeftTitle", myYTitleEnabled );
298   myY2TitleEnabled = resMgr->booleanValue( "Plot2d", "ShowVerRightTitle", myY2TitleEnabled );
299
300   myXGridMajorEnabled = resMgr->booleanValue( "Plot2d", "EnableHorMajorGrid", myXGridMajorEnabled );
301   myYGridMajorEnabled = resMgr->booleanValue( "Plot2d", "EnableVerMajorGrid", myYGridMajorEnabled );
302   myY2GridMajorEnabled = resMgr->booleanValue( "Plot2d", "EnableRightVerMajorGrid", myY2GridMajorEnabled );
303
304   myXGridMinorEnabled = resMgr->booleanValue( "Plot2d", "EnableHorMinorGrid", myXGridMinorEnabled );
305   myYGridMinorEnabled = resMgr->booleanValue( "Plot2d", "EnableVerMinorGrid", myYGridMinorEnabled );
306   myY2GridMinorEnabled = resMgr->booleanValue( "Plot2d", "EnableRightVerMinorGrid", myY2GridMinorEnabled );
307
308   myXGridMaxMajor = resMgr->integerValue( "Plot2d", "HorMajorGridMax", myXGridMaxMajor );
309   myYGridMaxMajor = resMgr->integerValue( "Plot2d", "VerMajorGridMax", myYGridMaxMajor );
310   if ( mySecondY )
311     myY2GridMaxMajor = resMgr->integerValue( "Plot2d", "VerMajorRightGridMax", myY2GridMaxMajor );
312
313   myXGridMaxMinor = resMgr->integerValue( "Plot2d", "HorMinorGridMax", myXGridMaxMinor );
314   myYGridMaxMinor = resMgr->integerValue( "Plot2d", "VerMinorGridMax", myYGridMaxMinor );
315   if ( mySecondY )
316     myY2GridMaxMinor = resMgr->integerValue( "Plot2d", "VerMinorGridMax", myY2GridMaxMinor );
317
318   myXMode = resMgr->integerValue( "Plot2d", "HorScaleMode", myXMode );
319   myXMode = QMAX( 0, QMIN( 1, myXMode ) );
320
321   myYMode = resMgr->integerValue( "Plot2d", "VerScaleMode", myYMode );
322   myYMode = QMAX( 0, QMIN( 1, myYMode ) );
323 }
324
325 /*!
326   Writes Plot2d view settings to the preferences
327 */
328 void Plot2d_ViewFrame::writePreferences()
329 {
330   SUIT_ResourceMgr* resMgr = SUIT_Session::session()->resourceMgr();
331
332   resMgr->setValue( "Plot2d", "CurveType", myCurveType );
333   resMgr->setValue( "Plot2d", "ShowLegend", myShowLegend );
334   resMgr->setValue( "Plot2d", "LegendPos", myLegendPos );
335   resMgr->setValue( "Plot2d", "MarkerSize", myMarkerSize );
336   resMgr->setValue( "Plot2d", "Background", myBackground );
337   resMgr->setValue( "Plot2d", "ShowTitle", myTitleEnabled );
338   resMgr->setValue( "Plot2d", "ShowHorTitle", myXTitleEnabled );
339   resMgr->setValue( "Plot2d", "ShowVerLeftTitle", myYTitleEnabled );
340   if ( mySecondY )
341     resMgr->setValue( "Plot2d", "ShowVerRightTitle", myY2TitleEnabled );
342
343   resMgr->setValue( "Plot2d", "EnableHorMajorGrid", myXGridMajorEnabled );
344   resMgr->setValue( "Plot2d", "EnableVerMajorGrid", myYGridMajorEnabled );
345   resMgr->setValue( "Plot2d", "EnableHorMinorGrid", myXGridMinorEnabled );
346   resMgr->setValue( "Plot2d", "EnableVerMinorGrid", myYGridMinorEnabled );
347
348   resMgr->setValue( "Plot2d", "HorMajorGridMax", myXGridMaxMajor );
349   resMgr->setValue( "Plot2d", "VerMajorGridMax", myYGridMaxMajor );
350
351   resMgr->setValue( "Plot2d", "HorMinorGridMax", myXGridMaxMinor );
352   resMgr->setValue( "Plot2d", "VerMinorGridMax", myYGridMaxMinor );
353
354   resMgr->setValue( "Plot2d", "HorScaleMode", myXMode );
355
356   if ( mySecondY )
357   {
358     resMgr->setValue( "Plot2d", "EnableRightVerMajorGrid", myY2GridMajorEnabled );
359     resMgr->setValue( "Plot2d", "EnableRightVerMinorGrid", myY2GridMinorEnabled );
360     resMgr->setValue( "Plot2d", "VerRightMajorGridMax", myY2GridMaxMajor );
361     resMgr->setValue( "Plot2d", "VerRightMinorGridMax", myY2GridMaxMinor );
362   }
363
364   resMgr->setValue( "Plot2d", "VerScaleMode", myYMode );
365 }
366
367 /*!
368   Prints mouse cursor coordinates into string
369 */
370 QString Plot2d_ViewFrame::getInfo( const QPoint& pnt ) 
371 {
372   int i;
373   bool xFound = false, yFound = false;
374   double xCoord, yCoord;
375   const QwtScaleDiv* aXscale = myPlot->axisScale( QwtPlot::xBottom );
376   for ( i = 0; i < aXscale->majCnt(); i++ ) {
377     double majXmark = aXscale->majMark( i );
378     int xmark = myPlot->transform( QwtPlot::xBottom, majXmark );
379     if ( xmark-2 == pnt.x() ) {
380       xCoord = majXmark; 
381       xFound = true;
382       break;
383     }
384   }
385   if ( !xFound ) {
386     for ( i = 0; i < aXscale->minCnt(); i++ ) {
387       double minXmark = aXscale->minMark( i );
388       int xmark = myPlot->transform( QwtPlot::xBottom, minXmark );
389       if ( xmark-2 == pnt.x() ) {
390         xCoord = minXmark; 
391         xFound = true;
392         break;
393       }
394     }
395   }  
396   const QwtScaleDiv* aYscale = myPlot->axisScale( QwtPlot::yLeft );
397   for ( i = 0; i < aYscale->majCnt(); i++ ) {
398     double majYmark = aYscale->majMark( i );
399     int ymark = myPlot->transform( QwtPlot::yLeft, majYmark );
400     if ( ymark-2 == pnt.y() ) {
401       yCoord = majYmark; 
402       yFound = true;
403       break;
404     }
405   }
406   if ( !yFound ) {
407     for ( i = 0; i < aYscale->minCnt(); i++ ) {
408       double minYmark = aYscale->minMark( i );
409       int ymark = myPlot->transform( QwtPlot::yLeft, minYmark );
410       if ( ymark-2 == pnt.y() ) {
411         yCoord = minYmark; 
412         yFound = true;
413         break;
414       }
415     }
416   }  
417
418   QString strX = QString::number( xFound ? xCoord : myPlot->invTransform( QwtPlot::xBottom, pnt.x() ) ).stripWhiteSpace();
419   if ( strX == "-0" )
420     strX = "0";
421   QString strY = QString::number( yFound ? yCoord : myPlot->invTransform( QwtPlot::yLeft, pnt.y() ) ).stripWhiteSpace();
422   if ( strY == "-0" )
423     strY = "0";
424   QString info = "";
425
426   if (mySecondY) {
427     bool yFound2 = false;
428     double yCoord2;
429
430     const QwtScaleDiv* aYscale2 = myPlot->axisScale( QwtPlot::yRight );
431     for ( i = 0; i < aYscale2->majCnt(); i++ ) {
432       double majYmark = aYscale2->majMark( i );
433       int ymark = myPlot->transform( QwtPlot::yRight, majYmark );
434       if ( ymark-2 == pnt.y() ) {
435         yCoord2 = majYmark; 
436         yFound2 = true;
437         break;
438       }
439     }
440     if ( !yFound2 ) {
441       for ( i = 0; i < aYscale2->minCnt(); i++ ) {
442         double minYmark = aYscale2->minMark( i );
443         int ymark = myPlot->transform( QwtPlot::yRight, minYmark );
444         if ( ymark-2 == pnt.y() ) {
445           yCoord2 = minYmark; 
446           yFound2 = true;
447           break;
448         }
449       }
450     }
451     QString strY2 = QString::number( yFound2 ? yCoord2 : 
452                       myPlot->invTransform( QwtPlot::yRight, pnt.y() ) ).stripWhiteSpace();
453     if ( strY2 == "-0" )
454     strY2 = "0";
455     info = tr("INF_COORDINATES_SOME_Y").arg( strX ).arg( strY ).arg( strY2 );
456   }
457   else
458     info = tr("INF_COORDINATES").arg( strX ).arg( strY );
459
460   return info;
461 }
462
463 /*!
464   Converts Plot2d_Curve's marker style to Qwt marker style [ static ]
465 */
466 static QwtSymbol::Style plot2qwtMarker( Plot2d_Curve::MarkerType m )
467 {
468   QwtSymbol::Style ms = QwtSymbol::None;  
469   switch ( m ) {
470   case Plot2d_Curve::Circle:
471     ms = QwtSymbol::Ellipse;   break;
472   case Plot2d_Curve::Rectangle:
473     ms = QwtSymbol::Rect;      break;
474   case Plot2d_Curve::Diamond:
475     ms = QwtSymbol::Diamond;   break;
476   case Plot2d_Curve::DTriangle:
477     ms = QwtSymbol::DTriangle; break;
478   case Plot2d_Curve::UTriangle:
479     ms = QwtSymbol::UTriangle; break;
480   case Plot2d_Curve::LTriangle: // Qwt confuses LTriangle and RTriangle :(((
481     ms = QwtSymbol::RTriangle; break;
482   case Plot2d_Curve::RTriangle: // Qwt confuses LTriangle and RTriangle :(((
483     ms = QwtSymbol::LTriangle; break;
484   case Plot2d_Curve::Cross:
485     ms = QwtSymbol::Cross;     break;
486   case Plot2d_Curve::XCross:
487     ms = QwtSymbol::XCross;    break;
488   case Plot2d_Curve::None:
489   default:
490     ms = QwtSymbol::None;      break;
491   }
492   return ms;
493 }
494
495 /*!
496   Converts Qwt marker style to Plot2d_Curve's marker style [ static ]
497 */
498 static Plot2d_Curve::MarkerType qwt2plotMarker( QwtSymbol::Style m )
499 {
500   Plot2d_Curve::MarkerType ms = Plot2d_Curve::None;  
501   switch ( m ) {
502   case QwtSymbol::Ellipse:
503     ms = Plot2d_Curve::Circle;    break;
504   case QwtSymbol::Rect:
505     ms = Plot2d_Curve::Rectangle; break;
506   case QwtSymbol::Diamond:
507     ms = Plot2d_Curve::Diamond;   break;
508   case QwtSymbol::DTriangle:
509     ms = Plot2d_Curve::DTriangle; break;
510   case QwtSymbol::UTriangle:
511     ms = Plot2d_Curve::UTriangle; break;
512   case QwtSymbol::RTriangle: // Qwt confuses LTriangle and RTriangle :(((
513     ms = Plot2d_Curve::LTriangle; break;
514   case QwtSymbol::LTriangle: // Qwt confuses LTriangle and RTriangle :(((
515     ms = Plot2d_Curve::RTriangle; break;
516   case QwtSymbol::Cross:
517     ms = Plot2d_Curve::Cross;     break;
518   case QwtSymbol::XCross:
519     ms = Plot2d_Curve::XCross;    break;
520   case QwtSymbol::None:
521   default:
522     ms = Plot2d_Curve::None;      break;
523   }
524   return ms;
525 }
526
527 /*!
528   Converts Plot2d_Curve's line style to Qwt line style [ static ]
529 */
530 static Qt::PenStyle plot2qwtLine( Plot2d_Curve::LineType p )
531 {
532   Qt::PenStyle ps = Qt::NoPen;
533   switch ( p ) {
534   case Plot2d_Curve::Solid:
535     ps = Qt::SolidLine;      break;
536   case Plot2d_Curve::Dash:
537     ps = Qt::DashLine;       break;
538   case Plot2d_Curve::Dot:
539     ps = Qt::DotLine;        break;
540   case Plot2d_Curve::DashDot:
541     ps = Qt::DashDotLine;    break;
542   case Plot2d_Curve::DashDotDot:
543     ps = Qt::DashDotDotLine; break;
544   case Plot2d_Curve::NoPen:
545   default:
546     ps = Qt::NoPen;          break;
547   }
548   return ps;
549 }
550
551 /*!
552   Converts Qwt line style to Plot2d_Curve's line style [ static ]
553 */
554 static Plot2d_Curve::LineType qwt2plotLine( Qt::PenStyle p )
555 {
556   Plot2d_Curve::LineType ps = Plot2d_Curve::NoPen;
557   switch ( p ) {
558   case Qt::SolidLine:
559     ps = Plot2d_Curve::Solid;      break;
560   case Qt::DashLine:
561     ps = Plot2d_Curve::Dash;       break;
562   case Qt::DotLine:
563     ps = Plot2d_Curve::Dot;        break;
564   case Qt::DashDotLine:
565     ps = Plot2d_Curve::DashDot;    break;
566   case Qt::DashDotDotLine:
567     ps = Plot2d_Curve::DashDotDot; break;
568   case Qt::NoPen:
569   default:
570     ps = Plot2d_Curve::NoPen;      break;
571   }
572   return ps;
573 }
574
575 /*!
576   Adds curve into view
577 */
578 void Plot2d_ViewFrame::displayCurve( Plot2d_Curve* curve, bool update )
579 {
580   if ( !curve )
581     return;
582   if ( hasCurve( curve ) ) {
583     updateCurve( curve, update );
584   }
585   else {
586     long curveKey = myPlot->insertCurve( curve->getVerTitle() );
587     myPlot->setCurveYAxis(curveKey, curve->getYAxis());
588
589     myCurves.insert( curveKey, curve );
590     if ( curve->isAutoAssign() ) {
591       QwtSymbol::Style typeMarker;
592       QColor           color;
593       Qt::PenStyle     typeLine;
594       myPlot->getNextMarker( typeMarker, color, typeLine );
595       myPlot->setCurvePen( curveKey, QPen( color, DEFAULT_LINE_WIDTH, typeLine ) );
596       myPlot->setCurveSymbol( curveKey, QwtSymbol( typeMarker, 
597                QBrush( color ), 
598                QPen( color ), 
599                QSize( myMarkerSize, myMarkerSize ) ) );
600       curve->setColor( color );
601       curve->setLine( qwt2plotLine( typeLine ) );
602       curve->setMarker( qwt2plotMarker( typeMarker ) );
603     }
604     else {
605       Qt::PenStyle     ps = plot2qwtLine( curve->getLine() );
606       QwtSymbol::Style ms = plot2qwtMarker( curve->getMarker() );
607       myPlot->setCurvePen( curveKey, QPen( curve->getColor(), curve->getLineWidth(), ps ) );
608       myPlot->setCurveSymbol( curveKey, QwtSymbol( ms, 
609                QBrush( curve->getColor() ), 
610                QPen( curve->getColor() ), 
611                QSize( myMarkerSize, myMarkerSize ) ) );
612     }
613     if ( myCurveType == 0 )
614       myPlot->setCurveStyle( curveKey, QwtCurve::NoCurve );
615     else if ( myCurveType == 1 )
616       myPlot->setCurveStyle( curveKey, QwtCurve::Lines );
617     else if ( myCurveType == 2 )
618       myPlot->setCurveStyle( curveKey, QwtCurve::Spline );
619     myPlot->setCurveData( curveKey, curve->horData(), curve->verData(), curve->nbPoints() );
620   }
621   if ( update )
622     myPlot->replot();
623 }
624
625 /*!
626   Adds curves into view
627 */
628 void Plot2d_ViewFrame::displayCurves( const curveList& curves, bool update )
629 {
630   myPlot->setUpdatesEnabled( false );
631   QPtrListIterator<Plot2d_Curve> it(curves);
632   Plot2d_Curve* aCurve;
633   while( (aCurve = it.current()) ) {
634     displayCurve( aCurve, false );
635     ++it;
636   }
637
638   fitAll();
639   myPlot->setUpdatesEnabled( true );
640   if ( update )
641     myPlot->replot();
642 }
643
644 /*!
645   Erases curve
646 */
647 void Plot2d_ViewFrame::eraseCurve( Plot2d_Curve* curve, bool update )
648 {
649   if ( !curve )
650     return;
651   int curveKey = hasCurve( curve );
652   if ( curveKey ) {
653     myPlot->removeCurve( curveKey );
654     myCurves.remove( curveKey );
655     if ( update )
656       myPlot->replot();
657   }
658 }
659
660 /*!
661   Erases curves
662 */
663 void Plot2d_ViewFrame::eraseCurves( const curveList& curves, bool update )
664 {
665   QPtrListIterator<Plot2d_Curve> it(curves);
666   Plot2d_Curve* aCurve;
667   while( (aCurve = it.current()) ) {
668     eraseCurve( aCurve, false );
669     ++it;
670   }
671 //  fitAll();
672   if ( update )
673     myPlot->replot();
674 }
675
676 /*!
677   Updates curves attributes
678 */
679 void Plot2d_ViewFrame::updateCurve( Plot2d_Curve* curve, bool update )
680 {
681   if ( !curve )
682     return;
683   int curveKey = hasCurve( curve );
684   if ( curveKey ) {
685     if ( !curve->isAutoAssign() ) {
686       Qt::PenStyle     ps = plot2qwtLine( curve->getLine() );
687       QwtSymbol::Style ms = plot2qwtMarker( curve->getMarker() );
688       myPlot->setCurvePen( curveKey, QPen( curve->getColor(), curve->getLineWidth(), ps ) );
689       myPlot->setCurveSymbol( curveKey, QwtSymbol( ms, 
690                QBrush( curve->getColor() ), 
691                QPen( curve->getColor() ), 
692                QSize( myMarkerSize, myMarkerSize ) ) );
693       myPlot->setCurveData( curveKey, curve->horData(), curve->verData(), curve->nbPoints() );
694     }
695     myPlot->setCurveTitle( curveKey, curve->getVerTitle() );
696     myPlot->curve( curveKey )->setEnabled( true );
697     if ( update )
698       myPlot->replot();
699   }
700 }
701
702 /*!
703   Returns curve key if is is displayed in the viewer and 0 otherwise
704 */
705 int Plot2d_ViewFrame::hasCurve( Plot2d_Curve* curve )
706 {
707   QIntDictIterator<Plot2d_Curve> it( myCurves );
708   for ( ; it.current(); ++it ) {
709     if ( it.current() == curve )
710       return it.currentKey();
711   }
712   return 0;
713 }
714
715 /*!
716   Gets lsit of displayed curves
717 */
718 int Plot2d_ViewFrame::getCurves( QList<Plot2d_Curve>& clist )
719 {
720   clist.clear();
721   clist.setAutoDelete( false );
722   QIntDictIterator<Plot2d_Curve> it( myCurves );
723   for ( ; it.current(); ++it ) {
724     clist.append( it.current() );
725   }
726   return clist.count();
727 }
728
729 /*!
730   Returns true if the curve is visible
731 */
732 bool Plot2d_ViewFrame::isVisible( Plot2d_Curve* curve )
733 {
734   if(curve) {
735     int key = hasCurve( curve );
736     if ( key )
737       return myPlot->curve( key )->enabled();
738   }
739   return false;
740
741
742 /*!
743   update legend
744 */
745 void Plot2d_ViewFrame::updateLegend( const Plot2d_Prs* prs )
746 {
747   if ( !prs || prs->IsNull() )
748     return;
749   curveList aCurves = prs->getCurves();
750
751   QPtrListIterator<Plot2d_Curve> it(aCurves);
752   Plot2d_Curve* aCurve;
753   while( (aCurve = it.current()) ) {
754     int curveKey = hasCurve( aCurve );
755     if ( curveKey )
756       myPlot->setCurveTitle( curveKey, aCurve->getVerTitle() );
757     ++it;
758   }
759 }
760
761 /*!
762   Fits the view to see all data
763 */
764 void Plot2d_ViewFrame::fitAll()
765 {
766   QwtDiMap xMap1 = myPlot->canvasMap( QwtPlot::xBottom );
767
768   myPlot->setAxisAutoScale( QwtPlot::yLeft );
769   myPlot->setAxisAutoScale( QwtPlot::xBottom );
770   myPlot->replot();
771
772   // for existing grid
773   QwtDiMap xMap = myPlot->canvasMap( QwtPlot::xBottom );
774   QwtDiMap yMap = myPlot->canvasMap( QwtPlot::yLeft );
775
776   myPlot->setAxisScale( QwtPlot::xBottom, 
777       myPlot->invTransform( QwtPlot::xBottom, xMap.i1() ), 
778       myPlot->invTransform( QwtPlot::xBottom, xMap.i2() ) );
779   myPlot->setAxisScale( QwtPlot::yLeft, 
780       myPlot->invTransform( QwtPlot::yLeft, yMap.i1() ), 
781       myPlot->invTransform( QwtPlot::yLeft, yMap.i2() ) );
782
783   if (mySecondY) {
784     myPlot->setAxisAutoScale( QwtPlot::yRight );
785     myPlot->replot();
786     QwtDiMap yMap2 = myPlot->canvasMap( QwtPlot::yRight );
787     myPlot->setAxisScale( QwtPlot::yRight, 
788         myPlot->invTransform( QwtPlot::yRight, yMap2.i1() ), 
789         myPlot->invTransform( QwtPlot::yRight, yMap2.i2() ) );
790   }
791   myPlot->replot();
792 }
793
794 /*!
795   Fits the view to rectangle area (pixels)
796 */
797 void Plot2d_ViewFrame::fitArea( const QRect& area )
798 {
799   QRect rect = area.normalize();
800   if ( rect.width() < MIN_RECT_SIZE ) {
801     rect.setWidth( MIN_RECT_SIZE );
802     rect.setLeft( rect.left() - MIN_RECT_SIZE/2 );
803   }
804   if ( rect.height() < MIN_RECT_SIZE ) {
805     rect.setHeight( MIN_RECT_SIZE );
806     rect.setTop( rect.top() - MIN_RECT_SIZE/2 );
807   }
808   myPlot->setAxisScale( QwtPlot::yLeft, 
809             myPlot->invTransform( QwtPlot::yLeft, rect.top() ), 
810             myPlot->invTransform( QwtPlot::yLeft, rect.bottom() ) );
811   if (mySecondY)
812     myPlot->setAxisScale( QwtPlot::yRight, 
813             myPlot->invTransform( QwtPlot::yRight, rect.top() ), 
814             myPlot->invTransform( QwtPlot::yRight, rect.bottom() ) );
815   myPlot->setAxisScale( QwtPlot::xBottom, 
816             myPlot->invTransform( QwtPlot::xBottom, rect.left() ), 
817             myPlot->invTransform( QwtPlot::xBottom, rect.right() ) );
818   myPlot->replot();
819 }
820
821 /*!
822   "Fit Data" command for TUI interface
823 */
824 void Plot2d_ViewFrame::fitData(const int mode,
825                                const double xMin, const double xMax,
826                                const double yMin, const double yMax,
827                                double y2Min, double y2Max)
828 {
829   if ( mode == 0 || mode == 2 ) {
830     myPlot->setAxisScale( QwtPlot::yLeft, yMax, yMin );
831     if (mySecondY)
832       myPlot->setAxisScale( QwtPlot::yRight, y2Max, y2Min );
833   }
834   if ( mode == 0 || mode == 1 ) 
835     myPlot->setAxisScale( QwtPlot::xBottom, xMin, xMax ); 
836   myPlot->replot();
837 }
838
839 /*!
840   Gets current fit ranges for view frame
841 */
842 void Plot2d_ViewFrame::getFitRanges(double& xMin,double& xMax,
843                                     double& yMin, double& yMax,
844                                     double& y2Min, double& y2Max)
845 {
846   int ixMin = myPlot->canvasMap( QwtPlot::xBottom ).i1();
847   int ixMax = myPlot->canvasMap( QwtPlot::xBottom ).i2();
848   int iyMin = myPlot->canvasMap( QwtPlot::yLeft ).i1();
849   int iyMax = myPlot->canvasMap( QwtPlot::yLeft ).i2();
850   xMin = myPlot->invTransform(QwtPlot::xBottom, ixMin);
851   xMax = myPlot->invTransform(QwtPlot::xBottom, ixMax);
852   yMin = myPlot->invTransform(QwtPlot::yLeft, iyMin);
853   yMax = myPlot->invTransform(QwtPlot::yLeft, iyMax);
854   y2Min = 0;
855   y2Max = 0;
856   if (mySecondY) {
857     int iyMin = myPlot->canvasMap( QwtPlot::yRight ).i1();
858     int iyMax = myPlot->canvasMap( QwtPlot::yRight ).i2();
859     y2Min = myPlot->invTransform(QwtPlot::yRight, iyMin);
860     y2Max = myPlot->invTransform(QwtPlot::yRight, iyMax);
861   }
862 }
863
864 /*!
865   Tests if it is necessary to start operation on mouse action
866 */
867 int Plot2d_ViewFrame::testOperation( const QMouseEvent& me )
868 {
869   int btn = me.button() | me.state();
870   const int zoomBtn = ControlButton | LeftButton;
871   const int panBtn  = ControlButton | MidButton;
872   const int fitBtn  = ControlButton | RightButton;
873
874   switch (btn)
875   {
876   case zoomBtn:
877     myPlot->canvas()->setCursor( zoomCursor );
878     return ZoomId;
879   case panBtn:
880     myPlot->canvas()->setCursor( QCursor( Qt::SizeAllCursor ) );
881     return PanId;
882   case fitBtn:
883     myPlot->canvas()->setCursor( QCursor( Qt::PointingHandCursor ) );
884     return FitAreaId;
885   default :
886     return NoOpId;
887   }
888 }
889
890 /*!
891   "Settings" toolbar action slot
892 */
893 void Plot2d_ViewFrame::onSettings()
894 {
895 #ifdef TEST_AUTOASSIGN
896   typedef QMap<int,int> IList;
897   typedef QMap<QString,int> SList;
898   IList mars, lins;
899   SList cols;
900   cols[ "red-min" ]   = 1000;
901   cols[ "red-max" ]   = -1;
902   cols[ "green-min" ] = 1000;
903   cols[ "green-max" ] = -1;
904   cols[ "blue-min" ]  = 1000;
905   cols[ "blue-max" ]  = -1;
906   for ( unsigned i = 0; i < 10000; i++ ) {
907     QwtSymbol::Style typeMarker;
908     QColor           color;
909     Qt::PenStyle     typeLine;
910     myPlot->getNextMarker( typeMarker, color, typeLine );
911     if ( mars.contains(typeMarker) )
912       mars[ typeMarker ] = mars[ typeMarker ]+1;
913     else
914       mars[ typeMarker ] = 0;
915     if ( lins.contains(typeLine) )
916       lins[ typeLine ] = lins[ typeLine ]+1;
917     else
918       lins[ typeLine ] = 0;
919     if ( cols[ "red-max" ] < color.red() )
920       cols[ "red-max" ] = color.red();
921     if ( cols[ "red-min" ] > color.red() )
922       cols[ "red-min" ] = color.red();
923     if ( cols[ "green-max" ] < color.green() )
924       cols[ "green-max" ] = color.green();
925     if ( cols[ "green-min" ] > color.green() )
926       cols[ "green-min" ] = color.green();
927     if ( cols[ "blue-max" ] < color.blue() )
928       cols[ "blue-max" ] = color.blue();
929     if ( cols[ "blue-min" ] > color.blue() )
930       cols[ "blue-min" ] = color.blue();
931   }
932 #endif
933   
934   Plot2d_SetupViewDlg* dlg = new Plot2d_SetupViewDlg( this, true, mySecondY );
935   dlg->setMainTitle( myTitleEnabled, myTitle );
936   dlg->setXTitle( myXTitleEnabled, myXTitle );
937   dlg->setYTitle( myYTitleEnabled, myYTitle );
938   if (mySecondY)
939     dlg->setY2Title( myY2TitleEnabled, myY2Title );
940   dlg->setCurveType( myCurveType );
941   dlg->setLegend( myShowLegend, myLegendPos );
942   dlg->setMarkerSize( myMarkerSize );
943   dlg->setBackgroundColor( myBackground );
944   dlg->setScaleMode(myXMode, myYMode);
945   //
946   dlg->setMajorGrid( myXGridMajorEnabled, myPlot->axisMaxMajor( QwtPlot::xBottom ),
947          myYGridMajorEnabled, myPlot->axisMaxMajor( QwtPlot::yLeft ),
948          myY2GridMajorEnabled, myPlot->axisMaxMajor( QwtPlot::yRight ) );
949   dlg->setMinorGrid( myXGridMinorEnabled, myPlot->axisMaxMinor( QwtPlot::xBottom ),
950          myYGridMinorEnabled, myPlot->axisMaxMinor( QwtPlot::yLeft ),
951          myY2GridMinorEnabled, myPlot->axisMaxMinor( QwtPlot::yRight ) );
952   if ( dlg->exec() == QDialog::Accepted ) {
953     // horizontal axis title
954     setTitle( dlg->isXTitleEnabled(), dlg->getXTitle(), XTitle, false );
955     // vertical left axis title
956     setTitle( dlg->isYTitleEnabled(), dlg->getYTitle(), YTitle, false );
957     if (mySecondY) // vertical right axis title
958       setTitle( dlg->isY2TitleEnabled(), dlg->getY2Title(), Y2Title, false );
959
960     // main title
961     setTitle( dlg->isMainTitleEnabled(), dlg->getMainTitle(), MainTitle, true );
962     // curve type
963     if ( myCurveType != dlg->getCurveType() ) {
964       setCurveType( dlg->getCurveType(), false );
965     }
966     // legend
967     if ( myShowLegend != dlg->isLegendEnabled() ) {
968       showLegend( dlg->isLegendEnabled(), false );
969     }
970     if ( myLegendPos != dlg->getLegendPos() ) {
971       setLegendPos( dlg->getLegendPos() );
972     }
973     // marker size
974     if ( myMarkerSize != dlg->getMarkerSize() ) {
975       setMarkerSize( dlg->getMarkerSize(), false );
976     }
977     // background color
978     if ( myBackground != dlg->getBackgroundColor() ) {
979       setBackgroundColor( dlg->getBackgroundColor() );
980     }
981     // grid
982     bool aXGridMajorEnabled, aXGridMinorEnabled, aYGridMajorEnabled, aYGridMinorEnabled,
983          aY2GridMajorEnabled, aY2GridMinorEnabled;
984     int  aXGridMaxMajor, aXGridMaxMinor, aYGridMaxMajor, aYGridMaxMinor,
985          aY2GridMaxMajor, aY2GridMaxMinor;
986     dlg->getMajorGrid( aXGridMajorEnabled, aXGridMaxMajor, aYGridMajorEnabled, aYGridMaxMajor,
987                        aY2GridMajorEnabled, aY2GridMaxMajor);
988     dlg->getMinorGrid( aXGridMinorEnabled, aXGridMaxMinor, aYGridMinorEnabled, aYGridMaxMinor,
989                        aY2GridMinorEnabled, aY2GridMaxMinor);
990     setXGrid( aXGridMajorEnabled, aXGridMaxMajor, aXGridMinorEnabled, aXGridMaxMinor, false );
991     setYGrid( aYGridMajorEnabled, aYGridMaxMajor, aYGridMinorEnabled, aYGridMaxMinor,
992               aY2GridMajorEnabled, aY2GridMaxMajor, aY2GridMinorEnabled, aY2GridMaxMinor, false );
993     if ( myXMode != dlg->getXScaleMode() ) {
994       setHorScaleMode( dlg->getXScaleMode() );
995     }
996     if ( myYMode != dlg->getYScaleMode() ) {
997       setVerScaleMode( dlg->getYScaleMode() );
998     }
999     // update view
1000     myPlot->replot();
1001     // update preferences
1002     if ( dlg->isSetAsDefault() ) 
1003       writePreferences();
1004   }
1005   delete dlg;
1006 }
1007
1008 /*!
1009   "Fit Data" command slot
1010 */
1011 void Plot2d_ViewFrame::onFitData()
1012 {
1013   Plot2d_FitDataDlg* dlg = new Plot2d_FitDataDlg( this, mySecondY );
1014   double xMin,xMax,yMin,yMax,y2Min,y2Max;
1015   getFitRanges(xMin,xMax,yMin,yMax,y2Min,y2Max);
1016   
1017   dlg->setRange( xMin, xMax, yMin, yMax, y2Min, y2Max );
1018   if ( dlg->exec() == QDialog::Accepted ) {
1019     int mode = dlg->getRange( xMin, xMax, yMin, yMax, y2Min, y2Max );
1020     fitData(mode,xMin,xMax,yMin,yMax,y2Min,y2Max);
1021   }
1022   delete dlg;
1023 }
1024
1025 /*!
1026   Change background color
1027 */
1028 void Plot2d_ViewFrame::onChangeBackground()
1029 {
1030   QColor selColor = QColorDialog::getColor ( backgroundColor(), this ); 
1031   if ( selColor.isValid() ) {
1032     setBackgroundColor( selColor );
1033   }
1034 }
1035
1036 /*!
1037   Sets curve type
1038 */
1039 void Plot2d_ViewFrame::setCurveType( int curveType, bool update )
1040 {
1041   myCurveType = curveType;
1042   QArray<long> keys = myPlot->curveKeys();
1043   for ( int i = 0; i < (int)keys.count(); i++ ) {
1044     if ( myCurveType == 0 )
1045       myPlot->setCurveStyle( keys[i], QwtCurve::Dots );//QwtCurve::NoCurve
1046     else if ( myCurveType == 1 )
1047       myPlot->setCurveStyle( keys[i], QwtCurve::Lines );
1048     else if ( myCurveType == 2 )
1049       myPlot->setCurveStyle( keys[i], QwtCurve::Spline );
1050   }
1051   if ( update )
1052     myPlot->replot();
1053   emit vpCurveChanged();
1054 }
1055
1056 void Plot2d_ViewFrame::setCurveTitle( int curveKey, const QString& title ) 
1057
1058   if(myPlot) myPlot->setCurveTitle(curveKey, title); 
1059 }   
1060
1061 /*!
1062   Shows/hides legend
1063 */
1064 void Plot2d_ViewFrame::showLegend( bool show, bool update )
1065 {
1066   myShowLegend = show;
1067   myPlot->setAutoLegend( myShowLegend );
1068   myPlot->enableLegend( myShowLegend );
1069   if ( update )
1070     myPlot->replot();
1071 }
1072
1073 /*!
1074   Sets legend position : 0 - left, 1 - right, 2 - top, 3 - bottom
1075 */
1076 void Plot2d_ViewFrame::setLegendPos( int pos )
1077 {
1078   myLegendPos = pos;
1079   switch( pos ) {
1080   case 0:
1081     myPlot->setLegendPos( Qwt::Left );
1082     break;
1083   case 1:
1084     myPlot->setLegendPos( Qwt::Right );
1085     break;
1086   case 2:
1087     myPlot->setLegendPos( Qwt::Top );
1088     break;
1089   case 3:
1090     myPlot->setLegendPos( Qwt::Bottom );
1091     break;
1092   }
1093 }
1094
1095 /*!
1096   Sets new marker size
1097 */
1098 void Plot2d_ViewFrame::setMarkerSize( const int size, bool update )
1099 {
1100   if ( myMarkerSize != size )
1101   {
1102     myMarkerSize = size;
1103     QArray<long> keys = myPlot->curveKeys();
1104     for ( int i = 0; i < (int)keys.count(); i++ )
1105     {
1106       QwtPlotCurve* crv = myPlot->curve( keys[i] );
1107       if ( crv )
1108       {
1109         QwtSymbol aSymbol = crv->symbol();
1110         aSymbol.setSize( myMarkerSize, myMarkerSize );
1111         myPlot->setCurveSymbol( keys[i], aSymbol );
1112       }
1113     }
1114     if ( update )
1115       myPlot->replot();
1116   }
1117 }
1118
1119 /*!
1120   Sets background color
1121 */
1122 void Plot2d_ViewFrame::setBackgroundColor( const QColor& color )
1123 {
1124   myBackground = color;
1125   //myPlot->setCanvasBackground( myBackground );
1126   myPlot->canvas()->setPalette( myBackground );
1127   myPlot->setPalette( myBackground );
1128   QPalette aPal = myPlot->getLegend()->palette();
1129   for ( int i = 0; i < QPalette::NColorGroups; i++ ) {
1130     QPalette::ColorGroup cg = (QPalette::ColorGroup)i;
1131     aPal.setColor( cg, QColorGroup::Base, myBackground );
1132     aPal.setColor( cg, QColorGroup::Background, myBackground );
1133   }
1134   myPlot->getLegend()->setPalette( aPal );
1135   Repaint();
1136 }
1137 /*!
1138   Gets background color
1139 */
1140 QColor Plot2d_ViewFrame::backgroundColor() const
1141 {
1142   return myBackground;
1143 }
1144 /*!
1145   Sets hor.axis grid parameters
1146 */
1147 void Plot2d_ViewFrame::setXGrid( bool xMajorEnabled, const int xMajorMax, 
1148          bool xMinorEnabled, const int xMinorMax, 
1149          bool update )
1150 {
1151   if( xMinorMax>=xMajorMax )
1152     return;
1153
1154   myXGridMajorEnabled = xMajorEnabled;
1155   myXGridMinorEnabled = xMinorEnabled;
1156   myXGridMaxMajor = xMajorMax;
1157   myXGridMaxMinor = xMinorMax;
1158   myPlot->setAxisMaxMajor( QwtPlot::xBottom, myXGridMaxMajor );
1159   myPlot->setAxisMaxMinor( QwtPlot::xBottom, myXGridMaxMinor );
1160   myPlot->setGridXAxis(QwtPlot::xBottom);
1161   myPlot->enableGridX( myXGridMajorEnabled );
1162   myPlot->enableGridXMin( myXGridMinorEnabled );
1163   if ( update )
1164     myPlot->replot();
1165 }
1166 /*!
1167   Sets ver.axis grid parameters
1168 */
1169 void Plot2d_ViewFrame::setYGrid( bool yMajorEnabled, const int yMajorMax, 
1170                                  bool yMinorEnabled, const int yMinorMax,
1171                                  bool y2MajorEnabled, const int y2MajorMax, 
1172                                  bool y2MinorEnabled, const int y2MinorMax, 
1173                                  bool update )
1174 {
1175   myYGridMajorEnabled = yMajorEnabled;
1176   myYGridMinorEnabled = yMinorEnabled;
1177   myYGridMaxMajor = yMajorMax;
1178   myYGridMaxMinor = yMinorMax;
1179
1180   if (mySecondY) {
1181     myY2GridMajorEnabled = y2MajorEnabled;
1182     myY2GridMinorEnabled = y2MinorEnabled;
1183     myY2GridMaxMajor = y2MajorMax;
1184     myY2GridMaxMinor = y2MinorMax;
1185   }
1186   myPlot->setAxisMaxMajor( QwtPlot::yLeft, myYGridMaxMajor );
1187   myPlot->setAxisMaxMinor( QwtPlot::yLeft, myYGridMaxMinor );
1188
1189   if (mySecondY) {
1190     myPlot->setAxisMaxMajor( QwtPlot::yRight, myY2GridMaxMajor );
1191     myPlot->setAxisMaxMinor( QwtPlot::yRight, myY2GridMaxMinor );
1192   }
1193
1194   myPlot->setGridYAxis(QwtPlot::yLeft);
1195
1196   if (mySecondY) {
1197     if (myYGridMajorEnabled) {
1198       myPlot->enableGridYMin(myYGridMinorEnabled);
1199       myPlot->enableGridY( myYGridMajorEnabled);
1200     }
1201     else if (myY2GridMajorEnabled) {
1202       myPlot->setGridYAxis(QwtPlot::yRight);
1203       myPlot->enableGridYMin(myY2GridMinorEnabled);
1204       myPlot->enableGridY(myY2GridMajorEnabled);
1205     }
1206     else {
1207       myPlot->enableGridYMin(false);
1208       myPlot->enableGridY(false);
1209     }
1210   }
1211   else {
1212     myPlot->enableGridY( myYGridMajorEnabled );
1213     myPlot->enableGridYMin( myYGridMinorEnabled );
1214   }
1215   if ( update )
1216     myPlot->replot();
1217 }
1218
1219 /*!
1220   Sets title for some axis
1221 */
1222 void Plot2d_ViewFrame::setTitle( bool enabled, const QString& title,
1223                                  ObjectType type, bool update )
1224 {
1225   switch (type) {
1226     case MainTitle:
1227       myTitleEnabled = enabled;
1228       myTitle = title;
1229       myPlot->setTitle( myTitleEnabled ? myTitle : QString::null );
1230       break;
1231     case XTitle:
1232       myXTitleEnabled = enabled;
1233       myXTitle = title;
1234       myPlot->setAxisTitle( QwtPlot::xBottom, myXTitleEnabled ? myXTitle : QString::null );
1235       break;
1236     case YTitle:
1237       myYTitleEnabled = enabled;
1238       myYTitle = title;
1239       myPlot->setAxisTitle( QwtPlot::yLeft, myYTitleEnabled ? myYTitle : QString::null );
1240       break;
1241     case Y2Title:
1242       myY2TitleEnabled = enabled;
1243       myY2Title = title;
1244       myPlot->setAxisTitle( QwtPlot::yRight, myY2TitleEnabled ? myY2Title : QString::null );
1245       break;
1246   }
1247   if ( update )
1248     myPlot->replot();
1249 }
1250 /*!
1251   Sets title for some axis
1252 */
1253 QString Plot2d_ViewFrame::getTitle( ObjectType type ) const
1254 {
1255   QString title = "";
1256   switch (type) {
1257     case MainTitle:
1258       title = myTitle;   break;
1259     case XTitle:
1260       title = myXTitle;  break;
1261     case YTitle:
1262       title = myYTitle;  break;
1263     case Y2Title:
1264       title = myY2Title; break;
1265   }
1266   return title;
1267 }
1268 /*!
1269   Sets font for Plot2d object : title or axis
1270 */
1271 void Plot2d_ViewFrame::setFont( const QFont& font, ObjectType type, bool update)
1272 {
1273   switch (type) {
1274     case MainTitle:
1275       myPlot->setTitleFont(font);
1276       break;
1277     case XTitle:
1278       myPlot->setAxisTitleFont(QwtPlot::xBottom, font); break;
1279     case YTitle:
1280       myPlot->setAxisTitleFont(QwtPlot::yLeft, font);   break;
1281     case Y2Title:
1282       myPlot->setAxisTitleFont(QwtPlot::yRight, font);  break;
1283     case XAxis:
1284       myPlot->setAxisFont(QwtPlot::xBottom, font);      break;
1285     case YAxis:
1286       myPlot->setAxisFont(QwtPlot::yLeft, font);        break;
1287     case Y2Axis:
1288       myPlot->setAxisFont(QwtPlot::yRight, font);       break;
1289   }
1290   if ( update )
1291     myPlot->replot();
1292 }
1293 /*!
1294   Sets scale mode for horizontal axis: 0 - linear, 1 - logarithmic
1295 */
1296 void Plot2d_ViewFrame::setHorScaleMode( const int mode, bool update )
1297 {
1298   myXMode = mode;
1299   if ( myXMode == 0 ) // linear
1300     myPlot->changeAxisOptions( QwtPlot::xBottom, QwtAutoScale::Logarithmic, false );
1301   else                // logarithmic
1302     myPlot->changeAxisOptions( QwtPlot::xBottom, QwtAutoScale::Logarithmic, true );
1303
1304   if ( update )
1305     fitAll();
1306   emit vpModeHorChanged();
1307 }
1308 /*!
1309   Sets scale mode for vertical axis: 0 - linear, 1 - logarithmic
1310 */
1311 void Plot2d_ViewFrame::setVerScaleMode( const int mode, bool update )
1312 {
1313   myYMode = mode;
1314   if ( myYMode == 0 ) { // linear
1315     myPlot->changeAxisOptions( QwtPlot::yLeft, QwtAutoScale::Logarithmic, false );
1316     if (mySecondY)
1317       myPlot->changeAxisOptions( QwtPlot::yRight, QwtAutoScale::Logarithmic, false );
1318   }
1319   else {               // logarithmic
1320     myPlot->changeAxisOptions( QwtPlot::yLeft, QwtAutoScale::Logarithmic, true );
1321     if (mySecondY)
1322       myPlot->changeAxisOptions( QwtPlot::yRight, QwtAutoScale::Logarithmic, true );
1323   }
1324   if ( update )
1325     fitAll();
1326   emit vpModeVerChanged();
1327 }
1328
1329 /*!
1330   Return, scale mode for horizontal axis
1331 */
1332 bool Plot2d_ViewFrame::isModeHorLinear()
1333 {
1334   return (myXMode == 0 ? true : false);
1335 }
1336
1337 /*!
1338   Return, scale mode for vertical axis
1339 */
1340 bool Plot2d_ViewFrame::isModeVerLinear()
1341 {
1342   return (myYMode == 0 ? true : false);
1343 }
1344 /*!
1345   Slot, called when user presses mouse button
1346 */
1347 void Plot2d_ViewFrame::plotMousePressed(const QMouseEvent& me )
1348 {
1349   ((Plot2d_ViewWindow*)parent())->putInfo(getInfo(me.pos()));
1350   if ( myOperation == NoOpId )
1351     myOperation = testOperation( me );
1352   if ( myOperation != NoOpId ) {
1353     myPnt = me.pos();
1354     if ( myOperation == FitAreaId ) {
1355       myPlot->setOutlineStyle( Qwt::Rect );
1356     }
1357     else if ( myOperation == GlPanId ) {
1358       myPlot->setAxisScale( QwtPlot::yLeft,
1359           myPlot->invTransform( QwtPlot::yLeft, myPnt.y() ) + myYDistance/2, 
1360           myPlot->invTransform( QwtPlot::yLeft, myPnt.y() ) - myYDistance/2 );
1361       myPlot->setAxisScale( QwtPlot::xBottom, 
1362           myPlot->invTransform( QwtPlot::xBottom, myPnt.x() ) - myXDistance/2, 
1363           myPlot->invTransform( QwtPlot::xBottom, myPnt.x() ) + myXDistance/2 );
1364       if (mySecondY)
1365         myPlot->setAxisScale( QwtPlot::yRight,
1366           myPlot->invTransform( QwtPlot::yRight, myPnt.y() ) + myYDistance2/2, 
1367           myPlot->invTransform( QwtPlot::yRight, myPnt.y() ) - myYDistance2/2 );
1368       myPlot->replot();
1369     }
1370   }
1371   else {
1372     int btn = me.button() | me.state();
1373     if (btn == RightButton) {
1374       QMouseEvent* aEvent = new QMouseEvent(QEvent::MouseButtonPress,
1375                                             me.pos(), btn, me.state());
1376       // QMouseEvent 'me' has the 'MouseButtonDblClick' type. In this case we create new event 'aEvent'.
1377       parent()->eventFilter(this, aEvent);
1378     }
1379   }
1380 }
1381 /*!
1382   Slot, called when user moves mouse
1383 */
1384 void Plot2d_ViewFrame::plotMouseMoved( const QMouseEvent& me )
1385 {
1386   int    dx = me.pos().x() - myPnt.x();
1387   int    dy = me.pos().y() - myPnt.y();
1388
1389   if ( myOperation != NoOpId) {
1390     if ( myOperation == ZoomId ) {
1391       QwtDiMap xMap = myPlot->canvasMap( QwtPlot::xBottom );
1392       QwtDiMap yMap = myPlot->canvasMap( QwtPlot::yLeft );
1393
1394       myPlot->setAxisScale( QwtPlot::yLeft, 
1395           myPlot->invTransform( QwtPlot::yLeft, yMap.i1() ), 
1396           myPlot->invTransform( QwtPlot::yLeft, yMap.i2() + dy ) );
1397       myPlot->setAxisScale( QwtPlot::xBottom, 
1398           myPlot->invTransform( QwtPlot::xBottom, xMap.i1() ), 
1399           myPlot->invTransform( QwtPlot::xBottom, xMap.i2() - dx ) );
1400       if (mySecondY) {
1401         QwtDiMap y2Map = myPlot->canvasMap( QwtPlot::yRight );
1402         myPlot->setAxisScale( QwtPlot::yRight, 
1403           myPlot->invTransform( QwtPlot::yRight, y2Map.i1() ), 
1404           myPlot->invTransform( QwtPlot::yRight, y2Map.i2() + dy ) );
1405       }
1406       myPlot->replot();
1407       myPnt = me.pos();
1408     }
1409     else if ( myOperation == PanId ) {
1410       QwtDiMap xMap = myPlot->canvasMap( QwtPlot::xBottom );
1411       QwtDiMap yMap = myPlot->canvasMap( QwtPlot::yLeft );
1412
1413       myPlot->setAxisScale( QwtPlot::yLeft, 
1414           myPlot->invTransform( QwtPlot::yLeft, yMap.i1()-dy ), 
1415           myPlot->invTransform( QwtPlot::yLeft, yMap.i2()-dy ) );
1416       myPlot->setAxisScale( QwtPlot::xBottom, 
1417           myPlot->invTransform( QwtPlot::xBottom, xMap.i1()-dx ),
1418           myPlot->invTransform( QwtPlot::xBottom, xMap.i2()-dx ) ); 
1419       if (mySecondY) {
1420         QwtDiMap y2Map = myPlot->canvasMap( QwtPlot::yRight );
1421         myPlot->setAxisScale( QwtPlot::yRight,
1422           myPlot->invTransform( QwtPlot::yRight, y2Map.i1()-dy ), 
1423           myPlot->invTransform( QwtPlot::yRight, y2Map.i2()-dy ) );
1424       }
1425       myPlot->replot();
1426       myPnt = me.pos();
1427     }
1428   }
1429   else {
1430     ((Plot2d_ViewWindow*)parent())->putInfo(getInfo(me.pos()));
1431   }
1432 }
1433 /*!
1434   Slot, called when user releases mouse
1435 */
1436 void Plot2d_ViewFrame::plotMouseReleased( const QMouseEvent& me )
1437 {
1438   if ( myOperation == NoOpId && me.button() == RightButton )
1439   {
1440     QContextMenuEvent aEvent( QContextMenuEvent::Mouse,
1441                               me.pos(), me.globalPos(),
1442                               me.state() );
1443     emit contextMenuRequested( &aEvent );
1444   }
1445   if ( myOperation == FitAreaId ) {
1446     QRect rect( myPnt, me.pos() );
1447     fitArea( rect );
1448   }
1449   myPlot->canvas()->setCursor( QCursor( Qt::CrossCursor ) );
1450   myPlot->setOutlineStyle( Qwt::Triangle );
1451
1452   ((Plot2d_ViewWindow*)parent())->putInfo(tr("INF_READY"));
1453   myOperation = NoOpId;
1454 }
1455 /*!
1456   Slot, called when user wheeling mouse
1457 */
1458 void Plot2d_ViewFrame::wheelEvent(QWheelEvent* event)
1459
1460   double aDelta = event->delta();
1461   double aScale = (aDelta < 0) ? 100./(-aDelta) : aDelta/100.; 
1462
1463   QwtDiMap xMap = myPlot->canvasMap( QwtPlot::xBottom );
1464   QwtDiMap yMap = myPlot->canvasMap( QwtPlot::yLeft );
1465
1466   myPlot->setAxisScale( QwtPlot::yLeft,
1467     myPlot->invTransform( QwtPlot::yLeft, yMap.i1() ), 
1468     myPlot->invTransform( QwtPlot::yLeft, yMap.i2() )*aScale );
1469   myPlot->setAxisScale( QwtPlot::xBottom, 
1470     myPlot->invTransform( QwtPlot::xBottom, xMap.i1() ),
1471     myPlot->invTransform( QwtPlot::xBottom, xMap.i2() )*aScale );
1472   if (mySecondY) {
1473     QwtDiMap y2Map = myPlot->canvasMap( QwtPlot::yRight );
1474     myPlot->setAxisScale( QwtPlot::yRight,
1475       myPlot->invTransform( QwtPlot::yRight, y2Map.i1() ), 
1476       myPlot->invTransform( QwtPlot::yRight, y2Map.i2() )*aScale );
1477   }
1478   myPlot->replot();
1479   myPnt = event->pos();
1480 }
1481 /*!
1482   View operations : Pan view
1483 */
1484 void Plot2d_ViewFrame::onViewPan()
1485
1486   myPlot->canvas()->setCursor( panCursor );
1487   myOperation = PanId;
1488   qApp->installEventFilter( this );
1489 }
1490 /*!
1491   View operations : Zoom view
1492 */
1493 void Plot2d_ViewFrame::onViewZoom() 
1494 {
1495   myPlot->canvas()->setCursor( zoomCursor );
1496   myOperation = ZoomId;
1497   qApp->installEventFilter( this );
1498 }
1499 /*!
1500   View operations : Fot All
1501 */
1502 void Plot2d_ViewFrame::onViewFitAll() 
1503
1504   fitAll();
1505 }
1506 /*!
1507   View operations : Fit Area
1508 */
1509 void Plot2d_ViewFrame::onViewFitArea() 
1510 {
1511   myPlot->canvas()->setCursor( QCursor( Qt::PointingHandCursor ) );
1512   myOperation = FitAreaId;
1513   qApp->installEventFilter( this );
1514 }
1515 /*!
1516   View operations : Global panning
1517 */
1518 void Plot2d_ViewFrame::onViewGlobalPan() 
1519 {
1520   myPlot->canvas()->setCursor( glPanCursor );
1521   myPlot->changeAxisOptions( QwtPlot::xBottom, QwtAutoScale::Logarithmic, false );
1522   myPlot->changeAxisOptions( QwtPlot::yLeft, QwtAutoScale::Logarithmic, false );
1523   if (mySecondY)
1524     myPlot->changeAxisOptions( QwtPlot::yRight, QwtAutoScale::Logarithmic, false );
1525   myPlot->replot();
1526   QwtDiMap xMap = myPlot->canvasMap( QwtPlot::xBottom );
1527   QwtDiMap yMap = myPlot->canvasMap( QwtPlot::yLeft );
1528
1529   myXDistance = xMap.d2() - xMap.d1();
1530   myYDistance = yMap.d2() - yMap.d1();
1531
1532   if (mySecondY) {
1533     QwtDiMap yMap2 = myPlot->canvasMap( QwtPlot::yRight );
1534     myYDistance2 = yMap2.d2() - yMap2.d1();
1535   }
1536   fitAll();
1537   myOperation = GlPanId;
1538   qApp->installEventFilter( this );
1539 }
1540
1541 //=================================================================================
1542 // Plot2d_Plot2d implementation
1543 //=================================================================================
1544 /*!
1545   Constructor
1546 */
1547 Plot2d_Plot2d::Plot2d_Plot2d( QWidget* parent )
1548      : QwtPlot( parent )
1549 {
1550   // outline
1551   enableOutline( true );
1552   setOutlineStyle( Qwt::Triangle );
1553   setOutlinePen( green );
1554   // legend
1555   setAutoLegend( false );
1556   setLegendFrameStyle( QFrame::Box | QFrame::Sunken );
1557   enableLegend( false );
1558   // grid
1559   enableGridX( false );
1560   enableGridXMin( false );
1561   enableGridY( false );
1562   enableGridYMin( false );
1563   // auto scaling by default
1564   setAxisAutoScale( QwtPlot::yLeft );
1565   setAxisAutoScale( QwtPlot::yRight );
1566   setAxisAutoScale( QwtPlot::xBottom );
1567 }
1568 /*!
1569   Recalculates and redraws Plot 2d view 
1570 */
1571 void Plot2d_Plot2d::replot()
1572 {
1573   updateLayout();  // to fix bug(?) of Qwt - view is not updated when title is changed
1574   QwtPlot::replot(); 
1575 }
1576
1577 /*!
1578   Checks if two colors are close to each other [ static ]
1579   uses COLOR_DISTANCE variable as max tolerance for comparing of colors
1580 */
1581 const long COLOR_DISTANCE = 100;
1582 const int  MAX_ATTEMPTS   = 10;
1583 static bool closeColors( const QColor& color1, const QColor& color2 )
1584 {
1585   long tol = abs( color2.red()   - color1.red() ) + 
1586              abs( color2.green() - color1.green() ) +
1587        abs( color2.blue()  - color1.blue() );
1588
1589   return ( tol <= COLOR_DISTANCE );
1590 }
1591 /*!
1592   Gets new unique marker for item if possible
1593 */
1594 void Plot2d_Plot2d::getNextMarker( QwtSymbol::Style& typeMarker, QColor& color, Qt::PenStyle& typeLine ) 
1595 {
1596   bool bOk = false;
1597   int cnt = 1;
1598   while ( !bOk ) {
1599     int aRed    = (int)( 256.0 * rand() / RAND_MAX);    // generate random color
1600     int aGreen  = (int)( 256.0 * rand() / RAND_MAX);    // ...
1601     int aBlue   = (int)( 256.0 * rand() / RAND_MAX);    // ...
1602     int aMarker = (int)( 9.0 * rand() / RAND_MAX) + 1;  // 9 markers types ( not including empty )
1603     int aLine   = (int)( 5.0 * rand() / RAND_MAX) + 1;  // 5 line types ( not including empty )
1604
1605     typeMarker = ( QwtSymbol::Style )aMarker;
1606     color      = QColor( aRed, aGreen, aBlue );
1607     typeLine   = ( Qt::PenStyle )aLine;
1608
1609     cnt++;
1610     if ( cnt == MAX_ATTEMPTS )
1611       bOk = true;
1612     else
1613       bOk = !existMarker( typeMarker, color, typeLine );
1614   }
1615 /*
1616   static int aMarker = -1;
1617   static int aColor  = -1;
1618   static int aLine   = -1;
1619
1620   if ( myColors.isEmpty() ) {
1621     // creating colors list
1622     myColors.append( Qt::white );
1623     myColors.append( Qt::blue );
1624     myColors.append( Qt::gray );
1625     myColors.append( Qt::darkGreen );
1626     myColors.append( Qt::magenta );
1627     myColors.append( Qt::darkGray );
1628     myColors.append( Qt::red );
1629     myColors.append( Qt::darkBlue );
1630     myColors.append( Qt::darkYellow );
1631     myColors.append( Qt::cyan );
1632     myColors.append( Qt::darkRed );
1633     myColors.append( Qt::darkCyan );
1634     myColors.append( Qt::yellow );
1635     myColors.append( Qt::darkMagenta );
1636     myColors.append( Qt::green );
1637     myColors.append( Qt::black );
1638   }
1639
1640   int nbMarkers = 11;                   // QwtSymbol supports 11 marker types
1641   int nbLines   = 6;                    // Qt supports 6 line types
1642   int nbColors  = myColors.count();     // number of default colors supported
1643
1644   aMarker = ( aMarker + 1 ) % nbMarkers;  
1645   if ( aMarker == QwtSymbol::None || aMarker == QwtSymbol::Triangle ) aMarker++;
1646   aColor  = ( aColor  + 1 ) % nbColors;
1647   aLine   = ( aLine   + 1 ) % nbLines;    
1648   if ( aLine == Qt::NoPen ) aLine++;             
1649
1650   typeMarker = ( QwtSymbol::Style )aMarker;
1651   color      = myColors[ aColor ];
1652   typeLine   = ( Qt::PenStyle )aLine;
1653   if ( !existMarker( typeMarker, color, typeLine ) )
1654     return;
1655
1656   int i, j, k;
1657   for ( i = 0; i < nbMarkers; i++ ) {
1658     aMarker = ( aMarker + 1 ) % nbMarkers;
1659     if ( aMarker == QwtSymbol::None || aMarker == QwtSymbol::Triangle ) aMarker++;
1660     for ( j = 0; j < nbColors; j++ ) {
1661       aColor  = ( aColor  + 1 ) % nbColors;
1662       for ( k = 0; k < nbLines; k++ ) {
1663         aLine = ( aLine + 1 ) % nbLines;
1664   if ( aLine == Qt::NoPen ) aLine++;             
1665         if ( !existMarker( ( QwtSymbol::Style )aMarker, aColor, ( Qt::PenStyle )aLine ) ) {
1666           typeMarker = ( QwtSymbol::Style )aMarker;
1667           color      = myColors[ aColor ];
1668           typeLine   = ( Qt::PenStyle )aLine;
1669           return;
1670         }
1671       }
1672     }
1673   }
1674 */
1675 }
1676
1677 QSizePolicy Plot2d_Plot2d::sizePolicy() const
1678 {
1679   return QSizePolicy( QSizePolicy::Preferred, QSizePolicy::Preferred );
1680 }
1681
1682 QSize Plot2d_Plot2d::sizeHint() const
1683 {
1684   return QwtPlot::minimumSizeHint();
1685 }
1686
1687 /*!
1688   return minimum size for qwt plot
1689 */
1690 QSize Plot2d_Plot2d::minimumSizeHint() const
1691 {
1692   return QSize( 0, 0 );
1693 //  QSize aSize = QwtPlot::minimumSizeHint();
1694 //  return QSize(aSize.width()*3/4, aSize.height());
1695 }
1696 /*!
1697   Checks if marker belongs to any enitity
1698 */
1699 bool Plot2d_Plot2d::existMarker( const QwtSymbol::Style typeMarker, const QColor& color, const Qt::PenStyle typeLine ) 
1700 {
1701   // getting all curves
1702   QArray<long> keys = curveKeys();
1703   //QColor aRgbColor;
1704
1705   if ( closeColors( color, backgroundColor() ) )
1706       return true;
1707   for ( int i = 0; i < (int)keys.count(); i++ )
1708   {
1709     QwtPlotCurve* crv = curve( keys[i] );
1710     if ( crv ) {
1711       QwtSymbol::Style aStyle = crv->symbol().style();
1712       QColor           aColor = crv->pen().color();
1713       Qt::PenStyle     aLine  = crv->pen().style();
1714 //      if ( aStyle == typeMarker && aColor == color && aLine == typeLine )
1715       if ( aStyle == typeMarker && closeColors( aColor,color ) && aLine == typeLine )
1716   return true;
1717     }
1718   }
1719   return false;
1720 }
1721
1722 // TEMPORARY SOLUTION!!!  TO BE IMPLEMENTED!!!
1723 Plot2d_Prs* Plot2d_ViewFrame::CreatePrs( const char* /*entry*/ )
1724 {
1725   return 0;
1726 }
1727
1728 void Plot2d_ViewFrame::copyPreferences( Plot2d_ViewFrame* vf )
1729 {
1730   if( !vf )
1731     return;
1732
1733   myCurveType = vf->myCurveType;
1734   myShowLegend = vf->myShowLegend;
1735   myLegendPos = vf->myLegendPos;
1736   myMarkerSize = vf->myMarkerSize;
1737   myBackground = vf->myBackground;
1738   myTitle = vf->myTitle; 
1739   myXTitle = vf->myXTitle;
1740   myYTitle = vf->myYTitle;
1741   myY2Title = vf->myY2Title;
1742   myTitleEnabled = vf->myTitleEnabled;
1743   myXTitleEnabled = vf->myXTitleEnabled;
1744   myYTitleEnabled = vf->myYTitleEnabled;
1745   myY2TitleEnabled = vf->myY2TitleEnabled;
1746   myXGridMajorEnabled = vf->myXGridMajorEnabled;
1747   myYGridMajorEnabled = vf->myYGridMajorEnabled;
1748   myY2GridMajorEnabled = vf->myY2GridMajorEnabled;
1749   myXGridMinorEnabled = vf->myXGridMinorEnabled;
1750   myYGridMinorEnabled = vf->myYGridMinorEnabled;
1751   myY2GridMinorEnabled = vf->myY2GridMinorEnabled;
1752   myXGridMaxMajor = vf->myXGridMaxMajor;
1753   myYGridMaxMajor = vf->myYGridMaxMajor;
1754   myY2GridMaxMajor = vf->myY2GridMaxMajor;
1755   myXGridMaxMinor = vf->myXGridMaxMinor;
1756   myYGridMaxMinor = vf->myYGridMaxMinor;
1757   myY2GridMaxMinor = vf->myY2GridMaxMinor;
1758   myXMode = vf->myXMode;
1759   myYMode = vf->myYMode;
1760   mySecondY = vf->mySecondY;
1761 }