2 * Copyright 2010 Christian Costa
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19 #include "wine/debug.h"
20 #include "d3dx9_36_private.h"
22 WINE_DEFAULT_DEBUG_CHANNEL(d3dx
);
24 HRESULT WINAPI
D3DXLoadVolumeFromFileA(IDirect3DVolume9
*dst_volume
,
25 const PALETTEENTRY
*dst_palette
,
26 const D3DBOX
*dst_box
,
28 const D3DBOX
*src_box
,
37 TRACE("(%p, %p, %p, %s, %p, %#x, %#x, %p)\n",
38 dst_volume
, dst_palette
, dst_box
, debugstr_a(filename
), src_box
,
39 filter
, color_key
, info
);
41 if (!dst_volume
|| !filename
) return D3DERR_INVALIDCALL
;
43 length
= MultiByteToWideChar(CP_ACP
, 0, filename
, -1, NULL
, 0);
44 filenameW
= HeapAlloc(GetProcessHeap(), 0, length
* sizeof(*filenameW
));
45 if (!filenameW
) return E_OUTOFMEMORY
;
47 hr
= D3DXLoadVolumeFromFileW(dst_volume
, dst_palette
, dst_box
, filenameW
,
48 src_box
, filter
, color_key
, info
);
49 HeapFree(GetProcessHeap(), 0, filenameW
);
54 HRESULT WINAPI
D3DXLoadVolumeFromFileW(IDirect3DVolume9
*dst_volume
,
55 const PALETTEENTRY
*dst_palette
,
56 const D3DBOX
*dst_box
,
57 const WCHAR
*filename
,
58 const D3DBOX
*src_box
,
67 TRACE("(%p, %p, %p, %s, %p, %#x, %#x, %p)\n",
68 dst_volume
, dst_palette
, dst_box
, debugstr_w(filename
), src_box
,
69 filter
, color_key
, info
);
71 if (!dst_volume
|| !filename
) return D3DERR_INVALIDCALL
;
73 if (FAILED(map_view_of_file(filename
, &data
, &data_size
)))
74 return D3DXERR_INVALIDDATA
;
76 hr
= D3DXLoadVolumeFromFileInMemory(dst_volume
, dst_palette
, dst_box
,
77 data
, data_size
, src_box
, filter
, color_key
, info
);
78 UnmapViewOfFile(data
);
83 HRESULT WINAPI
D3DXLoadVolumeFromMemory(IDirect3DVolume9
*dst_volume
,
84 const PALETTEENTRY
*dst_palette
,
85 const D3DBOX
*dst_box
,
86 const void *src_memory
,
90 const PALETTEENTRY
*src_palette
,
91 const D3DBOX
*src_box
,
97 D3DLOCKED_BOX locked_box
;
98 UINT dst_width
, dst_height
, dst_depth
;
99 UINT src_width
, src_height
, src_depth
;
100 const PixelFormatDesc
*src_format_desc
, *dst_format_desc
;
102 TRACE("(%p, %p, %p, %p, %#x, %u, %u, %p, %p, %x, %x)\n", dst_volume
, dst_palette
, dst_box
,
103 src_memory
, src_format
, src_row_pitch
, src_slice_pitch
, src_palette
, src_box
,
106 if (!dst_volume
|| !src_memory
|| !src_box
) return D3DERR_INVALIDCALL
;
108 if (src_format
== D3DFMT_UNKNOWN
109 || src_box
->Left
>= src_box
->Right
110 || src_box
->Top
>= src_box
->Bottom
111 || src_box
->Front
>= src_box
->Back
)
114 if (filter
== D3DX_DEFAULT
)
115 filter
= D3DX_FILTER_TRIANGLE
| D3DX_FILTER_DITHER
;
117 IDirect3DVolume9_GetDesc(dst_volume
, &desc
);
119 src_width
= src_box
->Right
- src_box
->Left
;
120 src_height
= src_box
->Bottom
- src_box
->Top
;
121 src_depth
= src_box
->Back
- src_box
->Front
;
125 dst_width
= desc
.Width
;
126 dst_height
= desc
.Height
;
127 dst_depth
= desc
.Depth
;
131 if (dst_box
->Left
>= dst_box
->Right
|| dst_box
->Right
> desc
.Width
)
132 return D3DERR_INVALIDCALL
;
133 if (dst_box
->Top
>= dst_box
->Bottom
|| dst_box
->Bottom
> desc
.Height
)
134 return D3DERR_INVALIDCALL
;
135 if (dst_box
->Front
>= dst_box
->Back
|| dst_box
->Back
> desc
.Depth
)
136 return D3DERR_INVALIDCALL
;
138 dst_width
= dst_box
->Right
- dst_box
->Left
;
139 dst_height
= dst_box
->Bottom
- dst_box
->Top
;
140 dst_depth
= dst_box
->Back
- dst_box
->Front
;
143 src_format_desc
= get_format_info(src_format
);
144 if (src_format_desc
->type
== FORMAT_UNKNOWN
)
147 dst_format_desc
= get_format_info(desc
.Format
);
148 if (dst_format_desc
->type
== FORMAT_UNKNOWN
)
151 if (desc
.Format
== src_format
152 && dst_width
== src_width
&& dst_height
== src_height
&& dst_depth
== src_depth
)
156 const BYTE
*src_addr
;
157 UINT row_block_count
= (src_width
+ src_format_desc
->block_width
- 1) / src_format_desc
->block_width
;
158 UINT row_count
= (src_height
+ src_format_desc
->block_height
- 1) / src_format_desc
->block_height
;
160 if (src_box
->Left
& (src_format_desc
->block_width
- 1)
161 || src_box
->Top
& (src_format_desc
->block_height
- 1)
162 || (src_box
->Right
& (src_format_desc
->block_width
- 1)
163 && src_width
!= desc
.Width
)
164 || (src_box
->Bottom
& (src_format_desc
->block_height
- 1)
165 && src_height
!= desc
.Height
))
167 FIXME("Source box (%u, %u, %u, %u) is misaligned\n",
168 src_box
->Left
, src_box
->Top
, src_box
->Right
, src_box
->Bottom
);
172 hr
= IDirect3DVolume9_LockBox(dst_volume
, &locked_box
, dst_box
, 0);
173 if (FAILED(hr
)) return hr
;
175 for (slice
= 0; slice
< src_depth
; slice
++)
177 src_addr
= src_memory
;
178 src_addr
+= (src_box
->Front
+ slice
) * src_slice_pitch
;
179 src_addr
+= (src_box
->Top
/ src_format_desc
->block_height
) * src_row_pitch
;
180 src_addr
+= (src_box
->Left
/ src_format_desc
->block_width
) * src_format_desc
->block_byte_count
;
182 dst_addr
= locked_box
.pBits
;
183 dst_addr
+= slice
* locked_box
.SlicePitch
;
185 for (row
= 0; row
< row_count
; row
++)
187 memcpy(dst_addr
, src_addr
, row_block_count
* src_format_desc
->block_byte_count
);
188 src_addr
+= src_row_pitch
;
189 dst_addr
+= locked_box
.RowPitch
;
193 IDirect3DVolume9_UnlockBox(dst_volume
);
197 const BYTE
*src_addr
;
198 SIZE src_size
, dst_size
;
200 if (src_format_desc
->bytes_per_pixel
> 4 || dst_format_desc
->bytes_per_pixel
> 4
201 || src_format_desc
->block_height
!= 1 || src_format_desc
->block_width
!= 1
202 || dst_format_desc
->block_height
!= 1 || dst_format_desc
->block_width
!= 1)
204 FIXME("Pixel format conversion not implemented %#x -> %#x\n",
205 src_format_desc
->format
, dst_format_desc
->format
);
209 src_size
.cx
= src_width
;
210 src_size
.cy
= src_height
;
211 dst_size
.cx
= dst_width
;
212 dst_size
.cy
= dst_height
;
214 src_addr
= src_memory
;
215 src_addr
+= src_box
->Front
* src_slice_pitch
;
216 src_addr
+= src_box
->Top
* src_row_pitch
;
217 src_addr
+= src_box
->Left
* src_format_desc
->bytes_per_pixel
;
219 hr
= IDirect3DVolume9_LockBox(dst_volume
, &locked_box
, dst_box
, 0);
220 if (FAILED(hr
)) return hr
;
222 if ((filter
& 0xf) == D3DX_FILTER_NONE
)
224 copy_simple_data(src_memory
, src_row_pitch
, src_slice_pitch
, src_size
, src_depth
, src_format_desc
,
225 locked_box
.pBits
, locked_box
.RowPitch
, locked_box
.SlicePitch
, dst_size
, dst_depth
, dst_format_desc
, color_key
);
229 FIXME("Filtering for volume textures not implemented\n");
233 IDirect3DVolume9_UnlockBox(dst_volume
);
239 HRESULT WINAPI
D3DXLoadVolumeFromFileInMemory(IDirect3DVolume9
*dst_volume
,
240 const PALETTEENTRY
*dst_palette
,
241 const D3DBOX
*dst_box
,
242 const void *src_data
,
244 const D3DBOX
*src_box
,
247 D3DXIMAGE_INFO
*src_info
)
251 D3DXIMAGE_INFO image_info
;
253 if (!dst_volume
|| !src_data
) return D3DERR_INVALIDCALL
;
255 hr
= D3DXGetImageInfoFromFileInMemory(src_data
, src_data_size
, &image_info
);
256 if (FAILED(hr
)) return hr
;
260 if (src_box
->Right
> image_info
.Width
261 || src_box
->Bottom
> image_info
.Height
262 || src_box
->Back
> image_info
.Depth
)
263 return D3DERR_INVALIDCALL
;
271 box
.Right
= image_info
.Width
;
272 box
.Bottom
= image_info
.Height
;
274 box
.Back
= image_info
.Depth
;
278 if (image_info
.ImageFileFormat
!= D3DXIFF_DDS
)
280 FIXME("File format %#x is not supported yet\n", image_info
.ImageFileFormat
);
284 hr
= load_volume_from_dds(dst_volume
, dst_palette
, dst_box
, src_data
, &box
,
285 filter
, color_key
, &image_info
);
286 if (FAILED(hr
)) return hr
;
289 *src_info
= image_info
;
294 HRESULT WINAPI
D3DXLoadVolumeFromVolume(IDirect3DVolume9
*dst_volume
,
295 const PALETTEENTRY
*dst_palette
,
296 const D3DBOX
*dst_box
,
297 IDirect3DVolume9
*src_volume
,
298 const PALETTEENTRY
*src_palette
,
299 const D3DBOX
*src_box
,
306 D3DLOCKED_BOX locked_box
;
308 TRACE("(%p, %p, %p, %p, %p, %p, %#x, %#x)\n",
309 dst_volume
, dst_palette
, dst_box
, src_volume
, src_palette
, src_box
,
312 if (!dst_volume
|| !src_volume
) return D3DERR_INVALIDCALL
;
314 IDirect3DVolume9_GetDesc(src_volume
, &desc
);
318 box
.Left
= box
.Top
= 0;
319 box
.Right
= desc
.Width
;
320 box
.Bottom
= desc
.Height
;
322 box
.Back
= desc
.Depth
;
326 hr
= IDirect3DVolume9_LockBox(src_volume
, &locked_box
, NULL
, D3DLOCK_READONLY
);
327 if (FAILED(hr
)) return hr
;
329 hr
= D3DXLoadVolumeFromMemory(dst_volume
, dst_palette
, dst_box
,
330 locked_box
.pBits
, desc
.Format
, locked_box
.RowPitch
, locked_box
.SlicePitch
,
331 src_palette
, &box
, filter
, color_key
);
333 IDirect3DVolume9_UnlockBox(src_volume
);