Salome HOME
335d05063864f6cd5d7e766bc273024b5be38768
[modules/superv.git] / src / SUPERVGUI / SUPERVGUI_Port.cxx
1 //  SUPERV SUPERVGUI : GUI for Supervisor component
2 //
3 //  Copyright (C) 2003  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 //  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS 
5 // 
6 //  This library is free software; you can redistribute it and/or 
7 //  modify it under the terms of the GNU Lesser General Public 
8 //  License as published by the Free Software Foundation; either 
9 //  version 2.1 of the License. 
10 // 
11 //  This library is distributed in the hope that it will be useful, 
12 //  but WITHOUT ANY WARRANTY; without even the implied warranty of 
13 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
14 //  Lesser General Public License for more details. 
15 // 
16 //  You should have received a copy of the GNU Lesser General Public 
17 //  License along with this library; if not, write to the Free Software 
18 //  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA 
19 // 
20 //  See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org 
21 //
22 //
23 //
24 //  File   : SUPERVGUI_Port.cxx
25 //  Author : Francis KLOSS
26 //  Module : SUPERV
27
28 using namespace std;
29 #include "SUPERVGUI_Port.h"
30 #include "SUPERVGUI_Def.h"
31 #include "SUPERVGUI_Main.h"
32 #include "SUPERVGUI_Link.h"
33 #include "SUPERVGUI.h"
34 #include "SUPERVGUI_BrowseNodeDlg.h"
35 #include "QAD_LeftFrame.h"
36 #include "QAD_ObjectBrowser.h"
37 #include <qpoint.h>
38 #include "SUPERVGUI_GraphNode.h"
39
40
41 // Port en general
42 // ---------------
43
44 SUPERVGUI_Port::SUPERVGUI_Port(QWidget* parent, SUPERVGUI_Main* m, SUPERV_Port p):
45     SUPERVGUI_Label(parent, PORT_WIDTH, PORT_HEIGHT, "", QLabel::AlignLeft | QLabel::AlignVCenter),
46     main(m),
47     port(p)
48 {
49   Trace("SUPERVGUI_Port::SUPERVGUI_Port");
50   myName = port->Name();
51   QString aName(port->Name());
52   aName += (port->IsInput())? "Input":"Output";
53   setName(aName);
54
55   if (myName.compare(OUTVOID) == 0)
56     setAlignment(QLabel::AlignRight | QLabel::AlignVCenter);
57
58   if (port->IsParam() || port->IsInLine())
59     setText(myName + "=" +  port->ToString());
60   else
61     setText(myName);
62     
63   setLineWidth(1);
64   setMidLineWidth(2);
65   setFrameShape(QLabel::Box);
66   setFrameShadow(QLabel::Plain);
67
68   popup = new QPopupMenu(this);
69   if (main->isEditable()) {
70     mySketchItem = popup->insertItem(tr("MSG_SKETCH_LINK"), this, SLOT(sketchLink()));
71     popup->insertSeparator();
72   }
73   if (port->IsInLine()) {
74     myDelItem = popup->insertItem(tr("ITM_DEL_PORT"), this, SLOT(deletePort()));    
75   }
76   connect(this, SIGNAL(MousePress(QMouseEvent*)), this, SLOT(showPopup(QMouseEvent*)));  
77   connect(this, SIGNAL(MouseRelease(QMouseEvent*)), this, SLOT(endSketch()));
78 }
79
80 SUPERVGUI_Port::~SUPERVGUI_Port() {
81     Trace("SUPERVGUI_Port::~SUPERVGUI_Port")
82 }
83
84 SUPERV_Port SUPERVGUI_Port::getPort() {
85     Trace("SUPERVGUI_Port::getPort")
86     return(port);
87 }
88
89 void SUPERVGUI_Port::showPopup(QMouseEvent* e) {
90   Trace("SUPERVGUI_Port::showPopup");
91   if (e->button() != RightButton) return;
92   if (main->getDataflow()->IsExecuting()) 
93     popup->setItemEnabled(mySketchItem, false);
94   else  
95     if (!port->IsInput() //output port
96         || 
97         port->IsInput() && (!port->IsLinked() //not linked input port
98                             ||
99                             port->Kind() == SUPERV::EndSwitchParameter)) { //input port of EndSwitch node
100       popup->setItemEnabled(mySketchItem, true);
101     }
102       
103   main->showPopup(popup, e);
104 }
105
106
107 QPoint SUPERVGUI_Port::getConnectPnt() {
108   return QPoint(0,0);
109 }
110
111
112 void SUPERVGUI_Port::sync() {
113   if (port->IsParam() || port->IsInLine())
114     setText(myName + "=" +  port->ToString());
115   else
116     setText(myName);
117
118 }
119
120
121 void SUPERVGUI_Port::sketchLink() {
122   main->getGraph()->sketchBegin(this);
123   if (port->IsInput()) 
124     setLineWidth(1);
125 }
126
127 void SUPERVGUI_Port::endSketch() {
128   main->getGraph()->sketchEnd(this);
129   if (port->IsInput() && port->IsLinked()) 
130     setLineWidth(1);
131 }
132
133
134 void SUPERVGUI_Port::deletePort() {
135   SUPERVGUI_GraphNode*  aNode = (SUPERVGUI_GraphNode* )main->getGraph()->child(port->Node()->Name(), "SUPERVGUI_GraphNode");
136   if (aNode) {
137     aNode->deletePort(this);
138   }
139 }
140
141
142
143
144 //***********************************************************
145 // Port d'entree
146 // -------------
147
148 SUPERVGUI_PortIn::SUPERVGUI_PortIn(QWidget* parent, SUPERVGUI_Main* m, SUPERV_Port p)
149   : SUPERVGUI_Port(parent, m, p), myDlg( 0 )
150 {
151   Trace("SUPERVGUI_PortIn::SUPERVGUI_PortIn");
152   myLinkPrs = 0;
153   //    link->move(0, height()/2-POINT_SIZE_HALF);
154
155   bool editing = port->IsInput() && ( !port->IsLinked() ); //main->isEditable();
156 //  bool linked  = port->IsLinked();
157 //  bool b = (!linked) && editing;
158   if ((!port->IsGate())  && editing ) {
159     psc = popup->insertItem(tr("MSG_SETVALUE"),      this, SLOT(setInput()));
160   }
161   browser = popup->insertItem(tr("MSG_BROWSE"),         this, SLOT(browse()));
162 }
163
164 SUPERVGUI_PortIn::~SUPERVGUI_PortIn() {
165   Trace("SUPERVGUI_PortIn::~SUPERVGUI_PortIn");
166 }
167
168
169 bool SUPERVGUI_PortIn::eventFilter( QObject* o, QEvent* e )
170 {
171   if ( o == myDlg && e->type() == QEvent::Close )
172     myDlg = 0;
173   return SUPERVGUI_Port::eventFilter( o, e );
174 }
175
176
177 void SUPERVGUI_PortIn::deleteLinks() {
178   if (myLinkPrs) {
179     disconnect(myLinkPrs, 0, this, 0);
180     main->getGraph()->deleteLink(myLinkPrs);
181     myLinkPrs = 0;
182   }
183 }
184
185
186 void SUPERVGUI_PortIn::sync() {
187   SUPERVGUI_Port::sync();
188   if (port->IsLinked()) {
189     popup->setItemEnabled(browser, port->State() == SUPERV_Ready);
190   } else {
191     if (port->HasInput()) {
192       popup->setItemEnabled(browser, true);
193       setLineWidth(2);
194     } else {
195       popup->setItemEnabled(browser, false);
196       setLineWidth(1);
197     }
198   }
199 }
200
201 void SUPERVGUI_PortIn::setValue(const char* d) {
202     Trace("SUPERVGUI_PortIn::setValue")
203     if (port->Input(Supervision.getEngine()->StringValue(d))) {
204         sync();
205     } else {
206         QMessageBox::warning(QAD_Application::getDesktop(), tr("ERROR"), tr("MSG_CANT_SETVAL"));
207     };
208 }
209
210 void SUPERVGUI_PortIn::setInput() {
211     Trace("SUPERVGUI_PortIn::setInput");
212     if ( !myDlg ) {
213       myDlg = new SUPERVGUI_GetValueDlg(this);
214       myDlg->installEventFilter( this );
215     }
216     if ( !myDlg->isVisible() )
217       myDlg->show();
218     else {
219       myDlg->raise();
220       myDlg->setActiveWindow();
221       myDlg->setFocus();
222     }
223 }
224
225 void SUPERVGUI_PortIn::browse() {
226     Trace("SUPERVGUI_PortIn::browse")
227     QString mess(tr("MSG_IPORT_VAL"));
228     mess += port->ToString();
229     QMessageBox::information(QAD_Application::getDesktop(), tr("MSG_INFO"), mess);
230 }
231
232
233
234 /**
235  * Returns coordinates of connection point in content coordinates
236  */
237 QPoint SUPERVGUI_PortIn::getConnectPnt() {
238   // Parent widget is internal node frame
239   // parent of parent is node it self
240   QWidget* aNode = parentWidget()->parentWidget()->parentWidget();
241   QPoint aPnt(aNode->pos()); // position of the node
242
243   if (parentWidget()->isVisible()) {
244     aPnt += parentWidget()->parentWidget()->pos();
245     aPnt += parentWidget()->pos();
246     return QPoint(aPnt.x() + pos().x(), 
247                   aPnt.y() + (pos().y() + height()/2));
248   }
249   return QPoint(aPnt.x(), 
250                 aPnt.y() + (aNode->height()/2));
251 }
252
253 void SUPERVGUI_PortIn::setLinkPrs(SUPERVGUI_Link* theLink) {
254   myLinkPrs = theLink;
255   connect(myLinkPrs, SIGNAL(linkDeleted(SUPERVGUI_Link*)),
256           this, SLOT(onDeleteLink(SUPERVGUI_Link*)));
257   popup->setItemEnabled(mySketchItem, false);
258 }
259
260 void SUPERVGUI_PortIn::onDeleteLink(SUPERVGUI_Link*) {
261   disconnect(myLinkPrs, 0, this, 0);
262   myLinkPrs = 0;
263   popup->setItemEnabled(psc, true);
264   if (port->HasInput())
265     setLineWidth(2);
266   if (main->isEditable()) {
267     popup->setItemEnabled(mySketchItem, true);
268   } else {
269     popup->setItemEnabled(mySketchItem, false);
270   }
271 }
272
273
274
275 //***********************************************************
276 // Port de sortie
277 // --------------
278
279 SUPERVGUI_PortOut::SUPERVGUI_PortOut(QWidget* parent, SUPERVGUI_Main* m, SUPERV_Port p):
280     SUPERVGUI_Port(parent, m, p),
281     study(false)
282 {
283     Trace("SUPERVGUI_PortOut::SUPERVGUI_PortOut")
284       //    link->move(width()-POINT_SIZE, height()/2-POINT_SIZE_HALF);
285     myLinksList.setAutoDelete(false);
286     
287     if (!port->IsGate()) {
288       pls = popup->insertItem(tr("MSG_PUT_INSTUDY"), this, SLOT(toStudy()));
289     }
290     browser = popup->insertItem(tr("MSG_BROWSE"), this, SLOT(browse()));
291
292     if (!main->getDataflow()->IsReadOnly()) {
293       popup->setItemEnabled(mySketchItem, true);
294     } else {
295       popup->setItemEnabled(mySketchItem, false);
296     }
297 }
298
299 SUPERVGUI_PortOut::~SUPERVGUI_PortOut() {
300   Trace("SUPERVGUI_PortOut::~SUPERVGUI_PortOut");
301 }
302
303 void SUPERVGUI_PortOut::sync() {
304     Trace("SUPERVGUI_PortOut::sync")
305     SUPERVGUI_Port::sync();
306
307     bool ok = (port->State() == SUPERV_Ready);
308     popup->setItemEnabled(browser, ok);
309     if (study && ok) {
310       study = main->putDataStudy(port, STUDY_PORT_OUT);
311     }
312
313     if (study) {
314         setLineWidth(2);
315         popup->changeItem(pls, tr("MSG_NOT_INSTUDY"));
316     } else {
317         setLineWidth(1);
318         popup->changeItem(pls, tr("MSG_PUT_INSTUDY"));
319     }
320
321 }
322
323 void SUPERVGUI_PortOut::updateStudy() {
324   Trace("SUPERVGUI_PortOut::updateStudy")
325   SUPERVGUI_Node*  aNode = (SUPERVGUI_Node* )main->getGraph()->child(port->Node()->Name(), "SUPERVGUI_Node");
326   if (aNode)
327     ((SUPERVGUI_PortOut*)aNode->child(port->Name(), "SUPERVGUI_PortOut"))->study = study;
328   else
329     {
330       aNode = (SUPERVGUI_Node* )main->getArray()->child(port->Node()->Name(), "SUPERVGUI_Node");
331       if (aNode)
332         ((SUPERVGUI_PortOut*)aNode->child(port->Name(), "SUPERVGUI_PortOut"))->study = study;
333     }
334 }
335
336 void SUPERVGUI_PortOut::toStudy() {
337     Trace("SUPERVGUI_PortOut::toStudy")
338       if (!main->isFromStudy()) {
339         if (main->addStudy()) main->setAsFromStudy(true);
340       }
341     if (!main->getStudy()->getStudyDocument()->GetProperties()->IsLocked()) study = !study;
342     sync();
343 }
344
345 void SUPERVGUI_PortOut::browse() {
346     Trace("SUPERVGUI_PortOut::browse")
347     QString mess(tr("MSG_OPORT_VAL"));
348     mess += port->ToString();
349     QMessageBox::information(QAD_Application::getDesktop(), tr("MSG_INFO"), mess);
350 }
351
352
353 /**
354  * Returns coordinates of connection point in scroll view content coordinates
355  */
356 QPoint SUPERVGUI_PortOut::getConnectPnt() {
357   // Parent widget is internal node frame
358   // parent of parent is node it self
359   QWidget* aNode = parentWidget()->parentWidget()->parentWidget();
360   QPoint aPnt(aNode->pos()); // position of the node
361   if (parentWidget()->isVisible()) {
362     aPnt += parentWidget()->parentWidget()->pos();
363     aPnt += parentWidget()->pos();
364     return QPoint(aPnt.x() + pos().x() + width(), 
365                   aPnt.y() + (pos().y() + height()/2));
366   }
367   return QPoint(aPnt.x() + aNode-> width(),
368                 aPnt.y() + (aNode->height()/2));
369 }
370
371
372 void SUPERVGUI_PortOut::addLinkPrs(SUPERVGUI_Link* theLink) {
373   myLinksList.append(theLink);
374   connect(theLink, SIGNAL(linkDeleted(SUPERVGUI_Link*)),
375           this, SLOT(onDeleteLink(SUPERVGUI_Link*)));
376 }
377
378
379 void SUPERVGUI_PortOut::onDeleteLink(SUPERVGUI_Link* theLink) {
380   disconnect(theLink, 0, this, 0);
381   myLinksList.remove(theLink);
382 }
383
384
385 void SUPERVGUI_PortOut::deleteLinks() {
386   if (myLinksList.count() > 0) {
387     SUPERVGUI_Link* aLink;
388     while (aLink = myLinksList.last()) {
389       disconnect(aLink, 0, this, 0); 
390       myLinksList.remove(aLink);
391       main->getGraph()->deleteLink(aLink);
392     }
393   }
394 }
395
396
397
398 //***********************************************************
399 // Input Port of EndSwitch Node
400 // ----------------------------
401 SUPERVGUI_PortInESNode::SUPERVGUI_PortInESNode(QWidget* parent, SUPERVGUI_Main* m, SUPERV_Port p)
402   : SUPERVGUI_Port(parent, m, p), myDlg( 0 )
403 {
404   Trace("SUPERVGUI_PortInESNode::SUPERVGUI_PortInESNode");
405   myLinksList.setAutoDelete(false);
406
407   bool editing = port->IsInput() && ( !port->IsLinked() ); //main->isEditable();
408   if ((!port->IsGate())  && editing ) {
409     psc = popup->insertItem(tr("MSG_SETVALUE"),      this, SLOT(setInput()));
410   }
411   browser = popup->insertItem(tr("MSG_BROWSE"),         this, SLOT(browse()));
412 }
413
414 SUPERVGUI_PortInESNode::~SUPERVGUI_PortInESNode() {
415   Trace("SUPERVGUI_PortInESNode::~SUPERVGUI_PortInESNode");
416 }
417
418 bool SUPERVGUI_PortInESNode::eventFilter( QObject* o, QEvent* e ) {
419   if ( o == myDlg && e->type() == QEvent::Close )
420     myDlg = 0;
421   return SUPERVGUI_Port::eventFilter( o, e );
422 }
423
424 void SUPERVGUI_PortInESNode::sync() {
425   SUPERVGUI_Port::sync();
426   if (port->IsLinked()) {
427     popup->setItemEnabled(browser, port->State() == SUPERV_Ready);
428   } else {
429     if (port->HasInput()) {
430       popup->setItemEnabled(browser, true);
431       setLineWidth(2);
432     } else {
433       popup->setItemEnabled(browser, false);
434       setLineWidth(1);
435     }
436   }
437 }
438
439 void SUPERVGUI_PortInESNode::setValue(const char* d) {
440     Trace("SUPERVGUI_PortIn::setValue")
441     if (port->Input(Supervision.getEngine()->StringValue(d))) {
442         sync();
443     } else {
444         QMessageBox::warning(QAD_Application::getDesktop(), tr("ERROR"), tr("MSG_CANT_SETVAL"));
445     };
446 }
447
448 /**
449  * Returns coordinates of connection point in content coordinates
450  */
451 QPoint SUPERVGUI_PortInESNode::getConnectPnt() {
452   QWidget* aNode = parentWidget()->parentWidget()->parentWidget();
453   QPoint aPnt(aNode->pos());
454
455   if (parentWidget()->isVisible()) {
456     aPnt += parentWidget()->parentWidget()->pos();
457     aPnt += parentWidget()->pos();
458     return QPoint(aPnt.x() + pos().x(), 
459                   aPnt.y() + (pos().y() + height()/2));
460   }
461   return QPoint(aPnt.x(), 
462                 aPnt.y() + (aNode->height()/2));
463 }
464
465 void SUPERVGUI_PortInESNode::setLinkPrs(SUPERVGUI_Link* theLink) {
466   myLinksList.append(theLink);
467   connect(theLink, SIGNAL(linkDeleted(SUPERVGUI_Link*)),
468           this, SLOT(onDeleteLink(SUPERVGUI_Link*)));
469 }
470
471 void SUPERVGUI_PortInESNode::deleteLinks() {
472   if (myLinksList.count() > 0) {
473     SUPERVGUI_Link* aLink;
474     while (aLink = myLinksList.last()) {
475       disconnect(aLink, 0, this, 0); 
476       myLinksList.remove(aLink);
477       main->getGraph()->deleteLink(aLink);
478     }
479   }
480 }
481
482 void SUPERVGUI_PortInESNode::setInput() {
483     Trace("SUPERVGUI_PortInESNode::setInput");
484     if ( !myDlg ) {
485       myDlg = new SUPERVGUI_GetValueDlg(this);
486       myDlg->installEventFilter( this );
487     }
488     if ( !myDlg->isVisible() )
489       myDlg->show();
490     else {
491       myDlg->raise();
492       myDlg->setActiveWindow();
493       myDlg->setFocus();
494     }
495 }
496
497 void SUPERVGUI_PortInESNode::browse() {
498     Trace("SUPERVGUI_PortInESNode::browse")
499     QString mess(tr("MSG_IPORT_VAL"));
500     mess += port->ToString();
501     QMessageBox::information(QAD_Application::getDesktop(), tr("MSG_INFO"), mess);
502 }
503
504
505 void SUPERVGUI_PortInESNode::onDeleteLink(SUPERVGUI_Link* theLink) {
506   disconnect(theLink, 0, this, 0);
507   myLinksList.remove(theLink);
508   
509   if (myLinksList.count() == 0) {
510     popup->setItemEnabled(psc, true);
511   } else {
512     popup->setItemEnabled(psc, false);
513   }
514   
515   if (port->HasInput())
516     setLineWidth(2);    
517   
518   if (main->isEditable()) {
519     popup->setItemEnabled(mySketchItem, true);
520   } else {
521     popup->setItemEnabled(mySketchItem, false);
522   }
523 }
524