- surface pool init fixes
[wine] / dlls / d3d8 / texture.c
1 /*
2  * IDirect3DTexture8 implementation
3  *
4  * Copyright 2002 Jason Edmeades
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  */
20
21 #include "config.h"
22
23 #include "windef.h"
24 #include "winbase.h"
25 #include "winuser.h"
26 #include "wingdi.h"
27 #include "wine/debug.h"
28
29 #include "d3d8_private.h"
30
31 WINE_DEFAULT_DEBUG_CHANNEL(d3d);
32
33 /* IDirect3DTexture8 IUnknown parts follow: */
34 HRESULT WINAPI IDirect3DTexture8Impl_QueryInterface(LPDIRECT3DTEXTURE8 iface,REFIID riid,LPVOID *ppobj)
35 {
36     ICOM_THIS(IDirect3DTexture8Impl,iface);
37     TRACE("(%p) : QueryInterface\n", This);
38     if (IsEqualGUID(riid, &IID_IUnknown)
39         || IsEqualGUID(riid, &IID_IDirect3DResource8)
40         || IsEqualGUID(riid, &IID_IDirect3DBaseTexture8)
41         || IsEqualGUID(riid, &IID_IDirect3DTexture8)) {
42         IDirect3DTexture8Impl_AddRef(iface);
43         *ppobj = This;
44         return D3D_OK;
45     }
46
47     WARN("(%p)->(%s,%p),not found\n",This,debugstr_guid(riid),ppobj);
48     return E_NOINTERFACE;
49 }
50
51 ULONG WINAPI IDirect3DTexture8Impl_AddRef(LPDIRECT3DTEXTURE8 iface) {
52     ICOM_THIS(IDirect3DTexture8Impl,iface);
53     TRACE("(%p) : AddRef from %ld\n", This, This->ref);
54     return ++(This->ref);
55 }
56
57 ULONG WINAPI IDirect3DTexture8Impl_Release(LPDIRECT3DTEXTURE8 iface) {
58     ICOM_THIS(IDirect3DTexture8Impl,iface);
59     ULONG ref = --This->ref;
60     int i;
61
62     TRACE("(%p) : ReleaseRef to %ld\n", This, This->ref);
63     if (ref == 0) {
64         for (i=0; i<This->levels; i++) {
65             if (This->surfaces[i] != NULL) {
66                 TRACE("(%p) : Releasing surface %p\n", This, This->surfaces[i]);
67                 IDirect3DSurface8Impl_Release((LPDIRECT3DSURFACE8) This->surfaces[i]);
68             }
69         }
70         HeapFree(GetProcessHeap(), 0, This);
71     }
72     return ref;
73 }
74
75 /* IDirect3DTexture8 IDirect3DResource8 Interface follow: */
76 HRESULT  WINAPI        IDirect3DTexture8Impl_GetDevice(LPDIRECT3DTEXTURE8 iface, IDirect3DDevice8** ppDevice) {
77     ICOM_THIS(IDirect3DTexture8Impl,iface);
78     TRACE("(%p) : returning %p\n", This, This->Device);
79     *ppDevice = (LPDIRECT3DDEVICE8) This->Device; 
80     /**
81      * Note  Calling this method will increase the internal reference count 
82      * on the IDirect3DDevice8 interface. 
83      */
84     IDirect3DDevice8Impl_AddRef(*ppDevice);
85     return D3D_OK;
86 }
87 HRESULT  WINAPI        IDirect3DTexture8Impl_SetPrivateData(LPDIRECT3DTEXTURE8 iface, REFGUID refguid, CONST void* pData, DWORD SizeOfData, DWORD Flags) {
88     ICOM_THIS(IDirect3DTexture8Impl,iface);
89     FIXME("(%p) : stub\n", This);    return D3D_OK;
90 }
91 HRESULT  WINAPI        IDirect3DTexture8Impl_GetPrivateData(LPDIRECT3DTEXTURE8 iface, REFGUID refguid, void* pData, DWORD* pSizeOfData) {
92     ICOM_THIS(IDirect3DTexture8Impl,iface);
93     FIXME("(%p) : stub\n", This);    return D3D_OK;
94 }
95 HRESULT  WINAPI        IDirect3DTexture8Impl_FreePrivateData(LPDIRECT3DTEXTURE8 iface, REFGUID refguid) {
96     ICOM_THIS(IDirect3DTexture8Impl,iface);
97     FIXME("(%p) : stub\n", This);    return D3D_OK;
98 }
99 DWORD    WINAPI        IDirect3DTexture8Impl_SetPriority(LPDIRECT3DTEXTURE8 iface, DWORD PriorityNew) {
100     ICOM_THIS(IDirect3DTexture8Impl,iface);
101     FIXME("(%p) : stub\n", This);    return D3D_OK;
102 }
103 DWORD    WINAPI        IDirect3DTexture8Impl_GetPriority(LPDIRECT3DTEXTURE8 iface) {
104     ICOM_THIS(IDirect3DTexture8Impl,iface);
105     FIXME("(%p) : stub\n", This);    return D3D_OK;
106 }
107 void     WINAPI        IDirect3DTexture8Impl_PreLoad(LPDIRECT3DTEXTURE8 iface) {
108     int i;
109     ICOM_THIS(IDirect3DTexture8Impl,iface);
110     TRACE("(%p) : About to load texture\n", This);
111     for (i=0; i<This->levels; i++) 
112     {
113
114         if (i==0 && This->surfaces[i]->textureName != 0 && This->Dirty == FALSE) {
115             glBindTexture(GL_TEXTURE_2D, This->surfaces[i]->textureName);
116             checkGLcall("glBindTexture");
117             TRACE("Texture %p (level %d) given name %d\n", This->surfaces[i], i, This->surfaces[i]->textureName);
118             /* No need to walk through all mip-map levels, since already all assigned */
119             i = This->levels;
120
121         } else {
122             if (i==0) {
123
124                 if (This->surfaces[i]->textureName == 0) {
125                     glGenTextures(1, &This->surfaces[i]->textureName);
126                     checkGLcall("glGenTextures");
127                     TRACE("Texture %p (level %d) given name %d\n", This->surfaces[i], i, This->surfaces[i]->textureName);
128                 }
129
130                 glBindTexture(GL_TEXTURE_2D, This->surfaces[i]->textureName);
131                 checkGLcall("glBindTexture");
132
133                 TRACE("Setting GL_TEXTURE_MAX_LEVEL to %d\n", This->levels-1);   
134                 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, This->levels-1);
135                 checkGLcall("glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, This->levels)");
136
137             }
138             TRACE("Calling glTexImage2D %x i=%d, intfmt=%x, w=%d, h=%d,0=%d, glFmt=%x, glType=%lx, Mem=%p\n",
139                   GL_TEXTURE_2D, i, fmt2glintFmt(This->format), This->surfaces[i]->myDesc.Width,
140                   This->surfaces[i]->myDesc.Height, 0, fmt2glFmt(This->format),fmt2glType(This->format),
141                   This->surfaces[i]->allocatedMemory);
142             glTexImage2D(GL_TEXTURE_2D, i,
143                          fmt2glintFmt(This->format),
144                          This->surfaces[i]->myDesc.Width,
145                          This->surfaces[i]->myDesc.Height,
146                          0,
147                          fmt2glFmt(This->format),
148                          fmt2glType(This->format),
149                          This->surfaces[i]->allocatedMemory
150                         );
151             checkGLcall("glTexImage2D");
152
153             /* Removed glTexParameterf now TextureStageStates are initialized at startup */
154             This->Dirty = FALSE;
155         }
156     }
157     return;
158 }
159 D3DRESOURCETYPE WINAPI IDirect3DTexture8Impl_GetType(LPDIRECT3DTEXTURE8 iface) {
160     ICOM_THIS(IDirect3DTexture8Impl,iface);
161     TRACE("(%p) : is %d \n", This, This->ResourceType);
162     return This->ResourceType;
163 }
164
165 /* IDirect3DTexture8 IDirect3DBaseTexture8 Interface follow: */
166 DWORD    WINAPI        IDirect3DTexture8Impl_SetLOD(LPDIRECT3DTEXTURE8 iface, DWORD LODNew) {
167     ICOM_THIS(IDirect3DTexture8Impl,iface);
168     FIXME("(%p) : stub\n", This);    return D3D_OK;
169 }
170 DWORD    WINAPI        IDirect3DTexture8Impl_GetLOD(LPDIRECT3DTEXTURE8 iface) {
171     ICOM_THIS(IDirect3DTexture8Impl,iface);
172     FIXME("(%p) : stub\n", This);    return D3D_OK;
173 }
174 DWORD    WINAPI        IDirect3DTexture8Impl_GetLevelCount(LPDIRECT3DTEXTURE8 iface) {
175     ICOM_THIS(IDirect3DTexture8Impl,iface);
176     TRACE("(%p) : returning %d\n", This, This->levels);
177     return This->levels;
178 }
179
180 /* IDirect3DTexture8 */
181 HRESULT  WINAPI        IDirect3DTexture8Impl_GetLevelDesc(LPDIRECT3DTEXTURE8 iface, UINT Level,D3DSURFACE_DESC* pDesc) {
182     ICOM_THIS(IDirect3DTexture8Impl,iface);
183
184     if (Level < This->levels) {
185         TRACE("(%p) Level (%d)\n", This, Level);
186         return IDirect3DSurface8Impl_GetDesc((LPDIRECT3DSURFACE8)This->surfaces[Level], pDesc);
187     } else {
188         FIXME("(%p) Level (%d)\n", This, Level);
189     }
190     return D3D_OK;
191 }
192 HRESULT  WINAPI        IDirect3DTexture8Impl_GetSurfaceLevel(LPDIRECT3DTEXTURE8 iface, UINT Level,IDirect3DSurface8** ppSurfaceLevel) {
193     ICOM_THIS(IDirect3DTexture8Impl,iface);
194     *ppSurfaceLevel = (LPDIRECT3DSURFACE8)This->surfaces[Level];
195     IDirect3DSurface8Impl_AddRef((LPDIRECT3DSURFACE8) This->surfaces[Level]);
196     TRACE("(%p) : returning %p for level %d\n", This, *ppSurfaceLevel, Level);
197     return D3D_OK;
198 }
199 HRESULT  WINAPI        IDirect3DTexture8Impl_LockRect(LPDIRECT3DTEXTURE8 iface, UINT Level,D3DLOCKED_RECT* pLockedRect,CONST RECT* pRect,DWORD Flags) {
200     HRESULT hr;
201     ICOM_THIS(IDirect3DTexture8Impl,iface);
202     TRACE("(%p) Level (%d)\n", This, Level);
203     if (Level < This->levels) {
204       /**
205        * Not dirtified while Surfaces don't notify dirtification
206        * This->Dirty = TRUE;
207        */
208       hr = IDirect3DSurface8Impl_LockRect((LPDIRECT3DSURFACE8) This->surfaces[Level], pLockedRect, pRect, Flags);
209       TRACE("(%p) Level (%d) success(%lu)\n", This, Level, hr);
210     } else {
211         FIXME("Levels seems too high?!!\n");
212     }
213     return hr;
214 }
215 HRESULT  WINAPI        IDirect3DTexture8Impl_UnlockRect(LPDIRECT3DTEXTURE8 iface, UINT Level) {
216     ICOM_THIS(IDirect3DTexture8Impl,iface);
217     TRACE("(%p) : stub\n", This);
218     return D3D_OK;
219 }
220 HRESULT  WINAPI        IDirect3DTexture8Impl_AddDirtyRect(LPDIRECT3DTEXTURE8 iface, CONST RECT* pDirtyRect) {
221     ICOM_THIS(IDirect3DTexture8Impl,iface);
222     This->Dirty = TRUE;
223     FIXME("(%p) : stub\n", This);    
224     return D3D_OK;
225 }
226
227
228 ICOM_VTABLE(IDirect3DTexture8) Direct3DTexture8_Vtbl =
229 {
230     ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
231     IDirect3DTexture8Impl_QueryInterface,
232     IDirect3DTexture8Impl_AddRef,
233     IDirect3DTexture8Impl_Release,
234     IDirect3DTexture8Impl_GetDevice,
235     IDirect3DTexture8Impl_SetPrivateData,
236     IDirect3DTexture8Impl_GetPrivateData,
237     IDirect3DTexture8Impl_FreePrivateData,
238     IDirect3DTexture8Impl_SetPriority,
239     IDirect3DTexture8Impl_GetPriority,
240     IDirect3DTexture8Impl_PreLoad,
241     IDirect3DTexture8Impl_GetType,
242     IDirect3DTexture8Impl_SetLOD,
243     IDirect3DTexture8Impl_GetLOD,
244     IDirect3DTexture8Impl_GetLevelCount,
245     IDirect3DTexture8Impl_GetLevelDesc,
246     IDirect3DTexture8Impl_GetSurfaceLevel,
247     IDirect3DTexture8Impl_LockRect,
248     IDirect3DTexture8Impl_UnlockRect,
249     IDirect3DTexture8Impl_AddDirtyRect
250
251 };