Merge branch 'main/rendor-staging' into fixes
[ryzomcore.git] / nel / src / gui / group_modal.cpp
blobafc0388a5828b5d1b0c69d4285b326a02479a924
1 // Ryzom - MMORPG Framework <http://dev.ryzom.com/projects/ryzom/>
2 // Copyright (C) 2010 Winch Gate Property Limited
3 //
4 // This source file has been modified by the following contributors:
5 // Copyright (C) 2013 Laszlo KIS-ADAM (dfighter) <dfighter1985@gmail.com>
6 //
7 // This program is free software: you can redistribute it and/or modify
8 // it under the terms of the GNU Affero General Public License as
9 // published by the Free Software Foundation, either version 3 of the
10 // License, or (at your option) any later version.
12 // This program is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 // GNU Affero General Public License for more details.
17 // You should have received a copy of the GNU Affero General Public License
18 // along with this program. If not, see <http://www.gnu.org/licenses/>.
21 #include "stdpch.h"
22 #include "nel/gui/group_modal.h"
23 #include "nel/gui/interface_element.h"
24 #include "nel/misc/xml_auto_ptr.h"
25 #include "nel/gui/view_renderer.h"
26 #include "nel/misc/i_xml.h"
28 using namespace std;
30 #ifdef DEBUG_NEW
31 #define new DEBUG_NEW
32 #endif
34 namespace NLGUI
37 NLMISC_REGISTER_OBJECT(CViewBase, CGroupModal, std::string, "modal");
39 // ***************************************************************************
40 CGroupModal::CGroupModal(const TCtorParam &param)
41 : CGroupFrame(param)
43 SpawnOnMousePos= true;
44 ExitClickOut= true;
45 ExitClickL= false;
46 ExitClickR= false;
47 ExitKeyPushed = false;
48 ForceInsideScreen= false;
49 SpawnMouseX= SpawnMouseY= 0;
50 _MouseDeltaX= _MouseDeltaY= 0;
51 //By default, modal are escapable
52 _Escapable= true;
56 std::string CGroupModal::getProperty( const std::string &name ) const
58 if( name == "mouse_pos" )
60 return NLMISC::toString( SpawnOnMousePos );
62 else
63 if( name == "exit_click_out" )
65 return NLMISC::toString( ExitClickOut );
67 else
68 if( name == "exit_click_l" )
70 return NLMISC::toString( ExitClickL );
72 else
73 if( name == "exit_click_r" )
75 return NLMISC::toString( ExitClickR );
77 else
78 if( name == "exit_click_b" )
80 if( ExitClickL == ExitClickR )
81 return NLMISC::toString( ExitClickL );
82 else
83 return "false";
85 else
86 if( name == "force_inside_screen" )
88 return NLMISC::toString( ForceInsideScreen );
90 else
91 if( name == "category" )
93 return Category;
95 else
96 if( name == "onclick_out" )
98 return OnClickOut;
100 else
101 if( name == "onclick_out_params" )
103 return OnClickOutParams;
105 else
106 if( name == "onpostclick_out" )
108 return OnPostClickOut;
110 else
111 if( name == "onpostclick_out_params" )
113 return OnPostClickOutParams;
115 else
116 if( name == "exit_key_pushed" )
118 return NLMISC::toString( ExitKeyPushed );
120 else
121 return CGroupFrame::getProperty( name );
124 void CGroupModal::setProperty( const std::string &name, const std::string &value )
126 if( name == "mouse_pos" )
128 bool b;
129 if( NLMISC::fromString( value, b ) )
130 SpawnOnMousePos = b;
131 return;
133 else
134 if( name == "exit_click_out" )
136 bool b;
137 if( NLMISC::fromString( value, b ) )
138 ExitClickOut = b;
139 return;
141 else
142 if( name == "exit_click_l" )
144 bool b;
145 if( NLMISC::fromString( value, b ) )
146 ExitClickL = b;
147 return;
149 else
150 if( name == "exit_click_r" )
152 bool b;
153 if( NLMISC::fromString( value, b ) )
154 ExitClickR = b;
155 return;
157 else
158 if( name == "exit_click_b" )
160 bool b;
161 if( NLMISC::fromString( value, b ) )
163 ExitClickL = ExitClickR = b;
165 return;
167 else
168 if( name == "force_inside_screen" )
170 bool b;
171 if( NLMISC::fromString( value, b ) )
172 ForceInsideScreen = b;
173 return;
175 else
176 if( name == "category" )
178 Category = value;
179 return;
181 else
182 if( name == "onclick_out" )
184 OnClickOut = value;
185 return;
187 else
188 if( name == "onclick_out_params" )
190 OnClickOutParams = value;
191 return;
193 else
194 if( name == "onpostclick_out" )
196 OnPostClickOut = value;
197 return;
199 else
200 if( name == "onpostclick_out_params" )
202 OnPostClickOutParams = value;
203 return;
205 else
206 if( name == "exit_key_pushed" )
208 bool b;
209 if( NLMISC::fromString( value, b ) )
210 ExitKeyPushed = b;
211 return;
213 else
214 CGroupFrame::setProperty( name, value );
219 xmlNodePtr CGroupModal::serialize( xmlNodePtr parentNode, const char *type ) const
221 xmlNodePtr node = CGroupFrame::serialize( parentNode, type );
222 if( node == NULL )
223 return NULL;
225 xmlSetProp( node, BAD_CAST "type", BAD_CAST "modal" );
226 xmlSetProp( node, BAD_CAST "mouse_pos", BAD_CAST NLMISC::toString( SpawnOnMousePos ).c_str() );
227 xmlSetProp( node, BAD_CAST "exit_click_out", BAD_CAST NLMISC::toString( ExitClickOut ).c_str() );
228 xmlSetProp( node, BAD_CAST "exit_click_l", BAD_CAST NLMISC::toString( ExitClickL ).c_str() );
229 xmlSetProp( node, BAD_CAST "exit_click_r", BAD_CAST NLMISC::toString( ExitClickR ).c_str() );
231 if( ExitClickL == ExitClickR )
232 xmlSetProp( node, BAD_CAST "exit_click_b", BAD_CAST NLMISC::toString( ExitClickL ).c_str() );
234 xmlSetProp( node, BAD_CAST "force_inside_screen", BAD_CAST NLMISC::toString( ForceInsideScreen ).c_str() );
235 xmlSetProp( node, BAD_CAST "category", BAD_CAST Category.c_str() );
236 xmlSetProp( node, BAD_CAST "onclick_out", BAD_CAST OnClickOut.c_str() );
237 xmlSetProp( node, BAD_CAST "onclick_out_params", BAD_CAST OnClickOutParams.c_str() );
238 xmlSetProp( node, BAD_CAST "onpostclick_out", BAD_CAST OnPostClickOut.c_str() );
239 xmlSetProp( node, BAD_CAST "onpostclick_out_params", BAD_CAST OnPostClickOutParams.c_str() );
240 xmlSetProp( node, BAD_CAST "exit_key_pushed", BAD_CAST NLMISC::toString( ExitKeyPushed ).c_str() );
242 return node;
245 // ***************************************************************************
246 bool CGroupModal::parse (xmlNodePtr cur, CInterfaceGroup *parentGroup)
248 if(!CGroupFrame::parse(cur, parentGroup))
249 return false;
251 // read modal option
252 CXMLAutoPtr prop;
253 prop = xmlGetProp (cur, (xmlChar*)"mouse_pos");
254 if (prop) SpawnOnMousePos= convertBool(prop);
255 prop = xmlGetProp (cur, (xmlChar*)"exit_click_out");
256 if (prop) ExitClickOut= convertBool(prop);
257 prop = xmlGetProp (cur, (xmlChar*)"exit_click_l");
258 if (prop) ExitClickL= convertBool(prop);
259 prop = xmlGetProp (cur, (xmlChar*)"exit_click_r");
260 if (prop) ExitClickR= convertBool(prop);
261 prop = xmlGetProp (cur, (xmlChar*)"exit_click_b");
262 if (prop) ExitClickR= ExitClickL= convertBool(prop);
263 prop = xmlGetProp (cur, (xmlChar*)"force_inside_screen");
264 if (prop) ForceInsideScreen= convertBool(prop);
265 prop = xmlGetProp (cur, (xmlChar*)"category");
266 if (prop) Category= (const char *) prop;
267 prop = xmlGetProp (cur, (xmlChar*)"onclick_out");
268 if (prop) OnClickOut = (const char *) prop;
269 prop = xmlGetProp (cur, (xmlChar*)"onclick_out_params");
270 if (prop) OnClickOutParams = (const char *) prop;
271 prop = xmlGetProp (cur, (xmlChar*)"onpostclick_out");
272 if (prop) OnPostClickOut = (const char *) prop;
273 prop = xmlGetProp (cur, (xmlChar*)"onpostclick_out_params");
274 if (prop) OnPostClickOutParams = (const char *) prop;
275 prop = xmlGetProp (cur, (xmlChar*)"exit_key_pushed");
276 if (prop) ExitKeyPushed= convertBool(prop);
278 // Force parent hotspot for spawn on mouse
279 if(SpawnOnMousePos)
280 setParentPosRef(Hotspot_BL);
282 // bkup x/y as the deltas.
283 _MouseDeltaX= getX();
284 _MouseDeltaY= getY();
286 // Modals are disabled by default
287 _Active = false;
289 return true;
292 // ***************************************************************************
293 void CGroupModal::updateCoords ()
295 // if snap to mouse pos.
296 if(SpawnOnMousePos)
298 // Special for menu for instance: If the size is bigger or equal to the screen, keep 0, because will be clipped just after
299 CViewRenderer &rVR = *CViewRenderer::getInstance();
300 uint32 w,h;
301 rVR.getScreenSize(w,h);
302 if(_W>=(sint32)w && _H>=(sint32)h)
304 _X= _Y= 0;
306 else
308 // change coords
309 _X= SpawnMouseX+_MouseDeltaX;
310 _Y= SpawnMouseY+_MouseDeltaY;
314 // update group
315 CGroupFrame::updateCoords();
317 // if snap to mouse pos or ForceInsideScreen
318 if(SpawnOnMousePos || ForceInsideScreen)
320 bool clipped = false;
321 // repos the group according to real size. clip against screen
322 if(_XReal<0)
324 _X+= -_XReal;
325 clipped = true;
327 else
329 if (!SpawnOnMousePos)
330 _X = _MouseDeltaX;
333 if(_XReal+_WReal>_Parent->getW())
335 _X-= _XReal+_WReal-_Parent->getW();
336 clipped =true;
338 else
340 if ((!SpawnOnMousePos) && (_XReal>=0))
341 _X = _MouseDeltaX;
344 if(_YReal<0)
346 _Y+= -_YReal;
347 clipped =true;
349 else
351 if (!SpawnOnMousePos)
352 _Y = _MouseDeltaY;
355 if(_YReal+_HReal>_Parent->getH())
357 _Y-= _YReal+_HReal-_Parent->getH();
358 clipped =true;
360 else
362 if ((!SpawnOnMousePos) && (_YReal>=0))
363 _Y = _MouseDeltaY;
366 if (clipped)
368 CGroupFrame::updateCoords();