Xcos: SEP_066_Xcos_hooks update to handle multiple pre/post hooks 59/9259/2
Clément DAVID [Tue, 25 Sep 2012 07:08:08 +0000 (09:08 +0200)]
Change-Id: Ide5b2d1094d351d35d9fee8aae5623306bee4577

SEP/SEP_066_Xcos_hooks.odt
scilab/modules/xcos/macros/xcos_simulate.sci
scilab/modules/xcos/tests/unit_tests/SEP_066_Xcos_multi_hooks.dia.ref [new file with mode: 0644]
scilab/modules/xcos/tests/unit_tests/SEP_066_Xcos_multi_hooks.tst [new file with mode: 0644]

index a588265..c6de916 100644 (file)
Binary files a/SEP/SEP_066_Xcos_hooks.odt and b/SEP/SEP_066_Xcos_hooks.odt differ
index cdbd110..a73dfb3 100644 (file)
@@ -22,19 +22,43 @@ function %cpr = xcos_simulate(scs_m, needcompile)
   [modelica_libs, scicos_pal_libs, %scicos_with_grid, %scs_wgrid] = initial_scicos_tables();
 
     // Hook according to SEP066
-    if isdef("pre_xcos_simulate") then
-      try
-      continueSimulation = pre_xcos_simulate(scs_m, needcompile);
-      if ~continueSimulation then
-        %cpr = []
-        return
-      end
-      catch
-      disp(_("Error occurred in pre_xcos_simulate: Cancelling simulation."))
-      %cpr = []
-      return
+    function [ok]=invoke_pre_simulate(fun, scs_m, needcompile)
+        ok=%f;
+        ierr=execstr('[continueSimulation]='+fun+'(scs_m, needcompile);', 'errcatch');
+        if ierr<>0 then
+            disp(_("Error occurred in pre_xcos_simulate: Cancelling simulation."));
+            [str,n,line,func]=lasterror();
+            mprintf(' at line %d of function %s\n', line, func);
+            return
+        end
+        if ~continueSimulation then
+            return
+        end
+        ok=%t;
+        
+        // force update on the parent in case of scoped modification
+        scs_m=resume(scs_m);
+    endfunction
+    
+  if isdef("pre_xcos_simulate") then
+      if type(pre_xcos_simulate) == 15 then
+          // if has a multiple implementation (on a list)
+          for f=pre_xcos_simulate;
+              ok=invoke_pre_simulate(f, scs_m, needcompile);
+              if ~ok then
+                  %cpr=[];
+                  return;
+              end
+          end
+      else
+          // if has a unique implementation
+          ok=invoke_pre_simulate("pre_xcos_simulate", scs_m, needcompile);
+          if ~ok then
+            %cpr=[];
+            return;
+          end
       end
-    end
+  end
 
   //**---- prepare from and to workspace stuff ( "From workspace" block )
   scicos_workspace_init()
@@ -350,14 +374,38 @@ function %cpr = xcos_simulate(scs_m, needcompile)
 
   end
 
-  // Hook according to SEP066
-  if isdef("post_xcos_simulate") then
-    try
-      post_xcos_simulate(%cpr, scs_m, needcompile);
-    catch
-      disp(_("Error in post_xcos_simulate: ending simulation."))
+    // Hook according to SEP066
+    function ok=invoke_post_simulate(fun, %cpr, scs_m, needcompile)
+        ok=%f;
+        ierr=execstr(fun+'(%cpr, scs_m, needcompile);', 'errcatch');
+        if ierr<>0 then
+            disp(_("Error in post_xcos_simulate: ending simulation."))
+            return
+        end
+        ok=%t
+        // force update on the parent in case of scoped modification
+        scs_m=resume(scs_m);
+    endfunction
+    
+    if isdef("post_xcos_simulate") then
+      if type(post_xcos_simulate) == 15 then
+          // if has a multiple implementation (on a list)
+          for f=post_xcos_simulate;
+              ok=invoke_post_simulate(f, scs_m, needcompile);
+              if ~ok then
+                  %cpr=[];
+                  return;
+              end
+          end
+      else
+          // if has a unique implementation
+          ok=invoke_post_simulate("post_xcos_simulate", %cpr, scs_m, needcompile);
+          if ~ok then
+            %cpr=[];
+            return;
+          end
+      end
     end
