31 #include <libFreeWRL.h>
33 #include "../vrml_parser/Structs.h"
34 #include "../main/headers.h"
36 #include "../x3d_parser/Bindable.h"
38 #include "../opengl/OpenGL_Utils.h"
39 #include "../scenegraph/RenderFuncs.h"
74 static layout_scale_item default_layout_scale_item = {{1.0f,1.0f},{LAYOUT_FRACTION,LAYOUT_FRACTION}};
77 Stack *layout_scale_stack;
79 void *Component_Layout_constructor(){
84 void Component_Layout_init(
struct tComponent_Layout *t){
87 t->prv = Component_Layout_constructor();
94 void Component_Layout_clear(
struct tComponent_Text *t){
107 #define strcasecmp _stricmp
113 {
"LEFT",LAYOUT_LEFT},
114 {
"CENTER",LAYOUT_CENTER},
115 {
"RIGHT",LAYOUT_RIGHT},
116 {
"BOTTOM",LAYOUT_BOTTOM},
118 {
"NONE",LAYOUT_NONE},
119 {
"WORLD",LAYOUT_WORLD},
120 {
"FRACTION",LAYOUT_FRACTION},
121 {
"PIXEL",LAYOUT_PIXEL},
122 {
"STRETCH",LAYOUT_STRETCH},
125 int lookup_layoutmode(
char *cmode){
132 lm = &layoutmodes[i];
133 if(!strcasecmp(lm->key,cmode)){
138 }
while(layoutmodes[i].
key);
141 void prep_Layout(
struct X3D_Node *_node);
142 void fin_Layout(
struct X3D_Node *_node);
143 void getPickrayXY(
int *x,
int *y);
144 void prep_Viewport(
struct X3D_Node * node);
145 void fin_Viewport(
struct X3D_Node * node);
149 void prep_LayoutGroup(
struct X3D_Node *_node){
150 if(_node->_nodeType == NODE_LayoutGroup){
166 FW_GL_SCALE_F(1.0f/lsi.scale[0],1.0f/lsi.scale[1],1.0f);
168 if(node->viewport) prep_Viewport(node->viewport);
171 if(node->layout) prep_Layout(node->layout);
174 void child_LayoutGroup(
struct X3D_Node *_node){
175 if(_node->_nodeType == NODE_LayoutGroup){
187 if(!rs->render_vp && !rs->render_collision){
190 vportstack = (
Stack *)tg->Mainloop._vportstack;
191 ivpvis = currentviewportvisible(vportstack);
193 setcurrentviewport(vportstack);
201 prep_sibAffectors((
struct X3D_Node*)node,&node->__sibAffectors);
202 normalChildren(node->children);
203 fin_sibAffectors((
struct X3D_Node*)node,&node->__sibAffectors);
207 void fin_LayoutGroup(
struct X3D_Node *_node){
208 if(_node->_nodeType == NODE_LayoutGroup){
216 if(node->layout) fin_Layout(node->layout);
217 if(node->viewport) fin_Viewport(node->viewport);
225 void compile_Layout(
struct X3D_Node *_node){
231 node->_align.p[0] = lookup_layoutmode(node->align.p[0]->strptr);
232 k = node->align.n -1;
233 node->_align.p[1] = lookup_layoutmode(node->align.p[k]->strptr);
234 node->_offsetUnits.p[0] = lookup_layoutmode(node->offsetUnits.p[0]->strptr);
235 k = node->offsetUnits.n -1;
236 node->_offsetUnits.p[1] = lookup_layoutmode(node->offsetUnits.p[k]->strptr);
237 node->_scaleMode.p[0] = lookup_layoutmode(node->scaleMode.p[0]->strptr);
238 k = node->scaleMode.n -1;
239 node->_scaleMode.p[1] = lookup_layoutmode(node->scaleMode.p[k]->strptr);
240 node->_sizeUnits.p[0] = lookup_layoutmode(node->sizeUnits.p[0]->strptr);
241 k = node->sizeUnits.n -1;
242 node->_sizeUnits.p[1] = lookup_layoutmode(node->sizeUnits.p[k]->strptr);
245 void check_compile_layout_required(
struct X3D_Node *node){
250 void prep_Layout(
struct X3D_Node *_node){
254 float offsetpx[2], differential_scale;
268 vportstack = (
Stack *)tg->Mainloop._vportstack;
269 pvport = stack_top(
ivec4,vportstack);
272 check_compile_layout_required(_node);
275 if(node->_sizeUnits.p[0] == LAYOUT_PIXEL)
276 vport.W =(int)node->size.p[0];
278 vport.W = (
int)(pvport.W * node->size.p[0]);
279 if(node->_sizeUnits.p[1] == LAYOUT_PIXEL)
280 vport.H = (int)(node->size.p[1]);
282 vport.H = (int)(pvport.H * node->size.p[1]);
285 if(node->_align.p[0] == LAYOUT_LEFT)
287 else if(node->_align.p[0] == LAYOUT_RIGHT)
288 vport.X = (pvport.X + pvport.W) - vport.W;
290 vport.X = (pvport.X + pvport.W/2) - vport.W/2;
292 if(node->_align.p[1] == LAYOUT_BOTTOM)
294 else if(node->_align.p[1] == LAYOUT_TOP)
295 vport.Y = (pvport.Y + pvport.H) - vport.H;
297 vport.Y = (pvport.Y + pvport.H/2) - vport.H/2;
300 if(node->_offsetUnits.p[0] == LAYOUT_PIXEL)
301 offsetpx[0] = node->offset.p[0];
303 offsetpx[0] = pvport.W * node->offset.p[0];
304 if(node->_offsetUnits.p[1] == LAYOUT_PIXEL)
305 offsetpx[1] = node->offset.p[1];
307 offsetpx[1] = pvport.H * node->offset.p[1];
310 vport.X += (int)offsetpx[0];
311 vport.Y += (int)offsetpx[1];
314 if(!rs->render_vp && !rs->render_collision){
315 if(rs->render_sensitive){
316 int mouseX, mouseY, inside;
318 getPickrayXY(&mouseX, &mouseY);
321 inside = pointinsideviewport(vport,pt);
328 pushviewport(vportstack, vport);
329 setcurrentviewport(vportstack);
333 glEnable(GL_SCISSOR_TEST);
334 glScissor(vport.X,vport.Y,vport.W,vport.H);
335 glClearColor(1.0f,1.0f,0.0f,.2f);
336 glClear(GL_COLOR_BUFFER_BIT);
337 glDisable(GL_SCISSOR_TEST);
343 differential_scale = ((float)vport.H/(
float)pvport.H)/((
float)vport.W/(float)pvport.W);
344 scale[0] = scale[1] = 1.0;
345 if(node->_scaleMode.p[0] == LAYOUT_PIXEL)
346 scale[0] = 2.0/(double)(vport.W);
347 if(node->_scaleMode.p[0] == LAYOUT_WORLD)
349 else if(node->_scaleMode.p[0] == LAYOUT_FRACTION)
352 if(node->_scaleMode.p[1] == LAYOUT_PIXEL)
353 scale[1] = 2.0/(double)(vport.H);
354 if(node->_scaleMode.p[1] == LAYOUT_WORLD)
356 else if(node->_scaleMode.p[1] == LAYOUT_FRACTION)
361 if(node->_scaleMode.p[0] == LAYOUT_STRETCH)
362 scale[0] = scale[1] * differential_scale;
363 if(node->_scaleMode.p[1] == LAYOUT_STRETCH)
364 scale[1] = scale[0] * 1.0f/differential_scale;
365 node->_scale.p[0] = (float) scale[0];
366 node->_scale.p[1] = (float) scale[1];
369 if(!rs->render_vp ) {
371 FW_GL_SCALE_F(node->_scale.p[0],node->_scale.p[1],1.0f);
372 lsi.scale[0] = (float)scale[0];
373 lsi.scale[1] = (float)scale[1];
374 lsi.scalemode[0] = node->_scaleMode.p[0];
375 lsi.scalemode[1] = node->_scaleMode.p[1];
380 lsi.scalemode[0] = LAYOUT_FRACTION;
381 lsi.scalemode[1] = LAYOUT_FRACTION;
386 void fin_Layout(
struct X3D_Node *_node){
402 if(!rs->render_vp && !rs->render_collision){
403 vportstack = (
Stack *)tg->Mainloop._vportstack;
404 popviewport(vportstack);
405 setcurrentviewport(vportstack);
411 if((node->_renderFlags & VF_Viewpoint) == VF_Viewpoint) {
412 FW_GL_SCALE_F(1.0f/node->_scale.p[0],1.0f/node->_scale.p[1],1.0f);
419 void prep_Layer(
struct X3D_Node * _node);
420 void child_Layer(
struct X3D_Node * _node);
421 void fin_Layer(
struct X3D_Node * _node);
424 void prep_LayoutLayer(
struct X3D_Node *_node){
427 if(layoutlayer->layout)
428 prep_Layout(layoutlayer->layout);
431 void child_LayoutLayer(
struct X3D_Node *_node){
434 void fin_LayoutLayer(
struct X3D_Node *_node){
437 if(layoutlayer->layout)
438 fin_Layout(layoutlayer->layout);
442 void prep_ScreenGroup(
struct X3D_Node *node){
443 if(node && node->_nodeType == NODE_ScreenGroup){
449 vportstack = (
Stack *)tg->Mainloop._vportstack;
450 pvport = stack_top(
ivec4,vportstack);
452 sx = 1.0f/(float)(pvport.W);
453 sy = 1.0f/(float)(pvport.H);
457 FW_GL_SCALE_F(sx,sy,sx);
462 void child_ScreenGroup(
struct X3D_Node *_node){
464 prep_sibAffectors((
struct X3D_Node*)node,&node->__sibAffectors);
465 normalChildren(node->children);
466 fin_sibAffectors((
struct X3D_Node*)node,&node->__sibAffectors);
468 void fin_ScreenGroup(
struct X3D_Node *node){
469 if(node && node->_nodeType == NODE_ScreenGroup){