Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
5564 | serge | 1 | /* |
2 | * Copyright 2011 Joakim Sindholt |
||
3 | * |
||
4 | * Permission is hereby granted, free of charge, to any person obtaining a |
||
5 | * copy of this software and associated documentation files (the "Software"), |
||
6 | * to deal in the Software without restriction, including without limitation |
||
7 | * on the rights to use, copy, modify, merge, publish, distribute, sub |
||
8 | * license, and/or sell copies of the Software, and to permit persons to whom |
||
9 | * the Software is furnished to do so, subject to the following conditions: |
||
10 | * |
||
11 | * The above copyright notice and this permission notice (including the next |
||
12 | * paragraph) shall be included in all copies or substantial portions of the |
||
13 | * Software. |
||
14 | * |
||
15 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
||
16 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
||
17 | * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL |
||
18 | * THE AUTHOR(S) AND/OR THEIR SUPPLIERS BE LIABLE FOR ANY CLAIM, |
||
19 | * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR |
||
20 | * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE |
||
21 | * USE OR OTHER DEALINGS IN THE SOFTWARE. */ |
||
22 | |||
23 | #include "device9.h" |
||
24 | #include "volumetexture9.h" |
||
25 | #include "nine_helpers.h" |
||
26 | #include "nine_pipe.h" |
||
27 | |||
28 | #define DBG_CHANNEL DBG_VOLUMETEXTURE |
||
29 | |||
30 | static HRESULT |
||
31 | NineVolumeTexture9_ctor( struct NineVolumeTexture9 *This, |
||
32 | struct NineUnknownParams *pParams, |
||
33 | UINT Width, UINT Height, UINT Depth, UINT Levels, |
||
34 | DWORD Usage, |
||
35 | D3DFORMAT Format, |
||
36 | D3DPOOL Pool, |
||
37 | HANDLE *pSharedHandle ) |
||
38 | { |
||
39 | struct pipe_resource *info = &This->base.base.info; |
||
40 | struct pipe_screen *screen = pParams->device->screen; |
||
41 | enum pipe_format pf; |
||
42 | unsigned l; |
||
43 | D3DVOLUME_DESC voldesc; |
||
44 | HRESULT hr; |
||
45 | |||
46 | DBG("This=%p pParams=%p Width=%u Height=%u Depth=%u Levels=%u " |
||
47 | "Usage=%d Format=%d Pool=%d pSharedHandle=%p\n", |
||
48 | This, pParams, Width, Height, Depth, Levels, |
||
49 | Usage, Format, Pool, pSharedHandle); |
||
50 | |||
51 | /* An IDirect3DVolume9 cannot be bound as a render target can it ? */ |
||
52 | user_assert(!(Usage & (D3DUSAGE_RENDERTARGET | D3DUSAGE_DEPTHSTENCIL)), |
||
53 | D3DERR_INVALIDCALL); |
||
54 | user_assert(!(Usage & D3DUSAGE_AUTOGENMIPMAP), D3DERR_INVALIDCALL); |
||
55 | |||
56 | user_assert(!pSharedHandle, D3DERR_INVALIDCALL); /* TODO */ |
||
57 | |||
58 | pf = d3d9_to_pipe_format_checked(screen, Format, PIPE_TEXTURE_3D, 0, |
||
59 | PIPE_BIND_SAMPLER_VIEW, FALSE); |
||
60 | if (pf == PIPE_FORMAT_NONE) |
||
61 | return D3DERR_INVALIDCALL; |
||
62 | |||
63 | /* We support ATI1 and ATI2 hacks only for 2D textures */ |
||
64 | if (Format == D3DFMT_ATI1 || Format == D3DFMT_ATI2) |
||
65 | return D3DERR_INVALIDCALL; |
||
66 | |||
67 | info->screen = pParams->device->screen; |
||
68 | info->target = PIPE_TEXTURE_3D; |
||
69 | info->format = pf; |
||
70 | info->width0 = Width; |
||
71 | info->height0 = Height; |
||
72 | info->depth0 = Depth; |
||
73 | if (Levels) |
||
74 | info->last_level = Levels - 1; |
||
75 | else |
||
76 | info->last_level = util_logbase2(MAX2(MAX2(Width, Height), Depth)); |
||
77 | info->array_size = 1; |
||
78 | info->nr_samples = 0; |
||
79 | info->bind = PIPE_BIND_SAMPLER_VIEW; |
||
80 | info->usage = PIPE_USAGE_DEFAULT; |
||
81 | info->flags = 0; |
||
82 | |||
83 | if (Usage & D3DUSAGE_DYNAMIC) { |
||
84 | info->usage = PIPE_USAGE_DYNAMIC; |
||
85 | info->bind |= |
||
86 | PIPE_BIND_TRANSFER_READ | |
||
87 | PIPE_BIND_TRANSFER_WRITE; |
||
88 | } |
||
89 | if (Usage & D3DUSAGE_SOFTWAREPROCESSING) |
||
90 | DBG("Application asked for Software Vertex Processing, " |
||
91 | "but this is unimplemented\n"); |
||
92 | |||
93 | This->volumes = CALLOC(info->last_level + 1, sizeof(*This->volumes)); |
||
94 | if (!This->volumes) |
||
95 | return E_OUTOFMEMORY; |
||
96 | This->base.pstype = 3; |
||
97 | |||
98 | hr = NineBaseTexture9_ctor(&This->base, pParams, NULL, |
||
99 | D3DRTYPE_VOLUMETEXTURE, Format, Pool, Usage); |
||
100 | if (FAILED(hr)) |
||
101 | return hr; |
||
102 | |||
103 | voldesc.Format = Format; |
||
104 | voldesc.Type = D3DRTYPE_VOLUME; |
||
105 | voldesc.Usage = Usage; |
||
106 | voldesc.Pool = Pool; |
||
107 | for (l = 0; l <= info->last_level; ++l) { |
||
108 | voldesc.Width = u_minify(Width, l); |
||
109 | voldesc.Height = u_minify(Height, l); |
||
110 | voldesc.Depth = u_minify(Depth, l); |
||
111 | |||
112 | hr = NineVolume9_new(This->base.base.base.device, NineUnknown(This), |
||
113 | This->base.base.resource, l, |
||
114 | &voldesc, &This->volumes[l]); |
||
115 | if (FAILED(hr)) |
||
116 | return hr; |
||
117 | } |
||
118 | |||
119 | return D3D_OK; |
||
120 | } |
||
121 | |||
122 | static void |
||
123 | NineVolumeTexture9_dtor( struct NineVolumeTexture9 *This ) |
||
124 | { |
||
125 | unsigned l; |
||
126 | |||
127 | DBG("This=%p\n", This); |
||
128 | |||
129 | if (This->volumes) { |
||
130 | for (l = 0; l < This->base.base.info.last_level; ++l) |
||
131 | NineUnknown_Destroy(&This->volumes[l]->base); |
||
132 | FREE(This->volumes); |
||
133 | } |
||
134 | |||
135 | NineBaseTexture9_dtor(&This->base); |
||
136 | } |
||
137 | |||
138 | HRESULT WINAPI |
||
139 | NineVolumeTexture9_GetLevelDesc( struct NineVolumeTexture9 *This, |
||
140 | UINT Level, |
||
141 | D3DVOLUME_DESC *pDesc ) |
||
142 | { |
||
143 | user_assert(Level <= This->base.base.info.last_level, D3DERR_INVALIDCALL); |
||
144 | |||
145 | *pDesc = This->volumes[Level]->desc; |
||
146 | |||
147 | return D3D_OK; |
||
148 | } |
||
149 | |||
150 | HRESULT WINAPI |
||
151 | NineVolumeTexture9_GetVolumeLevel( struct NineVolumeTexture9 *This, |
||
152 | UINT Level, |
||
153 | IDirect3DVolume9 **ppVolumeLevel ) |
||
154 | { |
||
155 | user_assert(Level <= This->base.base.info.last_level, D3DERR_INVALIDCALL); |
||
156 | |||
157 | NineUnknown_AddRef(NineUnknown(This->volumes[Level])); |
||
158 | *ppVolumeLevel = (IDirect3DVolume9 *)This->volumes[Level]; |
||
159 | |||
160 | return D3D_OK; |
||
161 | } |
||
162 | |||
163 | HRESULT WINAPI |
||
164 | NineVolumeTexture9_LockBox( struct NineVolumeTexture9 *This, |
||
165 | UINT Level, |
||
166 | D3DLOCKED_BOX *pLockedVolume, |
||
167 | const D3DBOX *pBox, |
||
168 | DWORD Flags ) |
||
169 | { |
||
170 | DBG("This=%p Level=%u pLockedVolume=%p pBox=%p Flags=%d\n", |
||
171 | This, Level, pLockedVolume, pBox, Flags); |
||
172 | |||
173 | user_assert(Level <= This->base.base.info.last_level, D3DERR_INVALIDCALL); |
||
174 | |||
175 | return NineVolume9_LockBox(This->volumes[Level], pLockedVolume, pBox, |
||
176 | Flags); |
||
177 | } |
||
178 | |||
179 | HRESULT WINAPI |
||
180 | NineVolumeTexture9_UnlockBox( struct NineVolumeTexture9 *This, |
||
181 | UINT Level ) |
||
182 | { |
||
183 | DBG("This=%p Level=%u\n", This, Level); |
||
184 | |||
185 | user_assert(Level <= This->base.base.info.last_level, D3DERR_INVALIDCALL); |
||
186 | |||
187 | return NineVolume9_UnlockBox(This->volumes[Level]); |
||
188 | } |
||
189 | |||
190 | HRESULT WINAPI |
||
191 | NineVolumeTexture9_AddDirtyBox( struct NineVolumeTexture9 *This, |
||
192 | const D3DBOX *pDirtyBox ) |
||
193 | { |
||
194 | DBG("This=%p pDirtybox=%p\n", This, pDirtyBox); |
||
195 | |||
196 | if (This->base.base.pool != D3DPOOL_MANAGED) { |
||
197 | return D3D_OK; |
||
198 | } |
||
199 | This->base.managed.dirty = TRUE; |
||
200 | |||
201 | BASETEX_REGISTER_UPDATE(&This->base); |
||
202 | |||
203 | if (!pDirtyBox) { |
||
204 | This->dirty_box.x = 0; |
||
205 | This->dirty_box.y = 0; |
||
206 | This->dirty_box.z = 0; |
||
207 | This->dirty_box.width = This->base.base.info.width0; |
||
208 | This->dirty_box.height = This->base.base.info.height0; |
||
209 | This->dirty_box.depth = This->base.base.info.depth0; |
||
210 | } else { |
||
211 | struct pipe_box box; |
||
212 | d3dbox_to_pipe_box(&box, pDirtyBox); |
||
213 | u_box_union_3d(&This->dirty_box, &This->dirty_box, &box); |
||
214 | This->dirty_box.x = MAX2(This->dirty_box.x, 0); |
||
215 | This->dirty_box.y = MAX2(This->dirty_box.y, 0); |
||
216 | This->dirty_box.z = MAX2(This->dirty_box.z, 0); |
||
217 | This->dirty_box.width = MIN2(This->dirty_box.width, |
||
218 | This->base.base.info.width0 - This->dirty_box.x); |
||
219 | This->dirty_box.height = MIN2(This->dirty_box.height, |
||
220 | This->base.base.info.height0 - This->dirty_box.y); |
||
221 | This->dirty_box.depth = MIN2(This->dirty_box.depth, |
||
222 | This->base.base.info.depth0 - This->dirty_box.z); |
||
223 | } |
||
224 | return D3D_OK; |
||
225 | } |
||
226 | |||
227 | IDirect3DVolumeTexture9Vtbl NineVolumeTexture9_vtable = { |
||
228 | (void *)NineUnknown_QueryInterface, |
||
229 | (void *)NineUnknown_AddRef, |
||
230 | (void *)NineUnknown_Release, |
||
231 | (void *)NineUnknown_GetDevice, /* actually part of Resource9 iface */ |
||
232 | (void *)NineResource9_SetPrivateData, |
||
233 | (void *)NineResource9_GetPrivateData, |
||
234 | (void *)NineResource9_FreePrivateData, |
||
235 | (void *)NineResource9_SetPriority, |
||
236 | (void *)NineResource9_GetPriority, |
||
237 | (void *)NineBaseTexture9_PreLoad, |
||
238 | (void *)NineResource9_GetType, |
||
239 | (void *)NineBaseTexture9_SetLOD, |
||
240 | (void *)NineBaseTexture9_GetLOD, |
||
241 | (void *)NineBaseTexture9_GetLevelCount, |
||
242 | (void *)NineBaseTexture9_SetAutoGenFilterType, |
||
243 | (void *)NineBaseTexture9_GetAutoGenFilterType, |
||
244 | (void *)NineBaseTexture9_GenerateMipSubLevels, |
||
245 | (void *)NineVolumeTexture9_GetLevelDesc, |
||
246 | (void *)NineVolumeTexture9_GetVolumeLevel, |
||
247 | (void *)NineVolumeTexture9_LockBox, |
||
248 | (void *)NineVolumeTexture9_UnlockBox, |
||
249 | (void *)NineVolumeTexture9_AddDirtyBox |
||
250 | }; |
||
251 | |||
252 | static const GUID *NineVolumeTexture9_IIDs[] = { |
||
253 | &IID_IDirect3DVolumeTexture9, |
||
254 | &IID_IDirect3DBaseTexture9, |
||
255 | &IID_IDirect3DResource9, |
||
256 | &IID_IUnknown, |
||
257 | NULL |
||
258 | }; |
||
259 | |||
260 | HRESULT |
||
261 | NineVolumeTexture9_new( struct NineDevice9 *pDevice, |
||
262 | UINT Width, UINT Height, UINT Depth, UINT Levels, |
||
263 | DWORD Usage, |
||
264 | D3DFORMAT Format, |
||
265 | D3DPOOL Pool, |
||
266 | struct NineVolumeTexture9 **ppOut, |
||
267 | HANDLE *pSharedHandle ) |
||
268 | { |
||
269 | NINE_DEVICE_CHILD_NEW(VolumeTexture9, ppOut, pDevice, |
||
270 | Width, Height, Depth, Levels, |
||
271 | Usage, Format, Pool, pSharedHandle); |
||
272 | }=>=>=>=>>=> |
||
273 |