OCC22377 Patch for visualization component
[occt.git] / src / OpenGl / OpenGl_telem_util.cxx
CommitLineData
7fd59977 1/***********************************************************************
2
3FONCTION :
4----------
5File OpenGl_telem_util :
6
7
8REMARQUES:
9----------
10
11
12HISTORIQUE DES MODIFICATIONS :
13--------------------------------
14xx-xx-xx : xxx ; Creation.
1507-02-96 : FMN ; - Ajout trace
16- Suppression code inutile
1708-03-96 : FMN ; - Ajout include manquant
1801-04-96 : CAL ; Integration MINSK portage WNT
1915-04-96 : CAL ; Integration travail PIXMAP de Jim ROTH
2022-04-96 : FMN ; Ajout TelReadImage TelDrawImage
2110-05-96 : CAL ; Ajout d'un nouveau delta dans les copies
22de pixels (voir CALL_DEF_DELTA)
2325-06-96 : FMN ; Suppression utilisation de glScissor.
2402-07-96 : FMN ; Suppression WSWSHeight et WSWSWidth
25Suppression glViewport inutile.
2618-07-96 : FMN ; Suppression TelFlush inutile.
2708-07-96 : FMN ; Suppression de OPENGL_DEBUG inutile avec la nouvelle
28version de ogldebug.
2924-10-96 : CAL ; Portage WNT
3023-01-97 : CAL ; Suppression de TelClearViews dans TelCopyBuffers
3130-01-97 : FMN ; Ajout commentaires + WNT.
3212-02-97 : FMN ; Suppression TelEnquireFacilities()
3322-04-97 : FMN ; Ajout affichage du cadre pour la copie de buffer
3430-06-97 : FMN ; Suppression OpenGl_telem_light.h
3518-07-97 : FMN ; Utilisation de la toolkit sur les lights
3607-10-97 : FMN ; Simplification WNT + correction Transient
3705-12-97 : FMN ; PRO11168: Suppression TglActiveWs pour project/unproject
3823-12-97 : FMN ; Suppression TelSetFrontFaceAttri et TelSetBackFaceAttri
3930-12-97 : FMN ; CTS18312: Correction back material
4004-05-98 : CAL ; Contournement bug SGI octane bavure de pixels (PRO12899)
4130-09-98 : CAL ; Optimisation pour eviter de charger inutilement
42les matrices de la vue.
4319-10-98 : FMN ; Suppression de glPixelTransferi dans TelEnable() car cela
44rentre en conflit avec l'utilisation d'une image de fond.
4502.14.100 : JR : Warnings on WNT truncations from double to float
4608-03-01 : GG ; BUC60823 Avoid crash in the normal computation method
47when a face has confused or aligned points.
48
49************************************************************************/
50
51#define IMP190100 /*GG To avoid too many REDRAW in immediat mode,
52// Add TelMakeFrontAndBackBufCurrent() function
53*/
54#define QTOCC_PATCH
55
56/*----------------------------------------------------------------------*/
57/*
58* Includes
59*/
60
61#include <string.h>
62#include <stdio.h>
63#include <stdlib.h>
64
65#ifndef WNT
66# include <X11/Xlib.h>
67#else
68# define STRICT
69# include <windows.h>
70#endif /* WNT */
71
72
73#include <GL/gl.h>
74#include <GL/glu.h>
75#ifndef WNT
76#include <GL/glx.h>
77#endif /* WNT */
78
79#include <InterfaceGraphic_Graphic3d.hxx>
80#include <InterfaceGraphic_Visual3d.hxx>
81
82#include <OpenGl_tgl_all.hxx>
83#include <OpenGl_tsm.hxx>
84#include <OpenGl_tsm_ws.hxx>
85#include <OpenGl_telem.hxx>
86#include <OpenGl_telem_attri.hxx>
87#include <OpenGl_telem_util.hxx>
88#include <OpenGl_telem_view.hxx>
89#include <OpenGl_tgl_tox.hxx>
90#include <OpenGl_tgl_subrvis.hxx>
91#include <OpenGl_txgl.hxx>
92#include <OpenGl_LightBox.hxx>
93#include <OpenGl_Memory.hxx>
94
95/*----------------------------------------------------------------------*/
96/*
97* Constantes
98*/
99
100#define NO_TRACE
101#define CALL_DEF_DELTA 10
102#define NO_COPYBUFFER
103
104/*----------------------------------------------------------------------*/
105/*
106* Variables statiques
107*/
108
109static Tint call_back_buffer_restored = TOff;
110
111#ifndef WNT
112
113/*
114* Wrappers and utilities used to select between pixmap and gl double buffering
115*/
116
117/* Cache some pixmap info for pixmap double buffering */
118
119static Display *window_display; /* the display in use */
120static Window window_id; /* the window to copy the pixmap to */
121static Pixmap pixmap_id; /* the pixmap id */
122static GLXPixmap glx_pixmap; /* the glx pixmap */
123static int
124window_width, /* window width and height for XCopyArea */
125window_height,
126window_depth;
127
128static GC window_gc; /* GC for XCopyArea */
129
130static GLXContext glx_context; /* GL Context */
131
132static int usePixmapDB = 0; /* True if doing pixmap double buffering */
133
134/*----------------------------------------------------------------------*/
135
136void TelSetPixmapDBParams(Display *dpy,
137 Window window,
138 int width, int height, int depth, GC gc,
139 Pixmap pixmap,
140 GLXPixmap glxpixmap,
141 GLXContext ctx)
142
143{
144 window_display = dpy;
145 window_id = window;
146 window_width = width;
147 window_height = height;
148 window_depth = depth;
149 window_gc = gc;
150
151 pixmap_id = pixmap;
152
153 glx_pixmap = glxpixmap;
154
155 glx_context = ctx;
156}
157
158GLXPixmap TelGetGLXPixmap()
159{
160 return glx_pixmap;
161}
162
163void TelSetPixmapDB(int flag)
164{
165 usePixmapDB = flag;
166}
167
168int TelTestPixmapDB()
169{
170 return usePixmapDB;
171}
172
173void TelDrawBuffer(GLenum buf)
174{
175 if (usePixmapDB)
176 glDrawBuffer(GL_FRONT);
177 else
178 glDrawBuffer(buf);
179}
180
181#endif /* WNT */
182
183/*----------------------------------------------------------------------*/
184
185void TelMakeFrontBufCurrent(Tint WsId)
186{
187#ifndef WNT
188 if (usePixmapDB)
189 {
190 glXMakeCurrent(window_display,window_id, glx_context);
191 glDrawBuffer(GL_FRONT);
192 }
193 else
194#endif /* WNT */
195 {
196 glDrawBuffer(GL_FRONT);
197 }
198}
199
200void TelMakeBackBufCurrent(Tint WsId)
201{
202#ifndef WNT
203 if (usePixmapDB)
204 {
205 glXMakeCurrent(window_display,glx_pixmap, glx_context);
206 glDrawBuffer(GL_BACK);
207 }
208 else
209#endif /* WNT */
210 {
211 glDrawBuffer(GL_BACK);
212 }
213}
214
215#ifdef IMP190100
216void TelMakeFrontAndBackBufCurrent(Tint WsId)
217{
218#ifndef WNT
219 if (usePixmapDB)
220 {
221 glXMakeCurrent(window_display,window_id, glx_context);
222 glDrawBuffer(GL_FRONT_AND_BACK);
223 }
224 else
225#endif /* WNT */
226 {
227 glDrawBuffer(GL_FRONT_AND_BACK);
228 }
229}
230#endif
231
232/*----------------------------------------------------------------------*/
233Tint
234TelRemdupnames(Tint *ls, Tint num )
235{
236 register Tint *ap, *bp, n;
237
238 if( num < 2 )
239 return num;
240
241 ap = bp = ls+1;
242 n = num-1;
243 while( n-- )
244 {
245 if( ap[-1] != *bp )
246 *ap++ = *bp++;
247 else
248 bp++;
249 }
250
251 return ap-ls;
252}
253
254/*----------------------------------------------------------------------*/
255#ifdef BUC60823
256#define GPRECIS 0.000001
257Tint TelGetPolygonNormal(tel_point pnts, Tint* indexs, Tint npnt, Tfloat *norm ) {
258 Tint status=0;
259
260 norm[0] = norm[1] = norm[2] = 0.;
261 if( npnt > 2 ) {
262 Tfloat a[3], b[3], c[3];
263 Tint i,j,i0,ii=0,jj;
264
265 i0 = 0; if( indexs ) i0 = indexs[0];
266 for( i=1 ; i<npnt ; i++ ) {
267 ii = i; if( indexs ) ii = indexs[i];
268 vecsub( a, pnts[ii].xyz, pnts[i0].xyz );
269 if( vecmg2(a) > GPRECIS ) break;
270 }
271 if( i < npnt-1 ) {
272 for( j=i+1 ; j<npnt ; j++ ) {
273 jj = j; if( indexs ) jj = indexs[j];
274 vecsub( b, pnts[jj].xyz, pnts[i0].xyz );
275 vecsub( c, pnts[jj].xyz, pnts[ii].xyz );
276 if( (vecmg2(b) > GPRECIS) && (vecmg2(c) > GPRECIS) ) break;
277 }
278 if( j < npnt ) {
279 Tfloat d;
280 veccrs( norm, a, b );
281 d = vecnrmd( norm, d );
282 status = (d > 0.) ? 1 : 0;
283 }
284 }
285 }
286#ifdef DEB
287 if( !status )
288 printf(" *** OpenGl_TelGetPolygonNormal.has found confused or aligned points\n");
289#endif
290
291 return status;
292}
293
294Tint TelGetNormal(Tfloat *data1, Tfloat *data2, Tfloat *data3, Tfloat *norm ) {
295 Tfloat a[3], b[3];
296 Tint status=0;
297
298 norm[0] = norm[1] = norm[2] = 0.;
299 vecsub( a, data2, data1 );
300 vecsub( b, data3, data2 );
301 if( (vecmg2(a) > GPRECIS) && (vecmg2(b) > GPRECIS) ) {
302 Tfloat d;
303 veccrs( norm, a, b );
304 d = vecnrmd( norm, d );
305 status = (d > 0.) ? 1 : 0;
306 }
307#ifdef DEB
308 if( !status )
309 printf(" *** OpenGl_TelGetNormal.has found confused or aligned points\n");
310#endif
311
312 return status;
313}
314#else
315void
316TelGetNormal(Tfloat *data1, Tfloat *data2, Tfloat *data3, Tfloat *norm ) {
317 Tfloat a[3], b[3];
318
319 vecsub( a, data2, data1 );
320 vecsub( b, data3, data2 );
321 veccrs( norm, a, b );
322}
323#endif
324
325/*----------------------------------------------------------------------*/
326Tint
327TelIsBackFace(Tmatrix3 n, Tfloat *nrm )
328{
329 Tfloat r[4], m[4];
330
331 veccpy(m,nrm);
332 m[3] = ( float )1.0;
333
334 TelTranpt3( r, m, n );
335
336 return r[2] < 0.0;
337}
338
339/*----------------------------------------------------------------------*/
340void
341TelTransposemat3 (Tmatrix3 a)
342{
343 Tint row, col;
344 Tmatrix3 res;
345 Tint dim = 4;
346
347 /* transposition de la sous-matrice dim x dim */
348 for (row = 0; row < dim; row++)
349 for (col = 0; col < dim; col++)
350 res[row][col] = a[col][row];
351
352 /* copie du resultat */
353 matcpy (a, res);
354
355 return;
356}
357
358/*----------------------------------------------------------------------*/
359void
360TelMultiplymat3 (Tmatrix3 c, Tmatrix3 a, Tmatrix3 b)
361{
362 Tint row, col, i;
363 Tmatrix3 res;
364 Tint dim = 4;
365
366 /* on multiplie d'abord les 2 matrices dim x dim */
367 for (row = 0; row < dim; row++) {
368 for (col = 0; col < dim; col++) {
369 Tfloat sum = ( float )0.0;
370 for (i = 0; i < dim; i++)
371 sum += a[row][i] * b[i][col];
372 res[row][col] = sum;
373 }
374 }
375
376 /* on copie ensuite le resultat */
377 matcpy (c, res);
378
379 return;
380}
381
382/*----------------------------------------------------------------------*/
383void
384TelTranpt3(Tfloat tpt[4], Tfloat pt[4], Tmatrix3 mat )
385{
386 register long i, j;
387 Tfloat sum;
388
389 for( i = 0; i < 4; i++ )
390 {
391 for( j = 0, sum = ( float )0.0; j < 4; j++ )
392 {
393 sum += pt[j] * mat[j][i];
394 }
395 tpt[i] = sum;
396 }
397 return;
398}
399
400/*----------------------------------------------------------------------*/
401void
402TelInitWS(Tint ws, Tint w, Tint h, Tfloat bgcolr, Tfloat bgcolg, Tfloat bgcolb )
403{
404 CMN_KEY_DATA data;
405
406 TsmGetWSAttri( ws, WSDbuff, &data );
407
408 glMatrixMode(GL_MODELVIEW);
409 glViewport( 0, 0, w, h);
410
411 /*
412 * CAL mai 1998
413 * Contournement bug SGI sur Octane (PRO12899)
414 * Bavures de pixels lors de la copie de vue 3d
415 */
416 glDisable (GL_SCISSOR_TEST);
417
418#ifdef TRACE
419 printf("OPENGL: TelInitWS: glClearColor %d \n", ws);
420#endif
421 if( data.ldata == TOn )
422 {
423#ifndef WNT
424 if (TelTestPixmapDB())
425 {
426 glDrawBuffer(GL_FRONT);
427 glClearColor(bgcolr, bgcolg, bgcolb, 1.0);
428 glClear(GL_COLOR_BUFFER_BIT);
429 }
430 else
431 {
432 /* QTOCC_PATCH by PCD: the frame buffer should not be cleared here
433 to avoid flicker. It is cleared properly in TelClearViews()
434 called by call_func_redraw_all_structs_begin() */
435 glDrawBuffer(GL_BACK);
436 }
437#else
438 /* QTOCC_PATCH by PCD: the frame buffer should not be cleared here
439 to avoid flicker. It is cleared properly in TelClearViews()
440 called by call_func_redraw_all_structs_begin() */
441 glDrawBuffer(GL_BACK);
442#endif /* WNT */
443 }
444 else
445 {
446 glClearColor(bgcolr, bgcolg, bgcolb, ( float )1.0);
447 glClear(GL_COLOR_BUFFER_BIT);
448 }
449 return;
450
451}
452
453
454/*----------------------------------------------------------------------*/
455void TelSwapBuffers ( Tint ws ) {
456
457#ifndef WNT
458
459 CMN_KEY_DATA data;
460
461 if (TelTestPixmapDB())
462 {
463 glFlush();
464 XCopyArea(call_thedisplay, pixmap_id, window_id,
465 window_gc, 0, 0,
466 window_width, window_height, 0, 0);
467 }
468 else
469 {
470 TsmGetWSAttri( ws, WSWindow, &data );
471 glXSwapBuffers ( call_thedisplay, data.ldata );
472 }
473
474#else
475
476 SwapBuffers ( wglGetCurrentDC () );
477 TelFlush(0);
478
479#endif /* WNT */
480
481 TelSetBackBufferRestored (TOff);
482
483#ifdef TRACE
484 printf("OPENGL: TelSwapBuffers: glXSwapBuffers %d \n", ws);
485#endif
486
487 return;
488
489} /* end TelSwapBuffers */
490
491/*----------------------------------------------------------------------*/
492Tint
493TelBackBufferRestored ()
494{
495 return call_back_buffer_restored;
496}
497
498/*----------------------------------------------------------------------*/
499void
500TelSetBackBufferRestored (Tint flag)
501{
502#ifdef TRACE
503 printf("OPENGL: TelSetBackBufferRestored(%d): \n",flag);
504#endif
505 call_back_buffer_restored = flag;
506}
507
508/*----------------------------------------------------------------------*/
509void
510TelCopyBuffers(Tint ws, GLenum from, GLenum to,
511 Tfloat xm, Tfloat ym, Tfloat zm, Tfloat XM, Tfloat YM, Tfloat ZM, Tint flag)
512{
513 CMN_KEY_DATA key;
514 Tint w, h;
515
516#ifdef TRACE
517 printf("OPENGL: TelCopyBuffers: \n");
518#endif
519
520 if (to == GL_BACK) TelSetBackBufferRestored (TOff);
521
522#ifndef WNT
523 if (TelTestPixmapDB())
524 {
525#ifdef TRACE
526 printf("OPENGL: TelSwapBuffers: glFlush \n");
527#endif
528 glFlush();
529 XCopyArea(window_display, pixmap_id, window_id,
530 window_gc, 0, 0,
531 window_width, window_height, 0, 0);
532 return;
533 }
534#endif /* WNT */
535
536 TsmGetWSAttri (ws, WSWidth, &key);
537 w = key.ldata;
538 TsmGetWSAttri (ws, WSHeight, &key);
539 h = key.ldata;
540
541 glMatrixMode (GL_PROJECTION);
542 glPushMatrix ();
543 glLoadIdentity ();
544 gluOrtho2D ((GLdouble) 0., (GLdouble) w, 0., (GLdouble) h);
545 glMatrixMode (GL_MODELVIEW);
546 glPushMatrix ();
547 glLoadIdentity ();
548
549 TelDisable (ws);
550 if (flag)
551 {
552 /*
553 * calcul de la projection de la boite
554 * et copie du rectangle projete
555 */
556 Tint i;
557 GLsizei width, height;
558 Tfloat xmr, ymr, XMR, YMR;
559 Tfloat xr[8], yr[8];
560 /*
561 * Projection de la boite englobante
562 */
563 if ((TelProjectionRaster (ws, xm, ym, zm, &xr[0], &yr[0]) == TSuccess)
564 && (TelProjectionRaster (ws, xm, YM, zm, &xr[1], &yr[1]) == TSuccess)
565 && (TelProjectionRaster (ws, XM, YM, zm, &xr[2], &yr[2]) == TSuccess)
566 && (TelProjectionRaster (ws, XM, ym, zm, &xr[3], &yr[3]) == TSuccess)
567 && (TelProjectionRaster (ws, xm, ym, ZM, &xr[4], &yr[4]) == TSuccess)
568 && (TelProjectionRaster (ws, xm, YM, ZM, &xr[5], &yr[5]) == TSuccess)
569 && (TelProjectionRaster (ws, XM, YM, ZM, &xr[6], &yr[6]) == TSuccess)
570 && (TelProjectionRaster (ws, XM, ym, ZM, &xr[7], &yr[7]) == TSuccess))
571 {
572 xmr = ymr = (float ) shortreallast ();
573 XMR = YMR = (float ) shortrealfirst ();
574 /*
575 * Recherche du rectangle projete
576 */
577 for (i=0; i<8; i++) {
578 if (xmr > xr[i]) xmr = xr[i];
579 if (ymr > yr[i]) ymr = yr[i];
580 if (XMR < xr[i]) XMR = xr[i];
581 if (YMR < yr[i]) YMR = yr[i];
582 }
583 /* pour eviter les bavures de pixels ! */
584 xmr--;ymr--;
585 XMR++;YMR++;
586
587 /*
588 * Ajout CAL : 10/05/96
589 * Si les MinMax viennent d'un ensemble de markers
590 * on ne tient pas compte du scale factor de ceux-ci
591 * dans les valeurs de MinMax. En effet, ce facteur
592 * est dans l'espace pixel et les MinMax dans l'espace
593 * du modele. Donc ajout d'un delta de pixels
594 * en esperant que les applis n'utilisent pas des
595 * markers tres gros !
596 */
597 xmr -= CALL_DEF_DELTA; ymr -= CALL_DEF_DELTA;
598 XMR += CALL_DEF_DELTA; YMR += CALL_DEF_DELTA;
599
600 /*
601 * Le rectangle projete peut-etre clippe
602 */
603 width = (GLsizei) (XMR-xmr+1);
604 height = (GLsizei) (YMR-ymr+1);
605#ifdef COPYBUFFER
606 printf ("avant clipping\n");
607 printf ("xm, ym, zm : %f, %f, %f\n", xm, ym, zm);
608 printf ("XM, YM, ZM : %f, %f, %f\n", XM, YM, ZM);
609 printf ("taille fenetre : %d, %d\n", w, h);
610 printf ("xmr, ymr by GLU : %f, %f\n", xmr, ymr);
611 printf ("YMR, YMR by GLU : %f, %f\n", XMR, YMR);
612 printf ("copie x, y, dx, dy : %d, %d, %d, %d\n\n",
613 (int) xmr, (int) ymr, (int) width, (int) height);
614#endif
615 /*
616 * (xmr,ymr) coin inferieur gauche
617 * (XMR,YMR) coin superieur droit
618 */
619 /* cas ou 1 coin est en dehors de la fenetre */
620 if (xmr < 0) { width = (GLsizei) (XMR+1); xmr = 0; }
621 if (ymr < 0) { height = (GLsizei) (YMR+1); ymr = 0; }
622 if (XMR > w) { width = (GLsizei) (w-xmr+1); }
623 if (YMR > h) { height = (GLsizei) (h-ymr+1); }
624
625 /* cas ou les 2 coins sont en dehors de la fenetre */
626 if (XMR < 0) { xmr = 0; width = height = 1; }
627 if (YMR < 0) { ymr = 0; width = height = 1; }
628 if (xmr > w) { xmr = 0; width = height = 1; }
629 if (ymr > h) { ymr = 0; width = height = 1; }
630#ifdef COPYBUFFER
631 printf ("apres clipping\n");
632 printf ("xmr, ymr by GLU : %f, %f\n", xmr, ymr);
633 printf ("YMR, YMR by GLU : %f, %f\n", XMR, YMR);
634 printf ("copie x, y, dx, dy : %d, %d, %d, %d\n\n",
635 (int) xmr, (int) ymr, (int) width, (int) height);
636#endif
637 glDrawBuffer (to);
638 glReadBuffer (from);
639 /* copie partielle */
640 glRasterPos2i ((GLint) xmr, (GLint) ymr);
641 glCopyPixels ((GLint) xmr, (GLint) ymr, width, height, GL_COLOR);
642 /* TelFlush (1); */
643 }
644 else
645 {
646 glDrawBuffer (to);
647 /* TelClearViews (ws); */
648 glReadBuffer (from);
649 /* copie complete */
650 glRasterPos2i (0, 0);
651 glCopyPixels (0, 0, w+1, h+1, GL_COLOR);
652 /* TelFlush (1); */
653 }
654 }
655 else
656 {
657 glDrawBuffer (to);
658 /* TelClearViews (ws); */
659 glReadBuffer (from);
660 /* copie complete */
661 glRasterPos2i (0, 0);
662 glCopyPixels (0, 0, w+1, h+1, GL_COLOR);
663 /* TelFlush (1); */
664 }
665 TelEnable (ws);
666
667 glMatrixMode (GL_PROJECTION);
668 glPopMatrix ();
669 glMatrixMode (GL_MODELVIEW);
670 glPopMatrix ();
671
672 glDrawBuffer (GL_BACK);
673 return;
674}
675
676/*----------------------------------------------------------------------*/
677void
678TelReadImage(Tint ws, GLenum from, Tint posx, Tint posy, Tint width, Tint height, unsigned int *image)
679{
680 CMN_KEY_DATA key;
681 Tint w, h;
682
683#ifdef TRACE
684 printf("OPENGL: TelReadImage: %d %d %d %d \n", posx, posy, width, height);
685#endif
686
687 if (image !=NULL)
688 {
689 TsmGetWSAttri (ws, WSWidth, &key);
690 w = key.ldata;
691 TsmGetWSAttri (ws, WSHeight, &key);
692 h = key.ldata;
693
694 glMatrixMode (GL_PROJECTION);
695 glLoadIdentity ();
696 gluOrtho2D ((GLdouble) 0., (GLdouble) w, 0., (GLdouble) h);
697 glMatrixMode (GL_MODELVIEW);
698 glLoadIdentity ();
699
700 glReadBuffer(from);
701
702 glRasterPos2i (posx, posy);
703 TelDisable (ws);
704 glReadPixels (posx, posy, width, height, GL_RGBA, GL_UNSIGNED_BYTE, image);
705 TelEnable (ws);
706
707 glReadBuffer(GL_BACK);
708 }
709
710 return;
711}
712
713/*----------------------------------------------------------------------*/
714void
715TelDrawImage(Tint ws, GLenum to, Tint posx, Tint posy, Tint width, Tint height, unsigned int *image)
716{
717 CMN_KEY_DATA key;
718 Tint w, h;
719
720#ifdef TRACE
721 printf("OPENGL: TelDrawImage: %d %d %d %d \n", posx, posy, width, height);
722#endif
723
724 if (image !=NULL)
725 {
726 TsmGetWSAttri (ws, WSWidth, &key);
727 w = key.ldata;
728 TsmGetWSAttri (ws, WSHeight, &key);
729 h = key.ldata;
730
731 glMatrixMode (GL_PROJECTION);
732 glLoadIdentity ();
733 gluOrtho2D ((GLdouble) 0., (GLdouble) w, 0., (GLdouble) h);
734 glMatrixMode (GL_MODELVIEW);
735 glLoadIdentity ();
736
737 glDrawBuffer(to);
738
739 glRasterPos2i (posx, posy);
740 TelDisable (ws);
741 glDrawPixels (width, height, GL_RGBA, GL_UNSIGNED_BYTE, image);
742 TelEnable (ws);
743
744 glDrawBuffer(GL_BACK);
745 }
746 return;
747}
748
749/*----------------------------------------------------------------------*/
750void
751TelReadDepths(Tint ws, Tint posx, Tint posy, Tint width, Tint height, float *depths)
752{
753 CMN_KEY_DATA key;
754 Tint w, h;
755
756#ifdef TRACE
757 printf("OPENGL: TelReadDepths: %d %d %d %d \n", posx, posy, width, height);
758#endif
759
760 if ( TsmGetWSAttri (ws, WSWindow, &key) != TSuccess ) return;
761
762 if (depths != NULL && TxglWinset (call_thedisplay, (WINDOW) key.ldata) == TSuccess)
763 {
764 TsmGetWSAttri (ws, WSWidth, &key);
765 w = key.ldata;
766 TsmGetWSAttri (ws, WSHeight, &key);
767 h = key.ldata;
768
769 glMatrixMode (GL_PROJECTION);
770 glLoadIdentity ();
771 gluOrtho2D ((GLdouble) 0., (GLdouble) w, 0., (GLdouble) h);
772 glMatrixMode (GL_MODELVIEW);
773 glLoadIdentity ();
774
775 glRasterPos2i (posx, posy);
776 TelDisable (ws);
777 glReadPixels (posx, posy, width, height, GL_DEPTH_COMPONENT, GL_FLOAT, depths);
778 TelEnable (ws);
779 }
780
781 return;
782}
783
784/*----------------------------------------------------------------------*/
785void
786TelEnable (Tint ws)
787{
788 /*glPixelTransferi (GL_MAP_COLOR, GL_TRUE);*/
789
790 /* GL_DITHER on/off pour le trace */
791 if (TxglGetDither())
792 glEnable (GL_DITHER);
793 else
794 glDisable (GL_DITHER);
795
796 return;
797}
798
799/*----------------------------------------------------------------------*/
800void
801TelDisable (Tint ws)
802{
803 glDisable (GL_DITHER);
804 glPixelTransferi (GL_MAP_COLOR, GL_FALSE);
805
806 /*
807 * Disable stuff that's likely to slow down glDrawPixels.
808 * (Omit as much of this as possible, when you know in advance
809 * that the OpenGL state will already be set correctly.)
810 */
811 glDisable(GL_ALPHA_TEST);
812 glDisable(GL_BLEND);
813 glDisable(GL_DEPTH_TEST);
814 glDisable(GL_FOG);
815 LightOff();
816
817 glDisable(GL_LOGIC_OP);
818 glDisable(GL_STENCIL_TEST);
819 glDisable(GL_TEXTURE_1D);
820 glDisable(GL_TEXTURE_2D);
821 glPixelTransferi(GL_MAP_COLOR, GL_FALSE);
822 glPixelTransferi(GL_RED_SCALE, 1);
823 glPixelTransferi(GL_RED_BIAS, 0);
824 glPixelTransferi(GL_GREEN_SCALE, 1);
825 glPixelTransferi(GL_GREEN_BIAS, 0);
826 glPixelTransferi(GL_BLUE_SCALE, 1);
827 glPixelTransferi(GL_BLUE_BIAS, 0);
828 glPixelTransferi(GL_ALPHA_SCALE, 1);
829 glPixelTransferi(GL_ALPHA_BIAS, 0);
830
831 /*
832 * Disable extensions that could slow down glDrawPixels.
833 * (Actually, you should check for the presence of the proper
834 * extension before making these calls. I've omitted that
835 * code for simplicity.)
836 */
837
838#ifdef GL_EXT_convolution
839 glDisable(GL_CONVOLUTION_1D_EXT);
840 glDisable(GL_CONVOLUTION_2D_EXT);
841 glDisable(GL_SEPARABLE_2D_EXT);
842#endif
843
844#ifdef GL_EXT_histogram
845 glDisable(GL_HISTOGRAM_EXT);
846 glDisable(GL_MINMAX_EXT);
847#endif
848
849#ifdef GL_EXT_texture3D
850 glDisable(GL_TEXTURE_3D_EXT);
851#endif
852
853 return;
854}
855
856/*----------------------------------------------------------------------*/
857TStatus
858TelProjectionRaster(Tint ws, Tfloat x, Tfloat y, Tfloat z, Tfloat *xr, Tfloat *yr)
859{
860 Tint w, h;
861 CMN_KEY_DATA key;
862 Tint vid; /* View index */
863 TEL_VIEW_REP vrep; /* View definition */
864
865 GLint status;
866
867 int i, j, k;
868 GLdouble objx, objy, objz;
869 GLdouble modelMatrix[16], projMatrix[16];
870 GLint viewport[4];
871 GLdouble winx, winy, winz;
872
873 vid = ws;
874
875 if (TelGetViewRepresentation (ws, vid, &vrep) != TSuccess)
876 return TFailure;
877
878 TsmGetWSAttri (ws, WSWidth, &key);
879 w = key.ldata;
880 TsmGetWSAttri (ws, WSHeight, &key);
881 h = key.ldata;
882
883 objx = ( GLdouble )x; objy = ( GLdouble )y; objz = ( GLdouble )z;
884
885 for (k = 0, i = 0; i < 4; i++)
886 for (j = 0; j < 4; j++, k++)
887 modelMatrix[k] = ( GLdouble )vrep.orientation_matrix[i][j];
888
889 for (k = 0, i = 0; i < 4; i++)
890 for (j = 0; j < 4; j++, k++)
891 projMatrix[k] = ( GLdouble )vrep.mapping_matrix[i][j];
892
893 viewport[0] = 0;
894 viewport[1] = 0;
895 viewport[2] = w;
896 viewport[3] = h;
897
898 /*
899 * glGetIntegerv (GL_VIEWPORT, viewport);
900 * glGetDoublev (GL_MODELVIEW_MATRIX, modelMatrix);
901 * glGetDoublev (GL_PROJECTION_MATRIX, projMatrix);
902 */
903
904 status = gluProject (objx, objy, objz,
905 modelMatrix, projMatrix, viewport,
906 &winx, &winy, &winz);
907
908 if (status == GL_TRUE) {
909 *xr = ( Tfloat )winx;
910 *yr = ( Tfloat )winy;
911 return TSuccess;
912 }
913 else
914 {
915 *xr = 0.0F;
916 *yr = 0.0F;
917 return TFailure;
918 }
919}
920
921/*----------------------------------------------------------------------*/
922TStatus
923TelUnProjectionRaster(Tint ws, Tint xr, Tint yr, Tfloat *x, Tfloat *y, Tfloat *z)
924{
925 Tint w, h;
926 CMN_KEY_DATA key;
927 Tint vid; /* View index */
928 TEL_VIEW_REP vrep; /* View definition */
929
930 int i, j, k;
931 GLdouble objx, objy, objz;
932 GLdouble modelMatrix[16], projMatrix[16];
933 GLint viewport[4];
934 GLdouble winx, winy, winz;
935 GLint status;
936
937 vid = ws;
938
939 if (TelGetViewRepresentation (ws, vid, &vrep) != TSuccess)
940 return TFailure;
941
942 TsmGetWSAttri (ws, WSWidth, &key);
943 w = key.ldata;
944 TsmGetWSAttri (ws, WSHeight, &key);
945 h = key.ldata;
946
947 winx = ( GLdouble )xr; winy = ( GLdouble )yr; winz = ( GLdouble )0.0;
948
949 for (k = 0, i = 0; i < 4; i++)
950 for (j = 0; j < 4; j++, k++)
951 modelMatrix[k] = ( GLdouble )vrep.orientation_matrix[i][j];
952
953 for (k = 0, i = 0; i < 4; i++)
954 for (j = 0; j < 4; j++, k++)
955 projMatrix[k] = ( GLdouble )vrep.mapping_matrix[i][j];
956
957 viewport[0] = 0;
958 viewport[1] = 0;
959 viewport[2] = w;
960 viewport[3] = h;
961
962 /*
963 * glGetIntegerv (GL_VIEWPORT, viewport);
964 * glGetDoublev (GL_MODELVIEW_MATRIX, modelMatrix);
965 * glGetDoublev (GL_PROJECTION_MATRIX, projMatrix);
966 */
967
968 status = gluUnProject (winx, winy, winz, modelMatrix, projMatrix, viewport,
969 &objx, &objy, &objz);
970
971 if (status == GL_TRUE) {
972 *x = ( Tfloat )objx;
973 *y = ( Tfloat )objy;
974 *z = ( Tfloat )objz;
975
976 return TSuccess;
977 }
978 else {
979 *x = 0.0F;
980 *y = 0.0F;
981 *z = 0.0F;
982
983 return TFailure;
984 }
985}
986
987/*----------------------------------------------------------------------*/
988TStatus
989TelUnProjectionRasterWithRay(Tint ws, Tint xr, Tint yr, Tfloat *x, Tfloat *y, Tfloat *z,
990 Tfloat *dx, Tfloat *dy, Tfloat *dz)
991{
992 Tint w, h;
993 CMN_KEY_DATA key;
994 Tint vid; /* View index */
995 TEL_VIEW_REP vrep; /* View definition */
996
997 int i, j, k;
998 GLdouble objx, objy, objz;
999 GLdouble objx1, objy1, objz1;
1000 GLdouble modelMatrix[16], projMatrix[16];
1001 GLint viewport[4];
1002 GLdouble winx, winy, winz;
1003 GLint status;
1004
1005 vid = ws;
1006
1007 if (TelGetViewRepresentation (ws, vid, &vrep) != TSuccess)
1008 return TFailure;
1009
1010 TsmGetWSAttri (ws, WSWidth, &key);
1011 w = key.ldata;
1012 TsmGetWSAttri (ws, WSHeight, &key);
1013 h = key.ldata;
1014
1015 winx = ( GLdouble )xr; winy = ( GLdouble )yr; winz = ( GLdouble )0.0;
1016
1017 for (k = 0, i = 0; i < 4; i++)
1018 for (j = 0; j < 4; j++, k++)
1019 modelMatrix[k] = ( GLdouble )vrep.orientation_matrix[i][j];
1020
1021 for (k = 0, i = 0; i < 4; i++)
1022 for (j = 0; j < 4; j++, k++)
1023 projMatrix[k] = ( GLdouble )vrep.mapping_matrix[i][j];
1024
1025 viewport[0] = 0;
1026 viewport[1] = 0;
1027 viewport[2] = w;
1028 viewport[3] = h;
1029
1030 /*
1031 * glGetIntegerv (GL_VIEWPORT, viewport);
1032 * glGetDoublev (GL_MODELVIEW_MATRIX, modelMatrix);
1033 * glGetDoublev (GL_PROJECTION_MATRIX, projMatrix);
1034 */
1035
1036 status = gluUnProject (winx, winy, winz, modelMatrix, projMatrix, viewport,
1037 &objx, &objy, &objz);
1038
1039 if (status == GL_TRUE) {
1040 *x = ( Tfloat )objx;
1041 *y = ( Tfloat )objy;
1042 *z = ( Tfloat )objz;
1043
1044 winz = ( GLdouble ) -10.0;
1045 status = gluUnProject (winx, winy, winz, modelMatrix, projMatrix, viewport,
1046 &objx1, &objy1, &objz1);
1047
1048 if (status == GL_TRUE) {
1049 *dx = ( Tfloat )(objx-objx1);
1050 *dy = ( Tfloat )(objy-objy1);
1051 *dz = ( Tfloat )(objz-objz1);
1052
1053 return TSuccess;
1054 }
1055 else {
1056 *dx = 0.0F;
1057 *dy = 0.0F;
1058 *dz = 0.0F;
1059
1060 return TFailure;
1061 }
1062 }
1063 else {
1064 *x = 0.0F;
1065 *y = 0.0F;
1066 *z = 0.0F;
1067 *dx = 0.0F;
1068 *dy = 0.0F;
1069 *dz = 0.0F;
1070
1071 return TFailure;
1072 }
1073}
1074
1075/*----------------------------------------------------------------------*/
1076void
1077TelFlush(Tint wait)
1078{
1079 if (wait)
1080 {
1081#ifdef TRACE
1082 printf("OPENGL: TelFlush: glFinish \n");
1083#endif
1084 glFinish ();
1085 }
1086 else
1087 {
1088#ifdef TRACE
1089 printf("OPENGL: TelFlush: glFlush \n");
1090#endif
1091 glFlush();
1092 }
1093 return;
1094}
1095
1096/*----------------------------------------------------------------------*/
1097Tint
1098TelIsBackFacePerspective(Tmatrix3 n, Tfloat *p1, Tfloat *p2, Tfloat *p3 )
1099{
1100 Tfloat r1[4], r2[4], r3[4], m[4], norm[4];
1101
1102 veccpy( m, p1 );
1103 m[3] = ( float )1.0;
1104 TelTranpt3( r1, m, n );
1105 r1[0] /= r1[3];
1106 r1[1] /= r1[3];
1107 r1[2] /= r1[3];
1108
1109 veccpy( m, p2 );
1110 m[3] = ( float )1.0;
1111 TelTranpt3( r2, m, n );
1112 r2[0] /= r2[3];
1113 r2[1] /= r2[3];
1114 r2[2] /= r2[3];
1115
1116 veccpy( m, p3 );
1117 m[3] = ( float )1.0;
1118 TelTranpt3( r3, m, n );
1119 r3[0] /= r3[3];
1120 r3[1] /= r3[3];
1121 r3[2] /= r3[3];
1122 TelGetNormal( r1, r2, r3, norm );
1123
1124 return norm[2] < 0.0;
1125}
1126
1127/*----------------------------------------------------------------------*/