Xcos MVC: move ports get/set/update in a separate file 61/14961/4
Paul Bignier [Wed, 30 Jul 2014 08:17:43 +0000 (10:17 +0200)]
Change-Id: Ib17f3f2deb7922f059e86f7627ebaae6060d3e06

scilab/modules/scicos/Makefile.am
scilab/modules/scicos/Makefile.in
scilab/modules/scicos/src/c/scicos.vcxproj
scilab/modules/scicos/src/c/scicos.vcxproj.filters
scilab/modules/scicos/src/cpp/view_scilab/GraphicsAdapter.cpp
scilab/modules/scicos/src/cpp/view_scilab/ports_management.cpp [new file with mode: 0644]
scilab/modules/scicos/src/cpp/view_scilab/ports_management.hxx [new file with mode: 0644]

index 0fd4a6e..cd00a8e 100644 (file)
@@ -29,7 +29,8 @@ src/cpp/view_scilab/ModelAdapter.cpp \
 src/cpp/view_scilab/ParamsAdapter.cpp \
 src/cpp/view_scilab/ScsAdapter.cpp \
 src/cpp/view_scilab/StateAdapter.cpp \
-src/cpp/view_scilab/TextAdapter.cpp
+src/cpp/view_scilab/TextAdapter.cpp \
+src/cpp/view_scilab/ports_management.cpp
 
 
 SCICOS_C_SOURCES = \
index faa2faa..02db0b5 100644 (file)
@@ -216,6 +216,7 @@ am__libsciscicos_algo_la_SOURCES_DIST = src/c/noscicos/noscicos.c \
        src/cpp/view_scilab/ScsAdapter.cpp \
        src/cpp/view_scilab/StateAdapter.cpp \
        src/cpp/view_scilab/TextAdapter.cpp \
+       src/cpp/view_scilab/ports_management.cpp \
        src/c/scilab5_needed_stubs.c src/c/tree.c \
        src/c/scicos_malloc.c src/c/scicos_print.c src/c/import.c \
        src/c/scicos.c src/c/scicos_free.c src/c/sciblk2.c \
@@ -246,7 +247,8 @@ am__objects_2 = src/cpp/libsciscicos_algo_la-Controller.lo \
        src/cpp/view_scilab/libsciscicos_algo_la-ParamsAdapter.lo \
        src/cpp/view_scilab/libsciscicos_algo_la-ScsAdapter.lo \
        src/cpp/view_scilab/libsciscicos_algo_la-StateAdapter.lo \
-       src/cpp/view_scilab/libsciscicos_algo_la-TextAdapter.lo
+       src/cpp/view_scilab/libsciscicos_algo_la-TextAdapter.lo \
+       src/cpp/view_scilab/libsciscicos_algo_la-ports_management.lo
 am__objects_3 = src/c/libsciscicos_algo_la-scilab5_needed_stubs.lo \
        src/c/libsciscicos_algo_la-tree.lo \
        src/c/libsciscicos_algo_la-scicos_malloc.lo \
@@ -887,7 +889,8 @@ src/cpp/view_scilab/ModelAdapter.cpp \
 src/cpp/view_scilab/ParamsAdapter.cpp \
 src/cpp/view_scilab/ScsAdapter.cpp \
 src/cpp/view_scilab/StateAdapter.cpp \
-src/cpp/view_scilab/TextAdapter.cpp
+src/cpp/view_scilab/TextAdapter.cpp \
+src/cpp/view_scilab/ports_management.cpp
 
 SCICOS_C_SOURCES = \
 src/c/scilab5_needed_stubs.c \
@@ -1439,6 +1442,9 @@ src/cpp/view_scilab/libsciscicos_algo_la-StateAdapter.lo:  \
 src/cpp/view_scilab/libsciscicos_algo_la-TextAdapter.lo:  \
        src/cpp/view_scilab/$(am__dirstamp) \
        src/cpp/view_scilab/$(DEPDIR)/$(am__dirstamp)
+src/cpp/view_scilab/libsciscicos_algo_la-ports_management.lo:  \
+       src/cpp/view_scilab/$(am__dirstamp) \
+       src/cpp/view_scilab/$(DEPDIR)/$(am__dirstamp)
 src/c/$(am__dirstamp):
        @$(MKDIR_P) src/c
        @: > src/c/$(am__dirstamp)
@@ -1944,6 +1950,7 @@ distclean-compile:
 @AMDEP_TRUE@@am__include@ @am__quote@src/cpp/view_scilab/$(DEPDIR)/libsciscicos_algo_la-ScsAdapter.Plo@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@src/cpp/view_scilab/$(DEPDIR)/libsciscicos_algo_la-StateAdapter.Plo@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@src/cpp/view_scilab/$(DEPDIR)/libsciscicos_algo_la-TextAdapter.Plo@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@src/cpp/view_scilab/$(DEPDIR)/libsciscicos_algo_la-ports_management.Plo@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@src/scicos_sundials/src/cvode/$(DEPDIR)/libscisundials_la-cvode.Plo@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@src/scicos_sundials/src/cvode/$(DEPDIR)/libscisundials_la-cvode_dense.Plo@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@src/scicos_sundials/src/cvode/$(DEPDIR)/libscisundials_la-cvode_direct.Plo@am__quote@
