Salome HOME
NRI : Merge from V1_2.
[modules/kernel.git] / src / Plot2d / Plot2d_ViewFrame.cxx
1 //  Copyright (C) 2003  CEA/DEN, EDF R&D
2 //
3 //
4 //
5 //  File   : Plot2d_ViewFrame.cxx
6 //  Author : Vadim SANDLER
7 //  Module : SALOME
8 //  $Header$
9
10 #include "Plot2d_ViewFrame.h"
11 #include "Plot2d_SetupViewDlg.h"
12 #include "QAD_Desktop.h"
13 #include "QAD_ResourceMgr.h"
14 #include "QAD_FileDlg.h"
15 #include "QAD_Tools.h"
16 #include "QAD_MessageBox.h"
17 #include "QAD_Config.h"
18 #include "SALOME_Selection.h"
19 #include "Plot2d_CurveContainer.h"
20 #include "Plot2d_Curve.h"
21 #include "Plot2d_FitDataDlg.h"
22 #include "utilities.h"
23 #include "qapplication.h"
24 #include <qtoolbar.h>
25 #include <qtoolbutton.h>
26 #include <qcursor.h>
27 #include <qwt_math.h>
28 #include <qwt_plot_canvas.h>
29 #include <stdlib.h>
30 #include "utilities.h"
31
32 // IDL headers
33 #include <SALOMEconfig.h>
34 #include CORBA_SERVER_HEADER(SALOMEDS)
35 #include CORBA_SERVER_HEADER(SALOMEDS_Attributes)
36
37 #define DEFAULT_LINE_WIDTH     0     // (default) line width
38 #define DEFAULT_MARKER_SIZE    9     // default marker size
39 #define MIN_RECT_SIZE          11    // min sensibility area size
40
41 /* XPM */
42 const char* imageZoomCursor[] = { 
43 "32 32 3 1",
44 ". c None",
45 "a c #000000",
46 "# c #ffffff",
47 "................................",
48 "................................",
49 ".#######........................",
50 "..aaaaaaa.......................",
51 "................................",
52 ".............#####..............",
53 "...........##.aaaa##............",
54 "..........#.aa.....a#...........",
55 ".........#.a.........#..........",
56 ".........#a..........#a.........",
57 "........#.a...........#.........",
58 "........#a............#a........",
59 "........#a............#a........",
60 "........#a............#a........",
61 "........#a............#a........",
62 ".........#...........#.a........",
63 ".........#a..........#a.........",
64 ".........##.........#.a.........",
65 "........#####.....##.a..........",
66 ".......###aaa#####.aa...........",
67 "......###aa...aaaaa.......#.....",
68 ".....###aa................#a....",
69 "....###aa.................#a....",
70 "...###aa...............#######..",
71 "....#aa.................aa#aaaa.",
72 ".....a....................#a....",
73 "..........................#a....",
74 "...........................a....",
75 "................................",
76 "................................",
77 "................................",
78 "................................"};
79
80
81 //=================================================================================
82 // Plot2d_ViewFrame implementation
83 //=================================================================================
84
85 /*!
86   Constructor
87 */
88 Plot2d_ViewFrame::Plot2d_ViewFrame( QWidget* parent, const QString& title )
89      : QAD_ViewFrame( parent, title ),
90        myOperation( NoOpId ), 
91        myCurveType( 1 ), 
92        myShowLegend( true ), myLegendPos( 1 ),
93        myMarkerSize( DEFAULT_MARKER_SIZE ),
94        myTitle( "" ), myXTitle( "" ), myYTitle( "" ),
95        myBackground( white ),
96        myTitleEnabled( true ), myXTitleEnabled( true ), myYTitleEnabled( true ),
97        myXGridMajorEnabled( true ), myYGridMajorEnabled( true ), 
98        myXGridMinorEnabled( false ), myYGridMinorEnabled( false ),
99        myXGridMaxMajor( 8 ), myYGridMaxMajor( 8 ), myXGridMaxMinor( 5 ), myYGridMaxMinor( 5 ),
100        myXMode( 0 ), myYMode( 0 )
101        
102 {
103   myCurves.setAutoDelete( true );
104   /* Plot 2d View */
105   myPlot = new Plot2d_Plot2d( this );
106   setCentralWidget( myPlot );
107
108   createActions();
109
110   connect( myPlot, SIGNAL( plotMouseMoved( const QMouseEvent& ) ),
111            this,   SLOT( plotMouseMoved( const QMouseEvent& ) ) );
112   connect( myPlot, SIGNAL( plotMousePressed( const QMouseEvent& ) ),
113            this,   SLOT( plotMousePressed( const QMouseEvent& ) ) );
114   connect( myPlot, SIGNAL( plotMouseReleased( const QMouseEvent& ) ),
115            this,   SLOT( plotMouseReleased( const QMouseEvent& ) ) );
116   connect( myPlot, SIGNAL( legendClicked( long ) ),
117            this,   SLOT( onLegendClicked( long ) ) );
118
119   /* Initial Setup - get from the preferences */
120   readPreferences();
121
122   myPlot->setMargin( 5 );
123   setCurveType( myCurveType, false );
124   setXGrid( myXGridMajorEnabled, myXGridMaxMajor, myXGridMinorEnabled, myXGridMaxMinor, false );
125   setYGrid( myYGridMajorEnabled, myYGridMaxMajor, myYGridMinorEnabled, myYGridMaxMinor, false );
126   setMainTitle( myTitleEnabled, myTitle, false );
127   setXTitle( myXTitleEnabled, myXTitle, false );
128   setYTitle( myYTitleEnabled, myYTitle, false );
129   setHorScaleMode( myXMode, false );
130   setVerScaleMode( myYMode, false );
131   setBackgroundColor( myBackground );
132   setLegendPos( myLegendPos );
133   showLegend( myShowLegend, false );
134   myPlot->replot();
135
136   if ( parent ) {
137     resize( (int)(0.8 * parent->width()), (int)(0.8 * parent->height()) );
138   }
139 }
140 /*!
141   Destructor
142 */
143 Plot2d_ViewFrame::~Plot2d_ViewFrame()
144 {
145   myActions.clear();
146   qApp->removeEventFilter( this );
147 }
148 /*!
149   Creates popup menu actions
150 */
151 void Plot2d_ViewFrame::createActions()
152 {
153   QAD_ResourceMgr* rmgr = QAD_Desktop::getResourceManager();
154   /* Linear/logarithmic mode */
155   // Horizontal axis
156   QActionPGroup* modeHorGrp = new QActionPGroup( this );
157   modeHorGrp->setExclusive( TRUE );
158   QActionP* linearXAction = new QActionP ( tr( "TOT_PLOT2D_MODE_LINEAR_HOR"),
159                                          rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_MODE_LINEAR_HOR") ) ,
160                                          tr( "MEN_PLOT2D_MODE_LINEAR_HOR" ), 0, modeHorGrp );
161   linearXAction->setStatusTip ( tr( "PRP_PLOT2D_MODE_LINEAR_HOR" ) );
162   linearXAction->setToggleAction( true );
163   myActions.insert( ModeXLinearId, linearXAction );
164   QActionP* logXAction = new QActionP ( tr( "TOT_PLOT2D_MODE_LOGARITHMIC_HOR"),
165                                       rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_MODE_LOGARITHMIC_HOR") ) ,
166                                       tr( "MEN_PLOT2D_MODE_LOGARITHMIC_HOR" ), 0, modeHorGrp );
167   logXAction->setStatusTip ( tr( "PRP_PLOT2D_MODE_LOGARITHMIC_HOR" ) );
168   logXAction->setToggleAction( true );
169   myActions.insert( ModeXLogarithmicId, logXAction );
170   connect( modeHorGrp, SIGNAL( selected( QActionP* ) ), this, SLOT( onHorMode() ) );
171
172   // Vertical axis
173   QActionPGroup* modeVerGrp = new QActionPGroup( this );
174   modeVerGrp->setExclusive( TRUE );
175   QActionP* linearYAction = new QActionP ( tr( "TOT_PLOT2D_MODE_LINEAR_VER"),
176                                          rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_MODE_LINEAR_VER") ) ,
177                                          tr( "MEN_PLOT2D_MODE_LINEAR_VER" ), 0, modeVerGrp );
178   linearYAction->setStatusTip ( tr( "PRP_PLOT2D_MODE_LINEAR_VER" ) );
179   linearYAction->setToggleAction( true );
180   myActions.insert( ModeYLinearId, linearYAction );
181   QActionP* logYAction = new QActionP ( tr( "TOT_PLOT2D_MODE_LOGARITHMIC_VER"),
182                                       rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_MODE_LOGARITHMIC_VER") ) ,
183                                       tr( "MEN_PLOT2D_MODE_LOGARITHMIC_VER" ), 0, modeVerGrp );
184   logYAction->setStatusTip ( tr( "PRP_PLOT2D_MODE_LOGARITHMIC_VER" ) );
185   logYAction->setToggleAction( true );
186   myActions.insert( ModeYLogarithmicId, logYAction );
187   connect( modeVerGrp, SIGNAL( selected( QActionP* ) ), this, SLOT( onVerMode() ) );
188
189   /* Legend */
190   QActionP* legendAction = new QActionP ( tr( "TOT_PLOT2D_SHOW_LEGEND"),
191                                         rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_SHOW_LEGEND") ) ,
192                                         tr( "MEN_PLOT2D_SHOW_LEGEND" ), 0, this );
193   legendAction->setStatusTip ( tr( "PRP_PLOT2D_SHOW_LEGEND" ) );
194   legendAction->setToggleAction( true );
195   myActions.insert( LegendId, legendAction );
196   connect( legendAction, SIGNAL( activated() ), this, SLOT( onLegend() ) );
197
198   /* Curve type */
199   QActionPGroup* curveGrp = new QActionPGroup( this );
200   curveGrp->setExclusive( TRUE );
201   QActionP* pointsAction = new QActionP ( tr( "TOT_PLOT2D_CURVES_POINTS"),
202                                         rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_CURVES_POINTS") ) ,
203                                         tr( "MEN_PLOT2D_CURVES_POINTS" ), 0, curveGrp );
204   pointsAction->setStatusTip ( tr( "PRP_PLOT2D_CURVES_POINTS" ) );
205   pointsAction->setToggleAction( true );
206   myActions.insert( CurvePointsId, pointsAction );
207   QActionP* linesAction = new QActionP ( tr( "TOT_PLOT2D_CURVES_LINES"),
208                                        rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_CURVES_LINES") ) ,
209                                        tr( "MEN_PLOT2D_CURVES_LINES" ), 0, curveGrp );
210   linesAction->setStatusTip ( tr( "PRP_PLOT2D_CURVES_LINES" ) );
211   linesAction->setToggleAction( true );
212   myActions.insert( CurveLinesId, linesAction );
213   QActionP* splinesAction = new QActionP ( tr( "TOT_PLOT2D_CURVES_SPLINES"),
214                                          rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_CURVES_SPLINES") ) ,
215                                          tr( "MEN_PLOT2D_CURVES_SPLINES" ), 0, curveGrp );
216   splinesAction->setStatusTip ( tr( "PRP_PLOT2D_CURVES_SPLINES" ) );
217   splinesAction->setToggleAction( true );
218   myActions.insert( CurveSplinesId, splinesAction );
219   connect( curveGrp, SIGNAL( selected( QActionP* ) ), this, SLOT( onCurves() ) );
220
221   // Settings
222   QActionP* settingsAction = new QActionP ( tr( "TOT_PLOT2D_SETTINGS"),
223                                           rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_SETTINGS") ) ,
224                                           tr( "MEN_PLOT2D_SETTINGS" ), 0, this );
225   settingsAction->setStatusTip ( tr( "PRP_PLOT2D_SETTINGS" ) );
226   myActions.insert( SettingsId, settingsAction );
227   connect( settingsAction, SIGNAL( activated() ), this, SLOT( onSettings() ) );
228
229   // Fit Data
230   QActionP* fitDataAction = new QActionP ( tr( "TOT_PLOT2D_FITDATA"),
231                                          rmgr->loadPixmap( "SALOMEGUI", tr("ICON_PLOT2D_FITDATA") ) ,
232                                          tr( "MEN_PLOT2D_FITDATA" ), 0, this );
233   fitDataAction->setStatusTip ( tr( "PRP_PLOT2D_FITDATA" ) );
234   myActions.insert( FitDataId, fitDataAction );
235   connect( fitDataAction, SIGNAL( activated() ), this, SLOT( onFitData() ) );
236 }
237 /*!
238   Gets window's central widget
239 */
240 QWidget* Plot2d_ViewFrame::getViewWidget()
241 {
242   return (QWidget*)myPlot;
243 }
244 /* Popup management : sets Popup server */
245 void Plot2d_ViewFrame::setPopupServer( QAD_Application* App )
246 {
247 //  QAD_PopupClientServer::setPopupServer( (QAD_PopupServer*)App );
248 }
249 /*!
250   Popup menu creation
251 */
252 void Plot2d_ViewFrame::onCreatePopup()
253 {
254   if ( myPopup ) {
255     myPopup->clear();
256     // scaling
257     QPopupMenu* scalingPopup = new QPopupMenu( myPopup );
258     myActions[ ModeXLinearId ]->addTo( scalingPopup );
259     myActions[ ModeXLogarithmicId ]->addTo( scalingPopup );
260     scalingPopup->insertSeparator();
261     myActions[ ModeYLinearId ]->addTo( scalingPopup );
262     myActions[ ModeYLogarithmicId ]->addTo( scalingPopup );
263     myActions[ FitDataId ]->addTo( myPopup );
264     myPopup->insertItem( tr( "SCALING_POPUP" ), scalingPopup );
265     // curve type
266     QPopupMenu* curTypePopup = new QPopupMenu( myPopup );
267     myActions[ CurvePointsId ]->addTo( curTypePopup );
268     myActions[ CurveLinesId ]->addTo( curTypePopup );
269     myActions[ CurveSplinesId ]->addTo( curTypePopup );
270     myPopup->insertItem( tr( "CURVE_TYPE_POPUP" ), curTypePopup );
271     // legend
272     myPopup->insertSeparator();
273     myActions[ LegendId ]->addTo( myPopup );
274     // settings
275     myPopup->insertSeparator();
276     myActions[ SettingsId ]->addTo( myPopup );
277   }
278 }
279 /*!
280   Renames curve if it is found
281 */
282 void Plot2d_ViewFrame::rename( const Handle(SALOME_InteractiveObject)& IObject, QString newName ) 
283 {
284   Plot2d_Curve* curve = getCurveByIO( IObject );
285   if ( curve ) {
286     curve->setVerTitle( newName );
287     int key = hasCurve( curve );
288     if ( key ) {
289       myPlot->setCurveTitle( key, newName );
290 //      int legendIndex = myPlot->getLegend()->findFirstKey( key );
291 //      if ( legendIndex != myPlot->getLegend()->itemCnt() )
292 //      myPlot->getLegend()->setText( legendIndex, aSymbol );
293     }
294   }
295   updateTitles();
296 }
297 /*!
298   Returns true if interactive object is presented in the viewer
299 */
300 bool Plot2d_ViewFrame::isInViewer( const Handle(SALOME_InteractiveObject)& IObject ) 
301 {
302   return ( getCurveByIO( IObject ) != NULL );
303 }
304 /*!
305   Returns true if interactive object is presented in the viewer and displayed
306 */
307 bool Plot2d_ViewFrame::isVisible( const Handle(SALOME_InteractiveObject)& IObject ) 
308 {
309   Plot2d_Curve* curve = getCurveByIO( IObject );
310   if ( curve ) {
311     int key = hasCurve( curve );
312     if ( key )
313       return myPlot->curve( key )->enabled();
314   }
315   return false;
316 }
317 /*!
318   Return interactive obeject if is presented in the viewer
319 */
320 Handle(SALOME_InteractiveObject) Plot2d_ViewFrame::FindIObject( const char* Entry )
321 {
322   Handle(SALOME_InteractiveObject) o;
323   QIntDictIterator<Plot2d_Curve> it( myCurves );
324   for ( ; it.current(); ++it ) {
325     if ( it.current()->hasIO() && !strcmp( it.current()->getIO()->getEntry(), Entry ) ) {
326       o = it.current()->getIO();
327       break;
328     }
329   }
330   return o;
331 }
332 /*!
333   Actually this method just re-displays curves which refers to the <IObject>
334 */
335 void Plot2d_ViewFrame::Display( const Handle(SALOME_InteractiveObject)& IObject, bool update )
336 {
337   Plot2d_Curve* curve = getCurveByIO( IObject );
338   if ( curve )
339     updateCurve( curve, update );
340 }
341 /*!
342   Actually this method just erases all curves which don't refer to <IOBject> 
343   and re-displays curve which is of <IObject>
344 */
345 void Plot2d_ViewFrame::DisplayOnly( const Handle(SALOME_InteractiveObject)& IObject )
346 {
347   Plot2d_Curve* curve = getCurveByIO( IObject );
348   QList<Plot2d_Curve> clist;
349   getCurves( clist );
350   for ( int i = 0; i < clist.count(); i++ ) {
351     if ( clist.at( i ) != curve )
352       eraseCurve( curve );
353     else
354       updateCurve( curve, false );
355   }
356   myPlot->replot();
357 }
358 /*!
359   Removes from the viewer the curves which refer to <IObject>
360 */
361 void Plot2d_ViewFrame::Erase( const Handle(SALOME_InteractiveObject)& IObject, bool update )
362 {
363   Plot2d_Curve* curve = getCurveByIO( IObject );
364   if ( curve )
365     eraseCurve( curve, update );
366 }
367 /*!
368   Actually this method just re-displays all curves which are presented in the viewer
369 */
370 void Plot2d_ViewFrame::DisplayAll()
371 {
372   QList<Plot2d_Curve> clist;
373   getCurves( clist );
374   for ( int i = 0; i < clist.count(); i++ ) {
375     updateCurve( clist.at( i ), false );
376   }
377   myPlot->replot();
378 }
379 /*!
380    Removes all curves from the view
381 */
382 void Plot2d_ViewFrame::EraseAll() 
383 {
384   myPlot->clear();
385   myCurves.clear();
386   myPlot->replot();
387 }
388 /*!
389   Redraws viewframe contents
390 */
391 void Plot2d_ViewFrame::Repaint()
392 {
393   myPlot->replot();
394 }
395 /*!
396   Event filter
397 */
398 bool Plot2d_ViewFrame::eventFilter( QObject* o, QEvent* e )
399 {
400   if ( ( e->type() == QEvent::MouseButtonPress || e->type() == QEvent::KeyPress ) && o != myPlot->canvas() ) {
401     myOperation = NoOpId;
402     qApp->removeEventFilter( this );
403   }
404   return QMainWindow::eventFilter( o, e );
405 }
406 /*!
407   Sets title
408 */
409 void Plot2d_ViewFrame::setTitle( const QString& title )
410 {
411   setMainTitle( myTitleEnabled, title, true );
412 }
413 /*!
414   Reads Plot2d view settings from the preferences
415 */
416 void Plot2d_ViewFrame::readPreferences()
417 {
418   if ( QAD_CONFIG->hasSetting( "Plot2d:CurveType" ) ) {                                          // curve type
419     myCurveType = QAD_CONFIG->getSetting( "Plot2d:CurveType" ).toInt();                             
420     if ( myCurveType < 0 || myCurveType > 2 ) myCurveType = 1;
421   }
422   if ( QAD_CONFIG->hasSetting( "Plot2d:ShowLegend" ) ) {                                          
423     myShowLegend = QAD_CONFIG->getSetting( "Plot2d:ShowLegend" ) == QString( "true" );           // show legend
424   }
425   if ( QAD_CONFIG->hasSetting( "Plot2d:LegendPos" ) ) {                                          // legend position
426     myLegendPos  = QAD_CONFIG->getSetting( "Plot2d:LegendPos" ).toInt();                            
427     if ( myLegendPos < 0 || myLegendPos > 3 ) myLegendPos = 1;
428   }
429   if ( QAD_CONFIG->hasSetting( "Plot2d:MarkerSize" ) ) {                                         // marker size
430     myMarkerSize = QAD_CONFIG->getSetting( "Plot2d:MarkerSize" ).toInt();                           
431   }
432   if ( QAD_CONFIG->hasSetting( "Plot2d:Background" ) ) {                                         // background color
433     QString bgString = QAD_CONFIG->getSetting( "Plot2d:Background" );                               
434     QStringList bgData = QStringList::split( ":", bgString, true );
435     int bgRed = 0, bgGreen = 0, bgBlue = 0;
436     if ( bgData.count() > 0 ) bgRed   = bgData[ 0 ].toInt();
437     if ( bgData.count() > 1 ) bgGreen = bgData[ 1 ].toInt();
438     if ( bgData.count() > 2 ) bgBlue  = bgData[ 2 ].toInt();
439     myBackground = QColor( bgRed, bgGreen, bgBlue );
440   }
441   if ( QAD_CONFIG->hasSetting( "Plot2d:ShowTitle" ) ) {                                          // main title
442     myTitleEnabled  = QAD_CONFIG->getSetting( "Plot2d:ShowTitle" ) == QString( "true" );               
443   }
444   if ( QAD_CONFIG->hasSetting( "Plot2d:ShowHorTitle" ) ) {                                       // hor.axis title
445     myXTitleEnabled = QAD_CONFIG->getSetting( "Plot2d:ShowHorTitle" ) == QString( "true" );
446   }
447   if ( QAD_CONFIG->hasSetting( "Plot2d:ShowVerTitle" ) ) {                                       // ver.axisn title
448     myYTitleEnabled = QAD_CONFIG->getSetting( "Plot2d:ShowVerTitle" ) == QString( "true" );
449   }
450   if ( QAD_CONFIG->hasSetting( "Plot2d:EnableHorMajorGrid" ) ) {                                 // grid
451     myXGridMajorEnabled = QAD_CONFIG->getSetting( "Plot2d:EnableHorMajorGrid" ) == QString( "true" ); 
452   }
453   if ( QAD_CONFIG->hasSetting( "Plot2d:EnableVerMajorGrid" ) ) {      
454     myYGridMajorEnabled = QAD_CONFIG->getSetting( "Plot2d:EnableVerMajorGrid" ) == QString( "true" );
455   }
456   if ( QAD_CONFIG->hasSetting( "Plot2d:EnableHorMinorGrid" ) ) {
457     myXGridMinorEnabled = QAD_CONFIG->getSetting( "Plot2d:EnableHorMinorGrid" ) == QString( "true" );
458   }
459   if ( QAD_CONFIG->hasSetting( "Plot2d:EnableVerMinorGrid" ) ) {
460     myYGridMinorEnabled = QAD_CONFIG->getSetting( "Plot2d:EnableVerMinorGrid" ) == QString( "true" );
461   }
462   if ( QAD_CONFIG->hasSetting( "Plot2d:HorMajorGridMax" ) ) {
463     myXGridMaxMajor = QAD_CONFIG->getSetting( "Plot2d:HorMajorGridMax" ).toInt();
464   }
465   if ( QAD_CONFIG->hasSetting( "Plot2d:VerMajorGridMax" ) ) {
466     myYGridMaxMajor = QAD_CONFIG->getSetting( "Plot2d:VerMajorGridMax" ).toInt();
467   }
468   if ( QAD_CONFIG->hasSetting( "Plot2d:HorMinorGridMax" ) ) {
469     myXGridMaxMinor = QAD_CONFIG->getSetting( "Plot2d:HorMinorGridMax" ).toInt();
470   }
471   if ( QAD_CONFIG->hasSetting( "Plot2d:VerMinorGridMax" ) ) {
472     myYGridMaxMinor = QAD_CONFIG->getSetting( "Plot2d:VerMinorGridMax" ).toInt();
473   }
474   if ( QAD_CONFIG->hasSetting( "Plot2d:HorScaleMode" ) ) {                                       // scale mode
475     myXMode = QAD_CONFIG->getSetting( "Plot2d:HorScaleMode" ).toInt();                             
476     if ( myXMode < 0 || myXMode > 1 ) myXMode = 0;
477   }
478   if ( QAD_CONFIG->hasSetting( "Plot2d:VerScaleMode" ) ) {                                       
479     myYMode = QAD_CONFIG->getSetting( "Plot2d:VerScaleMode" ).toInt();
480     if ( myYMode < 0 || myYMode > 1 ) myYMode = 0;
481   }
482 }
483 /*!
484   Writes Plot2d view settings to the preferences
485 */
486 void Plot2d_ViewFrame::writePreferences()
487 {
488   QAD_CONFIG->addSetting( "Plot2d:CurveType",  myCurveType );                                     // curve type
489   QAD_CONFIG->addSetting( "Plot2d:ShowLegend", myShowLegend ? "true" : "false" );                 // show legend
490   QAD_CONFIG->addSetting( "Plot2d:LegendPos",  myLegendPos );                                     // legend position
491   QAD_CONFIG->addSetting( "Plot2d:MarkerSize", myMarkerSize );                                    // marker size
492   QStringList bgData; 
493   bgData.append( QString::number( myBackground.red() ) );
494   bgData.append( QString::number( myBackground.green() ) );
495   bgData.append( QString::number( myBackground.blue() ) );
496   QAD_CONFIG->addSetting( "Plot2d:Background",   bgData.join( ":" ) );                            // background color
497   QAD_CONFIG->addSetting( "Plot2d:ShowTitle",    myTitleEnabled ?  "true" : "false" );            // titles
498   QAD_CONFIG->addSetting( "Plot2d:ShowHorTitle", myXTitleEnabled ? "true" : "false" ); 
499   QAD_CONFIG->addSetting( "Plot2d:ShowVerTitle", myYTitleEnabled ? "true" : "false" ); 
500   QAD_CONFIG->addSetting( "Plot2d:EnableHorMajorGrid", myXGridMajorEnabled ? "true" : "false" );  // grid
501   QAD_CONFIG->addSetting( "Plot2d:EnableVerMajorGrid", myYGridMajorEnabled ? "true" : "false" );  
502   QAD_CONFIG->addSetting( "Plot2d:EnableHorMinorGrid", myXGridMinorEnabled ? "true" : "false" );  
503   QAD_CONFIG->addSetting( "Plot2d:EnableVerMinorGrid", myYGridMinorEnabled ? "true" : "false" );  
504   QAD_CONFIG->addSetting( "Plot2d:HorMajorGridMax", myXGridMaxMajor );
505   QAD_CONFIG->addSetting( "Plot2d:VerMajorGridMax", myYGridMaxMajor );
506   QAD_CONFIG->addSetting( "Plot2d:HorMinorGridMax", myXGridMaxMinor );
507   QAD_CONFIG->addSetting( "Plot2d:VerMinorGridMax", myYGridMaxMinor );
508   QAD_CONFIG->addSetting( "Plot2d:HorScaleMode", myXMode );                                       // scale mode
509   QAD_CONFIG->addSetting( "Plot2d:VerScaleMode", myYMode );
510 }
511 /*!
512   Prints mouse cursor coordinates into string
513 */
514 QString Plot2d_ViewFrame::getInfo( const QPoint& pnt ) 
515 {
516   QString info;
517   info.sprintf( "X : %g\tY : %g",
518                 myPlot->invTransform( QwtPlot::xBottom, pnt.x() ),
519                 myPlot->invTransform( QwtPlot::yLeft,   pnt.y() ) );
520   info = tr( "INF_COORDINATES" ) + " : " + info;
521   return info;
522 }
523 /*!
524   Converts Plot2d_Curve's marker style to Qwt marker style [ static ]
525 */
526 static QwtSymbol::Style plot2qwtMarker( Plot2d_Curve::MarkerType m )
527 {
528   QwtSymbol::Style ms = QwtSymbol::None;  
529   switch ( m ) {
530   case Plot2d_Curve::Circle:
531     ms = QwtSymbol::Ellipse;   break;
532   case Plot2d_Curve::Rectangle:
533     ms = QwtSymbol::Rect;      break;
534   case Plot2d_Curve::Diamond:
535     ms = QwtSymbol::Diamond;   break;
536   case Plot2d_Curve::DTriangle:
537     ms = QwtSymbol::DTriangle; break;
538   case Plot2d_Curve::UTriangle:
539     ms = QwtSymbol::UTriangle; break;
540   case Plot2d_Curve::LTriangle: // Qwt confuses LTriangle and RTriangle :(((
541     ms = QwtSymbol::RTriangle; break;
542   case Plot2d_Curve::RTriangle: // Qwt confuses LTriangle and RTriangle :(((
543     ms = QwtSymbol::LTriangle; break;
544   case Plot2d_Curve::Cross:
545     ms = QwtSymbol::Cross;     break;
546   case Plot2d_Curve::XCross:
547     ms = QwtSymbol::XCross;    break;
548   case Plot2d_Curve::None:
549   default:
550     ms = QwtSymbol::None;      break;
551   }
552   return ms;
553 }
554 /*!
555   Converts Qwt marker style to Plot2d_Curve's marker style [ static ]
556 */
557 static Plot2d_Curve::MarkerType qwt2plotMarker( QwtSymbol::Style m )
558 {
559   Plot2d_Curve::MarkerType ms = Plot2d_Curve::None;  
560   switch ( m ) {
561   case QwtSymbol::Ellipse:
562     ms = Plot2d_Curve::Circle;    break;
563   case QwtSymbol::Rect:
564     ms = Plot2d_Curve::Rectangle; break;
565   case QwtSymbol::Diamond:
566     ms = Plot2d_Curve::Diamond;   break;
567   case QwtSymbol::DTriangle:
568     ms = Plot2d_Curve::DTriangle; break;
569   case QwtSymbol::UTriangle:
570     ms = Plot2d_Curve::UTriangle; break;
571   case QwtSymbol::RTriangle: // Qwt confuses LTriangle and RTriangle :(((
572     ms = Plot2d_Curve::LTriangle; break;
573   case QwtSymbol::LTriangle: // Qwt confuses LTriangle and RTriangle :(((
574     ms = Plot2d_Curve::RTriangle; break;
575   case QwtSymbol::Cross:
576     ms = Plot2d_Curve::Cross;     break;
577   case QwtSymbol::XCross:
578     ms = Plot2d_Curve::XCross;    break;
579   case QwtSymbol::None:
580   default:
581     ms = Plot2d_Curve::None;      break;
582   }
583   return ms;
584 }
585 /*!
586   Converts Plot2d_Curve's line style to Qwt line style [ static ]
587 */
588 static Qt::PenStyle plot2qwtLine( Plot2d_Curve::LineType p )
589 {
590   Qt::PenStyle ps = Qt::NoPen;
591   switch ( p ) {
592   case Plot2d_Curve::Solid:
593     ps = Qt::SolidLine;      break;
594   case Plot2d_Curve::Dash:
595     ps = Qt::DashLine;       break;
596   case Plot2d_Curve::Dot:
597     ps = Qt::DotLine;        break;
598   case Plot2d_Curve::DashDot:
599     ps = Qt::DashDotLine;    break;
600   case Plot2d_Curve::DashDotDot:
601     ps = Qt::DashDotDotLine; break;
602   case Plot2d_Curve::NoPen:
603   default:
604     ps = Qt::NoPen;          break;
605   }
606   return ps;
607 }
608 /*!
609   Converts Qwt line style to Plot2d_Curve's line style [ static ]
610 */
611 static Plot2d_Curve::LineType qwt2plotLine( Qt::PenStyle p )
612 {
613   Plot2d_Curve::LineType ps = Plot2d_Curve::NoPen;
614   switch ( p ) {
615   case Qt::SolidLine:
616     ps = Plot2d_Curve::Solid;      break;
617   case Qt::DashLine:
618     ps = Plot2d_Curve::Dash;       break;
619   case Qt::DotLine:
620     ps = Plot2d_Curve::Dot;        break;
621   case Qt::DashDotLine:
622     ps = Plot2d_Curve::DashDot;    break;
623   case Qt::DashDotDotLine:
624     ps = Plot2d_Curve::DashDotDot; break;
625   case Qt::NoPen:
626   default:
627     ps = Plot2d_Curve::NoPen;      break;
628   }
629   return ps;
630 }
631 /*!
632   Adds curve into view
633 */
634 void Plot2d_ViewFrame::displayCurve( Plot2d_Curve* curve, bool update )
635 {
636   if ( !curve )
637     return;
638   if ( hasCurve( curve ) ) {
639     updateCurve( curve, update );
640   }
641   else {
642     long curveKey = myPlot->insertCurve( curve->getVerTitle() );
643     myCurves.insert( curveKey, curve );
644     if ( curve->isAutoAssign() ) {
645       QwtSymbol::Style typeMarker;
646       QColor           color;
647       Qt::PenStyle     typeLine;
648       myPlot->getNextMarker( typeMarker, color, typeLine );
649       myPlot->setCurvePen( curveKey, QPen( color, DEFAULT_LINE_WIDTH, typeLine ) );
650       myPlot->setCurveSymbol( curveKey, QwtSymbol( typeMarker, 
651                                                    QBrush( color ), 
652                                                    QPen( color ), 
653                                                    QSize( myMarkerSize, myMarkerSize ) ) );
654       curve->setColor( color );
655       curve->setLine( qwt2plotLine( typeLine ) );
656       curve->setMarker( qwt2plotMarker( typeMarker ) );
657     }
658     else {
659       Qt::PenStyle     ps = plot2qwtLine( curve->getLine() );
660       QwtSymbol::Style ms = plot2qwtMarker( curve->getMarker() );
661       myPlot->setCurvePen( curveKey, QPen( curve->getColor(), curve->getLineWidth(), ps ) );
662       myPlot->setCurveSymbol( curveKey, QwtSymbol( ms, 
663                                                    QBrush( curve->getColor() ), 
664                                                    QPen( curve->getColor() ), 
665                                                    QSize( myMarkerSize, myMarkerSize ) ) );
666     }
667     if ( myCurveType == 0 )
668       myPlot->setCurveStyle( curveKey, QwtCurve::NoCurve );
669     else if ( myCurveType == 1 )
670       myPlot->setCurveStyle( curveKey, QwtCurve::Lines );
671     else if ( myCurveType == 2 )
672       myPlot->setCurveStyle( curveKey, QwtCurve::Spline );
673     myPlot->setCurveData( curveKey, curve->horData(), curve->verData(), curve->nbPoints() );
674   }
675   updateTitles();
676   if ( update )
677     myPlot->replot();
678 }
679 /*!
680   Adds curves into view
681 */
682 void Plot2d_ViewFrame::displayCurves( Plot2d_CurveContainer& curves, bool update )
683 {
684   myPlot->setUpdatesEnabled( false );
685   for ( int i = 0; i < curves.count(); i++ ) {
686     displayCurve( curves.curve( i ), false );
687   }
688 //  fitAll();
689   myPlot->setUpdatesEnabled( true );
690   if ( update )
691     myPlot->replot();
692 }
693 /*!
694   Erases curve
695 */
696 void Plot2d_ViewFrame::eraseCurve( Plot2d_Curve* curve, bool update )
697 {
698   if ( !curve )
699     return;
700   int curveKey = hasCurve( curve );
701   if ( curveKey ) {
702     myPlot->removeCurve( curveKey );
703     myCurves.remove( curveKey );
704     updateTitles();
705     if ( update )
706       myPlot->replot();
707   }
708 }
709 /*!
710   Erases curves
711 */
712 void Plot2d_ViewFrame::eraseCurves( Plot2d_CurveContainer& curves, bool update )
713 {
714   for ( int i = 0; i < curves.count(); i++ ) {
715     eraseCurve( curves.curve( i ), false );
716   }
717 //  fitAll();
718   if ( update )
719     myPlot->replot();
720 }
721 /*!
722   Updates curves attributes
723 */
724 void Plot2d_ViewFrame::updateCurve( Plot2d_Curve* curve, bool update )
725 {
726   if ( !curve )
727     return;
728   int curveKey = hasCurve( curve );
729   if ( curveKey ) {
730     if ( !curve->isAutoAssign() ) {
731       Qt::PenStyle     ps = plot2qwtLine( curve->getLine() );
732       QwtSymbol::Style ms = plot2qwtMarker( curve->getMarker() );
733       myPlot->setCurvePen( curveKey, QPen( curve->getColor(), curve->getLineWidth(), ps ) );
734       myPlot->setCurveSymbol( curveKey, QwtSymbol( ms, 
735                                                    QBrush( curve->getColor() ), 
736                                                    QPen( curve->getColor() ), 
737                                                    QSize( myMarkerSize, myMarkerSize ) ) );
738     }
739     myPlot->setCurveTitle( curveKey, curve->getVerTitle() );
740     myPlot->curve( curveKey )->setEnabled( true );
741     updateTitles();
742     if ( update )
743       myPlot->replot();
744   }
745 }
746 /*!
747   Returns curve key if is is displayed in the viewer and 0 otherwise
748 */
749 int Plot2d_ViewFrame::hasCurve( Plot2d_Curve* curve )
750 {
751   QIntDictIterator<Plot2d_Curve> it( myCurves );
752   for ( ; it.current(); ++it ) {
753     if ( it.current() == curve )
754       return it.currentKey();
755   }
756   return 0;
757 }
758 Plot2d_Curve* Plot2d_ViewFrame::getCurveByIO( const Handle(SALOME_InteractiveObject)& theIObject )
759 {
760   if ( !theIObject.IsNull() ) {
761     QIntDictIterator<Plot2d_Curve> it( myCurves );
762     for ( ; it.current(); ++it ) {
763       if ( it.current()->hasIO() && it.current()->getIO()->isSame( theIObject ) )
764         return it.current();
765     }
766   }
767   return 0;
768 }
769 /*!
770   Gets lsit of displayed curves
771 */
772 int Plot2d_ViewFrame::getCurves( QList<Plot2d_Curve>& clist )
773 {
774   clist.clear();
775   clist.setAutoDelete( false );
776   QIntDictIterator<Plot2d_Curve> it( myCurves );
777   for ( ; it.current(); ++it ) {
778     clist.append( it.current() );
779   }
780   return clist.count();
781 }
782
783 /*!
784   Updates titles according to curves
785 */
786 #define BRACKETIZE(x) QString( "[ " ) + x + QString( " ]" )
787 void Plot2d_ViewFrame::updateTitles() 
788 {
789   QAD_Study* activeStudy = QAD_Application::getDesktop()->getActiveStudy();
790   QIntDictIterator<Plot2d_Curve> it( myCurves );
791   QStringList aXTitles;
792   QStringList aYTitles;
793   QStringList aXUnits;
794   QStringList aYUnits;
795   QStringList aTables;
796   int i = 0;
797   while ( it.current() ) {
798     // collect titles and units from all curves...
799     QString xTitle = it.current()->getHorTitle().stripWhiteSpace();
800     QString yTitle = it.current()->getVerTitle().stripWhiteSpace();
801     QString xUnits = it.current()->getHorUnits().stripWhiteSpace();
802     QString yUnits = it.current()->getVerUnits().stripWhiteSpace();
803     
804     aYTitles.append( yTitle );
805     if ( aXTitles.find( xTitle ) == aXTitles.end() )
806       aXTitles.append( xTitle );
807     if ( aXUnits.find( xUnits ) == aXUnits.end() )
808       aXUnits.append( xUnits );
809     if ( aYUnits.find( yUnits ) == aYUnits.end() )
810       aYUnits.append( yUnits );
811
812     if ( activeStudy && it.current()->hasTableIO() ) { 
813       SALOMEDS::SObject_var SO = activeStudy->getStudyDocument()->FindObjectID( it.current()->getTableIO()->getEntry() );
814       if ( !SO->_is_nil() ) {
815         SALOMEDS::GenericAttribute_var anAttr;
816         if ( SO->FindAttribute( anAttr, "AttributeName" ) ) {
817           SALOMEDS::AttributeName_var aNameAttr = SALOMEDS::AttributeName::_narrow( anAttr );
818           QString aName = aNameAttr->Value();
819           if ( !aName.isEmpty() && aTables.find( aName ) == aTables.end() )
820             aTables.append( aName );
821         }
822       }
823     }
824
825     ++it;
826     ++i;
827   }
828   // ... and update plot 2d view
829   QString xUnits, yUnits;
830   if ( aXUnits.count() == 1 && !aXUnits[0].isEmpty() )
831     xUnits = BRACKETIZE( aXUnits[0] );
832   if ( aYUnits.count() == 1 && !aYUnits[0].isEmpty())
833     yUnits = BRACKETIZE( aYUnits[0] );
834   QString xTitle, yTitle;
835   if ( aXTitles.count() == 1 && aXUnits.count() == 1 )
836     xTitle = aXTitles[0];
837   if ( aYTitles.count() == 1 )
838     yTitle = aYTitles[0];
839
840   if ( !xTitle.isEmpty() && !xUnits.isEmpty() )
841     xTitle += " ";
842   if ( !yTitle.isEmpty() && !yUnits.isEmpty() )
843     yTitle += " ";
844
845   setXTitle( myXTitleEnabled, xTitle + xUnits );
846   setYTitle( myYTitleEnabled, yTitle + yUnits );
847   setTitle( aTables.join("; ") );
848 }
849 /*!
850   Fits the view to see all data
851 */
852 void Plot2d_ViewFrame::fitAll()
853 {
854   myPlot->setAxisAutoScale( QwtPlot::yLeft );
855   myPlot->setAxisAutoScale( QwtPlot::xBottom );
856   myPlot->replot();
857 }
858 /*!
859   Fits the view to rectangle area (pixels)
860 */
861 void Plot2d_ViewFrame::fitArea( const QRect& area )
862 {
863   QRect rect = area.normalize();
864   if ( rect.width() < MIN_RECT_SIZE ) {
865     rect.setWidth( MIN_RECT_SIZE );
866     rect.setLeft( rect.left() - MIN_RECT_SIZE/2 );
867   }
868   if ( rect.height() < MIN_RECT_SIZE ) {
869     rect.setHeight( MIN_RECT_SIZE );
870     rect.setTop( rect.top() - MIN_RECT_SIZE/2 );
871   }
872   myPlot->setAxisScale( QwtPlot::yLeft, 
873                         myPlot->invTransform( QwtPlot::yLeft, rect.top() ), 
874                         myPlot->invTransform( QwtPlot::yLeft, rect.bottom() ) );
875   myPlot->setAxisScale( QwtPlot::xBottom, 
876                         myPlot->invTransform( QwtPlot::xBottom, rect.left() ), 
877                         myPlot->invTransform( QwtPlot::xBottom, rect.right() ) );
878   myPlot->replot();
879 }
880 /*!
881   Tests if it is necessary to start operation on mouse action
882 */
883 int Plot2d_ViewFrame::testOperation( const QMouseEvent& me )
884 {
885   int btn = me.button() | me.state();
886   int zoomBtn = ControlButton | LeftButton;
887   int panBtn  = ControlButton | MidButton;
888   int fitBtn  = ControlButton | RightButton;
889
890   if ( btn == zoomBtn )
891     return ZoomId;
892   if ( btn == panBtn ) 
893     return PanId;
894   if ( btn == fitBtn )
895     return FitAreaId;
896   return NoOpId;
897 }
898 /*!
899   Mode toolbar buttons slot - horizontal axis (<Linear>/<Logarithmic>)
900 */
901 void Plot2d_ViewFrame::onHorMode()
902 {
903   if ( myActions[ ModeXLinearId ]->isOn() )
904     setHorScaleMode( 0 );
905   else if ( myActions[ ModeXLogarithmicId ]->isOn() )
906     setHorScaleMode( 1 );
907 }
908 /*!
909   Mode toolbar buttons slot - vertical axis (<Linear>/<Logarithmic>)
910 */
911 void Plot2d_ViewFrame::onVerMode()
912 {
913   if ( myActions[ ModeYLinearId ]->isOn() )
914     setVerScaleMode( 0 );
915   else if ( myActions[ ModeYLogarithmicId ]->isOn() )
916     setVerScaleMode( 1 );
917 }
918 /*!
919   "Show/hide legend" toolbar action slot
920 */
921 void Plot2d_ViewFrame::onLegend()
922 {
923   showLegend( myActions[ LegendId ]->isOn() );
924 }
925 /*!
926   "Curve type" toolbar action slot
927 */
928 void Plot2d_ViewFrame::onCurves()
929 {
930   if ( myActions[ CurvePointsId ]->isOn() )
931     setCurveType( 0 );
932   else if ( myActions[ CurveLinesId ]->isOn() )
933     setCurveType( 1 );
934   else if ( myActions[ CurveSplinesId ]->isOn() )
935     setCurveType( 2 );
936 }
937 /*!
938   "Settings" toolbar action slot
939 */
940 void Plot2d_ViewFrame::onSettings()
941 {
942 #ifdef TEST_AUTOASSIGN
943   typedef QMap<int,int> IList;
944   typedef QMap<QString,int> SList;
945   IList mars, lins;
946   SList cols;
947   cols[ "red-min" ]   = 1000;
948   cols[ "red-max" ]   = -1;
949   cols[ "green-min" ] = 1000;
950   cols[ "green-max" ] = -1;
951   cols[ "blue-min" ]  = 1000;
952   cols[ "blue-max" ]  = -1;
953   for ( unsigned i = 0; i < 10000; i++ ) {
954     QwtSymbol::Style typeMarker;
955     QColor           color;
956     Qt::PenStyle     typeLine;
957     myPlot->getNextMarker( typeMarker, color, typeLine );
958     if ( mars.contains(typeMarker) )
959       mars[ typeMarker ] = mars[ typeMarker ]+1;
960     else
961       mars[ typeMarker ] = 0;
962     if ( lins.contains(typeLine) )
963       lins[ typeLine ] = lins[ typeLine ]+1;
964     else
965       lins[ typeLine ] = 0;
966     if ( cols[ "red-max" ] < color.red() )
967       cols[ "red-max" ] = color.red();
968     if ( cols[ "red-min" ] > color.red() )
969       cols[ "red-min" ] = color.red();
970     if ( cols[ "green-max" ] < color.green() )
971       cols[ "green-max" ] = color.green();
972     if ( cols[ "green-min" ] > color.green() )
973       cols[ "green-min" ] = color.green();
974     if ( cols[ "blue-max" ] < color.blue() )
975       cols[ "blue-max" ] = color.blue();
976     if ( cols[ "blue-min" ] > color.blue() )
977       cols[ "blue-min" ] = color.blue();
978   }
979   for (IList::Iterator it = mars.begin();  it != mars.end(); ++it)
980     MESSAGE("markers( " << it.key() << ") = " << it.data() );
981   for (IList::Iterator it = lins.begin();  it != lins.end(); ++it)
982     MESSAGE("lines( " << it.key() << ") = " << it.data() );
983   for (SList::Iterator it = cols.begin();  it != cols.end(); ++it)
984     MESSAGE("colors( " << it.key() << ") = " << it.data() );
985 #endif
986   
987   Plot2d_SetupViewDlg* dlg = new Plot2d_SetupViewDlg( this, true );
988   dlg->setMainTitle( myTitleEnabled, myTitle );
989   dlg->setXTitle( myXTitleEnabled, myXTitle );
990   dlg->setYTitle( myYTitleEnabled, myYTitle );
991   dlg->setCurveType( myCurveType );
992   dlg->setLegend( myShowLegend, myLegendPos );
993   dlg->setMarkerSize( myMarkerSize );
994   dlg->setBackgroundColor( myBackground );
995   dlg->setMajorGrid( myXGridMajorEnabled, myPlot->axisMaxMajor( QwtPlot::xBottom ),
996                      myYGridMajorEnabled, myPlot->axisMaxMajor( QwtPlot::yLeft ) );
997   dlg->setMinorGrid( myXGridMinorEnabled, myPlot->axisMaxMinor( QwtPlot::xBottom ),
998                      myYGridMinorEnabled, myPlot->axisMaxMinor( QwtPlot::yLeft ) );
999   dlg->setScaleMode( myXMode, myYMode );
1000
1001   if ( dlg->exec() == QDialog::Accepted ) {
1002     // horizontal axis title
1003     setXTitle( dlg->isXTitleEnabled(), dlg->getXTitle(), false );
1004     // vertical axis title
1005     setYTitle( dlg->isYTitleEnabled(), dlg->getYTitle(), false );
1006     // main title
1007     setMainTitle( dlg->isMainTitleEnabled(), dlg->getMainTitle(), true );
1008     // curve type
1009     if ( myCurveType != dlg->getCurveType() ) {
1010       setCurveType( dlg->getCurveType(), false );
1011     }
1012     // legend
1013     if ( myShowLegend != dlg->isLegendEnabled() ) {
1014       showLegend( dlg->isLegendEnabled(), false );
1015     }
1016     if ( myLegendPos != dlg->getLegendPos() ) {
1017       setLegendPos( dlg->getLegendPos() );
1018     }
1019     // marker size
1020     if ( myMarkerSize != dlg->getMarkerSize() ) {
1021       setMarkerSize( dlg->getMarkerSize(), false );
1022     }
1023     // background color
1024     if ( myBackground != dlg->getBackgroundColor() ) {
1025       setBackgroundColor( dlg->getBackgroundColor() );
1026     }
1027     // grid
1028     bool aXGridMajorEnabled, aXGridMinorEnabled, aYGridMajorEnabled, aYGridMinorEnabled;
1029     int  aXGridMaxMajor,     aXGridMaxMinor,     aYGridMaxMajor,     aYGridMaxMinor;
1030     dlg->getMajorGrid( aXGridMajorEnabled, aXGridMaxMajor, aYGridMajorEnabled, aYGridMaxMajor );
1031     dlg->getMinorGrid( aXGridMinorEnabled, aXGridMaxMinor, aYGridMinorEnabled, aYGridMaxMinor );
1032     setXGrid( aXGridMajorEnabled, aXGridMaxMajor, aXGridMinorEnabled, aXGridMaxMinor, false );
1033     setYGrid( aYGridMajorEnabled, aYGridMaxMajor, aYGridMinorEnabled, aYGridMaxMinor, false );
1034     // scale mode
1035     if ( myXMode != dlg->getXScaleMode() ) {
1036       setHorScaleMode( dlg->getXScaleMode() );
1037     }
1038     if ( myYMode != dlg->getYScaleMode() ) {
1039       setVerScaleMode( dlg->getYScaleMode() );
1040     }
1041     // update view
1042     myPlot->replot();
1043     // update preferences
1044     if ( dlg->isSetAsDefault() ) 
1045       writePreferences();
1046   }
1047   delete dlg;
1048 }
1049 /*!
1050   "Fit Data" command slot
1051 */
1052 void Plot2d_ViewFrame::onFitData()
1053 {
1054   Plot2d_FitDataDlg* dlg = new Plot2d_FitDataDlg( this );
1055   int ixMin = myPlot->canvasMap( QwtPlot::xBottom ).i1();
1056   int ixMax = myPlot->canvasMap( QwtPlot::xBottom ).i2();
1057   int iyMin = myPlot->canvasMap( QwtPlot::yLeft ).i1();
1058   int iyMax = myPlot->canvasMap( QwtPlot::yLeft ).i2();
1059   double xMin = myPlot->invTransform(QwtPlot::xBottom, ixMin);
1060   double xMax = myPlot->invTransform(QwtPlot::xBottom, ixMax);
1061   double yMin = myPlot->invTransform(QwtPlot::yLeft, iyMin);
1062   double yMax = myPlot->invTransform(QwtPlot::yLeft, iyMax);
1063   
1064   dlg->setRange( xMin, xMax, yMin, yMax );
1065   if ( dlg->exec() == QDialog::Accepted ) {
1066     int mode = dlg->getRange( xMin, xMax, yMin, yMax );
1067     if ( mode == 0 || mode == 2 ) 
1068       myPlot->setAxisScale( QwtPlot::yLeft, yMax, yMin );
1069     if ( mode == 0 || mode == 1 ) 
1070       myPlot->setAxisScale( QwtPlot::xBottom, xMin, xMax ); 
1071     myPlot->replot();
1072   }
1073   delete dlg;
1074 }
1075 /*!
1076   Sets curve type
1077 */
1078 void Plot2d_ViewFrame::setCurveType( int curveType, bool update )
1079 {
1080   myCurveType = curveType;
1081   if ( curveType == 0 )
1082     myActions[ CurvePointsId ]->setOn( true );
1083   else if ( curveType == 1 )
1084     myActions[ CurveLinesId ]->setOn( true );
1085   else if ( curveType == 2 )
1086     myActions[ CurveSplinesId ]->setOn( true );
1087   
1088   QArray<long> keys = myPlot->curveKeys();
1089   for ( int i = 0; i < keys.count(); i++ ) {
1090     if ( myCurveType == 0 )
1091       myPlot->setCurveStyle( keys[i], QwtCurve::NoCurve );
1092     else if ( myCurveType == 1 )
1093       myPlot->setCurveStyle( keys[i], QwtCurve::Lines );
1094     else if ( myCurveType == 2 )
1095       myPlot->setCurveStyle( keys[i], QwtCurve::Spline );
1096   }
1097   if ( update )
1098     myPlot->replot();
1099 }
1100 /*!
1101   Shows/hides legend
1102 */
1103 void Plot2d_ViewFrame::showLegend( bool show, bool update )
1104 {
1105   myShowLegend = show;
1106   myActions[ LegendId ]->setOn( myShowLegend );
1107   {
1108     myPlot->setAutoLegend( myShowLegend );
1109     myPlot->enableLegend( myShowLegend );
1110   }
1111   if ( update )
1112     myPlot->replot();
1113 }
1114 /*!
1115   Sets legend position : 0 - left, 1 - right, 2 - top, 3 - bottom
1116 */
1117 void Plot2d_ViewFrame::setLegendPos( int pos )
1118 {
1119   myLegendPos = pos;
1120   switch( pos ) {
1121   case 0:
1122     myPlot->setLegendPos( Qwt::Left );
1123     break;
1124   case 1:
1125     myPlot->setLegendPos( Qwt::Right );
1126     break;
1127   case 2:
1128     myPlot->setLegendPos( Qwt::Top );
1129     break;
1130   case 3:
1131     myPlot->setLegendPos( Qwt::Bottom );
1132     break;
1133   }
1134 }
1135 /*!
1136   Sets new marker size
1137 */
1138 void Plot2d_ViewFrame::setMarkerSize( const int size, bool update )
1139 {
1140   if ( myMarkerSize != size ) {
1141     myMarkerSize = size;
1142     QArray<long> keys = myPlot->curveKeys();
1143     for ( int i = 0; i < keys.count(); i++ ) {
1144       QwtPlotCurve* crv = myPlot->curve( keys[i] );
1145       if ( crv ) {
1146         QwtSymbol aSymbol = crv->symbol();
1147         aSymbol.setSize( myMarkerSize, myMarkerSize );
1148         crv->setSymbol( aSymbol );
1149         int legendIndex = myPlot->getLegend()->findFirstKey( keys[i] );
1150         if ( legendIndex != myPlot->getLegend()->itemCnt() )
1151           myPlot->getLegend()->setSymbol( legendIndex, aSymbol );
1152       }
1153     }
1154     if ( update )
1155       myPlot->replot();
1156   }
1157 }
1158 /*!
1159   Sets background color
1160 */
1161 void Plot2d_ViewFrame::setBackgroundColor( const QColor& color )
1162 {
1163   myBackground = color;
1164   //myPlot->setCanvasBackground( myBackground );
1165   myPlot->canvas()->setPalette( myBackground );
1166   myPlot->setPalette( myBackground );
1167   QPalette aPal = myPlot->getLegend()->palette();
1168   for ( int i = 0; i < QPalette::NColorGroups; i++ ) {
1169     QPalette::ColorGroup cg = (QPalette::ColorGroup)i;
1170     aPal.setColor( cg, QColorGroup::Base, myBackground );
1171     aPal.setColor( cg, QColorGroup::Background, myBackground );
1172   }
1173   myPlot->getLegend()->setPalette( aPal );
1174 }
1175 /*!
1176   Gets background color
1177 */
1178 QColor Plot2d_ViewFrame::backgroundColor() const
1179 {
1180   return myBackground;
1181 }
1182 /*!
1183   Sets hor.axis grid parameters
1184 */
1185 void Plot2d_ViewFrame::setXGrid( bool xMajorEnabled, const int xMajorMax, 
1186                                  bool xMinorEnabled, const int xMinorMax, 
1187                                  bool update )
1188 {
1189   myXGridMajorEnabled = xMajorEnabled;
1190   myXGridMinorEnabled = xMinorEnabled;
1191   myXGridMaxMajor = xMajorMax;
1192   myXGridMaxMinor = xMinorMax;
1193   myPlot->setAxisMaxMajor( QwtPlot::xBottom, myXGridMaxMajor );
1194   myPlot->setAxisMaxMinor( QwtPlot::xBottom, myXGridMaxMinor );
1195   myPlot->enableGridX( myXGridMajorEnabled );
1196   myPlot->enableGridXMin( myXGridMinorEnabled );
1197   if ( update )
1198     myPlot->replot();
1199 }
1200 /*!
1201   Sets ver.axis grid parameters
1202 */
1203 void Plot2d_ViewFrame::setYGrid( bool yMajorEnabled, const int yMajorMax, 
1204                                  bool yMinorEnabled, const int yMinorMax, 
1205                                  bool update )
1206 {
1207   myYGridMajorEnabled = yMajorEnabled;
1208   myYGridMinorEnabled = yMinorEnabled;
1209   myYGridMaxMajor = yMajorMax;
1210   myYGridMaxMinor = yMinorMax;
1211   myPlot->setAxisMaxMajor( QwtPlot::yLeft, myYGridMaxMajor );
1212   myPlot->setAxisMaxMinor( QwtPlot::yLeft, myYGridMaxMinor );
1213   myPlot->enableGridY( myYGridMajorEnabled );
1214   myPlot->enableGridYMin( myYGridMinorEnabled );
1215   if ( update )
1216     myPlot->replot();
1217 }
1218 /*!
1219   Sets main title
1220 */
1221 void Plot2d_ViewFrame::setMainTitle( bool enabled, const QString& title, bool update )
1222 {
1223   myTitleEnabled = enabled;
1224   myTitle = title;
1225   myPlot->setTitle( myTitleEnabled ? myTitle : QString::null );
1226   if ( update )
1227     myPlot->replot();
1228 }
1229 /*!
1230   Sets hor.axis title
1231 */
1232 void Plot2d_ViewFrame::setXTitle( bool enabled, const QString& title, bool update )
1233 {
1234   myXTitleEnabled = enabled;
1235   myXTitle = title;
1236   myPlot->setAxisTitle( QwtPlot::xBottom, myXTitleEnabled ? myXTitle : QString::null );
1237   if ( update )
1238     myPlot->replot();
1239 }
1240 /*!
1241   Sets ver.axis title
1242 */
1243 void Plot2d_ViewFrame::setYTitle( bool enabled, const QString& title, bool update )
1244 {
1245   myYTitleEnabled = enabled;
1246   myYTitle = title;
1247   myPlot->setAxisTitle( QwtPlot::yLeft, myYTitleEnabled ? myYTitle : QString::null );
1248   if ( update )
1249     myPlot->replot();
1250 }
1251 /*!
1252   Sets scale mode for horizontal axis: 0 - linear, 1 - logarithmic
1253 */
1254 void Plot2d_ViewFrame::setHorScaleMode( const int mode, bool update )
1255 {
1256   myXMode = mode;
1257   if ( myXMode == 0 ) { // linear
1258     myActions[ ModeXLogarithmicId ]->setOn( false );
1259     myActions[ ModeXLinearId ]->setOn( true );
1260     myPlot->changeAxisOptions( QwtPlot::xBottom, QwtAutoScale::Logarithmic, false );
1261   }
1262   else {               // logarithmic
1263     myActions[ ModeXLinearId ]->setOn( false );
1264     myActions[ ModeXLogarithmicId ]->setOn( true );
1265     myPlot->changeAxisOptions( QwtPlot::xBottom, QwtAutoScale::Logarithmic, true );
1266   }
1267   if ( update )
1268 //    myPlot->replot();
1269     fitAll();
1270 }
1271 /*!
1272   Sets scale mode for vertical axis: 0 - linear, 1 - logarithmic
1273 */
1274 void Plot2d_ViewFrame::setVerScaleMode( const int mode, bool update )
1275 {
1276   myYMode = mode;
1277   if ( myYMode == 0 ) { // linear
1278     myActions[ ModeYLogarithmicId ]->setOn( false );
1279     myActions[ ModeYLinearId ]->setOn( true );
1280     myPlot->changeAxisOptions( QwtPlot::yLeft, QwtAutoScale::Logarithmic, false );
1281   }
1282   else {               // logarithmic
1283     myActions[ ModeYLinearId ]->setOn( false );
1284     myActions[ ModeYLogarithmicId ]->setOn( true );
1285     myPlot->changeAxisOptions( QwtPlot::yLeft, QwtAutoScale::Logarithmic, true );
1286   }
1287   if ( update )
1288 //    myPlot->replot();
1289     fitAll();
1290 }
1291 /*!
1292   Slot, called when Legend item is clicked
1293 */
1294 void Plot2d_ViewFrame::onLegendClicked( long key )
1295 {
1296   Plot2d_Curve* curve = myCurves[ key ];
1297   if ( curve && curve->hasIO() ) {
1298     SALOME_Selection* Sel = SALOME_Selection::Selection( QAD_Application::getDesktop()->getActiveStudy()->getSelection() );
1299     Sel->ClearIObjects();
1300     Sel->AddIObject( curve->getIO(), true );
1301   }
1302 }
1303
1304 /*!
1305   Slot, called when user presses mouse button
1306 */
1307 void Plot2d_ViewFrame::plotMousePressed( const QMouseEvent& me )
1308 {
1309   if ( myOperation == NoOpId )
1310     myOperation = testOperation( me );
1311   if ( myOperation != NoOpId ) {
1312     myPnt = me.pos();
1313     if ( myOperation == ZoomId ) {
1314       myPlot->canvas()->setCursor( QCursor( QPixmap( imageZoomCursor ) ) );
1315     }
1316     else if ( myOperation == PanId ) {
1317       myPlot->canvas()->setCursor( QCursor( Qt::SizeAllCursor ) );
1318     }
1319     else if ( myOperation == FitAreaId ) {
1320       myPlot->canvas()->setCursor( QCursor( Qt::PointingHandCursor ) );
1321       myPlot->setOutlineStyle( Qwt::Rect );
1322     }
1323   }
1324   else {
1325     int btn = me.button() | me.state();
1326     if ( btn == RightButton ) {
1327       createPopup();
1328       if ( myPopup ) {
1329         QAD_Tools::checkPopup( myPopup );
1330         if ( myPopup->count()>0 ) {
1331           myPopup->exec( QCursor::pos() );
1332         }
1333         destroyPopup();
1334       }
1335     }
1336     else {
1337       myPlot->setOutlineStyle( Qwt::Cross );
1338       QAD_Application::getDesktop()->putInfo( getInfo( me.pos() ) );
1339     }
1340   }
1341 }
1342 /*!
1343   Slot, called when user moves mouse
1344 */
1345 void Plot2d_ViewFrame::plotMouseMoved( const QMouseEvent& me )
1346 {
1347   int    dx = me.pos().x() - myPnt.x();
1348   int    dy = me.pos().y() - myPnt.y();
1349
1350   if ( myOperation != NoOpId) {
1351     if ( myOperation == ZoomId ) {
1352       QwtDiMap xMap = myPlot->canvasMap( QwtPlot::xBottom );
1353       QwtDiMap yMap = myPlot->canvasMap( QwtPlot::yLeft );
1354
1355       myPlot->setAxisScale( QwtPlot::yLeft, 
1356                             myPlot->invTransform( QwtPlot::yLeft, yMap.i1() ), 
1357                             myPlot->invTransform( QwtPlot::yLeft, yMap.i2() + dy ) );
1358       myPlot->setAxisScale( QwtPlot::xBottom, 
1359                             myPlot->invTransform( QwtPlot::xBottom, xMap.i1() ), 
1360                             myPlot->invTransform( QwtPlot::xBottom, xMap.i2() - dx ) );
1361       myPlot->replot();
1362       myPnt = me.pos();
1363     }
1364     else if ( myOperation == PanId ) {
1365       QwtDiMap xMap = myPlot->canvasMap( QwtPlot::xBottom );
1366       QwtDiMap yMap = myPlot->canvasMap( QwtPlot::yLeft );
1367       
1368       myPlot->setAxisScale( QwtPlot::yLeft, 
1369                             myPlot->invTransform( QwtPlot::yLeft, yMap.i1()-dy ), 
1370                             myPlot->invTransform( QwtPlot::yLeft, yMap.i2()-dy ) );
1371       myPlot->setAxisScale( QwtPlot::xBottom, 
1372                             myPlot->invTransform( QwtPlot::xBottom, xMap.i1()-dx ),
1373                             myPlot->invTransform( QwtPlot::xBottom, xMap.i2()-dx ) ); 
1374       myPlot->replot();
1375       myPnt = me.pos();
1376     }
1377   }
1378   else {
1379     QAD_Application::getDesktop()->putInfo( getInfo( me.pos() ) );
1380   }
1381 }
1382 /*!
1383   Slot, called when user releases mouse
1384 */
1385 void Plot2d_ViewFrame::plotMouseReleased( const QMouseEvent& me )
1386 {
1387   if ( myOperation == FitAreaId ) {
1388     QRect rect( myPnt, me.pos() );
1389     fitArea( rect );
1390   }
1391   myPlot->canvas()->setCursor( QCursor( Qt::CrossCursor ) );
1392   myPlot->setOutlineStyle( Qwt::Triangle );
1393   QAD_Application::getDesktop()->putInfo( tr( "INF_READY" ) );
1394   myOperation = NoOpId;
1395 }
1396 /*!
1397   View operations : Pan view
1398 */
1399 void Plot2d_ViewFrame::onViewPan() 
1400
1401   myOperation = PanId;
1402   qApp->installEventFilter( this );
1403 }
1404 /*!
1405   View operations : Zoom view
1406 */
1407 void Plot2d_ViewFrame::onViewZoom() 
1408 {
1409   myOperation = ZoomId;
1410   qApp->installEventFilter( this );
1411 }
1412 /*!
1413   View operations : Fot All
1414 */
1415 void Plot2d_ViewFrame::onViewFitAll() 
1416
1417   fitAll();
1418 }
1419 /*!
1420   View operations : Fit Area
1421 */
1422 void Plot2d_ViewFrame::onViewFitArea() 
1423 {
1424   myOperation = FitAreaId;
1425   qApp->installEventFilter( this );
1426 }
1427 /*!
1428   View operations : Global panning
1429 */
1430 void Plot2d_ViewFrame::onViewGlobalPan() 
1431 { MESSAGE( "Plot2d_ViewFrame::onViewGlobalPan : NOT SUPPORTED" ); }
1432 /*!
1433   View operations : Rotate view
1434 */
1435 void Plot2d_ViewFrame::onViewRotate() 
1436 { MESSAGE( "Plot2d_ViewFrame::onViewRotate : NOT SUPPORTED" ); }
1437 /*!
1438   View operations : Reset view
1439 */
1440 void Plot2d_ViewFrame::onViewReset() 
1441 { MESSAGE( "Plot2d_ViewFrame::onViewReset : NOT SUPPORTED" ); }
1442 /*!
1443   View operations : View front
1444 */
1445 void Plot2d_ViewFrame::onViewFront() 
1446 { MESSAGE( "Plot2d_ViewFrame::onViewFront : NOT SUPPORTED" ); }
1447 /*!
1448   View operations : View back
1449 */
1450 void Plot2d_ViewFrame::onViewBack() 
1451 { MESSAGE( "Plot2d_ViewFrame::onViewBack : NOT SUPPORTED" ); }
1452 /*!
1453   View operations : View right
1454 */
1455 void Plot2d_ViewFrame::onViewRight() 
1456 { MESSAGE( "Plot2d_ViewFrame::onViewRight : NOT SUPPORTED" ); }
1457 /*!
1458   View operations : View left
1459 */
1460 void Plot2d_ViewFrame::onViewLeft() 
1461 { MESSAGE( "Plot2d_ViewFrame::onViewLeft : NOT SUPPORTED" ); }
1462 /*!
1463   View operations : View bottom
1464 */
1465 void Plot2d_ViewFrame::onViewBottom() 
1466 { MESSAGE( "Plot2d_ViewFrame::onViewBottom : NOT SUPPORTED" ); }
1467 /*!
1468   View operations : View top
1469 */
1470 void Plot2d_ViewFrame::onViewTop() 
1471 { MESSAGE( "Plot2d_ViewFrame::onViewTop : NOT SUPPORTED" ); }
1472 /*!
1473   View operations : Show/hide trihedron
1474 */
1475 void Plot2d_ViewFrame::onViewTrihedron() 
1476 { MESSAGE( "Plot2d_ViewFrame::onViewTrihedron : NOT SUPPORTED" ); }
1477
1478
1479 //=================================================================================
1480 // Plot2d_Plot2d implementation
1481 //=================================================================================
1482
1483 /*!
1484   Constructor
1485 */
1486 Plot2d_Plot2d::Plot2d_Plot2d( QWidget* parent )
1487      : QwtPlot( parent )
1488 {
1489   // outline
1490   enableOutline( true );
1491   setOutlineStyle( Qwt::Triangle );
1492   setOutlinePen( green );
1493   // legend
1494   setAutoLegend( false );
1495   setLegendFrameStyle( QFrame::Box | QFrame::Sunken );
1496   enableLegend( false );
1497   // grid
1498   enableGridX( false );
1499   enableGridXMin( false );
1500   enableGridY( false );
1501   enableGridYMin( false );
1502   // auto scaling by default
1503   setAxisAutoScale( QwtPlot::yLeft );
1504   setAxisAutoScale( QwtPlot::xBottom );
1505 }
1506 /*!
1507   Recalculates and redraws Plot 2d view 
1508 */
1509 void Plot2d_Plot2d::replot()
1510 {
1511   updateLayout();  // to fix bug(?) of Qwt - view is not updated when title is changed
1512   QwtPlot::replot(); 
1513 }
1514 /*!
1515   Checks if two colors are close to each other [ static ]
1516   uses COLOR_DISTANCE variable as max tolerance for comparing of colors
1517 */
1518 const long COLOR_DISTANCE = 100;
1519 const int  MAX_ATTEMPTS   = 10;
1520 static bool closeColors( const QColor& color1, const QColor& color2 )
1521 {
1522   long tol = abs( color2.red()   - color1.red() ) + 
1523              abs( color2.green() - color1.green() ) +
1524              abs( color2.blue()  - color1.blue() );
1525
1526   return ( tol <= COLOR_DISTANCE );
1527 }
1528 /*!
1529   Gets new unique marker for item if possible
1530 */
1531 void Plot2d_Plot2d::getNextMarker( QwtSymbol::Style& typeMarker, QColor& color, Qt::PenStyle& typeLine ) 
1532 {
1533   bool bOk = false;
1534   int cnt = 1;
1535   while ( !bOk ) {
1536     int aRed    = (int)( 256.0 * random() / RAND_MAX);    // generate random color
1537     int aGreen  = (int)( 256.0 * random() / RAND_MAX);    // ...
1538     int aBlue   = (int)( 256.0 * random() / RAND_MAX);    // ...
1539     int aMarker = (int)( 9.0 * random() / RAND_MAX) + 1;  // 9 markers types ( not including empty )
1540     int aLine   = (int)( 5.0 * random() / RAND_MAX) + 1;  // 5 line types ( not including empty )
1541
1542     typeMarker = ( QwtSymbol::Style )aMarker;
1543     color      = QColor( aRed, aGreen, aBlue );
1544     typeLine   = ( Qt::PenStyle )aLine;
1545
1546     cnt++;
1547     if ( cnt == MAX_ATTEMPTS )
1548       bOk = true;
1549     else
1550       bOk = !existMarker( typeMarker, color, typeLine );
1551   }
1552 /*
1553   static int aMarker = -1;
1554   static int aColor  = -1;
1555   static int aLine   = -1;
1556
1557   if ( myColors.isEmpty() ) {
1558     // creating colors list
1559     myColors.append( Qt::white );
1560     myColors.append( Qt::blue );
1561     myColors.append( Qt::gray );
1562     myColors.append( Qt::darkGreen );
1563     myColors.append( Qt::magenta );
1564     myColors.append( Qt::darkGray );
1565     myColors.append( Qt::red );
1566     myColors.append( Qt::darkBlue );
1567     myColors.append( Qt::darkYellow );
1568     myColors.append( Qt::cyan );
1569     myColors.append( Qt::darkRed );
1570     myColors.append( Qt::darkCyan );
1571     myColors.append( Qt::yellow );
1572     myColors.append( Qt::darkMagenta );
1573     myColors.append( Qt::green );
1574     myColors.append( Qt::black );
1575   }
1576
1577   int nbMarkers = 11;                   // QwtSymbol supports 11 marker types
1578   int nbLines   = 6;                    // Qt supports 6 line types
1579   int nbColors  = myColors.count();     // number of default colors supported
1580
1581   aMarker = ( aMarker + 1 ) % nbMarkers;  
1582   if ( aMarker == QwtSymbol::None || aMarker == QwtSymbol::Triangle ) aMarker++;
1583   aColor  = ( aColor  + 1 ) % nbColors;
1584   aLine   = ( aLine   + 1 ) % nbLines;    
1585   if ( aLine == Qt::NoPen ) aLine++;             
1586
1587   typeMarker = ( QwtSymbol::Style )aMarker;
1588   color      = myColors[ aColor ];
1589   typeLine   = ( Qt::PenStyle )aLine;
1590   if ( !existMarker( typeMarker, color, typeLine ) )
1591     return;
1592
1593   int i, j, k;
1594   for ( i = 0; i < nbMarkers; i++ ) {
1595     aMarker = ( aMarker + 1 ) % nbMarkers;
1596     if ( aMarker == QwtSymbol::None || aMarker == QwtSymbol::Triangle ) aMarker++;
1597     for ( j = 0; j < nbColors; j++ ) {
1598       aColor  = ( aColor  + 1 ) % nbColors;
1599       for ( k = 0; k < nbLines; k++ ) {
1600         aLine = ( aLine + 1 ) % nbLines;
1601         if ( aLine == Qt::NoPen ) aLine++;             
1602         if ( !existMarker( ( QwtSymbol::Style )aMarker, aColor, ( Qt::PenStyle )aLine ) ) {
1603           typeMarker = ( QwtSymbol::Style )aMarker;
1604           color      = myColors[ aColor ];
1605           typeLine   = ( Qt::PenStyle )aLine;
1606           return;
1607         }
1608       }
1609     }
1610   }
1611 */
1612 }
1613 /*!
1614   Checks if marker belongs to any enitity
1615 */
1616 bool Plot2d_Plot2d::existMarker( const QwtSymbol::Style typeMarker, const QColor& color, const Qt::PenStyle typeLine ) 
1617 {
1618   // getting all curves
1619   QArray<long> keys = curveKeys();
1620   QColor aRgbColor;
1621
1622   if ( closeColors( color, backgroundColor() ) )
1623       return true;
1624   for ( int i = 0; i < keys.count(); i++ ) {
1625     QwtPlotCurve* crv = curve( keys[i] );
1626     if ( crv ) {
1627       QwtSymbol::Style aStyle = crv->symbol().style();
1628       QColor           aColor = crv->pen().color();
1629       Qt::PenStyle     aLine  = crv->pen().style();
1630 //      if ( aStyle == typeMarker && aColor == color && aLine == typeLine )
1631       if ( aStyle == typeMarker && closeColors( aColor,color ) && aLine == typeLine )
1632         return true;
1633     }
1634   }
1635   return false;
1636 }