blob: cfe1ed7f1ed907afc033ef0c6b3292aa8ef62853 [file] [log] [blame]
Nicolas Capens0bac2852016-05-07 06:09:58 -04001// Copyright 2016 The SwiftShader Authors. All Rights Reserved.
Nicolas Capensee16f0d2015-07-16 17:40:10 -04002//
Nicolas Capens0bac2852016-05-07 06:09:58 -04003// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
Nicolas Capensee16f0d2015-07-16 17:40:10 -04006//
Nicolas Capens0bac2852016-05-07 06:09:58 -04007// http://www.apache.org/licenses/LICENSE-2.0
Nicolas Capensee16f0d2015-07-16 17:40:10 -04008//
Nicolas Capens0bac2852016-05-07 06:09:58 -04009// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
Nicolas Capensee16f0d2015-07-16 17:40:10 -040014
15#include "Direct3DCubeTexture9.hpp"
16
17#include "Direct3DDevice9.hpp"
18#include "Direct3DSurface9.hpp"
19#include "Resource.hpp"
20#include "Debug.hpp"
21
22#include <assert.h>
23
24namespace D3D9
25{
26 Direct3DCubeTexture9::Direct3DCubeTexture9(Direct3DDevice9 *device, unsigned int edgeLength, unsigned int levels, unsigned long usage, D3DFORMAT format, D3DPOOL pool) : Direct3DBaseTexture9(device, D3DRTYPE_CUBETEXTURE, format, pool, levels, usage), edgeLength(edgeLength)
27 {
28 if(levels == 0)
29 {
30 this->levels = sw::log2(sw::max((int)edgeLength, 1)) + 1;
31 }
32
33 for(unsigned int face = 0; face < 6; face++)
34 {
35 int width = edgeLength;
36 int height = edgeLength;
37
Nicolas Capensb663f712016-04-18 12:02:39 -040038 for(unsigned int level = 0; level < sw::MIPMAP_LEVELS; level++)
Nicolas Capensee16f0d2015-07-16 17:40:10 -040039 {
40 if(level < this->levels)
Nicolas Capensb663f712016-04-18 12:02:39 -040041 {
Nicolas Capensee16f0d2015-07-16 17:40:10 -040042 surfaceLevel[face][level] = new Direct3DSurface9(device, this, width, height, format, pool, D3DMULTISAMPLE_NONE, 0, false, usage);
43 surfaceLevel[face][level]->bind();
44 }
45 else
46 {
47 surfaceLevel[face][level] = 0;
48 }
49
50 width = sw::max(1, width / 2);
51 height = sw::max(1, height / 2);
52 }
53 }
54 }
55
56 Direct3DCubeTexture9::~Direct3DCubeTexture9()
57 {
58 resource->lock(sw::DESTRUCT);
59
60 for(unsigned int face = 0; face < 6; face++)
61 {
Nicolas Capensb663f712016-04-18 12:02:39 -040062 for(int level = 0; level < sw::MIPMAP_LEVELS; level++)
Nicolas Capensee16f0d2015-07-16 17:40:10 -040063 {
64 if(surfaceLevel[face][level])
65 {
66 surfaceLevel[face][level]->unbind();
67 surfaceLevel[face][level] = 0;
68 }
69 }
70 }
71
72 resource->unlock();
73 }
74
75 long Direct3DCubeTexture9::QueryInterface(const IID &iid, void **object)
76 {
77 CriticalSection cs(device);
78
79 TRACE("");
80
81 if(iid == IID_IDirect3DCubeTexture9 ||
82 iid == IID_IDirect3DBaseTexture9 ||
83 iid == IID_IDirect3DResource9 ||
84 iid == IID_IUnknown)
85 {
86 AddRef();
87 *object = this;
88
89 return S_OK;
90 }
91
92 *object = 0;
93
94 return NOINTERFACE(iid);
95 }
96
97 unsigned long Direct3DCubeTexture9::AddRef()
98 {
99 TRACE("");
100
101 return Direct3DBaseTexture9::AddRef();
102 }
103
104 unsigned long Direct3DCubeTexture9::Release()
105 {
106 TRACE("");
107
108 return Direct3DBaseTexture9::Release();
109 }
110
111 long Direct3DCubeTexture9::FreePrivateData(const GUID &guid)
112 {
113 CriticalSection cs(device);
114
115 TRACE("");
116
117 return Direct3DBaseTexture9::FreePrivateData(guid);
118 }
119
120 long Direct3DCubeTexture9::GetPrivateData(const GUID &guid, void *data, unsigned long *size)
121 {
122 CriticalSection cs(device);
123
124 TRACE("");
125
126 return Direct3DBaseTexture9::GetPrivateData(guid, data, size);
127 }
128
129 void Direct3DCubeTexture9::PreLoad()
130 {
131 CriticalSection cs(device);
132
133 TRACE("");
134
135 Direct3DBaseTexture9::PreLoad();
136 }
137
138 long Direct3DCubeTexture9::SetPrivateData(const GUID &guid, const void *data, unsigned long size, unsigned long flags)
139 {
140 CriticalSection cs(device);
141
142 TRACE("");
143
144 return Direct3DBaseTexture9::SetPrivateData(guid, data, size, flags);
145 }
146
147 long Direct3DCubeTexture9::GetDevice(IDirect3DDevice9 **device)
148 {
149 CriticalSection cs(this->device);
150
151 TRACE("");
152
153 return Direct3DBaseTexture9::GetDevice(device);
154 }
155
156 unsigned long Direct3DCubeTexture9::SetPriority(unsigned long newPriority)
157 {
158 CriticalSection cs(device);
159
160 TRACE("");
161
162 return Direct3DBaseTexture9::SetPriority(newPriority);
163 }
164
165 unsigned long Direct3DCubeTexture9::GetPriority()
166 {
167 CriticalSection cs(device);
168
169 TRACE("");
170
171 return Direct3DBaseTexture9::GetPriority();
172 }
173
174 D3DRESOURCETYPE Direct3DCubeTexture9::GetType()
175 {
176 CriticalSection cs(device);
177
178 TRACE("");
179
180 return Direct3DBaseTexture9::GetType();
181 }
182
183 void Direct3DCubeTexture9::GenerateMipSubLevels()
184 {
185 CriticalSection cs(device);
186
187 TRACE("");
188
189 if(!(usage & D3DUSAGE_AUTOGENMIPMAP))
190 {
191 return;
192 }
193
194 resource->lock(sw::PUBLIC);
195
196 for(unsigned int face = 0; face < 6; face++)
197 {
198 if(!surfaceLevel[face][0]->hasDirtyMipmaps())
199 {
200 continue;
201 }
202
203 for(unsigned int i = 0; i < levels - 1; i++)
204 {
205 device->stretchRect(surfaceLevel[face][i], 0, surfaceLevel[face][i + 1], 0, GetAutoGenFilterType());
206 }
207
208 surfaceLevel[face][0]->cleanMipmaps();
209 }
210
211 resource->unlock();
212 }
213
214 D3DTEXTUREFILTERTYPE Direct3DCubeTexture9::GetAutoGenFilterType()
215 {
216 CriticalSection cs(device);
217
218 TRACE("");
219
220 return Direct3DBaseTexture9::GetAutoGenFilterType();
221 }
222
223 unsigned long Direct3DCubeTexture9::GetLevelCount()
224 {
225 CriticalSection cs(device);
226
227 TRACE("");
228
229 return Direct3DBaseTexture9::GetLevelCount();
230 }
231
232 unsigned long Direct3DCubeTexture9::GetLOD()
233 {
234 CriticalSection cs(device);
235
236 TRACE("");
237
238 return Direct3DBaseTexture9::GetLOD();
239 }
240
241 long Direct3DCubeTexture9::SetAutoGenFilterType(D3DTEXTUREFILTERTYPE filterType)
242 {
243 CriticalSection cs(device);
244
245 TRACE("");
246
247 return Direct3DBaseTexture9::SetAutoGenFilterType(filterType);
248 }
249
250 unsigned long Direct3DCubeTexture9::SetLOD(unsigned long newLOD)
251 {
252 CriticalSection cs(device);
253
254 TRACE("");
255
256 return Direct3DBaseTexture9::SetLOD(newLOD);
257 }
258
259 long Direct3DCubeTexture9::AddDirtyRect(D3DCUBEMAP_FACES face, const RECT *dirtyRect)
260 {
261 CriticalSection cs(device);
262
263 TRACE("");
264
265 // UNIMPLEMENTED();
266
267 return D3D_OK;
268 }
269
270 long Direct3DCubeTexture9::GetCubeMapSurface(D3DCUBEMAP_FACES face, unsigned int level, IDirect3DSurface9 **cubeMapSurface)
271 {
272 CriticalSection cs(device);
273
274 TRACE("");
275
276 *cubeMapSurface = 0;
277
278 if(face >= 6 || level >= GetLevelCount() || !surfaceLevel[face][level])
279 {
280 return INVALIDCALL();
281 }
282
283 surfaceLevel[face][level]->AddRef();
284 *cubeMapSurface = surfaceLevel[face][level];
285
286 return D3D_OK;
287 }
288
289 long Direct3DCubeTexture9::GetLevelDesc(unsigned int level, D3DSURFACE_DESC *description)
290 {
291 CriticalSection cs(device);
292
293 TRACE("");
294
295 if(!description || level >= GetLevelCount() || !surfaceLevel[0][level])
296 {
297 return INVALIDCALL();
298 }
299
300 return surfaceLevel[0][level]->GetDesc(description);
301 }
302
303 long Direct3DCubeTexture9::LockRect(D3DCUBEMAP_FACES face, unsigned int level, D3DLOCKED_RECT *lockedRect, const RECT *rect, unsigned long flags)
304 {
305 CriticalSection cs(device);
306
307 TRACE("");
308
309 if(!lockedRect || face >= 6 || level >= GetLevelCount() || !surfaceLevel[face][level])
310 {
311 return INVALIDCALL();
312 }
313
314 return surfaceLevel[face][level]->LockRect(lockedRect, rect, flags);
315 }
316
317 long Direct3DCubeTexture9::UnlockRect(D3DCUBEMAP_FACES face, unsigned int level)
318 {
319 CriticalSection cs(device);
320
321 TRACE("");
322
323 if(face >= 6 || level >= GetLevelCount() || !surfaceLevel[face][level])
324 {
325 return INVALIDCALL();
326 }
327
328 return surfaceLevel[face][level]->UnlockRect();
329 }
330
331 Direct3DSurface9 *Direct3DCubeTexture9::getInternalCubeMapSurface(D3DCUBEMAP_FACES face, unsigned int level)
332 {
333 return surfaceLevel[face][level];
334 }
335}