@@ -2628,6 +2635,13 @@ src/cpp/view_scilab/libsciscicos_algo_la-TextAdapter.lo: src/cpp/view_scilab/Tex
 @AMDEP_TRUE@@am__fastdepCXX_FALSE@     DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
 @am__fastdepCXX_FALSE@ $(AM_V_CXX@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libsciscicos_algo_la_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o src/cpp/view_scilab/libsciscicos_algo_la-TextAdapter.lo `test -f 'src/cpp/view_scilab/TextAdapter.cpp' || echo '$(srcdir)/'`src/cpp/view_scilab/TextAdapter.cpp
 
+src/cpp/view_scilab/libsciscicos_algo_la-ports_management.lo: src/cpp/view_scilab/ports_management.cpp
+@am__fastdepCXX_TRUE@  $(AM_V_CXX)$(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libsciscicos_algo_la_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT src/cpp/view_scilab/libsciscicos_algo_la-ports_management.lo -MD -MP -MF src/cpp/view_scilab/$(DEPDIR)/libsciscicos_algo_la-ports_management.Tpo -c -o src/cpp/view_scilab/libsciscicos_algo_la-ports_management.lo `test -f 'src/cpp/view_scilab/ports_management.cpp' || echo '$(srcdir)/'`src/cpp/view_scilab/ports_management.cpp
+@am__fastdepCXX_TRUE@  $(AM_V_at)$(am__mv) src/cpp/view_scilab/$(DEPDIR)/libsciscicos_algo_la-ports_management.Tpo src/cpp/view_scilab/$(DEPDIR)/libsciscicos_algo_la-ports_management.Plo
+@AMDEP_TRUE@@am__fastdepCXX_FALSE@     $(AM_V_CXX)source='src/cpp/view_scilab/ports_management.cpp' object='src/cpp/view_scilab/libsciscicos_algo_la-ports_management.lo' libtool=yes @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCXX_FALSE@     DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCXX_FALSE@ $(AM_V_CXX@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libsciscicos_algo_la_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o src/cpp/view_scilab/libsciscicos_algo_la-ports_management.lo `test -f 'src/cpp/view_scilab/ports_management.cpp' || echo '$(srcdir)/'`src/cpp/view_scilab/ports_management.cpp
+
 sci_gateway/cpp/libsciscicos_cli_la-sci_scicos_new.lo: sci_gateway/cpp/sci_scicos_new.cpp
 @am__fastdepCXX_TRUE@  $(AM_V_CXX)$(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(libsciscicos_cli_la_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT sci_gateway/cpp/libsciscicos_cli_la-sci_scicos_new.lo -MD -MP -MF sci_gateway/cpp/$(DEPDIR)/libsciscicos_cli_la-sci_scicos_new.Tpo -c -o sci_gateway/cpp/libsciscicos_cli_la-sci_scicos_new.lo `test -f 'sci_gateway/cpp/sci_scicos_new.cpp' || echo '$(srcdir)/'`sci_gateway/cpp/sci_scicos_new.cpp
 @am__fastdepCXX_TRUE@  $(AM_V_at)$(am__mv) sci_gateway/cpp/$(DEPDIR)/libsciscicos_cli_la-sci_scicos_new.Tpo sci_gateway/cpp/$(DEPDIR)/libsciscicos_cli_la-sci_scicos_new.Plo
index 98f5d31..baa2f62 100644 (file)
@@ -267,6 +267,7 @@ lib /DEF:"$(ProjectDir)differential_equations_f_Import.def" /SUBSYSTEM:WINDOWS /
     <ClCompile Include="..\cpp\view_scilab\ScsAdapter.cpp" />
     <ClCompile Include="..\cpp\view_scilab\StateAdapter.cpp" />
     <ClCompile Include="..\cpp\view_scilab\TextAdapter.cpp" />
+    <ClCompile Include="..\cpp\view_scilab\ports_management.cpp" />
     <ClCompile Include="copyvarfromlistentry.c" />
     <ClCompile Include="createblklist.c" />
     <ClCompile Include="DllmainScicos.c" />
@@ -338,6 +339,7 @@ lib /DEF:"$(ProjectDir)differential_equations_f_Import.def" /SUBSYSTEM:WINDOWS /
     <ClInclude Include="..\cpp\view_scilab\ScsAdapter.hxx" />
     <ClInclude Include="..\cpp\view_scilab\StateAdapter.hxx" />
     <ClInclude Include="..\cpp\view_scilab\TextAdapter.hxx" />
+    <ClInclude Include="..\cpp\view_scilab\ports_management.hxx" />
     <ClInclude Include="copyvarfromlistentry.h" />
     <ClInclude Include="createblklist.h" />
     <ClInclude Include="..\..\includes\dynlib_scicos.h" />
@@ -426,4 +428,4 @@ lib /DEF:"$(ProjectDir)differential_equations_f_Import.def" /SUBSYSTEM:WINDOWS /
   <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
   <ImportGroup Label="ExtensionTargets">
   </ImportGroup>
-</Project>
\ No newline at end of file
+</Project>
index 4d02a44..a926a99 100644 (file)
     <ClCompile Include="..\cpp\view_scilab\BlockAdapter.cpp">
       <Filter>Source Files\MVC\view_scilab</Filter>
     </ClCompile>
+    <ClCompile Include="..\cpp\view_scilab\ports_management.cpp">
+      <Filter>Source Files\MVC\view_scilab</Filter>
+    </ClCompile>
     <ClCompile Include="..\..\sci_gateway\cpp\sci_scicos_new.cpp">
       <Filter>Source Files</Filter>
     </ClCompile>
     <ClInclude Include="..\cpp\view_scilab\ParamsAdapter.hxx">
       <Filter>Header Files\MVC\view_scilab</Filter>
     </ClInclude>
+    <ClInclude Include="..\cpp\view_scilab\ports_management.hxx">
+      <Filter>Header Files\MVC\view_scilab</Filter>
+    </ClInclude>
     <ClInclude Include="..\..\includes\Controller.hxx">
       <Filter>Header Files\MVC</Filter>
     </ClInclude>
       <Filter>Resource Files</Filter>
     </ResourceCompile>
   </ItemGroup>
-</Project>
\ No newline at end of file
+</Project>
index eb6a42c..1542590 100644 (file)
 #include <vector>
 #include <cassert>
 
-#include "int.hxx"
+#include "list.hxx"
 #include "double.hxx"
 #include "string.hxx"
 
 #include "Controller.hxx"
 #include "GraphicsAdapter.hxx"
+#include "ports_management.hxx"
 
 extern "C" {
 #include "sci_malloc.h"
@@ -257,347 +258,17 @@ struct exprs
     }
 };
 
-static types::Double* create_port(const GraphicsAdapter& adaptor, object_properties_t p, const Controller& controller)
-{
-    model::Block* adaptee = adaptor.getAdaptee();
-
-    // retrieve the identifiers
-    std::vector<ScicosID> ids;
-    controller.getObjectProperty(adaptee->id(), adaptee->kind(), p, ids);
-
-    // allocate some space for the return value
-    double* ports;
-    types::Double* o = new types::Double(ids.size(), 1, &ports);
-
-    // translate identifiers to return values
-    for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++ports)
-    {
-        std::vector<ScicosID> connectedSignals;
-
-        controller.getObjectProperty(*it, PORT, CONNECTED_SIGNALS, connectedSignals);
-
-        // always return the first connected signals, at scilab level a port can only be connected to one signal at a time.
-        if (connectedSignals.empty())
-        {
-            // if the port is not connected returns 0
-            *ports = 0;
-        }
-        else
-        {
-            // if the port is connected, return the index of the link in the parent diagram
-            ScicosID link = connectedSignals[0];
-
-            ScicosID parentDiagram = 0;
-            controller.getObjectProperty(link, LINK, PARENT_DIAGRAM, parentDiagram);
-
-            std::vector<ScicosID> children;
-            controller.getObjectProperty(parentDiagram, DIAGRAM, CHILDREN, children);
-
-            std::vector<ScicosID>::iterator it = std::find(children.begin(), children.end(), link);
-            if (it != children.end())
-            {
-                int index = std::distance(children.begin(), it);
-                *ports = index;
-            }
-            else
-            {
-                *ports = 0;
-            }
-        }
-
-        ports++;
-    }
-
-    return o;
-}
-
-static types::String* get_port(const GraphicsAdapter& adaptor, object_properties_t p, const Controller& controller, object_properties_t p2)
-{
-    model::Block* adaptee = adaptor.getAdaptee();
-
-    // Retrieve the identifiers
-    std::vector<ScicosID> ids;
-    controller.getObjectProperty(adaptee->id(), adaptee->kind(), p, ids);
-
-    // Allocate some space for the return value
-    types::String* o = new types::String(ids.size(), 1);
-
-    // Translate identifiers to return values
-    int i = 0;
-    switch (p2)
-    {
-        case IMPLICIT:
-        {
-            for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
-            {
-                bool v;
-                controller.getObjectProperty(*it, PORT, p2, v);
-                o->set(i, (v == false) ? E : I);
-            }
-            break;
-        }
-        case STYLE:
-        case LABEL:
-        {
-            for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
-            {
-                std::string s;
-                controller.getObjectProperty(*it, PORT, p2, s);
-                o->set(i, s.data());
-            }
-            break;
-        }
-        default:
-            return false;
-    }
-
-    return o;
-}
-
-static bool set_port(const GraphicsAdapter& adaptor, types::InternalType* v, object_properties_t p, Controller& controller)
-{
-    model::Block* adaptee = adaptor.getAdaptee();
-
-    if (v->getType() != types::InternalType::ScilabDouble)
-    {
-        return false;
-    }
-    types::Double* value = v->getAs<types::Double>();
-
-    ScicosID parentDiagram;
-    controller.getObjectProperty(adaptee->id(), BLOCK, PARENT_DIAGRAM, parentDiagram);
-
-    std::vector<ScicosID> children;
-    if (parentDiagram != 0)
-    {
-        controller.getObjectProperty(parentDiagram, DIAGRAM, CHILDREN, children);
-    }
-
-    std::vector<int> newPorts = std::vector<int>(value->getSize());
-    double* d = value->getReal();
-    for (std::vector<int>::iterator it = newPorts.begin(); it != newPorts.end(); ++it, ++d)
-    {
-        if (0 > *d && *d >= children.size())
-        {
-            return false;
-        }
-
-        *it = (int) * d;
-    }
-    std::vector<ScicosID> deletedObjects;
-
-    // retrieve old data
-    std::vector<ScicosID> oldPorts;
-    controller.getObjectProperty(adaptee->id(), adaptee->kind(), p, oldPorts);
-    std::vector<ScicosID> previousPorts = oldPorts;
-
-    // updated ports
-    while (!oldPorts.empty() || !newPorts.empty())
-    {
-        ScicosID oldPort = oldPorts.back();
-        oldPorts.pop_back();
-        int newPort = newPorts.back();
-        newPorts.pop_back();
-
-        ScicosID oldSignal;
-        controller.getObjectProperty(oldPort, PORT, CONNECTED_SIGNALS, oldSignal);
-        ScicosID newSignal = children[newPort];
-
-        if (oldSignal != newSignal)
-        {
-            // disconnect the old link
-            ScicosID oldSignalSrc;
-            controller.getObjectProperty(oldSignal, LINK, SOURCE_PORT, oldSignalSrc);
-            ScicosID oldSignalDst;
-            controller.getObjectProperty(oldSignal, LINK, DESTINATION_PORT, oldSignalDst);
-
-            ScicosID unconnected = 0;
-            if (oldSignalSrc == oldPort)
-            {
-                controller.setObjectProperty(oldSignalDst, PORT, CONNECTED_SIGNALS, unconnected);
-            }
-            else // oldSignalDst == oldPort
-            {
-                controller.setObjectProperty(oldSignalSrc, PORT, CONNECTED_SIGNALS, unconnected);
-            }
-            // Link de-association is not performed as the link will be removed
-
-            // connect the new link
-            controller.setObjectProperty(newSignal, LINK, SOURCE_PORT, 0);
-            controller.setObjectProperty(oldPort, PORT, CONNECTED_SIGNALS, newSignal);
-
-            children.erase(std::find(children.begin(), children.end(), oldSignal));
-            deletedObjects.push_back(oldSignal);
-        }
-    }
-
-    // removed ports
-    if (!oldPorts.empty())
-    {
-        previousPorts.erase(previousPorts.begin() + oldPorts.size(), previousPorts.end());
-
-        while (!oldPorts.empty())
-        {
-            ScicosID oldPort = oldPorts.back();
-            oldPorts.pop_back();
-
-            ScicosID signal;
-            controller.getObjectProperty(oldPort, PORT, CONNECTED_SIGNALS, signal);
-            if (signal != 0)
-            {
-                // the link is connected, disconnect the other side
-                ScicosID oldSignalSrc;
-                controller.getObjectProperty(signal, LINK, SOURCE_PORT, oldSignalSrc);
-                ScicosID oldSignalDst;
-                controller.getObjectProperty(signal, LINK, DESTINATION_PORT, oldSignalDst);
-
-                ScicosID unconnected = 0;
-                if (oldSignalSrc == oldPort)
-                {
-                    controller.setObjectProperty(oldSignalDst, PORT, CONNECTED_SIGNALS, unconnected);
-                }
-                else     // oldSignalDst == oldPort
-                {
-                    controller.setObjectProperty(oldSignalSrc, PORT, CONNECTED_SIGNALS, unconnected);
-                }
-
-                children.erase(std::find(children.begin(), children.end(), signal));
-                deletedObjects.push_back(signal);
-            }
-
-            deletedObjects.push_back(oldPort);
-        }
-
-        controller.setObjectProperty(adaptee->id(), BLOCK, p, previousPorts);
-    }
-
-    // added ports
-    if (!newPorts.empty())
-    {
-        while (!newPorts.empty())
-        {
-            int newPort = newPorts.back();
-            oldPorts.pop_back();
-
-            ScicosID id = controller.createObject(PORT);
-            controller.setObjectProperty(id, PORT, SOURCE_BLOCK, adaptee->id());
-            // set the connected signal if applicable
-            if (newPort != 0)
-            {
-                ScicosID signal = children[newPort];
-                controller.setObjectProperty(id, PORT, CONNECTED_SIGNALS, signal);
-            }
-
-            previousPorts.push_back(id);
-        }
-
-        controller.setObjectProperty(adaptee->id(), BLOCK, p, previousPorts);
-    }
-
-    // remove objects from the model after de-association
-    if (parentDiagram != 0)
-    {
-        controller.setObjectProperty(parentDiagram, DIAGRAM, CHILDREN, children);
-    }
-    for (std::vector<ScicosID>::iterator it = deletedObjects.begin(); it != deletedObjects.end(); ++it)
-    {
-        controller.deleteObject(*it);
-    }
-
-    return true;
-}
-
-static bool set_port(const GraphicsAdapter& adaptor, types::InternalType* v, object_properties_t p, Controller& controller, object_properties_t p2)
-{
-    if (v->getType() == types::InternalType::ScilabString)
-    {
-        model::Block* adaptee = adaptor.getAdaptee();
-
-        types::String* current = v->getAs<types::String>();
-        if (current->getCols() != 0 && current->getCols() != 1)
-        {
-            return false;
-        }
-
-        // Retrieve the ports i dentifiers
-        std::vector<ScicosID> ids;
-        size_t rows = current->getRows();
-        controller.getObjectProperty(adaptee->id(), adaptee->kind(), p, ids);
-        if (rows != ids.size())
-        {
-            return false;
-        }
-
-        int i = 0;
-        switch (p2)
-        {
-            case IMPLICIT:
-            {
-                for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
-                {
-                    if (current->get(i) == I)
-                    {
-                        controller.setObjectProperty(*it, PORT, p2, true);
-                    }
-                    else if (current->get(i) == E)
-                    {
-                        controller.setObjectProperty(*it, PORT, p2, false);
-                    }
-                    else
-                    {
-                        return false;
-                    }
-                }
-                break;
-            }
-            case STYLE:
-            case LABEL:
-            {
-                std::vector<std::string> style = std::vector<std::string>(current->getSize());
-                for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
-                {
-                    char* c_str = wide_string_to_UTF8(current->get(i));
-                    style[i] = std::string(c_str);
-                    FREE(c_str);
-                    controller.setObjectProperty(*it, PORT, p2, style[i]);
-                }
-                break;
-            }
-            default:
-                return false;
-        }
-        return true;
-    }
-    else if (v->getType() == types::InternalType::ScilabDouble)
-    {
-        types::Double* current = v->getAs<types::Double>();
-        if (current->getRows() != 0 || current->getCols() != 0)
-        {
-            return false;
-        }
-        types::String* o = get_port(adaptor, p, controller, p2);
-        if (o->getSize() != 0)
-        {
-            return false;
-        }
-        // Do nothing, because if the sizes match, then there are already zero concerned ports, so no ports to update
-        delete o;
-        return true;
-    }
-    return false;
-}
-
 struct pin
 {
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return create_port(adaptor, INPUTS, controller);
+        return get_ports_property(adaptor, INPUTS, controller, CONNECTED_SIGNALS);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, INPUTS, controller);
+        return update_ports_with_property(adaptor, INPUTS, controller, CONNECTED_SIGNALS, v);
     }
 };
 
@@ -606,12 +277,12 @@ struct pout
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return create_port(adaptor, OUTPUTS, controller);
+        return get_ports_property(adaptor, OUTPUTS, controller, CONNECTED_SIGNALS);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, OUTPUTS, controller);
+        return update_ports_with_property(adaptor, OUTPUTS, controller, CONNECTED_SIGNALS, v);
     }
 };
 
