Plug rubberbox function :
[scilab.git] / scilab / modules / graphics / sci_gateway / c / sci_rubberbox.c
1 /*
2  * Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  * Copyright (C) 2008 - INRIA - Jean-Baptiste Silvy
4  * Copyright (C) 2012 - DIGITEO - Vincent COUVERT
5  * Copyright (C) 2012 - Scilab Enterprises - Bruno JOFRET
6  *
7  * This file must be used under the terms of the CeCILL.
8  * This source file is licensed as described in the file COPYING, which
9  * you should have received as part of this distribution.  The terms
10  * are also available at
11  * http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt
12  *
13  */
14
15 /*------------------------------------------------------------------------*/
16 /* file: sci_rubberbox.c                                                  */
17 /* desc : interface for rubberbox routine                                 */
18 /*------------------------------------------------------------------------*/
19 #include "gw_graphics.h"
20 #include "stack-c.h"
21 #include "localization.h"
22 #include "getPropertyAssignedValue.h"
23 #include "Scierror.h"
24 #include "JavaInteraction.h"
25 #include "HandleManagement.h"
26 #include "BuildObjects.h"
27 #include "CurrentSubwin.h"
28 #include "getGraphicObjectProperty.h"
29 #include "graphicObjectProperties.h"
30
31 /*--------------------------------------------------------------------------*/
32 static int getInitialRectangle(double initRect[4]);
33 static int getEditionMode(int rhsPos);
34 static int returnRectAndButton(const double *_piJavaValues, int _iSelectedRectSize);
35 /*--------------------------------------------------------------------------*/
36 static int getInitialRectangle(double initRect[4])
37 {
38     int rectNbRow = 0;
39     int rectNbCol = 0;
40     int rectStackPointer = 0;
41     int i;
42     int nbDims;
43     double * rect;
44
45     /* Initial rect is always in first position */
46     GetRhsVar(1, MATRIX_OF_DOUBLE_DATATYPE, &rectNbRow, &rectNbCol, &rectStackPointer);
47
48     /* We have found a matrix of double within the parameters check its dims */
49     nbDims = rectNbCol * rectNbRow;
50
51     if (nbDims != 2 && nbDims != 4)
52     {
53         return -1;
54     }
55
56
57     /* pointer on the stack */
58     rect = getDoubleMatrixFromStack(rectStackPointer);
59
60     /* intialize to 0 */
61     for (i = 0; i < 4; i++)
62     {
63         initRect[i] = 0.0;
64     }
65
66     /* Set specified values */
67     for (i = 0; i < nbDims; i++)
68     {
69         initRect[i] = rect[i];
70     }
71     return 1;
72 }
73 /*--------------------------------------------------------------------------*/
74 static int getEditionMode(int rhsPos)
75 {
76     int stackPointer = 0;
77     int nbRow = 0;
78     int nbCol = 0;
79     BOOL isEditionModeOn;
80     GetRhsVar(rhsPos, MATRIX_OF_BOOLEAN_DATATYPE, &nbRow, &nbCol, &stackPointer);
81
82     if (nbRow * nbCol != 1)
83     {
84         return -1;
85     }
86
87     isEditionModeOn = *istk(stackPointer);
88     if (isEditionModeOn)
89     {
90         return 1;
91     }
92     else
93     {
94         return 0;
95     }
96
97 }
98 /*--------------------------------------------------------------------------*/
99 static int returnRectAndButton(const double *_piJavaValues, int _iSelectedRectSize)
100 {
101     int zero = 0;
102     int one = 1;
103     int rectStackPointer = 0;
104     int i = 0;
105     int j = 0;
106
107     // button < 0 means user cancelled selection so return [] or [], []
108     if (_piJavaValues[0] < 0)
109     {
110         CreateVar(Rhs + 1, MATRIX_OF_DOUBLE_DATATYPE, &zero, &zero, &rectStackPointer);
111         LhsVar(1) = Rhs + 1;
112         if (Lhs >= 2)
113         {
114             CreateVar(Rhs + 2, MATRIX_OF_DOUBLE_DATATYPE, &zero, &zero, &rectStackPointer);
115             LhsVar(2) = Rhs + 2;
116         }
117         PutLhsVar();
118         return 0;
119     }
120
121     /* return rectangle */
122     CreateVar(Rhs + 1, MATRIX_OF_DOUBLE_DATATYPE, &one, &_iSelectedRectSize, &rectStackPointer);
123     for ( i = 0; i < _iSelectedRectSize / 2; i++)
124     {
125         j = i + _iSelectedRectSize / 2;
126         stk(rectStackPointer)[i] = _piJavaValues[i + 1];
127         stk(rectStackPointer)[j] = _piJavaValues[i + 4];
128     }
129     LhsVar(1) = Rhs + 1;
130
131     /* return button */
132     if (Lhs >= 2)
133     {
134         int buttonStackPointer = 0;
135         CreateVar(Rhs + 2, MATRIX_OF_DOUBLE_DATATYPE, &one, &one, &buttonStackPointer);
136         *stk(buttonStackPointer) = _piJavaValues[0];
137         LhsVar(2) = Rhs + 2;
138     }
139
140     PutLhsVar();
141     return 0;
142 }
143 /*--------------------------------------------------------------------------*/
144 int sci_rubberbox(char * fname, unsigned long fname_len)
145 {
146
147     /* [final_rect, btn] = rubberbox([initial_rect],[edition_mode]) */
148
149     int button = 0;
150     double initialRect[4] = {0.0, 0.0, 0.0, 0.0};
151     int initialRectSize = 0;
152
153     double *piJavaValues = NULL;
154     char *pFigureUID;
155     char *pSubwinUID = getOrCreateDefaultSubwin();
156     int iView = 0;
157     int* piView = &iView;
158
159     BOOL bClickMode = TRUE;
160
161     CheckRhs(0, 2);
162     CheckLhs(1, 2);
163     // iView == 1 => 2D
164     // else 3D
165     getGraphicObjectProperty(pSubwinUID, __GO_VIEW__, jni_int, &piView);
166     getGraphicObjectProperty(pSubwinUID, __GO_PARENT__, jni_string, &pFigureUID);
167
168     if (Rhs == 0)
169     {
170         /* rubberbox() */
171         bClickMode = TRUE;
172         initialRectSize = 0;
173     }
174     else if (Rhs == 1)
175     {
176         // Check we are running 2D view rubberbox,
177         // Otherwise initial_rect and edition_mode are not usable.
178         if (iView == 1) // 3D
179         {
180             Scierror(999, _("%s: Can not run rubberbox on a 3D view with initial_rect or edition_mode option. See help for more information.\n"), fname);
181             return -1;
182         }
183         /* rubberbox(initial_rect) or rubberbox(edition_mode) */
184         if (GetType(1) == sci_matrix)
185         {
186             /* rubberbox(initial_rect) */
187             if (getInitialRectangle(initialRect) == 1)
188             {
189                 bClickMode = TRUE;
190                 initialRectSize = 4;
191             }
192             else
193             {
194                 Scierror(999, _("%s: Wrong size for input argument #%d: Vector of size %d or %d expected.\n"), fname, 1, 2, 4);
195                 return -1;
196             }
197         }
198         else if (GetType(1) == sci_boolean)
199         {
200             /* rubberbox(editionMode) */
201             int editionModeStatus = getEditionMode(1);
202             initialRectSize = 0;
203             if (editionModeStatus == 1)
204             {
205                 /* rubberbox(%t) */
206                 bClickMode = FALSE;
207             }
208             else if (editionModeStatus == 0)
209             {
210                 /* rubberbox(%f) */
211                 bClickMode = TRUE;
212             }
213             else
214             {
215                 Scierror(999, _("%s: Wrong size for input argument #%d: A boolean expected\n."), fname, 1);
216                 return -1;
217             }
218         }
219         else
220         {
221             /* Wrong parameter specified, neither edition mode nor intial rect */
222             Scierror(999, _("%s: Wrong type for input argument #%d: Real row vector or a boolean expected.\n"), fname, 1);
223             return -1;
224         }
225     }
226     else if (Rhs == 2)
227     {
228         /* rubberbox(initial_rect, edition_mode) */
229
230         /* Default values, intial rect and edition mode to false */
231         double initialRect[4] = {0.0, 0.0, 0.0, 0.0};
232         int editionModeStatus;
233
234         // Check we are running 2D view rubberbox,
235         // Otherwise initial_rect and edition_mode are not usable.
236         if (iView == 1) // 3D
237         {
238             Scierror(999, _("%s: Can not run rubberbox on a 3D view with initial_rect or edition_mode option. See help for more information.\n"), fname);
239             return -1;
240         }
241
242         if (GetType(1) != sci_matrix)
243         {
244             Scierror(999, _("%s: Wrong type for input argument #%d: Real row vector expected.\n"), fname, 1);
245             return -1;
246         }
247
248         if (GetType(2) != sci_boolean)
249         {
250             Scierror(999, _("%s: Wrong type for input argument #%d: A boolean expected.\n"), fname, 2);
251             return -1;
252         }
253
254         /* Getting initial rect */
255         if (getInitialRectangle(initialRect) != 1)
256         {
257             Scierror(999, _("%s: Wrong size for input argument #%d: Vector of size %d or %d expected.\n"), fname, 1, 2, 4);
258             return -1;
259         }
260
261         /* Getting edition mode */
262         editionModeStatus = getEditionMode(2);
263
264         if (editionModeStatus == 1)
265         {
266             /* rubberbox(initial_rect, %t) */
267             /*
268             ** Force click mode !!! Don't know to drag
269             ** if first point is set using init rect
270             */
271             bClickMode = TRUE;
272         }
273         else if (editionModeStatus == 0)
274         {
275             /* rubberbox(initial_rect, %f) */
276             bClickMode = TRUE;
277         }
278         else
279         {
280             Scierror(999, _("%s: Wrong size for input argument #%d: A boolean expected\n."), fname, 2);
281             return -1;
282         }
283
284     }
285
286
287     if (bClickMode == TRUE)
288     {
289         piJavaValues = javaClickRubberBox(pFigureUID, initialRect, initialRectSize);
290     }
291     else
292     {
293         piJavaValues = javaDragRubberBox(pFigureUID);
294     }
295     /* Put values into the stack and return */
296     if (iView == 1)
297     {
298         return returnRectAndButton(piJavaValues, 6);
299     }
300     else
301     {
302         return returnRectAndButton(piJavaValues, 4);
303     }
304 }
305
306 /*--------------------------------------------------------------------------*/