Mercurial > sdl-ios-xcode
comparison src/video/windx5/SDL_dx5yuv.c @ 1662:782fd950bd46 SDL-1.3
Revamp of the video system in progress - adding support for multiple displays, multiple windows, and a full video mode selection API.
WARNING: None of the video drivers have been updated for the new API yet! The API is still under design and very fluid.
The code is now run through a consistent indent format:
indent -i4 -nut -nsc -br -ce
The headers are being converted to automatically generate doxygen documentation.
author | Sam Lantinga <slouken@libsdl.org> |
---|---|
date | Sun, 28 May 2006 13:04:16 +0000 |
parents | 51038e80ae59 |
children | 4da1ee79c9af |
comparison
equal
deleted
inserted
replaced
1661:281d3f4870e5 | 1662:782fd950bd46 |
---|---|
29 | 29 |
30 //#define USE_DIRECTX_OVERLAY | 30 //#define USE_DIRECTX_OVERLAY |
31 | 31 |
32 /* The functions used to manipulate software video overlays */ | 32 /* The functions used to manipulate software video overlays */ |
33 static struct private_yuvhwfuncs dx5_yuvfuncs = { | 33 static struct private_yuvhwfuncs dx5_yuvfuncs = { |
34 DX5_LockYUVOverlay, | 34 DX5_LockYUVOverlay, |
35 DX5_UnlockYUVOverlay, | 35 DX5_UnlockYUVOverlay, |
36 DX5_DisplayYUVOverlay, | 36 DX5_DisplayYUVOverlay, |
37 DX5_FreeYUVOverlay | 37 DX5_FreeYUVOverlay |
38 }; | 38 }; |
39 | 39 |
40 struct private_yuvhwdata { | 40 struct private_yuvhwdata |
41 LPDIRECTDRAWSURFACE3 surface; | 41 { |
42 | 42 LPDIRECTDRAWSURFACE3 surface; |
43 /* These are just so we don't have to allocate them separately */ | 43 |
44 Uint16 pitches[3]; | 44 /* These are just so we don't have to allocate them separately */ |
45 Uint8 *planes[3]; | 45 Uint16 pitches[3]; |
46 Uint8 *planes[3]; | |
46 }; | 47 }; |
47 | 48 |
48 | 49 |
49 static LPDIRECTDRAWSURFACE3 CreateYUVSurface(_THIS, | 50 static LPDIRECTDRAWSURFACE3 |
50 int width, int height, Uint32 format) | 51 CreateYUVSurface (_THIS, int width, int height, Uint32 format) |
51 { | 52 { |
52 HRESULT result; | 53 HRESULT result; |
53 LPDIRECTDRAWSURFACE dd_surface1; | 54 LPDIRECTDRAWSURFACE dd_surface1; |
54 LPDIRECTDRAWSURFACE3 dd_surface3; | 55 LPDIRECTDRAWSURFACE3 dd_surface3; |
55 DDSURFACEDESC ddsd; | 56 DDSURFACEDESC ddsd; |
56 | 57 |
57 /* Set up the surface description */ | 58 /* Set up the surface description */ |
58 SDL_memset(&ddsd, 0, sizeof(ddsd)); | 59 SDL_memset (&ddsd, 0, sizeof (ddsd)); |
59 ddsd.dwSize = sizeof(ddsd); | 60 ddsd.dwSize = sizeof (ddsd); |
60 ddsd.dwFlags = (DDSD_WIDTH|DDSD_HEIGHT|DDSD_CAPS|DDSD_PIXELFORMAT); | 61 ddsd.dwFlags = (DDSD_WIDTH | DDSD_HEIGHT | DDSD_CAPS | DDSD_PIXELFORMAT); |
61 ddsd.dwWidth = width; | 62 ddsd.dwWidth = width; |
62 ddsd.dwHeight= height; | 63 ddsd.dwHeight = height; |
63 #ifdef USE_DIRECTX_OVERLAY | 64 #ifdef USE_DIRECTX_OVERLAY |
64 ddsd.ddsCaps.dwCaps = (DDSCAPS_OVERLAY|DDSCAPS_VIDEOMEMORY); | 65 ddsd.ddsCaps.dwCaps = (DDSCAPS_OVERLAY | DDSCAPS_VIDEOMEMORY); |
65 #else | 66 #else |
66 ddsd.ddsCaps.dwCaps = (DDSCAPS_OFFSCREENPLAIN|DDSCAPS_VIDEOMEMORY); | 67 ddsd.ddsCaps.dwCaps = (DDSCAPS_OFFSCREENPLAIN | DDSCAPS_VIDEOMEMORY); |
67 #endif | 68 #endif |
68 ddsd.ddpfPixelFormat.dwSize = sizeof(ddsd.ddpfPixelFormat); | 69 ddsd.ddpfPixelFormat.dwSize = sizeof (ddsd.ddpfPixelFormat); |
69 ddsd.ddpfPixelFormat.dwFlags = DDPF_FOURCC; | 70 ddsd.ddpfPixelFormat.dwFlags = DDPF_FOURCC; |
70 ddsd.ddpfPixelFormat.dwFourCC = format; | 71 ddsd.ddpfPixelFormat.dwFourCC = format; |
71 | 72 |
72 /* Create the DirectDraw video surface */ | 73 /* Create the DirectDraw video surface */ |
73 result = IDirectDraw2_CreateSurface(ddraw2, &ddsd, &dd_surface1, NULL); | 74 result = IDirectDraw2_CreateSurface (ddraw2, &ddsd, &dd_surface1, NULL); |
74 if ( result != DD_OK ) { | 75 if (result != DD_OK) { |
75 SetDDerror("DirectDraw2::CreateSurface", result); | 76 SetDDerror ("DirectDraw2::CreateSurface", result); |
76 return(NULL); | 77 return (NULL); |
77 } | 78 } |
78 result = IDirectDrawSurface_QueryInterface(dd_surface1, | 79 result = IDirectDrawSurface_QueryInterface (dd_surface1, |
79 &IID_IDirectDrawSurface3, (LPVOID *)&dd_surface3); | 80 &IID_IDirectDrawSurface3, |
80 IDirectDrawSurface_Release(dd_surface1); | 81 (LPVOID *) & dd_surface3); |
81 if ( result != DD_OK ) { | 82 IDirectDrawSurface_Release (dd_surface1); |
82 SetDDerror("DirectDrawSurface::QueryInterface", result); | 83 if (result != DD_OK) { |
83 return(NULL); | 84 SetDDerror ("DirectDrawSurface::QueryInterface", result); |
84 } | 85 return (NULL); |
85 | 86 } |
86 /* Make sure the surface format was set properly */ | 87 |
87 SDL_memset(&ddsd, 0, sizeof(ddsd)); | 88 /* Make sure the surface format was set properly */ |
88 ddsd.dwSize = sizeof(ddsd); | 89 SDL_memset (&ddsd, 0, sizeof (ddsd)); |
89 result = IDirectDrawSurface3_Lock(dd_surface3, NULL, | 90 ddsd.dwSize = sizeof (ddsd); |
90 &ddsd, DDLOCK_NOSYSLOCK, NULL); | 91 result = IDirectDrawSurface3_Lock (dd_surface3, NULL, |
91 if ( result != DD_OK ) { | 92 &ddsd, DDLOCK_NOSYSLOCK, NULL); |
92 SetDDerror("DirectDrawSurface3::Lock", result); | 93 if (result != DD_OK) { |
93 IDirectDrawSurface_Release(dd_surface3); | 94 SetDDerror ("DirectDrawSurface3::Lock", result); |
94 return(NULL); | 95 IDirectDrawSurface_Release (dd_surface3); |
95 } | 96 return (NULL); |
96 IDirectDrawSurface3_Unlock(dd_surface3, NULL); | 97 } |
97 | 98 IDirectDrawSurface3_Unlock (dd_surface3, NULL); |
98 if ( !(ddsd.ddpfPixelFormat.dwFlags & DDPF_FOURCC) || | 99 |
99 (ddsd.ddpfPixelFormat.dwFourCC != format) ) { | 100 if (!(ddsd.ddpfPixelFormat.dwFlags & DDPF_FOURCC) || |
100 SDL_SetError("DDraw didn't use requested FourCC format"); | 101 (ddsd.ddpfPixelFormat.dwFourCC != format)) { |
101 IDirectDrawSurface_Release(dd_surface3); | 102 SDL_SetError ("DDraw didn't use requested FourCC format"); |
102 return(NULL); | 103 IDirectDrawSurface_Release (dd_surface3); |
103 } | 104 return (NULL); |
104 | 105 } |
105 /* We're ready to go! */ | 106 |
106 return(dd_surface3); | 107 /* We're ready to go! */ |
108 return (dd_surface3); | |
107 } | 109 } |
108 | 110 |
109 #ifdef DEBUG_YUV | 111 #ifdef DEBUG_YUV |
110 static char *PrintFOURCC(Uint32 code) | 112 static char * |
111 { | 113 PrintFOURCC (Uint32 code) |
112 static char buf[5]; | 114 { |
113 | 115 static char buf[5]; |
114 buf[3] = code >> 24; | 116 |
115 buf[2] = (code >> 16) & 0xFF; | 117 buf[3] = code >> 24; |
116 buf[1] = (code >> 8) & 0xFF; | 118 buf[2] = (code >> 16) & 0xFF; |
117 buf[0] = (code & 0xFF); | 119 buf[1] = (code >> 8) & 0xFF; |
118 return(buf); | 120 buf[0] = (code & 0xFF); |
119 } | 121 return (buf); |
120 #endif | 122 } |
121 | 123 #endif |
122 SDL_Overlay *DX5_CreateYUVOverlay(_THIS, int width, int height, Uint32 format, SDL_Surface *display) | 124 |
123 { | 125 SDL_Overlay * |
124 SDL_Overlay *overlay; | 126 DX5_CreateYUVOverlay (_THIS, int width, int height, Uint32 format, |
125 struct private_yuvhwdata *hwdata; | 127 SDL_Surface * display) |
128 { | |
129 SDL_Overlay *overlay; | |
130 struct private_yuvhwdata *hwdata; | |
126 | 131 |
127 #ifdef DEBUG_YUV | 132 #ifdef DEBUG_YUV |
128 DWORD numcodes; | 133 DWORD numcodes; |
129 DWORD *codes; | 134 DWORD *codes; |
130 | 135 |
131 printf("FOURCC format requested: 0x%x\n", PrintFOURCC(format)); | 136 printf ("FOURCC format requested: 0x%x\n", PrintFOURCC (format)); |
132 IDirectDraw2_GetFourCCCodes(ddraw2, &numcodes, NULL); | 137 IDirectDraw2_GetFourCCCodes (ddraw2, &numcodes, NULL); |
133 if ( numcodes ) { | 138 if (numcodes) { |
134 DWORD i; | 139 DWORD i; |
135 codes = SDL_malloc(numcodes*sizeof(*codes)); | 140 codes = SDL_malloc (numcodes * sizeof (*codes)); |
136 if ( codes ) { | 141 if (codes) { |
137 IDirectDraw2_GetFourCCCodes(ddraw2, &numcodes, codes); | 142 IDirectDraw2_GetFourCCCodes (ddraw2, &numcodes, codes); |
138 for ( i=0; i<numcodes; ++i ) { | 143 for (i = 0; i < numcodes; ++i) { |
139 fprintf(stderr, "Code %d: 0x%x\n", i, PrintFOURCC(codes[i])); | 144 fprintf (stderr, "Code %d: 0x%x\n", i, |
140 } | 145 PrintFOURCC (codes[i])); |
141 SDL_free(codes); | 146 } |
142 } | 147 SDL_free (codes); |
143 } else { | 148 } |
144 fprintf(stderr, "No FOURCC codes supported\n"); | 149 } else { |
145 } | 150 fprintf (stderr, "No FOURCC codes supported\n"); |
146 #endif | 151 } |
147 | 152 #endif |
148 /* Create the overlay structure */ | 153 |
149 overlay = (SDL_Overlay *)SDL_malloc(sizeof *overlay); | 154 /* Create the overlay structure */ |
150 if ( overlay == NULL ) { | 155 overlay = (SDL_Overlay *) SDL_malloc (sizeof *overlay); |
151 SDL_OutOfMemory(); | 156 if (overlay == NULL) { |
152 return(NULL); | 157 SDL_OutOfMemory (); |
153 } | 158 return (NULL); |
154 SDL_memset(overlay, 0, (sizeof *overlay)); | 159 } |
155 | 160 SDL_memset (overlay, 0, (sizeof *overlay)); |
156 /* Fill in the basic members */ | 161 |
157 overlay->format = format; | 162 /* Fill in the basic members */ |
158 overlay->w = width; | 163 overlay->format = format; |
159 overlay->h = height; | 164 overlay->w = width; |
160 | 165 overlay->h = height; |
161 /* Set up the YUV surface function structure */ | 166 |
162 overlay->hwfuncs = &dx5_yuvfuncs; | 167 /* Set up the YUV surface function structure */ |
163 | 168 overlay->hwfuncs = &dx5_yuvfuncs; |
164 /* Create the pixel data and lookup tables */ | 169 |
165 hwdata = (struct private_yuvhwdata *)SDL_malloc(sizeof *hwdata); | 170 /* Create the pixel data and lookup tables */ |
166 overlay->hwdata = hwdata; | 171 hwdata = (struct private_yuvhwdata *) SDL_malloc (sizeof *hwdata); |
167 if ( hwdata == NULL ) { | 172 overlay->hwdata = hwdata; |
168 SDL_OutOfMemory(); | 173 if (hwdata == NULL) { |
169 SDL_FreeYUVOverlay(overlay); | 174 SDL_OutOfMemory (); |
170 return(NULL); | 175 SDL_FreeYUVOverlay (overlay); |
171 } | 176 return (NULL); |
172 hwdata->surface = CreateYUVSurface(this, width, height, format); | 177 } |
173 if ( hwdata->surface == NULL ) { | 178 hwdata->surface = CreateYUVSurface (this, width, height, format); |
174 SDL_FreeYUVOverlay(overlay); | 179 if (hwdata->surface == NULL) { |
175 return(NULL); | 180 SDL_FreeYUVOverlay (overlay); |
176 } | 181 return (NULL); |
177 overlay->hw_overlay = 1; | 182 } |
178 | 183 overlay->hw_overlay = 1; |
179 /* Set up the plane pointers */ | 184 |
180 overlay->pitches = hwdata->pitches; | 185 /* Set up the plane pointers */ |
181 overlay->pixels = hwdata->planes; | 186 overlay->pitches = hwdata->pitches; |
182 switch (format) { | 187 overlay->pixels = hwdata->planes; |
183 case SDL_YV12_OVERLAY: | 188 switch (format) { |
184 case SDL_IYUV_OVERLAY: | 189 case SDL_YV12_OVERLAY: |
185 overlay->planes = 3; | 190 case SDL_IYUV_OVERLAY: |
186 break; | 191 overlay->planes = 3; |
187 default: | 192 break; |
188 overlay->planes = 1; | 193 default: |
189 break; | 194 overlay->planes = 1; |
190 } | 195 break; |
191 | 196 } |
192 /* We're all done.. */ | 197 |
193 return(overlay); | 198 /* We're all done.. */ |
194 } | 199 return (overlay); |
195 | 200 } |
196 int DX5_LockYUVOverlay(_THIS, SDL_Overlay *overlay) | 201 |
197 { | 202 int |
198 HRESULT result; | 203 DX5_LockYUVOverlay (_THIS, SDL_Overlay * overlay) |
199 LPDIRECTDRAWSURFACE3 surface; | 204 { |
200 DDSURFACEDESC ddsd; | 205 HRESULT result; |
201 | 206 LPDIRECTDRAWSURFACE3 surface; |
202 surface = overlay->hwdata->surface; | 207 DDSURFACEDESC ddsd; |
203 SDL_memset(&ddsd, 0, sizeof(ddsd)); | 208 |
204 ddsd.dwSize = sizeof(ddsd); | 209 surface = overlay->hwdata->surface; |
205 result = IDirectDrawSurface3_Lock(surface, NULL, | 210 SDL_memset (&ddsd, 0, sizeof (ddsd)); |
206 &ddsd, DDLOCK_NOSYSLOCK, NULL); | 211 ddsd.dwSize = sizeof (ddsd); |
207 if ( result == DDERR_SURFACELOST ) { | 212 result = IDirectDrawSurface3_Lock (surface, NULL, |
208 result = IDirectDrawSurface3_Restore(surface); | 213 &ddsd, DDLOCK_NOSYSLOCK, NULL); |
209 result = IDirectDrawSurface3_Lock(surface, NULL, &ddsd, | 214 if (result == DDERR_SURFACELOST) { |
210 (DDLOCK_NOSYSLOCK|DDLOCK_WAIT), NULL); | 215 result = IDirectDrawSurface3_Restore (surface); |
211 } | 216 result = IDirectDrawSurface3_Lock (surface, NULL, &ddsd, |
212 if ( result != DD_OK ) { | 217 (DDLOCK_NOSYSLOCK | DDLOCK_WAIT), |
213 SetDDerror("DirectDrawSurface3::Lock", result); | 218 NULL); |
214 return(-1); | 219 } |
215 } | 220 if (result != DD_OK) { |
216 | 221 SetDDerror ("DirectDrawSurface3::Lock", result); |
217 /* Find the pitch and offset values for the overlay */ | 222 return (-1); |
223 } | |
224 | |
225 /* Find the pitch and offset values for the overlay */ | |
218 #if defined(NONAMELESSUNION) | 226 #if defined(NONAMELESSUNION) |
219 overlay->pitches[0] = (Uint16)ddsd.u1.lPitch; | 227 overlay->pitches[0] = (Uint16) ddsd.u1.lPitch; |
220 #else | 228 #else |
221 overlay->pitches[0] = (Uint16)ddsd.lPitch; | 229 overlay->pitches[0] = (Uint16) ddsd.lPitch; |
222 #endif | 230 #endif |
223 overlay->pixels[0] = (Uint8 *)ddsd.lpSurface; | 231 overlay->pixels[0] = (Uint8 *) ddsd.lpSurface; |
224 switch (overlay->format) { | 232 switch (overlay->format) { |
225 case SDL_YV12_OVERLAY: | 233 case SDL_YV12_OVERLAY: |
226 case SDL_IYUV_OVERLAY: | 234 case SDL_IYUV_OVERLAY: |
227 /* Add the two extra planes */ | 235 /* Add the two extra planes */ |
228 overlay->pitches[1] = overlay->pitches[0] / 2; | 236 overlay->pitches[1] = overlay->pitches[0] / 2; |
229 overlay->pitches[2] = overlay->pitches[0] / 2; | 237 overlay->pitches[2] = overlay->pitches[0] / 2; |
230 overlay->pixels[1] = overlay->pixels[0] + | 238 overlay->pixels[1] = overlay->pixels[0] + |
231 overlay->pitches[0] * overlay->h; | 239 overlay->pitches[0] * overlay->h; |
232 overlay->pixels[2] = overlay->pixels[1] + | 240 overlay->pixels[2] = overlay->pixels[1] + |
233 overlay->pitches[1] * overlay->h / 2; | 241 overlay->pitches[1] * overlay->h / 2; |
234 break; | 242 break; |
235 default: | 243 default: |
236 /* Only one plane, no worries */ | 244 /* Only one plane, no worries */ |
237 break; | 245 break; |
238 } | 246 } |
239 return(0); | 247 return (0); |
240 } | 248 } |
241 | 249 |
242 void DX5_UnlockYUVOverlay(_THIS, SDL_Overlay *overlay) | 250 void |
243 { | 251 DX5_UnlockYUVOverlay (_THIS, SDL_Overlay * overlay) |
244 LPDIRECTDRAWSURFACE3 surface; | 252 { |
245 | 253 LPDIRECTDRAWSURFACE3 surface; |
246 surface = overlay->hwdata->surface; | 254 |
247 IDirectDrawSurface3_Unlock(surface, NULL); | 255 surface = overlay->hwdata->surface; |
248 } | 256 IDirectDrawSurface3_Unlock (surface, NULL); |
249 | 257 } |
250 int DX5_DisplayYUVOverlay(_THIS, SDL_Overlay *overlay, SDL_Rect *src, SDL_Rect *dst) | 258 |
251 { | 259 int |
252 HRESULT result; | 260 DX5_DisplayYUVOverlay (_THIS, SDL_Overlay * overlay, SDL_Rect * src, |
253 LPDIRECTDRAWSURFACE3 surface; | 261 SDL_Rect * dst) |
254 RECT srcrect, dstrect; | 262 { |
255 | 263 HRESULT result; |
256 surface = overlay->hwdata->surface; | 264 LPDIRECTDRAWSURFACE3 surface; |
257 srcrect.top = src->y; | 265 RECT srcrect, dstrect; |
258 srcrect.bottom = srcrect.top+src->h; | 266 |
259 srcrect.left = src->x; | 267 surface = overlay->hwdata->surface; |
260 srcrect.right = srcrect.left+src->w; | 268 srcrect.top = src->y; |
261 dstrect.top = SDL_bounds.top+dst->y; | 269 srcrect.bottom = srcrect.top + src->h; |
262 dstrect.left = SDL_bounds.left+dst->x; | 270 srcrect.left = src->x; |
263 dstrect.bottom = dstrect.top+dst->h; | 271 srcrect.right = srcrect.left + src->w; |
264 dstrect.right = dstrect.left+dst->w; | 272 dstrect.top = SDL_bounds.top + dst->y; |
273 dstrect.left = SDL_bounds.left + dst->x; | |
274 dstrect.bottom = dstrect.top + dst->h; | |
275 dstrect.right = dstrect.left + dst->w; | |
265 #ifdef USE_DIRECTX_OVERLAY | 276 #ifdef USE_DIRECTX_OVERLAY |
266 result = IDirectDrawSurface3_UpdateOverlay(surface, &srcrect, | 277 result = IDirectDrawSurface3_UpdateOverlay (surface, &srcrect, |
267 SDL_primary, &dstrect, DDOVER_SHOW, NULL); | 278 SDL_primary, &dstrect, |
268 if ( result != DD_OK ) { | 279 DDOVER_SHOW, NULL); |
269 SetDDerror("DirectDrawSurface3::UpdateOverlay", result); | 280 if (result != DD_OK) { |
270 return(-1); | 281 SetDDerror ("DirectDrawSurface3::UpdateOverlay", result); |
271 } | 282 return (-1); |
283 } | |
272 #else | 284 #else |
273 result = IDirectDrawSurface3_Blt(SDL_primary, &dstrect, surface, &srcrect, | 285 result = |
274 DDBLT_WAIT, NULL); | 286 IDirectDrawSurface3_Blt (SDL_primary, &dstrect, surface, &srcrect, |
275 if ( result != DD_OK ) { | 287 DDBLT_WAIT, NULL); |
276 SetDDerror("DirectDrawSurface3::Blt", result); | 288 if (result != DD_OK) { |
277 return(-1); | 289 SetDDerror ("DirectDrawSurface3::Blt", result); |
278 } | 290 return (-1); |
279 #endif | 291 } |
280 return(0); | 292 #endif |
281 } | 293 return (0); |
282 | 294 } |
283 void DX5_FreeYUVOverlay(_THIS, SDL_Overlay *overlay) | 295 |
284 { | 296 void |
285 struct private_yuvhwdata *hwdata; | 297 DX5_FreeYUVOverlay (_THIS, SDL_Overlay * overlay) |
286 | 298 { |
287 hwdata = overlay->hwdata; | 299 struct private_yuvhwdata *hwdata; |
288 if ( hwdata ) { | 300 |
289 if ( hwdata->surface ) { | 301 hwdata = overlay->hwdata; |
290 IDirectDrawSurface_Release(hwdata->surface); | 302 if (hwdata) { |
291 } | 303 if (hwdata->surface) { |
292 SDL_free(hwdata); | 304 IDirectDrawSurface_Release (hwdata->surface); |
293 } | 305 } |
294 } | 306 SDL_free (hwdata); |
295 | 307 } |
308 } | |
309 | |
310 /* vi: set ts=4 sw=4 expandtab: */ |