Xcos: resolve SCI on scicosDiagramToScilab calls
[scilab.git] / scilab / modules / scicos / sci_gateway / cpp / sci_scicosDiagramToScilab.cpp
1 /*
2  * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  * Copyright (C) Scilab Enterprises - 2016-2016 - ClĂ©ment DAVID
4  *
5  * Copyright (C) 2012 - 2016 - Scilab Enterprises
6  *
7  * This file is hereby licensed under the terms of the GNU GPL v2.0,
8  * pursuant to article 5.3.4 of the CeCILL v.2.1.
9  * This file was originally licensed under the terms of the CeCILL v2.1,
10  * and continues to be available under such terms.
11  * For more information, see the COPYING file which you should have received
12  * along with this program.
13  *
14  */
15 /*--------------------------------------------------------------------------*/
16 #include "Controller.hxx"
17 #include "view_scilab/Adapters.hxx"
18 #include "XMIResource.hxx"
19
20 #include "types.hxx"
21 #include "function.hxx"
22 #include "string.hxx"
23 #include "user.hxx"
24 #include "int.hxx"
25
26 #include "gw_scicos.hxx"
27
28 extern "C"
29 {
30 #include "sci_malloc.h"
31 #include "localization.h"
32 #include "getFullFilename.h"
33 #include "Scierror.h"
34 }
35 /*--------------------------------------------------------------------------*/
36 using namespace org_scilab_modules_scicos;
37 /*--------------------------------------------------------------------------*/
38 static char funname[] = "scicosDiagramToScilab";
39 static types::InternalType* importFile(char const* file);
40 static bool exportFile(int index, char const* file, types::InternalType* uid);
41 /*--------------------------------------------------------------------------*/
42 types::Function::ReturnValue sci_scicosDiagramToScilab(types::typed_list &in, int _iRetCount, types::typed_list &out)
43 {
44     /*
45      * to import some files
46      * scs_m = scicosDiagramToScilab("/path/to/a/file")
47      * [scs_m1, scs_m2] = scicosDiagramToScilab(["/path/to/a/file", "/path/to/files"])
48      *
49      * to export a file
50      * scicosDiagramToScilab("/path/to/a/file", scs_m)
51      * scicosDiagramToScilab(["/path/to/a/file", "/path/to/files"], scs_m1, scs_m2)
52      */
53
54     if (in.size() < 1)
55     {
56         Scierror(77, _("%s: Wrong number of input arguments: at least %d expected.\n"), funname, 1);
57         return types::Function::Error;
58     }
59
60     if (!in[0]->isString())
61     {
62         Scierror(77, _("%s: Wrong type for input argument #%d: string expected.\n"), funname, 1);
63         return types::Function::Error;
64     }
65
66     types::String* files = in[0]->getAs<types::String>();
67     if (in.size() == 1 && files->getSize() == _iRetCount)
68     {
69         // the user asked to import
70         out.resize(_iRetCount);
71         for (int i = 0; i < _iRetCount; i++)
72         {
73             wchar_t* fullName = getFullFilenameW(files->get(i));
74             char* f = wide_string_to_UTF8(fullName);
75             FREE(fullName);
76             out[i] = importFile(f);
77             FREE(f);
78             if (out[i] == nullptr)
79             {
80                 return types::Function::Error;
81             }
82         }
83     }
84     else if (in.size() == 1 + static_cast<size_t>(files->getSize()) && _iRetCount <= 1)
85     {
86         // the user asked to export
87         for (int i = 0; i < _iRetCount; i++)
88         {
89             if (!in[1 + i]->isUserType())
90             {
91                 Scierror(77, _("%s: Wrong type for input argument #%d: ""%s"" expected.\n"), funname, "diagram");
92                 return types::Function::Error;
93             }
94         }
95         for (int i = 0; i < _iRetCount; i++)
96         {
97             wchar_t* fullName = getFullFilenameW(files->get(i));
98             char* f = wide_string_to_UTF8(fullName);
99             FREE(fullName);
100             bool success = exportFile(1 + i, f, in[1 + i]);
101             FREE(f);
102             if (!success)
103             {
104                 return types::Function::Error;
105             }
106         }
107     }
108     else
109     {
110         // report a comprehensible error message
111         if (in.size() == 1)
112         {
113             Scierror(77, _("%s: Wrong number of output arguments: %d expected.\n"), funname, files->getSize());
114         }
115         else if (in.size() == 1 + static_cast<size_t>(files->getSize()))
116         {
117             Scierror(77, _("%s: Wrong number of output arguments: %d expected.\n"), funname, 0);
118         }
119         else
120         {
121             Scierror(77, _("%s: Wrong number of input arguments: %d expected.\n"), funname, 1);
122         }
123         return types::Function::Error;
124     }
125
126     return types::Function::OK;
127 }
128 /*--------------------------------------------------------------------------*/
129 static types::InternalType* importFile(char const* file)
130 {
131     // create a diagram
132     org_scilab_modules_scicos::Controller controller;
133     ScicosID uid = controller.createObject(DIAGRAM);
134
135     // load it
136     if (XMIResource(uid).load(file) != 0)
137     {
138         Scierror(999, _("%s: Unable to load \"%s\" .\n"), funname, file);
139         return nullptr;
140     }
141
142     types::InternalType* pIT = view_scilab::Adapters::instance().allocate_view(uid, DIAGRAM);
143     return pIT;
144 }
145 /*--------------------------------------------------------------------------*/
146 static bool exportFile(int index, char const* file, types::InternalType* type)
147 {
148     // check that the passed argument is a diagram
149     const model::BaseObject* o = view_scilab::Adapters::instance().descriptor(type);
150     if (o == nullptr || o->kind() != DIAGRAM)
151     {
152         Scierror(77, _("%s: Wrong type for input argument #%d: ""%s"" expected.\n"), funname, index, "diagram");
153         return false;
154     }
155
156     if (XMIResource(o->id()).save(file) < 0)
157     {
158         Scierror(999, _("%s: Unable to save \"%s\" .\n"), funname, file);
159         return false;
160
161     }
162
163     return true;
164 }
165 /*--------------------------------------------------------------------------*/