@@ -620,12 +291,12 @@ struct pein
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return create_port(adaptor, EVENT_INPUTS, controller);
+        return get_ports_property(adaptor, EVENT_INPUTS, controller, CONNECTED_SIGNALS);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, EVENT_INPUTS, controller);
+        return update_ports_with_property(adaptor, EVENT_INPUTS, controller, CONNECTED_SIGNALS, v);
     }
 };
 
@@ -634,12 +305,12 @@ struct peout
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return create_port(adaptor, EVENT_OUTPUTS, controller);
+        return get_ports_property(adaptor, EVENT_OUTPUTS, controller, CONNECTED_SIGNALS);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, EVENT_OUTPUTS, controller);
+        return update_ports_with_property(adaptor, EVENT_OUTPUTS, controller, CONNECTED_SIGNALS, v);
     }
 };
 
@@ -703,12 +374,12 @@ struct in_implicit
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return get_port(adaptor, INPUTS, controller, IMPLICIT);
+        return get_ports_property(adaptor, INPUTS, controller, IMPLICIT);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, INPUTS, controller, IMPLICIT);
+        return set_ports_property(adaptor, INPUTS, controller, IMPLICIT, v);
     }
 };
 
@@ -717,12 +388,12 @@ struct out_implicit
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return get_port(adaptor, OUTPUTS, controller, IMPLICIT);
+        return get_ports_property(adaptor, OUTPUTS, controller, IMPLICIT);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, OUTPUTS, controller, IMPLICIT);
+        return set_ports_property(adaptor, OUTPUTS, controller, IMPLICIT, v);
     }
 };
 
