source: trunk/src/opengl/mesa/wmesa.c@ 2959

Last change on this file since 2959 was 2938, checked in by sandervl, 25 years ago

created

File size: 86.9 KB
Line 
1/* $Id: wmesa.c,v 1.1 2000-02-29 00:50:15 sandervl Exp $ */
2
3/*
4* File name : wmesa.c
5* Version : 2.3
6*
7* Display driver for Mesa 2.3 under
8* Windows95 and WindowsNT
9*
10* Copyright (C) 1996- Li Wei
11* Address : Institute of Artificial Intelligence
12* : & Robotics
13* : Xi'an Jiaotong University
14* Email : liwei@aiar.xjtu.edu.cn
15* Web page : http://sun.aiar.xjtu.edu.cn
16*
17* This file and its associations are partially borrowed from the
18* Windows NT driver for Mesa 1.8 , written by Mark Leaming
19* (mark@rsinc.com).
20*/
21
22
23/*
24 * $Log: wmesa.c,v $
25 * Revision 1.1 2000-02-29 00:50:15 sandervl
26 * created
27 *
28 * Revision 1.1.1.1 1999/08/19 00:55:42 jtg
29 * Imported sources
30 *
31 * Revision 3.10 1999/06/15 01:35:06 brianp
32 * small change to wmSetPixel() from TWILMOT@cpr.fr
33 *
34 * Revision 3.9 1999/05/11 19:06:01 brianp
35 * fixed a few VB->Index bugs (mikec@ensoniq.com)
36 *
37 * Revision 3.8 1999/05/08 15:15:23 brianp
38 * various updates from mikec@ensoniq.com
39 *
40 * Revision 3.7 1999/04/01 01:27:34 brianp
41 * always flip Y coord in read_rgba_span()
42 *
43 * Revision 3.6 1999/03/28 21:17:27 brianp
44 * updated SetBuffer driver function
45 *
46 * Revision 3.5 1999/03/16 01:36:42 brianp
47 * patched dither() to check if Current is NULL, per xzhou@nyx.net
48 *
49 * Revision 3.4 1999/02/25 14:12:33 keithw
50 * Merged in kw3 patch
51 *
52 * Revision 3.3 1999/01/03 03:08:57 brianp
53 * Ted Jump's changes
54 *
55 * Revision 3.2 1998/08/29 00:26:01
56 * updated for Mesa 3.0 to accomodate EGCS-Mingw32 build
57 *
58 * Revision 3.1 1998/06/11 01:42:08 brianp
59 * updated for Mesa 3.0 device driver interface (but not tested)
60 *
61 * Revision 3.0 1998/06/11 01:18:25 brianp
62 * initial revision
63 *
64 */
65
66
67#define WMESA_STEREO_C
68
69#include <windows.h>
70#include <stdio.h>
71#include <stdlib.h>
72#include "wmesa.h"
73#include "mesa_extend.h"
74#include "colors.h"
75#include "macros.h"
76#include "context.h"
77#include "dd.h"
78#include "xform.h"
79#include "vb.h"
80#include "matrix.h"
81#include "depth.h"
82#include "wmesadef.h"
83
84#ifndef __WIN32OS2__
85#pragma warning ( disable : 4133 4761 )
86#endif
87
88#ifdef PROFILE
89 /* #include "profile.h" */
90#endif
91
92#ifdef DITHER
93#include <wing.h>
94#endif
95
96#ifdef __CYGWIN32__
97#include "macros.h"
98#include <string.h>
99#define CopyMemory memcpy
100#endif
101
102#if !defined(NO_STEREO)
103
104#include "glu.h"
105#include "stereo.h"
106
107#endif
108#if !defined(NO_PARALLEL)
109 /* #include "parallel.h" */
110#endif
111
112struct DISPLAY_OPTIONS displayOptions;
113
114GLenum stereoCompile = GL_FALSE ;
115GLenum stereoShowing = GL_FALSE ;
116GLenum stereoBuffer = GL_FALSE;
117#if !defined(NO_STEREO)
118GLint displayList = MAXIMUM_DISPLAY_LIST ;
119#endif
120GLint stereo_flag = 0 ;
121
122/* end of added code*/
123
124static PWMC Current = NULL;
125WMesaContext WC = NULL;
126
127#ifdef NDEBUG
128#ifndef assert
129#define assert(ignore) ((void) 0)
130#endif
131#else
132void Mesa_Assert(void *Cond,void *File,unsigned Line)
133{
134 char Msg[512];
135 sprintf(Msg,"%s %s %d",Cond,File,Line);
136 MessageBox(NULL,Msg,"Assertion failed.",MB_OK);
137 exit(1);
138}
139#undef assert
140#define assert(e) if (!e) Mesa_Assert(#e,__FILE__,__LINE__);
141#endif
142
143//#define DD_GETDC (Current->hDC )
144#define DD_GETDC ((Current->db_flag) ? Current->dib.hDC : Current->hDC )
145//#define DD_GETDC ((Current->db_flag) ? Current->hDCPrimary : Current->hDCBack )
146#define DD_RELEASEDC
147
148//#define BEGINGDICALL if(Current->rgb_flag)wmFlushBits(Current);
149#define BEGINGDICALL
150//#define ENDGDICALL if(Current->rgb_flag)wmGetBits(Current);
151#define ENDGDICALL
152
153//#define FLIP(Y) (Current->dither_flag? Y : Current->height-(Y)-1)
154//#define FLIP(Y) (Current->height-(Y)-1)
155//#define FLIP(Y) Y
156/*
157 * XXX Why only flip Y coord if single buffered???
158 */
159#define FLIP(Y) (Current->db_flag? Y: Current->height-(Y)-1)
160#define STARTPROFILE
161#define ENDPROFILE(PARA)
162
163#define DITHER_RGB_TO_8BIT_SETUP \
164GLubyte pixelDithered;
165
166#define DITHER_RGB_TO_8BIT(red, green, blue, pixel, scanline) \
167{ \
168 char unsigned redtemp, greentemp, bluetemp, paletteindex; \
169 redtemp = aDividedBy51[red] \
170 + (aModulo51[red] > aHalftone8x8[(pixel%8)*8 \
171 + scanline%8]); \
172 greentemp = aDividedBy51[(char unsigned)green] \
173 + (aModulo51[green] > aHalftone8x8[ \
174 (pixel%8)*8 + scanline%8]); \
175 bluetemp = aDividedBy51[(char unsigned)blue] \
176 + (aModulo51[blue] > aHalftone8x8[ \
177 (pixel%8)*8 +scanline%8]); \
178 paletteindex = redtemp + aTimes6[greentemp] + aTimes36[bluetemp]; \
179 pixelDithered = aWinGHalftoneTranslation[paletteindex]; \
180}
181
182
183#ifdef DDRAW
184static BOOL DDInit( WMesaContext wc, HWND hwnd);
185static void DDFree( WMesaContext wc);
186static HRESULT DDRestoreAll( WMesaContext wc );
187static void DDDeleteOffScreen(WMesaContext wc);
188static BOOL DDCreateOffScreen(WMesaContext wc);
189#endif
190
191static void FlushToFile(PWMC pwc, PSTR szFile);
192
193BOOL wmCreateBackingStore(PWMC pwc, long lxSize, long lySize);
194BOOL wmDeleteBackingStore(PWMC pwc);
195void wmCreatePalette( PWMC pwdc );
196BOOL wmSetDibColors(PWMC pwc);
197void wmSetPixel(PWMC pwc, int iScanLine, int iPixel, BYTE r, BYTE g, BYTE b);
198
199void wmCreateDIBSection(
200 HDC hDC,
201 PWMC pwc, /* handle of device context */
202 CONST BITMAPINFO *pbmi,/* address of structure containing bitmap size, format, and color data*/
203 UINT iUsage/* color data type indicator: RGB values or palette indices*/
204 );
205
206
207void WMesaViewport( GLcontext *ctx,
208 GLint x, GLint y, GLsizei width, GLsizei height );
209
210
211static triangle_func choose_triangle_function( GLcontext *ctx );
212
213
214static void wmSetPixelFormat( PWMC wc, HDC hDC)
215{
216 if(wc->rgb_flag)
217 wc->cColorBits = GetDeviceCaps(hDC, BITSPIXEL);
218 else
219 wc->cColorBits = 8;
220 switch(wc->cColorBits){
221 case 8:
222 if(wc->dither_flag != GL_TRUE)
223 wc->pixelformat = PF_INDEX8;
224 else
225 wc->pixelformat = PF_DITHER8;
226 break;
227 case 16:
228 wc->pixelformat = PF_5R6G5B;
229 break;
230 case 32:
231 wc->pixelformat = PF_8R8G8B;
232 break;
233 default:
234 wc->pixelformat = PF_BADFORMAT;
235 }
236}
237
238//
239// This function sets the color table of a DIB section
240// to match that of the destination DC
241//
242BOOL /*WINAPI*/ wmSetDibColors(PWMC pwc)
243{
244 RGBQUAD *pColTab, *pRGB;
245 PALETTEENTRY *pPal, *pPE;
246 int i, nColors;
247 BOOL bRet=TRUE;
248 DWORD dwErr=0;
249
250 /* Build a color table in the DIB that maps to the
251 selected palette in the DC.
252 */
253 nColors = 1 << pwc->cColorBits;
254 pPal = (PALETTEENTRY *)malloc( nColors * sizeof(PALETTEENTRY));
255 memset( pPal, 0, nColors * sizeof(PALETTEENTRY) );
256 GetPaletteEntries( pwc->hGLPalette, 0, nColors, pPal );
257 pColTab = (RGBQUAD *)malloc( nColors * sizeof(RGBQUAD));
258 for (i = 0, pRGB = pColTab, pPE = pPal; i < nColors; i++, pRGB++, pPE++) {
259 pRGB->rgbRed = pPE->peRed;
260 pRGB->rgbGreen = pPE->peGreen;
261 pRGB->rgbBlue = pPE->peBlue;
262 }
263 if(pwc->db_flag)
264 bRet = SetDIBColorTable(pwc->dib.hDC, 0, nColors, pColTab );
265
266 if(!bRet)
267 dwErr = GetLastError();
268
269 free( pColTab );
270 free( pPal );
271
272 return(bRet);
273}
274
275
276//
277// Free up the dib section that was created
278//
279BOOL wmDeleteBackingStore(PWMC pwc)
280{
281 SelectObject(pwc->dib.hDC, pwc->hOldBitmap);
282 DeleteDC(pwc->dib.hDC);
283 DeleteObject(pwc->hbmDIB);
284 UnmapViewOfFile(pwc->dib.base);
285 CloseHandle(pwc->dib.hFileMap);
286 return TRUE;
287}
288
289
290//
291// This function creates the DIB section that is used for combined
292// GL and GDI calls
293//
294BOOL /*WINAPI*/ wmCreateBackingStore(PWMC pwc, long lxSize, long lySize)
295{
296 HDC hdc = pwc->hDC;
297 LPBITMAPINFO pbmi = &(pwc->bmi);
298 int iUsage;
299
300 pbmi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
301 pbmi->bmiHeader.biWidth = lxSize;
302 pbmi->bmiHeader.biHeight= -lySize;
303 pbmi->bmiHeader.biPlanes = 1;
304 if(pwc->rgb_flag)
305 pbmi->bmiHeader.biBitCount = GetDeviceCaps(pwc->hDC, BITSPIXEL);
306 else
307 pbmi->bmiHeader.biBitCount = 8;
308 pbmi->bmiHeader.biCompression = BI_RGB;
309 pbmi->bmiHeader.biSizeImage = 0;
310 pbmi->bmiHeader.biXPelsPerMeter = 0;
311 pbmi->bmiHeader.biYPelsPerMeter = 0;
312 pbmi->bmiHeader.biClrUsed = 0;
313 pbmi->bmiHeader.biClrImportant = 0;
314
315 iUsage = (pbmi->bmiHeader.biBitCount <= 8) ? DIB_PAL_COLORS : DIB_RGB_COLORS;
316
317 pwc->cColorBits = pbmi->bmiHeader.biBitCount;
318 pwc->ScanWidth = pwc->pitch = lxSize;
319
320 wmCreateDIBSection(hdc, pwc, pbmi, iUsage);
321
322 if ((iUsage == DIB_PAL_COLORS) && !(pwc->hGLPalette)) {
323 wmCreatePalette( pwc );
324 wmSetDibColors( pwc );
325 }
326 wmSetPixelFormat(pwc, pwc->hDC);
327 return(TRUE);
328
329}
330
331
332//
333// This function copies one scan line in a DIB section to another
334//
335BOOL WINAPI wmSetDIBits(PWMC pwc, UINT uiScanWidth, UINT uiNumScans, UINT nBypp, UINT uiNewWidth, LPBYTE pBits)
336{
337 UINT uiScans = 0;
338 LPBYTE pDest = pwc->pbPixels;
339 DWORD dwNextScan = uiScanWidth;
340 DWORD dwNewScan = uiNewWidth;
341 DWORD dwScanWidth = (uiScanWidth * nBypp);
342
343 dprintf(("OPENGL32: wmSetDIBits\n"));
344
345 //
346 // We need to round up to the nearest DWORD
347 // and multiply by the number of bytes per
348 // pixel
349 //
350 dwNextScan = (((dwNextScan * nBypp)+ 3) & ~3);
351 dwNewScan = (((dwNewScan * nBypp)+ 3) & ~3);
352
353 for(uiScans = 0; uiScans < uiNumScans; uiScans++){
354 memcpy(pDest, pBits, dwScanWidth);
355 pBits += dwNextScan;
356 pDest += dwNewScan;
357 }
358
359 return(TRUE);
360
361}
362
363
364BOOL wmFlush(PWMC pwc);
365
366/*
367* Useful macros:
368Modified from file osmesa.c
369*/
370
371
372#define PIXELADDR(X,Y) ((GLubyte *)Current->pbPixels + (Current->height-Y-1)* Current->ScanWidth + (X)*nBypp)
373#define PIXELADDR1( X, Y ) \
374((GLubyte *)wmesa->pbPixels + (wmesa->height-Y-1)* wmesa->ScanWidth + (X))
375#define PIXELADDR2( X, Y ) \
376((GLubyte *)wmesa->pbPixels + (wmesa->height-Y-1)* wmesa->ScanWidth + (X)*2)
377#define PIXELADDR4( X, Y ) \
378((GLubyte *)wmesa->pbPixels + (wmesa->height-Y-1)* wmesa->ScanWidth + (X)*4)
379
380
381BYTE DITHER_RGB_2_8BIT( int r, int g, int b, int x, int y);
382
383/* Finish all pending operations and synchronize. */
384static void finish(GLcontext* ctx)
385{
386 /* No op */
387}
388
389
390//
391// We cache all gl draw routines until a flush is made
392//
393static void flush(GLcontext* ctx)
394{
395 STARTPROFILE
396 if((Current->rgb_flag /*&& !(Current->dib.fFlushed)*/&&!(Current->db_flag))
397 ||(!Current->rgb_flag))
398 {
399 wmFlush(Current);
400 }
401 ENDPROFILE(flush)
402
403}
404
405
406
407/*
408* Set the color index used to clear the color buffer.
409*/
410static void clear_index(GLcontext* ctx, GLuint index)
411{
412 STARTPROFILE
413 Current->clearpixel = index;
414 ENDPROFILE(clear_index)
415}
416
417
418
419/*
420* Set the color used to clear the color buffer.
421*/
422static void clear_color( GLcontext* ctx, GLubyte r, GLubyte g, GLubyte b, GLubyte a )
423{
424 STARTPROFILE
425 Current->clearpixel=RGB(r, g, b );
426 ENDPROFILE(clear_color)
427}
428
429
430
431/*
432* Clear the specified region of the color buffer using the clear color
433* or index as specified by one of the two functions above.
434*/
435//static void clear(GLcontext* ctx,
436// GLboolean all,GLint x, GLint y, GLint width, GLint height )
437// TODO: I modified this function to match the prototype in dd.h. (swansma@geocities.com)
438// dd.h does not explain what the return type is so I could not set this to the proper
439// value.
440static GLbitfield clear(GLcontext* ctx, GLbitfield mask,
441 GLboolean all, GLint x, GLint y, GLint width, GLint height)
442{
443 DWORD dwColor;
444 WORD wColor;
445 BYTE bColor;
446 LPDWORD lpdw = (LPDWORD)Current->pbPixels;
447 LPWORD lpw = (LPWORD)Current->pbPixels;
448 LPBYTE lpb = Current->pbPixels;
449 int lines;
450
451 dprintf(("OPENGL32: clear\n"));
452
453 STARTPROFILE
454
455 if (all){
456 x=y=0;
457 width=Current->width;
458 height=Current->height;
459 }
460 if(Current->db_flag==GL_TRUE){
461 UINT nBypp = Current->cColorBits / 8;
462 int i = 0;
463 int iSize = 0;
464
465 if(nBypp ==1 ){
466 /* Need rectification */
467 iSize = Current->width/4;
468 bColor = BGR8(GetRValue(Current->clearpixel),
469 GetGValue(Current->clearpixel),
470 GetBValue(Current->clearpixel));
471 wColor = MAKEWORD(bColor,bColor);
472 dwColor = MAKELONG(wColor, wColor);
473 }
474 if(nBypp == 2){
475 iSize = Current->width / 2;
476 wColor = BGR16(GetRValue(Current->clearpixel),
477 GetGValue(Current->clearpixel),
478 GetBValue(Current->clearpixel));
479 dwColor = MAKELONG(wColor, wColor);
480 }
481 else if(nBypp == 4){
482 iSize = Current->width;
483 dwColor = BGR32(GetRValue(Current->clearpixel),
484 GetGValue(Current->clearpixel),
485 GetBValue(Current->clearpixel));
486 }
487
488 while(i < iSize){
489 *lpdw = dwColor;
490 lpdw++;
491 i++;
492 }
493
494 //
495 // This is the 24bit case
496 //
497 if (nBypp == 3) {
498 iSize = Current->width *3/4;
499 dwColor = BGR24(GetRValue(Current->clearpixel),
500 GetGValue(Current->clearpixel),
501 GetBValue(Current->clearpixel));
502 while(i < iSize){
503 *lpdw = dwColor;
504 lpb += nBypp;
505 lpdw = (LPDWORD)lpb;
506 i++;
507 }
508 }
509
510 i = 0;
511 if (stereo_flag)
512 lines = height /2;
513 else
514 lines = height;
515 do {
516 memcpy(lpb, Current->pbPixels, iSize*4);
517 lpb += Current->ScanWidth;
518 i++;
519 }
520 while (i<lines-1);
521 }
522 else { // For single buffer
523 HDC DC=DD_GETDC;
524 HPEN Pen=CreatePen(PS_SOLID,1,Current->clearpixel);
525 HBRUSH Brush=CreateSolidBrush(Current->clearpixel);
526 HPEN Old_Pen=SelectObject(DC,Pen);
527 HBRUSH Old_Brush=SelectObject(DC,Brush);
528// Rectangle(DC,x,y,x+width,y+height);
529 SelectObject(DC,Old_Pen);
530 SelectObject(DC,Old_Brush);
531 DeleteObject(Pen);
532 DeleteObject(Brush);
533 DD_RELEASEDC;
534 }
535
536
537
538 ENDPROFILE(clear)
539
540 return mask; // TODO: I doubt this is correct. dd.h doesn't explain what this should
541 // be...
542}
543
544
545
546/* Set the current color index. */
547static void set_index(GLcontext* ctx, GLuint index)
548{
549 STARTPROFILE
550 Current->pixel=index;
551 ENDPROFILE(set_index)
552}
553
554
555
556/* Set the current RGBA color. */
557static void set_color( GLcontext* ctx, GLubyte r, GLubyte g, GLubyte b, GLubyte a )
558{
559 STARTPROFILE
560 Current->pixel = RGB( r, g, b );
561 ENDPROFILE(set_color)
562}
563
564
565
566/* Set the index mode bitplane mask. */
567static GLboolean index_mask(GLcontext* ctx, GLuint mask)
568{
569 /* can't implement */
570 return GL_FALSE;
571}
572
573
574
575/* Set the RGBA drawing mask. */
576static GLboolean color_mask( GLcontext* ctx,
577 GLboolean rmask, GLboolean gmask,
578 GLboolean bmask, GLboolean amask)
579{
580 /* can't implement */
581 return GL_FALSE;
582}
583
584
585
586/*
587* Set the pixel logic operation. Return GL_TRUE if the device driver
588* can perform the operation, otherwise return GL_FALSE. If GL_FALSE
589* is returned, the logic op will be done in software by Mesa.
590*/
591GLboolean logicop( GLcontext* ctx, GLenum op )
592{
593 /* can't implement */
594 return GL_FALSE;
595}
596
597
598static void dither( GLcontext* ctx, GLboolean enable )
599{
600 if (!Current)
601 return;
602
603 if(enable == GL_FALSE){
604 Current->dither_flag = GL_FALSE;
605 if(Current->cColorBits == 8)
606 Current->pixelformat = PF_INDEX8;
607 }
608 else{
609 if (Current->rgb_flag && Current->cColorBits == 8){
610 Current->pixelformat = PF_DITHER8;
611 Current->dither_flag = GL_TRUE;
612 }
613 else
614 Current->dither_flag = GL_FALSE;
615 }
616}
617
618
619
620static GLboolean set_buffer( GLcontext* ctx, GLenum mode )
621{
622 STARTPROFILE
623 /* TODO: this could be better */
624 if (mode==GL_FRONT_LEFT || mode==GL_BACK_LEFT) {
625 return GL_TRUE;
626 }
627 else {
628 return GL_FALSE;
629 }
630 ENDPROFILE(set_buffer)
631}
632
633
634
635/* Return characteristics of the output buffer. */
636static void buffer_size( GLcontext* ctx, GLuint *width, GLuint *height )
637{
638 int New_Size;
639 RECT CR;
640
641 STARTPROFILE
642 GetClientRect(Current->Window,&CR);
643
644 *width=CR.right;
645 *height=CR.bottom;
646
647 New_Size=((*width)!=Current->width) || ((*height)!=Current->height);
648
649 if (New_Size){
650 Current->width=*width;
651 Current->height=*height;
652 Current->ScanWidth=Current->width;
653 if ((Current->ScanWidth%sizeof(long))!=0)
654 Current->ScanWidth+=(sizeof(long)-(Current->ScanWidth%sizeof(long)));
655
656 if (Current->db_flag){
657#ifdef DDRAW
658 DDDeleteOffScreen(Current);
659 DDCreateOffScreen(Current);
660#else
661 if (Current->rgb_flag==GL_TRUE && Current->dither_flag!=GL_TRUE){
662 wmDeleteBackingStore(Current);
663 wmCreateBackingStore(Current, Current->width, Current->height);
664 }
665#endif
666 }
667
668 // Resize OsmesaBuffer if in Parallel mode
669#if !defined(NO_PARALLEL)
670 if(parallelFlag)
671 PRSizeRenderBuffer(Current->width, Current->height,Current->ScanWidth,
672 Current->rgb_flag == GL_TRUE ? Current->pbPixels: Current->ScreenMem);
673#endif
674 }
675 ENDPROFILE(buffer_size)
676}
677
678
679
680/**********************************************************************/
681/***** Accelerated point, line, polygon rendering *****/
682/**********************************************************************/
683
684
685static void fast_rgb_points( GLcontext* ctx, GLuint first, GLuint last )
686{
687 GLuint i;
688 // HDC DC=DD_GETDC;
689 PWMC pwc = Current;
690
691 STARTPROFILE
692
693 if (0 /*Current->gl_ctx->VB->MonoColor*/) {
694 /* all drawn with current color */
695 for (i=first;i<=last;i++) {
696 if (!Current->gl_ctx->VB->ClipMask[i]) {
697 int x, y;
698 x = (GLint) Current->gl_ctx->VB->Win.data[i][0];
699 y = FLIP( (GLint) Current->gl_ctx->VB->Win.data[i][1] );
700 wmSetPixel(pwc, y,x,GetRValue(Current->pixel),
701 GetGValue(Current->pixel), GetBValue(Current->pixel));
702 }
703 }
704 }
705 else {
706 /* draw points of different colors */
707 for (i=first;i<=last;i++) {
708 if (!Current->gl_ctx->VB->ClipMask[i]) {
709 int x, y;
710 unsigned long pixel=RGB((GLubyte)(Current->gl_ctx->VB->ColorPtr->data[i][0]*255.0),
711 (GLubyte)(Current->gl_ctx->VB->ColorPtr->data[i][1]*255.0),
712 (GLubyte)(Current->gl_ctx->VB->ColorPtr->data[i][2]*255.0));
713 x = (GLint) Current->gl_ctx->VB->Win.data[i][0];
714 y = FLIP( (GLint) Current->gl_ctx->VB->Win.data[i][1] );
715 wmSetPixel(pwc, y,x,Current->gl_ctx->VB->ColorPtr->data[i][0]*255.0,
716 Current->gl_ctx->VB->ColorPtr->data[i][1]*255.0,
717 Current->gl_ctx->VB->ColorPtr->data[i][2]*255.0);
718 }
719 }
720 }
721 // DD_RELEASEDC;
722 ENDPROFILE(fast_rgb_points)
723}
724
725
726
727/* Return pointer to accerated points function */
728extern points_func choose_points_function( GLcontext* ctx )
729{
730 STARTPROFILE
731 if (ctx->Point.Size==1.0 && !ctx->Point.SmoothFlag && ctx->RasterMask==0
732 && !ctx->Texture.Enabled && ctx->Visual->RGBAflag) {
733 ENDPROFILE(choose_points_function)
734 return fast_rgb_points;
735 }
736 else {
737 ENDPROFILE(choose_points_function)
738 return NULL;
739 }
740}
741
742
743
744/* Draw a line using the color specified by Current->gl_ctx->VB->ColorPtr->data[pv] */
745static void fast_flat_rgb_line( GLcontext* ctx, GLuint v0, GLuint v1, GLuint pv )
746{
747 STARTPROFILE
748 int x0, y0, x1, y1;
749 unsigned long pixel;
750 HDC DC=DD_GETDC;
751 HPEN Pen;
752 HPEN Old_Pen;
753
754 if (0 /*Current->gl_ctx->VB->MonoColor*/) {
755 pixel = Current->pixel; /* use current color */
756 }
757 else {
758 pixel = RGB((GLubyte)(Current->gl_ctx->VB->ColorPtr->data[pv][0]),
759 (GLubyte)(Current->gl_ctx->VB->ColorPtr->data[pv][1]),
760 (GLubyte)(Current->gl_ctx->VB->ColorPtr->data[pv][2]));
761 }
762
763 x0 = (int) Current->gl_ctx->VB->Win.data[v0][0];
764 y0 = FLIP( (int) Current->gl_ctx->VB->Win.data[v0][1] );
765 x1 = (int) Current->gl_ctx->VB->Win.data[v1][0];
766 y1 = FLIP( (int) Current->gl_ctx->VB->Win.data[v1][1] );
767
768
769 BEGINGDICALL
770
771 Pen=CreatePen(PS_SOLID,1,pixel);
772 Old_Pen=SelectObject(DC,Pen);
773 MoveToEx(DC,x0,y0,NULL);
774 LineTo(DC,x1,y1);
775 SelectObject(DC,Old_Pen);
776 DeleteObject(Pen);
777 DD_RELEASEDC;
778
779 ENDGDICALL
780
781 ENDPROFILE(fast_flat_rgb_line)
782}
783
784
785
786/* Return pointer to accerated line function */
787static line_func choose_line_function( GLcontext* ctx )
788{
789 STARTPROFILE
790 if (ctx->Line.Width==1.0 && !ctx->Line.SmoothFlag && !ctx->Line.StippleFlag
791 && ctx->Light.ShadeModel==GL_FLAT && ctx->RasterMask==0
792 && !ctx->Texture.Enabled && Current->rgb_flag) {
793 ENDPROFILE(choose_line_function)
794 return fast_flat_rgb_line;
795 }
796 else {
797 ENDPROFILE(choose_line_function)
798 return NULL;
799 }
800}
801
802
803/**********************************************************************/
804/***** Span-based pixel drawing *****/
805/**********************************************************************/
806
807
808/* Write a horizontal span of 32-bit color-index pixels with a boolean mask. */
809static void write_ci32_span( const GLcontext* ctx,
810 GLuint n, GLint x, GLint y,
811 const GLuint index[],
812 const GLubyte mask[] )
813{
814 STARTPROFILE
815 GLuint i;
816 PBYTE Mem=Current->ScreenMem+FLIP(y)*Current->ScanWidth+x;
817 assert(Current->rgb_flag==GL_FALSE);
818 for (i=0; i<n; i++)
819 if (mask[i])
820 Mem[i]=index[i];
821 ENDPROFILE(write_ci32_span)
822}
823
824
825/* Write a horizontal span of 8-bit color-index pixels with a boolean mask. */
826static void write_ci8_span( const GLcontext* ctx,
827 GLuint n, GLint x, GLint y,
828 const GLubyte index[],
829 const GLubyte mask[] )
830{
831 STARTPROFILE
832 GLuint i;
833 PBYTE Mem=Current->ScreenMem+FLIP(y)*Current->ScanWidth+x;
834 assert(Current->rgb_flag==GL_FALSE);
835 for (i=0; i<n; i++)
836 if (mask[i])
837 Mem[i]=index[i];
838 ENDPROFILE(write_ci8_span)
839}
840
841
842
843/*
844* Write a horizontal span of pixels with a boolean mask. The current
845* color index is used for all pixels.
846*/
847static void write_mono_ci_span(const GLcontext* ctx,
848 GLuint n,GLint x,GLint y,
849 const GLubyte mask[])
850{
851 STARTPROFILE
852 GLuint i;
853 BYTE *Mem=Current->ScreenMem+FLIP(y)*Current->ScanWidth+x;
854 assert(Current->rgb_flag==GL_FALSE);
855 for (i=0; i<n; i++)
856 if (mask[i])
857 Mem[i]=Current->pixel;
858 ENDPROFILE(write_mono_ci_span)
859}
860
861/*
862 * To improve the performance of this routine, frob the data into an actual
863 * scanline and call bitblt on the complete scan line instead of SetPixel.
864 */
865
866/* Write a horizontal span of RGBA color pixels with a boolean mask. */
867static void write_rgba_span( const GLcontext* ctx, GLuint n, GLint x, GLint y,
868 const GLubyte rgba[][4], const GLubyte mask[] )
869{
870 STARTPROFILE
871 PWMC pwc = Current;
872
873 if (pwc->rgb_flag==GL_TRUE)
874 {
875 GLuint i;
876 HDC DC=DD_GETDC;
877 y=FLIP(y);
878 if (mask) {
879 for (i=0; i<n; i++)
880 if (mask[i])
881 wmSetPixel(pwc, y, x + i, rgba[i][RCOMP], rgba[i][GCOMP], rgba[i][BCOMP]);
882 }
883 else {
884 for (i=0; i<n; i++)
885 wmSetPixel(pwc, y, x + i, rgba[i][RCOMP], rgba[i][GCOMP], rgba[i][BCOMP] );
886 }
887 DD_RELEASEDC;
888 }
889 else
890 {
891 GLuint i;
892 BYTE *Mem=Current->ScreenMem+y*Current->ScanWidth+x;
893 y = FLIP(y);
894 if (mask) {
895 for (i=0; i<n; i++)
896 if (mask[i])
897 Mem[i] = GetNearestPaletteIndex(Current->hPal,RGB(rgba[i][RCOMP], rgba[i][GCOMP], rgba[i][BCOMP]));
898 }
899 else {
900 for (i=0; i<n; i++)
901 Mem[i] = GetNearestPaletteIndex(Current->hPal,RGB(rgba[i][RCOMP], rgba[i][GCOMP], rgba[i][BCOMP]));
902 }
903 }
904 ENDPROFILE(write_rgba_span)
905
906}
907
908/* Write a horizontal span of RGB color pixels with a boolean mask. */
909static void write_rgb_span( const GLcontext* ctx,
910 GLuint n, GLint x, GLint y,
911 const GLubyte rgb[][3], const GLubyte mask[] )
912{
913 STARTPROFILE
914 PWMC pwc = Current;
915
916 if (pwc->rgb_flag==GL_TRUE)
917 {
918 GLuint i;
919 HDC DC=DD_GETDC;
920 y=FLIP(y);
921 if (mask) {
922 for (i=0; i<n; i++)
923 if (mask[i])
924 wmSetPixel(pwc, y, x + i, rgb[i][RCOMP], rgb[i][GCOMP], rgb[i][BCOMP]);
925 }
926 else {
927 for (i=0; i<n; i++)
928 wmSetPixel(pwc, y, x + i, rgb[i][RCOMP], rgb[i][GCOMP], rgb[i][BCOMP] );
929 }
930 DD_RELEASEDC;
931 }
932 else
933 {
934 GLuint i;
935 BYTE *Mem=Current->ScreenMem+y*Current->ScanWidth+x;
936 y = FLIP(y);
937 if (mask) {
938 for (i=0; i<n; i++)
939 if (mask[i])
940 Mem[i] = GetNearestPaletteIndex(Current->hPal,RGB(rgb[i][RCOMP], rgb[i][GCOMP], rgb[i][BCOMP]));
941 }
942 else {
943 for (i=0; i<n; i++)
944 Mem[i] = GetNearestPaletteIndex(Current->hPal,RGB(rgb[i][RCOMP], rgb[i][GCOMP], rgb[i][BCOMP]));
945 }
946 }
947 ENDPROFILE(write_rgb_span)
948
949}
950
951/*
952* Write a horizontal span of pixels with a boolean mask. The current color
953* is used for all pixels.
954*/
955static void write_mono_rgba_span( const GLcontext* ctx,
956 GLuint n, GLint x, GLint y,
957 const GLubyte mask[])
958{
959 STARTPROFILE
960 GLuint i;
961 HDC DC=DD_GETDC;
962 PWMC pwc = Current;
963 assert(Current->rgb_flag==GL_TRUE);
964 y=FLIP(y);
965 if(Current->rgb_flag==GL_TRUE){
966 for (i=0; i<n; i++)
967 if (mask[i])
968 // Trying
969 wmSetPixel(pwc,y,x+i,GetRValue(Current->pixel), GetGValue(Current->pixel), GetBValue(Current->pixel));
970 }
971 else {
972 for (i=0; i<n; i++)
973 if (mask[i])
974 SetPixel(DC, y, x+i, Current->pixel);
975 }
976 DD_RELEASEDC;
977 ENDPROFILE(write_mono_rgba_span)
978}
979
980
981
982/**********************************************************************/
983/***** Array-based pixel drawing *****/
984/**********************************************************************/
985
986
987/* Write an array of 32-bit index pixels with a boolean mask. */
988static void write_ci32_pixels( const GLcontext* ctx,
989 GLuint n, const GLint x[], const GLint y[],
990 const GLuint index[], const GLubyte mask[] )
991{
992 STARTPROFILE
993 GLuint i;
994 assert(Current->rgb_flag==GL_FALSE);
995 for (i=0; i<n; i++) {
996 if (mask[i]) {
997 BYTE *Mem=Current->ScreenMem+FLIP(y[i])*Current->ScanWidth+x[i];
998 *Mem = index[i];
999 }
1000 }
1001 ENDPROFILE(write_ci32_pixels)
1002}
1003
1004
1005
1006/*
1007* Write an array of pixels with a boolean mask. The current color
1008* index is used for all pixels.
1009*/
1010static void write_mono_ci_pixels( const GLcontext* ctx,
1011 GLuint n,
1012 const GLint x[], const GLint y[],
1013 const GLubyte mask[] )
1014{
1015 STARTPROFILE
1016 GLuint i;
1017 assert(Current->rgb_flag==GL_FALSE);
1018 for (i=0; i<n; i++) {
1019 if (mask[i]) {
1020 BYTE *Mem=Current->ScreenMem+FLIP(y[i])*Current->ScanWidth+x[i];
1021 *Mem = Current->pixel;
1022 }
1023 }
1024 ENDPROFILE(write_mono_ci_pixels)
1025}
1026
1027
1028
1029/* Write an array of RGBA pixels with a boolean mask. */
1030static void write_rgba_pixels( const GLcontext* ctx,
1031 GLuint n, const GLint x[], const GLint y[],
1032 const GLubyte rgba[][4], const GLubyte mask[] )
1033{
1034 STARTPROFILE
1035 GLuint i;
1036 PWMC pwc = Current;
1037 HDC DC=DD_GETDC;
1038 assert(Current->rgb_flag==GL_TRUE);
1039 for (i=0; i<n; i++)
1040 if (mask[i])
1041 wmSetPixel(pwc, FLIP(y[i]),x[i],rgba[i][RCOMP],rgba[i][GCOMP],rgba[i][BCOMP]);
1042 DD_RELEASEDC;
1043 ENDPROFILE(write_rgba_pixels)
1044}
1045
1046
1047
1048/*
1049* Write an array of pixels with a boolean mask. The current color
1050* is used for all pixels.
1051*/
1052static void write_mono_rgba_pixels( const GLcontext* ctx,
1053 GLuint n,
1054 const GLint x[], const GLint y[],
1055 const GLubyte mask[] )
1056{
1057 STARTPROFILE
1058 GLuint i;
1059 PWMC pwc = Current;
1060 HDC DC=DD_GETDC;
1061 assert(Current->rgb_flag==GL_TRUE);
1062 for (i=0; i<n; i++)
1063 if (mask[i])
1064 wmSetPixel(pwc, FLIP(y[i]),x[i],GetRValue(Current->pixel),
1065 GetGValue(Current->pixel), GetBValue(Current->pixel));
1066 DD_RELEASEDC;
1067 ENDPROFILE(write_mono_rgba_pixels)
1068}
1069
1070
1071
1072/**********************************************************************/
1073/***** Read spans/arrays of pixels *****/
1074/**********************************************************************/
1075
1076
1077/* Read a horizontal span of color-index pixels. */
1078static void read_ci32_span( const GLcontext* ctx, GLuint n, GLint x, GLint y,
1079 GLuint index[])
1080{
1081 STARTPROFILE
1082 GLuint i;
1083 BYTE *Mem=Current->ScreenMem+FLIP(y)*Current->ScanWidth+x;
1084 assert(Current->rgb_flag==GL_FALSE);
1085 for (i=0; i<n; i++)
1086 index[i]=Mem[i];
1087 ENDPROFILE(read_ci32_span)
1088}
1089
1090
1091
1092
1093/* Read an array of color index pixels. */
1094static void read_ci32_pixels( const GLcontext* ctx,
1095 GLuint n, const GLint x[], const GLint y[],
1096 GLuint indx[], const GLubyte mask[] )
1097{
1098 STARTPROFILE
1099 GLuint i;
1100 assert(Current->rgb_flag==GL_FALSE);
1101 for (i=0; i<n; i++) {
1102 if (mask[i]) {
1103 indx[i]=*(Current->ScreenMem+FLIP(y[i])*Current->ScanWidth+x[i]);
1104 }
1105 }
1106 ENDPROFILE(read_ci32_pixels)
1107}
1108
1109
1110
1111/* Read a horizontal span of color pixels. */
1112static void read_rgba_span( const GLcontext* ctx,
1113 GLuint n, GLint x, GLint y,
1114 GLubyte rgba[][4] )
1115{
1116 STARTPROFILE
1117 UINT i;
1118 COLORREF Color;
1119 HDC DC=DD_GETDC;
1120 assert(Current->rgb_flag==GL_TRUE);
1121 /* y=FLIP(y);*/
1122 y = Current->height - y - 1;
1123 for (i=0; i<n; i++) {
1124 Color=GetPixel(DC,x+i,y);
1125 rgba[i][RCOMP] = GetRValue(Color);
1126 rgba[i][GCOMP] = GetGValue(Color);
1127 rgba[i][BCOMP] = GetBValue(Color);
1128 rgba[i][ACOMP] = 255;
1129 }
1130 DD_RELEASEDC;
1131// Brian P. Has mentioned to comment this out.
1132// memset(alpha,0,n*sizeof(GLubyte));
1133 ENDPROFILE(read_rgba_span)
1134}
1135
1136
1137/* Read an array of color pixels. */
1138static void read_rgba_pixels( const GLcontext* ctx,
1139 GLuint n, const GLint x[], const GLint y[],
1140 GLubyte rgba[][4], const GLubyte mask[] )
1141{
1142 STARTPROFILE
1143 GLuint i;
1144 COLORREF Color;
1145 HDC DC=DD_GETDC;
1146 assert(Current->rgb_flag==GL_TRUE);
1147 for (i=0; i<n; i++) {
1148 if (mask[i]) {
1149 Color=GetPixel(DC,x[i],FLIP(y[i]));
1150 rgba[i][RCOMP] = GetRValue(Color);
1151 rgba[i][GCOMP] = GetGValue(Color);
1152 rgba[i][BCOMP] = GetBValue(Color);
1153 rgba[i][ACOMP] = 255;
1154 }
1155 }
1156 DD_RELEASEDC;
1157// Brian P. has mentioned to comment this out.
1158// memset(alpha,0,n*sizeof(GLint));
1159 ENDPROFILE(read_rgba_pixels)
1160}
1161
1162
1163
1164/**********************************************************************/
1165/**********************************************************************/
1166
1167
1168static const char *renderer_string(void)
1169{
1170 return "Windows";
1171}
1172
1173
1174
1175void setup_DD_pointers( GLcontext* ctx )
1176{
1177 ctx->Driver.RendererString = renderer_string;
1178 ctx->Driver.UpdateState = setup_DD_pointers;
1179 ctx->Driver.GetBufferSize = buffer_size;
1180 ctx->Driver.Finish = finish;
1181 ctx->Driver.Flush = flush;
1182
1183 ctx->Driver.ClearIndex = clear_index;
1184 ctx->Driver.ClearColor = clear_color;
1185 ctx->Driver.Clear = clear;
1186
1187 ctx->Driver.Index = set_index;
1188 ctx->Driver.Color = set_color;
1189 ctx->Driver.IndexMask = index_mask;
1190 ctx->Driver.ColorMask = color_mask;
1191
1192 ctx->Driver.LogicOp = logicop;
1193 ctx->Driver.Dither = dither;
1194
1195 ctx->Driver.SetBuffer = set_buffer;
1196 ctx->Driver.GetBufferSize = buffer_size;
1197
1198 ctx->Driver.PointsFunc = choose_points_function(ctx);
1199 ctx->Driver.LineFunc = choose_line_function(ctx);
1200 ctx->Driver.TriangleFunc = choose_triangle_function( ctx );
1201
1202 /* Pixel/span writing functions: */
1203 ctx->Driver.WriteRGBASpan = write_rgba_span;
1204 ctx->Driver.WriteRGBSpan = write_rgb_span;
1205 ctx->Driver.WriteMonoRGBASpan = write_mono_rgba_span;
1206 ctx->Driver.WriteRGBAPixels = write_rgba_pixels;
1207 ctx->Driver.WriteMonoRGBAPixels = write_mono_rgba_pixels;
1208 ctx->Driver.WriteCI32Span = write_ci32_span;
1209 ctx->Driver.WriteCI8Span = write_ci8_span;
1210 ctx->Driver.WriteMonoCISpan = write_mono_ci_span;
1211 ctx->Driver.WriteCI32Pixels = write_ci32_pixels;
1212 ctx->Driver.WriteMonoCIPixels = write_mono_ci_pixels;
1213
1214 ctx->Driver.ReadCI32Span = read_ci32_span;
1215 ctx->Driver.ReadRGBASpan = read_rgba_span;
1216 ctx->Driver.ReadCI32Pixels = read_ci32_pixels;
1217 ctx->Driver.ReadRGBAPixels = read_rgba_pixels;
1218}
1219
1220
1221/**********************************************************************/
1222/***** WMesa API Functions *****/
1223/**********************************************************************/
1224
1225
1226
1227#define PAL_SIZE 256
1228static void GetPalette(HPALETTE Pal,RGBQUAD *aRGB)
1229{
1230 STARTPROFILE
1231 int i;
1232 HDC hdc;
1233 struct
1234 {
1235 WORD Version;
1236 WORD NumberOfEntries;
1237 PALETTEENTRY aEntries[PAL_SIZE];
1238 } Palette =
1239 {
1240 0x300,
1241 PAL_SIZE
1242 };
1243 hdc=GetDC(NULL);
1244 if (Pal!=NULL)
1245 GetPaletteEntries(Pal,0,PAL_SIZE,Palette.aEntries);
1246 else
1247 GetSystemPaletteEntries(hdc,0,PAL_SIZE,Palette.aEntries);
1248 if (GetSystemPaletteUse(hdc) == SYSPAL_NOSTATIC)
1249 {
1250 for(i = 0; i <PAL_SIZE; i++)
1251 Palette.aEntries[i].peFlags = PC_RESERVED;
1252 Palette.aEntries[255].peRed = 255;
1253 Palette.aEntries[255].peGreen = 255;
1254 Palette.aEntries[255].peBlue = 255;
1255 Palette.aEntries[255].peFlags = 0;
1256 Palette.aEntries[0].peRed = 0;
1257 Palette.aEntries[0].peGreen = 0;
1258 Palette.aEntries[0].peBlue = 0;
1259 Palette.aEntries[0].peFlags = 0;
1260 }
1261 else
1262 {
1263 int nStaticColors;
1264 int nUsableColors;
1265 nStaticColors = GetDeviceCaps(hdc, NUMCOLORS)/2;
1266 for (i=0; i<nStaticColors; i++)
1267 Palette.aEntries[i].peFlags = 0;
1268 nUsableColors = PAL_SIZE-nStaticColors;
1269 for (; i<nUsableColors; i++)
1270 Palette.aEntries[i].peFlags = PC_RESERVED;
1271 for (; i<PAL_SIZE-nStaticColors; i++)
1272 Palette.aEntries[i].peFlags = PC_RESERVED;
1273 for (i=PAL_SIZE-nStaticColors; i<PAL_SIZE; i++)
1274 Palette.aEntries[i].peFlags = 0;
1275 }
1276 ReleaseDC(NULL,hdc);
1277 for (i=0; i<PAL_SIZE; i++)
1278 {
1279 aRGB[i].rgbRed=Palette.aEntries[i].peRed;
1280 aRGB[i].rgbGreen=Palette.aEntries[i].peGreen;
1281 aRGB[i].rgbBlue=Palette.aEntries[i].peBlue;
1282 aRGB[i].rgbReserved=Palette.aEntries[i].peFlags;
1283 }
1284 ENDPROFILE(GetPalette)
1285}
1286
1287
1288WMesaContext WMesaCreateContext( HWND hWnd, HPALETTE* Pal,
1289 GLboolean rgb_flag,
1290 GLboolean db_flag )
1291{
1292 RECT CR;
1293 WMesaContext c;
1294 GLboolean true_color_flag;
1295 c = (struct wmesa_context * ) calloc(1,sizeof(struct wmesa_context));
1296 if (!c)
1297 return NULL;
1298
1299 c->Window=hWnd;
1300 c->hDC = GetDC(hWnd);
1301 true_color_flag = GetDeviceCaps(c->hDC, BITSPIXEL) > 8;
1302#ifdef DDRAW
1303 if(true_color_flag) c->rgb_flag = rgb_flag = GL_TRUE;
1304#endif
1305
1306
1307#ifdef DITHER
1308 if ((true_color_flag==GL_FALSE) && (rgb_flag == GL_TRUE)){
1309 c->dither_flag = GL_TRUE;
1310 c->hPalHalfTone = WinGCreateHalftonePalette();
1311 }
1312 else
1313 c->dither_flag = GL_FALSE;
1314#else
1315 c->dither_flag = GL_FALSE;
1316#endif
1317
1318
1319 if (rgb_flag==GL_FALSE)
1320 {
1321 c->rgb_flag = GL_FALSE;
1322 // c->pixel = 1;
1323 c->db_flag = db_flag =GL_TRUE; // WinG requires double buffering
1324 printf("Single buffer is not supported in color index mode, setting to double buffer.\n");
1325 }
1326 else
1327 {
1328 c->rgb_flag = GL_TRUE;
1329 // c->pixel = 0;
1330 }
1331 GetClientRect(c->Window,&CR);
1332 c->width=CR.right;
1333 c->height=CR.bottom;
1334 if (db_flag)
1335 {
1336 c->db_flag = 1;
1337 /* Double buffered */
1338#ifndef DDRAW
1339 // if (c->rgb_flag==GL_TRUE && c->dither_flag != GL_TRUE )
1340 {
1341 wmCreateBackingStore(c, c->width, c->height);
1342
1343 }
1344#endif
1345 }
1346 else
1347 {
1348 /* Single Buffered */
1349 if (c->rgb_flag)
1350 c->db_flag = 0;
1351 }
1352#ifdef DDRAW
1353 if (DDInit(c,hWnd) == GL_FALSE) {
1354 free( (void *) c );
1355 exit(1);
1356 }
1357#endif
1358
1359
1360 c->gl_visual = gl_create_visual(rgb_flag,
1361 GL_FALSE, /* software alpha */
1362 db_flag, /* db_flag */
1363 GL_FALSE, /* stereo */
1364 16, /* depth_bits */
1365 8, /* stencil_bits */
1366 8, /* accum_bits */
1367 0, /* index bits */
1368 8,8,8,8 ); /* r, g, b, a bits */
1369
1370 if (!c->gl_visual) {
1371 return NULL;
1372 }
1373
1374 /* allocate a new Mesa context */
1375 c->gl_ctx = gl_create_context( c->gl_visual, NULL, c, GL_TRUE);
1376
1377 if (!c->gl_ctx) {
1378 gl_destroy_visual( c->gl_visual );
1379 free(c);
1380 return NULL;
1381 }
1382
1383 c->gl_buffer = gl_create_framebuffer( c->gl_visual );
1384 if (!c->gl_buffer) {
1385 gl_destroy_visual( c->gl_visual );
1386 gl_destroy_context( c->gl_ctx );
1387 free(c);
1388 return NULL;
1389 }
1390
1391 c->gl_ctx->Driver.UpdateState = setup_DD_pointers;
1392
1393 // setup_DD_pointers(c->gl_ctx);
1394
1395 return c;
1396}
1397
1398void WMesaDestroyContext( void )
1399{
1400 WMesaContext c = Current;
1401 ReleaseDC(c->Window,c->hDC);
1402 WC = c;
1403 if(c->hPalHalfTone != NULL)
1404 DeleteObject(c->hPalHalfTone);
1405 gl_destroy_visual( c->gl_visual );
1406 gl_destroy_framebuffer( c->gl_buffer );
1407 gl_destroy_context( c->gl_ctx );
1408
1409 if (c->db_flag)
1410#ifdef DDRAW
1411 DDFree(c);
1412#else
1413 wmDeleteBackingStore(c);
1414#endif
1415 free( (void *) c );
1416 //Following code is added to enable parallel render
1417 // Parallel render only work in double buffer mode
1418#if !defined(NO_PARALLEL)
1419 if(parallelMachine)
1420 PRDestroyRenderBuffer();
1421#endif
1422 // End modification
1423}
1424
1425
1426
1427void WIN32API WMesaMakeCurrent( WMesaContext c )
1428{
1429 if(!c){
1430 Current = c;
1431 return;
1432 }
1433
1434 //
1435 // A little optimization
1436 // If it already is current,
1437 // don't set it again
1438 //
1439 if(Current == c)
1440 return;
1441
1442 //gl_set_context( c->gl_ctx );
1443 gl_make_current(c->gl_ctx, c->gl_buffer);
1444 setup_DD_pointers(c->gl_ctx);
1445 Current = c;
1446 if (Current->gl_ctx->Viewport.Width==0) {
1447 /* initialize viewport to window size */
1448 gl_Viewport( Current->gl_ctx,
1449 0, 0, Current->width, Current->height );
1450 }
1451 if ((c->cColorBits <= 8 ) && (c->rgb_flag == GL_TRUE)){
1452 WMesaPaletteChange(c->hPalHalfTone);
1453 }
1454}
1455
1456
1457
1458void WIN32API WMesaSwapBuffers( void )
1459{
1460 HDC DC = Current->hDC;
1461 if (Current->db_flag)
1462 wmFlush(Current);
1463}
1464
1465
1466
1467void WIN32API WMesaPaletteChange(HPALETTE Pal)
1468{
1469 int vRet;
1470 LPPALETTEENTRY pPal;
1471 if (Current && (Current->rgb_flag==GL_FALSE || Current->dither_flag == GL_TRUE))
1472 {
1473 pPal = (PALETTEENTRY *)malloc( 256 * sizeof(PALETTEENTRY));
1474 Current->hPal=Pal;
1475 // GetPaletteEntries( Pal, 0, 256, pPal );
1476 GetPalette( Pal, (RGBQUAD *)pPal );
1477#ifdef DDRAW
1478 Current->lpDD->lpVtbl->CreatePalette(Current->lpDD,DDPCAPS_8BIT,
1479 pPal, &(Current->lpDDPal), NULL);
1480 if (Current->lpDDPal)
1481 Current->lpDDSPrimary->lpVtbl->SetPalette(Current->lpDDSPrimary,Current->lpDDPal);
1482#else
1483 vRet = SetDIBColorTable(Current->dib.hDC,0,256,(RGBQUAD *)pPal);
1484#endif
1485 free( pPal );
1486 }
1487
1488}
1489
1490
1491
1492
1493static unsigned char threeto8[8] = {
1494 0, 0111>>1, 0222>>1, 0333>>1, 0444>>1, 0555>>1, 0666>>1, 0377
1495};
1496
1497static unsigned char twoto8[4] = {
1498 0, 0x55, 0xaa, 0xff
1499};
1500
1501static unsigned char oneto8[2] = {
1502 0, 255
1503};
1504
1505static unsigned char componentFromIndex(UCHAR i, UINT nbits, UINT shift)
1506{
1507 unsigned char val;
1508
1509 val = i >> shift;
1510 switch (nbits) {
1511
1512 case 1:
1513 val &= 0x1;
1514 return oneto8[val];
1515
1516 case 2:
1517 val &= 0x3;
1518 return twoto8[val];
1519
1520 case 3:
1521 val &= 0x7;
1522 return threeto8[val];
1523
1524 default:
1525 return 0;
1526 }
1527}
1528
1529void /*WINAPI*/ wmCreatePalette( PWMC pwdc )
1530{
1531 /* Create a compressed and re-expanded 3:3:2 palette */
1532 int i;
1533 LOGPALETTE *pPal;
1534 BYTE rb, rs, gb, gs, bb, bs;
1535
1536 pwdc->nColors = 0x100;
1537
1538 pPal = (PLOGPALETTE)malloc(sizeof(LOGPALETTE) + pwdc->nColors * sizeof(PALETTEENTRY));
1539 memset( pPal, 0, sizeof(LOGPALETTE) + pwdc->nColors * sizeof(PALETTEENTRY) );
1540
1541 pPal->palVersion = 0x300;
1542
1543 rb = REDBITS;
1544 rs = REDSHIFT;
1545 gb = GREENBITS;
1546 gs = GREENSHIFT;
1547 bb = BLUEBITS;
1548 bs = BLUESHIFT;
1549
1550 if (pwdc->db_flag) {
1551
1552 /* Need to make two palettes: one for the screen DC and one for the DIB. */
1553 pPal->palNumEntries = pwdc->nColors;
1554 for (i = 0; i < pwdc->nColors; i++) {
1555 pPal->palPalEntry[i].peRed = componentFromIndex( i, rb, rs );
1556 pPal->palPalEntry[i].peGreen = componentFromIndex( i, gb, gs );
1557 pPal->palPalEntry[i].peBlue = componentFromIndex( i, bb, bs );
1558 pPal->palPalEntry[i].peFlags = 0;
1559 }
1560 pwdc->hGLPalette = CreatePalette( pPal );
1561 pwdc->hPalette = CreatePalette( pPal );
1562 }
1563
1564 else {
1565 pPal->palNumEntries = pwdc->nColors;
1566 for (i = 0; i < pwdc->nColors; i++) {
1567 pPal->palPalEntry[i].peRed = componentFromIndex( i, rb, rs );
1568 pPal->palPalEntry[i].peGreen = componentFromIndex( i, gb, gs );
1569 pPal->palPalEntry[i].peBlue = componentFromIndex( i, bb, bs );
1570 pPal->palPalEntry[i].peFlags = 0;
1571 }
1572 pwdc->hGLPalette = CreatePalette( pPal );
1573 }
1574
1575 free(pPal);
1576
1577}
1578
1579void /*WINAPI*/ wmSetPixel(PWMC pwc, int iScanLine, int iPixel, BYTE r, BYTE g, BYTE b)
1580{
1581 if (Current->db_flag) {
1582 LPBYTE lpb = pwc->pbPixels;
1583 LPDWORD lpdw;
1584 LPWORD lpw;
1585 UINT nBypp = pwc->cColorBits >> 3;
1586 UINT nOffset = iPixel % nBypp;
1587
1588 // Move the pixel buffer pointer to the scanline that we
1589 // want to access
1590
1591 // pwc->dib.fFlushed = FALSE;
1592
1593 lpb += pwc->ScanWidth * iScanLine;
1594 // Now move to the desired pixel
1595 lpb += iPixel * nBypp;
1596 lpb = PIXELADDR(iPixel, iScanLine);
1597 lpdw = (LPDWORD)lpb;
1598 lpw = (LPWORD)lpb;
1599
1600 if(nBypp == 1){
1601 if(pwc->dither_flag)
1602 *lpb = DITHER_RGB_2_8BIT(r,g,b,iScanLine,iPixel);
1603 else
1604 *lpb = BGR8(r,g,b);
1605 }
1606 else if(nBypp == 2)
1607 *lpw = BGR16(r,g,b);
1608 else if (nBypp == 3){
1609 *lpdw = BGR24(r,g,b);
1610 }
1611 else if (nBypp == 4)
1612 *lpdw = BGR32(r,g,b);
1613 }
1614 else{
1615 SetPixel(Current->hDC, iPixel, iScanLine, RGB(r,g,b));
1616 DD_RELEASEDC;
1617 }
1618}
1619
1620void /*WINAPI*/ wmCreateDIBSection(
1621 HDC hDC,
1622 PWMC pwc, // handle of device context
1623 CONST BITMAPINFO *pbmi, // address of structure containing bitmap size, format, and color data
1624 UINT iUsage // color data type indicator: RGB values or palette indices
1625 )
1626{
1627 DWORD dwSize = 0;
1628 DWORD dwScanWidth;
1629 UINT nBypp = pwc->cColorBits / 8;
1630 HDC hic;
1631
1632 dprintf(("OPENGL32: wmCreateDIBSection - HDC is %08X",hDC));
1633
1634 dwScanWidth = (((pwc->ScanWidth * nBypp)+ 3) & ~3);
1635
1636 pwc->ScanWidth =pwc->pitch = dwScanWidth;
1637
1638 if (stereo_flag)
1639 pwc->ScanWidth = 2* pwc->pitch;
1640
1641 dwSize = sizeof(BITMAPINFO) + (dwScanWidth * pwc->height);
1642
1643 pwc->dib.hFileMap = CreateFileMapping((HANDLE)PAGE_FILE,
1644 NULL,
1645 PAGE_READWRITE | SEC_COMMIT,
1646 0,
1647 dwSize,
1648 NULL);
1649
1650 if (!pwc->dib.hFileMap)
1651 return;
1652
1653 pwc->dib.base = MapViewOfFile(pwc->dib.hFileMap,
1654 FILE_MAP_ALL_ACCESS,
1655 0,
1656 0,
1657 0);
1658
1659 if(!pwc->dib.base){
1660 CloseHandle(pwc->dib.hFileMap);
1661 return;
1662 }
1663
1664 // pwc->pbPixels = pwc->addrOffScreen = ((LPBYTE)pwc->dib.base) + sizeof(BITMAPINFO);
1665
1666 // pwc->dib.hDC = CreateCompatibleDC(hDC);
1667
1668 memcpy(pwc->dib.base, pbmi, sizeof(BITMAPINFO));
1669
1670 hic = CreateIC("display", NULL, NULL, NULL);
1671 pwc->dib.hDC = CreateCompatibleDC(hic);
1672
1673
1674 /* pwc->hbmDIB = CreateDIBitmap(hic,
1675 &(pwc->bmi.bmiHeader),
1676 CBM_INIT,
1677 pwc->pbPixels,
1678 &(pwc->bmi),
1679 DIB_RGB_COLORS);
1680 */
1681 pwc->hbmDIB = CreateDIBSection(hic,
1682 &(pwc->bmi),
1683 (iUsage ? DIB_PAL_COLORS : DIB_RGB_COLORS),
1684 (LPVOID*)&(pwc->pbPixels),
1685 pwc->dib.hFileMap,
1686 0);
1687 /*
1688 pwc->hbmDIB = CreateDIBSection(hic,
1689 &(pwc->bmi),
1690 DIB_RGB_COLORS,
1691 &(pwc->pbPixels),
1692 pwc->dib.hFileMap,
1693 0);
1694 */
1695 dprintf(("CreateDIBSection set pix %08X\n",pwc->pbPixels));
1696
1697 pwc->ScreenMem = pwc->addrOffScreen = pwc->pbPixels;
1698 pwc->hOldBitmap = SelectObject(pwc->dib.hDC, pwc->hbmDIB);
1699
1700 DeleteDC(hic);
1701
1702 return;
1703
1704}
1705
1706//
1707// Blit memory DC to screen DC
1708//
1709BOOL /*WINAPI*/ wmFlush(PWMC pwc)
1710{
1711 BOOL bRet = 0;
1712 DWORD dwErr = 0;
1713#ifdef DDRAW
1714 HRESULT ddrval;
1715#endif
1716
1717 // Now search through the torus frames and mark used colors
1718 if(pwc->db_flag){
1719#ifdef DDRAW
1720 if (pwc->lpDDSOffScreen == NULL)
1721 if(DDCreateOffScreen(pwc) == GL_FALSE)
1722 return 0;
1723
1724 pwc->lpDDSOffScreen->lpVtbl->Unlock(pwc->lpDDSOffScreen, NULL);
1725
1726 while( 1 )
1727 {
1728 ddrval = pwc->lpDDSPrimary->lpVtbl->Blt( pwc->lpDDSPrimary,
1729 &(pwc->rectSurface), pwc->lpDDSOffScreen, &(pwc->rectOffScreen), 0, NULL );
1730
1731 if( ddrval == DD_OK )
1732 {
1733 break;
1734 }
1735 if( ddrval == DDERR_SURFACELOST )
1736 {
1737 if(!DDRestoreAll(pwc))
1738 {
1739 break;
1740 }
1741 }
1742 if( ddrval != DDERR_WASSTILLDRAWING )
1743 {
1744 break;
1745 }
1746 }
1747
1748 while (pwc->lpDDSOffScreen->lpVtbl->Lock(pwc->lpDDSOffScreen,
1749 NULL, &(pwc->ddsd), 0, NULL) == DDERR_WASSTILLDRAWING)
1750 ;
1751
1752 if(ddrval != DD_OK)
1753 dwErr = GetLastError();
1754#else
1755 bRet = BitBlt(pwc->hDC, 0, 0, pwc->width, pwc->height,
1756 pwc->dib.hDC, 0, 0, SRCCOPY);
1757#endif
1758 }
1759
1760 return(TRUE);
1761
1762}
1763
1764
1765// The following code is added by Li Wei to enable stereo display
1766
1767#if !defined(NO_STEREO)
1768
1769void WMesaShowStereo(GLuint list)
1770{
1771
1772 GLbitfield mask = GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT;
1773 GLfloat cm[16];
1774 GLint matrix_mode;
1775 // Must use double Buffer
1776 if( ! Current-> db_flag )
1777 return;
1778
1779
1780 glGetIntegerv(GL_MATRIX_MODE,&matrix_mode);
1781
1782 // glPushMatrix(); //****
1783 WMesaViewport(Current->gl_ctx,0,Current->height/2,Current->width,Current->height/2);
1784 // Current->gl_ctx->NewState = 0;
1785
1786 // glViewport(0,0,Current->width,Current->height/2);
1787 if(matrix_mode!=GL_MODELVIEW)
1788 glMatrixMode(GL_MODELVIEW);
1789
1790 glGetFloatv(GL_MODELVIEW_MATRIX,cm);
1791 glLoadIdentity();
1792 gluLookAt(viewDistance/2,0.0,0.0 ,
1793 viewDistance/2,0.0,-1.0,
1794 0.0,1.0,0.0 );
1795 // glTranslatef(viewDistance/2.0,0.,0.);
1796 glMultMatrixf( cm );
1797
1798 Current->ScreenMem = Current->pbPixels = Current->addrOffScreen;
1799 //glPushMatrix();
1800 glCallList( list );
1801 //glPopMatrix();
1802
1803 glGetFloatv(GL_MODELVIEW_MATRIX,cm);
1804 glLoadIdentity();
1805 gluLookAt(-viewDistance/2,0.0,0.0 ,
1806 -viewDistance/2,0.0,-1.0,
1807 0.0,1.0,0.0 );
1808 // glTranslatef(-viewDistance/2.0,0.,0.);
1809 glMultMatrixf(cm);
1810
1811 Current->ScreenMem = Current->pbPixels = Current->addrOffScreen + Current->pitch;
1812 glCallList(list);
1813 if(matrix_mode!=GL_MODELVIEW)
1814 glMatrixMode(matrix_mode);
1815
1816 // glPopMatrix();
1817 glFlush();
1818
1819 WMesaViewport(Current->gl_ctx,0,0,Current->width,Current->height);
1820 // Current->gl_ctx->NewState = 0;
1821 WMesaSwapBuffers();
1822
1823}
1824
1825void toggleStereoMode()
1826{
1827 if(!Current->db_flag)
1828 return;
1829 if(!stereo_flag){
1830 stereo_flag = 1;
1831 if(stereoBuffer==GL_FALSE)
1832#if !defined(NO_PARALLEL)
1833 if(!parallelFlag)
1834#endif
1835 {
1836 Current->ScanWidth = Current->pitch*2;
1837 }
1838 }
1839 else {
1840 stereo_flag = 0;
1841#if !defined(NO_PARALLEL)
1842 if(!parallelFlag)
1843#endif
1844 Current->ScanWidth = Current->pitch;
1845 Current->pbPixels = Current->addrOffScreen;
1846 }
1847}
1848
1849/* if in stereo mode, the following function is called */
1850void glShowStereo(GLuint list)
1851{
1852 WMesaShowStereo(list);
1853}
1854
1855#endif // End if NO_STEREO not defined
1856
1857#if !defined(NO_PARALLEL)
1858
1859void toggleParallelMode(void)
1860{
1861 if(!parallelFlag){
1862 parallelFlag = GL_TRUE;
1863 if(parallelMachine==GL_FALSE){
1864 PRCreateRenderBuffer( Current->rgb_flag? GL_RGBA :GL_COLOR_INDEX,
1865 Current->cColorBits/8,
1866 Current->width ,Current->height,
1867 Current->ScanWidth,
1868 Current->rgb_flag? Current->pbPixels: Current->ScreenMem);
1869 parallelMachine = GL_TRUE;
1870 }
1871 }
1872 else {
1873 parallelFlag = GL_FALSE;
1874 if(parallelMachine==GL_TRUE){
1875 PRDestroyRenderBuffer();
1876 parallelMachine=GL_FALSE;
1877 ReadyForNextFrame = GL_TRUE;
1878 }
1879
1880 /***********************************************
1881 // Seems something wrong!!!!
1882 ************************************************/
1883
1884 WMesaMakeCurrent(Current);
1885#if !defined(NO_STEREO)
1886 stereo_flag = GL_FALSE ;
1887#endif
1888 }
1889}
1890
1891void PRShowRenderResult(void)
1892{
1893 int flag = 0;
1894 if(!glImageRendered())
1895 return;
1896
1897 if (parallelFlag)
1898 {
1899 WMesaSwapBuffers();
1900 }
1901
1902}
1903#endif //End if NO_PARALLEL not defined
1904
1905//end modification
1906
1907BYTE DITHER_RGB_2_8BIT( int red, int green, int blue, int pixel, int scanline)
1908{
1909 char unsigned redtemp, greentemp, bluetemp, paletteindex;
1910
1911 //*** now, look up each value in the halftone matrix
1912 //*** using an 8x8 ordered dither.
1913 redtemp = aDividedBy51[red]
1914 + (aModulo51[red] > aHalftone8x8[(pixel%8)*8
1915 + scanline%8]);
1916 greentemp = aDividedBy51[(char unsigned)green]
1917 + (aModulo51[green] > aHalftone8x8[
1918 (pixel%8)*8 + scanline%8]);
1919 bluetemp = aDividedBy51[(char unsigned)blue]
1920 + (aModulo51[blue] > aHalftone8x8[
1921 (pixel%8)*8 +scanline%8]);
1922
1923 //*** recombine the halftoned rgb values into a palette index
1924 paletteindex =
1925 redtemp + aTimes6[greentemp] + aTimes36[bluetemp];
1926
1927 //*** and translate through the wing halftone palette
1928 //*** translation vector to give the correct value.
1929 return aWinGHalftoneTranslation[paletteindex];
1930}
1931
1932#ifdef DDRAW
1933/*
1934* restoreAll
1935*
1936* restore all lost objects
1937*/
1938HRESULT DDRestoreAll( WMesaContext wc )
1939{
1940 HRESULT ddrval;
1941
1942 ddrval = wc->lpDDSPrimary->lpVtbl->Restore(wc->lpDDSPrimary);
1943 if( ddrval == DD_OK )
1944 {
1945 ddrval = wc->lpDDSOffScreen->lpVtbl->Restore(wc->lpDDSOffScreen);
1946 }
1947 return ddrval;
1948
1949} /* restoreAll */
1950
1951
1952 /*
1953 * This function is called if the initialization function fails
1954*/
1955BOOL initFail( HWND hwnd, WMesaContext wc )
1956{
1957 DDFree(wc);
1958 MessageBox( hwnd, "DirectDraw Init FAILED", "", MB_OK );
1959 return FALSE;
1960
1961} /* initFail */
1962
1963
1964static void DDDeleteOffScreen(WMesaContext wc)
1965{
1966 if( wc->lpDDSOffScreen != NULL )
1967 {
1968 wc->lpDDSOffScreen->lpVtbl->Unlock(wc->lpDDSOffScreen,NULL);
1969 wc->lpDDSOffScreen->lpVtbl->Release(wc->lpDDSOffScreen);
1970 wc->lpDDSOffScreen = NULL;
1971 }
1972
1973}
1974
1975static void DDFreePrimarySurface(WMesaContext wc)
1976{
1977 if( wc->lpDDSPrimary != NULL )
1978 {
1979 if(wc->db_flag == GL_FALSE)
1980 wc->lpDDSPrimary->lpVtbl->ReleaseDC(wc->lpDDSPrimary, wc->hDC);
1981 wc->lpDDSPrimary->lpVtbl->Release(wc->lpDDSPrimary);
1982 wc->lpDDSPrimary = NULL;
1983 }
1984}
1985
1986static BOOL DDCreatePrimarySurface(WMesaContext wc)
1987{
1988 HRESULT ddrval;
1989 DDSCAPS ddscaps;
1990 wc->ddsd.dwSize = sizeof( wc->ddsd );
1991 wc->ddsd.dwFlags = DDSD_CAPS;
1992 wc->ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE;
1993
1994 ddrval = wc->lpDD->lpVtbl->CreateSurface( wc->lpDD,&(wc->ddsd), &(wc->lpDDSPrimary), NULL );
1995 if( ddrval != DD_OK )
1996 {
1997 return initFail(wc->hwnd , wc);
1998 }
1999 if(wc->db_flag == GL_FALSE)
2000 wc->lpDDSPrimary->lpVtbl->GetDC(wc->lpDDSPrimary, wc->hDC);
2001 return TRUE;
2002}
2003
2004static BOOL DDCreateOffScreen(WMesaContext wc)
2005{
2006 POINT pt;
2007 HRESULT ddrval;
2008 if(wc->lpDD == NULL)
2009 return FALSE;
2010 GetClientRect( wc->hwnd, &(wc->rectOffScreen) );
2011 wc->ddsd.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;
2012 wc->ddsd.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN;
2013 wc->ddsd.dwHeight = wc->rectOffScreen.bottom - wc->rectOffScreen.top;
2014 wc->ddsd.dwWidth = wc->rectOffScreen.right - wc->rectOffScreen.left;
2015
2016 ddrval = wc->lpDD->lpVtbl->CreateSurface( wc->lpDD, &(wc->ddsd), &(wc->lpDDSOffScreen), NULL );
2017 if( ddrval != DD_OK )
2018 {
2019 return FALSE;
2020 }
2021
2022 while (wc->lpDDSOffScreen->lpVtbl->Lock(wc->lpDDSOffScreen,NULL, &(wc->ddsd), 0, NULL) == DDERR_WASSTILLDRAWING)
2023 ;
2024 // while ((ddrval = wc->lpDDSOffScreen->lpVtbl->Lock(wc->lpDDSOffScreen,NULL, &(wc->ddsd), DDLOCK_SURFACEMEMORYPTR , NULL)) != DD_OK)
2025 ;
2026 if(wc->ddsd.lpSurface==NULL)
2027 return initFail(wc->hwnd, wc);
2028
2029 wc->ScreenMem = wc->pbPixels = wc->addrOffScreen = (PBYTE)(wc->ddsd.lpSurface);
2030 wc->ScanWidth = wc->pitch = wc->ddsd.lPitch;
2031 if (stereo_flag)
2032 wc->ScanWidth = wc->ddsd.lPitch*2;
2033
2034 GetClientRect( wc->hwnd, &(wc->rectSurface) );
2035 pt.x = pt.y = 0;
2036 ClientToScreen( wc->hwnd, &pt );
2037 OffsetRect(&(wc->rectSurface), pt.x, pt.y);
2038 wmSetPixelFormat(wc, wc->hDC);
2039 return TRUE;
2040}
2041
2042/*
2043* doInit - do work required for every instance of the application:
2044* create the window, initialize data
2045*/
2046static BOOL DDInit( WMesaContext wc, HWND hwnd)
2047{
2048 HRESULT ddrval;
2049 DWORD dwFrequency;
2050
2051 LPDIRECTDRAW lpDD; // DirectDraw object
2052 LPDIRECTDRAW2 lpDD2;
2053
2054
2055 wc->fullScreen = displayOptions.fullScreen;
2056 wc->gMode = displayOptions.mode;
2057 wc->hwnd = hwnd;
2058 stereo_flag = displayOptions.stereo;
2059 if(wc->db_flag!= GL_TRUE)
2060 stereo_flag = GL_FALSE;
2061 /*
2062 * create the main DirectDraw object
2063 */
2064 ddrval = DirectDrawCreate( NULL, &(wc->lpDD), NULL );
2065 if( ddrval != DD_OK )
2066 {
2067 return initFail(hwnd,wc);
2068 }
2069
2070 // Get exclusive mode if requested
2071 if(wc->fullScreen)
2072 {
2073 ddrval = wc->lpDD->lpVtbl->SetCooperativeLevel( wc->lpDD, hwnd, DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN );
2074 }
2075 else
2076 {
2077 ddrval = wc->lpDD->lpVtbl->SetCooperativeLevel( wc->lpDD, hwnd, DDSCL_NORMAL );
2078 }
2079 if( ddrval != DD_OK )
2080 {
2081 return initFail(hwnd , wc);
2082 }
2083
2084
2085 /* ddrval = wc->lpDD->lpVtbl->QueryInterface(wc->lpDD, IID_IDirectDraw2,
2086 (LPVOID *)((wc->lpDD2)));
2087
2088 */
2089 if(ddrval != DD_OK)
2090 return initFail(hwnd , wc);
2091
2092
2093 //ddrval = wc->lpDD->lpVtbl->GetDisplayMode( wc->lpDD, &(wc->ddsd));
2094 // wc->lpDD2->lpVtbl->GetMonitorFrequency(wc->lpDD, &dwFrequency);
2095 switch( wc->gMode )
2096 {
2097 case 1: ddrval = wc->lpDD->lpVtbl->SetDisplayMode( wc->lpDD, 640, 480, displayOptions.bpp); break;
2098 case 2: ddrval = wc->lpDD->lpVtbl->SetDisplayMode( wc->lpDD, 800, 600, displayOptions.bpp); break;
2099 case 3: ddrval = wc->lpDD->lpVtbl->SetDisplayMode( wc->lpDD, 1024, 768, displayOptions.bpp); break;
2100 case 4: ddrval = wc->lpDD->lpVtbl->SetDisplayMode( wc->lpDD, 1152, 864, displayOptions.bpp); break;
2101 case 5: ddrval = wc->lpDD->lpVtbl->SetDisplayMode( wc->lpDD, 1280, 1024, displayOptions.bpp); break;
2102 }
2103
2104 if( ddrval != DD_OK )
2105 {
2106 printf("Can't modify display mode, current mode used\n");
2107 // return initFail(hwnd , wc);
2108 }
2109 //ddrval = wc->lpDD->lpVtbl->GetDisplayMode( wc->lpDD, &(wc->ddsd));
2110 switch(ddrval){
2111 case DDERR_INVALIDOBJECT:
2112 break;
2113 case DDERR_INVALIDPARAMS:
2114 break;
2115 case DDERR_UNSUPPORTEDMODE:
2116 ;
2117 }
2118
2119 if(DDCreatePrimarySurface(wc) == GL_FALSE)
2120 return initFail(hwnd, wc);
2121
2122 if(wc->db_flag)
2123 return DDCreateOffScreen(wc);
2124
2125 return 0; /* Eliminate compiler warning */
2126} /* DDInit */
2127
2128static void DDFree( WMesaContext wc)
2129{
2130 if( wc->lpDD != NULL )
2131 {
2132 DDFreePrimarySurface(wc);
2133 DDDeleteOffScreen(wc);
2134 wc->lpDD->lpVtbl->Release(wc->lpDD);
2135 wc->lpDD = NULL;
2136 }
2137 // Clean up the screen on exit
2138 RedrawWindow( NULL, NULL, NULL, RDW_INVALIDATE | RDW_ERASE |
2139 RDW_ALLCHILDREN );
2140
2141}
2142#endif
2143
2144void WMesaMove(void)
2145{
2146 WMesaContext wc = Current;
2147 POINT pt;
2148 if (Current != NULL){
2149 GetClientRect( wc->hwnd, &(wc->rectSurface) );
2150 pt.x = pt.y = 0;
2151 ClientToScreen( wc->hwnd, &pt );
2152 OffsetRect(&(wc->rectSurface), pt.x, pt.y);
2153 }
2154}
2155
2156
2157
2158/*
2159* Like PACK_8A8B8G8R() but don't use alpha. This is usually an acceptable
2160* shortcut.
2161*/
2162#define PACK_8B8G8R( R, G, B ) ( ((B) << 16) | ((G) << 8) | (R) )
2163
2164
2165/**********************************************************************/
2166/*** Triangle rendering ***/
2167/**********************************************************************/
2168
2169/*
2170 * XImage, smooth, depth-buffered, PF_8A8B8G8R triangle.
2171 */
2172static void smooth_8A8B8G8R_z_triangle( GLcontext *ctx,
2173 GLuint v0, GLuint v1, GLuint v2,
2174 GLuint pv )
2175{
2176 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2177#define INTERP_Z 1
2178#define INTERP_RGB 1
2179#define PIXEL_ADDRESS(X,Y) PIXELADDR4(X,Y)
2180#define PIXEL_TYPE GLuint
2181 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2182#define BYTES_PER_ROW (wmesa->ScanWidth)
2183#define INNER_LOOP( LEFT, RIGHT, Y ) \
2184 { \
2185 GLint i, len = RIGHT-LEFT; \
2186 for (i=0;i<len;i++) { \
2187 GLdepth z = FixedToDepth(ffz); \
2188 if (z < zRow[i]) { \
2189 pRow[i] = PACK_8B8G8R( FixedToInt(ffr), FixedToInt(ffg), \
2190 FixedToInt(ffb) ); \
2191 zRow[i] = z; \
2192 } \
2193 ffr += fdrdx; ffg += fdgdx; ffb += fdbdx; \
2194 ffz += fdzdx; \
2195 } \
2196 }
2197
2198#ifdef __MINGW32__
2199 #include "tritemp.h"
2200#else
2201
2202 #ifdef WIN32
2203 #include "..\tritemp.h"
2204 #else
2205 #include "tritemp.h"
2206 #endif
2207#endif
2208}
2209
2210
2211/*
2212* XImage, smooth, depth-buffered, PF_8R8G8B triangle.
2213*/
2214static void smooth_8R8G8B_z_triangle( GLcontext *ctx,
2215 GLuint v0, GLuint v1, GLuint v2,
2216 GLuint pv )
2217{
2218 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2219#define INTERP_Z 1
2220#define INTERP_RGB 1
2221#define PIXEL_ADDRESS(X,Y) PIXELADDR4(X,Y)
2222#define PIXEL_TYPE GLuint
2223 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2224#define BYTES_PER_ROW (wmesa->ScanWidth)
2225#define INNER_LOOP( LEFT, RIGHT, Y ) \
2226 { \
2227 GLint i, len = RIGHT-LEFT; \
2228 for (i=0;i<len;i++) { \
2229 GLdepth z = FixedToDepth(ffz); \
2230 if (z < zRow[i]) { \
2231 pRow[i] = PACK_8R8G8B( FixedToInt(ffr), FixedToInt(ffg), \
2232 FixedToInt(ffb) ); \
2233 zRow[i] = z; \
2234 } \
2235 ffr += fdrdx; ffg += fdgdx; ffb += fdbdx; \
2236 ffz += fdzdx; \
2237 } \
2238 }
2239#ifdef __MINGW32__
2240 #include "tritemp.h"
2241#else
2242
2243 #ifdef WIN32
2244 #include "..\tritemp.h"
2245 #else
2246 #include "tritemp.h"
2247 #endif
2248#endif
2249}
2250
2251
2252
2253/*
2254* XImage, smooth, depth-buffered, PF_5R6G5B triangle.
2255*/
2256static void smooth_5R6G5B_z_triangle( GLcontext *ctx,
2257 GLuint v0, GLuint v1, GLuint v2,
2258 GLuint pv )
2259{
2260 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2261#define INTERP_Z 1
2262#define INTERP_RGB 1
2263#define PIXEL_ADDRESS(X,Y) PIXELADDR2(X,Y)
2264#define PIXEL_TYPE GLushort
2265 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2266#define BYTES_PER_ROW (wmesa->ScanWidth)
2267#define INNER_LOOP( LEFT, RIGHT, Y ) \
2268 { \
2269 GLint i, len = RIGHT-LEFT; \
2270 for (i=0;i<len;i++) { \
2271 GLdepth z = FixedToDepth(ffz); \
2272 if (z < zRow[i]) { \
2273 pRow[i] = PACK_5R6G5B( FixedToInt(ffr), FixedToInt(ffg), \
2274 FixedToInt(ffb) ); \
2275 zRow[i] = z; \
2276 } \
2277 ffr += fdrdx; ffg += fdgdx; ffb += fdbdx; \
2278 ffz += fdzdx; \
2279 } \
2280 }
2281#ifdef __MINGW32__
2282 #include "tritemp.h"
2283#else
2284
2285 #ifdef WIN32
2286 #include "..\tritemp.h"
2287 #else
2288 #include "tritemp.h"
2289 #endif
2290#endif
2291}
2292
2293/*
2294* XImage, flat, depth-buffered, PF_8A8B8G8R triangle.
2295*/
2296static void flat_8A8B8G8R_z_triangle( GLcontext *ctx, GLuint v0,
2297 GLuint v1, GLuint v2, GLuint pv )
2298{
2299 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2300#define INTERP_Z 1
2301#define PIXEL_ADDRESS(X,Y) PIXELADDR4(X,Y)
2302#define PIXEL_TYPE GLuint
2303 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2304#define BYTES_PER_ROW (wmesa->ScanWidth)
2305#define SETUP_CODE \
2306 unsigned long p = PACK_8B8G8R( VB->ColorPtr->data[pv][0], \
2307 VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2] );
2308#define INNER_LOOP( LEFT, RIGHT, Y ) \
2309 { \
2310 GLint i, len = RIGHT-LEFT; \
2311 for (i=0;i<len;i++) { \
2312 GLdepth z = FixedToDepth(ffz); \
2313 if (z < zRow[i]) { \
2314 pRow[i] = p; \
2315 zRow[i] = z; \
2316 } \
2317 ffz += fdzdx; \
2318 } \
2319 }
2320#ifdef __MINGW32__
2321 #include "tritemp.h"
2322#else
2323
2324 #ifdef WIN32
2325 #include "..\tritemp.h"
2326 #else
2327 #include "tritemp.h"
2328 #endif
2329#endif
2330}
2331
2332
2333/*
2334* XImage, flat, depth-buffered, PF_8R8G8B triangle.
2335*/
2336static void flat_8R8G8B_z_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2337 GLuint v2, GLuint pv )
2338{
2339 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2340#define INTERP_Z 1
2341#define PIXEL_ADDRESS(X,Y) PIXELADDR4(X,Y)
2342#define PIXEL_TYPE GLuint
2343 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2344#define BYTES_PER_ROW (wmesa->ScanWidth)
2345#define SETUP_CODE \
2346 unsigned long p = PACK_8R8G8B( VB->ColorPtr->data[pv][0], \
2347 VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2] );
2348#define INNER_LOOP( LEFT, RIGHT, Y ) \
2349 { \
2350 GLint i, len = RIGHT-LEFT; \
2351 for (i=0;i<len;i++) { \
2352 GLdepth z = FixedToDepth(ffz); \
2353 if (z < zRow[i]) { \
2354 pRow[i] = p; \
2355 zRow[i] = z; \
2356 } \
2357 ffz += fdzdx; \
2358 } \
2359 }
2360#ifdef __MINGW32__
2361 #include "tritemp.h"
2362#else
2363
2364 #ifdef WIN32
2365 #include "..\tritemp.h"
2366 #else
2367 #include "tritemp.h"
2368 #endif
2369#endif
2370}
2371
2372
2373/*
2374* XImage, flat, depth-buffered, PF_5R6G5B triangle.
2375*/
2376static void flat_5R6G5B_z_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2377 GLuint v2, GLuint pv )
2378{
2379 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2380#define INTERP_Z 1
2381#define PIXEL_ADDRESS(X,Y) PIXELADDR2(X,Y)
2382#define PIXEL_TYPE GLushort
2383 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2384#define BYTES_PER_ROW (wmesa->ScanWidth)
2385#define SETUP_CODE \
2386 unsigned long p = PACK_5R6G5B( VB->ColorPtr->data[pv][0], \
2387 VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2] );
2388#define INNER_LOOP( LEFT, RIGHT, Y ) \
2389 { \
2390 GLint i, len = RIGHT-LEFT; \
2391 for (i=0;i<len;i++) { \
2392 GLdepth z = FixedToDepth(ffz); \
2393 if (z < zRow[i]) { \
2394 pRow[i] = p; \
2395 zRow[i] = z; \
2396 } \
2397 ffz += fdzdx; \
2398 } \
2399 }
2400#ifdef __MINGW32__
2401 #include "tritemp.h"
2402#else
2403
2404 #ifdef WIN32
2405 #include "..\tritemp.h"
2406 #else
2407 #include "tritemp.h"
2408 #endif
2409#endif
2410}
2411
2412
2413/*
2414* XImage, smooth, NON-depth-buffered, PF_8A8B8G8R triangle.
2415*/
2416static void smooth_8A8B8G8R_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2417 GLuint v2, GLuint pv )
2418{
2419 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2420#define INTERP_RGB 1
2421#define PIXEL_ADDRESS(X,Y) PIXELADDR4(X,Y)
2422#define PIXEL_TYPE GLuint
2423 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2424#define BYTES_PER_ROW (wmesa->ScanWidth)
2425#define INNER_LOOP( LEFT, RIGHT, Y ) \
2426 { \
2427 GLint xx; \
2428 PIXEL_TYPE *pixel = pRow; \
2429 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2430 *pixel = PACK_8B8G8R( FixedToInt(ffr), FixedToInt(ffg), \
2431 FixedToInt(ffb) ); \
2432 ffr += fdrdx; ffg += fdgdx; ffb += fdbdx; \
2433 } \
2434 }
2435#ifdef __MINGW32__
2436 #include "tritemp.h"
2437#else
2438
2439 #ifdef WIN32
2440 #include "..\tritemp.h"
2441 #else
2442 #include "tritemp.h"
2443 #endif
2444#endif
2445}
2446
2447
2448/*
2449* XImage, smooth, NON-depth-buffered, PF_8R8G8B triangle.
2450*/
2451static void smooth_8R8G8B_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2452 GLuint v2, GLuint pv )
2453{
2454 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2455#define INTERP_RGB 1
2456#define PIXEL_ADDRESS(X,Y) PIXELADDR4(X,Y)
2457#define PIXEL_TYPE GLuint
2458 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2459#define BYTES_PER_ROW (wmesa->ScanWidth)
2460#define INNER_LOOP( LEFT, RIGHT, Y ) \
2461 { \
2462 GLint xx; \
2463 PIXEL_TYPE *pixel = pRow; \
2464 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2465 *pixel = PACK_8R8G8B( FixedToInt(ffr), FixedToInt(ffg), \
2466 FixedToInt(ffb) ); \
2467 ffr += fdrdx; ffg += fdgdx; ffb += fdbdx; \
2468 } \
2469 }
2470#ifdef __MINGW32__
2471 #include "tritemp.h"
2472#else
2473
2474 #ifdef WIN32
2475 #include "..\tritemp.h"
2476 #else
2477 #include "tritemp.h"
2478 #endif
2479#endif
2480}
2481
2482
2483/*
2484* XImage, smooth, NON-depth-buffered, PF_5R6G5B triangle.
2485*/
2486static void smooth_5R6G5B_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2487 GLuint v2, GLuint pv )
2488{
2489 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2490#define INTERP_RGB 1
2491#define PIXEL_ADDRESS(X,Y) PIXELADDR2(X,Y)
2492#define PIXEL_TYPE GLushort
2493 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2494#define BYTES_PER_ROW (wmesa->ScanWidth)
2495#define INNER_LOOP( LEFT, RIGHT, Y ) \
2496 { \
2497 GLint xx; \
2498 PIXEL_TYPE *pixel = pRow; \
2499 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2500 *pixel = PACK_5R6G5B( FixedToInt(ffr), FixedToInt(ffg), \
2501 FixedToInt(ffb) ); \
2502 ffr += fdrdx; ffg += fdgdx; ffb += fdbdx; \
2503 } \
2504 }
2505#ifdef __MINGW32__
2506 #include "tritemp.h"
2507#else
2508
2509 #ifdef WIN32
2510 #include "..\tritemp.h"
2511 #else
2512 #include "tritemp.h"
2513 #endif
2514#endif
2515}
2516
2517
2518
2519/*
2520* XImage, flat, NON-depth-buffered, PF_8A8B8G8R triangle.
2521*/
2522static void flat_8A8B8G8R_triangle( GLcontext *ctx, GLuint v0,
2523 GLuint v1, GLuint v2, GLuint pv )
2524{
2525 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2526#define PIXEL_ADDRESS(X,Y) PIXELADDR4(X,Y)
2527#define PIXEL_TYPE GLuint
2528 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2529#define BYTES_PER_ROW (wmesa->ScanWidth)
2530#define SETUP_CODE \
2531 unsigned long p = PACK_8B8G8R( VB->ColorPtr->data[pv][0], \
2532 VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2] );
2533#define INNER_LOOP( LEFT, RIGHT, Y ) \
2534 { \
2535 GLint xx; \
2536 PIXEL_TYPE *pixel = pRow; \
2537 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2538 *pixel = p; \
2539 } \
2540 }
2541
2542#ifdef __MINGW32__
2543 #include "tritemp.h"
2544#else
2545
2546 #ifdef WIN32
2547 #include "..\tritemp.h"
2548 #else
2549 #include "tritemp.h"
2550 #endif
2551#endif
2552}
2553
2554
2555/*
2556* XImage, flat, NON-depth-buffered, PF_8R8G8B triangle.
2557*/
2558static void flat_8R8G8B_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2559 GLuint v2, GLuint pv )
2560{
2561 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2562#define PIXEL_ADDRESS(X,Y) PIXELADDR4(X,Y)
2563#define PIXEL_TYPE GLuint
2564 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2565#define BYTES_PER_ROW (wmesa->ScanWidth)
2566#define SETUP_CODE \
2567 unsigned long p = PACK_8R8G8B( VB->ColorPtr->data[pv][0], \
2568 VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2] );
2569#define INNER_LOOP( LEFT, RIGHT, Y ) \
2570 { \
2571 GLint xx; \
2572 PIXEL_TYPE *pixel = pRow; \
2573 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2574 *pixel = p; \
2575 } \
2576 }
2577#ifdef __MINGW32__
2578 #include "tritemp.h"
2579#else
2580
2581 #ifdef WIN32
2582 #include "..\tritemp.h"
2583 #else
2584 #include "tritemp.h"
2585 #endif
2586#endif
2587}
2588
2589
2590/*
2591* XImage, flat, NON-depth-buffered, PF_5R6G5B triangle.
2592*/
2593static void flat_5R6G5B_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2594 GLuint v2, GLuint pv )
2595{
2596 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2597#define PIXEL_ADDRESS(X,Y) PIXELADDR2(X,Y)
2598#define PIXEL_TYPE GLushort
2599 //#define BYTES_PER_ROW (wmesa->xm_buffer->backimage->bytes_per_line)
2600#define BYTES_PER_ROW (wmesa->ScanWidth)
2601#define SETUP_CODE \
2602 unsigned long p = PACK_5R6G5B( VB->ColorPtr->data[pv][0], \
2603 VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2] );
2604#define INNER_LOOP( LEFT, RIGHT, Y ) \
2605 { \
2606 GLint xx; \
2607 PIXEL_TYPE *pixel = pRow; \
2608 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2609 *pixel = p; \
2610 } \
2611 }
2612#ifdef __MINGW32__
2613 #include "tritemp.h"
2614#else
2615
2616 #ifdef WIN32
2617 #include "..\tritemp.h"
2618 #else
2619 #include "tritemp.h"
2620 #endif
2621#endif
2622}
2623
2624
2625/*
2626* XImage, smooth, depth-buffered, 8-bit PF_LOOKUP triangle.
2627*/
2628
2629static void smooth_ci_z_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2630 GLuint v2, GLuint pv )
2631{
2632 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2633#define INTERP_Z 1
2634#define INTERP_INDEX 1
2635#define PIXEL_ADDRESS(X,Y) PIXELADDR1(X,Y)
2636#define PIXEL_TYPE GLubyte
2637#define BYTES_PER_ROW (wmesa->ScanWidth)
2638#define INNER_LOOP( LEFT, RIGHT, Y ) \
2639 { \
2640 GLint i, len = RIGHT-LEFT; \
2641 for (i=0;i<len;i++) { \
2642 GLdepth z = FixedToDepth(ffz); \
2643 if (z < zRow[i]) { \
2644 pRow[i] = FixedToInt(ffi); \
2645 zRow[i] = z; \
2646 } \
2647 ffi += fdidx; \
2648 ffz += fdzdx; \
2649 } \
2650 }
2651#ifdef __MINGW32__
2652 #include "tritemp.h"
2653#else
2654
2655 #ifdef WIN32
2656 #include "..\tritemp.h"
2657 #else
2658 #include "tritemp.h"
2659 #endif
2660#endif
2661}
2662
2663
2664/*
2665* XImage, flat, depth-buffered, 8-bit PF_LOOKUP triangle.
2666*/
2667
2668static void flat_ci_z_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2669 GLuint v2, GLuint pv )
2670{
2671 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2672#define INTERP_Z 1
2673#define PIXEL_ADDRESS(X,Y) PIXELADDR1(X,Y)
2674#define PIXEL_TYPE GLubyte
2675#define BYTES_PER_ROW (wmesa->ScanWidth)
2676#define SETUP_CODE \
2677 GLuint index = VB->IndexPtr->data[pv]; \
2678 (*ctx->Driver.Index)( ctx, index );
2679#define INNER_LOOP( LEFT, RIGHT, Y ) \
2680 { \
2681 GLint i, len = RIGHT-LEFT; \
2682 for (i=0;i<len;i++) { \
2683 GLdepth z = FixedToDepth(ffz); \
2684 if (z < zRow[i]) { \
2685 pRow[i] = index; \
2686 zRow[i] = z; \
2687 } \
2688 ffz += fdzdx; \
2689 } \
2690 }
2691#ifdef __MINGW32__
2692 #include "tritemp.h"
2693#else
2694
2695 #ifdef WIN32
2696 #include "..\tritemp.h"
2697 #else
2698 #include "tritemp.h"
2699 #endif
2700#endif
2701}
2702
2703
2704
2705/*
2706* XImage, smooth, NON-depth-buffered, 8-bit PF_LOOKUP triangle.
2707*/
2708
2709static void smooth_ci_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2710 GLuint v2, GLuint pv )
2711{
2712 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2713#define INTERP_Z 1
2714#define INTERP_INDEX 1
2715#define PIXEL_ADDRESS(X,Y) PIXELADDR1(X,Y)
2716#define PIXEL_TYPE GLubyte
2717#define BYTES_PER_ROW (wmesa->ScanWidth)
2718#define INNER_LOOP( LEFT, RIGHT, Y ) \
2719 { \
2720 GLint xx; \
2721 PIXEL_TYPE *pixel = pRow; \
2722 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2723 *pixel = FixedToInt(ffi); \
2724 ffi += fdidx; \
2725 } \
2726 }
2727#ifdef __MINGW32__
2728 #include "tritemp.h"
2729#else
2730
2731 #ifdef WIN32
2732 #include "..\tritemp.h"
2733 #else
2734 #include "tritemp.h"
2735 #endif
2736#endif
2737}
2738
2739
2740/*
2741* XImage, flat, NON-depth-buffered, 8-bit PF_LOOKUP triangle.
2742*/
2743static void flat_ci_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2744 GLuint v2, GLuint pv )
2745{
2746 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2747#define INTERP_Z 1
2748#define PIXEL_ADDRESS(X,Y) PIXELADDR1(X,Y)
2749#define PIXEL_TYPE GLubyte
2750#define BYTES_PER_ROW (wmesa->ScanWidth)
2751#define SETUP_CODE \
2752 GLuint index = VB->IndexPtr->data[pv]; \
2753 (*ctx->Driver.Index)( ctx, index );
2754#define INNER_LOOP( LEFT, RIGHT, Y ) \
2755 { \
2756 GLint xx; \
2757 PIXEL_TYPE *pixel = pRow; \
2758 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2759 *pixel = index; \
2760 } \
2761 }
2762#ifdef __MINGW32__
2763 #include "tritemp.h"
2764#else
2765
2766 #ifdef WIN32
2767 #include "..\tritemp.h"
2768 #else
2769 #include "tritemp.h"
2770 #endif
2771#endif
2772}
2773
2774/*
2775* XImage, smooth, depth-buffered, 8-bit, PF_DITHER8 triangle.
2776*/
2777static void smooth_DITHER8_z_triangle( GLcontext *ctx,
2778 GLuint v0, GLuint v1, GLuint v2,
2779 GLuint pv )
2780{
2781 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2782 DITHER_RGB_TO_8BIT_SETUP
2783#define INTERP_Z 1
2784#define INTERP_RGB 1
2785#define PIXEL_ADDRESS(X,Y) PIXELADDR1(X,Y)
2786#define PIXEL_TYPE GLubyte
2787#define BYTES_PER_ROW (wmesa->ScanWidth)
2788#define INNER_LOOP( LEFT, RIGHT, Y ) \
2789 { \
2790 GLint i, xx = LEFT, yy = FLIP(Y), len = RIGHT-LEFT; \
2791 for (i=0;i<len;i++,xx++) { \
2792 GLdepth z = FixedToDepth(ffz); \
2793 if (z < zRow[i]) { \
2794 DITHER_RGB_TO_8BIT( FixedToInt(ffr), FixedToInt(ffg), \
2795 FixedToInt(ffb), xx, yy); \
2796 pRow[i] = pixelDithered; \
2797 zRow[i] = z; \
2798 } \
2799 ffr += fdrdx; ffg += fdgdx; ffb += fdbdx; \
2800 ffz += fdzdx; \
2801 } \
2802 }
2803#ifdef __MINGW32__
2804 #include "tritemp.h"
2805#else
2806
2807 #ifdef WIN32
2808 #include "..\tritemp.h"
2809 #else
2810 #include "tritemp.h"
2811 #endif
2812#endif
2813}
2814
2815/*
2816* XImage, flat, depth-buffered, 8-bit PF_DITHER triangle.
2817*/
2818static void flat_DITHER8_z_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2819 GLuint v2, GLuint pv )
2820{
2821 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2822 DITHER_RGB_TO_8BIT_SETUP
2823#define INTERP_Z 1
2824#define PIXEL_ADDRESS(X,Y) PIXELADDR1(X,Y)
2825#define PIXEL_TYPE GLubyte
2826#define BYTES_PER_ROW (wmesa->ScanWidth)
2827
2828#define INNER_LOOP( LEFT, RIGHT, Y ) \
2829 { \
2830 GLint i, xx = LEFT, yy = FLIP(Y), len = RIGHT-LEFT; \
2831 for (i=0;i<len;i++,xx++) { \
2832 GLdepth z = FixedToDepth(ffz); \
2833 if (z < zRow[i]) { \
2834 DITHER_RGB_TO_8BIT( VB->ColorPtr->data[pv][0], \
2835 VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2], xx, yy); \
2836 pRow[i] = pixelDithered; \
2837 zRow[i] = z; \
2838 } \
2839 ffz += fdzdx; \
2840 } \
2841 }
2842#ifdef __MINGW32__
2843 #include "tritemp.h"
2844#else
2845
2846 #ifdef WIN32
2847 #include "..\tritemp.h"
2848 #else
2849 #include "tritemp.h"
2850 #endif
2851#endif
2852}
2853
2854/*
2855* XImage, smooth, NON-depth-buffered, 8-bit PF_DITHER triangle.
2856*/
2857static void smooth_DITHER8_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2858 GLuint v2, GLuint pv )
2859{
2860 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2861 DITHER_RGB_TO_8BIT_SETUP
2862#define INTERP_RGB 1
2863#define PIXEL_ADDRESS(X,Y) PIXELADDR1(X,Y)
2864#define PIXEL_TYPE GLubyte
2865#define BYTES_PER_ROW (wmesa->ScanWidth)
2866#define INNER_LOOP( LEFT, RIGHT, Y ) \
2867 { \
2868 GLint xx, yy = FLIP(Y); \
2869 PIXEL_TYPE *pixel = pRow; \
2870 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2871 DITHER_RGB_TO_8BIT( VB->ColorPtr->data[pv][0], VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2], xx, yy);\
2872 *pixel = pixelDithered; \
2873 ffr += fdrdx; ffg += fdgdx; ffb += fdbdx; \
2874 } \
2875 }
2876#ifdef __MINGW32__
2877 #include "tritemp.h"
2878#else
2879
2880 #ifdef WIN32
2881 #include "..\tritemp.h"
2882 #else
2883 #include "tritemp.h"
2884 #endif
2885#endif
2886}
2887
2888/*
2889* XImage, flat, NON-depth-buffered, 8-bit PF_DITHER triangle.
2890*/
2891
2892static void flat_DITHER8_triangle( GLcontext *ctx, GLuint v0, GLuint v1,
2893 GLuint v2, GLuint pv )
2894{
2895 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2896 DITHER_RGB_TO_8BIT_SETUP
2897#define PIXEL_ADDRESS(X,Y) PIXELADDR1(X,Y)
2898#define PIXEL_TYPE GLubyte
2899#define BYTES_PER_ROW (wmesa->ScanWidth)
2900
2901#define INNER_LOOP( LEFT, RIGHT, Y ) \
2902 { \
2903 GLint xx, yy = FLIP(Y); \
2904 PIXEL_TYPE *pixel = pRow; \
2905 for (xx=LEFT;xx<RIGHT;xx++,pixel++) { \
2906 DITHER_RGB_TO_8BIT( VB->ColorPtr->data[pv][0], \
2907 VB->ColorPtr->data[pv][1], VB->ColorPtr->data[pv][2], xx, yy); \
2908 *pixel = pixelDithered; \
2909 } \
2910 }
2911#ifdef __MINGW32__
2912 #include "tritemp.h"
2913#else
2914
2915 #ifdef WIN32
2916 #include "..\tritemp.h"
2917 #else
2918 #include "tritemp.h"
2919 #endif
2920#endif
2921}
2922
2923
2924
2925
2926static triangle_func choose_triangle_function( GLcontext *ctx )
2927{
2928 WMesaContext wmesa = (WMesaContext) ctx->DriverCtx;
2929 int depth = wmesa->cColorBits;
2930
2931 if (ctx->Polygon.SmoothFlag) return NULL;
2932 if (ctx->Texture.Enabled) return NULL;
2933 if (!wmesa->db_flag) return NULL;
2934 /*if (wmesa->xm_buffer->buffer==XIMAGE)*/ {
2935 if ( ctx->Light.ShadeModel==GL_SMOOTH
2936 && ctx->RasterMask==DEPTH_BIT
2937 && ctx->Depth.Func==GL_LESS
2938 && ctx->Depth.Mask==GL_TRUE
2939 && ctx->Polygon.StippleFlag==GL_FALSE) {
2940 switch (wmesa->pixelformat) {
2941 case PF_8A8B8G8R:
2942 return smooth_8A8B8G8R_z_triangle;
2943 case PF_8R8G8B:
2944 return smooth_8R8G8B_z_triangle;
2945 case PF_5R6G5B:
2946 return smooth_5R6G5B_z_triangle;
2947 case PF_DITHER8:
2948 return smooth_DITHER8_z_triangle;
2949 case PF_INDEX8:
2950 return smooth_ci_z_triangle;
2951 default:
2952 return NULL;
2953 }
2954 }
2955 if ( ctx->Light.ShadeModel==GL_FLAT
2956 && ctx->RasterMask==DEPTH_BIT
2957 && ctx->Depth.Func==GL_LESS
2958 && ctx->Depth.Mask==GL_TRUE
2959 && ctx->Polygon.StippleFlag==GL_FALSE) {
2960 switch (wmesa->pixelformat) {
2961 case PF_8A8B8G8R:
2962 return flat_8A8B8G8R_z_triangle;
2963 case PF_8R8G8B:
2964 return flat_8R8G8B_z_triangle;
2965 case PF_5R6G5B:
2966 return flat_5R6G5B_z_triangle;
2967 case PF_DITHER8:
2968 return flat_DITHER8_z_triangle;
2969 case PF_INDEX8:
2970 return flat_ci_z_triangle;
2971 default:
2972 return NULL;
2973 }
2974 }
2975 if ( ctx->RasterMask==0 /* no depth test */
2976 && ctx->Light.ShadeModel==GL_SMOOTH
2977 && ctx->Polygon.StippleFlag==GL_FALSE) {
2978 switch (wmesa->pixelformat) {
2979 case PF_8A8B8G8R:
2980 return smooth_8A8B8G8R_triangle;
2981 case PF_8R8G8B:
2982 return smooth_8R8G8B_triangle;
2983 case PF_5R6G5B:
2984 return smooth_5R6G5B_triangle;
2985 case PF_DITHER8:
2986 return smooth_DITHER8_triangle;
2987 case PF_INDEX8:
2988 return smooth_ci_triangle;
2989 default:
2990 return NULL;
2991 }
2992 }
2993
2994 if ( ctx->RasterMask==0 /* no depth test */
2995 && ctx->Light.ShadeModel==GL_FLAT
2996 && ctx->Polygon.StippleFlag==GL_FALSE) {
2997 switch (wmesa->pixelformat) {
2998 case PF_8A8B8G8R:
2999 return flat_8A8B8G8R_triangle;
3000 case PF_8R8G8B:
3001 return flat_8R8G8B_triangle;
3002 case PF_5R6G5B:
3003 return flat_5R6G5B_triangle;
3004 case PF_DITHER8:
3005 return flat_DITHER8_triangle;
3006 case PF_INDEX8:
3007 return flat_ci_triangle;
3008 default:
3009 return NULL;
3010 }
3011 }
3012
3013 return NULL;
3014 }
3015}
3016
3017/*
3018* Define a new viewport and reallocate auxillary buffers if the size of
3019* the window (color buffer) has changed.
3020*/
3021void WMesaViewport( GLcontext *ctx,
3022 GLint x, GLint y, GLsizei width, GLsizei height )
3023{
3024 /* Save viewport */
3025 ctx->Viewport.X = x;
3026 ctx->Viewport.Width = width;
3027 ctx->Viewport.Y = y;
3028 ctx->Viewport.Height = height;
3029
3030 /* compute scale and bias values */
3031/* Pre-Keith 3.1 changes
3032 ctx->Viewport.Map.m[Sx] = (GLfloat) width / 2.0F;
3033 ctx->Viewport.Map.m[Tx] = ctx->Viewport.Sx + x;
3034 ctx->Viewport.Map.m[Sy] = (GLfloat) height / 2.0F;
3035 ctx->Viewport.Map.m[Ty] = ctx->Viewport.Sy + y;
3036*/
3037 ctx->Viewport.WindowMap.m[MAT_SX] = (GLfloat) width / 2.0F;
3038 ctx->Viewport.WindowMap.m[MAT_TX] = ctx->Viewport.WindowMap.m[MAT_SX] + x;
3039 ctx->Viewport.WindowMap.m[MAT_SY] = (GLfloat) height / 2.0F;
3040 ctx->Viewport.WindowMap.m[MAT_TY] = ctx->Viewport.WindowMap.m[MAT_SY] + y;
3041}
Note: See TracBrowser for help on using the repository browser.