Salome HOME
It removes AIS curve presentation.
[modules/hydro.git] / src / HYDROCurveCreator / CurveCreator_Widget.cxx
1 // Copyright (C) 2013  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License.
7 //
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11 // Lesser General Public License for more details.
12 //
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19
20 #include "CurveCreator_Widget.h"
21 #include "CurveCreator_TreeView.h"
22 #include "CurveCreator_ICurve.hxx"
23 //#include "CurveCreator_CurveEditor.hxx"
24 #include "CurveCreator.hxx"
25 //#include "CurveCreator_NewPointDlg.h"
26 #include "CurveCreator_NewSectionDlg.h"
27 #include "CurveCreator_Utils.h"
28 #include "CurveCreator_UtilsICurve.hxx"
29 #include "CurveCreator_TableView.h"
30
31 #include <SUIT_Session.h>
32 #include <SUIT_Desktop.h>
33 #include <SUIT_ResourceMgr.h>
34 #include <SUIT_ViewManager.h>
35
36 #include <OCCViewer_ViewWindow.h>
37 #include <OCCViewer_ViewManager.h>
38 #include <OCCViewer_ViewPort3d.h>
39 #include "OCCViewer_Utilities.h"
40
41 #include <BRep_Tool.hxx>
42 #include <TopoDS.hxx>
43 #include <TopoDS_Vertex.hxx>
44 #include <TopoDS_Wire.hxx>
45 #include <TopoDS_Edge.hxx>
46 #include <gp_Lin.hxx>
47 #include <gp_Dir.hxx>
48 #include <TopExp_Explorer.hxx>
49
50 #include <GeomAPI_ProjectPointOnCurve.hxx>
51
52 #include <AIS_ListOfInteractive.hxx>
53 #include <AIS_ListIteratorOfListOfInteractive.hxx>
54 #include <AIS_Shape.hxx>
55 #include <AIS_LocalContext.hxx>
56 #include <Geom_Point.hxx>
57 #include <Geom_BSplineCurve.hxx>
58 #include <Geom_Line.hxx>
59 #include <StdSelect_BRepOwner.hxx>
60 #include <SelectMgr_Selection.hxx>
61 #include <Select3D_SensitivePoint.hxx>
62
63 #include <QHBoxLayout>
64 #include <QVBoxLayout>
65 #include <QLabel>
66 #include <QLineEdit>
67 #include <QGroupBox>
68 #include <QToolButton>
69 #include <QToolBar>
70 #include <QAction>
71 #include <QMenu>
72 #include <QMouseEvent>
73 #include <QApplication>
74 #include <QTableWidget>
75 #include <QTime>
76
77 #define MEASURE_TIME
78
79 #ifdef MEASURE_TIME
80
81   #define START_MEASURE_TIME \
82     QTime aTimer;            \
83     aTimer.start();          \
84
85   #define END_MEASURE_TIME( theMsg )                      \
86     double aTime = aTimer.elapsed() * 0.001;              \
87     FILE* aFile = fopen( "performance", "a" );            \
88     fprintf( aFile, "%s = %.3lf sec\n", theMsg, aTime );  \
89     fclose( aFile );                                      \
90
91 #else
92
93   #define START_MEASURE_TIME
94   #define END_MEASURE_TIME( theMsg )
95
96 #endif
97
98
99
100
101
102
103 const double LOCAL_SELECTION_TOLERANCE = 0.0001;
104
105 CurveCreator_Widget::CurveCreator_Widget(QWidget* parent,
106                                          CurveCreator_ICurve *theCurve,
107                                          Qt::WindowFlags fl,
108                                          int theLocalPointRowLimit )
109 : QWidget(parent), myNewSectionEditor(NULL), myCurve(theCurve), mySection(0),
110   myDragStarted( false ), myDragInteractionStyle( SUIT_ViewModel::STANDARD ),
111   myOCCViewer( 0 ), myLocalPointRowLimit( theLocalPointRowLimit )
112 {
113   myNewSectionEditor = new CurveCreator_NewSectionDlg( this );
114   myNewSectionEditor->hide();
115   connect( myNewSectionEditor, SIGNAL(addSection()), this, SLOT(onAddNewSection()) );
116   connect( myNewSectionEditor, SIGNAL(modifySection()), this, SLOT(onModifySection()) );
117   connect( myNewSectionEditor, SIGNAL(cancelSection()), this, SLOT(onCancelSection()) );
118
119   QGroupBox* aSectionGroup = new QGroupBox(tr("Sections"),this);
120
121   mySectionView = new CurveCreator_TreeView(myCurve, aSectionGroup);
122   connect( mySectionView, SIGNAL(selectionChanged()), this, SLOT( onSelectionChanged() ) );
123   connect( mySectionView, SIGNAL(sectionEntered(int)), this, SLOT(onEditSection(int)) );
124   connect( mySectionView, SIGNAL(customContextMenuRequested(QPoint)), this, SLOT(onContextMenu(QPoint)) );
125
126   myLocalPointView = new CurveCreator_TableView( myCurve, this );
127   connect( myLocalPointView, SIGNAL( cellChanged( int, int ) ),
128            this, SLOT( onCellChanged( int, int ) ) );
129
130   QToolBar* aTB = new QToolBar(tr("TOOL_BAR_TLT"), aSectionGroup);
131 //    QToolButton* anUndoBtn = new QToolButton(aTB);
132
133   SUIT_ResourceMgr* aResMgr = SUIT_Session::session()->resourceMgr();
134   QPixmap anUndoPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_UNDO")));
135   QPixmap aRedoPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_REDO")));
136   QPixmap aNewSectionPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_NEW_SECTION")));
137   QPixmap aNewPointPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_NEW_POINT")));
138   QPixmap anEditPointsPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_EDIT_POINTS")));
139   QPixmap aDetectPointsPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_EDIT_POINTS")));
140   QPixmap aPolylinePixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_POLYLINE")));
141   QPixmap aSplinePixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_SPLINE")));
142   QPixmap aRemovePixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_DELETE")));
143   QPixmap aJoinPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_JOIN")));
144   QPixmap aStepUpPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_ARROW_UP")));
145   QPixmap aStepDownPixmap(aResMgr->loadPixmap("GEOM", tr("ICON_CC_ARROW_DOWN")));
146
147   QAction* anAct = createAction( UNDO_ID, tr("UNDO"), anUndoPixmap, tr("UNDO_TLT"), 
148                                  QKeySequence(Qt::ControlModifier|Qt::Key_Z) );
149   connect(anAct, SIGNAL(triggered()), this, SLOT(onUndo()) );
150   aTB->addAction(anAct);
151
152   anAct = createAction( REDO_ID, tr("REDO"), aRedoPixmap, tr("REDO_TLT"), 
153                         QKeySequence(Qt::ControlModifier|Qt::Key_Y) );
154   connect(anAct, SIGNAL(triggered()), this, SLOT(onRedo()) );
155   aTB->addAction(anAct);
156
157   aTB->addSeparator();
158
159   anAct = createAction( NEW_SECTION_ID, tr("NEW_SECTION"), aNewSectionPixmap, tr("NEW_SECTION_TLT"), 
160                         QKeySequence(Qt::ControlModifier|Qt::Key_N) );
161   connect(anAct, SIGNAL(triggered()), this, SLOT(onNewSection()) );
162   aTB->addAction(anAct);
163   aTB->addSeparator();
164
165   anAct = createAction( ADDITION_MODE_ID, tr("ADDITION_MODE"), aNewPointPixmap, tr("ADDITION_MODE_TLT"), 
166                         QKeySequence() );
167   anAct->setCheckable(true);
168   connect(anAct, SIGNAL(triggered(bool)), this, SLOT(onAdditionMode(bool)) );
169   connect(anAct, SIGNAL(toggled(bool)), this, SLOT(onModeChanged(bool)) );
170   aTB->addAction(anAct);
171   
172   anAct = createAction( MODIFICATION_MODE_ID, tr("MODIFICATION_MODE"), anEditPointsPixmap, tr("MODIFICATION_MODE_TLT"), 
173                         QKeySequence() );
174   anAct->setCheckable(true);
175   connect(anAct, SIGNAL(triggered(bool)), this, SLOT(onModificationMode(bool)) );
176   connect(anAct, SIGNAL(toggled(bool)), this, SLOT(onModeChanged(bool)) );
177   aTB->addAction(anAct);
178
179   anAct = createAction( DETECTION_MODE_ID, tr("DETECTION_MODE"), aDetectPointsPixmap, tr("DETECTION_MODE_TLT"), 
180                         QKeySequence() );
181   anAct->setCheckable(true);
182   connect(anAct, SIGNAL(triggered(bool)), this, SLOT(onDetectionMode(bool)) );
183   connect(anAct, SIGNAL(toggled(bool)), this, SLOT(onModeChanged(bool)) );
184   aTB->addAction(anAct);
185
186   anAct = createAction( CLOSE_SECTIONS_ID, tr("CLOSE_SECTIONS"), QPixmap(), tr("CLOSE_SECTIONS_TLT"), 
187                         QKeySequence(Qt::ControlModifier|Qt::Key_W) );
188   connect(anAct, SIGNAL(triggered()), this, SLOT(onCloseSections()) );
189
190   anAct = createAction( UNCLOSE_SECTIONS_ID, tr("UNCLOSE_SECTIONS"), QPixmap(), 
191                         tr("UNCLOSE_SECTIONS_TLT"), QKeySequence(Qt::ControlModifier|Qt::Key_S) );
192   connect(anAct, SIGNAL(triggered()), this, SLOT(onUncloseSections()) );
193
194   anAct = createAction( SET_SECTIONS_POLYLINE_ID, tr("SET_SECTIONS_POLYLINE"), 
195                         aPolylinePixmap, tr("SET_POLYLINE_TLT"), 
196                         QKeySequence(Qt::ControlModifier|Qt::Key_E) );
197   connect(anAct, SIGNAL(triggered()), this, SLOT(onSetPolyline()) );
198
199   anAct = createAction( SET_SECTIONS_SPLINE_ID, tr("SET_SECTIONS_SPLINE"), aSplinePixmap, 
200                         tr("SET_SPLINE_TLT"), QKeySequence(Qt::ControlModifier|Qt::Key_R) );
201   connect(anAct, SIGNAL(triggered()), this, SLOT(onSetSpline()) );
202
203   anAct = createAction( REMOVE_ID, tr("REMOVE"), aRemovePixmap, tr("REMOVE_TLT"), 
204                         QKeySequence(Qt::ControlModifier|Qt::Key_Delete ) );
205   connect(anAct, SIGNAL(triggered()), this, SLOT(onRemove()) );
206   aTB->addAction(anAct);
207   // TODO join
208   //aTB->addSeparator();
209
210   //anAct = createAction( JOIN_ID, tr("JOIN"), aJoinPixmap, tr("JOIN_TLT"), 
211   //                      QKeySequence(Qt::ControlModifier|Qt::Key_Plus ) );
212   //connect( anAct, SIGNAL(triggered()), this, SLOT(onJoin()) );
213   //aTB->addAction(anAct);
214
215   anAct = createAction( CLEAR_ALL_ID, tr("CLEAR_ALL"), QPixmap(), tr("CLEAR_ALL_TLT"), 
216                         QKeySequence(Qt::ControlModifier | Qt::ShiftModifier | Qt::Key_Delete ) );
217   connect( anAct, SIGNAL(triggered()), this, SLOT( onClearAll()) );
218
219   // TODO join
220   //anAct = createAction( JOIN_ALL_ID, tr("JOIN_ALL"), QPixmap(), tr("JOIN_ALL_TLT"), 
221   //                      QKeySequence(Qt::ControlModifier | Qt::ShiftModifier | Qt::Key_Plus ) );
222   //connect( anAct, SIGNAL(triggered()), this, SLOT(onJoinAll()) );
223
224   QVBoxLayout* aSectLayout = new QVBoxLayout();
225   aSectLayout->setMargin( 5 );
226   aSectLayout->setSpacing( 5 );
227   aSectLayout->addWidget(aTB);
228   aSectLayout->addWidget(mySectionView);
229   aSectLayout->addWidget( myLocalPointView );
230   aSectionGroup->setLayout(aSectLayout);
231   QVBoxLayout* aLay = new QVBoxLayout();
232   aLay->setMargin( 0 );
233   aLay->setSpacing( 5 );
234 //    aLay->addLayout(aNameLayout);
235   aLay->addWidget(aSectionGroup);
236   setLayout(aLay);
237
238   updateActionsStates();
239   updateUndoRedo();
240 }
241
242 /**
243  * Set an OCC viewer
244  */
245 void CurveCreator_Widget::setOCCViewer( OCCViewer_Viewer* theViewer )
246 {
247   if ( myOCCViewer == theViewer )
248     return;
249
250   if ( myOCCViewer ) {
251     OCCViewer_ViewManager* aViewManager = dynamic_cast<OCCViewer_ViewManager*>
252                                                     ( myOCCViewer->getViewManager() );
253     disconnect( aViewManager, SIGNAL( mousePress( SUIT_ViewWindow*, QMouseEvent* ) ),
254            this, SLOT( onMousePress( SUIT_ViewWindow*, QMouseEvent* ) ) );
255     disconnect( aViewManager, SIGNAL( mouseRelease( SUIT_ViewWindow*, QMouseEvent* ) ),
256            this, SLOT( onMouseRelease( SUIT_ViewWindow*, QMouseEvent* ) ) );
257     disconnect( aViewManager, SIGNAL( mouseMove( SUIT_ViewWindow*, QMouseEvent* ) ),
258            this, SLOT( onMouseMove( SUIT_ViewWindow*, QMouseEvent* ) ) );
259     disconnect( aViewManager, SIGNAL( lastViewClosed( SUIT_ViewManager* ) ),
260            this, SLOT( onLastViewClosed( SUIT_ViewManager* ) ) );
261     // restore normal mode in the viewer
262     OCCViewer_Utilities::setViewer2DMode( myOCCViewer, OCCViewer_ViewWindow::No2dMode );
263     // all local contexts should be closed if the viewer is not more used
264     setLocalPointContext( false, true );
265   }
266
267   myOCCViewer = theViewer;
268   if ( myOCCViewer ) {
269     OCCViewer_ViewManager* aViewManager = dynamic_cast<OCCViewer_ViewManager*>
270                                                     ( myOCCViewer->getViewManager() );
271     connect( aViewManager, SIGNAL( mousePress( SUIT_ViewWindow*, QMouseEvent* ) ),
272            this, SLOT( onMousePress( SUIT_ViewWindow*, QMouseEvent* ) ) );
273     connect( aViewManager, SIGNAL( mouseRelease( SUIT_ViewWindow*, QMouseEvent* ) ),
274            this, SLOT( onMouseRelease( SUIT_ViewWindow*, QMouseEvent* ) ) );
275     connect( aViewManager, SIGNAL( mouseMove( SUIT_ViewWindow*, QMouseEvent* ) ),
276            this, SLOT( onMouseMove( SUIT_ViewWindow*, QMouseEvent* ) ) );
277     connect( aViewManager, SIGNAL( lastViewClosed( SUIT_ViewManager* ) ),
278            this, SLOT( onLastViewClosed( SUIT_ViewManager* ) ) );
279     OCCViewer_Utilities::setViewer2DMode( myOCCViewer, OCCViewer_ViewWindow::XYPlane );
280   }
281 }
282
283 /**
284  * Returns current OCC viewer
285  */
286 OCCViewer_Viewer* CurveCreator_Widget::getOCCViewer()
287 {
288   return myOCCViewer;
289 }
290
291 /**
292  * Returns OCC viewer context
293  */
294 Handle(AIS_InteractiveContext) CurveCreator_Widget::getAISContext()
295 {
296   Handle(AIS_InteractiveContext) aContext;
297   OCCViewer_Viewer* aViewer = getOCCViewer();
298   if ( aViewer )
299     aContext = aViewer->getAISContext();
300
301   return aContext;
302 }
303
304 /**
305  * Returns OCC viewer view port
306  */
307 OCCViewer_ViewPort3d* CurveCreator_Widget::getViewPort()
308 {
309   OCCViewer_ViewPort3d* aViewPort = 0;
310   OCCViewer_Viewer* aViewer = getOCCViewer();
311   if ( aViewer )
312     aViewPort = ((OCCViewer_ViewWindow*)aViewer->getViewManager()->getActiveView())->getViewPort();
313     
314   return aViewPort;
315 }
316
317 /**
318  * Set interaction style in the OCC viewer
319  * \param theStyle a new style
320  * \return the previous style
321  */
322 int CurveCreator_Widget::changeInteractionStyle( int theStyle )
323 {
324   OCCViewer_Viewer* aViewer = getOCCViewer();
325   if ( !aViewer )
326     return -1;
327
328   int aPrevStyle = aViewer->interactionStyle();
329   aViewer->setInteractionStyle( theStyle );
330
331   return aPrevStyle;
332 }
333
334 /**
335  * Set interaction style in the OCC viewer
336  * \param theStyle a new style
337  * \return the previous style
338  */
339 void CurveCreator_Widget::setObjectsSelected(const AIS_ListOfInteractive& theList)
340 {
341   OCCViewer_Viewer* aViewer = getOCCViewer();
342   if ( aViewer )
343     aViewer->setObjectsSelected(theList);
344 }
345
346 //=======================================================================
347 // function: reset
348 // purpose: reset the widget viewer, close local context, clear selection
349 //=======================================================================
350 void CurveCreator_Widget::reset()
351 {
352 }
353
354 void CurveCreator_Widget::setCurve( CurveCreator_ICurve* theCurve )
355 {
356   myCurve = theCurve;
357   mySectionView->setCurve( myCurve );
358   myLocalPointView->setCurve( myCurve );
359   updateActionsStates();
360   updateUndoRedo();
361 }
362
363 void CurveCreator_Widget::onSelectionChanged()
364 {
365   updateActionsStates();
366   updateUndoRedo();
367   emit selectionChanged();
368 }
369
370 void CurveCreator_Widget::updateActionsStates()
371 {
372   QList<ActionId> anEnabledAct;
373   if( myCurve ){
374     anEnabledAct << NEW_SECTION_ID << MODIFICATION_MODE_ID;
375     if ( removeEnabled() )
376       anEnabledAct << REMOVE_ID;
377     QList<int> aSelSections = mySectionView->getSelectedSections();
378     QList< QPair< int, int > > aSelPoints = mySectionView->getSelectedPoints();
379     CurveCreator_TreeView::SelectionType aSelType = mySectionView->getSelectionType();
380     switch( aSelType ){
381     case CurveCreator_TreeView::ST_NOSEL:{
382       break;
383     }
384     case CurveCreator_TreeView::ST_SECTIONS:{
385       /*if( aSelSections[0] > 0 ){
386         anEnabledAct << UP_ID;
387       }*/
388       if( aSelSections.size() == 1 ){
389         anEnabledAct << ADDITION_MODE_ID << DETECTION_MODE_ID;
390       }
391       switch ( getActionMode() ) {
392         case AdditionMode: {
393           mySection = -1;
394           myPointNum = -1;
395           QList<int> aSelSection = mySectionView->getSelectedSections();
396           if( aSelSection.size() > 0 ){
397             mySection = aSelSection[0];
398             myPointNum = myCurve->getNbPoints(mySection);
399           }
400         }
401         break;
402         case ModificationMode: {
403          anEnabledAct << CLOSE_SECTIONS_ID << UNCLOSE_SECTIONS_ID << SET_SECTIONS_POLYLINE_ID << SET_SECTIONS_SPLINE_ID;
404           int aSectCnt = myCurve->getNbSections();
405           if( aSectCnt > 0 )
406             anEnabledAct << CLEAR_ALL_ID;
407           // TODO
408           //if( aSectCnt > 1 )
409           //  anEnabledAct << JOIN_ALL_ID;
410           //if( aSelSections.size() > 1 ){
411           //  anEnabledAct << JOIN_ID;
412           //}
413         }
414         break;
415         case DetectionMode: {
416         }
417         break;
418         case NoneMode:
419         default:
420         break;
421       }
422       /*if( aSelSections[ aSelSections.size() - 1 ] < ( myCurve->getNbSections() - 1 ) ){
423         anEnabledAct << DOWN_ID;
424       }*/
425       break;
426     }
427     /*case CurveCreator_TreeView::ST_POINTS_ONE_SECTION:{
428       if( aSelPoints[0].second > 0 ){
429         anEnabledAct << UP_ID;
430       }
431       int aLastIndex = aSelPoints.size()-1;
432       int aSect = aSelPoints[0].first;
433       if( aSelPoints[aLastIndex].second < (myCurve->getNbPoints(aSect) - 1)){
434         anEnabledAct << DOWN_ID;
435       }
436       if( aSelPoints.size() == 1){
437         anEnabledAct << INSERT_POINT_BEFORE_ID << INSERT_POINT_AFTER_ID;
438       }
439       break;
440     }*/
441
442     }
443     
444     /*int aSelObjsCnt = aSelPoints.size() + aSelSections.size();
445     if( aSelObjsCnt > 0 ){
446       anEnabledAct << REMOVE_ID;
447     }
448     if( (myCurve->getNbSections() + myCurve->getNbPoints()) > 0 ){
449       anEnabledAct << REMOVE_ALL_ID;
450     }*/
451     // TODO
452     //if( myCurve->getNbSections() > 1 ){
453     //  anEnabledAct << JOIN_ALL_ID;
454     //}
455   }
456   QList<ActionId> anIds = myActionMap.keys();
457   for( int i = 0 ; i < anIds.size() ; i++ ){
458     if( myActionMap.contains(anIds[i]) ){
459       if( anEnabledAct.contains(anIds[i]) ){
460         myActionMap[anIds[i]]->setEnabled(true);
461       }
462       else{
463         myActionMap[anIds[i]]->setEnabled(false);
464       }
465     }
466   }
467 }
468
469 void CurveCreator_Widget::onAdditionMode(bool checked)
470 {
471   if (!checked)
472     return;
473
474   Handle(AIS_InteractiveContext) aContext = getAISContext();
475   if( !myCurve || aContext.IsNull() )
476     return;
477
478   mySection= -1;
479   myPointNum = -1;
480   QList<int> aSelSection = mySectionView->getSelectedSections();
481   if( aSelSection.size() > 0 ){
482     mySection = aSelSection[0];
483   }
484   else{
485     QList< QPair<int,int> > aSelPoints = mySectionView->getSelectedPoints();
486     if( aSelPoints.size() > 0 ){
487       mySection = aSelPoints[0].first;
488       myPointNum = aSelPoints[0].second + 1;
489     }
490   }
491 //  emit subOperationStarted( myNewPointEditor );
492 }
493
494 void CurveCreator_Widget::onModificationMode(bool checked)
495 {
496   myLocalPointView->setVisible( checked );
497 }
498
499 void CurveCreator_Widget::onDetectionMode(bool checked)
500 {
501 }
502
503 void CurveCreator_Widget::onModeChanged(bool checked)
504 {
505   ActionMode aMode = NoneMode;
506   if (checked) {
507     QAction* anAction = (QAction*)sender();
508     switch(myActionMap.key(anAction)) {
509       case ADDITION_MODE_ID:
510         aMode = AdditionMode;
511         if (myActionMap[MODIFICATION_MODE_ID]->isChecked())
512           myActionMap[MODIFICATION_MODE_ID]->trigger();
513         else if (myActionMap[DETECTION_MODE_ID]->isChecked())
514           myActionMap[DETECTION_MODE_ID]->trigger();
515         break;
516       case MODIFICATION_MODE_ID:
517         aMode = ModificationMode;
518         if (myActionMap[ADDITION_MODE_ID]->isChecked())
519           myActionMap[ADDITION_MODE_ID]->trigger();
520         else if (myActionMap[DETECTION_MODE_ID]->isChecked())
521           myActionMap[DETECTION_MODE_ID]->trigger();
522         break;
523       case DETECTION_MODE_ID:
524         aMode = DetectionMode;
525         if (myActionMap[ADDITION_MODE_ID]->isChecked())
526           myActionMap[ADDITION_MODE_ID]->trigger();
527         else if (myActionMap[MODIFICATION_MODE_ID]->isChecked())
528           myActionMap[MODIFICATION_MODE_ID]->trigger();
529         break;
530     }
531   }
532   updateActionsStates();
533   updateUndoRedo();
534   setLocalPointContext( aMode == ModificationMode, true );
535 }
536
537 void CurveCreator_Widget::onAddNewPoint(const CurveCreator::Coordinates& theCoords)
538 {
539   if( !myCurve )
540     return;
541   //myCurve->addPoints(theCoords, mySection, myPointNum );
542   //mySectionView->pointsAdded( mySection, myPointNum );
543   //myPointNum++;
544   QList<int> aSections = mySectionView->getSelectedSections();
545   if( aSections.size() == 0 ){
546     return;
547   }
548   int aSection = aSections[0];
549   myCurve->addPoints(theCoords, aSection); // add to the end of section
550   mySectionView->pointsAdded( aSection, myCurve->getNbPoints( aSection ) );
551   updateActionsStates();
552   updateUndoRedo();
553 }
554
555 void CurveCreator_Widget::onNewSection()
556 {
557   if( !myCurve )
558     return;
559   myNewSectionEditor->clear();
560   myNewSectionEditor->setEditMode(false);
561   QString aSectName = QString( CurveCreator_UtilsICurve::getUniqSectionName( myCurve ).c_str() );
562   myNewSectionEditor->setSectionParameters(aSectName, true, CurveCreator::Polyline );
563   emit subOperationStarted( myNewSectionEditor );
564 }
565
566 void CurveCreator_Widget::onAddNewSection()
567 {
568   if( !myCurve )
569     return;
570   myCurve->addSection( myNewSectionEditor->getName().toStdString(),
571                        myNewSectionEditor->getSectionType(),
572                        myNewSectionEditor->isClosed() );
573   mySectionView->sectionAdded( -1 ); // add a new section to the end of list
574   QString aNewName = QString( CurveCreator_UtilsICurve::getUniqSectionName( myCurve ).c_str() );
575   myNewSectionEditor->setSectionName(aNewName);
576   updateActionsStates();
577   updateUndoRedo();
578   onCancelSection();
579 }
580
581 void CurveCreator_Widget::onCancelSection()
582 {
583   emit subOperationFinished( myNewSectionEditor );
584 }
585
586 QAction* CurveCreator_Widget::createAction( ActionId theId, const QString& theName, const QPixmap& theImage,
587                                             const QString& theToolTip, const QKeySequence& theShortcut )
588 {
589   QAction* anAct = new QAction(theName,this);
590   if( !theImage.isNull() ){
591     anAct->setIcon(theImage);
592   }
593   anAct->setShortcut(theShortcut);
594   anAct->setToolTip(theToolTip);
595   myActionMap[theId] = anAct;
596   return anAct;
597 }
598
599 QAction* CurveCreator_Widget::getAction(ActionId theId)
600 {
601   if( myActionMap.contains(theId) )
602     return myActionMap[theId];
603   return NULL;
604 }
605
606 CurveCreator_Widget::ActionMode CurveCreator_Widget::getActionMode() const
607 {
608   ActionMode aMode = NoneMode;
609
610   if ( myActionMap[ADDITION_MODE_ID]->isChecked() )
611     aMode = AdditionMode;
612   else if ( myActionMap[MODIFICATION_MODE_ID]->isChecked() )
613     aMode = ModificationMode;
614   else if ( myActionMap[DETECTION_MODE_ID]->isChecked() )
615     aMode = DetectionMode;
616
617   return aMode;
618 }
619
620 void CurveCreator_Widget::onEditSection( int theSection )
621 {
622   if( !myCurve )
623     return;
624   mySection = theSection;
625   QString aSectName = QString::fromStdString( myCurve->getSectionName(theSection));
626   bool isClosed = myCurve->isClosed(theSection);
627   CurveCreator::SectionType aType = myCurve->getSectionType(theSection);
628   myNewSectionEditor->setEditMode(true);
629   myNewSectionEditor->setSectionParameters( aSectName, isClosed, aType );
630
631   emit subOperationStarted( myNewSectionEditor );
632 }
633
634 void CurveCreator_Widget::onModifySection()
635 {
636   if( !myCurve )
637     return;
638   QString aName = myNewSectionEditor->getName();
639   bool isClosed = myNewSectionEditor->isClosed();
640   CurveCreator::SectionType aSectType = myNewSectionEditor->getSectionType();
641 //  myCurve->startOperation();
642   if( myCurve->getSectionName(mySection) != aName.toStdString() )
643     myCurve->setSectionName( mySection , aName.toStdString() );
644
645   if( myCurve->getSectionType(mySection) != aSectType )
646     myCurve->setSectionType( mySection, aSectType );
647
648   if( myCurve->isClosed(mySection) != isClosed )
649     myCurve->setClosed( mySection, isClosed );
650 //  myCurve->finishOperation();
651   mySectionView->sectionChanged(mySection);
652   updateUndoRedo();
653   onCancelSection();
654 }
655
656 /*void CurveCreator_Widget::onEditPoint( int theSection, int thePoint )
657 {
658   if( !myNewPointEditor || !myEdit )
659     return;
660   mySection = theSection;
661   myPointNum = thePoint;
662   QString aSectName = QString::fromStdString( myCurve->getSectionName(theSection));
663   myNewPointEditor->setEditMode(true);
664   myNewPointEditor->setSectionName(aSectName);
665   myNewPointEditor->setDimension( myCurve->getDimension() );
666   CurveCreator::Coordinates aCoords = myCurve->getCoordinates(theSection,thePoint);
667   myNewPointEditor->setCoordinates(aCoords);
668   emit subOperationStarted( myNewPointEditor );
669 }
670
671 void CurveCreator_Widget::onModifyPoint()
672 {
673   if( !myEdit )
674     return;
675   CurveCreator::Coordinates aCoords = myNewPointEditor->getCoordinates();
676   myEdit->setCoordinates( aCoords, mySection, myPointNum );
677   mySectionView->pointDataChanged( mySection, myPointNum );
678   updateUndoRedo();
679   onCancelPoint();
680 }*/
681
682 void CurveCreator_Widget::onJoin()
683 {
684   if( !myCurve )
685     return;
686   QList<int> aSections = mySectionView->getSelectedSections();
687   if( aSections.size() == 0 ){
688     return;
689   }
690   int aMainSect = aSections[0];
691   int aMainSectSize = myCurve->getNbPoints(aMainSect);
692 //  myCurve->startOperation();
693   for( int i = 1 ; i < aSections.size() ; i++ ){
694     int aSectNum = aSections[i] - (i-1);
695     myCurve->join( aMainSect, aSectNum );
696     mySectionView->sectionsRemoved( aSectNum );
697   }
698 //  myCurve->finishOperation();
699   int aNewSectSize = myCurve->getNbPoints(aMainSect);
700   if( aNewSectSize != aMainSectSize )
701     mySectionView->pointsAdded( aMainSect, aMainSectSize, aNewSectSize-aMainSectSize );
702   updateUndoRedo();
703 }
704
705 void CurveCreator_Widget::onRemove()
706 {
707   if( !myCurve )
708     return;
709
710   switch( getActionMode() ) {
711     case NoneMode:
712       removeSection();
713     break;
714     case ModificationMode:
715       removePoint();
716     break;
717     default:
718       break;
719   }
720 }
721
722 void CurveCreator_Widget::onClearAll()
723 {
724   if( !myCurve )
725     return;
726   myCurve->clear();
727   mySectionView->reset();
728   updateActionsStates();
729   updateUndoRedo();
730 }
731
732 void CurveCreator_Widget::onJoinAll()
733 {
734   if( !myCurve )
735     return;
736   myCurve->join();
737   mySectionView->reset();
738   updateActionsStates();
739   updateUndoRedo();
740 }
741
742 void CurveCreator_Widget::onUndoSettings()
743 {
744
745 }
746
747 void CurveCreator_Widget::onSetSpline()
748 {
749   if( !myCurve )
750     return;
751   QList<int> aSelSections = mySectionView->getSelectedSections();
752 //  myCurve->startOperation();
753   for( int i = 0 ; i < aSelSections.size() ; i++ ){
754     myCurve->setSectionType(aSelSections[i], CurveCreator::Spline );
755     mySectionView->sectionChanged(aSelSections[i]);
756   }
757 //  myCurve->finishOperation();
758   updateUndoRedo();
759 }
760
761 void CurveCreator_Widget::onSetPolyline()
762 {
763   if( !myCurve )
764     return;
765 //  myCurve->startOperation();
766   QList<int> aSelSections = mySectionView->getSelectedSections();
767   for( int i = 0 ; i < aSelSections.size() ; i++ ){
768     myCurve->setSectionType( aSelSections[i], CurveCreator::Polyline );
769     mySectionView->sectionChanged( aSelSections[i] );
770   }
771 //  myCurve->finishOperation();
772   updateUndoRedo();
773 }
774
775 void CurveCreator_Widget::onCloseSections()
776 {
777   if( !myCurve )
778     return;
779 //  myCurve->startOperation();
780   QList<int> aSelSections = mySectionView->getSelectedSections();
781   for( int i = 0 ; i < aSelSections.size() ; i++ ){
782     myCurve->setClosed(aSelSections[i], true);
783     mySectionView->sectionChanged(aSelSections[i]);
784   }
785 //  myCurve->finishOperation();
786   updateUndoRedo();
787 }
788
789 void CurveCreator_Widget::onUncloseSections()
790 {
791   if( !myCurve )
792     return;
793 //  myCurve->startOperation();
794   QList<int> aSelSections = mySectionView->getSelectedSections();
795   for( int i = 0 ; i < aSelSections.size() ; i++ ){
796     myCurve->setClosed(aSelSections[i], false);
797     mySectionView->sectionChanged(aSelSections[i]);
798   }
799 //  myCurve->finishOperation();
800   updateUndoRedo();
801 }
802
803 void CurveCreator_Widget::onUndo()
804 {
805     if( !myCurve )
806       return;
807
808     CurveCreator_ICurve::SectionToPointList aPoints;
809     startCurveModification( aPoints, false );
810     myCurve->undo();
811     finishCurveModification();
812     mySectionView->reset();
813 }
814
815 void CurveCreator_Widget::onRedo()
816 {
817     if( !myCurve )
818       return;
819     CurveCreator_ICurve::SectionToPointList aPoints;
820     startCurveModification( aPoints, false );
821     myCurve->redo();
822     finishCurveModification();
823     mySectionView->reset();
824 }
825
826 void CurveCreator_Widget::updateUndoRedo()
827 {
828   if( !myCurve )
829     return;
830   QAction* anAct = myActionMap[UNDO_ID];
831   if( anAct != 0 ){
832     if( myCurve->getNbUndo() != 0 ){
833       anAct->setEnabled(true);
834     }
835     else{
836       anAct->setDisabled(true);
837     }
838   }
839   anAct = myActionMap[REDO_ID];
840   if( anAct != 0 ){
841     if( myCurve->getNbRedo() != 0 ){
842       anAct->setEnabled(true);
843     }
844     else{
845       anAct->setDisabled(true);
846     }
847   }
848 }
849
850 void CurveCreator_Widget::onContextMenu( QPoint thePoint )
851 {
852   QList<ActionId> aContextActions;
853   aContextActions << CLEAR_ALL_ID << JOIN_ALL_ID << SEPARATOR_ID <<
854                      CLOSE_SECTIONS_ID << UNCLOSE_SECTIONS_ID << SET_SECTIONS_POLYLINE_ID <<
855                      SET_SECTIONS_SPLINE_ID;
856   QPoint aGlPoint = mySectionView->mapToGlobal(thePoint);
857   bool isVis = false;
858   QList<ActionId> aResAct;
859   for( int i = 0 ; i < aContextActions.size() ; i++ ){
860     if( aContextActions[i] != SEPARATOR_ID ){
861       if( myActionMap.contains(aContextActions[i]) ){
862         QAction* anAct = myActionMap[aContextActions[i]];
863         if( anAct->isEnabled() ){
864           aResAct << aContextActions[i];
865           isVis = true;
866         }
867       }
868     }
869     else{
870       aResAct << SEPARATOR_ID;
871     }
872   }
873   if( !isVis )
874     return;
875
876   QMenu* aMenu = new QMenu(this);
877   for( int i = 0 ; i < aResAct.size() ; i++ ){
878     if( aResAct[i] == SEPARATOR_ID ){
879       aMenu->addSeparator();
880     }
881     else{
882       QAction* anAct = myActionMap[aResAct[i]];
883       aMenu->insertAction(NULL, anAct);
884     }
885   }
886   aMenu->exec(aGlPoint);
887 }
888
889 QList<int> CurveCreator_Widget::getSelectedSections()
890 {
891   return mySectionView->getSelectedSections();
892 }
893
894 QList< QPair< int, int > > CurveCreator_Widget::getSelectedPoints()
895 {
896   return mySectionView->getSelectedPoints();
897 }
898
899 /**
900  * According to the widget state, performs the remove action
901  */
902 void CurveCreator_Widget::removeSelected()
903 {
904   onRemove();
905 }
906
907 /**
908  * Checks whether there are some selection to be removed
909  */
910 bool CurveCreator_Widget::removeEnabled()
911 {
912   bool isEnabled = getActionMode() == ModificationMode;
913   if ( !isEnabled ) {
914     QList<int> aSelSections = mySectionView->getSelectedSections();
915     CurveCreator_TreeView::SelectionType aSelType = mySectionView->getSelectionType();
916     isEnabled = aSelType == CurveCreator_TreeView::ST_SECTIONS &&
917                 aSelSections.size() == 1;
918   }
919   return isEnabled;
920 }
921
922
923 //=================================================================================
924 // function : GeometryGUI::onGetCoordsByClick()
925 // purpose  : Manage mouse press events in Additon mode
926 //=================================================================================
927 void CurveCreator_Widget::onGetCoordsByClick( QMouseEvent* pe )
928 {
929   if (pe->button() != Qt::LeftButton)
930     return;
931
932   if ( pe->modifiers() != Qt::ControlModifier ) {
933     Handle(AIS_InteractiveContext) ic = getAISContext();
934     if ( ic.IsNull() )
935       return;
936
937     gp_Pnt aPnt;    
938
939     ic->InitSelected();
940     if ( pe->modifiers() == Qt::ShiftModifier )
941       ic->ShiftSelect();  // Append selection
942     else
943       ic->Select();       // New selection
944
945     /*TopoDS_Shape aShape;
946
947     ic->InitSelected();
948     if ( ic->MoreSelected() )
949       aShape = ic->SelectedShape();
950
951     if ( !aShape.IsNull() && aShape.ShapeType() == TopAbs_VERTEX )
952       aPnt = BRep_Tool::Pnt( TopoDS::Vertex( ic->SelectedShape() ) );
953     else*/
954     {
955       OCCViewer_ViewPort3d* vp = getViewPort();
956       aPnt = CurveCreator_Utils::ConvertClickToPoint( pe->x(), pe->y(), vp->getView() );
957     }
958     // set the coordinates into dialog
959     CurveCreator::Coordinates aCoords;
960     aCoords.push_back( aPnt.X() );
961     aCoords.push_back( aPnt.Y() );
962     if ( myCurve->getDimension() == 3 ) {
963       aCoords.push_back( aPnt.Z() );
964     }
965     onAddNewPoint(aCoords);
966 //    myNewPointEditor->setCoordinates( aCoords );
967   }
968 }
969
970 /**
971  * Manage mouse press events
972  * \param theWindow an owner of the signal
973  * \param theEvent a mouse event
974  */
975 void CurveCreator_Widget::onMousePress( SUIT_ViewWindow*, QMouseEvent* theEvent )
976 {
977   if ( theEvent->button() != Qt::LeftButton )
978     return;
979
980   switch( getActionMode() ) {
981     case ModificationMode: {
982       //store initial cursor position for Drag&Drop
983       setDragStarted( true, theEvent->pos() );
984       break;
985     }
986     case AdditionMode: {
987       onGetCoordsByClick( theEvent );
988       break;
989     }
990     default:
991       break;
992   }
993 }
994
995 /**
996  * Manage mouse release events in Modification mode
997  * \param theWindow an owner of the signal
998  * \param theEvent a mouse event
999  */
1000 void CurveCreator_Widget::onMouseRelease( SUIT_ViewWindow*, QMouseEvent* theEvent )
1001 {
1002   if ( getActionMode() != ModificationMode )
1003     return;
1004
1005   if ( myDragStarted ) {
1006     bool isDragged = myDragged;
1007     CurveCreator_ICurve::SectionToPointList aDraggedPoints;
1008     if ( myDragged )
1009       aDraggedPoints = myDragPoints;
1010
1011     setDragStarted( false );
1012     // if the drag of some points has happened, restore the drag selection
1013     if ( aDraggedPoints.size() > 0 )
1014     {
1015       START_MEASURE_TIME;
1016       setSelectedPoints( aDraggedPoints );
1017       END_MEASURE_TIME( "drop" );
1018     }
1019   }
1020   else // check whether the segment is clicked an a new point should be added to the segment
1021     insertPointToSelectedSegment( theEvent->pos().x(), theEvent->pos().y() );
1022
1023   // updates the input panel table to show the selected point coordinates
1024   updateLocalPointView();
1025 }
1026
1027 /**
1028  * Manage mouse move events in Modification mode
1029  * \param theWindow an owner of the signal
1030  * \param theEvent a mouse event
1031  */
1032 void CurveCreator_Widget::onMouseMove( SUIT_ViewWindow*, QMouseEvent* theEvent )
1033 {
1034   if ( getActionMode() != ModificationMode || !myDragStarted )
1035     return;
1036
1037   QPoint aPos = theEvent->pos();
1038   if ( (aPos - myDragStartPosition).manhattanLength() < QApplication::startDragDistance() )
1039     return;
1040
1041   START_MEASURE_TIME;
1042
1043   moveSelectedPoints( aPos.x(), aPos.y() );
1044   myDragStartPosition = aPos;
1045
1046   END_MEASURE_TIME( "drag" );
1047 }
1048
1049 /**
1050  * Set zero viewer by the last view closed in
1051  * \param theManager a viewer manager
1052  */
1053 void CurveCreator_Widget::onLastViewClosed( SUIT_ViewManager* theManager )
1054 {
1055   myOCCViewer = 0;
1056 }
1057
1058 void CurveCreator_Widget::onMousePress( QMouseEvent* theEvent )
1059 {
1060   onMousePress( 0, theEvent );
1061 }
1062
1063 void CurveCreator_Widget::onMouseRelease( QMouseEvent* theEvent )
1064 {
1065   onMouseRelease( 0, theEvent );
1066 }
1067
1068 void CurveCreator_Widget::onMouseMove( QMouseEvent* theEvent )
1069 {
1070   onMouseMove( 0, theEvent );
1071 }
1072
1073 void CurveCreator_Widget::onCellChanged( int theRow, int theColumn )
1074 {
1075   int aCurrSect = myLocalPointView->getSectionId( theRow );
1076   int aPntIndex = myLocalPointView->getPointId( theRow );
1077
1078   if ( aPntIndex < 0 )
1079     return;
1080
1081   CurveCreator_ICurve::SectionToPointList aSelPoints;
1082   startCurveModification( aSelPoints );
1083
1084   double aX  = myLocalPointView->item( theRow, 2 )->data( Qt::UserRole ).toDouble();
1085   double anY = myLocalPointView->item( theRow, 3 )->data( Qt::UserRole ).toDouble();
1086   std::deque<float> aChangedPos;
1087   aChangedPos.push_back( aX );
1088   aChangedPos.push_back( anY );
1089   myCurve->setPoint( aCurrSect, aPntIndex, aChangedPos );
1090
1091   finishCurveModification( aSelPoints );
1092 }
1093
1094 /**
1095  * Removes a selected section from the curve. Updates undo/redo status
1096  */
1097 void CurveCreator_Widget::removeSection()
1098 {
1099   QList< QPair<int,int> > aSelPoints = mySectionView->getSelectedPoints();
1100   int aCurrSect=-1;
1101   int aRemoveCnt = 0;
1102 //  myCurve->startOperation();
1103   for( int i = 0 ; i < aSelPoints.size() ; i++ ){
1104     if( aCurrSect != aSelPoints[i].first ){
1105       aRemoveCnt = 0;
1106       aCurrSect = aSelPoints[i].first;
1107     }
1108     int aPntIndx = aSelPoints[i].second - aRemoveCnt;
1109     myCurve->removePoint( aCurrSect, aPntIndx );
1110     mySectionView->pointsRemoved( aCurrSect, aPntIndx );
1111     aRemoveCnt++;
1112   }
1113   QList<int> aSections = mySectionView->getSelectedSections();
1114   for( int i = 0 ; i < aSections.size() ; i++ ){
1115     int aSectNum = aSections[i] - (i);
1116     myCurve->removeSection( aSectNum );
1117     mySectionView->sectionsRemoved( aSectNum );
1118   }
1119 //  myCurve->finishOperation();
1120   mySectionView->clearSelection();
1121   updateUndoRedo();
1122 }
1123
1124 /**
1125  * Removes a selected points from the curve. Updates undo/redo status
1126  */
1127 void CurveCreator_Widget::removePoint()
1128 {
1129   CurveCreator_ICurve::SectionToPointList aPoints;
1130   getSelectedPoints( aPoints );
1131   if ( aPoints.size() == 0 )
1132     return;
1133
1134   CurveCreator_ICurve::SectionToPointList aSelPoints;
1135   startCurveModification( aSelPoints, false );
1136
1137   myCurve->removeSeveralPoints( aPoints );
1138   finishCurveModification( CurveCreator_ICurve::SectionToPointList() );
1139 }
1140
1141 void CurveCreator_Widget::insertPointToSelectedSegment( const int theX,
1142                                                         const int theY )
1143 {
1144   Handle(AIS_InteractiveContext) aContext = getAISContext();
1145
1146   OCCViewer_ViewPort3d* aViewPort = getViewPort();
1147   Handle(V3d_View) aView;
1148   if ( aViewPort )
1149     aView = aViewPort->getView();
1150
1151   if ( aContext.IsNull() || aView.IsNull() )
1152     return;
1153   gp_Pnt aPoint;
1154   gp_Pnt aPoint1, aPoint2;
1155   bool isFoundPoint = CurveCreator_Utils::getNeighbourPoints( aContext, aView, theX, theY,
1156                                                               aPoint, aPoint1, aPoint2 );
1157   if ( !isFoundPoint )
1158     return;
1159
1160   // insert the point to the model curve
1161   CurveCreator_ICurve::SectionToPointList aSelPoints;
1162   startCurveModification( aSelPoints );
1163
1164   CurveCreator::Coordinates aCoords;
1165   aCoords.push_back( aPoint.X() );
1166   aCoords.push_back( aPoint.Y() );
1167
1168   CurveCreator_ICurve::SectionToPointList aPoints1, aPoints2;
1169   findSectionsToPoints( aPoint1.X(), aPoint1.Y(), aPoints1 );
1170   findSectionsToPoints( aPoint2.X(), aPoint2.Y(), aPoints2 );
1171   CurveCreator_ICurve::SectionToPointList::const_iterator anIt = aPoints1.begin(),
1172                                                           aLast = aPoints1.end();
1173   int aSectionId = -1;
1174   // there can be a case when a new point is added into two sections
1175   int aPoint1Id = -1, aPoint2Id = -1;
1176   for ( ; anIt != aLast && aSectionId < 0; anIt++ ) {
1177     int aSectionCur = anIt->first;
1178     CurveCreator_ICurve::SectionToPointList::const_iterator anIt2 = aPoints2.begin(),
1179                                                             aLast2 = aPoints2.end();
1180     for ( ; anIt2 != aLast2 && aSectionId < 0; anIt2++ ) {
1181       if ( anIt2->first == aSectionCur ) {
1182         aSectionId = aSectionCur;
1183         aPoint1Id = anIt->second;
1184         aPoint2Id = anIt2->second;
1185       }
1186     }
1187   }
1188
1189   int anInsertPos = -1;
1190   int aLastPoint = myCurve->getNbPoints( aSectionId )-1; 
1191   if ( ( aPoint1Id == aLastPoint && aPoint2Id == 0 ) ||
1192        ( aPoint2Id == aLastPoint && aPoint1Id == 0 ) )
1193     anInsertPos = -1; // if the section happens between first and last points
1194   else
1195     anInsertPos = aPoint1Id < aPoint2Id ? aPoint1Id + 1 : aPoint2Id + 1;
1196
1197   myCurve->addPoints( aCoords, aSectionId, anInsertPos );
1198   mySectionView->pointsAdded( aSectionId, myCurve->getNbPoints( aSectionId ) );
1199
1200   finishCurveModification( aSelPoints );
1201
1202   setSelectedPoints();
1203 }
1204
1205 void CurveCreator_Widget::moveSelectedPoints( const int theXPosition,
1206                                               const int theYPosition )
1207 {
1208   OCCViewer_ViewPort3d* aViewPort = getViewPort();
1209   if ( !aViewPort )
1210     return;
1211
1212   CurveCreator_ICurve::SectionToPointList aPoints;
1213   startCurveModification( aPoints, false );
1214
1215   gp_Pnt aStartPnt = CurveCreator_Utils::ConvertClickToPoint( myDragStartPosition.x(),
1216                                                               myDragStartPosition.y(),
1217                                                               aViewPort->getView() );
1218   gp_Pnt anEndPnt = CurveCreator_Utils::ConvertClickToPoint( theXPosition, theYPosition,
1219                                                              aViewPort->getView() );
1220   double aXDelta = aStartPnt.X() - anEndPnt.X();
1221   double anYDelta = aStartPnt.Y() - anEndPnt.Y();
1222
1223   CurveCreator_ICurve::SectionToPointCoordsList aCoordList;
1224   std::deque<float> aChangedPos;
1225   CurveCreator_ICurve::SectionToPointList::const_iterator anIt = myDragPoints.begin(),
1226                                                           aLast = myDragPoints.end();
1227   for ( ; anIt != aLast; anIt++ ) {
1228     int aSectionId = anIt->first;
1229     int aPointId = anIt->second;
1230     aChangedPos = myCurve->getPoint( aSectionId, aPointId );
1231     if ( aChangedPos.size() < 2 )
1232       continue;
1233     aChangedPos[0] = aChangedPos[0] - aXDelta;
1234     aChangedPos[1] = aChangedPos[1] - anYDelta;
1235     
1236     aCoordList.push_back(
1237       std::make_pair(std::make_pair( aSectionId, aPointId ), 
1238                      aChangedPos ));
1239   }
1240   myCurve->setSeveralPoints( aCoordList );
1241
1242   myDragged = true;
1243   finishCurveModification( myDragPoints );
1244 }
1245
1246 void CurveCreator_Widget::updateLocalPointView()
1247 {
1248   if ( myDragStarted )
1249     return;
1250   Handle(AIS_InteractiveContext) aContext = getAISContext();
1251   if ( aContext.IsNull() )
1252     return;
1253
1254   CurveCreator_Utils::getSelectedPoints( aContext, myCurve, myLocalPoints );
1255   int aNbPoints = myLocalPoints.size();
1256   bool isRowLimit = aNbPoints > myLocalPointRowLimit;
1257   myLocalPointView->setVisible( !isRowLimit );
1258
1259   if ( !isRowLimit ) {
1260     bool isBlocked = myLocalPointView->blockSignals(true);
1261     myLocalPointView->setRowCount( 0 );
1262     CurveCreator_ICurve::SectionToPointList::const_iterator anIt = myLocalPoints.begin(),
1263                                                             aLast = myLocalPoints.end();
1264     for ( ; anIt != aLast; anIt++ )
1265       myLocalPointView->addLocalPointToTable( *anIt );
1266
1267     myLocalPointView->blockSignals( isBlocked );
1268   }
1269 }
1270
1271 /**
1272  * 
1273  */
1274 void CurveCreator_Widget::setLocalPointContext( const bool theOpen, const bool isUpdateTable )
1275 {
1276   CurveCreator_Utils::setLocalPointContext( getAISContext(), theOpen );
1277   if ( !theOpen && isUpdateTable )
1278     updateLocalPointView();
1279 }
1280
1281 /**
1282  * Set drag operation started. Save the position and a list of dragged points
1283  * \param theState the drag operation state: started/finished
1284  * \param thePoint the start drag position
1285  */
1286 void CurveCreator_Widget::setDragStarted( const bool theState, const QPoint& thePoint )
1287 {
1288   if ( theState ) {
1289     getSelectedPoints( myDragPoints );
1290     myDragStarted = myDragPoints.size();
1291     myDragStartPosition = thePoint;
1292     if ( myDragStarted ) {
1293       // change a viewer interaction style in order to avoid a select rectangle build
1294       myDragInteractionStyle = changeInteractionStyle( SUIT_ViewModel::KEY_FREE );
1295     }
1296   }
1297   else {
1298     if ( myDragStarted )
1299       changeInteractionStyle( myDragInteractionStyle );
1300     myDragStarted = false;
1301     myDragPoints.clear();
1302   }
1303   myDragged = false;
1304 }
1305
1306 void CurveCreator_Widget::getSelectedPoints( CurveCreator_ICurve::SectionToPointList& thePoints )
1307 {
1308   thePoints.clear();
1309   thePoints = myLocalPoints;
1310 }
1311
1312
1313 bool CurveCreator_Widget::isIntersectVertexToPoint( const TopoDS_Vertex& theVertex,
1314                                const CurveCreator_ICurve::SectionToPoint& theSToPoint )
1315 {
1316   bool isIntersect = false;
1317   if ( theVertex.IsNull() )
1318     return isIntersect;
1319
1320   gp_Pnt aSPoint;
1321   CurveCreator_UtilsICurve::getPoint( myCurve, theSToPoint.first, theSToPoint.second,
1322                                       aSPoint );
1323   gp_Pnt aVertexPoint = BRep_Tool::Pnt( theVertex );
1324   isIntersect = fabs( aVertexPoint.X() - aSPoint.X() ) < LOCAL_SELECTION_TOLERANCE &&
1325                 fabs( aVertexPoint.Y() - aSPoint.Y() ) < LOCAL_SELECTION_TOLERANCE;
1326
1327   return isIntersect;
1328 }
1329
1330
1331 void CurveCreator_Widget::setSelectedPoints( const CurveCreator_ICurve::SectionToPointList& thePoints )
1332 {
1333   if ( myDragStarted )
1334     return;
1335
1336   Handle(AIS_InteractiveContext) ic = getAISContext();
1337   if ( ic.IsNull() || !ic->HasOpenedContext() )
1338     return;
1339
1340   AIS_ListOfInteractive aListToSelect;
1341   AIS_ListOfInteractive aDisplayedList;
1342   ic->DisplayedObjects( aDisplayedList );
1343   ic->ClearSelected( Standard_False );
1344
1345   bool isSelectedVertex = false;
1346
1347   //ASL: std::vector<TopoDS_Vertex> aVetexVec;
1348   for ( AIS_ListIteratorOfListOfInteractive it( aDisplayedList ); it.More(); it.Next() )
1349   {
1350     Handle(AIS_InteractiveObject) anAIS = it.Value();
1351     if ( anAIS.IsNull() )
1352       continue;
1353     Handle(AIS_Shape) anAISShape = Handle(AIS_Shape)::DownCast( anAIS );
1354     if ( anAISShape.IsNull() )
1355       continue;
1356
1357
1358     /*ASL: const TopoDS_Shape& aShape = anAISShape->Shape();
1359     TopExp_Explorer aExpV( aShape, TopAbs_VERTEX);
1360     for ( ; aExpV.More(); aExpV.Next() )
1361     {
1362       const TopoDS_Vertex& aVertex = TopoDS::Vertex( aExpV.Current() );
1363       aVetexVec.push_back( aVertex );
1364     }*/
1365
1366
1367     //ASL: we convert list of point indices to list of points coordinates
1368     int aSize = thePoints.size();
1369     std::vector<gp_Pnt> aPntsToSelect( aSize );
1370
1371     CurveCreator_ICurve::SectionToPointList::const_iterator
1372       aPIt = thePoints.begin(), aPLast = thePoints.end();
1373     CurveCreator_ICurve::SectionToPoint aSToPoint;
1374     for( int i=0; aPIt != aPLast; aPIt++, i++ )
1375     {
1376       gp_Pnt aPntToSelect;
1377       CurveCreator_UtilsICurve::getPoint( myCurve, aPIt->first, aPIt->second, aPntToSelect );
1378       aPntsToSelect[i] = aPntToSelect;
1379     }
1380
1381
1382     //ASL: we switch off automatic highlight to improve performance of selection
1383     ic->SetAutomaticHilight( Standard_False );
1384
1385     Handle_SelectMgr_Selection aSelection = anAISShape->Selection( AIS_Shape::SelectionMode( TopAbs_VERTEX ) );
1386     for( aSelection->Init(); aSelection->More(); aSelection->Next() )
1387     {
1388       Handle_SelectBasics_SensitiveEntity aSenEntity = aSelection->Sensitive();
1389       Handle_Select3D_SensitivePoint aSenPnt = Handle_Select3D_SensitivePoint::DownCast( aSenEntity );
1390
1391       gp_Pnt anOwnerPnt = aSenPnt->Point();
1392       Handle_SelectMgr_EntityOwner anOwner = Handle_SelectMgr_EntityOwner::DownCast( aSenPnt->OwnerId() );
1393
1394
1395       CurveCreator_ICurve::SectionToPointList::const_iterator anIt = thePoints.begin(),
1396                                                                      aLast = thePoints.end();
1397       bool isFound = false;
1398       for( int i=0; i<aSize; i++ )
1399       {
1400         bool isIntersect = fabs( aPntsToSelect[i].X() - anOwnerPnt.X() ) < LOCAL_SELECTION_TOLERANCE &&
1401                            fabs( aPntsToSelect[i].Y() - anOwnerPnt.Y() ) < LOCAL_SELECTION_TOLERANCE;
1402         if( isIntersect )
1403         {
1404           ic->AddOrRemoveSelected( anOwner, Standard_False );
1405           break;
1406         }
1407       }
1408     }
1409   }
1410
1411   /*ASL: std::vector<TopoDS_Vertex>::const_iterator aVecIt = aVetexVec.begin(), aVecLast = aVetexVec.end(); 
1412   CurveCreator_ICurve::SectionToPointList::const_iterator anIt = thePoints.begin(),
1413                                                           aLast = thePoints.end();
1414   int aSize = aVetexVec.size();
1415   CurveCreator_ICurve::SectionToPoint aSToPoint;
1416   int anAddedSize = 0;
1417   for( ; anIt != aLast; anIt++ ) {
1418     aSToPoint = *anIt;
1419
1420     for ( aVecIt = aVetexVec.begin(); aVecIt != aVecLast; aVecIt++ )
1421     {
1422       TopoDS_Vertex aVertex = TopoDS::Vertex( *aVecIt );
1423       if ( isIntersectVertexToPoint( aVertex, aSToPoint ) ) {
1424         ic->AddOrRemoveSelected( aVertex, Standard_False );
1425         isSelectedVertex = true;
1426         anAddedSize++;
1427       }
1428     }
1429   }*/
1430
1431   //ASL: we switch on again automatic highlight (otherwise selection will not be shown)
1432   //     and call HilightPicked to draw selected owners
1433   ic->SetAutomaticHilight( Standard_True );
1434   ic->LocalContext()->HilightPicked( Standard_True );
1435
1436   //ic->UpdateCurrentViewer();
1437   if ( !isSelectedVertex )
1438     setObjectsSelected( aListToSelect );
1439   updateLocalPointView();
1440 }
1441
1442 /**
1443  * Get viewer information before perform the curve modification.
1444  * Take a list of selected cuve points an close local context.
1445  * The context should be closed because the curve presentation is
1446  * redisplayed and if it is not closed, when we close the local context
1447  * later, the presentation shown in the local context is disappeared.
1448  * \param thePoints an output list of curve selected points
1449  * \param theFillPoints a flag whether the selection list should be filled
1450  */
1451 void CurveCreator_Widget::startCurveModification(
1452                            CurveCreator_ICurve::SectionToPointList& thePoints,
1453                            const bool theFillPoints )
1454 {
1455   if ( theFillPoints ) {
1456     thePoints.clear();
1457     getSelectedPoints( thePoints );
1458   }
1459   setLocalPointContext( false );
1460 }
1461
1462 /**
1463  * Restore the viewer state after the curve modification is done.
1464  * Open local context and select given points inside it.
1465  * \param thePoints a list of curve selected points
1466  */
1467 void CurveCreator_Widget::finishCurveModification(
1468                            const CurveCreator_ICurve::SectionToPointList& thePoints )
1469 {
1470   if ( getActionMode() == ModificationMode )
1471     setLocalPointContext( true );
1472   setSelectedPoints( thePoints );
1473   updateUndoRedo();
1474 }
1475
1476 /**
1477  * Returns a point index in the model curve by the point coordinates in the viewer
1478  * \param theX the X coordinate of the point
1479  * \param theY the Y coordinate of the point
1480  */
1481 int CurveCreator_Widget::findLocalPointIndex( int theSectionId, float theX, float theY )
1482 {
1483   return CurveCreator_UtilsICurve::findLocalPointIndex( myCurve, theSectionId, theX, theY );
1484 }
1485
1486 void CurveCreator_Widget::findSectionsToPoints( const double theX, const double theY,
1487                                  CurveCreator_ICurve::SectionToPointList& thePoints )
1488 {
1489   return CurveCreator_UtilsICurve::findSectionsToPoints( myCurve, theX, theY, thePoints );
1490 }
1491
1492 void CurveCreator_Widget::convert( const CurveCreator_ICurve::SectionToPointList& thePoints,
1493                                    QMap<int, QList<int> >& theConvPoints )
1494 {
1495   return CurveCreator_UtilsICurve::convert( thePoints, theConvPoints );
1496 }
1497
1498 /**
1499  * Returns whethe the container has the value
1500  * \param theList a container of values
1501  * \param theValue a value
1502  */
1503 bool CurveCreator_Widget::contains( const CurveCreator_ICurve::SectionToPointList& theList,
1504                                     const CurveCreator_ICurve::SectionToPoint& theValue ) const
1505 {
1506   return CurveCreator_UtilsICurve::contains( theList, theValue );
1507 }