OCC22105 Suspicious call to XOpenDisplay() in OSD_FontMgr class
[occt.git] / src / OpenGl / OpenGl_view.cxx
CommitLineData
7fd59977 1/***********************************************************************
2
3FONCTION :
4----------
5File OpenGl_view :
6
7
8REMARQUES:
9----------
10
11An implementation of the PHIGS viewing pipeline
12
13This module provides services for setting view representations and view
14indices, viewport management, coordinate conversion routines and help
15functions.
16
17The corresponding header file is telem_view.h
18
19
20HISTORIQUE DES MODIFICATIONS :
21--------------------------------
22xx-xx-xx : xxx ; Creation.
2311-03-96 : FMN ; Correction warning compilation
2420-03-96 : CAL ; Modif de TelClearViews
25appel a call_tox_getscreen pour effacer tout
26meme apres un resize
2701-04-96 : CAL ; Integration MINSK portage WNT
2822-04-96 : FMN ; Suppression prototype inutile.
2925-06-96 : FMN ; Suppression utilisation de glScissor.
3028-06-96 : CAL ; Simplification de TelClearViews
3102-07-96 : FMN ; Suppression WSWSHeight et WSWSWidth
32Suppression de TelSetWSWindow
33Suppression glViewport inutile
3403-07-96 : FMN ; A une workstation correspond une vue.
3512-07-96 : FMN ; Correction calcul matrice orientatione.
3617-07-96 : FMN ; Ajout clear pour le zbuffer.
3721-10-96 : FMN ; Suppression LMC_COLOR fait dans OpenGl_execstruct.c
3824-01-97 : CAL ; Suppression code inutile (DEBUG_ONLY)
3930-06-97 : FMN ; Suppression OpenGl_telem_light.h
4027-08-97 : FMN ; Ajout glDepthMask avant le clear (PRO8939)
4109-12-97 : FMN ; Prise en compte environnement mapping.
4203-03-98 : FMN ; Suppression variable externe TglWhetherPerspective
4313-03-98 : FMN ; Suppression variable WSNeedsClear
4410-04-98 : CAL ; Suppression du calcul de inverse_matrix
4530-04-98 : FMN ; Suppression variable externe TglUpdateView0
4624-11-98 : FMN ; PRO16215: Suppression test sur le GL_MAX_CLIP_PLANES
47Si OpenGL n'a pas de plans de clipping on ne le simule pas.
4824-11-98 : FMN ; Correction sur la gestion de la perspective (cf Programming Guide)
49- Suppression du test (prp between front and back planes)
50- Suppression matrice perspective (modify the next two cells to change clipping policy)
51Ces modifs sont necessaires pour pouvoir mettre le prp entre le Front et Back plane
52
53************************************************************************/
54
55#define BUC60920 /* GG 010601
56Change the z buffer comparaison for minimizing
57unavailable or unviewable drawing of pixels in the same plane
58*/
59
60#define BUC61044 /* 25/10/01 SAV ; added functionality to control gl depth testing
61from higher API */
62
63#define OCC1188 /* SAV 23/12/02 TelClearBackground() draws background texture
64if any was defined
65*/
66
67
68/*----------------------------------------------------------------------*/
69/*
70* Includes
71*/
72
73#include <OpenGl_tgl_all.hxx>
74
75#include <stddef.h>
76#include <stdio.h>
77#include <string.h>
78#include <stdlib.h>
79
80#include <OpenGl_cmn_varargs.hxx>
81#include <OpenGl_telem.hxx>
82#include <OpenGl_telem_util.hxx>
83#include <OpenGl_telem_attri.hxx>
84#include <OpenGl_telem_view.hxx>
85#include <OpenGl_tsm.hxx>
86#include <OpenGl_tsm_ws.hxx>
87#include <OpenGl_txgl.hxx>
88#include <OpenGl_Memory.hxx>
89
90/*----------------------------------------------------------------------*/
91/*
92* Variable globales
93*/
94
95EXPORT extern GLboolean env_walkthrow; /* definit dans OpenGl_togl_begin.c */
96/* OCC18942: The new perspective projection matrix is off by default */
97EXPORT extern GLboolean env_sym_perspective; /* defined in OpenGl_togl_begin.c */
98
99/*----------------------------------------------------------------------*/
100/*
101* Constantes
102*/
103
104#define NO_TRACE_MAT
105#define NO_TRACE_MATRIX
106#define NO_PRINT
107
108#define ENVTEX
109
110
111/*----------------------------------------------------------------------*/
112/*
113* Prototypes
114*/
115
116#ifdef DEB
117static void pr_matrix( Tmatrix3 );
118#endif
119
120
121/*----------------------------------------------------------------------*/
122/*
123* Type definitions
124*/
125
126struct TEL_VIEW_DATA
127{
128 TEL_VIEW_REP vrep;
129#ifdef CAL_100498
130 Tmatrix3 inverse_matrix;/* accelerates UVN2XYZ conversion */
131#endif
132 IMPLEMENT_MEMORY_OPERATORS
133};
134typedef TEL_VIEW_DATA *tel_view_data; /* Internal data stored for every view rep */
135
136/*----------------------------------------------------------------------*/
137/*
138* Variables statiques
139*/
140
141static void set_clipplanes( tel_view_rep );
142#ifdef CAL_100498
143static void TelEvalInverseMatrix( Tfloat*, Tfloat*, Tfloat*, /*vrp,vpn,vup*/
144 Tfloat, Tmatrix3 ); /*vpd,inverse*/
145#endif
146static Tmatrix3 ident = {
147 { ( float )1.0, ( float )0.0, ( float )0.0, ( float )0.0 },
148 { ( float )0.0, ( float )1.0, ( float )0.0, ( float )0.0 },
149 { ( float )0.0, ( float )0.0, ( float )1.0, ( float )0.0 },
150 { ( float )0.0, ( float )0.0, ( float )0.0, ( float )1.0 }
151};
152
153/*----------------------------------------------------------------------*/
154/*+
155Qsearch number comparison routine
156
157Compares view ids during sorting of the list of defined views
158for a workstation
159+*/
160
161/*----------------------------------------------------------------------*/
162/*+
163Evaluate View Mapping Matrix
164
165This routine computes the mapping matrix based on the Window and Viewport
166limits, Projection type and View plane, Front plane and Back plane
167distances.
168+*/
169
170static void
171EvalViewMappingMatrix( tel_view_mapping mapping /* View Mapping */,
172 Tint *error_ind /* Out: Error Indicator */,
173 Tmatrix3 mat /* Out: Mapping Matrix * */,
174 Tint flag,
175 Tfloat cx,
176 Tfloat cy,
177 Tint clip_flag,
178 Tlimit3 *clip_limit
179 )
180{
181 Tfloat gx, gy, xsf, ysf, zsf;
182 Tfloat fpd, bpd;
183
184 /* OCC18942 */
185 Tfloat n, f, r, l, t, b, Zprp, dx, dy, VPD;
186
187 /* FSXXX */
188 /* GLint gdtmp; */
189 Tlimit3 vp = { ( float )-1.0, ( float )1.0, ( float )-1.0, ( float )1.0, ( float )1.0, ( float )-1.0 };
190 Tmatrix3 pmat = { { ( float )1.0, ( float )0.0, ( float )0.0, ( float )0.0 },
191 { ( float )0.0, ( float )1.0, ( float )0.0, ( float )0.0 },
192 { ( float )0.0, ( float )0.0, ( float )1.0, ( float )0.0 },
193 { ( float )0.0, ( float )0.0, ( float )0.0, ( float )1.0 } };
194 Tmatrix3 mmat = { { ( float )1.0, ( float )0.0, ( float )0.0, ( float )0.0 },
195 { ( float )0.0, ( float )1.0, ( float )0.0, ( float )0.0 },
196 { ( float )0.0, ( float )0.0, ( float )1.0, ( float )0.0 },
197 { ( float )0.0, ( float )0.0, ( float )0.0, ( float )1.0 } };
198
199 fpd = mapping->fpd;
200 bpd = mapping->bpd;
201
202 /* invalid window */
203 if( mapping->window.xmin >= mapping->window.xmax ||
204 mapping->window.ymin >= mapping->window.ymax )
205 {
206 *error_ind = 1;
207 return;
208 }
209
210 /* invalid viewport */
211 if( mapping->viewport.xmin >= mapping->viewport.xmax ||
212 mapping->viewport.ymin >= mapping->viewport.ymax ||
213 mapping->viewport.zmin >= mapping->viewport.zmax )
214 {
215 *error_ind = 2;
216 return;
217 }
218
219 /* invalid back/front plane distances */
220 if( mapping->bpd >= mapping->fpd )
221 {
222 *error_ind = 3;
223 return;
224 }
225
226 /* prp between front and back planes */
227 if (!env_walkthrow)
228 {
229 if( mapping->prp[2] < mapping->fpd &&
230 mapping->prp[2] > mapping->bpd )
231 {
232 *error_ind = 4;
233 return;
234 }
235 }
236
237 if( mapping->prp[2] == mapping->vpd )
238 {
239 *error_ind = 5; /* prp on view plane */
240 return;
241 }
242
243 if( mapping->viewport.xmin < 0 ||
244 mapping->viewport.xmax > 1 ||
245 mapping->viewport.ymin < 0 ||
246 mapping->viewport.ymax > 1 ||
247 mapping->viewport.zmin < 0 ||
248 mapping->viewport.zmax > 1 )
249 {
250 *error_ind = 6; /* viewport limits outside NPC space */
251 return;
252 }
253
254 *error_ind = 0;
255
256 /* OCC18942: Moved here while debugging perspective projection matrix */
257 /* centers */
258 if( flag == 0 )
259 {
260 cx = mapping->window.xmin + mapping->window.xmax, cx /= ( float )2.0;
261 cy = mapping->window.ymin + mapping->window.ymax, cy /= ( float )2.0;
262 }
263
264 gx = (cx - mapping->prp[0]) / (mapping->vpd - mapping->prp[2]);
265 gy = (cy - mapping->prp[1]) / (mapping->vpd - mapping->prp[2]);
266
267#ifdef PRINT
268 printf("EvalViewMappingMatrix \n");
269 printf("prp %f %f %f \n", mapping->prp[0], mapping->prp[1], mapping->prp[2]);
270 printf("vpd fpd bpd %f %f %f \n", mapping->vpd, mapping->fpd, mapping->bpd);
271 printf("window limit %f %f %f %f\n", mapping->window.xmin, mapping->window.xmax,
272 mapping->window.ymin, mapping->window.ymax);
273 printf("viewport limit %f %f %f %f\n", mapping->viewport.xmin, mapping->viewport.xmax,
274 mapping->viewport.ymin, mapping->viewport.ymax);
275#endif
276
277 /* projection matrix */
278 if( mapping->proj == TelParallel )
279 {
280
281 pmat[2][0] = -gx; pmat[3][0] = mapping->vpd*gx;
282 pmat[2][1] = -gy; pmat[3][1] = mapping->vpd*gy;
283 }
284 else if ( !env_sym_perspective )/* TelPerspective */
285 {
286 pmat[0][0] = pmat[1][1] = mapping->prp[2] - mapping->vpd;
287 pmat[2][0] = -gx;
288 pmat[2][1] = -gy;
289 pmat[2][3] = ( float )-1.0;
290 pmat[3][0] = mapping->vpd * gx;
291 pmat[3][1] = mapping->vpd * gy;
292 pmat[3][3] = mapping->prp[2];
293
294 /* modify the next two cells to change clipping policy */
295 if (!env_walkthrow)
296 {
297 pmat[2][2] = mapping->prp[2] - ( fpd + bpd );
298 pmat[3][2] = fpd * bpd;
299 }
300 }
301 /* OCC18942: New approach to calculation of mapping (projection) matrix */
302 else
303 {
304 dx = mapping->window.xmax - mapping->window.xmin;
305 dy = mapping->window.ymax - mapping->window.ymin;
306 Zprp = mapping->prp[2];
307 VPD = Zprp - mapping->vpd;
308
309 /*
310 Calculate canonical perspective projection parameters as if we were about
311 to use glFrustum() to create symmetric perspective frustum.
312
313 After the view orientation matrix is applied, the coordinate system origin is located
314 at the VRP and oriented properly. However, the viewplane has width = dx and height = dy
315 and its center (cx, cy, VPD) is not always located at the view Z axis.
316 The canonical perspective projection matrix assumes the eye is located at (0, 0, 0).
317 Thus the old approach resulted in a non-symmetric perspective,
318 as X and Y coordinates of the projection reference point (PRP) were not updated
319 when cx and cy changed. Moreover, such "static" perspective had some other disadvantages,
320 such as non-realistic panning, i.e. instead of moving the eye (or camera) over the model
321 a sort of "frame" moved over the static perspective projection picture,
322 exposing a part of this static picture to the user.
323
324 In order to make the perspective symmetric, we need to translate
325 the coordinate system to PRP before projection.
326 Thus we translate X, Y and Z co-ordinates by -cx, -cy and -Zprp respectively.
327
328 NOTE: mat[i][j] means j-th element of i-th column, as OpenGL accepts the matrices
329 in column-major order, while in C two-dimensional arrays are stored in memory
330 in row-major order!
331
332 VPD is used below instead of near clipping plane dispance (n) in order to simplify
333 calculation of l and r values. If we did not use VPD in the matrix calculation, we would have to
334 project 0.5 * dx, -0.5 * dx, 0.5 * dy and - 0.5 * dy onto the near clipping plane
335 to calculate these values.
336
337 Pending issues:
338 1. It is still necessary to find a way to calculate the perspective projection matrix
339 for TPM_WALKTHROUGH projection model. This projection model is not supported yet
340 by the new code.
341 */
342 r = .5f * dx;
343 l = -r;
344 t = .5f * dy;
345 b = -t;
346 n = Zprp - fpd; f = Zprp - bpd;
347
348 mat[0][0] = 2.f * VPD / (r - l);
349 mat[1][1] = 2.f * VPD / (t - b);
350 mat[2][0] = (r + l) / (r - l);
351 mat[2][1] = (t + b) / (t - b);
352 mat[2][2] = - (f + n) / (f - n);
353 mat[2][3] = -1.f;
354 /*
355 The last column takes into account translation along X, Y and Z axis
356 before projecting. This can be considered as a result of right-multiplying the canonical
357 perspective projection matrix P by a translation matrix T
358 (it differs form the canonical matrix by the last column only):
359 | 1 0 0 -cx |
360 | 0 1 0 -cy |
361 mat = P * T, where T = | 0 0 1 -Zprp |
362 | 0 0 0 1 |
363 */
364 mat[3][0] = -mat[2][0] * Zprp - mat[0][0] * cx;
365 mat[3][1] = -mat[2][1] * Zprp - mat[1][1] * cy;
366 mat[3][2] = -2.f * f * n / (f - n) - mat[2][2] * Zprp;
367 mat[3][3] = Zprp;
368
369#ifdef PRINT
370 printf("r l t b n f: %f %f %f %f %f %f \n", r,l,t,b,n,f);
371 printf( "mapping_matrix (new code):\n" );
372 pr_matrix(mat);
373#endif
374
375 /* return here, as further calculations are related to the old approach */
376 return;
377 }
378
379 /* scale factors */
380 xsf = (vp.xmax - vp.xmin) / (mapping->window.xmax - mapping->window.xmin);
381 ysf = (vp.ymax - vp.ymin) / (mapping->window.ymax - mapping->window.ymin);
382 zsf = (vp.zmax - vp.zmin) / (fpd - bpd);
383
384 /* map matrix */
385 mmat[0][0] = xsf, mmat[1][1] = ysf, mmat[2][2] = zsf;
386 mmat[3][0] = vp.xmin - xsf*mapping->window.xmin;
387 mmat[3][1] = vp.ymin - ysf*mapping->window.ymin;
388 mmat[3][2] = vp.zmin - zsf*bpd;
389
390 /* multiply to obtain mapping matrix */
391 TelMultiplymat3( mat, pmat, mmat );
392
393#ifdef PRINT
394 printf( "mapping_matrix :\n" );
395 pr_matrix(mat);
396#endif
397}
398
399/*----------------------------------------------------------------------*/
400/*+
401Set View Representation
402
403This routine defines a view representation for a workstation.
404
405The representation of the view is stored in a storage table.
406An entry is made into the list of defined views for the workstation.
407If the view id being defined already exists, its representation gets
408modified, else a new representation is created.
409An inverse transformation matrix is computed and stored in the internal
410data for the view to accelerate UVN2XYZ conversions. To be able to compute
411this matrix, it requires some extra information about the view orientation,
412view plane distance and viewport limits.
413+*/
414
415TStatus
416TelSetViewRepresentation( Tint Wsid /* Workstation id*/,
417 Tint Vid /* View id */,
418 tel_view_rep vrep /* view repesentation */
419 )
420{
421 CMN_KEY_DATA key;
422 tel_view_data vptr;
423
424 if( Vid == 0 )
425 return TFailure; /* attempt to modify default view */
426
427 /* Mise a jour de l'update_mode */
428 key.ldata = TNotDone;
429 TsmSetWSAttri( Wsid, WSUpdateState, &key );
430
431 TsmGetWSAttri( Wsid, WSViews, &key );
432 vptr = (tel_view_data)(key.pdata) ; /* Obtain defined view data*/
433
434 if( !vptr ) /* no view defined yet */
435 { /* allocate */
436 //cmn_memreserve(vptr, 1, 0 );
437 vptr = new TEL_VIEW_DATA();
438 if( !vptr ) return TFailure;
439
440 key.pdata = vptr;
441 TsmSetWSAttri( Wsid, WSViews, &key ); /* Set defined view data*/
442 }
443
444 /* copy view definition to storage table record */
445 /* NOTE: Use the matrices already calculated and stored in vrep */
446 vptr->vrep = *vrep;
447
448#ifdef CAL_100498
449 /* compute inverse transformation matrix */
450 TelEvalInverseMatrix( vrep->extra.vrp, vrep->extra.vpn, vrep->extra.vup,
451 vrep->extra.map.vpd, vptr->inverse_matrix );
452#endif
453#ifdef TRACE_MAT
454 printf( "\nTelSetViewRepresentation WS : %d, view : %d\n", Wsid, Vid );
455 printf( "orientation_matrix :\n" );
456 pr_matrix( vptr->vrep.orientation_matrix );
457 printf( "mapping_matrix :\n" );
458 pr_matrix( vptr->vrep.mapping_matrix );
459#endif
460 return TSuccess;
461}
462
463
464/*----------------------------------------------------------------------*/
465TStatus
466TelGetViewRepresentation( Tint Wsid /* Workstation id*/,
467 Tint Vid /* View id */,
468 tel_view_rep vrep /* view representation */
469 )
470{
471 CMN_KEY_DATA key;
472 tel_view_data vptr;
473
474 if( Vid == 0 )
475 {
476 matcpy( vrep->orientation_matrix, ident );
477 matcpy( vrep->mapping_matrix, ident );
478 vrep->clip_limit.xmin = vrep->clip_limit.ymin =
479 vrep->clip_limit.zmin = ( float )0.0;
480 vrep->clip_limit.xmax = vrep->clip_limit.ymax =
481 vrep->clip_limit.zmax = ( float )1.0;
482 vrep->clip_xy = TOff;
483 vrep->clip_back = vrep->clip_front = TOn;
484 vrep->shield_indicator = TOn;
485 vrep->shield_colour.rgb[0] = vrep->shield_colour.rgb[1] =
486 vrep->shield_colour.rgb[2] = ( float )0.0;
487 vrep->border_indicator = TOff; /* non utilise */
488 vrep->border_colour.rgb[0] = vrep->border_colour.rgb[1] =
489 vrep->border_colour.rgb[2] = ( float )0.0;
490 vrep->active_status = TOn;
491 vrep->extra.vrp[0] = vrep->extra.vrp[1] = vrep->extra.vrp[2] = ( float )0.0;
492 vrep->extra.vpn[0] = ( float )0.0,
493 vrep->extra.vpn[1] = ( float )0.0,
494 vrep->extra.vpn[2] = ( float )1.0;
495 vrep->extra.vup[0] = ( float )0.0,
496 vrep->extra.vup[1] = ( float )1.0,
497 vrep->extra.vup[2] = ( float )0.0;
498 vrep->extra.map.vpd = ( float )0.0,
499 vrep->extra.map.fpd = ( float )0.0,
500 vrep->extra.map.bpd = ( float )-1.0;
501 vrep->extra.map.window.xmin = vrep->extra.map.window.ymin = ( float )0.0;
502 vrep->extra.map.window.xmax = vrep->extra.map.window.ymax = ( float )1.0;
503 vrep->extra.map.viewport.xmin = vrep->extra.map.viewport.ymin =
504 vrep->extra.map.viewport.zmin = ( float )0.0;
505 vrep->extra.map.viewport.xmax = vrep->extra.map.viewport.ymax =
506 vrep->extra.map.viewport.zmax = ( float )1.0;
507 return TSuccess;
508 }
509
510 if(TsmGetWSAttri( Wsid, WSViews, &key ) != TSuccess) {
511 return TFailure;
512 }
513 vptr = (tel_view_data)key.pdata ; /* Obtain defined view data*/
514 if( !vptr ) return TFailure; /* no view defined yet */
515 *vrep = vptr->vrep; /* copy view definition */
516
517 return TSuccess;
518}
519
520/*----------------------------------------------------------------------*/
521/*+
522Evaluate View Orientation Matrix
523
524This routine computes the orientation matrix based on the View Reference
525Point, View Plane Normal and the View Up Vector.
526+*/
527
528void
529TelEvalViewOrientationMatrix( Tfloat *vrp /* View Reference Point */,
530 Tfloat *vpn /* View Plane Normal */,
531 Tfloat *vup /* View Up Vector */,
532 Tfloat *asf /* Axial Scale Factors */,
533 Tint *error_ind/* Out: Error indicator */,
534 Tmatrix3 rmat /* Out: Orientation Matrix */
535 )
536{
537 Tfloat u[3], v[3], n[3], f;
538
539 /* view plane normal of zero length */
540 if( vecmag(vpn) == 0.0 )
541 {
542 *error_ind = 1;
543 return;
544 }
545
546 /* view up vector of zero length */
547 if( vecmag(vup) == 0.0 )
548 {
549 *error_ind = 2;
550 return;
551 }
552
553 /* view up vector parallel to view plane normal */
554 vecang(vup, vpn, f);
555 if( f == 0.0 )
556 {
557 *error_ind = 3;
558 return;
559 }
560
561 *error_ind = 0;
562
563 veccpy(n, vpn);
564 veccpy(v, vup);
565 vecnrm(n);
566
567 veccrs(u,v,n); /* up vector cross plane normal gives U axis */
568 vecnrm(u);
569
570 veccrs(v,n,u); /* plane normal cross U axis gives modified up vector */
571 vecnrm(v); /* redundant ? */
572
573 /* rotate to align along u, v, n */
574 rmat[0][0] = ( float )u[0] * asf[0],
575 rmat[0][1] = ( float )v[0] * asf[0],
576 rmat[0][2] = ( float )n[0] * asf[0],
577 rmat[0][3] = ( float )0.0;
578
579 rmat[1][0] = ( float )u[1] * asf[1],
580 rmat[1][1] = ( float )v[1] * asf[1],
581 rmat[1][2] = ( float )n[1] * asf[1],
582 rmat[1][3] = ( float )0.0;
583
584 rmat[2][0] = ( float )u[2] * asf[2],
585 rmat[2][1] = ( float )v[2] * asf[2],
586 rmat[2][2] = ( float )n[2] * asf[2],
587 rmat[2][3] = ( float )0.0;
588
589 /* translate to centre at vrp */
590
591 rmat[3][0] = - ( float ) (u[0]*vrp[0] + u[1]*vrp[1] + u[2]*vrp[2]);
592 rmat[3][1] = - ( float ) (v[0]*vrp[0] + v[1]*vrp[1] + v[2]*vrp[2]);
593 rmat[3][2] = - ( float ) (n[0]*vrp[0] + n[1]*vrp[1] + n[2]*vrp[2]);
594 rmat[3][3] = ( float )1.0;
595
596#ifdef PRINT
597 printf("TelEvalViewOrientationMatrix \n");
598 printf("view_ref_pt %f %f %f \n", vrp[0], vrp[1], vrp[2]);
599 printf("view_up_vec %f %f %f \n", vup[0], vup[1], vup[2]);
600 printf("view_plane_normal %f %f %f \n", vpn[0], vpn[1], vpn[2]);
601 pr_matrix(rmat);
602#endif
603
604 return;
605}
606/*----------------------------------------------------------------------*/
607
608void
609TelEvalViewMappingMatrix( tel_view_mapping mapping /* View Mapping */,
610 Tint *error_ind /* Out: Error Indicator */,
611 Tmatrix3 mat /* Out: Mapping Matrix */
612 )
613{
614 EvalViewMappingMatrix( mapping, error_ind, mat, 0, ( float )0.0, ( float )0.0, 0, 0 );
615}
616
617/*----------------------------------------------------------------------*/
618
619void
620TelEvalViewMappingMatrixPick( tel_view_mapping mapping /* View Mapping */,
621 Tint *error_ind /* Out: Error Indicator */,
622 Tmatrix3 mat /* Out: Mapping Matrix */,
623 Tfloat cx,
624 Tfloat cy
625 )
626{
627 EvalViewMappingMatrix( mapping, error_ind, mat, 1, cx, cy, 0, 0 );
628}
629
630/*----------------------------------------------------------------------*/
631/*+
632Evalute inverse transformation matrix.
633
634This routine computes a matrix required to convert UVN coordinates to XYZ
635coordinates. It is called every time a View Representation is created or
636modified, and the inverse matrix is stored along with the internal data
637for the view representation.
638+*/
639
640#ifdef CAL_100498
641static void
642TelEvalInverseMatrix( Tfloat *vrp /* View Reference Point */,
643 Tfloat *vpn /* View Plane Normal */,
644 Tfloat *vup /* View Up Vector */,
645 Tfloat vpd /* View Plane Distance */,
646 Tmatrix3 mat /* Out: Inverse Transformation Matrix */
647 )
648{
649 Tfloat u[3], v[3], n[3], p[3], t[3];
650 Tfloat dist = ( float )0.0;
651
652 veccpy(n, vpn); /* compute UVN orientation */
653 veccpy(v, vup);
654 veccpy(p, vrp);
655
656 veccrs(u,v,n);
657 vecnrm(u);
658
659 veccrs(v,n,u);
660 vecnrm(v);
661
662 dist = vpd;
663 veccpy(t,n);
664 vecscl(dist,t);
665 vecadd(t,t,p); /* translation vector */
666
667 veccpy(mat[0],u);
668 veccpy(mat[1],v);
669 veccpy(mat[2],n);
670 veccpy(mat[3],t);
671
672 mat[0][3] = mat[1][3] = mat[2][3] = ( float )0.0, mat[3][3] = ( float )1.0;
673
674 return;
675}
676#endif
677
678#ifdef CAL_100498
679/*----------------------------------------------------------------------*/
680/*+
681Convert Coordinates utility routine
682
683This routine converts coordinates from UVN space to XYZ space and
684vice versa. For UVN2XYZ, the inverse transformation matrix is used and for
685XYZ2UVN, the orientation matrix is used.
686+*/
687
688TStatus
689TelConvertCoord( Tint Wsid /* Workstation id */,
690 Tint Vid /* View id */,
691 TelCoordType type /* Conversion type (UVN2XYZ or XYZ2UVN) */,
692 Tfloat *uvn /* UVN coords if type is UVN2XYZ else Out */,
693 Tfloat *xyz /* XYZ coords if type is XYZ2UVN else Out */
694 )
695{
696 CMN_KEY_DATA key;
697 tel_view_data vptr;
698 register Tint i;
699
700 Tfloat pt[4], tpt[4];
701
702 if( Vid == 0 )
703 { /* default view */
704 switch( type )
705 {
706 case UVN2XYZ:
707 veccpy(xyz,uvn);
708 break;
709 case XYZ2UVN:
710 veccpy(uvn,xyz);
711 break;
712 }
713 return TSuccess;
714 }
715
716 TsmGetWSAttri( Wsid, WSViews, &key );
717 vptr = key.pdata ; /* Obtain defined view data*/
718 if( !vptr ) return TFailure; /* no view defined yet */
719
720 switch( type )
721 {
722 case UVN2XYZ:
723 veccpy(pt,uvn);
724 pt[3] = ( float )1.0;
725 TelTranpt3( tpt, pt, vptr->inverse_matrix );
726 veccpy(xyz,tpt);
727 break;
728
729 case XYZ2UVN:
730 veccpy(pt,xyz);
731 pt[3] = ( float )1.0;
732 TelTranpt3( tpt, pt, vptr->vrep.orientation_matrix );
733 veccpy(uvn,tpt);
734 break;
735 }
736
737 return TSuccess;
738}
739#endif
740
741/*----------------------------------------------------------------------*/
742/*+
743Print Matrix
744
745Debug tool
746+*/
747
748#ifdef DEB
749void
750pr_matrix( Tmatrix3 mat )
751{
752 printf( "%f %f %f %f\n", mat[0][0], mat[0][1], mat[0][2], mat[0][3] );
753 printf( "%f %f %f %f\n", mat[1][0], mat[1][1], mat[1][2], mat[1][3] );
754 printf( "%f %f %f %f\n", mat[2][0], mat[2][1], mat[2][2], mat[2][3] );
755 printf( "%f %f %f %f\n", mat[3][0], mat[3][1], mat[3][2], mat[3][3] );
756 printf( "\n" );
757 return;
758}
759#endif
760
761/*----------------------------------------------------------------------*/
762/*+
763Set View Index
764
765This routine activates the view representation which has been defined
766previously.
767+*/
768
769TStatus
770TelSetViewIndex( Tint Wsid /* Workstation id */,
771 Tint Vid /* View id */ )
772{
773 CMN_KEY_DATA key;
774 tel_view_data vptr;
775
776 if( Vid == 0 )
777 { /* default view */
778 GLint mm;
779 glGetIntegerv(GL_MATRIX_MODE, &mm);
780#ifdef TRACE_MATRIX
781 printf("OpenGl_view.c::TelSetViewIndex::glMatrixMode(GL_PROJECTION) \n");
782#endif
783 glMatrixMode(GL_PROJECTION);
784 glLoadIdentity();
785 glOrtho( -0.5, 0.5, -0.5, 0.5, -0.5, 0.5 );
786 glMatrixMode(mm);
787 return TSuccess;
788 }
789
790 TsmGetWSAttri( Wsid, WSViews, &key );
791 vptr = (tel_view_data)key.pdata ; /* Obtain defined view data*/
792 if( !vptr ) return TFailure; /* no view defined yet */
793
794#ifdef TRACE_MATRIX
795 printf("OpenGl_view.c::TelSetViewIndex::glMatrixMode(GL_MODELVIEW) \n");
796#endif
797 if(vptr->vrep.extra.scaleFactors[0] != 1. ||
798 vptr->vrep.extra.scaleFactors[1] != 1. ||
799 vptr->vrep.extra.scaleFactors[2] != 1.)
800 glEnable(GL_NORMALIZE); /* if the view is scaled normal vectors are scaled to unit length for correct displaying of shaded objects*/
801 else if(glIsEnabled(GL_NORMALIZE))
802 glDisable(GL_NORMALIZE);
803 glMatrixMode(GL_MODELVIEW);
804 set_clipplanes( &(vptr->vrep) );
805
806 glLoadMatrixf((GLfloat *) vptr->vrep.orientation_matrix );
807
808#ifdef ENVTEX
809 /*
810 * Ajout translation necessaire pour l'environnement mapping
811 */
812 {
813 GLfloat dep;
814
815 TsmGetWSAttri(Wsid, WSSurfaceDetail, &key);
816 /* TOD_ENVIRONMENT ou TOD_ALL */
817 if (key.ldata == 1 || key.ldata == 2)
818 {
819 /* dep = vptr->vrep.extra.map.fpd * 0.5F; */
820 dep = (vptr->vrep.extra.map.fpd + vptr->vrep.extra.map.bpd) * 0.5F; /* OCC280: FitAll work incorrect for perspective view if the SurfaceDetail mode is V3d_TEX_ENVIRONMENT or V3d_TEX_ALL */
821 glTranslatef(-dep*vptr->vrep.extra.vpn[0],
822 -dep*vptr->vrep.extra.vpn[1],
823 -dep*vptr->vrep.extra.vpn[2]);
824#ifdef PRINT
825 printf("glTranslatef: %f %f %f \n",
826 -dep*vptr->vrep.extra.vpn[0],
827 -dep*vptr->vrep.extra.vpn[1],
828 -dep*vptr->vrep.extra.vpn[2]);
829#endif
830 }
831 }
832#endif
833
834#ifdef TRACE_MATRIX
835 printf("OpenGl_view.c::TelSetViewIndex::glMatrixMode(GL_PROJECTION) \n");
836#endif
837 glMatrixMode(GL_PROJECTION);
838 glLoadMatrixf((GLfloat *) vptr->vrep.mapping_matrix );
839
840#ifdef TRACE_MAT
841 printf( "\nTelSetViewIndex WS : %d, view : %d", Wsid, Vid );
842 printf( "orientation_matrix :\n" );
843 pr_matrix( vptr->vrep.orientation_matrix );
844 printf( "mapping_matrix :\n" );
845 pr_matrix( vptr->vrep.mapping_matrix );
846#endif
847
848
849 return vptr->vrep.active_status == TOn ? TSuccess : TFailure;
850}
851
852
853/*----------------------------------------------------------------------*/
854/*+
855Set View Projection
856
857This routine activates the Projection matrix for a previously defined
858view representation. It is meant to be used exclusively to restore the
859Projection transformation at the end of an ExecuteStructure element
860traversal. The restoration of the Viewing matrix is done by a GL popmatrix
861call.
862+*/
863
864TStatus
865TelSetViewProjection( Tint Wsid /* Workstation id */,
866 Tint Vid /* View id */ )
867{
868 CMN_KEY_DATA key;
869 tel_view_data vptr;
870
871 if( Vid == 0 )
872 { /* default view */
873 GLint mm;
874 glGetIntegerv(GL_MATRIX_MODE, &mm);
875#ifdef TRACE_MATRIX
876 printf("OpenGl_view.c::TelSetViewProjection::glMatrixMode(GL_PROJECTION) \n");
877#endif
878 glMatrixMode(GL_PROJECTION);
879 glLoadIdentity();
880 glOrtho( 0, 1, 0, 1, 0, 1 );
881 glMatrixMode(mm);
882
883
884 return TSuccess;
885 }
886
887 TsmGetWSAttri( Wsid, WSViews, &key );
888 vptr = (tel_view_data)key.pdata ; /* Obtain defined view data*/
889 if( !vptr ) return TFailure; /* no view defined yet */
890
891 set_clipplanes( &(vptr->vrep) );
892
893#ifdef TRACE_MATRIX
894 printf("OpenGl_view.c::TelSetViewProjection::glMatrixMode(GL_PROJECTION) \n");
895#endif
896 glMatrixMode(GL_PROJECTION);
897 glLoadMatrixf((GLfloat *) vptr->vrep.mapping_matrix );
898
899
900 return vptr->vrep.active_status == TOn ? TSuccess : TFailure;
901}
902
903/*----------------------------------------------------------------------*/
904/*+
905Clear all active views in a workstation
906
907This routine clears all the viewports, draws the viewport borders and
908sets the viewport background if the corresponding indicators are on.
909It also clears view 0 (default view), if the workstation state demands it.
910+*/
911
912void
913TelClearViews( Tint Wsid /* Workstation id */ )
914{
915 CMN_KEY_DATA key;
916 tel_view_data vptr;
917
918 TelResetMaterial();
919
920 TsmGetWSAttri( Wsid, WSViews, &key );
921 vptr = (tel_view_data)key.pdata ; /* Obtain defined view data*/
922 if( !vptr ) return; /* no view defined yet */
923
924 if( vptr->vrep.active_status == TOn ) /* for each active view only */
925 {
926 if( vptr->vrep.shield_indicator == TOn ) TelClearBackground( Wsid );
927 }
928
929 return;
930}
931
932/*----------------------------------------------------------------------*/
933/* Function for printing view information */
934
935TStatus
936TelPrintViewRepresentation( Tint Wsid /* Workstation id*/,
937 Tint Vid /* View id */
938 )
939{
940 CMN_KEY_DATA key;
941 tel_view_data vptr;
942
943 printf( "\n\tPrint : Workstation %d View %d", Wsid, Vid );
944
945 if( Vid == 0 )
946 return TSuccess;
947
948 TsmGetWSAttri( Wsid, WSViews, &key );
949 vptr = (tel_view_data)key.pdata ; /* Obtain defined view data*/
950 if( !vptr ) return TFailure; /* no view defined yet */
951
952 /* Print the information */
953 printf( "\n\tshield indicator : %s",
954 vptr->vrep.shield_indicator == TOn ? "ON" : "OFF" );
955 printf( "\n\tshield_colour r = %f, g = %f, b = %f",
956 vptr->vrep.shield_colour.rgb[0],
957 vptr->vrep.shield_colour.rgb[1],
958 vptr->vrep.shield_colour.rgb[2] );
959 printf( "\n\tactive_status : %s",
960 vptr->vrep.active_status == TOn ? "ON":"OFF");
961 printf( "\n\tVRP : %f %f %f", vptr->vrep.extra.vrp[0],
962 vptr->vrep.extra.vrp[1],
963 vptr->vrep.extra.vrp[2] );
964 printf( "\n\tVPN : %f %f %f", vptr->vrep.extra.vpn[0],
965 vptr->vrep.extra.vpn[1],
966 vptr->vrep.extra.vpn[2] );
967 printf( "\n\tVUP : %f %f %f", vptr->vrep.extra.vup[0],
968 vptr->vrep.extra.vup[1],
969 vptr->vrep.extra.vup[2] );
970 printf( "\n\tPRP : %f %f %f", vptr->vrep.extra.map.prp[0],
971 vptr->vrep.extra.map.prp[1],
972 vptr->vrep.extra.map.prp[2] );
973 printf( "\n\tWindow Limits xmin xmax ymin ymax :\n\t\t%f %f %f %f",
974 vptr->vrep.extra.map.window.xmin,
975 vptr->vrep.extra.map.window.xmax,
976 vptr->vrep.extra.map.window.ymin,
977 vptr->vrep.extra.map.window.ymax );
978 printf( "\n\tViewport Limits xmin xmax ymin ymax zmin zmax :\n\t\t%f %f %f %f %f %f", vptr->vrep.extra.map.viewport.xmin,
979 vptr->vrep.extra.map.viewport.xmax,
980 vptr->vrep.extra.map.viewport.ymin,
981 vptr->vrep.extra.map.viewport.ymax,
982 vptr->vrep.extra.map.viewport.zmin,
983 vptr->vrep.extra.map.viewport.zmax );
984 printf( "\n\tProjection type : %s",
985 vptr->vrep.extra.map.proj == TelParallel
986 ? "PARALLEL" : "PERSPECTIVE" );
987 printf( "\n\tVPD FPD BPD : %f %f %f\n", vptr->vrep.extra.map.vpd,
988 vptr->vrep.extra.map.fpd,
989 vptr->vrep.extra.map.bpd );
990 return TSuccess;
991}
992
993
994/*----------------------------------------------------------------------*/
995
996#define FRONT_CLIPPING_PLANE (GL_CLIP_PLANE0 + 0)
997#define BACK_CLIPPING_PLANE (GL_CLIP_PLANE0 + 1)
998/*
999
1000While drawing after a clipplane has been defined and enabled, each vertex
1001is transformed to eye-coordinates, where it is dotted with the transformed
1002clipping plane equation. Eye-coordinate vertexes whose dot product with
1003the transformed clipping plane equation is positive or zero are in, and
1004require no clipping. Those eye-coordinate vertexes whose dot product is
1005negative are clipped. Because clipplane clipping is done in eye-
1006coordinates, changes to the projection matrix have no effect on its
1007operation.
1008
1009A point and a normal are converted to a plane equation in the following
1010manner:
1011
1012point = [Px,Py,Pz]
1013
1014normal = |Nx|
1015|Ny|
1016|Nz|
1017
1018plane equation = |A|
1019|B|
1020|C|
1021|D|
1022A = Nx
1023B = Ny
1024C = Nz
1025D = -[Px,Py,Pz] dot |Nx|
1026|Ny|
1027|Nz|
1028
1029*/
1030
1031/*----------------------------------------------------------------------*/
1032
1033static void
1034set_clipplanes( tel_view_rep vrep )
1035{
1036 GLdouble arr[4];
1037 Tfloat front, back;
1038 GLfloat mat[4][4];
1039#ifdef TRACE_MATRIX
1040 printf("OpenGl_view.c::set_clipplanes::glMatrixMode(GL_MODELVIEW) \n");
1041#endif
1042 glMatrixMode( GL_MODELVIEW );
1043 glGetFloatv( GL_MODELVIEW_MATRIX,(GLfloat *) mat );
1044 glLoadIdentity();
1045
1046 if( vrep->clip_limit.zmin < 0.0 ||
1047 vrep->clip_limit.zmin > 1.0 ||
1048 vrep->clip_back == TOff )
1049 glDisable( BACK_CLIPPING_PLANE );
1050 else
1051 {
1052 /* cf Opengl_togl_cliplimit */
1053 back = (vrep->extra.map.fpd - vrep->extra.map.bpd) *
1054 vrep->clip_limit.zmin + vrep->extra.map.bpd;
1055 arr[0] = 0.0; /* Nx */
1056 arr[1] = 0.0; /* Ny */
1057 arr[2] = 1.0; /* Nz */
1058 arr[3] = -( (GLdouble) (back) * arr[2] ); /* P dot N */
1059 glClipPlane( BACK_CLIPPING_PLANE, arr );
1060 glEnable( BACK_CLIPPING_PLANE );
1061 }
1062
1063 if( vrep->clip_limit.zmax < 0.0 ||
1064 vrep->clip_limit.zmax > 1.0 ||
1065 vrep->clip_front == TOff )
1066 glDisable( FRONT_CLIPPING_PLANE );
1067 else
1068 {
1069 /* cf Opengl_togl_cliplimit */
1070 front = (vrep->extra.map.fpd - vrep->extra.map.bpd) *
1071 vrep->clip_limit.zmax + vrep->extra.map.bpd;
1072 arr[0] = 0.0; /* Nx */
1073 arr[1] = 0.0; /* Ny */
1074 arr[2] = -1.0; /* Nz */
1075 arr[3] = -( (GLdouble) (front) * arr[2] ); /* P dot N */
1076 glClipPlane( FRONT_CLIPPING_PLANE, arr );
1077 glEnable( FRONT_CLIPPING_PLANE );
1078 }
1079
1080 glLoadMatrixf( (GLfloat *) mat );
1081}
1082
1083/*----------------------------------------------------------------------*/
1084
1085TStatus
1086Tel2Dto3D( Tint ws, Tint vid, Tint x, Tint y,
1087 Tfloat *x1, Tfloat *y1, Tfloat *z1,
1088 Tfloat *x2, Tfloat *y2, Tfloat *z2 )
1089 /* x is from bottom */
1090 /* y is from top */
1091{
1092 CMN_KEY_DATA key;
1093 TEL_VIEW_REP vrep;
1094 Tint w, h;
1095 GLint viewp[4];
1096 GLdouble xx1, yy1, zz1, xx2, yy2, zz2;
1097
1098 TsmGetWSAttri( ws, WSWidth, &key );
1099 w = key.ldata;
1100 TsmGetWSAttri( ws, WSHeight, &key );
1101 h = key.ldata;
1102 y = key.ldata - y;
1103
1104 /* FSXXX */
1105 printf("WARNING: Tel2Dto3D non verifie\n");
1106
1107 TelGetViewRepresentation( ws, vid, &vrep );
1108
1109 viewp[0] = 0; viewp[2] = w;
1110 viewp[1] = 0; viewp[3] = h;
1111
1112
1113 /* OGLXXX XXX I think this is backwards */
1114 gluProject((GLdouble) x, (GLdouble) y, 0.0,
1115 (GLdouble *) vrep.orientation_matrix,
1116 (GLdouble *) vrep.mapping_matrix,
1117 viewp, &xx1, &yy1, &zz1);
1118 gluProject((GLdouble) x, (GLdouble) y, 1.0,
1119 (GLdouble *) vrep.orientation_matrix,
1120 (GLdouble *) vrep.mapping_matrix,
1121 viewp, &xx2, &yy2, &zz2);
1122
1123 *x1 = (float) xx1; *y1 = (float) yy1; *z1 = (float) zz1;
1124 *x2 = (float) xx2; *y2 = (float) yy2; *z2 = (float) zz2;
1125
1126 return TSuccess;
1127
1128}
1129
1130/*----------------------------------------------------------------------*/
1131
1132TStatus
1133TelDeleteViewsForWS( Tint wsid )
1134{
1135 CMN_KEY_DATA key;
1136 tel_view_data vptr;
1137
1138 TsmGetWSAttri( wsid, WSViews, &key );
1139 vptr = (tel_view_data)key.pdata ; /* Obtain defined view data*/
1140
1141 if( !vptr ) return TSuccess;
1142 delete vptr;
1143
1144 return TSuccess;
1145}
1146
1147/*----------------------------------------------------------------------*/
1148
1149void
1150TelClearBackground( Tint Wsid /* Workstation id */ )
1151{
1152 CMN_KEY_DATA key;
1153 Tfloat *rgb;
1154 Tint zbuffer;
1155#ifdef BUC61044
1156 Tint dTest;
1157#endif
1158#ifdef OCC1188
1159 tsm_bg_texture texture;
1160#endif
1161 tsm_bg_gradient gradient;
1162
1163
1164 TsmGetWSAttri (Wsid, WSBackground, &key);
1165 rgb = (Tfloat *)key.pdata;
1166
1167#ifdef OCC1188
1168 TsmGetWSAttri (Wsid, WSBgTexture, &key);
1169 texture = (tsm_bg_texture)key.pdata;
1170#endif
1171 TsmGetWSAttri (Wsid, WSZbuffer, &key);
1172 zbuffer = key.ldata;
1173
1174 TsmGetWSAttri (Wsid, WSBgGradient, &key);
1175 gradient = (tsm_bg_gradient)key.pdata;
1176
1177 /* GL_DITHER on/off pour le background */
1178 if (TxglGetBackDither ())
1179 glEnable (GL_DITHER);
1180 else
1181 glDisable (GL_DITHER);
1182
1183 if (zbuffer)
1184 {
1185#ifdef BUC60920
1186 glDepthFunc(GL_LEQUAL);
1187#else
1188 glDepthFunc(GL_LESS);
1189#endif
1190 glDepthMask(GL_TRUE);
1191
1192#ifdef BUC61044
1193 /* getting depth testing flag */
1194 TsmGetWSAttri( Wsid, WSDepthTest, &key );
1195 dTest = key.ldata;
1196 /* SAV checking if depth test was depricated somewhere outside */
1197 if ( dTest == TOn )
1198 glEnable(GL_DEPTH_TEST);
1199 else
1200 glDisable(GL_DEPTH_TEST);
1201#else
1202 glEnable(GL_DEPTH_TEST);
1203#endif
1204
1205 glClearDepth(1.0);
1206 glClearColor (rgb[0], rgb[1], rgb[2], ( float )0.0);
1207 glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
1208 }
1209 else
1210 {
1211 glDisable(GL_DEPTH_TEST);
1212 glClearColor (rgb[0], rgb[1], rgb[2], ( float )0.0);
1213 glClear (GL_COLOR_BUFFER_BIT);
1214 }
1215#ifdef OCC1188
1216 glPushAttrib( GL_ENABLE_BIT | GL_TEXTURE_BIT );
1217 /* drawing bg image if any */
1218 if ( texture->texId != 0 ) {
1219 GLint width, height; /* window dimensions*/
1220 GLfloat x_center, y_center; /* window center */
1221 GLfloat x_offset, y_offset; /* half of the texture size */
1222 GLfloat texX_range = 1.0;
1223 /* texture <s> coordinate */
1224 GLfloat texY_range = 1.0; /* texture <t> coordinate */
1225
1226 TsmGetWSAttri( Wsid, WSWidth, &key );
1227 width = key.ldata;
1228 x_center = (GLfloat)( width / 2. );
1229 TsmGetWSAttri( Wsid, WSHeight, &key );
1230 height = key.ldata;
1231 y_center = (GLfloat)( height / 2. );
1232
1233 x_offset = (GLfloat)( texture->width / 2. ); /* style = center */
1234 y_offset = (GLfloat)( texture->height / 2. ); /* style = center */
1235 if ( texture->style != 0 ) { /* stretch or tile */
1236 x_offset = x_center;
1237 y_offset = y_center;
1238 if ( texture->style == 1 ) { /* tile */
1239 texX_range = (float)( width / texture->width );
1240 if ( texX_range < 1.0 )
1241 texX_range = 1.0;
1242 texY_range = (float)( height / texture->height );
1243 if ( texY_range < 1.0 )
1244 texY_range = 1.0;
1245 }
1246 }
1247 /* drawing background texture */
1248 glMatrixMode( GL_PROJECTION );
1249 glPushMatrix();
1250 glLoadIdentity();
1251 gluOrtho2D( 0.0, (GLdouble)width, 0.0, (GLdouble)height );
1252 glMatrixMode( GL_MODELVIEW );
1253 glPushMatrix();
1254 glLoadIdentity();
1255 glEnable( GL_TEXTURE_2D );
1256 glBindTexture( GL_TEXTURE_2D, texture->texId );
1257 glDisable( GL_DEPTH_TEST );
1258
1259 glDisable( GL_BLEND );
1260 glColor3f( rgb[0], rgb[1], rgb[2] );
1261 glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);
1262 glBegin( GL_QUADS );
1263 glTexCoord2f(0.0f, 0.0f);glVertex2f( x_center - x_offset, y_center - y_offset );
1264 glTexCoord2f(texX_range, 0.0f);glVertex2f( x_center + x_offset, y_center - y_offset );
1265 glTexCoord2f(texX_range, texY_range);glVertex2f( x_center + x_offset, y_center + y_offset );
1266 glTexCoord2f(0.0f, texY_range);glVertex2f( x_center - x_offset, y_center + y_offset );
1267 glEnd();
1268 if ( zbuffer )
1269 glEnable( GL_DEPTH_TEST );
1270 glDisable( GL_TEXTURE_2D );
1271 glPopMatrix(); /*modelview*/
1272 glMatrixMode( GL_PROJECTION );
1273 glPopMatrix(); /*projection*/
1274 glMatrixMode( GL_MODELVIEW );
1275 }
1276 else if( gradient->type > 0 )
1277 {
1278
1279 Tfloat* corner1 = 0;/* -1,-1*/
1280 Tfloat* corner2 = 0;/* 1,-1*/
1281 Tfloat* corner3 = 0;/* 1, 1*/
1282 Tfloat* corner4 = 0;/* -1, 1*/
1283 Tfloat* dcorner1 = (Tfloat*)malloc(3*sizeof(Tfloat));
1284 Tfloat* dcorner2 = (Tfloat*)malloc(3*sizeof(Tfloat));
1285
1286 int upset[3] = {0} ;
1287
1288 switch( gradient->type )
1289 {
1290 case 1:
1291 corner1 = gradient->color2.rgb;
1292 corner2 = gradient->color2.rgb;
1293 corner3 = gradient->color1.rgb;
1294 corner4 = gradient->color1.rgb;
1295 break;
1296 case 2:
1297 corner1 = gradient->color2.rgb;
1298 corner2 = gradient->color1.rgb;
1299 corner3 = gradient->color1.rgb;
1300 corner4 = gradient->color2.rgb;
1301 break;
1302 case 3:
1303 corner2 = gradient->color2.rgb;
1304 corner4 = gradient->color1.rgb;
1305 dcorner1 [0] = dcorner2[0] = (corner2[0] + corner4[0]) / 2.0;
1306 dcorner1 [1] = dcorner2[1] = (corner2[1] + corner4[1]) / 2.0;
1307 dcorner1 [2] = dcorner2[2] = (corner2[2] + corner4[2]) / 2.0;
1308 corner1 = dcorner1;
1309 corner3 = dcorner2;
1310 break;
1311 case 4:
1312 corner1 = gradient->color2.rgb;
1313 corner3 = gradient->color1.rgb;
1314 dcorner1 [0] = dcorner2[0] = (corner1[0] + corner3[0]) / 2.0;
1315 dcorner1 [1] = dcorner2[1] = (corner1[1] + corner3[1]) / 2.0;
1316 dcorner1 [2] = dcorner2[2] = (corner1[2] + corner3[2]) / 2.0;
1317 corner2 = dcorner1;
1318 corner4 = dcorner2;
1319 break;
1320 case 5:
1321 corner1 = gradient->color1.rgb;
1322 corner2 = gradient->color2.rgb;
1323 corner3 = gradient->color2.rgb;
1324 corner4 = gradient->color2.rgb;
1325 break;
1326 case 6:
1327 corner1 = gradient->color2.rgb;
1328 corner2 = gradient->color1.rgb;
1329 corner3 = gradient->color2.rgb;
1330 corner4 = gradient->color2.rgb;
1331 break;
1332 case 7:
1333 corner1 = gradient->color2.rgb;
1334 corner2 = gradient->color2.rgb;
1335 corner3 = gradient->color1.rgb;
1336 corner4 = gradient->color2.rgb;
1337 break;
1338 case 8:
1339 corner1 = gradient->color2.rgb;
1340 corner2 = gradient->color2.rgb;
1341 corner3 = gradient->color2.rgb;
1342 corner4 = gradient->color1.rgb;
1343 break;
1344 default:
1345 printf("gradient background type not right\n");
1346
1347 }
1348 glMatrixMode( GL_PROJECTION );
1349 glPushMatrix();
1350 glLoadIdentity();
1351 glMatrixMode( GL_MODELVIEW );
1352 glPushMatrix();
1353 glLoadIdentity();
1354
1355 if ( glIsEnabled( GL_DEPTH_TEST) )
1356 {
1357 upset[0] = 1;
1358 glDisable( GL_DEPTH_TEST );
1359 }
1360 if ( glIsEnabled( GL_LIGHTING ) )
1361 {
1362 upset[1] = 1;
1363 glDisable( GL_LIGHTING );
1364 }
1365 if ( !glIsEnabled( GL_SMOOTH ) )
1366 {
1367 upset[2] = 1;
1368 glShadeModel( GL_SMOOTH ) ;
1369 }
1370
1371 if( gradient->type <= 5 || gradient->type == 7 )
1372 {
1373 glBegin(GL_TRIANGLES);
1374 glColor3f(corner1[0],corner1[1],corner1[2]);
1375 glVertex2f(-1.,-1.);
1376 glColor3f(corner2[0],corner2[1],corner2[2]);
1377 glVertex2f( 1.,-1.);
1378 glColor3f(corner3[0],corner3[1],corner3[2]);
1379 glVertex2f( 1., 1.);
1380 glEnd();
1381 glBegin(GL_TRIANGLES);
1382 glColor3f(corner1[0],corner1[1],corner1[2]);
1383 glVertex2f(-1.,-1.);
1384 glColor3f(corner3[0],corner3[1],corner3[2]);
1385 glVertex2f( 1., 1.);
1386 glColor3f(corner4[0],corner4[1],corner4[2]);
1387 glVertex2f(-1., 1.);
1388 glEnd();
1389 }
1390 else if( gradient->type == 6 || gradient->type == 8 )
1391 {
1392 glBegin(GL_TRIANGLES);
1393 glColor3f(corner1[0],corner1[1],corner1[2]);
1394 glVertex2f(-1.,-1.);
1395 glColor3f(corner2[0],corner2[1],corner2[2]);
1396 glVertex2f( 1.,-1.);
1397 glColor3f(corner4[0],corner4[1],corner4[2]);
1398 glVertex2f(-1., 1.);
1399 glEnd();
1400 glBegin(GL_TRIANGLES);
1401 glColor3f(corner2[0],corner2[1],corner2[2]);
1402 glVertex2f( 1.,-1.);
1403 glColor3f(corner3[0],corner3[1],corner3[2]);
1404 glVertex2f( 1., 1.);
1405 glColor3f(corner4[0],corner4[1],corner4[2]);
1406 glVertex2f(-1., 1.);
1407 glEnd();
1408
1409 }
1410
1411 if ( upset[0] )
1412 glEnable( GL_DEPTH_TEST );
1413
1414 if ( upset[1] )
1415 glEnable( GL_LIGHTING );
1416
1417 if ( upset[2] )
1418 glShadeModel( GL_FLAT );
1419
1420 if ( zbuffer )
1421 glEnable( GL_DEPTH_TEST );
1422 glPopMatrix();
1423 glMatrixMode( GL_PROJECTION );
1424 glPopMatrix();
1425 glMatrixMode( GL_MODELVIEW );
1426
1427 free(dcorner1);
1428 free(dcorner2);
1429 dcorner1 = 0;
1430 dcorner2 = 0;
1431
1432 }
1433
1434#endif /* OCC1188*/
1435
1436 glPopAttrib();
1437
1438 /* GL_DITHER on/off pour le trace */
1439 if (TxglGetDither ())
1440 glEnable (GL_DITHER);
1441 else
1442 glDisable (GL_DITHER);
1443
1444
1445}
1446/*----------------------------------------------------------------------*/