@@ -731,12 +402,12 @@ struct in_style
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return get_port(adaptor, INPUTS, controller, STYLE);
+        return get_ports_property(adaptor, INPUTS, controller, STYLE);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, INPUTS, controller, STYLE);
+        return set_ports_property(adaptor, INPUTS, controller, STYLE, v);
     }
 };
 
@@ -745,12 +416,12 @@ struct out_style
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return get_port(adaptor, OUTPUTS, controller, STYLE);
+        return get_ports_property(adaptor, OUTPUTS, controller, STYLE);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, OUTPUTS, controller, STYLE);
+        return set_ports_property(adaptor, OUTPUTS, controller, STYLE, v);
     }
 };
 
@@ -759,12 +430,12 @@ struct in_label
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return get_port(adaptor, INPUTS, controller, LABEL);
+        return get_ports_property(adaptor, INPUTS, controller, LABEL);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, INPUTS, controller, LABEL);
+        return set_ports_property(adaptor, INPUTS, controller, LABEL, v);
     }
 };
 
@@ -773,12 +444,12 @@ struct out_label
 
     static types::InternalType* get(const GraphicsAdapter& adaptor, const Controller& controller)
     {
-        return get_port(adaptor, OUTPUTS, controller, LABEL);
+        return get_ports_property(adaptor, OUTPUTS, controller, LABEL);
     }
 
     static bool set(GraphicsAdapter& adaptor, types::InternalType* v, Controller& controller)
     {
-        return set_port(adaptor, v, OUTPUTS, controller, LABEL);
+        return set_ports_property(adaptor, OUTPUTS, controller, LABEL, v);
     }
 };
 
