More comm tests.
[wine/wine64.git] / dlls / wined3d / basetexture.c
blobd309ec6a4813b02464f70e29cded4e779a0d3fbb
1 /*
2 * IWineD3DBaseTexture Implementation
4 * Copyright 2002-2004 Jason Edmeades
5 * Copyright 2002-2004 Raphael Junqueira
6 * Copyright 2005 Oliver Stieber
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with this library; if not, write to the Free Software
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
23 #include "config.h"
24 #include "wined3d_private.h"
26 WINE_DEFAULT_DEBUG_CHANNEL(d3d_texture);
27 #define GLINFO_LOCATION ((IWineD3DImpl *)(((IWineD3DDeviceImpl *)This->resource.wineD3DDevice)->wineD3D))->gl_info
29 static const Wined3dTextureStateMap textureObjectSamplerStates[] = {
30 {WINED3DSAMP_ADDRESSU, WINED3DSAMP_ADDRESSU},
31 {WINED3DSAMP_ADDRESSV, WINED3DSAMP_ADDRESSV},
32 {WINED3DSAMP_ADDRESSW, WINED3DSAMP_ADDRESSW},
33 /* NOTE: Sometimes it's a good idea to disable the setting of border colour, e.g. Axis and Allies */
34 {WINED3DSAMP_BORDERCOLOR, WINED3DFUNC_NOTSUPPORTED/* WINED3DSAMP_BORDERCOLOR */},
35 {WINED3DSAMP_MAGFILTER, WINED3DSAMP_MAGFILTER},
36 {WINED3DSAMP_MINFILTER, WINED3DSAMP_MINFILTER},
37 {WINED3DSAMP_MIPFILTER, WINED3DSAMP_MIPFILTER},
38 /* applies to the texture unit
39 WINED3DSAMP_MIPMAPLODBIAS, WINED3DSAMP_MIPMAPLODBIAS,
41 {WINED3DSAMP_MAXMIPLEVEL, WINED3DSAMP_MAXMIPLEVEL},
42 #if 0
43 {WINED3DSAMP_MAXANISOTROPY, GL_SUPPORTED(EXT_TEXTURE_FILTER_ANISOTROPIC) ? WINED3DSAMP_MAXANISOTROPY : WINED3DFUNC_NOTSUPPORTED},
44 #else
45 {WINED3DSAMP_MAXANISOTROPY, WINED3DSAMP_MAXANISOTROPY},
46 #endif
47 {WINED3DSAMP_SRGBTEXTURE, WINED3DFUNC_UNIMPLEMENTED},
48 {WINED3DSAMP_ELEMENTINDEX, WINED3DFUNC_UNIMPLEMENTED},
49 {WINED3DSAMP_DMAPOFFSET, WINED3DFUNC_UNIMPLEMENTED},
50 {-1, 0}
53 static const Wined3dTextureStateMap textureObjectTextureStates[] = {
54 {WINED3DTSS_ADDRESSW , WINED3DTSS_ADDRESSW},
55 {-1, 0}
58 /* *******************************************
59 IWineD3DBaseTexture IUnknown parts follow
60 ******************************************* */
61 HRESULT WINAPI IWineD3DBaseTextureImpl_QueryInterface(IWineD3DBaseTexture *iface, REFIID riid, LPVOID *ppobj)
63 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
64 TRACE("(%p)->(%s,%p)\n",This,debugstr_guid(riid),ppobj);
65 /* FIXME: This needs to extend an IWineD3DBaseObject */
66 if (IsEqualGUID(riid, &IID_IUnknown)
67 || IsEqualGUID(riid, &IID_IWineD3DResource)
68 || IsEqualGUID(riid, &IID_IWineD3DBaseTexture)) {
69 IUnknown_AddRef(iface);
70 *ppobj = This;
71 return D3D_OK;
73 return E_NOINTERFACE;
76 ULONG WINAPI IWineD3DBaseTextureImpl_AddRef(IWineD3DBaseTexture *iface) {
77 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
78 ULONG ref = InterlockedIncrement(&This->resource.ref);
80 TRACE("(%p) : AddRef increasing from %ld\n", This,ref - 1);
81 return ref;
84 ULONG WINAPI IWineD3DBaseTextureImpl_Release(IWineD3DBaseTexture *iface) {
85 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
86 ULONG ref = InterlockedDecrement(&This->resource.ref);
87 TRACE("(%p) : Releasing from %ld\n", This, ref + 1);
88 if (ref == 0) {
89 IWineD3DBaseTextureImpl_CleanUp(iface);
90 HeapFree(GetProcessHeap(), 0, This);
92 return ref;
95 /* class static */
96 void IWineD3DBaseTextureImpl_CleanUp(IWineD3DBaseTexture *iface) {
97 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
98 TRACE("(%p) : textureName(%d)\n", This, This->baseTexture.textureName);
99 if (This->baseTexture.textureName != 0) {
100 ENTER_GL();
101 TRACE("(%p) : Deleting texture %d\n", This, This->baseTexture.textureName);
102 glDeleteTextures(1, &This->baseTexture.textureName);
103 LEAVE_GL();
105 IWineD3DResourceImpl_CleanUp((IWineD3DResource *)iface);
108 /* ****************************************************
109 IWineD3DBaseTexture IWineD3DResource parts follow
110 **************************************************** */
111 HRESULT WINAPI IWineD3DBaseTextureImpl_GetDevice(IWineD3DBaseTexture *iface, IWineD3DDevice** ppDevice) {
112 return IWineD3DResourceImpl_GetDevice((IWineD3DResource *)iface, ppDevice);
115 HRESULT WINAPI IWineD3DBaseTextureImpl_SetPrivateData(IWineD3DBaseTexture *iface, REFGUID refguid, CONST void* pData, DWORD SizeOfData, DWORD Flags) {
116 return IWineD3DResourceImpl_SetPrivateData((IWineD3DResource *)iface, refguid, pData, SizeOfData, Flags);
119 HRESULT WINAPI IWineD3DBaseTextureImpl_GetPrivateData(IWineD3DBaseTexture *iface, REFGUID refguid, void* pData, DWORD* pSizeOfData) {
120 return IWineD3DResourceImpl_GetPrivateData((IWineD3DResource *)iface, refguid, pData, pSizeOfData);
123 HRESULT WINAPI IWineD3DBaseTextureImpl_FreePrivateData(IWineD3DBaseTexture *iface, REFGUID refguid) {
124 return IWineD3DResourceImpl_FreePrivateData((IWineD3DResource *)iface, refguid);
127 DWORD WINAPI IWineD3DBaseTextureImpl_SetPriority(IWineD3DBaseTexture *iface, DWORD PriorityNew) {
128 return IWineD3DResourceImpl_SetPriority((IWineD3DResource *)iface, PriorityNew);
131 DWORD WINAPI IWineD3DBaseTextureImpl_GetPriority(IWineD3DBaseTexture *iface) {
132 return IWineD3DResourceImpl_GetPriority((IWineD3DResource *)iface);
135 void WINAPI IWineD3DBaseTextureImpl_PreLoad(IWineD3DBaseTexture *iface) {
136 return IWineD3DResourceImpl_PreLoad((IWineD3DResource *)iface);
139 D3DRESOURCETYPE WINAPI IWineD3DBaseTextureImpl_GetType(IWineD3DBaseTexture *iface) {
140 return IWineD3DResourceImpl_GetType((IWineD3DResource *)iface);
143 HRESULT WINAPI IWineD3DBaseTextureImpl_GetParent(IWineD3DBaseTexture *iface, IUnknown **pParent) {
144 return IWineD3DResourceImpl_GetParent((IWineD3DResource *)iface, pParent);
147 /* ******************************************************
148 IWineD3DBaseTexture IWineD3DBaseTexture parts follow
149 ****************************************************** */
151 /* There is no OpenGL equivilent of setLOD, getLOD, all they do it priortise testure loading
152 * so just pretend that they work unless something really needs a failure. */
153 DWORD WINAPI IWineD3DBaseTextureImpl_SetLOD(IWineD3DBaseTexture *iface, DWORD LODNew) {
154 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
156 if (This->resource.pool != D3DPOOL_MANAGED) {
157 return D3DERR_INVALIDCALL;
160 if(LODNew >= This->baseTexture.levels)
161 LODNew = This->baseTexture.levels - 1;
162 This->baseTexture.LOD = LODNew;
164 TRACE("(%p) : set bogus LOD to %d \n", This, This->baseTexture.LOD);
166 return This->baseTexture.LOD;
169 DWORD WINAPI IWineD3DBaseTextureImpl_GetLOD(IWineD3DBaseTexture *iface) {
170 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
172 if (This->resource.pool != D3DPOOL_MANAGED) {
173 return D3DERR_INVALIDCALL;
176 TRACE("(%p) : returning %d \n", This, This->baseTexture.LOD);
178 return This->baseTexture.LOD;
181 DWORD WINAPI IWineD3DBaseTextureImpl_GetLevelCount(IWineD3DBaseTexture *iface) {
182 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
183 TRACE("(%p) : returning %d\n", This, This->baseTexture.levels);
184 return This->baseTexture.levels;
187 HRESULT WINAPI IWineD3DBaseTextureImpl_SetAutoGenFilterType(IWineD3DBaseTexture *iface, D3DTEXTUREFILTERTYPE FilterType) {
188 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
190 if (!(This->baseTexture.usage & D3DUSAGE_AUTOGENMIPMAP)) {
191 TRACE("(%p) : returning invalid call\n", This);
192 return D3DERR_INVALIDCALL;
194 This->baseTexture.filterType = FilterType;
195 TRACE("(%p) : \n", This);
196 return D3D_OK;
199 D3DTEXTUREFILTERTYPE WINAPI IWineD3DBaseTextureImpl_GetAutoGenFilterType(IWineD3DBaseTexture *iface) {
200 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
201 FIXME("(%p) : stub\n", This);
202 if (!(This->baseTexture.usage & D3DUSAGE_AUTOGENMIPMAP)) {
203 return D3DTEXF_NONE;
205 return This->baseTexture.filterType;
206 return D3DTEXF_LINEAR; /* default */
209 void WINAPI IWineD3DBaseTextureImpl_GenerateMipSubLevels(IWineD3DBaseTexture *iface) {
210 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
211 /* TODO: implement filters using GL_SGI_generate_mipmaps http://oss.sgi.com/projects/ogl-sample/registry/SGIS/generate_mipmap.txt */
212 FIXME("(%p) : stub\n", This);
213 return ;
216 /* Internal function, No d3d mapping */
217 BOOL WINAPI IWineD3DBaseTextureImpl_SetDirty(IWineD3DBaseTexture *iface, BOOL dirty) {
218 BOOL old;
219 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
220 old = This->baseTexture.dirty;
221 This->baseTexture.dirty = dirty;
222 return old;
225 BOOL WINAPI IWineD3DBaseTextureImpl_GetDirty(IWineD3DBaseTexture *iface) {
226 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
227 return This->baseTexture.dirty;
230 HRESULT WINAPI IWineD3DBaseTextureImpl_BindTexture(IWineD3DBaseTexture *iface) {
231 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
232 HRESULT hr = D3D_OK;
233 UINT textureDimensions;
234 BOOL isNewTexture = FALSE;
235 TRACE("(%p) : About to bind texture\n", This);
237 textureDimensions = IWineD3DBaseTexture_GetTextureDimensions(iface);
238 ENTER_GL();
239 #if 0 /* TODO: context manager support */
240 IWineD3DContextManager_PushState(This->contextManager, textureDimensions, ENABLED, NOW /* make sure the state is applied now */);
241 #else
242 glEnable(textureDimensions);
243 #endif
245 /* Generate a texture name if we don't already have one */
246 if (This->baseTexture.textureName == 0) {
247 glGenTextures(1, &This->baseTexture.textureName);
248 checkGLcall("glGenTextures");
249 TRACE("Generated texture %d\n", This->baseTexture.textureName);
250 if (This->resource.pool == D3DPOOL_DEFAULT) {
251 /* Tell opengl to try and keep this texture in video ram (well mostly) */
252 GLclampf tmp;
253 tmp = 0.9f;
254 glPrioritizeTextures(1, &This->baseTexture.textureName, &tmp);
257 /* Initilise the state of the texture object
258 to the openGL defaults, not the directx defaults */
259 This->baseTexture.states[WINED3DTEXSTA_ADDRESSU] = D3DTADDRESS_WRAP;
260 This->baseTexture.states[WINED3DTEXSTA_ADDRESSV] = D3DTADDRESS_WRAP;
261 This->baseTexture.states[WINED3DTEXSTA_ADDRESSW] = D3DTADDRESS_WRAP;
262 This->baseTexture.states[WINED3DTEXSTA_BORDERCOLOR] = 0;
263 This->baseTexture.states[WINED3DTEXSTA_MAGFILTER] = D3DTEXF_POINT;
264 This->baseTexture.states[WINED3DTEXSTA_MINFILTER] = D3DTEXF_POINT;
265 This->baseTexture.states[WINED3DTEXSTA_MIPFILTER] = D3DTEXF_NONE;
266 This->baseTexture.states[WINED3DTEXSTA_MAXMIPLEVEL] = 0;
267 This->baseTexture.states[WINED3DTEXSTA_MAXANISOTROPY] = 0;
268 This->baseTexture.states[WINED3DTEXSTA_SRGBTEXTURE] = 0;
269 This->baseTexture.states[WINED3DTEXSTA_ELEMENTINDEX] = 0;
270 This->baseTexture.states[WINED3DTEXSTA_DMAPOFFSET] = 0;
271 This->baseTexture.states[WINED3DTEXSTA_TSSADDRESSW] = D3DTADDRESS_WRAP;
272 IWineD3DBaseTexture_SetDirty(iface, TRUE);
273 isNewTexture = TRUE;
276 /* Bind the texture */
277 if (This->baseTexture.textureName != 0) {
278 /* Always need to reset the number of mipmap levels when rebinding as it is
279 a property of the active texture unit, and another texture may have set it
280 to a different value */
281 if (This->baseTexture.levels > 1) {
282 TRACE("Setting GL_TEXTURE_MAX_LEVEL to %d\n", This->baseTexture.levels - 1);
283 glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.levels - 1);
284 checkGLcall("glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.levels)");
285 } else {
286 glTexParameteri(textureDimensions, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
288 glBindTexture(textureDimensions, This->baseTexture.textureName);
289 checkGLcall("glBindTexture");
290 if (isNewTexture || (TRUE && This->baseTexture.levels >1)) {
291 /* For a new texture we have to set the textures levels after binding the texture,
292 * in theory this is all we should ever have to dom, but because ATI's drivers are broken we
293 * also need to set the texture dimensins before the texture is is set */
294 TRACE("Setting GL_TEXTURE_MAX_LEVEL to %d\n", This->baseTexture.levels - 1);
295 glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.levels - 1);
296 checkGLcall("glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.levels)");
297 } else {
298 TRACE("Setting GL_TEXTURE_MAX_LEVEL to %d\n", This->baseTexture.levels - 1);
299 glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.levels - 1);
300 checkGLcall("glTexParameteri(textureDimensions, GL_TEXTURE_MAX_LEVEL, This->baseTexture.levels)");
303 } else { /* this only happened if we've run out of openGL textures */
304 WARN("This texture doesn't have an openGL texture assigned to it\n");
305 hr = D3DERR_INVALIDCALL;
308 LEAVE_GL();
309 return hr;
312 HRESULT WINAPI IWineD3DBaseTextureImpl_UnBindTexture(IWineD3DBaseTexture *iface) {
313 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
314 UINT textureDimensions;
316 TRACE("(%p) : About to bind texture\n", This);
317 textureDimensions = IWineD3DBaseTexture_GetTextureDimensions(iface);
319 ENTER_GL();
321 glBindTexture(textureDimensions, 0);
322 #if 0 /* TODO: context manager support */
323 IWineD3DContextManager_PopState(This->contextManager, textureDimensions, ENABLED, NOW /* make sure the state is applied now */);
324 #else
325 glDisable(textureDimensions);
326 #endif
328 LEAVE_GL();
329 return D3D_OK;
332 UINT WINAPI IWineD3DBaseTextureImpl_GetTextureDimensions(IWineD3DBaseTexture *iface){
333 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
334 FIXME("(%p) : This shouldn't be called\n", This);
335 return D3D_OK;
338 static inline GLenum warpLookupType(WINED3DSAMPLERSTATETYPE Type) {
339 switch(Type) {
340 case WINED3DSAMP_ADDRESSU:
341 return GL_TEXTURE_WRAP_S;
342 case WINED3DSAMP_ADDRESSV:
343 return GL_TEXTURE_WRAP_T;
344 case WINED3DSAMP_ADDRESSW:
345 return GL_TEXTURE_WRAP_R;
346 default:
347 FIXME("Unexpected warp type %d\n", Type);
348 return 0;
352 void WINAPI IWineD3DBaseTextureImpl_ApplyStateChanges(IWineD3DBaseTexture *iface,
353 const DWORD textureStates[WINED3D_HIGHEST_TEXTURE_STATE + 1],
354 const DWORD samplerStates[WINED3D_HIGHEST_SAMPLER_STATE + 1]) {
355 IWineD3DBaseTextureImpl *This = (IWineD3DBaseTextureImpl *)iface;
356 int i;
357 DWORD *state = This->baseTexture.states;
358 GLint textureDimensions = IWineD3DBaseTexture_GetTextureDimensions(iface);
359 IWineD3DBaseTexture_PreLoad(iface);
360 /* run through a couple of loops and apply and states that are different */
361 /* this will reduce the number of texture state changes to an absolute minimum
362 for multi-parameter states we pickup the first one that changes, work out the correct values for the other states
363 and set all the states that we've just applied to their new values */
365 for (i = 0 ;textureObjectSamplerStates[i].state != -1; i++) {
366 if (*state != samplerStates[textureObjectSamplerStates[i].state]) {
367 /* apply the state */
368 TRACE("(%p) : Changing state %u from %ld to %ld \n",This, i, *state , samplerStates[textureObjectSamplerStates[i].state]);
369 switch (textureObjectSamplerStates[i].function) {
370 case WINED3DSAMP_ADDRESSU:
371 case WINED3DSAMP_ADDRESSV: /* fall through */
372 case WINED3DSAMP_ADDRESSW: /* fall through */
373 *state = samplerStates[textureObjectSamplerStates[i].state];
374 if (*state < minLookup[WINELOOKUP_WARPPARAM] || *state > maxLookup[WINELOOKUP_WARPPARAM]) {
375 FIXME("Unrecognized or unsupported D3DTADDRESS_* value %ld, state %d\n", *state, textureObjectSamplerStates[i].function);
376 } else {
377 GLint wrapParm = stateLookup[WINELOOKUP_WARPPARAM][*state - minLookup[WINELOOKUP_WARPPARAM]];
378 TRACE("Setting WRAP_R to %d for %x\n", wrapParm, textureDimensions);
379 glTexParameteri(textureDimensions, warpLookupType(textureObjectSamplerStates[i].function), wrapParm);
380 checkGLcall("glTexParameteri(..., GL_TEXTURE_WRAP_R, wrapParm)");
382 break;
383 case WINED3DSAMP_BORDERCOLOR:
385 float col[4];
386 *state = samplerStates[textureObjectSamplerStates[i].state];
387 D3DCOLORTOGLFLOAT4(*state, col);
388 TRACE("Setting border color for %u to %lx\n", textureDimensions, *state);
389 glTexParameterfv(textureDimensions, GL_TEXTURE_BORDER_COLOR, &col[0]);
390 checkGLcall("glTexParameteri(..., GL_TEXTURE_BORDER_COLOR, ...)");
392 break;
393 case WINED3DSAMP_MAGFILTER:
395 GLint glValue;
396 *state = samplerStates[textureObjectSamplerStates[i].state];
397 if (*state < minLookup[WINELOOKUP_MAGFILTER] || *state > maxLookup[WINELOOKUP_MAGFILTER]) {
398 FIXME("Unrecognized or unsupported MAGFILTER* value %ld, state %d\n", *state, textureObjectSamplerStates[i].function);
400 glValue = stateLookup[WINELOOKUP_MAGFILTER][*state - minLookup[WINELOOKUP_MAGFILTER]];
401 TRACE("ValueMAG=%ld setting MAGFILTER to %x\n", *state, glValue);
402 glTexParameteri(textureDimensions, GL_TEXTURE_MAG_FILTER, glValue);
403 /* We need to reset the Aniotropic filtering state when we change the mag filter to D3DTEXF_ANISOTROPIC (this seems a bit weird, check the documentataion to see how it should be switched off. */
404 if (GL_SUPPORT(EXT_TEXTURE_FILTER_ANISOTROPIC) && D3DTEXF_ANISOTROPIC == *state) {
405 glTexParameteri(textureDimensions, GL_TEXTURE_MAX_ANISOTROPY_EXT, samplerStates[WINED3DSAMP_MAXANISOTROPY]);
408 break;
410 case WINED3DSAMP_MINFILTER:
411 This->baseTexture.states[WINED3DTEXSTA_MIPFILTER] = samplerStates[WINED3DSAMP_MIPFILTER];
412 case WINED3DSAMP_MIPFILTER: /* fall through */
414 GLint glValue;
415 *state = samplerStates[textureObjectSamplerStates[i].state];
416 if (This->baseTexture.states[WINED3DTEXSTA_MINFILTER] < D3DTEXF_NONE ||
417 This->baseTexture.states[WINED3DTEXSTA_MIPFILTER] < D3DTEXF_NONE ||
418 This->baseTexture.states[WINED3DTEXSTA_MINFILTER] > D3DTEXF_ANISOTROPIC ||
419 This->baseTexture.states[WINED3DTEXSTA_MIPFILTER] > D3DTEXF_LINEAR)
422 FIXME("Unrecognized or unsupported D3DSAMP_MINFILTER value %ld, state %d D3DSAMP_MIPFILTER value %ld, state %d\n",
423 This->baseTexture.states[WINED3DTEXSTA_MINFILTER],
424 textureObjectSamplerStates[WINED3DTEXSTA_MINFILTER].function,
425 This->baseTexture.states[WINED3DTEXSTA_MIPFILTER],
426 textureObjectSamplerStates[WINED3DTEXSTA_MIPFILTER].function);
428 glValue = minMipLookup[min(max(This->baseTexture.states[WINED3DTEXSTA_MINFILTER],D3DTEXF_NONE), D3DTEXF_ANISOTROPIC)]
429 [min(max(This->baseTexture.states[WINED3DTEXSTA_MIPFILTER],D3DTEXF_NONE), D3DTEXF_LINEAR)];
431 TRACE("ValueMIN=%ld, ValueMIP=%ld, setting MINFILTER to %x\n",
432 This->baseTexture.states[WINED3DTEXSTA_MINFILTER],
433 This->baseTexture.states[WINED3DTEXSTA_MIPFILTER], glValue);
434 glTexParameteri(textureDimensions, GL_TEXTURE_MIN_FILTER, glValue);
435 checkGLcall("glTexParameter GL_TEXTURE_MIN_FILTER, ...");
437 break;
438 case WINED3DSAMP_MAXMIPLEVEL:
439 *state = samplerStates[textureObjectSamplerStates[i].state];
441 * Not really the same, but the more apprioprate than nothing
443 glTexParameteri(textureDimensions, GL_TEXTURE_BASE_LEVEL, *state);
444 break;
445 case WINED3DSAMP_MAXANISOTROPY:
446 *state = samplerStates[textureObjectSamplerStates[i].state];
447 glTexParameteri(textureDimensions, GL_TEXTURE_MAX_ANISOTROPY_EXT, *state);
448 checkGLcall("glTexParameteri GL_TEXTURE_MAX_ANISOTROPY_EXT ...");
449 break;
450 case WINED3DFUNC_UNIMPLEMENTED: /* unimplemented */
451 TRACE("(%p) : stub\n", This);
452 *state = samplerStates[textureObjectSamplerStates[i].state];
453 break;
454 case WINED3DFUNC_NOTSUPPORTED: /* nop */
455 TRACE("(%p) : %s function is not supported by this opengl implementation\n", This, "unknown" /* TODO: replace with debug_blah... */);
456 *state = samplerStates[textureObjectSamplerStates[i].state];
457 break;
460 state++;
463 for(i = 0 ;textureObjectTextureStates[i].state != - 1; i++) {
464 if(*state != textureStates[textureObjectTextureStates[i].state] ) {
465 /* apply the state */
466 *state = textureStates[textureObjectTextureStates[i].state];
467 switch (textureObjectTextureStates[i].function) {
468 case WINED3DTSS_ADDRESSW:
469 /* I'm not sure what to do if this is set as well as ADDRESSW on the sampler, how do they interact together? */
470 break;
471 case WINED3DFUNC_UNIMPLEMENTED: /* unimplemented */
472 TRACE("(%p) : stub\n", This);
473 break;
474 case WINED3DFUNC_NOTSUPPORTED: /* nop */
475 TRACE("(%p) : function no supported by this opengl implementation\n", This);
476 break;
479 state++;
484 static const IWineD3DBaseTextureVtbl IWineD3DBaseTexture_Vtbl =
486 /* IUnknown */
487 IWineD3DBaseTextureImpl_QueryInterface,
488 IWineD3DBaseTextureImpl_AddRef,
489 IWineD3DBaseTextureImpl_Release,
490 /* IWineD3DResource */
491 IWineD3DBaseTextureImpl_GetParent,
492 IWineD3DBaseTextureImpl_GetDevice,
493 IWineD3DBaseTextureImpl_SetPrivateData,
494 IWineD3DBaseTextureImpl_GetPrivateData,
495 IWineD3DBaseTextureImpl_FreePrivateData,
496 IWineD3DBaseTextureImpl_SetPriority,
497 IWineD3DBaseTextureImpl_GetPriority,
498 IWineD3DBaseTextureImpl_PreLoad,
499 IWineD3DBaseTextureImpl_GetType,
500 /*IWineD3DBaseTexture*/
501 IWineD3DBaseTextureImpl_SetLOD,
502 IWineD3DBaseTextureImpl_GetLOD,
503 IWineD3DBaseTextureImpl_GetLevelCount,
504 IWineD3DBaseTextureImpl_SetAutoGenFilterType,
505 IWineD3DBaseTextureImpl_GetAutoGenFilterType,
506 IWineD3DBaseTextureImpl_GenerateMipSubLevels,
507 IWineD3DBaseTextureImpl_SetDirty,
508 IWineD3DBaseTextureImpl_GetDirty,
509 /* internal */
510 IWineD3DBaseTextureImpl_BindTexture,
511 IWineD3DBaseTextureImpl_UnBindTexture,
512 IWineD3DBaseTextureImpl_GetTextureDimensions,
513 IWineD3DBaseTextureImpl_ApplyStateChanges