-  end
 
   // finally restore the exported variables on the parent context
   if ~isempty(txt) then
diff --git a/scilab/modules/xcos/tests/unit_tests/SEP_066_Xcos_multi_hooks.dia.ref b/scilab/modules/xcos/tests/unit_tests/SEP_066_Xcos_multi_hooks.dia.ref
new file mode 100644 (file)
index 0000000..15d0459
--- /dev/null
@@ -0,0 +1,49 @@
+// Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
+// Copyright (C) Scilab Enterprises - 201é - Clément DAVID
+//
+// This file is distributed under the same license as the Scilab package.
+// <-- ENGLISH IMPOSED -->
+// <-- TEST WITH XCOS -->
+//
+// <-- Short Description -->
+// Check the API of multiple Xcos hooks, see SEP_066_Xcos_hooks.odt
+loadXcosLibs();
+global status;
+status = [];
+function continueSimulation = pre1(scs_m, needcompile)
+  global status;
+  [linenum,mac]=where();
+  status = [status mac(1)];
+  continueSimulation=%t;
+endfunction
+function continueSimulation = pre2(scs_m, needcompile)
+  global status;
+  [linenum,mac]=where();
+  status = [status mac(1)];
+  continueSimulation=%t;
+endfunction
+function continueSimulation = pre3(scs_m, needcompile)
+  global status;
+  [linenum,mac]=where();
+  status = [status mac(1)];
+  continueSimulation=%t;
+endfunction
+function post1(%cpr, scs_m, needcompile)
+  global status;
+  [linenum,mac]=where();
+  status = [status mac(1)];
+endfunction
+function post2(%cpr, scs_m, needcompile)
+  global status;
+  [linenum,mac]=where();
+  status = [status mac(1)];
+endfunction
+// register the hooks
+pre_xcos_simulate=list('pre1', 'pre2', 'pre3');
+post_xcos_simulate=list('post1', 'post2');
+assert_checktrue(importXcosDiagram(SCI + "/modules/xcos/demos/Simple_Demo.xcos"));
+xcos_simulate(scs_m, 4);
+assert_checkequal(status, ['pre1', 'pre2', 'pre3', 'post1', 'post2'])
+ ans  =
+  T  
diff --git a/scilab/modules/xcos/tests/unit_tests/SEP_066_Xcos_multi_hooks.tst b/scilab/modules/xcos/tests/unit_tests/SEP_066_Xcos_multi_hooks.tst
new file mode 100644 (file)
index 0000000..b9cea91
--- /dev/null
@@ -0,0 +1,63 @@
+// Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
+// Copyright (C) Scilab Enterprises - 201é - Clément DAVID
+//
+// This file is distributed under the same license as the Scilab package.
+
+// <-- ENGLISH IMPOSED -->
+// <-- TEST WITH XCOS -->
+//
+// <-- Short Description -->
+// Check the API of multiple Xcos hooks, see SEP_066_Xcos_hooks.odt
+
+loadXcosLibs();
+global status;
+status = [];
+
+function continueSimulation = pre1(scs_m, needcompile)
+  global status;
+
+  [linenum,mac]=where();
+  status = [status mac(1)];
+  continueSimulation=%t;
+endfunction
+
+function continueSimulation = pre2(scs_m, needcompile)
+  global status;
+
+  [linenum,mac]=where();
+  status = [status mac(1)];
+  continueSimulation=%t;
+endfunction
+
+function continueSimulation = pre3(scs_m, needcompile)
+  global status;
+
+  [linenum,mac]=where();
+  status = [status mac(1)];
+  continueSimulation=%t;
+endfunction
+
+function post1(%cpr, scs_m, needcompile)
+  global status;
+
+  [linenum,mac]=where();
+  status = [status mac(1)];
+endfunction
+
+function post2(%cpr, scs_m, needcompile)
+  global status;
+
+  [linenum,mac]=where();
+  status = [status mac(1)];
+endfunction
+
+// register the hooks
+pre_xcos_simulate=list('pre1', 'pre2', 'pre3');
+post_xcos_simulate=list('post1', 'post2');
+
+assert_checktrue(importXcosDiagram(SCI + "/modules/xcos/demos/Simple_Demo.xcos"));
+xcos_simulate(scs_m, 4);
+
+assert_checkequal(status, ['pre1', 'pre2', 'pre3', 'post1', 'post2'])
+
+