1 /****************************************************************************
3 * Mesa 3-D graphics library
4 * Direct3D Driver Interface
6 * ========================================================================
8 * Copyright (C) 1991-2004 SciTech Software, Inc. All rights reserved.
10 * Permission is hereby granted, free of charge, to any person obtaining a
11 * copy of this software and associated documentation files (the "Software"),
12 * to deal in the Software without restriction, including without limitation
13 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
14 * and/or sell copies of the Software, and to permit persons to whom the
15 * Software is furnished to do so, subject to the following conditions:
17 * The above copyright notice and this permission notice shall be included
18 * in all copies or substantial portions of the Software.
20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
21 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
23 * SCITECH SOFTWARE INC BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
24 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
25 * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
28 * ======================================================================
31 * Environment: Windows 9x/2000/XP/XBox (Win32)
33 * Description: Texture / Bitmap functions
35 ****************************************************************************/
37 #include "dglcontext.h"
41 //#include <d3dx8tex.h>
43 #include "texformat.h"
49 //---------------------------------------------------------------------------
51 #define GLD_FLIP_HEIGHT(y,h) (gldCtx->dwHeight - (y) - (h))
53 D3DX_SURFACEFORMAT
_gldD3DXFormatFromSurface(IDirectDrawSurface7
*pSurface
);
55 //---------------------------------------------------------------------------
57 //---------------------------------------------------------------------------
59 #define CHAN_SRC( t, i, j, k, sz ) \
60 ((GLchan *)(t)->Data + (i) * (sz))
61 #define UBYTE_SRC( t, i, j, k, sz ) \
62 ((GLubyte *)(t)->Data + (i) * (sz))
63 #define USHORT_SRC( t, i, j, k ) \
64 ((GLushort *)(t)->Data + (i))
65 #define FLOAT_SRC( t, i, j, k ) \
66 ((GLfloat *)(t)->Data + (i))
68 //---------------------------------------------------------------------------
70 static void gld_fetch_1d_texel_X8R8G8B8(
71 const struct gl_texture_image
*texImage
,
72 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
74 const GLchan
*src
= CHAN_SRC( texImage
, i
, j
, k
, 4 );
75 GLchan
*rgba
= (GLchan
*)texel
;
79 rgba
[ACOMP
] = CHAN_MAX
;
82 //---------------------------------------------------------------------------
84 static void gld_fetch_1d_texel_f_X8R8G8B8(
85 const struct gl_texture_image
*texImage
,
86 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
88 const GLchan
*src
= CHAN_SRC( texImage
, i
, j
, k
, 4 );
89 texel
[RCOMP
] = CHAN_TO_FLOAT(src
[0]);
90 texel
[GCOMP
] = CHAN_TO_FLOAT(src
[1]);
91 texel
[BCOMP
] = CHAN_TO_FLOAT(src
[2]);
95 //---------------------------------------------------------------------------
97 static void gld_fetch_1d_texel_X1R5G5B5(
98 const struct gl_texture_image
*texImage
,
99 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
101 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
102 GLchan
*rgba
= (GLchan
*) texel
; GLushort s
= *src
;
103 rgba
[RCOMP
] = UBYTE_TO_CHAN( ((s
>> 10) & 0xf8) * 255 / 0xf8 );
104 rgba
[GCOMP
] = UBYTE_TO_CHAN( ((s
>> 5) & 0xf8) * 255 / 0xf8 );
105 rgba
[BCOMP
] = UBYTE_TO_CHAN( ((s
) & 0xf8) * 255 / 0xf8 );
106 rgba
[ACOMP
] = CHAN_MAX
;
109 //---------------------------------------------------------------------------
111 static void gld_fetch_1d_texel_f_X1R5G5B5(
112 const struct gl_texture_image
*texImage
,
113 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
115 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
117 texel
[RCOMP
] = UBYTE_TO_FLOAT( ((s
>> 10) & 0xf8) * 255 / 0xf8 );
118 texel
[GCOMP
] = UBYTE_TO_FLOAT( ((s
>> 5) & 0xf8) * 255 / 0xf8 );
119 texel
[BCOMP
] = UBYTE_TO_FLOAT( ((s
) & 0xf8) * 255 / 0xf8 );
123 //---------------------------------------------------------------------------
125 static void gld_fetch_1d_texel_X4R4G4B4(
126 const struct gl_texture_image
*texImage
,
127 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
129 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
130 GLchan
*rgba
= (GLchan
*) texel
; GLushort s
= *src
;
131 rgba
[RCOMP
] = UBYTE_TO_CHAN( ((s
>> 8) & 0xf) * 255 / 0xf );
132 rgba
[GCOMP
] = UBYTE_TO_CHAN( ((s
>> 4) & 0xf) * 255 / 0xf );
133 rgba
[BCOMP
] = UBYTE_TO_CHAN( ((s
) & 0xf) * 255 / 0xf );
134 rgba
[ACOMP
] = CHAN_MAX
;
137 //---------------------------------------------------------------------------
139 static void gld_fetch_1d_texel_f_X4R4G4B4(
140 const struct gl_texture_image
*texImage
,
141 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
143 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
145 texel
[RCOMP
] = UBYTE_TO_FLOAT( ((s
>> 8) & 0xf) * 255 / 0xf );
146 texel
[GCOMP
] = UBYTE_TO_FLOAT( ((s
>> 4) & 0xf) * 255 / 0xf );
147 texel
[BCOMP
] = UBYTE_TO_FLOAT( ((s
) & 0xf) * 255 / 0xf );
151 //---------------------------------------------------------------------------
158 //---------------------------------------------------------------------------
160 //---------------------------------------------------------------------------
162 #define CHAN_SRC( t, i, j, k, sz ) \
163 ((GLchan *)(t)->Data + ((t)->Width * (j) + (i)) * (sz))
164 #define UBYTE_SRC( t, i, j, k, sz ) \
165 ((GLubyte *)(t)->Data + ((t)->Width * (j) + (i)) * (sz))
166 #define USHORT_SRC( t, i, j, k ) \
167 ((GLushort *)(t)->Data + ((t)->Width * (j) + (i)))
168 #define FLOAT_SRC( t, i, j, k ) \
169 ((GLfloat *)(t)->Data + ((t)->Width * (j) + (i)))
171 //---------------------------------------------------------------------------
173 static void gld_fetch_2d_texel_X8R8G8B8(
174 const struct gl_texture_image
*texImage
,
175 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
177 const GLchan
*src
= CHAN_SRC( texImage
, i
, j
, k
, 4 );
178 GLchan
*rgba
= (GLchan
*)texel
;
179 rgba
[RCOMP
] = src
[2];
180 rgba
[GCOMP
] = src
[1];
181 rgba
[BCOMP
] = src
[0];
182 rgba
[ACOMP
] = CHAN_MAX
;
185 //---------------------------------------------------------------------------
187 static void gld_fetch_2d_texel_f_X8R8G8B8(
188 const struct gl_texture_image
*texImage
,
189 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
191 const GLchan
*src
= CHAN_SRC( texImage
, i
, j
, k
, 4 );
192 texel
[RCOMP
] = CHAN_TO_FLOAT(src
[0]);
193 texel
[GCOMP
] = CHAN_TO_FLOAT(src
[1]);
194 texel
[BCOMP
] = CHAN_TO_FLOAT(src
[2]);
198 //---------------------------------------------------------------------------
200 static void gld_fetch_2d_texel_X1R5G5B5(
201 const struct gl_texture_image
*texImage
,
202 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
204 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
205 GLchan
*rgba
= (GLchan
*) texel
; GLushort s
= *src
;
206 rgba
[RCOMP
] = UBYTE_TO_CHAN( ((s
>> 10) & 0xf8) * 255 / 0xf8 );
207 rgba
[GCOMP
] = UBYTE_TO_CHAN( ((s
>> 5) & 0xf8) * 255 / 0xf8 );
208 rgba
[BCOMP
] = UBYTE_TO_CHAN( ((s
) & 0xf8) * 255 / 0xf8 );
209 rgba
[ACOMP
] = CHAN_MAX
;
212 //---------------------------------------------------------------------------
214 static void gld_fetch_2d_texel_f_X1R5G5B5(
215 const struct gl_texture_image
*texImage
,
216 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
218 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
220 texel
[RCOMP
] = UBYTE_TO_FLOAT( ((s
>> 10) & 0xf8) * 255 / 0xf8 );
221 texel
[GCOMP
] = UBYTE_TO_FLOAT( ((s
>> 5) & 0xf8) * 255 / 0xf8 );
222 texel
[BCOMP
] = UBYTE_TO_FLOAT( ((s
) & 0xf8) * 255 / 0xf8 );
226 //---------------------------------------------------------------------------
228 static void gld_fetch_2d_texel_X4R4G4B4(
229 const struct gl_texture_image
*texImage
,
230 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
232 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
233 GLchan
*rgba
= (GLchan
*) texel
; GLushort s
= *src
;
234 rgba
[RCOMP
] = UBYTE_TO_CHAN( ((s
>> 8) & 0xf) * 255 / 0xf );
235 rgba
[GCOMP
] = UBYTE_TO_CHAN( ((s
>> 4) & 0xf) * 255 / 0xf );
236 rgba
[BCOMP
] = UBYTE_TO_CHAN( ((s
) & 0xf) * 255 / 0xf );
237 rgba
[ACOMP
] = CHAN_MAX
;
240 //---------------------------------------------------------------------------
242 static void gld_fetch_2d_texel_f_X4R4G4B4(
243 const struct gl_texture_image
*texImage
,
244 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
246 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
248 texel
[RCOMP
] = UBYTE_TO_FLOAT( ((s
>> 8) & 0xf) * 255 / 0xf );
249 texel
[GCOMP
] = UBYTE_TO_FLOAT( ((s
>> 4) & 0xf) * 255 / 0xf );
250 texel
[BCOMP
] = UBYTE_TO_FLOAT( ((s
) & 0xf) * 255 / 0xf );
254 //---------------------------------------------------------------------------
261 //---------------------------------------------------------------------------
263 //---------------------------------------------------------------------------
265 #define CHAN_SRC( t, i, j, k, sz ) \
266 (GLchan *)(t)->Data + (((t)->Height * (k) + (j)) * \
267 (t)->Width + (i)) * (sz)
268 #define UBYTE_SRC( t, i, j, k, sz ) \
269 ((GLubyte *)(t)->Data + (((t)->Height * (k) + (j)) * \
270 (t)->Width + (i)) * (sz))
271 #define USHORT_SRC( t, i, j, k ) \
272 ((GLushort *)(t)->Data + (((t)->Height * (k) + (j)) * \
274 #define FLOAT_SRC( t, i, j, k ) \
275 ((GLfloat *)(t)->Data + (((t)->Height * (k) + (j)) * \
278 //---------------------------------------------------------------------------
280 static void gld_fetch_3d_texel_X8R8G8B8(
281 const struct gl_texture_image
*texImage
,
282 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
284 const GLchan
*src
= CHAN_SRC( texImage
, i
, j
, k
, 4 );
285 GLchan
*rgba
= (GLchan
*)texel
;
286 rgba
[RCOMP
] = src
[2];
287 rgba
[GCOMP
] = src
[1];
288 rgba
[BCOMP
] = src
[0];
289 rgba
[ACOMP
] = CHAN_MAX
;
292 //---------------------------------------------------------------------------
294 static void gld_fetch_3d_texel_f_X8R8G8B8(
295 const struct gl_texture_image
*texImage
,
296 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
298 const GLchan
*src
= CHAN_SRC( texImage
, i
, j
, k
, 4 );
299 texel
[RCOMP
] = CHAN_TO_FLOAT(src
[0]);
300 texel
[GCOMP
] = CHAN_TO_FLOAT(src
[1]);
301 texel
[BCOMP
] = CHAN_TO_FLOAT(src
[2]);
305 //---------------------------------------------------------------------------
307 static void gld_fetch_3d_texel_X1R5G5B5(
308 const struct gl_texture_image
*texImage
,
309 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
311 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
312 GLchan
*rgba
= (GLchan
*) texel
; GLushort s
= *src
;
313 rgba
[RCOMP
] = UBYTE_TO_CHAN( ((s
>> 10) & 0xf8) * 255 / 0xf8 );
314 rgba
[GCOMP
] = UBYTE_TO_CHAN( ((s
>> 5) & 0xf8) * 255 / 0xf8 );
315 rgba
[BCOMP
] = UBYTE_TO_CHAN( ((s
) & 0xf8) * 255 / 0xf8 );
316 rgba
[ACOMP
] = CHAN_MAX
;
319 //---------------------------------------------------------------------------
321 static void gld_fetch_3d_texel_f_X1R5G5B5(
322 const struct gl_texture_image
*texImage
,
323 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
325 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
327 texel
[RCOMP
] = UBYTE_TO_FLOAT( ((s
>> 10) & 0xf8) * 255 / 0xf8 );
328 texel
[GCOMP
] = UBYTE_TO_FLOAT( ((s
>> 5) & 0xf8) * 255 / 0xf8 );
329 texel
[BCOMP
] = UBYTE_TO_FLOAT( ((s
) & 0xf8) * 255 / 0xf8 );
333 //---------------------------------------------------------------------------
335 static void gld_fetch_3d_texel_X4R4G4B4(
336 const struct gl_texture_image
*texImage
,
337 GLint i
, GLint j
, GLint k
, GLchan
*texel
)
339 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
340 GLchan
*rgba
= (GLchan
*) texel
; GLushort s
= *src
;
341 rgba
[RCOMP
] = UBYTE_TO_CHAN( ((s
>> 8) & 0xf) * 255 / 0xf );
342 rgba
[GCOMP
] = UBYTE_TO_CHAN( ((s
>> 4) & 0xf) * 255 / 0xf );
343 rgba
[BCOMP
] = UBYTE_TO_CHAN( ((s
) & 0xf) * 255 / 0xf );
344 rgba
[ACOMP
] = CHAN_MAX
;
347 //---------------------------------------------------------------------------
349 static void gld_fetch_3d_texel_f_X4R4G4B4(
350 const struct gl_texture_image
*texImage
,
351 GLint i
, GLint j
, GLint k
, GLfloat
*texel
)
353 const GLushort
*src
= USHORT_SRC( texImage
, i
, j
, k
);
355 texel
[RCOMP
] = UBYTE_TO_FLOAT( ((s
>> 8) & 0xf) * 255 / 0xf );
356 texel
[GCOMP
] = UBYTE_TO_FLOAT( ((s
>> 4) & 0xf) * 255 / 0xf );
357 texel
[BCOMP
] = UBYTE_TO_FLOAT( ((s
) & 0xf) * 255 / 0xf );
361 //---------------------------------------------------------------------------
368 //---------------------------------------------------------------------------
369 // Direct3D texture formats that have no Mesa equivalent
370 //---------------------------------------------------------------------------
372 const struct gl_texture_format _gld_texformat_X8R8G8B8
= {
373 MESA_FORMAT_ARGB8888
, /* MesaFormat */
374 GL_RGBA
, /* BaseFormat */
375 GL_UNSIGNED_NORMALIZED_ARB
, /* DataType */
380 0, /* LuminanceBits */
381 0, /* IntensityBits */
385 _mesa_texstore_argb8888
, /* StoreTexImageFunc */
386 gld_fetch_1d_texel_X8R8G8B8
, /* FetchTexel1D */
387 gld_fetch_2d_texel_X8R8G8B8
, /* FetchTexel2D */
388 gld_fetch_3d_texel_X8R8G8B8
, /* FetchTexel3D */
389 gld_fetch_1d_texel_f_X8R8G8B8
, /* FetchTexel1Df */
390 gld_fetch_2d_texel_f_X8R8G8B8
, /* FetchTexel2Df */
391 gld_fetch_3d_texel_f_X8R8G8B8
, /* FetchTexel3Df */
394 const struct gl_texture_format _gld_texformat_X1R5G5B5
= {
395 MESA_FORMAT_ARGB1555
, /* MesaFormat */
396 GL_RGBA
, /* BaseFormat */
397 GL_UNSIGNED_NORMALIZED_ARB
, /* DataType */
402 0, /* LuminanceBits */
403 0, /* IntensityBits */
407 _mesa_texstore_argb1555
, /* StoreTexImageFunc */
408 gld_fetch_1d_texel_X1R5G5B5
, /* FetchTexel1D */
409 gld_fetch_2d_texel_X1R5G5B5
, /* FetchTexel2D */
410 gld_fetch_3d_texel_X1R5G5B5
, /* FetchTexel3D */
411 gld_fetch_1d_texel_f_X1R5G5B5
, /* FetchTexel1Df */
412 gld_fetch_2d_texel_f_X1R5G5B5
, /* FetchTexel2Df */
413 gld_fetch_3d_texel_f_X1R5G5B5
, /* FetchTexel3Df */
416 const struct gl_texture_format _gld_texformat_X4R4G4B4
= {
417 MESA_FORMAT_ARGB4444
, /* MesaFormat */
418 GL_RGBA
, /* BaseFormat */
419 GL_UNSIGNED_NORMALIZED_ARB
, /* DataType */
424 0, /* LuminanceBits */
425 0, /* IntensityBits */
429 _mesa_texstore_argb4444
, /* StoreTexImageFunc */
430 gld_fetch_1d_texel_X4R4G4B4
, /* FetchTexel1D */
431 gld_fetch_2d_texel_X4R4G4B4
, /* FetchTexel2D */
432 gld_fetch_3d_texel_X4R4G4B4
, /* FetchTexel3D */
433 gld_fetch_1d_texel_f_X4R4G4B4
, /* FetchTexel1Df */
434 gld_fetch_2d_texel_f_X4R4G4B4
, /* FetchTexel2Df */
435 gld_fetch_3d_texel_f_X4R4G4B4
, /* FetchTexel3Df */
438 //---------------------------------------------------------------------------
439 // Texture unit constants
440 //---------------------------------------------------------------------------
442 // List of possible combinations of texture environments.
443 // Example: GLD_TEXENV_MODULATE_RGBA means
444 // GL_MODULATE, GL_RGBA base internal format.
445 #define GLD_TEXENV_DECAL_RGB 0
446 #define GLD_TEXENV_DECAL_RGBA 1
447 #define GLD_TEXENV_DECAL_ALPHA 2
448 #define GLD_TEXENV_REPLACE_RGB 3
449 #define GLD_TEXENV_REPLACE_RGBA 4
450 #define GLD_TEXENV_REPLACE_ALPHA 5
451 #define GLD_TEXENV_MODULATE_RGB 6
452 #define GLD_TEXENV_MODULATE_RGBA 7
453 #define GLD_TEXENV_MODULATE_ALPHA 8
454 #define GLD_TEXENV_BLEND_RGB 9
455 #define GLD_TEXENV_BLEND_RGBA 10
456 #define GLD_TEXENV_BLEND_ALPHA 11
457 #define GLD_TEXENV_ADD_RGB 12
458 #define GLD_TEXENV_ADD_RGBA 13
459 #define GLD_TEXENV_ADD_ALPHA 14
461 // Per-stage (i.e. per-unit) texture environment
463 DWORD ColorArg1
; // Colour argument 1
464 D3DTEXTUREOP ColorOp
; // Colour operation
465 DWORD ColorArg2
; // Colour argument 2
466 DWORD AlphaArg1
; // Alpha argument 1
467 D3DTEXTUREOP AlphaOp
; // Alpha operation
468 DWORD AlphaArg2
; // Alpha argument 2
471 // TODO: Do we really need to set ARG1 and ARG2 every time?
472 // They seem to always be TEXTURE and CURRENT respectively.
476 // Ct = Colour from Texture
477 // Cf = Colour from fragment (diffuse)
478 // At = Alpha from Texture
479 // Af = Alpha from fragment (diffuse)
480 // Cc = GL_TEXTURE_ENV_COLOUR (GL_BLEND)
481 const GLD_texenv gldTexEnv
[] = {
482 // DECAL_RGB: C=Ct, A=Af
483 {D3DTA_TEXTURE
, D3DTOP_SELECTARG1
, D3DTA_CURRENT
,
484 D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
},
485 // DECAL_RGBA: C=Cf(1-At)+CtAt, A=Af
486 {D3DTA_TEXTURE
, D3DTOP_BLENDTEXTUREALPHA
, D3DTA_CURRENT
,
487 D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
},
488 // DECAL_ALPHA: <undefined> use DECAL_RGB
489 {D3DTA_TEXTURE
, D3DTOP_SELECTARG1
, D3DTA_CURRENT
,
490 D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
},
492 // REPLACE_RGB: C=Ct, A=Af
493 {D3DTA_TEXTURE
, D3DTOP_SELECTARG1
, D3DTA_CURRENT
,
494 D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
},
495 // REPLACE_RGBA: C=Ct, A=At
496 {D3DTA_TEXTURE
, D3DTOP_SELECTARG1
, D3DTA_CURRENT
,
497 D3DTA_TEXTURE
, D3DTOP_SELECTARG1
, D3DTA_CURRENT
},
498 // REPLACE_ALPHA: C=Cf, A=At
499 {D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
,
500 D3DTA_TEXTURE
, D3DTOP_SELECTARG1
, D3DTA_CURRENT
},
502 // MODULATE_RGB: C=CfCt, A=Af
503 {D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
,
504 D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
},
505 // MODULATE_RGBA: C=CfCt, A=AfAt
506 {D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
,
507 D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
},
508 // MODULATE_ALPHA: C=Cf, A=AfAt
509 {D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
,
510 D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
},
513 // DX7 Does not support D3DTOP_LERP
514 // Emulate(?) via D3DTOP_ADDSMOOTH
517 // BLEND_RGB: C=Cf(1-Ct)+CcCt, A=Af
518 {D3DTA_TEXTURE
, D3DTOP_LERP
, D3DTA_CURRENT
,
519 D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
},
520 // BLEND_RGBA: C=Cf(1-Ct)+CcCt, A=AfAt
521 {D3DTA_TEXTURE
, D3DTOP_LERP
, D3DTA_CURRENT
,
522 D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
},
524 // BLEND_RGB: C=Cf(1-Ct)+CcCt, A=Af
525 {D3DTA_TEXTURE
, D3DTOP_ADDSMOOTH
, D3DTA_CURRENT
,
526 D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
},
527 // BLEND_RGBA: C=Cf(1-Ct)+CcCt, A=AfAt
528 {D3DTA_TEXTURE
, D3DTOP_ADDSMOOTH
, D3DTA_CURRENT
,
529 D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
},
531 // BLEND_ALPHA: C=Cf, A=AfAt
532 {D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
,
533 D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
},
535 // ADD_RGB: C=Cf+Ct, A=Af
536 {D3DTA_TEXTURE
, D3DTOP_ADD
, D3DTA_CURRENT
,
537 D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
},
538 // ADD_RGBA: C=Cf+Ct, A=AfAt
539 {D3DTA_TEXTURE
, D3DTOP_ADD
, D3DTA_CURRENT
,
540 D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
},
541 // ADD_ALPHA: C=Cf, A=AfAt
542 {D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_CURRENT
,
543 D3DTA_TEXTURE
, D3DTOP_MODULATE
, D3DTA_CURRENT
},
546 //---------------------------------------------------------------------------
548 D3DTEXTUREADDRESS
_gldConvertWrap(
551 // ASSERT(wrap==GL_CLAMP || wrap==GL_REPEAT);
552 return (wrap
== GL_CLAMP
) ? D3DTADDRESS_CLAMP
: D3DTADDRESS_WRAP
;
555 //---------------------------------------------------------------------------
557 D3DTEXTUREMAGFILTER
_gldConvertMagFilter(
560 ASSERT(magfilter
==GL_LINEAR
|| magfilter
==GL_NEAREST
);
561 return (magfilter
== GL_LINEAR
) ? D3DTFG_LINEAR
: D3DTFG_POINT
;
564 //---------------------------------------------------------------------------
566 void _gldConvertMinFilter(
568 D3DTEXTUREMINFILTER
*min_filter
,
569 D3DTEXTUREMIPFILTER
*mip_filter
)
573 *min_filter
= D3DTFN_POINT
;
574 *mip_filter
= D3DTFP_NONE
;
577 *min_filter
= D3DTFN_LINEAR
;
578 *mip_filter
= D3DTFP_NONE
;
580 case GL_NEAREST_MIPMAP_NEAREST
:
581 *min_filter
= D3DTFN_POINT
;
582 *mip_filter
= D3DTFP_POINT
;
584 case GL_LINEAR_MIPMAP_NEAREST
:
585 *min_filter
= D3DTFN_LINEAR
;
586 *mip_filter
= D3DTFP_POINT
;
588 case GL_NEAREST_MIPMAP_LINEAR
:
589 *min_filter
= D3DTFN_POINT
;
590 *mip_filter
= D3DTFP_LINEAR
;
592 case GL_LINEAR_MIPMAP_LINEAR
:
593 *min_filter
= D3DTFN_LINEAR
;
594 *mip_filter
= D3DTFP_LINEAR
;
601 //---------------------------------------------------------------------------
603 D3DX_SURFACEFORMAT
_gldGLFormatToD3DFormat(
604 GLenum internalFormat
)
606 switch (internalFormat
) {
612 // LUNIMANCE != INTENSITY, but D3D doesn't have I8 textures
628 case GL_COLOR_INDEX1_EXT
:
629 case GL_COLOR_INDEX2_EXT
:
630 case GL_COLOR_INDEX4_EXT
:
631 case GL_COLOR_INDEX8_EXT
:
632 case GL_COLOR_INDEX12_EXT
:
633 case GL_COLOR_INDEX16_EXT
:
634 return D3DX_SF_X8R8G8B8
;
636 case GL_LUMINANCE_ALPHA
:
637 case GL_LUMINANCE4_ALPHA4
:
638 case GL_LUMINANCE6_ALPHA2
:
639 case GL_LUMINANCE8_ALPHA8
:
640 case GL_LUMINANCE12_ALPHA4
:
641 case GL_LUMINANCE12_ALPHA12
:
642 case GL_LUMINANCE16_ALPHA16
:
645 // TODO: Mesa does not support RGB332 internally
646 return D3DX_SF_X4R4G4B4
; //D3DFMT_R3G3B2;
648 return D3DX_SF_X4R4G4B4
;
650 return D3DX_SF_R5G5B5
;
657 return D3DX_SF_R8G8B8
;
659 return D3DX_SF_A4R4G4B4
;
667 return D3DX_SF_A8R8G8B8
;
669 return D3DX_SF_A1R5G5B5
;
674 // Return an acceptable default
675 return D3DX_SF_A8R8G8B8
;
678 //---------------------------------------------------------------------------
680 GLenum
_gldDecodeBaseFormat(
681 IDirectDrawSurface7
*pTex
)
683 // Examine Direct3D texture and return base OpenGL internal texture format
684 // NOTE: We can't use any base format info from Mesa because D3D might have
685 // used a different texture format when we used D3DXCreateTexture().
687 // Base internal format is one of (Red Book p355):
690 // GL_LUMINANCE_ALPHA,
695 // NOTE: INTENSITY not used (not supported by Direct3D)
696 // LUMINANCE has same texture functions as RGB
697 // LUMINANCE_ALPHA has same texture functions as RGBA
699 // TODO: cache format instead of using GetLevelDesc()
700 // D3DSURFACE_DESC desc;
701 // _GLD_DX7_TEX(GetLevelDesc(pTex, 0, &desc));
703 D3DX_SURFACEFORMAT sf
;
705 sf
= _gldD3DXFormatFromSurface(pTex
);
709 case D3DX_SF_X8R8G8B8
:
713 case D3DX_SF_X4R4G4B4
:
714 case D3DX_SF_PALETTE8
:
717 case D3DX_SF_A8R8G8B8
:
718 case D3DX_SF_A1R5G5B5
:
719 case D3DX_SF_A4R4G4B4
:
720 // case D3DX_SF_A8R3G3B2: // Unsupported by DX7
721 // case D3DX_SF_A8P8: // Unsupported by DX7
723 // case D3DX_SF_A4L4: // Unsupported by DX7
727 // Compressed texture formats. Need to check these...
730 // case D3DX_SF_DXT2: // Unsupported by DX7
734 // case D3DX_SF_DXT4: // Unsupported by DX7
740 // Fell through. Return arbitary default.
745 //---------------------------------------------------------------------------
747 const struct gl_texture_format
* _gldMesaFormatForD3DFormat(
748 D3DX_SURFACEFORMAT d3dfmt
)
751 case D3DX_SF_A8R8G8B8
:
752 return &_mesa_texformat_argb8888
;
754 return &_mesa_texformat_rgb888
;
756 return &_mesa_texformat_rgb565
;
757 case D3DX_SF_A4R4G4B4
:
758 return &_mesa_texformat_argb4444
;
759 case D3DX_SF_A1R5G5B5
:
760 return &_mesa_texformat_argb1555
;
762 return &_mesa_texformat_al88
;
764 return &_mesa_texformat_rgb332
;
766 return &_mesa_texformat_a8
;
768 return &_mesa_texformat_l8
;
769 case D3DX_SF_X8R8G8B8
:
770 return &_gld_texformat_X8R8G8B8
;
772 return &_gld_texformat_X1R5G5B5
;
773 case D3DX_SF_X4R4G4B4
:
774 return &_gld_texformat_X4R4G4B4
;
777 // If we reach here then we've made an error somewhere else
778 // by allowing a format that is not supported.
781 return NULL
; // Shut up compiler warning
784 //---------------------------------------------------------------------------
786 D3DX_SURFACEFORMAT
_gldD3DXFormatFromSurface(
787 IDirectDrawSurface7
*pSurface
)
791 ddpf
.dwSize
= sizeof(ddpf
);
793 // Obtain pixel format of surface
794 _GLD_DX7_TEX(GetPixelFormat(pSurface
, &ddpf
));
795 // Decode to D3DX surface format
796 return D3DXMakeSurfaceFormat(&ddpf
);
799 //---------------------------------------------------------------------------
801 void _gldClearSurface(
802 IDirectDrawSurface
*pSurface
,
805 DDBLTFX bltFX
; // Used for colour fill
808 bltFX
.dwSize
= sizeof(bltFX
);
810 bltFX
.dwFillColor
= dwColour
;
811 // Clear surface. HW accelerated if available.
812 IDirectDrawSurface7_Blt(pSurface
, NULL
, NULL
, NULL
, DDBLT_COLORFILL
, &bltFX
);
815 //---------------------------------------------------------------------------
817 //---------------------------------------------------------------------------
819 void gldCopyTexImage1D_DX7(
821 GLenum target
, GLint level
,
822 GLenum internalFormat
,
824 GLsizei width
, GLint border
)
829 //---------------------------------------------------------------------------
831 void gldCopyTexImage2D_DX7(
835 GLenum internalFormat
,
845 //---------------------------------------------------------------------------
847 void gldCopyTexSubImage1D_DX7(
849 GLenum target
, GLint level
,
850 GLint xoffset
, GLint x
, GLint y
, GLsizei width
)
855 //---------------------------------------------------------------------------
857 void gldCopyTexSubImage2D_DX7(
871 //---------------------------------------------------------------------------
873 void gldCopyTexSubImage3D_DX7(
888 //---------------------------------------------------------------------------
889 // Bitmap/Pixel functions
890 //---------------------------------------------------------------------------
892 #define GLD_FLIP_Y(y) (gldCtx->dwHeight - (y))
894 #define _GLD_FVF_IMAGE (D3DFVF_XYZRHW | D3DFVF_TEX1)
897 FLOAT x
, y
; // 2D raster coords
898 FLOAT z
; // depth value
899 FLOAT rhw
; // reciprocal homogenous W (always 1.0f)
900 FLOAT tu
, tv
; // texture coords
903 //---------------------------------------------------------------------------
905 HRESULT
_gldDrawPixels(
907 BOOL bChromakey
, // Alpha test for glBitmap() images
908 GLint x
, // GL x position
909 GLint y
, // GL y position (needs flipping)
910 GLsizei width
, // Width of input image
911 GLsizei height
, // Height of input image
912 IDirectDrawSurface7
*pImage
)
915 // Draw input image as texture implementing PixelZoom and clipping.
916 // Any fragment operations currently enabled will be used.
919 // NOTE: This DX7 version does not create a new texture in which
920 // to copy the input image, as the image is already a texture.
922 GLD_context
*gldCtx
= GLD_GET_CONTEXT(ctx
);
923 GLD_driver_dx7
*gld
= GLD_GET_DX7_DRIVER(gldCtx
);
926 _GLD_IMAGE_VERTEX v
[4];
928 float ZoomWidth
, ZoomHeight
;
929 float ScaleWidth
, ScaleHeight
;
931 // Fixup for rasterisation rules
932 const float cfEpsilon
= 1.0f
/ (float)height
;
935 // Set up the quad like this (ascii-art ahead!)
944 v
[0].z
= v
[1].z
= v
[2].z
= v
[3].z
= ctx
->Current
.RasterPos
[2];
945 // Set Reciprocal Homogenous W
946 v
[0].rhw
= v
[1].rhw
= v
[2].rhw
= v
[3].rhw
= 1.0f
;
949 // Examine texture size - if different to input width and height
950 // then we'll need to munge the texcoords to fit.
951 ddsd
.dwSize
= sizeof(DDSURFACEDESC2
);
952 IDirectDrawSurface7_GetSurfaceDesc(pImage
, &ddsd
);
953 ScaleWidth
= (float)width
/ (float)ddsd
.dwWidth
;
954 ScaleHeight
= (float)height
/ (float)ddsd
.dwHeight
;
955 v
[0].tu
= 0.0f
; v
[0].tv
= 0.0f
;
956 v
[1].tu
= ScaleWidth
; v
[1].tv
= 0.0f
;
957 v
[2].tu
= ScaleWidth
; v
[2].tv
= ScaleHeight
;
958 v
[3].tu
= 0.0f
; v
[3].tv
= ScaleHeight
;
960 // Set raster positions
961 ZoomWidth
= (float)width
* ctx
->Pixel
.ZoomX
;
962 ZoomHeight
= (float)height
* ctx
->Pixel
.ZoomY
;
964 v
[0].x
= x
; v
[0].y
= GLD_FLIP_Y(y
+cfEpsilon
);
965 v
[1].x
= x
+ZoomWidth
; v
[1].y
= GLD_FLIP_Y(y
+cfEpsilon
);
966 v
[2].x
= x
+ZoomWidth
; v
[2].y
= GLD_FLIP_Y(y
+ZoomHeight
+cfEpsilon
);
967 v
[3].x
= x
; v
[3].y
= GLD_FLIP_Y(y
+ZoomHeight
+cfEpsilon
);
969 // Draw image with full HW acceleration
970 // NOTE: Be nice to use a State Block for all this state...
971 IDirect3DDevice7_SetTexture(gld
->pDev
, 0, pImage
);
972 IDirect3DDevice7_SetRenderState(gld
->pDev
, D3DRENDERSTATE_CULLMODE
, D3DCULL_NONE
);
973 IDirect3DDevice7_SetRenderState(gld
->pDev
, D3DRENDERSTATE_CLIPPING
, TRUE
);
974 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_MINFILTER
, D3DTFN_POINT
);
975 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_MIPFILTER
, D3DTFP_POINT
);
976 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_MAGFILTER
, D3DTFG_POINT
);
977 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_ADDRESSU
, D3DTADDRESS_CLAMP
);
978 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_ADDRESSV
, D3DTADDRESS_CLAMP
);
979 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_COLOROP
, D3DTOP_SELECTARG1
);
980 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_ALPHAOP
, D3DTOP_SELECTARG1
);
981 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_COLORARG1
, D3DTA_TEXTURE
);
982 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 0, D3DTSS_ALPHAARG1
, D3DTA_TEXTURE
);
983 // Ensure texture unit 1 is disabled
984 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 1, D3DTSS_COLOROP
, D3DTOP_DISABLE
);
985 IDirect3DDevice7_SetTextureStageState(gld
->pDev
, 1, D3DTSS_ALPHAOP
, D3DTOP_DISABLE
);
988 // Emulate Chromakey with an Alpha Test.
989 // [Alpha Test is more widely supported anyway]
992 // Switch on alpha testing
993 IDirect3DDevice7_SetRenderState(gld
->pDev
, D3DRENDERSTATE_ALPHATESTENABLE
, TRUE
);
994 // Fragment passes is alpha is greater than reference value
995 IDirect3DDevice7_SetRenderState(gld
->pDev
, D3DRENDERSTATE_ALPHAFUNC
, D3DCMP_GREATER
);
996 // Set alpha reference value between Bitmap alpha values of
997 // zero (transparent) and one (opaque).
998 IDirect3DDevice7_SetRenderState(gld
->pDev
, D3DRENDERSTATE_ALPHAREF
, 0x7f);
1001 IDirect3DDevice7_DrawPrimitive(gld
->pDev
, D3DPT_TRIANGLEFAN
, _GLD_FVF_IMAGE
, &v
, 4, 0);
1003 // Reset state to before we messed it up
1004 FLUSH_VERTICES(ctx
, _NEW_ALL
);
1009 //---------------------------------------------------------------------------
1011 void gld_DrawPixels_DX7(
1013 GLint x
, GLint y
, GLsizei width
, GLsizei height
,
1014 GLenum format
, GLenum type
,
1015 const struct gl_pixelstore_attrib
*unpack
,
1016 const GLvoid
*pixels
)
1018 GLD_context
*gldCtx
;
1019 GLD_driver_dx7
*gld
;
1021 IDirectDrawSurface7
*pImage
;
1023 DDSURFACEDESC2 ddsd
;
1025 D3DX_SURFACEFORMAT sf
;
1028 const struct gl_texture_format
*MesaFormat
;
1030 MesaFormat
= _mesa_choose_tex_format(ctx
, format
, format
, type
);
1032 gldCtx
= GLD_GET_CONTEXT(ctx
);
1033 gld
= GLD_GET_DX7_DRIVER(gldCtx
);
1035 dwFlags
= D3DX_TEXTURE_NOMIPMAP
;
1036 sf
= D3DX_SF_A8R8G8B8
;
1039 hr
= D3DXCreateTexture(
1045 &pImage
, // Output texture
1051 // D3DXCreateTexture() may not clear the texture is creates.
1052 _gldClearSurface(pImage
, 0);
1055 // Use Mesa to fill in image
1058 // Lock all of surface
1059 ddsd
.dwSize
= sizeof(DDSURFACEDESC2
);
1060 dwFlags
= DDLOCK_SURFACEMEMORYPTR
| DDLOCK_WAIT
;
1061 hr
= IDirectDrawSurface7_Lock(pImage
, NULL
, &ddsd
, dwFlags
, NULL
);
1063 SAFE_RELEASE_SURFACE7(pImage
);
1067 // unpack image, apply transfer ops and store directly in texture
1068 MesaFormat
->StoreImage(
1072 &_mesa_texformat_argb8888
,
1074 width
, height
, 1, 0, 0, 0,
1076 0, /* dstImageStride */
1077 format
, type
, pixels
, unpack
);
1079 IDirectDrawSurface7_Unlock(pImage
, NULL
);
1081 _gldDrawPixels(ctx
, FALSE
, x
, y
, width
, height
, pImage
);
1083 SAFE_RELEASE_SURFACE7(pImage
);
1086 //---------------------------------------------------------------------------
1088 void gld_ReadPixels_DX7(
1090 GLint x
, GLint y
, GLsizei width
, GLsizei height
,
1091 GLenum format
, GLenum type
,
1092 const struct gl_pixelstore_attrib
*pack
,
1097 GLD_context
*gldCtx
;
1098 GLD_driver_dx7
*gld
;
1100 IDirect3DSurface8
*pBackbuffer
= NULL
;
1101 IDirect3DSurface8
*pNativeImage
= NULL
;
1102 IDirect3DSurface8
*pCanonicalImage
= NULL
;
1104 D3DSURFACE_DESC d3dsd
;
1105 RECT rcSrc
; // Source rect
1106 POINT ptDst
; // Dest point
1108 D3DLOCKED_RECT d3dLockedRect
;
1109 struct gl_pixelstore_attrib srcPacking
;
1112 const struct gl_texture_format
*MesaFormat
;
1115 case GL_STENCIL_INDEX
:
1116 case GL_DEPTH_COMPONENT
:
1120 MesaFormat
= _mesa_choose_tex_format(ctx
, format
, format
, type
);
1121 DstRowStride
= _mesa_image_row_stride(pack
, width
, format
, type
);
1123 gldCtx
= GLD_GET_CONTEXT(ctx
);
1124 gld
= GLD_GET_DX7_DRIVER(gldCtx
);
1127 hr
= IDirect3DDevice8_GetBackBuffer(
1129 0, // First backbuffer
1130 D3DBACKBUFFER_TYPE_MONO
,
1135 // Get backbuffer description
1136 hr
= IDirect3DSurface8_GetDesc(pBackbuffer
, &d3dsd
);
1138 goto gld_ReadPixels_DX7_return
;
1141 // Create a surface compatible with backbuffer
1142 hr
= IDirect3DDevice8_CreateImageSurface(
1149 goto gld_ReadPixels_DX7_return
;
1152 // Compute source rect and dest point
1153 SetRect(&rcSrc
, 0, 0, width
, height
);
1154 OffsetRect(&rcSrc
, x
, GLD_FLIP_HEIGHT(y
, height
));
1155 ptDst
.x
= ptDst
.y
= 0;
1157 // Get source pixels.
1159 // This intermediate surface ensure that we can use CopyRects()
1160 // instead of relying on D3DXLoadSurfaceFromSurface(), which may
1161 // try and lock the backbuffer. This way seems safer.
1163 hr
= IDirect3DDevice8_CopyRects(
1171 goto gld_ReadPixels_DX7_return
;
1174 // Create an RGBA8888 surface
1175 hr
= IDirect3DDevice8_CreateImageSurface(
1182 goto gld_ReadPixels_DX7_return
;
1185 // Convert to RGBA8888
1186 hr
= D3DXLoadSurfaceFromSurface(
1187 pCanonicalImage
, // Dest surface
1188 NULL
, NULL
, // Dest palette, RECT
1189 pNativeImage
, // Src surface
1190 NULL
, NULL
, // Src palette, RECT
1191 D3DX_FILTER_NONE
, // Filter
1194 goto gld_ReadPixels_DX7_return
;
1197 srcPacking
.Alignment
= 1;
1198 srcPacking
.ImageHeight
= height
;
1199 srcPacking
.LsbFirst
= GL_FALSE
;
1200 srcPacking
.RowLength
= 0;
1201 srcPacking
.SkipImages
= 0;
1202 srcPacking
.SkipPixels
= 0;
1203 srcPacking
.SkipRows
= 0;
1204 srcPacking
.SwapBytes
= GL_FALSE
;
1206 // Lock all of image
1207 hr
= IDirect3DSurface8_LockRect(pCanonicalImage
, &d3dLockedRect
, NULL
, 0);
1209 goto gld_ReadPixels_DX7_return
;
1212 // We need to flip the data. Yuck.
1213 // Perhaps Mesa has a span packer we can use in future...
1214 for (i
=0; i
<height
; i
++) {
1215 BYTE
*pDestRow
= (BYTE
*)_mesa_image_address(2,pack
, dest
, width
, height
, format
, type
, 0, i
, 0);
1216 BYTE
*pSrcRow
= (BYTE
*)d3dLockedRect
.pBits
+ (d3dLockedRect
.Pitch
* (height
-i
-1));
1217 texImage
->TexFormat
->StoreImage(
1220 GL_RGBA
, // base format
1221 MesaFormat
, // dst format
1222 pDestRow
, // dest addr
1223 width
, 1, 1, 0, 0, 0, // src x,y,z & dst offsets x,y,z
1224 DstRowStride
, // dst row stride
1225 0, // dstImageStride
1226 GL_BGRA
, // src format
1227 GL_UNSIGNED_BYTE
, // src type
1228 pSrcRow
, // src addr
1229 &srcPacking
); // packing params of source image
1232 IDirect3DSurface8_UnlockRect(pCanonicalImage
);
1234 gld_ReadPixels_DX7_return
:
1235 SAFE_RELEASE_SURFACE8(pCanonicalImage
);
1236 SAFE_RELEASE_SURFACE8(pNativeImage
);
1237 SAFE_RELEASE_SURFACE8(pBackbuffer
);
1241 //---------------------------------------------------------------------------
1243 void gld_CopyPixels_DX7(
1256 // NOTE: Not allowed to copy vidmem to vidmem!
1257 // Therefore we use an intermediate image surface.
1260 GLD_context
*gldCtx
;
1261 GLD_driver_dx7
*gld
;
1263 IDirect3DSurface8
*pBackbuffer
;
1264 D3DSURFACE_DESC d3dsd
;
1265 IDirect3DSurface8
*pImage
;
1266 RECT rcSrc
; // Source rect
1267 POINT ptDst
; // Dest point
1271 if (type
!= GL_COLOR
)
1274 gldCtx
= GLD_GET_CONTEXT(ctx
);
1275 gld
= GLD_GET_DX7_DRIVER(gldCtx
);
1278 hr
= IDirect3DDevice8_GetBackBuffer(
1280 0, // First backbuffer
1281 D3DBACKBUFFER_TYPE_MONO
,
1286 // Get backbuffer description
1287 hr
= IDirect3DSurface8_GetDesc(pBackbuffer
, &d3dsd
);
1289 IDirect3DSurface8_Release(pBackbuffer
);
1293 // Create a surface compatible with backbuffer
1294 hr
= IDirect3DDevice8_CreateImageSurface(
1301 IDirect3DSurface8_Release(pBackbuffer
);
1305 // Compute source rect and dest point
1306 SetRect(&rcSrc
, 0, 0, width
, height
);
1307 OffsetRect(&rcSrc
, srcx
, GLD_FLIP_HEIGHT(srcy
, height
));
1308 ptDst
.x
= ptDst
.y
= 0;
1310 // Get source pixels
1311 hr
= IDirect3DDevice8_CopyRects(
1318 IDirect3DSurface8_Release(pBackbuffer
);
1320 IDirect3DSurface8_Release(pImage
);
1324 _gldDrawPixels(ctx
, FALSE
, dstx
, dsty
, width
, height
, pImage
);
1326 IDirect3DSurface8_Release(pImage
);
1330 //---------------------------------------------------------------------------
1332 void gld_Bitmap_DX7(
1338 const struct gl_pixelstore_attrib
*unpack
,
1339 const GLubyte
*bitmap
)
1341 GLD_context
*gldCtx
;
1342 GLD_driver_dx7
*gld
;
1344 IDirectDrawSurface7
*pImage
; // Bitmap texture
1346 BYTE
*pTempBitmap
; // Pointer to unpacked bitmap
1347 D3DCOLOR clBitmapOne
; // Opaque bitmap colour
1348 D3DCOLOR clBitmapZero
; // Transparent bitmap colour
1349 D3DCOLOR
*pBits
; // Pointer to texture surface
1353 DDSURFACEDESC2 ddsd
; // Surface desc returned by lock call
1355 D3DX_SURFACEFORMAT sf
;
1358 // Keep a copy of width/height as D3DXCreateTexture() call may alter input dimensions
1359 GLsizei dwWidth
= width
;
1360 GLsizei dwHeight
= height
;
1362 gldCtx
= GLD_GET_CONTEXT(ctx
);
1363 gld
= GLD_GET_DX7_DRIVER(gldCtx
);
1365 // Bail if no bitmap (only raster pos is updated)
1366 if ((bitmap
== NULL
) && (width
==0) && (height
==0))
1370 // TODO: Detect conditions when created texture (pImage) is non-pow2.
1371 // Texture coords may need to be adjusted to compensate.
1374 clBitmapZero
= D3DCOLOR_RGBA(0,0,0,0); // NOTE: Alpha is Zero
1375 clBitmapOne
= D3DCOLOR_COLORVALUE(
1376 ctx
->Current
.RasterColor
[0],
1377 ctx
->Current
.RasterColor
[1],
1378 ctx
->Current
.RasterColor
[2],
1379 1.0f
); // NOTE: Alpha is One
1381 // Use Mesa to unpack bitmap into a canonical format
1382 pTempBitmap
= _mesa_unpack_bitmap(width
, height
, bitmap
, unpack
);
1383 if (pTempBitmap
== NULL
)
1386 // Flags for texture creation
1387 dwFlags
= D3DX_TEXTURE_NOMIPMAP
;
1388 sf
= D3DX_SF_A8R8G8B8
;
1391 // Create a D3D texture to hold the bitmap
1392 hr
= D3DXCreateTexture(
1395 &dwWidth
, &dwHeight
,
1398 &pImage
, // Output texture
1405 // D3DXCreateTexture may return a texture bigger than we asked for
1406 // (i.e. padded to POW2) so let's clear the entire image bitmap.
1407 // Additional: Looks like this is not strictly necessary.
1408 // _gldClearSurface(pImage, clBitmapZero);
1410 ddsd
.dwSize
= sizeof(DDSURFACEDESC2
);
1411 dwFlags
= DDLOCK_SURFACEMEMORYPTR
| DDLOCK_WAIT
;
1412 hr
= IDirectDrawSurface7_Lock(pImage
, NULL
, &ddsd
, dwFlags
, NULL
);
1415 SAFE_RELEASE_SURFACE7(pImage
);
1421 if (!(width
==ddsd
.dwWidth
&& height
==ddsd
.dwHeight
))
1422 ddlogPrintf(GLDLOG_WARN
, "gld_Bitmap: In=%d,%d / Tex=%d,%d", width
,height
,ddsd
.dwWidth
,ddsd
.dwHeight
);
1427 ddlogPrintf(GLDLOG_SYSTEM
, "gld_Bitmap: In=%d,%d / Tex=%d,%d", width
,height
,ddsd
.dwWidth
,ddsd
.dwHeight
);
1428 ddlogPrintf(GLDLOG_SYSTEM
, "gld_Bitmap: bpp=%d", ddsd
.ddpfPixelFormat
.dwRGBBitCount
);
1431 // Cast texel pointer to texture surface.
1432 // We can do this because we used D3DX_SF_A8R8G8B8 as the format
1433 pBits
= (D3DCOLOR
*)ddsd
.lpSurface
;
1436 // Copy from the input bitmap into the texture
1437 for (i
=0; i
<height
; i
++) {
1439 pBits
= (D3DCOLOR
*)((BYTE
*)ddsd
.lpSurface
+ (i
*ddsd
.lPitch
));
1440 src
= (const GLubyte
*) _mesa_image_address(2,
1441 &ctx
->DefaultPacking
, pTempBitmap
, width
, height
, GL_COLOR_INDEX
, GL_BITMAP
,
1443 for (j
=0; j
<(width
>>3); j
++) {
1445 for (k
=0; k
<8; k
++) {
1446 *pBits
++ = (byte
& 128) ? clBitmapOne
: clBitmapZero
;
1450 // Fill remaining bits from bitmap
1453 for (k
=0; k
<(width
& 7); k
++) {
1454 *pBits
++ = (byte
& 128) ? clBitmapOne
: clBitmapZero
;
1460 // We're done with the unpacked bitmap
1463 // Finished with texture surface - unlock it
1464 IDirectDrawSurface7_Unlock(pImage
, NULL
);
1466 // Use internal function to draw bitmap onto rendertarget
1467 _gldDrawPixels(ctx
, TRUE
, x
, y
, width
, height
, pImage
);
1469 // We're done with the bitmap texure - release it
1470 IDirectDrawSurface7_Release(pImage
);
1473 //---------------------------------------------------------------------------
1474 // Texture functions
1475 //---------------------------------------------------------------------------
1477 void _gldAllocateTexture(
1479 struct gl_texture_object
*tObj
,
1480 struct gl_texture_image
*texImage
)
1482 GLD_context
*gldCtx
= GLD_GET_CONTEXT(ctx
);
1483 GLD_driver_dx7
*gld
= GLD_GET_DX7_DRIVER(gldCtx
);
1486 IDirectDrawSurface7
*pTex
;
1487 D3DX_SURFACEFORMAT d3dFormat
;
1490 DWORD dwWidth
, dwHeight
;
1492 if (!tObj
|| !texImage
)
1495 pTex
= (IDirectDrawSurface7
*)tObj
->DriverData
;
1497 // Decide whether we can keep existing D3D texture
1498 // by examining top-level surface.
1499 DDSURFACEDESC2 ddsd
;
1500 ddsd
.dwSize
= sizeof(DDSURFACEDESC2
);
1501 _GLD_DX7_TEX(GetSurfaceDesc(pTex
, &ddsd
));
1502 // Release existing texture if not compatible
1503 if ((ddsd
.dwWidth
== texImage
->Width
) ||
1504 (ddsd
.dwHeight
== texImage
->Height
))
1506 return; // Keep the existing texture
1508 tObj
->DriverData
= NULL
;
1509 _GLD_DX7_TEX(Release(pTex
));
1512 dwFlags
= (glb
.bUseMipmaps
) ? 0 : D3DX_TEXTURE_NOMIPMAP
;
1513 dwMipmaps
= (glb
.bUseMipmaps
) ? D3DX_DEFAULT
: 1;
1514 dwWidth
= texImage
->Width
;
1515 dwHeight
= texImage
->Height
;
1517 d3dFormat
= _gldGLFormatToD3DFormat(texImage
->IntFormat
);
1518 hr
= D3DXCreateTexture(
1528 gldLogError(GLDLOG_ERROR
, "AllocateTexture failed", hr
);
1530 tObj
->DriverData
= pTex
;
1533 //---------------------------------------------------------------------------
1535 const struct gl_texture_format
* gld_ChooseTextureFormat_DX7(
1537 GLint internalFormat
,
1541 // [Based on mesa_choose_tex_format()]
1543 // We will choose only texture formats that are supported
1544 // by Direct3D. If the hardware doesn't support a particular
1545 // texture format, then the D3DX texture calls that we use
1546 // will automatically use a HW supported format.
1548 // The most critical aim is to reduce copying; if we can use
1549 // texture-image data directly then it will be a big performance assist.
1552 switch (internalFormat
) {
1556 case GL_INTENSITY12
:
1557 case GL_INTENSITY16
:
1558 return &_mesa_texformat_l8
; // D3DFMT_L8
1563 case GL_LUMINANCE12
:
1564 case GL_LUMINANCE16
:
1565 return &_mesa_texformat_l8
; // D3DFMT_L8
1571 return &_mesa_texformat_a8
; // D3DFMT_A8
1572 case GL_COLOR_INDEX
:
1573 case GL_COLOR_INDEX1_EXT
:
1574 case GL_COLOR_INDEX2_EXT
:
1575 case GL_COLOR_INDEX4_EXT
:
1576 case GL_COLOR_INDEX8_EXT
:
1577 case GL_COLOR_INDEX12_EXT
:
1578 case GL_COLOR_INDEX16_EXT
:
1579 return &_mesa_texformat_rgb565
; // D3DFMT_R5G6B5
1580 // Mesa will convert this for us later...
1581 // return &_mesa_texformat_ci8; // D3DFMT_R5G6B5
1583 case GL_LUMINANCE_ALPHA
:
1584 case GL_LUMINANCE4_ALPHA4
:
1585 case GL_LUMINANCE6_ALPHA2
:
1586 case GL_LUMINANCE8_ALPHA8
:
1587 case GL_LUMINANCE12_ALPHA4
:
1588 case GL_LUMINANCE12_ALPHA12
:
1589 case GL_LUMINANCE16_ALPHA16
:
1590 return &_mesa_texformat_al88
; // D3DFMT_A8L8
1592 return &_mesa_texformat_rgb332
; // D3DFMT_R3G3B2
1596 return &_mesa_texformat_argb4444
; // D3DFMT_A4R4G4B4
1604 return &_mesa_texformat_rgb565
;
1611 return &_mesa_texformat_argb8888
;
1613 return &_mesa_texformat_argb1555
;
1615 _mesa_problem(NULL
, "unexpected format in fxDDChooseTextureFormat");
1620 //---------------------------------------------------------------------------
1623 // Safer(?), slower version.
1624 void gld_TexImage2D_DX7(
1628 GLint internalFormat,
1634 const GLvoid *pixels,
1635 const struct gl_pixelstore_attrib *packing,
1636 struct gl_texture_object *tObj,
1637 struct gl_texture_image *texImage)
1639 GLD_context *gldCtx = GLD_GET_CONTEXT(ctx);
1640 GLD_driver_dx7 *gld = GLD_GET_DX7_DRIVER(gldCtx);
1642 IDirect3DTexture8 *pTex;
1643 IDirect3DSurface8 *pSurface;
1646 GLint texelBytes = 4;
1649 if (!tObj || !texImage)
1653 _gldAllocateTexture(ctx, tObj, texImage);
1656 pTex = (IDirect3DTexture8*)tObj->DriverData;
1658 return; // Texture has not been created
1659 if (level >= IDirect3DTexture8_GetLevelCount(pTex))
1660 return; // Level does not exist
1661 hr = IDirect3DTexture8_GetSurfaceLevel(pTex, level, &pSurface);
1663 return; // Surface level doesn't exist (or just a plain error)
1665 tempImage = MALLOC(width * height * texelBytes);
1667 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glTexImage2D");
1668 IDirect3DSurface8_Release(pSurface);
1671 // unpack image, apply transfer ops and store in tempImage
1672 texImage->TexFormat->StoreImage(ctx, 2, texImage->Format,
1673 &_mesa_texformat_argb8888, // dest format
1675 width, height, 1, 0, 0, 0,
1677 0, // dstImageStride
1678 format, type, pixels, packing);
1680 SetRect(&rcSrcRect, 0, 0, width, height);
1681 D3DXLoadSurfaceFromMemory(
1694 IDirect3DSurface8_Release(pSurface);
1698 //---------------------------------------------------------------------------
1700 // Faster, more efficient version.
1701 // Copies subimage straight to dest texture
1702 void gld_TexImage2D_DX7(
1706 GLint internalFormat
,
1712 const GLvoid
*pixels
,
1713 const struct gl_pixelstore_attrib
*packing
,
1714 struct gl_texture_object
*tObj
,
1715 struct gl_texture_image
*texImage
)
1717 GLD_context
*gldCtx
= GLD_GET_CONTEXT(ctx
);
1718 GLD_driver_dx7
*gld
= GLD_GET_DX7_DRIVER(gldCtx
);
1720 IDirectDrawSurface7
*pTex
= NULL
;
1721 IDirectDrawSurface7
*pSurface
= NULL
;
1723 DDSURFACEDESC2 ddsd
;
1727 if (!tObj
|| !texImage
)
1731 // Test for input alpha data with non-alpha internalformat
1732 if (((internalFormat
==3) || (internalFormat
==GL_RGB
)) && (format
==GL_RGBA
)) {
1733 // Input format has alpha, but a non-alpha format has been requested.
1734 texImage
->IntFormat
= GL_RGBA
;
1735 internalFormat
= GL_RGBA
;
1739 _gldAllocateTexture(ctx
, tObj
, texImage
);
1742 pTex
= (IDirectDrawSurface7
*)tObj
->DriverData
;
1745 return; // Texture has not been created
1750 ddsd
.dwSize
= sizeof(ddsd
);
1751 _GLD_DX7_TEX(GetSurfaceDesc(pTex
, &ddsd
));
1752 if ((level
> 0) && (level
>= ddsd
.dwMipMapCount
))
1753 return; // Level does not exist
1754 ZeroMemory(&ddsCaps
, sizeof(ddsCaps
));
1755 for (i
=0; i
<level
; i
++) {
1756 ddsCaps
.dwCaps
= DDSCAPS_TEXTURE
| DDSCAPS_MIPMAP
;
1757 hr
= IDirectDrawSurface7_GetAttachedSurface(
1761 if (SUCCEEDED(hr
)) {
1762 IDirectDrawSurface7_Release(pSurface
);
1769 // Lock all of surface
1770 ddsd
.dwSize
= sizeof(ddsd
);
1771 hr
= IDirectDrawSurface7_Lock(pSurface
, NULL
, &ddsd
, 0, 0);
1773 IDirectDrawSurface7_Release(pSurface
);
1777 // unpack image, apply transfer ops and store directly in texture
1778 texImage
->TexFormat
->StoreImage(
1782 //_gldMesaFormatForD3DFormat(d3dsd.Format),
1783 _gldMesaFormatForD3DFormat(_gldD3DXFormatFromSurface(pSurface
)),
1785 width
, height
, 1, 0, 0, 0,
1787 0, // dstImageStride
1788 format
, type
, pixels
, packing
);
1790 IDirectDrawSurface7_Unlock(pSurface
, NULL
);
1793 //---------------------------------------------------------------------------
1795 void gld_TexImage1D_DX7(GLcontext
*ctx
, GLenum target
, GLint level
,
1796 GLint internalFormat
,
1797 GLint width
, GLint border
,
1798 GLenum format
, GLenum type
, const GLvoid
*pixels
,
1799 const struct gl_pixelstore_attrib
*packing
,
1800 struct gl_texture_object
*texObj
,
1801 struct gl_texture_image
*texImage
)
1803 // A 1D texture is a 2D texture with a height of zero
1804 gld_TexImage2D_DX7(ctx
, target
, level
, internalFormat
, width
, 1, border
, format
, type
, pixels
, packing
, texObj
, texImage
);
1807 //---------------------------------------------------------------------------
1810 void gld_TexSubImage2D( GLcontext *ctx, GLenum target, GLint level,
1811 GLint xoffset, GLint yoffset,
1812 GLsizei width, GLsizei height,
1813 GLenum format, GLenum type,
1814 const GLvoid *pixels,
1815 const struct gl_pixelstore_attrib *packing,
1816 struct gl_texture_object *tObj,
1817 struct gl_texture_image *texImage )
1820 IDirect3DTexture8 *pTex;
1821 IDirect3DSurface8 *pSurface;
1822 D3DFORMAT d3dFormat;
1824 GLint texelBytes = 4;
1829 if (!tObj || !texImage)
1832 pTex = (IDirect3DTexture8*)tObj->DriverData;
1834 return; // Texture has not been created
1835 if (level >= _GLD_DX8_TEX(GetLevelCount(pTex))
1836 return; // Level does not exist
1837 hr = _GLD_DX8_TEX(GetSurfaceLevel(pTex, level, &pSurface);
1839 return; // Surface level doesn't exist (or just a plain error)
1841 d3dFormat = _gldGLFormatToD3DFormat(texImage->Format);
1842 tempImage = MALLOC(width * height * texelBytes);
1844 _mesa_error(ctx, GL_OUT_OF_MEMORY, "glTexImage2D");
1845 IDirect3DSurface8_Release(pSurface);
1849 // unpack image, apply transfer ops and store in tempImage
1850 texImage->TexFormat->StoreImage(ctx, 2, texImage->Format,
1851 &_mesa_texformat_argb8888, // dest format
1853 width, height, 1, 0, 0, 0,
1855 0, // dstImageStride
1856 format, type, pixels, packing);
1858 // Source rectangle is whole of input image
1859 SetRect(&rcSrcRect, 0, 0, width, height);
1861 // Dest rectangle must be offset to dest image
1862 SetRect(&rcDstRect, 0, 0, width, height);
1863 OffsetRect(&rcDstRect, xoffset, yoffset);
1865 D3DXLoadSurfaceFromMemory(
1878 IDirect3DSurface8_Release(pSurface);
1882 //---------------------------------------------------------------------------
1884 // Faster, more efficient version.
1885 // Copies subimage straight to dest texture
1886 void gld_TexSubImage2D_DX7( GLcontext
*ctx
, GLenum target
, GLint level
,
1887 GLint xoffset
, GLint yoffset
,
1888 GLsizei width
, GLsizei height
,
1889 GLenum format
, GLenum type
,
1890 const GLvoid
*pixels
,
1891 const struct gl_pixelstore_attrib
*packing
,
1892 struct gl_texture_object
*tObj
,
1893 struct gl_texture_image
*texImage
)
1895 GLD_context
*gldCtx
= GLD_GET_CONTEXT(ctx
);
1896 GLD_driver_dx7
*gld
= GLD_GET_DX7_DRIVER(gldCtx
);
1898 IDirectDrawSurface7
*pTex
;
1899 IDirectDrawSurface7
*pSurface
;
1902 DDSURFACEDESC2 ddsd
;
1906 if (!tObj
|| !texImage
)
1909 pTex
= (IDirectDrawSurface7
*)tObj
->DriverData
;
1911 return; // Texture has not been created
1915 ddsd
.dwSize
= sizeof(ddsd
);
1916 _GLD_DX7_TEX(GetSurfaceDesc(pTex
, &ddsd
));
1917 if ((level
> 0) && (level
>= ddsd
.dwMipMapCount
))
1918 return; // Level does not exist
1920 ZeroMemory(&ddsCaps
, sizeof(ddsCaps
));
1922 for (i
=0; i
<level
; i
++) {
1923 ddsCaps
.dwCaps
= DDSCAPS_TEXTURE
| DDSCAPS_MIPMAP
;
1924 hr
= IDirectDrawSurface7_GetAttachedSurface(
1929 IDirectDrawSurface7_Release(pSurface
);
1935 // Dest rectangle must be offset to dest image
1936 SetRect(&rcDstRect
, 0, 0, width
, height
);
1937 OffsetRect(&rcDstRect
, xoffset
, yoffset
);
1939 // Lock sub-rect of surface
1940 hr
= IDirectDrawSurface7_Lock(pSurface
, &rcDstRect
, &ddsd
, 0, 0);
1942 IDirectDrawSurface7_Release(pSurface
);
1946 // unpack image, apply transfer ops and store directly in texture
1947 texImage
->TexFormat
->StoreImage(ctx
, 2, texImage
->Format
,
1948 _gldMesaFormatForD3DFormat(_gldD3DXFormatFromSurface(pSurface
)),
1951 0, 0, 0, // NOTE: d3dLockedRect.pBits is already offset!!!
1953 0, // dstImageStride
1954 format
, type
, pixels
, packing
);
1957 IDirectDrawSurface7_Unlock(pSurface
, &rcDstRect
);
1959 __except(EXCEPTION_EXECUTE_HANDLER
) {
1964 //---------------------------------------------------------------------------
1966 void gld_TexSubImage1D_DX7( GLcontext
*ctx
, GLenum target
, GLint level
,
1967 GLint xoffset
, GLsizei width
,
1968 GLenum format
, GLenum type
,
1969 const GLvoid
*pixels
,
1970 const struct gl_pixelstore_attrib
*packing
,
1971 struct gl_texture_object
*texObj
,
1972 struct gl_texture_image
*texImage
)
1974 gld_TexSubImage2D_DX7(ctx
, target
, level
, xoffset
, 0, width
, 1, format
, type
, pixels
, packing
, texObj
, texImage
);
1977 //---------------------------------------------------------------------------
1979 void gld_DeleteTexture_DX7(
1981 struct gl_texture_object
*tObj
)
1983 GLD_context
*gld
= (GLD_context
*)(ctx
->DriverCtx
);
1988 IDirectDrawSurface7
*pTex
= (IDirectDrawSurface7
*)tObj
->DriverData
;
1990 /* // Make sure texture is not bound to a stage before releasing it
1991 for (int i=0; i<MAX_TEXTURE_UNITS; i++) {
1992 if (gld->CurrentTexture[i] == pTex) {
1993 gld->pDev->SetTexture(i, NULL);
1994 gld->CurrentTexture[i] = NULL;
1997 _GLD_DX7_TEX(Release(pTex
));
1998 tObj
->DriverData
= NULL
;
2003 __except(EXCEPTION_EXECUTE_HANDLER
) {
2008 //---------------------------------------------------------------------------
2010 __inline
void _gldSetColorOps(
2011 const GLD_driver_dx7
*gld
,
2014 D3DTEXTUREOP ColorOp
,
2017 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_COLORARG1
, ColorArg1
));
2018 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_COLOROP
, ColorOp
));
2019 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_COLORARG2
, ColorArg2
));
2022 //---------------------------------------------------------------------------
2024 __inline
void _gldSetAlphaOps(
2025 const GLD_driver_dx7
*gld
,
2028 D3DTEXTUREOP AlphaOp
,
2031 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_ALPHAARG1
, AlphaArg1
));
2032 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_ALPHAOP
, AlphaOp
));
2033 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_ALPHAARG2
, AlphaArg2
));
2036 //---------------------------------------------------------------------------
2038 void gldUpdateTextureUnit(
2043 GLD_context
*gldCtx
= GLD_GET_CONTEXT(ctx
);
2044 GLD_driver_dx7
*gld
= GLD_GET_DX7_DRIVER(gldCtx
);
2046 D3DTEXTUREMINFILTER minfilter
;
2047 D3DTEXTUREMIPFILTER mipfilter
;
2051 GLD_texenv
*pTexenv
;
2053 // NOTE: If bPassThrough is FALSE then texture stage can be
2054 // disabled otherwise it must pass-through it's current fragment.
2056 const struct gl_texture_unit
*pUnit
= &ctx
->Texture
.Unit
[unit
];
2057 const struct gl_texture_object
*tObj
= pUnit
->_Current
;
2059 IDirectDrawSurface7
*pTex
= NULL
;
2061 pTex
= (IDirectDrawSurface7
*)tObj
->DriverData
;
2066 // Enable texturing if unit is enabled and a valid D3D texture exists
2067 // Mesa 5: TEXTUREn_x altered to TEXTURE_nD_BIT
2068 //if (pTex && (pUnit->Enabled & (TEXTURE0_1D | TEXTURE0_2D))) {
2069 if (pTex
&& (pUnit
->_ReallyEnabled
& (TEXTURE_1D_BIT
| TEXTURE_2D_BIT
))) {
2071 _GLD_DX7_DEV(SetTexture(gld
->pDev
, unit
, pTex
));
2073 // Disable texturing, then return
2074 _GLD_DX7_DEV(SetTexture(gld
->pDev
, unit
, NULL
));
2076 _gldSetColorOps(gld
, unit
, D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_DIFFUSE
);
2077 _gldSetAlphaOps(gld
, unit
, D3DTA_TEXTURE
, D3DTOP_SELECTARG2
, D3DTA_DIFFUSE
);
2079 _gldSetColorOps(gld
, unit
, D3DTA_TEXTURE
, D3DTOP_DISABLE
, D3DTA_DIFFUSE
);
2080 _gldSetAlphaOps(gld
, unit
, D3DTA_TEXTURE
, D3DTOP_DISABLE
, D3DTA_DIFFUSE
);
2085 // Texture parameters
2086 _gldConvertMinFilter(tObj
->MinFilter
, &minfilter
, &mipfilter
);
2087 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_MINFILTER
, minfilter
));
2088 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_MIPFILTER
, mipfilter
));
2089 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_MAGFILTER
, _gldConvertMagFilter(tObj
->MagFilter
)));
2090 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_ADDRESSU
, _gldConvertWrap(tObj
->WrapS
)));
2091 _GLD_DX7_DEV(SetTextureStageState(gld
->pDev
, unit
, D3DTSS_ADDRESSV
, _gldConvertWrap(tObj
->WrapT
)));
2094 _GLD_DX7_TEX(SetPriority(pTex
, (DWORD
)(tObj
->Priority
*65535.0f
)));
2096 // Texture environment
2097 // TODO: Examine input texture for alpha and use specific alpha/non-alpha ops.
2098 // See Page 355 of the Red Book.
2099 BaseFormat
= _gldDecodeBaseFormat(pTex
);
2101 switch (BaseFormat
) {
2113 switch (pUnit
->EnvMode
) {
2125 // Unsupported by DX7
2126 // dwColorArg0 = D3DCOLOR_COLORVALUE(pUnit->EnvColor[0], pUnit->EnvColor[1], pUnit->EnvColor[2], pUnit->EnvColor[3]);
2127 // _GLD_DX7_DEV(SetTextureStageState(gld->pDev, unit, D3DTSS_COLORARG0, dwColorArg0));
2128 // gldLogMessage(GLDLOG_WARN, "GL_BLEND\n");
2135 pTexenv
= (GLD_texenv
*)&gldTexEnv
[iTexEnv
];
2136 _gldSetColorOps(gld
, unit
, pTexenv
->ColorArg1
, pTexenv
->ColorOp
, pTexenv
->ColorArg2
);
2137 _gldSetAlphaOps(gld
, unit
, pTexenv
->AlphaArg1
, pTexenv
->AlphaOp
, pTexenv
->AlphaArg2
);
2140 __except(EXCEPTION_EXECUTE_HANDLER
) {
2145 //---------------------------------------------------------------------------
2147 void gld_NEW_TEXTURE_DX7(
2150 // TODO: Support for three (ATI Radeon) or more (nVidia GeForce3) texture units
2156 return; // Sanity check
2158 if (ctx
->Const
.MaxTextureUnits
== 1) {
2159 gldUpdateTextureUnit(ctx
, 0, TRUE
);
2164 // NOTE: THE FOLLOWING RELATES TO TWO TEXTURE UNITS, AND TWO ONLY!!
2167 // Mesa 5: Texture Units altered
2168 bUnit0Enabled
= (ctx
->Texture
.Unit
[0]._ReallyEnabled
& (TEXTURE_1D_BIT
| TEXTURE_2D_BIT
)) ? TRUE
: FALSE
;
2169 bUnit1Enabled
= (ctx
->Texture
.Unit
[1]._ReallyEnabled
& (TEXTURE_1D_BIT
| TEXTURE_2D_BIT
)) ? TRUE
: FALSE
;
2171 // If Unit0 is disabled and Unit1 is enabled then we must pass-though
2172 gldUpdateTextureUnit(ctx
, 0, (!bUnit0Enabled
&& bUnit1Enabled
) ? TRUE
: FALSE
);
2173 // We can always disable the last texture unit
2174 gldUpdateTextureUnit(ctx
, 1, FALSE
);
2178 // Find out whether device supports current renderstates
2179 GLD_context
*gldCtx
= GLD_GET_CONTEXT(ctx
);
2180 GLD_driver_dx7
*gld
= GLD_GET_DX7_DRIVER(gldCtx
);
2183 _GLD_DX7_DEV(ValidateDevice(gld
->pDev
, &dwPasses
));
2186 gldLogError(GLDLOG_ERROR
, "ValidateDevice failed", hr
);
2189 if (dwPasses
!= 1) {
2190 gldLogMessage(GLDLOG_ERROR
, "ValidateDevice: Can't do in one pass\n");
2196 //---------------------------------------------------------------------------