diff --git a/scilab/modules/scicos/src/cpp/view_scilab/ports_management.cpp b/scilab/modules/scicos/src/cpp/view_scilab/ports_management.cpp
new file mode 100644 (file)
index 0000000..f11463d
--- /dev/null
@@ -0,0 +1,339 @@
+/*
+ *  Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
+ *  Copyright (C) 2014 - Scilab Enterprises - Paul Bignier
+ *  Copyright (C) 2014 - Scilab Enterprises - Clement DAVID
+ *
+ *  This file must be used under the terms of the CeCILL.
+ *  This source file is licensed as described in the file COPYING, which
+ *  you should have received as part of this distribution.  The terms
+ *  are also available at
+ *  http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt
+ *
+ */
+
+#include <algorithm>
+#include <string>
+#include <vector>
+
+#include "internal.hxx"
+#include "double.hxx"
+#include "string.hxx"
+
+#include "ports_management.hxx"
+
+namespace org_scilab_modules_scicos
+{
+namespace view_scilab
+{
+
+static const wchar_t E[] = L"E";
+static const wchar_t I[] = L"I";
+
+types::InternalType* get_ports_property(const GraphicsAdapter& adaptor, object_properties_t port_kind, const Controller& controller, object_properties_t p)
+{
+    model::Block* adaptee = adaptor.getAdaptee();
+
+    // Retrieve the identifiers
+    std::vector<ScicosID> ids;
+    controller.getObjectProperty(adaptee->id(), adaptee->kind(), p, ids);
+
+    // Translate identifiers to return values
+    int i = 0;
+    switch (p)
+    {
+        case CONNECTED_SIGNALS:
+        {
+            double* v;
+            types::Double* o = new types::Double(ids.size(), 1, &v);
+
+            ScicosID diagram;
+            controller.getObjectProperty(adaptee->id(), adaptee->kind(), PARENT_DIAGRAM, diagram);
+
+            std::vector<ScicosID> children;
+            controller.getObjectProperty(diagram, DIAGRAM, CHILDREN, children);
+
+            for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
+            {
+                ScicosID id;
+                controller.getObjectProperty(*it, PORT, p, id);
+
+                std::vector<ScicosID>::iterator found = std::find(children.begin(), children.end(), id);
+
+                if (found != children.end())
+                {
+                    v[i] = std::distance(found, children.begin());
+                }
+                else
+                {
+                    v[i] = 0;
+                }
+            }
+            return o;
+        }
+        case STYLE:
+        case LABEL:
+        {
+            types::String* o = new types::String(ids.size(), 1);
+            for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
+            {
+                std::string s;
+                controller.getObjectProperty(*it, PORT, p, s);
+                o->set(i, s.data());
+            }
+            return o;
+        }
+        case IMPLICIT:
+        {
+            types::String* o = new types::String(ids.size(), 1);
+            for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
+            {
+                bool v;
+                controller.getObjectProperty(*it, PORT, p, v);
+                o->set(i, (v == false) ? E : I);
+            }
+            return o;
+        }
+        default:
+            return 0;
+    }
+}
+
+bool set_ports_property(const GraphicsAdapter& adaptor, object_properties_t port_kind, Controller& controller, object_properties_t p, types::InternalType* v)
+{
+    model::Block* adaptee = adaptor.getAdaptee();
+
+    // Retrieve the ports identifiers
+    std::vector<ScicosID> ids;
+    controller.getObjectProperty(adaptee->id(), adaptee->kind(), port_kind, ids);
+
+    if (v->getType() == types::InternalType::ScilabString)
+    {
+        types::String* current = v->getAs<types::String>();
+        if (current->getCols() != 0 && current->getCols() != 1)
+        {
+            return false;
+        }
+
+        size_t rows = current->getRows();
+        if (rows != ids.size())
+        {
+            return false;
+        }
+
+        int i = 0;
+        switch (p)
+        {
+            case IMPLICIT:
+            {
+                for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
+                {
+                    if (current->get(i) == I)
+                    {
+                        controller.setObjectProperty(*it, PORT, p, true);
+                    }
+                    else if (current->get(i) == E)
+                    {
+                        controller.setObjectProperty(*it, PORT, p, false);
+                    }
+                    else
+                    {
+                        return false;
+                    }
+                }
+                return true;
+            }
+            case STYLE:
+            case LABEL:
+            {
+                std::vector<std::string> style = std::vector<std::string>(current->getSize());
+                for (std::vector<ScicosID>::iterator it = ids.begin(); it != ids.end(); ++it, ++i)
+                {
+                    char* c_str = wide_string_to_UTF8(current->get(i));
+                    style[i] = std::string(c_str);
+                    FREE(c_str);
+                    controller.setObjectProperty(*it, PORT, p, style[i]);
+                }
+                return true;
+            }
+            default:
+                return false;
+        }
+    }
+    else if (v->getType() == types::InternalType::ScilabDouble)
+    {
+        types::Double* current = v->getAs<types::Double>();
+        if (current->getRows() != 0 || current->getCols() != 0)
+        {
+            return false;
+        }
+        if (ids.size() != 0)
+        {
+            return false;
+        }
+        // Do nothing, because if the sizes match, then there are already zero concerned ports, so no ports to update
+        return true;
+    }
+    return false;
+}
+
+bool update_ports_with_property(const GraphicsAdapter& adaptor, object_properties_t port_kind, Controller& controller, object_properties_t p, types::InternalType* v)
+{
+    model::Block* adaptee = adaptor.getAdaptee();
+
+    if (v->getType() != types::InternalType::ScilabDouble)
+    {
+        return false;
+    }
+    types::Double* value = v->getAs<types::Double>();
+
+    ScicosID parentDiagram;
+    controller.getObjectProperty(adaptee->id(), BLOCK, PARENT_DIAGRAM, parentDiagram);
+
+    std::vector<ScicosID> children;
+    if (parentDiagram != 0)
+    {
+        controller.getObjectProperty(parentDiagram, DIAGRAM, CHILDREN, children);
+    }
+
+    std::vector<int> newPorts = std::vector<int>(value->getSize());
+    double* d = value->getReal();
+    for (std::vector<int>::iterator it = newPorts.begin(); it != newPorts.end(); ++it, ++d)
+    {
+        if (0 > *d && *d >= children.size())
+        {
+            return false;
+        }
+
+        *it = (int) * d;
+    }
+    std::vector<ScicosID> deletedObjects;
+
+    // retrieve old data
+    std::vector<ScicosID> oldPorts;
+    controller.getObjectProperty(adaptee->id(), adaptee->kind(), port_kind, oldPorts);
+    std::vector<ScicosID> previousPorts = oldPorts;
+
+    if (p != CONNECTED_SIGNALS)
+    {
+        // FIXME: implement port creation for the blk.model
+        return false;
+    }
+
+    // updated ports
+    while (!oldPorts.empty() || !newPorts.empty())
+    {
+        ScicosID oldPort = oldPorts.back();
+        oldPorts.pop_back();
+        int newPort = newPorts.back();
+        newPorts.pop_back();
+
+        ScicosID oldSignal;
+        controller.getObjectProperty(oldPort, PORT, CONNECTED_SIGNALS, oldSignal);
+        ScicosID newSignal = children[newPort];
+
+        if (oldSignal != newSignal)
+        {
+            // disconnect the old link
+            ScicosID oldSignalSrc;
+            controller.getObjectProperty(oldSignal, LINK, SOURCE_PORT, oldSignalSrc);
+            ScicosID oldSignalDst;
+            controller.getObjectProperty(oldSignal, LINK, DESTINATION_PORT, oldSignalDst);
+
+            ScicosID unconnected = 0;
+            if (oldSignalSrc == oldPort)
+            {
+                controller.setObjectProperty(oldSignalDst, PORT, CONNECTED_SIGNALS, unconnected);
+            }
+            else // oldSignalDst == oldPort
+            {
+                controller.setObjectProperty(oldSignalSrc, PORT, CONNECTED_SIGNALS, unconnected);
+            }
+            // Link de-association is not performed as the link will be removed
+
+            // connect the new link
+            controller.setObjectProperty(newSignal, LINK, SOURCE_PORT, 0);
+            controller.setObjectProperty(oldPort, PORT, CONNECTED_SIGNALS, newSignal);
+
+            children.erase(std::find(children.begin(), children.end(), oldSignal));
+            deletedObjects.push_back(oldSignal);
+        }
+    }
+
+    // removed ports
+    if (!oldPorts.empty())
+    {
+        previousPorts.erase(previousPorts.begin() + oldPorts.size(), previousPorts.end());
+
+        while (!oldPorts.empty())
+        {
+            ScicosID oldPort = oldPorts.back();
+            oldPorts.pop_back();
+
+            ScicosID signal;
+            controller.getObjectProperty(oldPort, PORT, CONNECTED_SIGNALS, signal);
+            if (signal != 0)
+            {
+                // the link is connected, disconnect the other side
+                ScicosID oldSignalSrc;
+                controller.getObjectProperty(signal, LINK, SOURCE_PORT, oldSignalSrc);
+                ScicosID oldSignalDst;
+                controller.getObjectProperty(signal, LINK, DESTINATION_PORT, oldSignalDst);
+
+                ScicosID unconnected = 0;
+                if (oldSignalSrc == oldPort)
+                {
+                    controller.setObjectProperty(oldSignalDst, PORT, CONNECTED_SIGNALS, unconnected);
+                }
+                else     // oldSignalDst == oldPort
+                {
+                    controller.setObjectProperty(oldSignalSrc, PORT, CONNECTED_SIGNALS, unconnected);
+                }
+
+                children.erase(std::find(children.begin(), children.end(), signal));
+                deletedObjects.push_back(signal);
+            }
+
+            deletedObjects.push_back(oldPort);
+        }
+
+        controller.setObjectProperty(adaptee->id(), BLOCK, port_kind, previousPorts);
+    }
+
+    // added ports
+    if (!newPorts.empty())
+    {
+        while (!newPorts.empty())
+        {
+            int newPort = newPorts.back();
+            oldPorts.pop_back();
+
+            ScicosID id = controller.createObject(PORT);
+            controller.setObjectProperty(id, PORT, SOURCE_BLOCK, adaptee->id());
+            // set the connected signal if applicable
+            if (newPort != 0)
+            {
+                ScicosID signal = children[newPort];
+                controller.setObjectProperty(id, PORT, CONNECTED_SIGNALS, signal);
+            }
+
+            previousPorts.push_back(id);
+        }
+
+        controller.setObjectProperty(adaptee->id(), BLOCK, port_kind, previousPorts);
+    }
+
+    // remove objects from the model after de-association
+    if (parentDiagram != 0)
+    {
+        controller.setObjectProperty(parentDiagram, DIAGRAM, CHILDREN, children);
+    }
+    for (std::vector<ScicosID>::iterator it = deletedObjects.begin(); it != deletedObjects.end(); ++it)
+    {
+        controller.deleteObject(*it);
+    }
+
+    return true;
+}
+
+} /* view_scilab */
+} /* namespace org_scilab_modules_scicos */
diff --git a/scilab/modules/scicos/src/cpp/view_scilab/ports_management.hxx b/scilab/modules/scicos/src/cpp/view_scilab/ports_management.hxx
new file mode 100644 (file)
index 0000000..492be05
--- /dev/null
@@ -0,0 +1,53 @@
+/*
+ *  Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
+ *  Copyright (C) 2014 - Scilab Enterprises - Paul Bignier
+ *  Copyright (C) 2014 - Scilab Enterprises - Clement DAVID
+ *
+ *  This file must be used under the terms of the CeCILL.
+ *  This source file is licensed as described in the file COPYING, which
+ *  you should have received as part of this distribution.  The terms
+ *  are also available at
+ *  http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt
+ *
+ */
+
+#ifndef PORTS_MANAGEMENT_HXX_
+#define PORTS_MANAGEMENT_HXX_
+
+#include <string>
+#include <vector>
+
+#include "internal.hxx"
+
+#include "Controller.hxx"
+#include "GraphicsAdapter.hxx"
+
+namespace org_scilab_modules_scicos
+{
+namespace view_scilab
+{
+
+/*
+ * Return a Scilab encoded value for a property.
+ */
+types::InternalType* get_ports_property(const GraphicsAdapter& adaptor, object_properties_t port_kind, const Controller& controller, object_properties_t p);
+
+/*
+ * Set a Scilab encoded values as a property.
+ *
+ * \note this method will return false if one of the ports does not exist
+ */
+bool set_ports_property(const GraphicsAdapter& adaptor, object_properties_t port_kind, Controller& controller, object_properties_t p, types::InternalType* v);
+
+/**
+ * Update the ports with a specific property.
+ *
+ * Create ports if needed, remove ports if needed and set a default property on each port.
+ */
+bool update_ports_with_property(const GraphicsAdapter& adaptor, object_properties_t port_kind, Controller& controller, object_properties_t p, types::InternalType* v);
+
+
+} /* view_scilab */
+} /* namespace org_scilab_modules_scicos */
+
+#endif /* PORTS_MANAGEMENT_HXX_ */