Salome HOME
[EDF30399] : Expose replay-dir parameter to define directory holding scenarii in...
[modules/yacs.git] / src / hmi / guiObservers.cxx
index 4888242c49bb005ffcea39da991d46cd8242443e..3797b1c872b78d101d1710150c7152c6412d57c6 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright (C) 2006-2014  CEA/DEN, EDF R&D
+// Copyright (C) 2006-2024  CEA, EDF
 //
 // This library is free software; you can redistribute it and/or
 // modify it under the terms of the GNU Lesser General Public
@@ -45,6 +45,7 @@
 #include "OutputPort.hxx"
 #include "InputDataStreamPort.hxx"
 #include "OutputDataStreamPort.hxx"
+#include "SalomeHPContainer.hxx"
 #include "SalomeContainer.hxx"
 #include "SalomeComponent.hxx"
 #include "ComponentDefinition.hxx"
@@ -276,7 +277,7 @@ bool Subject::destroy(Subject *son)
           startnode = proc->getChildName(sclink->getSubjectOutNode()->getNode());
           endnode = proc->getChildName(sclink->getSubjectInNode()->getNode());
         }
-      else if (SubjectContainer* scont = dynamic_cast<SubjectContainer*>(son))
+      else if (SubjectContainerBase* scont = dynamic_cast<SubjectContainerBase*>(son))
         {
           if(scont->getName() == "DefaultContainer")
             {
@@ -527,8 +528,8 @@ SubjectNode::~SubjectNode()
     try
       {
         // Remove child except if it's the splitter node of a ForEachLoop
-        if (dynamic_cast<ForEachLoop*>(father) == NULL ||
-            getName() != ForEachLoop::NAME_OF_SPLITTERNODE)
+        if (dynamic_cast<ForEachLoopGen*>(father) == NULL ||
+            getName() != ForEachLoopGen::NAME_OF_SPLITTERNODE)
           {
             father->edRemoveChild(_node);
           }
@@ -621,7 +622,7 @@ void SubjectNode::registerUndoDestroy()
   Bloc *undoBloc = new Bloc(blocName.str());
   undoProc->edAddChild(undoBloc);
   ComposedNode *newFather = undoBloc;
-  Node *clone = _node->clone(0);
+  Node *clone = _node->cloneWithoutCompAndContDeepCpy(0);
   newFather->edAddChild(clone);
 
   // --- register a CommandCopyNode from undoProc
@@ -823,6 +824,12 @@ bool SubjectNode::copy(Subject* parent)
   YASSERT(cnp);
   Proc *proc = GuiContext::getCurrent()->getProc();
   Proc *fromproc=_node->getProc();
+  if(proc != fromproc)
+    {
+      GuiContext::getCurrent()->_lastErrorMessage = "It is not possible to paste an object from one schema to another.";
+      DEBTRACE(GuiContext::getCurrent()->_lastErrorMessage);
+      return false;
+    }
 
   string position = "";
   if (fromproc != dynamic_cast<Proc*>(_node))
@@ -901,7 +908,7 @@ void SubjectNode::saveLinks()
       Node* n2=_node;
       DEBTRACE(n1->getName()<< " " << n2->getName());
     }
-  std::set<InGate *>::const_iterator iti;
+  std::list<InGate *>::const_iterator iti;
   for(iti=singate.begin();iti != singate.end();iti++)
     {
       Node* n1=_node;
@@ -1075,7 +1082,7 @@ void SubjectNode::restoreLinks()
         }
     }
 
-  std::set<InGate *>::const_iterator it2;
+  std::list<InGate *>::const_iterator it2;
   for(it2=singate.begin();it2 != singate.end();it2++)
     {
       Node* n1=_node;
@@ -1438,7 +1445,7 @@ SubjectNode *SubjectComposedNode::addSubjectNode(YACS::ENGINE::Node * node,
       son = new SubjectSwitch(dynamic_cast<YACS::ENGINE::Switch*>(node), this);
       break;
     case FOREACHLOOP:
-      son = new SubjectForEachLoop(dynamic_cast<YACS::ENGINE::ForEachLoop*>(node), this);
+      son = new SubjectForEachLoop(dynamic_cast<YACS::ENGINE::ForEachLoopGen*>(node), this);
       break;
     case OPTIMIZERLOOP:
       son = new SubjectOptimizerLoop(dynamic_cast<YACS::ENGINE::OptimizerLoop*>(node), this);
@@ -1468,9 +1475,9 @@ void SubjectComposedNode::completeChildrenSubjectList(SubjectNode *son)
 void SubjectComposedNode::loadChildren()
 {
   list<Node *> setOfNode= _composedNode->edGetDirectDescendants();
-  if (ForEachLoop *feloop = dynamic_cast<ForEachLoop*>(_composedNode))
+  if (ForEachLoopGen *feloop = dynamic_cast<ForEachLoopGen*>(_composedNode))
     {
-      Node *node2Insert=feloop->getChildByName(ForEachLoop::NAME_OF_SPLITTERNODE);
+      Node *node2Insert=feloop->getChildByName(ForEachLoopGen::NAME_OF_SPLITTERNODE);
       if(find(setOfNode.begin(),setOfNode.end(),node2Insert)==setOfNode.end())
         setOfNode.push_back(node2Insert);
     }
@@ -1648,8 +1655,8 @@ void SubjectComposedNode::loadLinks()
     {
       SubjectNode* sno = GuiContext::getCurrent()->_mapOfSubjectNode[*itn];
       OutGate* outgate = (*itn)->getOutGate();
-      std::set<InGate*> setIngate = outgate->edSetInGate();
-      std::set<InGate*>::const_iterator itg;
+      std::list<InGate*> setIngate = outgate->edSetInGate();
+      std::list<InGate*>::const_iterator itg;
       for(itg = setIngate.begin(); itg != setIngate.end(); ++itg)
         {
           Node* inNode = (*itg)->getNode();
@@ -1890,13 +1897,10 @@ void SubjectProc::loadComponents()
 void SubjectProc::loadContainers()
 {
   Proc* aProc = GuiContext::getCurrent()->getProc();
-  for (map<string, Container*>::const_iterator itCont = aProc->containerMap.begin();
-       itCont != aProc->containerMap.end(); ++itCont)
-    if ( GuiContext::getCurrent()->_mapOfSubjectContainer.find((*itCont).second)
-         ==
-         GuiContext::getCurrent()->_mapOfSubjectContainer.end() )
+  for (map<string, Container*>::const_iterator itCont = aProc->containerMap.begin(); itCont != aProc->containerMap.end(); ++itCont)
+    if ( GuiContext::getCurrent()->_mapOfSubjectContainer.find((*itCont).second) == GuiContext::getCurrent()->_mapOfSubjectContainer.end() )
       // engine object for container already exists => add only a subject for it
-      addSubjectContainer((*itCont).second, (*itCont).second->getName());
+      addSubjectContainer((*itCont).second,(*itCont).second->getName());
 }
 
 SubjectComponent* SubjectProc::addComponent(std::string compoName, std::string containerName)
@@ -1912,12 +1916,12 @@ SubjectComponent* SubjectProc::addComponent(std::string compoName, std::string c
   return 0;
 }
 
-SubjectContainerSubjectProc::addContainer(std::string name, std::string ref)
+SubjectContainerBase *SubjectProc::addContainer(std::string name, std::string ref)
 {
   DEBTRACE("SubjectProc::addContainer " << name << " " << ref);
   if (! GuiContext::getCurrent()->getProc()->containerMap.count(name))
     {
-      CommandAddContainer *command = new CommandAddContainer(name,ref);
+      CommandAddContainer *command(new CommandAddContainer(name,ref));
       if (command->execute())
         {
           GuiContext::getCurrent()->getInvoc()->add(command);
@@ -1930,6 +1934,24 @@ SubjectContainer* SubjectProc::addContainer(std::string name, std::string ref)
   return 0;
 }
 
+SubjectContainerBase* SubjectProc::addHPContainer(std::string name, std::string ref)
+{
+  DEBTRACE("SubjectProc::addContainer " << name << " " << ref);
+  if (! GuiContext::getCurrent()->getProc()->containerMap.count(name))
+    {
+      CommandAddHPContainer *command(new CommandAddHPContainer(name,ref));
+      if (command->execute())
+        {
+          GuiContext::getCurrent()->getInvoc()->add(command);
+          return command->getSubjectContainer();
+        }
+      else
+        delete command;
+    }
+  else GuiContext::getCurrent()->_lastErrorMessage = "There is already a container with that name";
+  return 0;
+}
+
 bool SubjectProc::addDataType(YACS::ENGINE::Catalog* catalog, std::string typeName)
 {
   DEBTRACE("SubjectProc::addDataType " << typeName);
@@ -1954,13 +1976,12 @@ SubjectComponent* SubjectProc::addSubjectComponent(YACS::ENGINE::ComponentInstan
   return son;
 }
 
-SubjectContainer* SubjectProc::addSubjectContainer(YACS::ENGINE::Container* cont,
-                                                   std::string name)
+SubjectContainerBase *SubjectProc::addSubjectContainer(YACS::ENGINE::Container *cont, std::string name)
 {
   DEBTRACE("SubjectProc::addSubjectContainer " << name);
-  SubjectContainer *son = new SubjectContainer(cont, this);
+  SubjectContainerBase *son(SubjectContainerBase::New(cont,this));
   // In edition mode do not clone containers
-  cont->attachOnCloning();
+  // cont->attachOnCloning(); // agy : do not use _attachOnCloning attribute in edition mode. This attribute should be used now at runtime.
   GuiContext::getCurrent()->_mapOfSubjectContainer[cont] = son;
   update(ADD, CONTAINER, son);
   return son;
@@ -2025,7 +2046,7 @@ void SubjectProc::removeSubjectDataType(std::string typeName)
   aTypeCode->decrRef();
 }
 
-void SubjectProc::removeSubjectContainer(SubjectContainer* scont)
+void SubjectProc::removeSubjectContainer(SubjectContainerBase* scont)
 {
   YASSERT(GuiContext::getCurrent()->_mapOfSubjectContainer.count(scont->getContainer()));
   erase(scont); // do all the necessary updates
@@ -2302,7 +2323,7 @@ bool SubjectInlineNode::setExecutionMode(const std::string& mode)
   return false;
 }
 
-bool SubjectInlineNode::setContainer(SubjectContainerscont)
+bool SubjectInlineNode::setContainer(SubjectContainerBase *scont)
 {
   DEBTRACE("SubjectInlineNode::setContainer ");
   Proc *proc = GuiContext::getCurrent()->getProc();
@@ -3373,12 +3394,16 @@ bool SubjectDynParaLoop::hasValue()
 
 std::string SubjectDynParaLoop::getValue()
 {
-  return _dynParaLoop->edGetNbOfBranchesPort()->getAsString();
+  InputPort *port(_dynParaLoop->edGetNbOfBranchesPort());
+  if(port)
+    return port->getAsString();
+  else
+    return std::string();
 }
 
 // ----------------------------------------------------------------------------
 
-SubjectForEachLoop::SubjectForEachLoop(YACS::ENGINE::ForEachLoop *forEachLoop, Subject *parent)
+SubjectForEachLoop::SubjectForEachLoop(YACS::ENGINE::ForEachLoopGen *forEachLoop, Subject *parent)
   : SubjectDynParaLoop(forEachLoop, parent), _forEachLoop(forEachLoop)
 {
   _splitter = 0;
@@ -3495,7 +3520,6 @@ SubjectDataPort::~SubjectDataPort()
   if (isDestructible())
     {
       Node* node = _dataPort->getNode();
-      YASSERT(node);
       ElementaryNode * father = dynamic_cast<ElementaryNode*>(node);
       if (father)
         {
@@ -3720,7 +3744,7 @@ SubjectInputPort::SubjectInputPort(YACS::ENGINE::InputPort *port, Subject *paren
     {
       if (_inputPort->getName() == "select") _destructible = false;
     }
-  else if (ForEachLoop* foreach = dynamic_cast<ForEachLoop*>(node))
+  else if (ForEachLoopGen* foreach = dynamic_cast<ForEachLoopGen*>(node))
     {
       if (_inputPort->getName() == "nbBranches") _destructible = false;
     }
@@ -4236,7 +4260,7 @@ void SubjectComponent::localclean(Command *command)
       
     Container* container = _compoInst->getContainer();
     if (!container) return;
-    SubjectContainer *subContainer;
+    SubjectContainerBase *subContainer(0);
     YASSERT(GuiContext::getCurrent()->_mapOfSubjectContainer.count(container));
     subContainer = GuiContext::getCurrent()->_mapOfSubjectContainer[container];
     subContainer->removeSubComponentFromSet(this);
@@ -4269,7 +4293,7 @@ void SubjectComponent::setContainer()
   Container* container = _compoInst->getContainer();
   if (container)
     {
-      SubjectContainer *subContainer;
+      SubjectContainerBase *subContainer;
       if (GuiContext::getCurrent()->_mapOfSubjectContainer.count(container))
         subContainer = GuiContext::getCurrent()->_mapOfSubjectContainer[container];
       else
@@ -4284,7 +4308,7 @@ void SubjectComponent::setContainer()
     }
 }
 
-bool SubjectComponent::associateToContainer(SubjectContainersubcont)
+bool SubjectComponent::associateToContainer(SubjectContainerBase *subcont)
 {
   DEBTRACE("SubjectComponent::associateToContainer " << getName() << " " << subcont->getName());
   CommandAssociateComponentToContainer *command =
@@ -4375,16 +4399,25 @@ std::map<std::string, std::string> SubjectComponent::getProperties()
 
 // ----------------------------------------------------------------------------
 
-SubjectContainer::SubjectContainer(YACS::ENGINE::Container* container, Subject *parent)
-  : Subject(parent), _container(container)
+SubjectContainerBase *SubjectContainerBase::New(YACS::ENGINE::Container* container, Subject *parent)
+{
+  if(!container)
+    return 0;
+  if(!dynamic_cast<YACS::ENGINE::HomogeneousPoolContainer *>(container))
+    return new SubjectContainer(container,parent);
+  else
+    return new SubjectHPContainer(dynamic_cast<YACS::ENGINE::HomogeneousPoolContainer *>(container),parent);
+}
+
+SubjectContainerBase::SubjectContainerBase(YACS::ENGINE::Container* container, Subject *parent):Subject(parent), _container(container)
 {
   _subComponentSet.clear();
   _subReferenceMap.clear();
 }
 
-SubjectContainer::~SubjectContainer()
+SubjectContainerBase::~SubjectContainerBase()
 {
-  DEBTRACE("SubjectContainer::~SubjectContainer");
+  DEBTRACE("SubjectContainerBase::~SubjectContainerBase");
   Proc* aProc = GuiContext::getCurrent()->getProc();
   if ( aProc )
   {
@@ -4403,24 +4436,25 @@ SubjectContainer::~SubjectContainer()
   }
 }
 
-std::map<std::string, std::string> SubjectContainer::getProperties()
+std::map<std::string, std::string> SubjectContainerBase::getProperties()
 {
   return _container->getProperties();
 }
 
-bool SubjectContainer::setProperties(std::map<std::string, std::string> properties)
+bool SubjectContainerBase::setProperties(std::map<std::string, std::string> properties)
 {
-  CommandSetContainerProperties *command = new CommandSetContainerProperties(getName(), properties);
+  CommandSetContainerProperties *command(new CommandSetContainerProperties(getName(), properties));
   if (command->execute())
     {
       GuiContext::getCurrent()->getInvoc()->add(command);
       return true;
     }
-  else delete command;
+  else
+    delete command;
   return false;
 }
 
-bool SubjectContainer::setName(std::string name)
+bool SubjectContainerBase::setName(std::string name)
 {
   DEBTRACE("SubjectContainer::setName " << name);
   if (name == getName())
@@ -4435,7 +4469,7 @@ bool SubjectContainer::setName(std::string name)
   return false;
 }
 
-SubjectReference* SubjectContainer::attachComponent(SubjectComponent* component)
+SubjectReference* SubjectContainerBase::attachComponent(SubjectComponent* component)
 {
   DEBTRACE("SubjectContainer::attachComponent");
   SubjectReference *son = new SubjectReference(component, this);
@@ -4445,18 +4479,18 @@ SubjectReference* SubjectContainer::attachComponent(SubjectComponent* component)
   return son;
 }
 
-void SubjectContainer::detachComponent(SubjectComponent* component)
+void SubjectContainerBase::detachComponent(SubjectComponent* component)
 {
   DEBTRACE("SubjectContainer::detachComponent");
   YASSERT(_subReferenceMap.count(component));
   SubjectReference *reference = _subReferenceMap[component];
-  update(REMOVECHILDREF, COMPONENT, reference);
+  update(REMOVECHILDREF, PYTHONNODE, reference);
   _subComponentSet.erase(component);
   _subReferenceMap.erase(component);
   erase(reference);
 }
 
-void SubjectContainer::moveComponent(SubjectReference* reference)
+void SubjectContainerBase::moveComponent(SubjectReference* reference)
 {
   DEBTRACE("SubjectContainer::moveComponent");
   SubjectContainer* oldcont = dynamic_cast<SubjectContainer*>(reference->getParent());
@@ -4470,14 +4504,14 @@ void SubjectContainer::moveComponent(SubjectReference* reference)
   update(PASTE, COMPONENT, reference);
 }
 
-void SubjectContainer::removeSubComponentFromSet(SubjectComponent *component)
+void SubjectContainerBase::removeSubComponentFromSet(SubjectComponent *component)
 {
   DEBTRACE("SubjectContainer::removeSubComponentFromSet");
   _subComponentSet.erase(component);
   _subReferenceMap.erase(component);
 }
 
-void SubjectContainer::notifyComponentsChange(GuiEvent event, int type, Subject* son)
+void SubjectContainerBase::notifyComponentsChange(GuiEvent event, int type, Subject* son)
 {
   DEBTRACE("SubjectContainer::notifyComponentsChange");
   set<SubjectComponent*>::iterator it = _subComponentSet.begin();
@@ -4488,8 +4522,7 @@ void SubjectContainer::notifyComponentsChange(GuiEvent event, int type, Subject*
     }
 }
 
-
-void SubjectContainer::clean(Command *command)
+void SubjectContainerBase::clean(Command *command)
 {
   if (_askRegisterUndo)
     {
@@ -4500,9 +4533,9 @@ void SubjectContainer::clean(Command *command)
   Subject::clean(command);
 }
 
-void SubjectContainer::localclean(Command *command)
+void SubjectContainerBase::localclean(Command *command)
 {
-  DEBTRACE("SubjectContainer::localClean ");
+  DEBTRACE("SubjectContainerBase::localClean ");
   Proc* aProc = GuiContext::getCurrent()->getProc();
   if ( aProc )
   {
@@ -4526,14 +4559,15 @@ void SubjectContainer::localclean(Command *command)
   }
 }
 
-std::string SubjectContainer::getName()
+std::string SubjectContainerBase::getName()
 {
   return _container->getName();
 }
 
-YACS::ENGINE::Container* SubjectContainer::getContainer() const
+// ----------------------------------------------------------------------------
+
+SubjectContainer::SubjectContainer(YACS::ENGINE::Container *container, Subject *parent):SubjectContainerBase(container,parent)
 {
-  return _container;
 }
 
 void SubjectContainer::registerUndoDestroy()
@@ -4545,6 +4579,32 @@ void SubjectContainer::registerUndoDestroy()
 
 // ----------------------------------------------------------------------------
 
+SubjectHPContainer::SubjectHPContainer(YACS::ENGINE::HomogeneousPoolContainer *container, Subject *parent):SubjectContainerBase(container,parent)
+{
+}
+
+YACS::ENGINE::Container *SubjectHPContainer::getContainer() const
+{
+  if(!_container)
+    return 0;
+  else
+    {
+      YACS::ENGINE::HomogeneousPoolContainer *ret(dynamic_cast<YACS::ENGINE::HomogeneousPoolContainer *>(_container));
+      if(!ret)
+        throw Exception("Invalid container type in SubjectHPContainer !");
+      return ret;
+    }
+}
+
+void SubjectHPContainer::registerUndoDestroy()
+{
+  DEBTRACE("SubjectHPContainer::registerUndoDestroy");
+  Command *command = new CommandAddHPContainer(getName(),"");
+  GuiContext::getCurrent()->getInvoc()->add(command);
+}
+
+// ----------------------------------------------------------------------------
+
 SubjectDataType::SubjectDataType(YACS::ENGINE::TypeCode *typeCode, Subject *parent, std::string alias)
   : Subject(parent), _typeCode(typeCode), _alias(alias)
 {