2 * Video Mixing Renderer for dx9
4 * Copyright 2004 Christian Costa
5 * Copyright 2008 Maarten Lankhorst
6 * Copyright 2012 Aric Stewart
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with this library; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
23 #include "quartz_private.h"
39 #include "wine/debug.h"
41 WINE_DEFAULT_DEBUG_CHANNEL(quartz
);
43 static inline const char *debugstr_normalized_rect(const VMR9NormalizedRect
*rect
)
45 if (!rect
) return "(null)";
46 return wine_dbg_sprintf("(%.8e,%.8e)-(%.8e,%.8e)", rect
->left
, rect
->top
, rect
->right
, rect
->bottom
);
49 static const BITMAPINFOHEADER
*get_bitmap_header(const AM_MEDIA_TYPE
*mt
)
51 if (IsEqualGUID(&mt
->formattype
, &FORMAT_VideoInfo
))
52 return &((VIDEOINFOHEADER
*)mt
->pbFormat
)->bmiHeader
;
54 return &((VIDEOINFOHEADER2
*)mt
->pbFormat
)->bmiHeader
;
59 struct strmbase_renderer renderer
;
60 struct video_window window
;
62 IAMCertifiedOutputProtection IAMCertifiedOutputProtection_iface
;
63 IAMFilterMiscFlags IAMFilterMiscFlags_iface
;
64 IVMRAspectRatioControl9 IVMRAspectRatioControl9_iface
;
65 IVMRFilterConfig IVMRFilterConfig_iface
;
66 IVMRFilterConfig9 IVMRFilterConfig9_iface
;
67 IVMRMixerBitmap9 IVMRMixerBitmap9_iface
;
68 IVMRMixerControl9 IVMRMixerControl9_iface
;
69 IVMRMonitorConfig IVMRMonitorConfig_iface
;
70 IVMRMonitorConfig9 IVMRMonitorConfig9_iface
;
71 IVMRSurfaceAllocatorNotify IVMRSurfaceAllocatorNotify_iface
;
72 IVMRSurfaceAllocatorNotify9 IVMRSurfaceAllocatorNotify9_iface
;
73 IVMRWindowlessControl IVMRWindowlessControl_iface
;
74 IVMRWindowlessControl9 IVMRWindowlessControl9_iface
;
76 /* Devil May Cry 3 releases the last IBaseFilter reference while still
77 * holding an IVMRSurfaceAllocatorNotify9 reference, and depends on
78 * IVMRSurfaceAllocator9::TerminateDevice() being called as a result.
79 * Native uses a separate reference count for IVMRSurfaceAllocatorNotify9. */
80 LONG IVMRSurfaceAllocatorNotify9_refcount
;
82 IAMVideoAccelerator IAMVideoAccelerator_iface
;
83 IOverlay IOverlay_iface
;
85 IVMRSurfaceAllocator9
*allocator
;
86 IVMRImagePresenter9
*presenter
;
92 * The Video Mixing Renderer supports 3 modes, renderless, windowless and windowed
93 * What I do is implement windowless as a special case of renderless, and then
94 * windowed also as a special case of windowless. This is probably the easiest way.
100 /* Presentation related members */
101 IDirect3DDevice9
*allocator_d3d9_dev
;
102 IDirect3DSurface9
**surfaces
;
107 HWND clipping_window
;
109 VMR9AspectRatioMode aspect_mode
;
112 static const BITMAPINFOHEADER
*get_filter_bitmap_header(const struct quartz_vmr
*filter
)
114 return get_bitmap_header(&filter
->renderer
.sink
.pin
.mt
);
117 static inline BOOL
is_vmr9(const struct quartz_vmr
*filter
)
119 return IsEqualGUID(&filter
->renderer
.filter
.clsid
, &CLSID_VideoMixingRenderer9
);
122 static inline struct quartz_vmr
*impl_from_video_window(struct video_window
*iface
)
124 return CONTAINING_RECORD(iface
, struct quartz_vmr
, window
);
127 static inline struct quartz_vmr
*impl_from_IAMCertifiedOutputProtection(IAMCertifiedOutputProtection
*iface
)
129 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IAMCertifiedOutputProtection_iface
);
132 static inline struct quartz_vmr
*impl_from_IAMFilterMiscFlags(IAMFilterMiscFlags
*iface
)
134 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IAMFilterMiscFlags_iface
);
137 static inline struct quartz_vmr
*impl_from_IVMRFilterConfig(IVMRFilterConfig
*iface
)
139 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRFilterConfig_iface
);
142 static inline struct quartz_vmr
*impl_from_IVMRFilterConfig9(IVMRFilterConfig9
*iface
)
144 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRFilterConfig9_iface
);
147 static inline struct quartz_vmr
*impl_from_IVMRMonitorConfig(IVMRMonitorConfig
*iface
)
149 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRMonitorConfig_iface
);
152 static inline struct quartz_vmr
*impl_from_IVMRMonitorConfig9(IVMRMonitorConfig9
*iface
)
154 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRMonitorConfig9_iface
);
157 static inline struct quartz_vmr
*impl_from_IVMRSurfaceAllocatorNotify(IVMRSurfaceAllocatorNotify
*iface
)
159 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRSurfaceAllocatorNotify_iface
);
162 static inline struct quartz_vmr
*impl_from_IVMRSurfaceAllocatorNotify9(IVMRSurfaceAllocatorNotify9
*iface
)
164 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRSurfaceAllocatorNotify9_iface
);
167 static inline struct quartz_vmr
*impl_from_IVMRWindowlessControl(IVMRWindowlessControl
*iface
)
169 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRWindowlessControl_iface
);
172 static inline struct quartz_vmr
*impl_from_IVMRWindowlessControl9(IVMRWindowlessControl9
*iface
)
174 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRWindowlessControl9_iface
);
177 struct default_presenter
179 IVMRImagePresenter9 IVMRImagePresenter9_iface
;
180 IVMRSurfaceAllocator9 IVMRSurfaceAllocator9_iface
;
184 IDirect3DDevice9
*d3d9_dev
;
185 IDirect3D9
*d3d9_ptr
;
186 IDirect3DSurface9
**d3d9_surfaces
;
190 VMR9AllocationInfo info
;
192 struct quartz_vmr
* pVMR9
;
193 IVMRSurfaceAllocatorNotify9
*SurfaceAllocatorNotify
;
196 static inline struct default_presenter
*impl_from_IVMRImagePresenter9(IVMRImagePresenter9
*iface
)
198 return CONTAINING_RECORD(iface
, struct default_presenter
, IVMRImagePresenter9_iface
);
201 static inline struct default_presenter
*impl_from_IVMRSurfaceAllocator9(IVMRSurfaceAllocator9
*iface
)
203 return CONTAINING_RECORD(iface
, struct default_presenter
, IVMRSurfaceAllocator9_iface
);
206 static HRESULT
default_presenter_create(struct quartz_vmr
*parent
, struct default_presenter
**presenter
);
208 static inline struct quartz_vmr
*impl_from_IBaseFilter(IBaseFilter
*iface
)
210 return CONTAINING_RECORD(iface
, struct quartz_vmr
, renderer
.filter
.IBaseFilter_iface
);
213 static HRESULT
vmr_render(struct strmbase_renderer
*iface
, IMediaSample
*sample
)
215 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
216 unsigned int data_size
, width
, depth
, src_pitch
;
217 const BITMAPINFOHEADER
*bitmap_header
;
218 REFERENCE_TIME start_time
, end_time
;
219 VMR9PresentationInfo info
= {};
220 D3DLOCKED_RECT locked_rect
;
225 TRACE("filter %p, sample %p.\n", filter
, sample
);
227 /* It is possible that there is no device at this point */
229 if (!filter
->allocator
|| !filter
->presenter
)
231 ERR("NO PRESENTER!!\n");
235 info
.dwFlags
= VMR9Sample_SrcDstRectsValid
;
237 if (SUCCEEDED(hr
= IMediaSample_GetTime(sample
, &start_time
, &end_time
)))
238 info
.dwFlags
|= VMR9Sample_TimeValid
;
240 if (IMediaSample_IsDiscontinuity(sample
) == S_OK
)
241 info
.dwFlags
|= VMR9Sample_Discontinuity
;
243 if (IMediaSample_IsPreroll(sample
) == S_OK
)
244 info
.dwFlags
|= VMR9Sample_Preroll
;
246 if (IMediaSample_IsSyncPoint(sample
) == S_OK
)
247 info
.dwFlags
|= VMR9Sample_SyncPoint
;
249 if (FAILED(hr
= IMediaSample_GetPointer(sample
, &data
)))
251 ERR("Failed to get pointer to sample data, hr %#lx.\n", hr
);
254 data_size
= IMediaSample_GetActualDataLength(sample
);
256 bitmap_header
= get_filter_bitmap_header(filter
);
257 width
= bitmap_header
->biWidth
;
258 height
= bitmap_header
->biHeight
;
259 depth
= bitmap_header
->biBitCount
;
260 if (bitmap_header
->biCompression
== mmioFOURCC('N','V','1','2')
261 || bitmap_header
->biCompression
== mmioFOURCC('Y','V','1','2'))
263 else /* packed YUV (UYVY or YUY2) or RGB */
264 src_pitch
= ((width
* depth
/ 8) + 3) & ~3;
266 info
.rtStart
= start_time
;
267 info
.rtEnd
= end_time
;
268 info
.szAspectRatio
.cx
= width
;
269 info
.szAspectRatio
.cy
= height
;
270 info
.lpSurf
= filter
->surfaces
[(++filter
->cur_surface
) % filter
->num_surfaces
];
272 if (FAILED(hr
= IDirect3DSurface9_LockRect(info
.lpSurf
, &locked_rect
, NULL
, D3DLOCK_DISCARD
)))
274 ERR("Failed to lock surface, hr %#lx.\n", hr
);
278 if (height
> 0 && bitmap_header
->biCompression
== BI_RGB
)
280 BYTE
*dst
= (BYTE
*)locked_rect
.pBits
+ (height
* locked_rect
.Pitch
);
281 const BYTE
*src
= data
;
283 TRACE("Inverting image.\n");
287 dst
-= locked_rect
.Pitch
;
288 memcpy(dst
, src
, width
* depth
/ 8);
292 else if (locked_rect
.Pitch
!= src_pitch
)
294 BYTE
*dst
= locked_rect
.pBits
;
295 const BYTE
*src
= data
;
297 height
= abs(height
);
299 TRACE("Source pitch %u does not match dest pitch %u; copying manually.\n",
300 src_pitch
, locked_rect
.Pitch
);
304 memcpy(dst
, src
, width
* depth
/ 8);
306 dst
+= locked_rect
.Pitch
;
311 memcpy(locked_rect
.pBits
, data
, data_size
);
314 IDirect3DSurface9_UnlockRect(info
.lpSurf
);
316 return IVMRImagePresenter9_PresentImage(filter
->presenter
, filter
->cookie
, &info
);
319 static HRESULT
vmr_query_accept(struct strmbase_renderer
*iface
, const AM_MEDIA_TYPE
*mt
)
321 if (!IsEqualIID(&mt
->majortype
, &MEDIATYPE_Video
) || !mt
->pbFormat
)
324 if (!IsEqualGUID(&mt
->formattype
, &FORMAT_VideoInfo
)
325 && !IsEqualGUID(&mt
->formattype
, &FORMAT_VideoInfo2
))
331 static HRESULT
initialize_device(struct quartz_vmr
*filter
, VMR9AllocationInfo
*info
, DWORD count
)
336 if (FAILED(hr
= IVMRSurfaceAllocator9_InitializeDevice(filter
->allocator
,
337 filter
->cookie
, info
, &count
)))
339 WARN("Failed to initialize device (flags %#lx), hr %#lx.\n", info
->dwFlags
, hr
);
343 for (i
= 0; i
< count
; ++i
)
345 if (FAILED(hr
= IVMRSurfaceAllocator9_GetSurface(filter
->allocator
,
346 filter
->cookie
, i
, 0, &filter
->surfaces
[i
])))
348 ERR("Failed to get surface %lu, hr %#lx.\n", i
, hr
);
350 IDirect3DSurface9_Release(filter
->surfaces
[i
]);
351 IVMRSurfaceAllocator9_TerminateDevice(filter
->allocator
, filter
->cookie
);
359 static HRESULT
allocate_surfaces(struct quartz_vmr
*filter
, const AM_MEDIA_TYPE
*mt
)
361 VMR9AllocationInfo info
= {};
365 const BITMAPINFOHEADER
*bmiheader
= get_bitmap_header(mt
);
375 {&MEDIASUBTYPE_ARGB1555
, D3DFMT_A1R5G5B5
, VMR9AllocFlag_TextureSurface
},
376 {&MEDIASUBTYPE_ARGB32
, D3DFMT_A8R8G8B8
, VMR9AllocFlag_TextureSurface
},
377 {&MEDIASUBTYPE_ARGB4444
, D3DFMT_A4R4G4B4
, VMR9AllocFlag_TextureSurface
},
379 {&MEDIASUBTYPE_RGB24
, D3DFMT_R8G8B8
, VMR9AllocFlag_TextureSurface
| VMR9AllocFlag_OffscreenSurface
},
380 {&MEDIASUBTYPE_RGB32
, D3DFMT_X8R8G8B8
, VMR9AllocFlag_TextureSurface
| VMR9AllocFlag_OffscreenSurface
},
381 {&MEDIASUBTYPE_RGB555
, D3DFMT_X1R5G5B5
, VMR9AllocFlag_TextureSurface
| VMR9AllocFlag_OffscreenSurface
},
382 {&MEDIASUBTYPE_RGB565
, D3DFMT_R5G6B5
, VMR9AllocFlag_TextureSurface
| VMR9AllocFlag_OffscreenSurface
},
384 {&MEDIASUBTYPE_NV12
, MAKEFOURCC('N','V','1','2'), VMR9AllocFlag_OffscreenSurface
},
385 {&MEDIASUBTYPE_UYVY
, D3DFMT_UYVY
, VMR9AllocFlag_OffscreenSurface
},
386 {&MEDIASUBTYPE_YUY2
, D3DFMT_YUY2
, VMR9AllocFlag_OffscreenSurface
},
387 {&MEDIASUBTYPE_YV12
, MAKEFOURCC('Y','V','1','2'), VMR9AllocFlag_OffscreenSurface
},
390 TRACE("Initializing in mode %u, our window %p, clipping window %p.\n",
391 filter
->mode
, filter
->window
.hwnd
, filter
->clipping_window
);
393 if (filter
->mode
== VMR9Mode_Windowless
&& !filter
->clipping_window
)
396 info
.Pool
= D3DPOOL_DEFAULT
;
397 info
.MinBuffers
= count
;
398 info
.dwWidth
= info
.szAspectRatio
.cx
= info
.szNativeSize
.cx
= bmiheader
->biWidth
;
399 info
.dwHeight
= info
.szAspectRatio
.cy
= info
.szNativeSize
.cy
= bmiheader
->biHeight
;
401 if (!(filter
->surfaces
= calloc(count
, sizeof(IDirect3DSurface9
*))))
402 return E_OUTOFMEMORY
;
403 filter
->num_surfaces
= count
;
404 filter
->cur_surface
= 0;
406 if (!is_vmr9(filter
))
408 switch (bmiheader
->biCompression
)
411 switch (bmiheader
->biBitCount
)
413 case 24: info
.Format
= D3DFMT_R8G8B8
; break;
414 case 32: info
.Format
= D3DFMT_X8R8G8B8
; break;
416 FIXME("Unhandled bit depth %u.\n", bmiheader
->biBitCount
);
417 free(filter
->surfaces
);
418 return VFW_E_TYPE_NOT_ACCEPTED
;
421 info
.dwFlags
= VMR9AllocFlag_TextureSurface
;
424 case mmioFOURCC('N','V','1','2'):
425 case mmioFOURCC('U','Y','V','Y'):
426 case mmioFOURCC('Y','U','Y','2'):
427 case mmioFOURCC('Y','V','1','2'):
428 info
.Format
= bmiheader
->biCompression
;
429 info
.dwFlags
= VMR9AllocFlag_OffscreenSurface
;
433 WARN("Unhandled video compression %#lx.\n", bmiheader
->biCompression
);
434 free(filter
->surfaces
);
435 return VFW_E_TYPE_NOT_ACCEPTED
;
437 if (FAILED(hr
= initialize_device(filter
, &info
, count
)))
438 free(filter
->surfaces
);
442 for (i
= 0; i
< ARRAY_SIZE(formats
); ++i
)
444 if (IsEqualGUID(&mt
->subtype
, formats
[i
].subtype
))
446 info
.Format
= formats
[i
].format
;
448 if (formats
[i
].flags
& VMR9AllocFlag_TextureSurface
)
450 info
.dwFlags
= VMR9AllocFlag_TextureSurface
;
451 if (SUCCEEDED(hr
= initialize_device(filter
, &info
, count
)))
455 if (formats
[i
].flags
& VMR9AllocFlag_OffscreenSurface
)
457 info
.dwFlags
= VMR9AllocFlag_OffscreenSurface
;
458 if (SUCCEEDED(hr
= initialize_device(filter
, &info
, count
)))
464 free(filter
->surfaces
);
465 return VFW_E_TYPE_NOT_ACCEPTED
;
468 static void vmr_init_stream(struct strmbase_renderer
*iface
)
470 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
472 if (filter
->window
.hwnd
&& filter
->window
.AutoShow
)
473 ShowWindow(filter
->window
.hwnd
, SW_SHOW
);
476 static void vmr_start_stream(struct strmbase_renderer
*iface
)
478 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
480 IVMRImagePresenter9_StartPresenting(filter
->presenter
, filter
->cookie
);
483 static void vmr_stop_stream(struct strmbase_renderer
*iface
)
485 struct quartz_vmr
*This
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
487 TRACE("(%p)\n", This
);
489 if (This
->renderer
.filter
.state
== State_Running
)
490 IVMRImagePresenter9_StopPresenting(This
->presenter
, This
->cookie
);
493 static HRESULT
vmr_connect(struct strmbase_renderer
*iface
, const AM_MEDIA_TYPE
*mt
)
495 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
496 const BITMAPINFOHEADER
*bitmap_header
= get_bitmap_header(mt
);
497 HWND window
= filter
->window
.hwnd
;
501 SetRect(&rect
, 0, 0, bitmap_header
->biWidth
, bitmap_header
->biHeight
);
502 filter
->window
.src
= rect
;
504 AdjustWindowRectEx(&rect
, GetWindowLongW(window
, GWL_STYLE
), FALSE
,
505 GetWindowLongW(window
, GWL_EXSTYLE
));
506 SetWindowPos(window
, NULL
, 0, 0, rect
.right
- rect
.left
, rect
.bottom
- rect
.top
,
507 SWP_NOMOVE
| SWP_NOZORDER
| SWP_NOACTIVATE
);
508 GetClientRect(window
, &filter
->window
.dst
);
511 || SUCCEEDED(hr
= IVMRFilterConfig9_SetRenderingMode(&filter
->IVMRFilterConfig9_iface
, VMR9Mode_Windowed
)))
512 hr
= allocate_surfaces(filter
, mt
);
517 static void deallocate_surfaces(struct quartz_vmr
*filter
)
521 if (filter
->mode
&& filter
->allocator
&& filter
->presenter
)
523 for (i
= 0; i
< filter
->num_surfaces
; ++i
)
524 IDirect3DSurface9_Release(filter
->surfaces
[i
]);
525 free(filter
->surfaces
);
527 IVMRSurfaceAllocator9_TerminateDevice(filter
->allocator
, filter
->cookie
);
528 filter
->num_surfaces
= 0;
532 static void vmr_disconnect(struct strmbase_renderer
*This
)
534 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&This
->filter
.IBaseFilter_iface
);
535 deallocate_surfaces(filter
);
538 static void vmr_destroy(struct strmbase_renderer
*iface
)
540 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
542 video_window_cleanup(&filter
->window
);
544 /* Devil May Cry 3 releases the IVMRSurfaceAllocatorNotify9 interface from
545 * TerminateDevice(). Artificially increase the reference count so that we
546 * don't free the filter yet. */
547 InterlockedIncrement(&filter
->renderer
.filter
.refcount
);
549 if (filter
->allocator
)
551 IVMRSurfaceAllocator9_TerminateDevice(filter
->allocator
, filter
->cookie
);
552 IVMRSurfaceAllocator9_Release(filter
->allocator
);
554 if (filter
->presenter
)
555 IVMRImagePresenter9_Release(filter
->presenter
);
557 filter
->num_surfaces
= 0;
558 if (filter
->allocator_d3d9_dev
)
560 IDirect3DDevice9_Release(filter
->allocator_d3d9_dev
);
561 filter
->allocator_d3d9_dev
= NULL
;
564 FreeLibrary(filter
->hD3d9
);
565 strmbase_renderer_cleanup(&filter
->renderer
);
566 if (!filter
->IVMRSurfaceAllocatorNotify9_refcount
)
570 static HRESULT
vmr_query_interface(struct strmbase_renderer
*iface
, REFIID iid
, void **out
)
572 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
574 if (IsEqualGUID(iid
, &IID_IVideoWindow
))
575 *out
= &filter
->window
.IVideoWindow_iface
;
576 else if (IsEqualGUID(iid
, &IID_IBasicVideo
))
577 *out
= &filter
->window
.IBasicVideo_iface
;
578 else if (IsEqualGUID(iid
, &IID_IAMCertifiedOutputProtection
))
579 *out
= &filter
->IAMCertifiedOutputProtection_iface
;
580 else if (IsEqualGUID(iid
, &IID_IAMFilterMiscFlags
))
581 *out
= &filter
->IAMFilterMiscFlags_iface
;
582 else if (IsEqualGUID(iid
, &IID_IVMRAspectRatioControl9
) && is_vmr9(filter
))
583 *out
= &filter
->IVMRAspectRatioControl9_iface
;
584 else if (IsEqualGUID(iid
, &IID_IVMRFilterConfig
) && !is_vmr9(filter
))
585 *out
= &filter
->IVMRFilterConfig_iface
;
586 else if (IsEqualGUID(iid
, &IID_IVMRFilterConfig9
) && is_vmr9(filter
))
587 *out
= &filter
->IVMRFilterConfig9_iface
;
588 else if (IsEqualGUID(iid
, &IID_IVMRMixerBitmap9
) && is_vmr9(filter
))
589 *out
= &filter
->IVMRMixerBitmap9_iface
;
590 else if (IsEqualGUID(iid
, &IID_IVMRMixerControl9
) && is_vmr9(filter
) && filter
->stream_count
)
591 *out
= &filter
->IVMRMixerControl9_iface
;
592 else if (IsEqualGUID(iid
, &IID_IVMRMonitorConfig
) && !is_vmr9(filter
))
593 *out
= &filter
->IVMRMonitorConfig_iface
;
594 else if (IsEqualGUID(iid
, &IID_IVMRMonitorConfig9
)
595 && filter
->mode
!= VMR9Mode_Renderless
&& is_vmr9(filter
))
596 *out
= &filter
->IVMRMonitorConfig9_iface
;
597 else if (IsEqualGUID(iid
, &IID_IVMRSurfaceAllocatorNotify
)
598 && filter
->mode
== (VMR9Mode
)VMRMode_Renderless
&& !is_vmr9(filter
))
599 *out
= &filter
->IVMRSurfaceAllocatorNotify_iface
;
600 else if (IsEqualGUID(iid
, &IID_IVMRSurfaceAllocatorNotify9
)
601 && filter
->mode
== VMR9Mode_Renderless
&& is_vmr9(filter
))
602 *out
= &filter
->IVMRSurfaceAllocatorNotify9_iface
;
603 else if (IsEqualGUID(iid
, &IID_IVMRWindowlessControl
)
604 && filter
->mode
== (VMR9Mode
)VMRMode_Windowless
&& !is_vmr9(filter
))
605 *out
= &filter
->IVMRWindowlessControl_iface
;
606 else if (IsEqualGUID(iid
, &IID_IVMRWindowlessControl9
)
607 && filter
->mode
== VMR9Mode_Windowless
&& is_vmr9(filter
))
608 *out
= &filter
->IVMRWindowlessControl9_iface
;
610 return E_NOINTERFACE
;
612 IUnknown_AddRef((IUnknown
*)*out
);
616 static HRESULT
vmr_pin_query_interface(struct strmbase_renderer
*iface
, REFIID iid
, void **out
)
618 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
620 if (IsEqualGUID(iid
, &IID_IAMVideoAccelerator
))
621 *out
= &filter
->IAMVideoAccelerator_iface
;
622 else if (IsEqualGUID(iid
, &IID_IOverlay
))
623 *out
= &filter
->IOverlay_iface
;
625 return E_NOINTERFACE
;
627 IUnknown_AddRef((IUnknown
*)*out
);
631 static const struct strmbase_renderer_ops renderer_ops
=
633 .renderer_query_accept
= vmr_query_accept
,
634 .renderer_render
= vmr_render
,
635 .renderer_init_stream
= vmr_init_stream
,
636 .renderer_start_stream
= vmr_start_stream
,
637 .renderer_stop_stream
= vmr_stop_stream
,
638 .renderer_connect
= vmr_connect
,
639 .renderer_disconnect
= vmr_disconnect
,
640 .renderer_destroy
= vmr_destroy
,
641 .renderer_query_interface
= vmr_query_interface
,
642 .renderer_pin_query_interface
= vmr_pin_query_interface
,
645 static RECT
vmr_get_default_rect(struct video_window
*This
)
647 struct quartz_vmr
*pVMR9
= impl_from_video_window(This
);
648 const BITMAPINFOHEADER
*bmiheader
= get_filter_bitmap_header(pVMR9
);
651 SetRect(&defRect
, 0, 0, bmiheader
->biWidth
, bmiheader
->biHeight
);
656 static HRESULT
vmr_get_current_image(struct video_window
*iface
, LONG
*size
, LONG
*image
)
658 struct quartz_vmr
*filter
= impl_from_video_window(iface
);
659 IDirect3DSurface9
*rt
= NULL
, *surface
= NULL
;
660 D3DLOCKED_RECT locked_rect
;
661 IDirect3DDevice9
*device
;
662 unsigned int row_size
;
663 BITMAPINFOHEADER bih
;
668 EnterCriticalSection(&filter
->renderer
.filter
.stream_cs
);
669 device
= filter
->allocator_d3d9_dev
;
671 bih
= *get_filter_bitmap_header(filter
);
672 bih
.biSizeImage
= bih
.biWidth
* bih
.biHeight
* bih
.biBitCount
/ 8;
676 *size
= sizeof(BITMAPINFOHEADER
) + bih
.biSizeImage
;
677 LeaveCriticalSection(&filter
->renderer
.filter
.stream_cs
);
681 if (FAILED(hr
= IDirect3DDevice9_GetRenderTarget(device
, 0, &rt
)))
684 if (FAILED(hr
= IDirect3DDevice9_CreateOffscreenPlainSurface(device
, bih
.biWidth
,
685 bih
.biHeight
, D3DFMT_X8R8G8B8
, D3DPOOL_SYSTEMMEM
, &surface
, NULL
)))
688 if (FAILED(hr
= IDirect3DDevice9_GetRenderTargetData(device
, rt
, surface
)))
691 if (FAILED(hr
= IDirect3DSurface9_LockRect(surface
, &locked_rect
, NULL
, D3DLOCK_READONLY
)))
695 memcpy(image
, &bih
, min(size_left
, sizeof(BITMAPINFOHEADER
)));
696 size_left
-= sizeof(BITMAPINFOHEADER
);
698 dst
= (char *)image
+ sizeof(BITMAPINFOHEADER
);
699 row_size
= bih
.biWidth
* bih
.biBitCount
/ 8;
701 for (i
= 0; i
< bih
.biHeight
&& size_left
> 0; ++i
)
703 memcpy(dst
, (char *)locked_rect
.pBits
+ (i
* locked_rect
.Pitch
), min(row_size
, size_left
));
705 size_left
-= row_size
;
708 IDirect3DSurface9_UnlockRect(surface
);
711 if (surface
) IDirect3DSurface9_Release(surface
);
712 if (rt
) IDirect3DSurface9_Release(rt
);
713 LeaveCriticalSection(&filter
->renderer
.filter
.stream_cs
);
717 static const struct video_window_ops window_ops
=
719 .get_default_rect
= vmr_get_default_rect
,
720 .get_current_image
= vmr_get_current_image
,
723 static const IVideoWindowVtbl IVideoWindow_VTable
=
725 BaseControlWindowImpl_QueryInterface
,
726 BaseControlWindowImpl_AddRef
,
727 BaseControlWindowImpl_Release
,
728 BaseControlWindowImpl_GetTypeInfoCount
,
729 BaseControlWindowImpl_GetTypeInfo
,
730 BaseControlWindowImpl_GetIDsOfNames
,
731 BaseControlWindowImpl_Invoke
,
732 BaseControlWindowImpl_put_Caption
,
733 BaseControlWindowImpl_get_Caption
,
734 BaseControlWindowImpl_put_WindowStyle
,
735 BaseControlWindowImpl_get_WindowStyle
,
736 BaseControlWindowImpl_put_WindowStyleEx
,
737 BaseControlWindowImpl_get_WindowStyleEx
,
738 BaseControlWindowImpl_put_AutoShow
,
739 BaseControlWindowImpl_get_AutoShow
,
740 BaseControlWindowImpl_put_WindowState
,
741 BaseControlWindowImpl_get_WindowState
,
742 BaseControlWindowImpl_put_BackgroundPalette
,
743 BaseControlWindowImpl_get_BackgroundPalette
,
744 BaseControlWindowImpl_put_Visible
,
745 BaseControlWindowImpl_get_Visible
,
746 BaseControlWindowImpl_put_Left
,
747 BaseControlWindowImpl_get_Left
,
748 BaseControlWindowImpl_put_Width
,
749 BaseControlWindowImpl_get_Width
,
750 BaseControlWindowImpl_put_Top
,
751 BaseControlWindowImpl_get_Top
,
752 BaseControlWindowImpl_put_Height
,
753 BaseControlWindowImpl_get_Height
,
754 BaseControlWindowImpl_put_Owner
,
755 BaseControlWindowImpl_get_Owner
,
756 BaseControlWindowImpl_put_MessageDrain
,
757 BaseControlWindowImpl_get_MessageDrain
,
758 BaseControlWindowImpl_get_BorderColor
,
759 BaseControlWindowImpl_put_BorderColor
,
760 BaseControlWindowImpl_get_FullScreenMode
,
761 BaseControlWindowImpl_put_FullScreenMode
,
762 BaseControlWindowImpl_SetWindowForeground
,
763 BaseControlWindowImpl_NotifyOwnerMessage
,
764 BaseControlWindowImpl_SetWindowPosition
,
765 BaseControlWindowImpl_GetWindowPosition
,
766 BaseControlWindowImpl_GetMinIdealImageSize
,
767 BaseControlWindowImpl_GetMaxIdealImageSize
,
768 BaseControlWindowImpl_GetRestorePosition
,
769 BaseControlWindowImpl_HideCursor
,
770 BaseControlWindowImpl_IsCursorHidden
773 static HRESULT WINAPI
AMCertifiedOutputProtection_QueryInterface(IAMCertifiedOutputProtection
*iface
,
774 REFIID riid
, void **ppv
)
776 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
777 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
780 static ULONG WINAPI
AMCertifiedOutputProtection_AddRef(IAMCertifiedOutputProtection
*iface
)
782 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
783 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
786 static ULONG WINAPI
AMCertifiedOutputProtection_Release(IAMCertifiedOutputProtection
*iface
)
788 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
789 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
792 static HRESULT WINAPI
AMCertifiedOutputProtection_KeyExchange(IAMCertifiedOutputProtection
*iface
,
793 GUID
* pRandom
, BYTE
** VarLenCertGH
,
794 DWORD
* pdwLengthCertGH
)
796 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
798 FIXME("(%p/%p)->(%p, %p, %p) stub\n", iface
, This
, pRandom
, VarLenCertGH
, pdwLengthCertGH
);
799 return VFW_E_NO_COPP_HW
;
802 static HRESULT WINAPI
AMCertifiedOutputProtection_SessionSequenceStart(IAMCertifiedOutputProtection
*iface
,
803 AMCOPPSignature
* pSig
)
805 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
807 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pSig
);
808 return VFW_E_NO_COPP_HW
;
811 static HRESULT WINAPI
AMCertifiedOutputProtection_ProtectionCommand(IAMCertifiedOutputProtection
*iface
,
812 const AMCOPPCommand
* cmd
)
814 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
816 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, cmd
);
817 return VFW_E_NO_COPP_HW
;
820 static HRESULT WINAPI
AMCertifiedOutputProtection_ProtectionStatus(IAMCertifiedOutputProtection
*iface
,
821 const AMCOPPStatusInput
* pStatusInput
,
822 AMCOPPStatusOutput
* pStatusOutput
)
824 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
826 FIXME("(%p/%p)->(%p, %p) stub\n", iface
, This
, pStatusInput
, pStatusOutput
);
827 return VFW_E_NO_COPP_HW
;
830 static const IAMCertifiedOutputProtectionVtbl IAMCertifiedOutputProtection_Vtbl
=
832 AMCertifiedOutputProtection_QueryInterface
,
833 AMCertifiedOutputProtection_AddRef
,
834 AMCertifiedOutputProtection_Release
,
835 AMCertifiedOutputProtection_KeyExchange
,
836 AMCertifiedOutputProtection_SessionSequenceStart
,
837 AMCertifiedOutputProtection_ProtectionCommand
,
838 AMCertifiedOutputProtection_ProtectionStatus
841 static HRESULT WINAPI
AMFilterMiscFlags_QueryInterface(IAMFilterMiscFlags
*iface
, REFIID riid
, void **ppv
) {
842 struct quartz_vmr
*This
= impl_from_IAMFilterMiscFlags(iface
);
843 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
846 static ULONG WINAPI
AMFilterMiscFlags_AddRef(IAMFilterMiscFlags
*iface
) {
847 struct quartz_vmr
*This
= impl_from_IAMFilterMiscFlags(iface
);
848 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
851 static ULONG WINAPI
AMFilterMiscFlags_Release(IAMFilterMiscFlags
*iface
) {
852 struct quartz_vmr
*This
= impl_from_IAMFilterMiscFlags(iface
);
853 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
856 static ULONG WINAPI
AMFilterMiscFlags_GetMiscFlags(IAMFilterMiscFlags
*iface
) {
857 return AM_FILTER_MISC_FLAGS_IS_RENDERER
;
860 static const IAMFilterMiscFlagsVtbl IAMFilterMiscFlags_Vtbl
= {
861 AMFilterMiscFlags_QueryInterface
,
862 AMFilterMiscFlags_AddRef
,
863 AMFilterMiscFlags_Release
,
864 AMFilterMiscFlags_GetMiscFlags
867 static HRESULT WINAPI
VMR7FilterConfig_QueryInterface(IVMRFilterConfig
*iface
, REFIID riid
,
870 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
871 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
874 static ULONG WINAPI
VMR7FilterConfig_AddRef(IVMRFilterConfig
*iface
)
876 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
877 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
880 static ULONG WINAPI
VMR7FilterConfig_Release(IVMRFilterConfig
*iface
)
882 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
883 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
886 static HRESULT WINAPI
VMR7FilterConfig_SetImageCompositor(IVMRFilterConfig
*iface
,
887 IVMRImageCompositor
*compositor
)
889 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
891 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, compositor
);
895 static HRESULT WINAPI
VMR7FilterConfig_SetNumberOfStreams(IVMRFilterConfig
*iface
, DWORD count
)
897 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig(iface
);
899 FIXME("filter %p, count %lu, stub!\n", filter
, count
);
904 static HRESULT WINAPI
VMR7FilterConfig_GetNumberOfStreams(IVMRFilterConfig
*iface
, DWORD
*max
)
906 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
908 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, max
);
912 static HRESULT WINAPI
VMR7FilterConfig_SetRenderingPrefs(IVMRFilterConfig
*iface
, DWORD flags
)
914 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig(iface
);
916 FIXME("filter %p, flags %#lx, stub!\n", filter
, flags
);
921 static HRESULT WINAPI
VMR7FilterConfig_GetRenderingPrefs(IVMRFilterConfig
*iface
, DWORD
*renderflags
)
923 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
925 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, renderflags
);
929 static HRESULT WINAPI
VMR7FilterConfig_SetRenderingMode(IVMRFilterConfig
*iface
, DWORD mode
)
931 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig(iface
);
933 TRACE("iface %p, mode %#lx.\n", iface
, mode
);
935 return IVMRFilterConfig9_SetRenderingMode(&filter
->IVMRFilterConfig9_iface
, mode
);
938 static HRESULT WINAPI
VMR7FilterConfig_GetRenderingMode(IVMRFilterConfig
*iface
, DWORD
*mode
)
940 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
942 TRACE("(%p/%p)->(%p)\n", iface
, This
, mode
);
943 if (!mode
) return E_POINTER
;
948 *mode
= VMRMode_Windowed
;
953 static const IVMRFilterConfigVtbl VMR7_FilterConfig_Vtbl
=
955 VMR7FilterConfig_QueryInterface
,
956 VMR7FilterConfig_AddRef
,
957 VMR7FilterConfig_Release
,
958 VMR7FilterConfig_SetImageCompositor
,
959 VMR7FilterConfig_SetNumberOfStreams
,
960 VMR7FilterConfig_GetNumberOfStreams
,
961 VMR7FilterConfig_SetRenderingPrefs
,
962 VMR7FilterConfig_GetRenderingPrefs
,
963 VMR7FilterConfig_SetRenderingMode
,
964 VMR7FilterConfig_GetRenderingMode
967 struct get_available_monitors_args
969 VMRMONITORINFO
*info7
;
970 VMR9MonitorInfo
*info9
;
975 static BOOL CALLBACK
get_available_monitors_proc(HMONITOR hmon
, HDC hdc
, LPRECT lprc
, LPARAM lparam
)
977 struct get_available_monitors_args
*args
= (struct get_available_monitors_args
*)lparam
;
980 if (args
->info7
|| args
->info9
)
983 if (!args
->arraysize
)
986 mi
.cbSize
= sizeof(mi
);
987 if (!GetMonitorInfoW(hmon
, (MONITORINFO
*)&mi
))
990 /* fill VMRMONITORINFO struct */
993 VMRMONITORINFO
*info
= args
->info7
++;
994 memset(info
, 0, sizeof(*info
));
996 if (args
->numdev
> 0)
998 info
->guid
.pGUID
= &info
->guid
.GUID
;
999 info
->guid
.GUID
.Data4
[7] = args
->numdev
;
1002 info
->guid
.pGUID
= NULL
;
1004 info
->rcMonitor
= mi
.rcMonitor
;
1006 info
->dwFlags
= mi
.dwFlags
;
1008 lstrcpynW(info
->szDevice
, mi
.szDevice
, ARRAY_SIZE(info
->szDevice
));
1010 /* FIXME: how to get these values? */
1011 info
->szDescription
[0] = 0;
1014 /* fill VMR9MonitorInfo struct */
1017 VMR9MonitorInfo
*info
= args
->info9
++;
1018 memset(info
, 0, sizeof(*info
));
1020 info
->uDevID
= 0; /* FIXME */
1021 info
->rcMonitor
= mi
.rcMonitor
;
1023 info
->dwFlags
= mi
.dwFlags
;
1025 lstrcpynW(info
->szDevice
, mi
.szDevice
, ARRAY_SIZE(info
->szDevice
));
1027 /* FIXME: how to get these values? */
1028 info
->szDescription
[0] = 0;
1029 info
->dwVendorId
= 0;
1030 info
->dwDeviceId
= 0;
1031 info
->dwSubSysId
= 0;
1032 info
->dwRevision
= 0;
1042 static HRESULT WINAPI
VMR7MonitorConfig_QueryInterface(IVMRMonitorConfig
*iface
, REFIID riid
,
1045 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1046 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1049 static ULONG WINAPI
VMR7MonitorConfig_AddRef(IVMRMonitorConfig
*iface
)
1051 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1052 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1055 static ULONG WINAPI
VMR7MonitorConfig_Release(IVMRMonitorConfig
*iface
)
1057 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1058 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1061 static HRESULT WINAPI
VMR7MonitorConfig_SetMonitor(IVMRMonitorConfig
*iface
, const VMRGUID
*pGUID
)
1063 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1065 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pGUID
);
1073 static HRESULT WINAPI
VMR7MonitorConfig_GetMonitor(IVMRMonitorConfig
*iface
, VMRGUID
*pGUID
)
1075 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1077 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pGUID
);
1082 pGUID
->pGUID
= NULL
; /* default DirectDraw device */
1086 static HRESULT WINAPI
VMR7MonitorConfig_SetDefaultMonitor(IVMRMonitorConfig
*iface
,
1087 const VMRGUID
*pGUID
)
1089 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1091 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pGUID
);
1099 static HRESULT WINAPI
VMR7MonitorConfig_GetDefaultMonitor(IVMRMonitorConfig
*iface
, VMRGUID
*pGUID
)
1101 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1103 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pGUID
);
1108 pGUID
->pGUID
= NULL
; /* default DirectDraw device */
1112 static HRESULT WINAPI
VMR7MonitorConfig_GetAvailableMonitors(IVMRMonitorConfig
*iface
,
1113 VMRMONITORINFO
*info
, DWORD arraysize
,
1116 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1117 struct get_available_monitors_args args
;
1119 TRACE("filter %p, info %p, arraysize %lu, numdev %p.\n", This
, info
, arraysize
, numdev
);
1124 if (info
&& arraysize
== 0)
1125 return E_INVALIDARG
;
1129 args
.arraysize
= arraysize
;
1131 EnumDisplayMonitors(NULL
, NULL
, get_available_monitors_proc
, (LPARAM
)&args
);
1133 *numdev
= args
.numdev
;
1137 static const IVMRMonitorConfigVtbl VMR7_MonitorConfig_Vtbl
=
1139 VMR7MonitorConfig_QueryInterface
,
1140 VMR7MonitorConfig_AddRef
,
1141 VMR7MonitorConfig_Release
,
1142 VMR7MonitorConfig_SetMonitor
,
1143 VMR7MonitorConfig_GetMonitor
,
1144 VMR7MonitorConfig_SetDefaultMonitor
,
1145 VMR7MonitorConfig_GetDefaultMonitor
,
1146 VMR7MonitorConfig_GetAvailableMonitors
1149 static HRESULT WINAPI
VMR9MonitorConfig_QueryInterface(IVMRMonitorConfig9
*iface
, REFIID riid
,
1152 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1153 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1156 static ULONG WINAPI
VMR9MonitorConfig_AddRef(IVMRMonitorConfig9
*iface
)
1158 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1159 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1162 static ULONG WINAPI
VMR9MonitorConfig_Release(IVMRMonitorConfig9
*iface
)
1164 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1165 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1168 static HRESULT WINAPI
VMR9MonitorConfig_SetMonitor(IVMRMonitorConfig9
*iface
, UINT uDev
)
1170 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1172 FIXME("(%p/%p)->(%u) stub\n", iface
, This
, uDev
);
1177 static HRESULT WINAPI
VMR9MonitorConfig_GetMonitor(IVMRMonitorConfig9
*iface
, UINT
*uDev
)
1179 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1181 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, uDev
);
1190 static HRESULT WINAPI
VMR9MonitorConfig_SetDefaultMonitor(IVMRMonitorConfig9
*iface
, UINT uDev
)
1192 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1194 FIXME("(%p/%p)->(%u) stub\n", iface
, This
, uDev
);
1199 static HRESULT WINAPI
VMR9MonitorConfig_GetDefaultMonitor(IVMRMonitorConfig9
*iface
, UINT
*uDev
)
1201 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1203 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, uDev
);
1212 static HRESULT WINAPI
VMR9MonitorConfig_GetAvailableMonitors(IVMRMonitorConfig9
*iface
,
1213 VMR9MonitorInfo
*info
, DWORD arraysize
,
1216 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1217 struct get_available_monitors_args args
;
1219 TRACE("filter %p, info %p, arraysize %lu, numdev %p.\n", This
, info
, arraysize
, numdev
);
1224 if (info
&& arraysize
== 0)
1225 return E_INVALIDARG
;
1229 args
.arraysize
= arraysize
;
1231 EnumDisplayMonitors(NULL
, NULL
, get_available_monitors_proc
, (LPARAM
)&args
);
1233 *numdev
= args
.numdev
;
1237 static const IVMRMonitorConfig9Vtbl VMR9_MonitorConfig_Vtbl
=
1239 VMR9MonitorConfig_QueryInterface
,
1240 VMR9MonitorConfig_AddRef
,
1241 VMR9MonitorConfig_Release
,
1242 VMR9MonitorConfig_SetMonitor
,
1243 VMR9MonitorConfig_GetMonitor
,
1244 VMR9MonitorConfig_SetDefaultMonitor
,
1245 VMR9MonitorConfig_GetDefaultMonitor
,
1246 VMR9MonitorConfig_GetAvailableMonitors
1249 static HRESULT WINAPI
VMR9FilterConfig_QueryInterface(IVMRFilterConfig9
*iface
, REFIID riid
, LPVOID
* ppv
)
1251 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1252 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1255 static ULONG WINAPI
VMR9FilterConfig_AddRef(IVMRFilterConfig9
*iface
)
1257 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1258 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1261 static ULONG WINAPI
VMR9FilterConfig_Release(IVMRFilterConfig9
*iface
)
1263 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1264 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1267 static HRESULT WINAPI
VMR9FilterConfig_SetImageCompositor(IVMRFilterConfig9
*iface
, IVMRImageCompositor9
*compositor
)
1269 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1271 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, compositor
);
1275 static HRESULT WINAPI
VMR9FilterConfig_SetNumberOfStreams(IVMRFilterConfig9
*iface
, DWORD count
)
1277 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig9(iface
);
1279 FIXME("iface %p, count %lu, stub!\n", iface
, count
);
1283 WARN("Application requested zero streams; returning E_INVALIDARG.\n");
1284 return E_INVALIDARG
;
1287 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1289 if (filter
->stream_count
)
1291 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1292 WARN("Stream count is already set; returning VFW_E_WRONG_STATE.\n");
1293 return VFW_E_WRONG_STATE
;
1296 filter
->stream_count
= count
;
1298 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1302 static HRESULT WINAPI
VMR9FilterConfig_GetNumberOfStreams(IVMRFilterConfig9
*iface
, DWORD
*count
)
1304 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig9(iface
);
1306 TRACE("filter %p, count %p.\n", filter
, count
);
1308 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1310 if (!filter
->stream_count
)
1312 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1313 return VFW_E_VMR_NOT_IN_MIXER_MODE
;
1316 *count
= filter
->stream_count
;
1318 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1322 static HRESULT WINAPI
VMR9FilterConfig_SetRenderingPrefs(IVMRFilterConfig9
*iface
, DWORD flags
)
1324 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig9(iface
);
1326 TRACE("filter %p, flags %#lx.\n", filter
, flags
);
1331 static HRESULT WINAPI
VMR9FilterConfig_GetRenderingPrefs(IVMRFilterConfig9
*iface
, DWORD
*renderflags
)
1333 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1335 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, renderflags
);
1339 static HRESULT WINAPI
VMR9FilterConfig_SetRenderingMode(IVMRFilterConfig9
*iface
, DWORD mode
)
1341 struct default_presenter
*default_presenter
;
1343 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1345 TRACE("filter %p, mode %lu.\n", This
, mode
);
1347 EnterCriticalSection(&This
->renderer
.filter
.filter_cs
);
1350 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1351 return VFW_E_WRONG_STATE
;
1356 case VMR9Mode_Windowed
:
1357 case VMR9Mode_Windowless
:
1358 if (FAILED(hr
= default_presenter_create(This
, &default_presenter
)))
1360 ERR("Failed to create default presenter, hr %#lx.\n", hr
);
1361 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1364 This
->allocator
= &default_presenter
->IVMRSurfaceAllocator9_iface
;
1365 This
->presenter
= &default_presenter
->IVMRImagePresenter9_iface
;
1366 IVMRImagePresenter9_AddRef(This
->presenter
);
1368 IVMRSurfaceAllocator9_AdviseNotify(This
->allocator
, &This
->IVMRSurfaceAllocatorNotify9_iface
);
1370 case VMR9Mode_Renderless
:
1373 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1374 return E_INVALIDARG
;
1377 if (mode
!= VMR9Mode_Windowed
)
1378 video_window_cleanup(&This
->window
);
1381 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1385 static HRESULT WINAPI
VMR9FilterConfig_GetRenderingMode(IVMRFilterConfig9
*iface
, DWORD
*mode
)
1387 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1389 TRACE("(%p/%p)->(%p)\n", iface
, This
, mode
);
1396 *mode
= VMR9Mode_Windowed
;
1401 static const IVMRFilterConfig9Vtbl VMR9_FilterConfig_Vtbl
=
1403 VMR9FilterConfig_QueryInterface
,
1404 VMR9FilterConfig_AddRef
,
1405 VMR9FilterConfig_Release
,
1406 VMR9FilterConfig_SetImageCompositor
,
1407 VMR9FilterConfig_SetNumberOfStreams
,
1408 VMR9FilterConfig_GetNumberOfStreams
,
1409 VMR9FilterConfig_SetRenderingPrefs
,
1410 VMR9FilterConfig_GetRenderingPrefs
,
1411 VMR9FilterConfig_SetRenderingMode
,
1412 VMR9FilterConfig_GetRenderingMode
1415 static HRESULT WINAPI
VMR7WindowlessControl_QueryInterface(IVMRWindowlessControl
*iface
, REFIID riid
,
1418 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1419 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1422 static ULONG WINAPI
VMR7WindowlessControl_AddRef(IVMRWindowlessControl
*iface
)
1424 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1425 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1428 static ULONG WINAPI
VMR7WindowlessControl_Release(IVMRWindowlessControl
*iface
)
1430 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1431 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1434 static HRESULT WINAPI
VMR7WindowlessControl_GetNativeVideoSize(IVMRWindowlessControl
*iface
,
1435 LONG
*width
, LONG
*height
, LONG
*aspect_width
, LONG
*aspect_height
)
1437 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl(iface
);
1438 const BITMAPINFOHEADER
*bmiheader
= get_filter_bitmap_header(filter
);
1440 TRACE("filter %p, width %p, height %p, aspect_width %p, aspect_height %p.\n",
1441 filter
, width
, height
, aspect_width
, aspect_height
);
1443 if (!width
|| !height
)
1446 *width
= bmiheader
->biWidth
;
1447 *height
= bmiheader
->biHeight
;
1449 *aspect_width
= bmiheader
->biWidth
;
1451 *aspect_height
= bmiheader
->biHeight
;
1456 static HRESULT WINAPI
VMR7WindowlessControl_GetMinIdealVideoSize(IVMRWindowlessControl
*iface
,
1457 LONG
*width
, LONG
*height
)
1459 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1461 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1465 static HRESULT WINAPI
VMR7WindowlessControl_GetMaxIdealVideoSize(IVMRWindowlessControl
*iface
,
1466 LONG
*width
, LONG
*height
)
1468 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1470 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1474 static HRESULT WINAPI
VMR7WindowlessControl_SetVideoPosition(IVMRWindowlessControl
*iface
,
1475 const RECT
*source
, const RECT
*dest
)
1477 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1479 TRACE("(%p/%p)->(%p, %p)\n", iface
, This
, source
, dest
);
1481 EnterCriticalSection(&This
->renderer
.filter
.filter_cs
);
1484 This
->window
.src
= *source
;
1486 This
->window
.dst
= *dest
;
1488 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1493 static HRESULT WINAPI
VMR7WindowlessControl_GetVideoPosition(IVMRWindowlessControl
*iface
,
1494 RECT
*source
, RECT
*dest
)
1496 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1499 *source
= This
->window
.src
;
1502 *dest
= This
->window
.dst
;
1504 FIXME("(%p/%p)->(%p/%p) stub\n", iface
, This
, source
, dest
);
1508 static HRESULT WINAPI
VMR7WindowlessControl_GetAspectRatioMode(IVMRWindowlessControl
*iface
,
1511 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1513 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1517 static HRESULT WINAPI
VMR7WindowlessControl_SetAspectRatioMode(IVMRWindowlessControl
*iface
,
1520 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1522 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1526 static HRESULT WINAPI
VMR7WindowlessControl_SetVideoClippingWindow(IVMRWindowlessControl
*iface
, HWND window
)
1528 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl(iface
);
1530 TRACE("iface %p, window %p.\n", iface
, window
);
1532 return IVMRWindowlessControl9_SetVideoClippingWindow(&filter
->IVMRWindowlessControl9_iface
, window
);
1535 static HRESULT WINAPI
VMR7WindowlessControl_RepaintVideo(IVMRWindowlessControl
*iface
,
1538 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1540 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1544 static HRESULT WINAPI
VMR7WindowlessControl_DisplayModeChanged(IVMRWindowlessControl
*iface
)
1546 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1548 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1552 static HRESULT WINAPI
VMR7WindowlessControl_GetCurrentImage(IVMRWindowlessControl
*iface
,
1555 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1557 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1561 static HRESULT WINAPI
VMR7WindowlessControl_SetBorderColor(IVMRWindowlessControl
*iface
,
1564 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1566 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1570 static HRESULT WINAPI
VMR7WindowlessControl_GetBorderColor(IVMRWindowlessControl
*iface
,
1573 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1575 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1579 static HRESULT WINAPI
VMR7WindowlessControl_SetColorKey(IVMRWindowlessControl
*iface
, COLORREF color
)
1581 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1583 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1587 static HRESULT WINAPI
VMR7WindowlessControl_GetColorKey(IVMRWindowlessControl
*iface
, COLORREF
*color
)
1589 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1591 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1595 static const IVMRWindowlessControlVtbl VMR7_WindowlessControl_Vtbl
=
1597 VMR7WindowlessControl_QueryInterface
,
1598 VMR7WindowlessControl_AddRef
,
1599 VMR7WindowlessControl_Release
,
1600 VMR7WindowlessControl_GetNativeVideoSize
,
1601 VMR7WindowlessControl_GetMinIdealVideoSize
,
1602 VMR7WindowlessControl_GetMaxIdealVideoSize
,
1603 VMR7WindowlessControl_SetVideoPosition
,
1604 VMR7WindowlessControl_GetVideoPosition
,
1605 VMR7WindowlessControl_GetAspectRatioMode
,
1606 VMR7WindowlessControl_SetAspectRatioMode
,
1607 VMR7WindowlessControl_SetVideoClippingWindow
,
1608 VMR7WindowlessControl_RepaintVideo
,
1609 VMR7WindowlessControl_DisplayModeChanged
,
1610 VMR7WindowlessControl_GetCurrentImage
,
1611 VMR7WindowlessControl_SetBorderColor
,
1612 VMR7WindowlessControl_GetBorderColor
,
1613 VMR7WindowlessControl_SetColorKey
,
1614 VMR7WindowlessControl_GetColorKey
1617 static HRESULT WINAPI
VMR9WindowlessControl_QueryInterface(IVMRWindowlessControl9
*iface
, REFIID riid
, LPVOID
* ppv
)
1619 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1620 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1623 static ULONG WINAPI
VMR9WindowlessControl_AddRef(IVMRWindowlessControl9
*iface
)
1625 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1626 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1629 static ULONG WINAPI
VMR9WindowlessControl_Release(IVMRWindowlessControl9
*iface
)
1631 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1632 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1635 static HRESULT WINAPI
VMR9WindowlessControl_GetNativeVideoSize(IVMRWindowlessControl9
*iface
,
1636 LONG
*width
, LONG
*height
, LONG
*aspect_width
, LONG
*aspect_height
)
1638 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1639 const BITMAPINFOHEADER
*bmiheader
= get_filter_bitmap_header(filter
);
1641 TRACE("filter %p, width %p, height %p, aspect_width %p, aspect_height %p.\n",
1642 filter
, width
, height
, aspect_width
, aspect_height
);
1644 if (!width
|| !height
)
1647 *width
= bmiheader
->biWidth
;
1648 *height
= bmiheader
->biHeight
;
1650 *aspect_width
= bmiheader
->biWidth
;
1652 *aspect_height
= bmiheader
->biHeight
;
1657 static HRESULT WINAPI
VMR9WindowlessControl_GetMinIdealVideoSize(IVMRWindowlessControl9
*iface
, LONG
*width
, LONG
*height
)
1659 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1661 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1665 static HRESULT WINAPI
VMR9WindowlessControl_GetMaxIdealVideoSize(IVMRWindowlessControl9
*iface
, LONG
*width
, LONG
*height
)
1667 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1669 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1673 static HRESULT WINAPI
VMR9WindowlessControl_SetVideoPosition(IVMRWindowlessControl9
*iface
,
1674 const RECT
*src
, const RECT
*dst
)
1676 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1678 TRACE("filter %p, src %s, dst %s.\n", filter
, wine_dbgstr_rect(src
), wine_dbgstr_rect(dst
));
1680 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1683 filter
->window
.src
= *src
;
1685 filter
->window
.dst
= *dst
;
1687 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1692 static HRESULT WINAPI
VMR9WindowlessControl_GetVideoPosition(IVMRWindowlessControl9
*iface
, RECT
*src
, RECT
*dst
)
1694 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1696 TRACE("filter %p, src %p, dst %p.\n", filter
, src
, dst
);
1699 *src
= filter
->window
.src
;
1702 *dst
= filter
->window
.dst
;
1707 static HRESULT WINAPI
VMR9WindowlessControl_GetAspectRatioMode(IVMRWindowlessControl9
*iface
, DWORD
*mode
)
1709 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1711 TRACE("filter %p, mode %p.\n", filter
, mode
);
1713 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1714 *mode
= filter
->aspect_mode
;
1715 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1719 static HRESULT WINAPI
VMR9WindowlessControl_SetAspectRatioMode(IVMRWindowlessControl9
*iface
, DWORD mode
)
1721 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1723 TRACE("filter %p, mode %lu.\n", filter
, mode
);
1725 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1726 filter
->aspect_mode
= mode
;
1727 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1731 static HRESULT WINAPI
VMR9WindowlessControl_SetVideoClippingWindow(IVMRWindowlessControl9
*iface
, HWND window
)
1733 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1736 TRACE("filter %p, window %p.\n", filter
, window
);
1738 if (!IsWindow(window
))
1740 WARN("Invalid window %p, returning E_INVALIDARG.\n", window
);
1741 return E_INVALIDARG
;
1744 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1746 if (filter
->renderer
.sink
.pin
.peer
)
1748 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1749 WARN("Attempt to set the clipping window while connected; returning VFW_E_WRONG_STATE.\n");
1750 return VFW_E_WRONG_STATE
;
1753 filter
->clipping_window
= window
;
1755 hr
= IVMRFilterConfig9_SetNumberOfStreams(&filter
->IVMRFilterConfig9_iface
, 4);
1757 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1761 static HRESULT WINAPI
VMR9WindowlessControl_RepaintVideo(IVMRWindowlessControl9
*iface
, HWND hwnd
, HDC hdc
)
1763 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1766 FIXME("(%p/%p)->(...) semi-stub\n", iface
, This
);
1768 EnterCriticalSection(&This
->renderer
.filter
.filter_cs
);
1769 if (hwnd
!= This
->clipping_window
)
1771 ERR("Not handling changing windows yet!!!\n");
1772 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1776 if (!This
->allocator_d3d9_dev
)
1778 ERR("No d3d9 device!\n");
1779 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1780 return VFW_E_WRONG_STATE
;
1783 /* Windowless extension */
1784 hr
= IDirect3DDevice9_Present(This
->allocator_d3d9_dev
, NULL
, NULL
, NULL
, NULL
);
1785 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1790 static HRESULT WINAPI
VMR9WindowlessControl_DisplayModeChanged(IVMRWindowlessControl9
*iface
)
1792 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1794 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1798 static HRESULT WINAPI
VMR9WindowlessControl_GetCurrentImage(IVMRWindowlessControl9
*iface
, BYTE
**dib
)
1800 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1802 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1806 static HRESULT WINAPI
VMR9WindowlessControl_SetBorderColor(IVMRWindowlessControl9
*iface
, COLORREF color
)
1808 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1810 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1814 static HRESULT WINAPI
VMR9WindowlessControl_GetBorderColor(IVMRWindowlessControl9
*iface
, COLORREF
*color
)
1816 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1818 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1822 static const IVMRWindowlessControl9Vtbl VMR9_WindowlessControl_Vtbl
=
1824 VMR9WindowlessControl_QueryInterface
,
1825 VMR9WindowlessControl_AddRef
,
1826 VMR9WindowlessControl_Release
,
1827 VMR9WindowlessControl_GetNativeVideoSize
,
1828 VMR9WindowlessControl_GetMinIdealVideoSize
,
1829 VMR9WindowlessControl_GetMaxIdealVideoSize
,
1830 VMR9WindowlessControl_SetVideoPosition
,
1831 VMR9WindowlessControl_GetVideoPosition
,
1832 VMR9WindowlessControl_GetAspectRatioMode
,
1833 VMR9WindowlessControl_SetAspectRatioMode
,
1834 VMR9WindowlessControl_SetVideoClippingWindow
,
1835 VMR9WindowlessControl_RepaintVideo
,
1836 VMR9WindowlessControl_DisplayModeChanged
,
1837 VMR9WindowlessControl_GetCurrentImage
,
1838 VMR9WindowlessControl_SetBorderColor
,
1839 VMR9WindowlessControl_GetBorderColor
1842 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_QueryInterface(IVMRSurfaceAllocatorNotify
*iface
,
1843 REFIID riid
, LPVOID
* ppv
)
1845 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1846 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1849 static ULONG WINAPI
VMR7SurfaceAllocatorNotify_AddRef(IVMRSurfaceAllocatorNotify
*iface
)
1851 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1852 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1855 static ULONG WINAPI
VMR7SurfaceAllocatorNotify_Release(IVMRSurfaceAllocatorNotify
*iface
)
1857 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1858 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1861 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_AdviseSurfaceAllocator(IVMRSurfaceAllocatorNotify
*iface
,
1863 IVMRSurfaceAllocator
*alloc
)
1865 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1867 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1871 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_SetDDrawDevice(IVMRSurfaceAllocatorNotify
*iface
,
1872 IDirectDraw7
*device
, HMONITOR monitor
)
1874 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1876 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1880 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_ChangeDDrawDevice(IVMRSurfaceAllocatorNotify
*iface
,
1881 IDirectDraw7
*device
, HMONITOR monitor
)
1883 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1885 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1889 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_RestoreDDrawSurfaces(IVMRSurfaceAllocatorNotify
*iface
)
1891 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1893 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1897 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_NotifyEvent(IVMRSurfaceAllocatorNotify
*iface
, LONG code
,
1898 LONG_PTR param1
, LONG_PTR param2
)
1900 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1902 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1906 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_SetBorderColor(IVMRSurfaceAllocatorNotify
*iface
,
1909 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1911 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1915 static const IVMRSurfaceAllocatorNotifyVtbl VMR7_SurfaceAllocatorNotify_Vtbl
=
1917 VMR7SurfaceAllocatorNotify_QueryInterface
,
1918 VMR7SurfaceAllocatorNotify_AddRef
,
1919 VMR7SurfaceAllocatorNotify_Release
,
1920 VMR7SurfaceAllocatorNotify_AdviseSurfaceAllocator
,
1921 VMR7SurfaceAllocatorNotify_SetDDrawDevice
,
1922 VMR7SurfaceAllocatorNotify_ChangeDDrawDevice
,
1923 VMR7SurfaceAllocatorNotify_RestoreDDrawSurfaces
,
1924 VMR7SurfaceAllocatorNotify_NotifyEvent
,
1925 VMR7SurfaceAllocatorNotify_SetBorderColor
1928 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_QueryInterface(IVMRSurfaceAllocatorNotify9
*iface
, REFIID riid
, LPVOID
* ppv
)
1930 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
1931 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1934 static ULONG WINAPI
VMR9SurfaceAllocatorNotify_AddRef(IVMRSurfaceAllocatorNotify9
*iface
)
1936 struct quartz_vmr
*filter
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
1937 ULONG refcount
= InterlockedIncrement(&filter
->IVMRSurfaceAllocatorNotify9_refcount
);
1939 TRACE("%p increasing refcount to %lu.\n", iface
, refcount
);
1944 static ULONG WINAPI
VMR9SurfaceAllocatorNotify_Release(IVMRSurfaceAllocatorNotify9
*iface
)
1946 struct quartz_vmr
*filter
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
1947 ULONG refcount
= InterlockedDecrement(&filter
->IVMRSurfaceAllocatorNotify9_refcount
);
1949 TRACE("%p decreasing refcount to %lu.\n", iface
, refcount
);
1951 if (!refcount
&& !filter
->renderer
.filter
.refcount
)
1957 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_AdviseSurfaceAllocator(
1958 IVMRSurfaceAllocatorNotify9
*iface
, DWORD_PTR cookie
, IVMRSurfaceAllocator9
*allocator
)
1960 struct quartz_vmr
*filter
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
1961 IVMRImagePresenter9
*presenter
;
1963 TRACE("filter %p, cookie %#Ix, allocator %p.\n", filter
, cookie
, allocator
);
1965 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1967 filter
->cookie
= cookie
;
1969 if (filter
->renderer
.sink
.pin
.peer
)
1971 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1972 WARN("Attempt to set allocator while connected; returning VFW_E_WRONG_STATE.\n");
1973 return VFW_E_WRONG_STATE
;
1976 if (FAILED(IVMRSurfaceAllocator9_QueryInterface(allocator
, &IID_IVMRImagePresenter9
, (void **)&presenter
)))
1978 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1979 return E_NOINTERFACE
;
1982 if (filter
->allocator
)
1984 IVMRImagePresenter9_Release(filter
->presenter
);
1985 IVMRSurfaceAllocator9_Release(filter
->allocator
);
1987 filter
->allocator
= allocator
;
1988 filter
->presenter
= presenter
;
1989 IVMRSurfaceAllocator9_AddRef(allocator
);
1991 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1995 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_SetD3DDevice(IVMRSurfaceAllocatorNotify9
*iface
,
1996 IDirect3DDevice9
*device
, HMONITOR monitor
)
1998 struct quartz_vmr
*filter
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
2000 TRACE("filter %p, device %p, monitor %p.\n", filter
, device
, monitor
);
2002 if (filter
->allocator_d3d9_dev
)
2003 IDirect3DDevice9_Release(filter
->allocator_d3d9_dev
);
2004 filter
->allocator_d3d9_dev
= device
;
2005 IDirect3DDevice9_AddRef(device
);
2010 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_ChangeD3DDevice(IVMRSurfaceAllocatorNotify9
*iface
,
2011 IDirect3DDevice9
*device
, HMONITOR monitor
)
2013 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
2015 TRACE("(%p/%p)->(...).\n", iface
, This
);
2017 if (This
->allocator_d3d9_dev
)
2018 IDirect3DDevice9_Release(This
->allocator_d3d9_dev
);
2019 This
->allocator_d3d9_dev
= device
;
2020 IDirect3DDevice9_AddRef(This
->allocator_d3d9_dev
);
2022 if (This
->mode
&& This
->allocator
&& This
->presenter
)
2024 deallocate_surfaces(This
);
2025 allocate_surfaces(This
, &This
->renderer
.sink
.pin
.mt
);
2031 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_AllocateSurfaceHelper(IVMRSurfaceAllocatorNotify9
*iface
, VMR9AllocationInfo
*allocinfo
, DWORD
*numbuffers
, IDirect3DSurface9
**surface
)
2033 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
2037 TRACE("filter %p, allocinfo %p, numbuffers %p, surface %p.\n", This
, numbuffers
, allocinfo
, surface
);
2039 if (!allocinfo
|| !numbuffers
|| !surface
)
2042 TRACE("Flags %#lx, size %lux%lu, format %u (%#x), pool %u, minimum buffers %lu.\n",
2043 allocinfo
->dwFlags
, allocinfo
->dwWidth
, allocinfo
->dwHeight
,
2044 allocinfo
->Format
, allocinfo
->Format
, allocinfo
->Pool
, allocinfo
->MinBuffers
);
2046 if ((allocinfo
->dwFlags
& VMR9AllocFlag_TextureSurface
)
2047 && (allocinfo
->dwFlags
& VMR9AllocFlag_OffscreenSurface
))
2049 WARN("Invalid flags specified; returning E_INVALIDARG.\n");
2050 return E_INVALIDARG
;
2053 if (!allocinfo
->Format
)
2055 IDirect3DSurface9
*backbuffer
;
2056 D3DSURFACE_DESC desc
;
2058 IDirect3DDevice9_GetBackBuffer(This
->allocator_d3d9_dev
, 0, 0,
2059 D3DBACKBUFFER_TYPE_MONO
, &backbuffer
);
2060 IDirect3DSurface9_GetDesc(backbuffer
, &desc
);
2061 IDirect3DSurface9_Release(backbuffer
);
2062 allocinfo
->Format
= desc
.Format
;
2065 if (!*numbuffers
|| *numbuffers
< allocinfo
->MinBuffers
)
2067 WARN("%lu surfaces requested (minimum %lu); returning E_INVALIDARG.\n",
2068 *numbuffers
, allocinfo
->MinBuffers
);
2069 return E_INVALIDARG
;
2072 if (!This
->allocator_d3d9_dev
)
2074 WARN("No Direct3D device; returning VFW_E_WRONG_STATE.\n");
2075 return VFW_E_WRONG_STATE
;
2078 if (allocinfo
->dwFlags
== VMR9AllocFlag_OffscreenSurface
)
2080 for (i
= 0; i
< *numbuffers
; ++i
)
2082 hr
= IDirect3DDevice9_CreateOffscreenPlainSurface(This
->allocator_d3d9_dev
, allocinfo
->dwWidth
, allocinfo
->dwHeight
,
2083 allocinfo
->Format
, allocinfo
->Pool
, &surface
[i
], NULL
);
2088 else if (allocinfo
->dwFlags
== VMR9AllocFlag_TextureSurface
)
2090 for (i
= 0; i
< *numbuffers
; ++i
)
2092 IDirect3DTexture9
*texture
;
2094 hr
= IDirect3DDevice9_CreateTexture(This
->allocator_d3d9_dev
, allocinfo
->dwWidth
, allocinfo
->dwHeight
, 1, D3DUSAGE_DYNAMIC
,
2095 allocinfo
->Format
, allocinfo
->Pool
, &texture
, NULL
);
2098 IDirect3DTexture9_GetSurfaceLevel(texture
, 0, &surface
[i
]);
2099 IDirect3DTexture9_Release(texture
);
2102 else if (allocinfo
->dwFlags
== VMR9AllocFlag_3DRenderTarget
)
2104 for (i
= 0; i
< *numbuffers
; ++i
)
2106 if (FAILED(hr
= IDirect3DDevice9_CreateRenderTarget(This
->allocator_d3d9_dev
,
2107 allocinfo
->dwWidth
, allocinfo
->dwHeight
, allocinfo
->Format
,
2108 D3DMULTISAMPLE_NONE
, 0, FALSE
, &surface
[i
], NULL
)))
2114 FIXME("Unhandled flags %#lx.\n", allocinfo
->dwFlags
);
2119 WARN("%lu/%lu surfaces allocated, hr %#lx.\n", i
, *numbuffers
, hr
);
2121 if (i
>= allocinfo
->MinBuffers
)
2128 for ( ; i
> 0; --i
) IDirect3DSurface9_Release(surface
[i
- 1]);
2134 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_NotifyEvent(IVMRSurfaceAllocatorNotify9
*iface
, LONG code
, LONG_PTR param1
, LONG_PTR param2
)
2136 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
2137 IMediaEventSink
*sink
;
2140 TRACE("filter %p, code %#lx, param1 %#Ix, param2 %#Ix.\n", This
, code
, param1
, param2
);
2142 hr
= IFilterGraph_QueryInterface(This
->renderer
.filter
.graph
, &IID_IMediaEventSink
, (void **)&sink
);
2145 hr
= IMediaEventSink_Notify(sink
, code
, param1
, param2
);
2146 IMediaEventSink_Release(sink
);
2150 static const IVMRSurfaceAllocatorNotify9Vtbl VMR9_SurfaceAllocatorNotify_Vtbl
=
2152 VMR9SurfaceAllocatorNotify_QueryInterface
,
2153 VMR9SurfaceAllocatorNotify_AddRef
,
2154 VMR9SurfaceAllocatorNotify_Release
,
2155 VMR9SurfaceAllocatorNotify_AdviseSurfaceAllocator
,
2156 VMR9SurfaceAllocatorNotify_SetD3DDevice
,
2157 VMR9SurfaceAllocatorNotify_ChangeD3DDevice
,
2158 VMR9SurfaceAllocatorNotify_AllocateSurfaceHelper
,
2159 VMR9SurfaceAllocatorNotify_NotifyEvent
2162 static inline struct quartz_vmr
*impl_from_IVMRMixerControl9(IVMRMixerControl9
*iface
)
2164 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRMixerControl9_iface
);
2167 static HRESULT WINAPI
mixer_control9_QueryInterface(IVMRMixerControl9
*iface
, REFIID iid
, void **out
)
2169 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2170 return IUnknown_QueryInterface(filter
->renderer
.filter
.outer_unk
, iid
, out
);
2173 static ULONG WINAPI
mixer_control9_AddRef(IVMRMixerControl9
*iface
)
2175 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2176 return IUnknown_AddRef(filter
->renderer
.filter
.outer_unk
);
2179 static ULONG WINAPI
mixer_control9_Release(IVMRMixerControl9
*iface
)
2181 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2182 return IUnknown_Release(filter
->renderer
.filter
.outer_unk
);
2185 static HRESULT WINAPI
mixer_control9_SetAlpha(IVMRMixerControl9
*iface
, DWORD stream
, float alpha
)
2187 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2189 FIXME("filter %p, stream %lu, alpha %.8e, stub!\n", filter
, stream
, alpha
);
2194 static HRESULT WINAPI
mixer_control9_GetAlpha(IVMRMixerControl9
*iface
, DWORD stream
, float *alpha
)
2196 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2198 FIXME("filter %p, stream %lu, alpha %p, stub!\n", filter
, stream
, alpha
);
2203 static HRESULT WINAPI
mixer_control9_SetZOrder(IVMRMixerControl9
*iface
, DWORD stream
, DWORD z
)
2205 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2207 FIXME("filter %p, stream %lu, z %lu, stub!\n", filter
, stream
, z
);
2212 static HRESULT WINAPI
mixer_control9_GetZOrder(IVMRMixerControl9
*iface
, DWORD stream
, DWORD
*z
)
2214 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2216 FIXME("filter %p, stream %lu, z %p, stub!\n", filter
, stream
, z
);
2221 static HRESULT WINAPI
mixer_control9_SetOutputRect(IVMRMixerControl9
*iface
,
2222 DWORD stream
, const VMR9NormalizedRect
*rect
)
2224 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2226 FIXME("filter %p, stream %lu, rect %s, stub!\n", filter
, stream
, debugstr_normalized_rect(rect
));
2231 static HRESULT WINAPI
mixer_control9_GetOutputRect(IVMRMixerControl9
*iface
,
2232 DWORD stream
, VMR9NormalizedRect
*rect
)
2234 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2236 FIXME("filter %p, stream %lu, rect %p, stub!\n", filter
, stream
, rect
);
2241 static HRESULT WINAPI
mixer_control9_SetBackgroundClr(IVMRMixerControl9
*iface
, COLORREF color
)
2243 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2245 FIXME("filter %p, color #%06lx, stub!\n", filter
, color
);
2250 static HRESULT WINAPI
mixer_control9_GetBackgroundClr(IVMRMixerControl9
*iface
, COLORREF
*color
)
2252 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2254 FIXME("filter %p, color %p, stub!\n", filter
, color
);
2259 static HRESULT WINAPI
mixer_control9_SetMixingPrefs(IVMRMixerControl9
*iface
, DWORD flags
)
2261 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2263 FIXME("filter %p, flags %#lx, stub!\n", filter
, flags
);
2265 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2266 filter
->mixing_prefs
= flags
;
2267 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2271 static HRESULT WINAPI
mixer_control9_GetMixingPrefs(IVMRMixerControl9
*iface
, DWORD
*flags
)
2273 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2275 FIXME("filter %p, flags %p, stub!\n", filter
, flags
);
2277 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2278 *flags
= filter
->mixing_prefs
;
2279 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2283 static HRESULT WINAPI
mixer_control9_SetProcAmpControl(IVMRMixerControl9
*iface
,
2284 DWORD stream
, VMR9ProcAmpControl
*settings
)
2286 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2288 FIXME("filter %p, settings %p, stub!\n", filter
, settings
);
2293 static HRESULT WINAPI
mixer_control9_GetProcAmpControl(IVMRMixerControl9
*iface
,
2294 DWORD stream
, VMR9ProcAmpControl
*settings
)
2296 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2298 FIXME("filter %p, settings %p, stub!\n", filter
, settings
);
2303 static HRESULT WINAPI
mixer_control9_GetProcAmpControlRange(IVMRMixerControl9
*iface
,
2304 DWORD stream
, VMR9ProcAmpControlRange
*settings
)
2306 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2308 FIXME("filter %p, settings %p, stub!\n", filter
, settings
);
2313 static const IVMRMixerControl9Vtbl mixer_control9_vtbl
=
2315 mixer_control9_QueryInterface
,
2316 mixer_control9_AddRef
,
2317 mixer_control9_Release
,
2318 mixer_control9_SetAlpha
,
2319 mixer_control9_GetAlpha
,
2320 mixer_control9_SetZOrder
,
2321 mixer_control9_GetZOrder
,
2322 mixer_control9_SetOutputRect
,
2323 mixer_control9_GetOutputRect
,
2324 mixer_control9_SetBackgroundClr
,
2325 mixer_control9_GetBackgroundClr
,
2326 mixer_control9_SetMixingPrefs
,
2327 mixer_control9_GetMixingPrefs
,
2328 mixer_control9_SetProcAmpControl
,
2329 mixer_control9_GetProcAmpControl
,
2330 mixer_control9_GetProcAmpControlRange
,
2333 static inline struct quartz_vmr
*impl_from_IVMRMixerBitmap9(IVMRMixerBitmap9
*iface
)
2335 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRMixerBitmap9_iface
);
2338 static HRESULT WINAPI
mixer_bitmap9_QueryInterface(IVMRMixerBitmap9
*iface
, REFIID iid
, void **out
)
2340 struct quartz_vmr
*filter
= impl_from_IVMRMixerBitmap9(iface
);
2341 return IUnknown_QueryInterface(filter
->renderer
.filter
.outer_unk
, iid
, out
);
2344 static ULONG WINAPI
mixer_bitmap9_AddRef(IVMRMixerBitmap9
*iface
)
2346 struct quartz_vmr
*filter
= impl_from_IVMRMixerBitmap9(iface
);
2347 return IUnknown_AddRef(filter
->renderer
.filter
.outer_unk
);
2350 static ULONG WINAPI
mixer_bitmap9_Release(IVMRMixerBitmap9
*iface
)
2352 struct quartz_vmr
*filter
= impl_from_IVMRMixerBitmap9(iface
);
2353 return IUnknown_Release(filter
->renderer
.filter
.outer_unk
);
2356 static HRESULT WINAPI
mixer_bitmap9_SetAlphaBitmap(IVMRMixerBitmap9
*iface
,
2357 const VMR9AlphaBitmap
*bitmap
)
2359 FIXME("iface %p, bitmap %p, stub!\n", iface
, bitmap
);
2360 TRACE("dwFlags %#lx, hdc %p, pDDS %p, rSrc %s, rDest %s, fAlpha %.8e, clrSrcKey #%06lx, dwFilterMode %#lx.\n",
2361 bitmap
->dwFlags
, bitmap
->hdc
, bitmap
->pDDS
, wine_dbgstr_rect(&bitmap
->rSrc
),
2362 debugstr_normalized_rect(&bitmap
->rDest
), bitmap
->fAlpha
, bitmap
->clrSrcKey
, bitmap
->dwFilterMode
);
2366 static HRESULT WINAPI
mixer_bitmap9_UpdateAlphaBitmapParameters(IVMRMixerBitmap9
*iface
,
2367 const VMR9AlphaBitmap
*bitmap
)
2369 FIXME("iface %p, bitmap %p, stub!\n", iface
, bitmap
);
2373 static HRESULT WINAPI
mixer_bitmap9_GetAlphaBitmapParameters(IVMRMixerBitmap9
*iface
,
2374 VMR9AlphaBitmap
*bitmap
)
2376 FIXME("iface %p, bitmap %p, stub!\n", iface
, bitmap
);
2380 static const IVMRMixerBitmap9Vtbl mixer_bitmap9_vtbl
=
2382 mixer_bitmap9_QueryInterface
,
2383 mixer_bitmap9_AddRef
,
2384 mixer_bitmap9_Release
,
2385 mixer_bitmap9_SetAlphaBitmap
,
2386 mixer_bitmap9_UpdateAlphaBitmapParameters
,
2387 mixer_bitmap9_GetAlphaBitmapParameters
,
2390 static inline struct quartz_vmr
*impl_from_IVMRAspectRatioControl9(IVMRAspectRatioControl9
*iface
)
2392 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRAspectRatioControl9_iface
);
2395 static HRESULT WINAPI
aspect_ratio_control9_QueryInterface(IVMRAspectRatioControl9
*iface
, REFIID iid
, void **out
)
2397 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2398 return IUnknown_QueryInterface(filter
->renderer
.filter
.outer_unk
, iid
, out
);
2401 static ULONG WINAPI
aspect_ratio_control9_AddRef(IVMRAspectRatioControl9
*iface
)
2403 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2404 return IUnknown_AddRef(filter
->renderer
.filter
.outer_unk
);
2407 static ULONG WINAPI
aspect_ratio_control9_Release(IVMRAspectRatioControl9
*iface
)
2409 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2410 return IUnknown_Release(filter
->renderer
.filter
.outer_unk
);
2413 static HRESULT WINAPI
aspect_ratio_control9_GetAspectRatioMode(IVMRAspectRatioControl9
*iface
, DWORD
*mode
)
2415 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2417 TRACE("filter %p, mode %p.\n", filter
, mode
);
2419 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2420 *mode
= filter
->aspect_mode
;
2421 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2425 static HRESULT WINAPI
aspect_ratio_control9_SetAspectRatioMode(IVMRAspectRatioControl9
*iface
, DWORD mode
)
2427 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2429 TRACE("filter %p, mode %lu.\n", filter
, mode
);
2431 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2432 filter
->aspect_mode
= mode
;
2433 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2437 static const IVMRAspectRatioControl9Vtbl aspect_ratio_control9_vtbl
=
2439 aspect_ratio_control9_QueryInterface
,
2440 aspect_ratio_control9_AddRef
,
2441 aspect_ratio_control9_Release
,
2442 aspect_ratio_control9_GetAspectRatioMode
,
2443 aspect_ratio_control9_SetAspectRatioMode
,
2446 static struct quartz_vmr
*impl_from_IAMVideoAccelerator(IAMVideoAccelerator
*iface
)
2448 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IAMVideoAccelerator_iface
);
2451 static HRESULT WINAPI
video_accelerator_QueryInterface(IAMVideoAccelerator
*iface
, REFIID iid
, void **out
)
2453 struct quartz_vmr
*filter
= impl_from_IAMVideoAccelerator(iface
);
2454 return IPin_QueryInterface(&filter
->renderer
.sink
.pin
.IPin_iface
, iid
, out
);
2457 static ULONG WINAPI
video_accelerator_AddRef(IAMVideoAccelerator
*iface
)
2459 struct quartz_vmr
*filter
= impl_from_IAMVideoAccelerator(iface
);
2460 return IPin_AddRef(&filter
->renderer
.sink
.pin
.IPin_iface
);
2463 static ULONG WINAPI
video_accelerator_Release(IAMVideoAccelerator
*iface
)
2465 struct quartz_vmr
*filter
= impl_from_IAMVideoAccelerator(iface
);
2466 return IPin_Release(&filter
->renderer
.sink
.pin
.IPin_iface
);
2469 static HRESULT WINAPI
video_accelerator_GetVideoAcceleratorGUIDs(
2470 IAMVideoAccelerator
*iface
, DWORD
*count
, GUID
*accelerators
)
2472 FIXME("iface %p, count %p, accelerators %p, stub!\n", iface
, count
, accelerators
);
2476 static HRESULT WINAPI
video_accelerator_GetUncompFormatsSupported(IAMVideoAccelerator
*iface
,
2477 const GUID
*accelerator
, DWORD
*count
, DDPIXELFORMAT
*formats
)
2479 FIXME("iface %p, accelerator %s, count %p, formats %p, stub!\n",
2480 iface
, debugstr_guid(accelerator
), count
, formats
);
2484 static HRESULT WINAPI
video_accelerator_GetInternalMemInfo(IAMVideoAccelerator
*iface
,
2485 const GUID
*accelerator
, const AMVAUncompDataInfo
*format_info
, AMVAInternalMemInfo
*mem_info
)
2487 FIXME("iface %p, accelerator %s, format_info %p, mem_info %p, stub!\n",
2488 iface
, debugstr_guid(accelerator
), format_info
, mem_info
);
2492 static HRESULT WINAPI
video_accelerator_GetCompBufferInfo(IAMVideoAccelerator
*iface
,
2493 const GUID
*accelerator
, const AMVAUncompDataInfo
*uncompressed_info
,
2494 DWORD
*compressed_info_count
, AMVACompBufferInfo
*compressed_infos
)
2496 FIXME("iface %p, accelerator %s, uncompressed_info %p, compressed_info_count %p, compressed_infos %p, stub!\n",
2497 iface
, debugstr_guid(accelerator
), uncompressed_info
, compressed_info_count
, compressed_infos
);
2501 static HRESULT WINAPI
video_accelerator_GetInternalCompBufferInfo(
2502 IAMVideoAccelerator
*iface
, DWORD
*count
, AMVACompBufferInfo
*infos
)
2504 FIXME("iface %p, count %p, infos %p, stub!\n", iface
, count
, infos
);
2508 static HRESULT WINAPI
video_accelerator_BeginFrame(IAMVideoAccelerator
*iface
, const AMVABeginFrameInfo
*info
)
2510 FIXME("iface %p, info %p, stub!\n", iface
, info
);
2514 static HRESULT WINAPI
video_accelerator_EndFrame(IAMVideoAccelerator
*iface
, const AMVAEndFrameInfo
*info
)
2516 FIXME("iface %p, info %p, stub!\n", iface
, info
);
2520 static HRESULT WINAPI
video_accelerator_GetBuffer(IAMVideoAccelerator
*iface
,
2521 DWORD type_index
, DWORD buffer_index
, BOOL read_only
, void **buffer
, LONG
*stride
)
2523 FIXME("iface %p, type_index %lu, buffer_index %lu, read_only %d, buffer %p, stride %p, stub!\n",
2524 iface
, type_index
, buffer_index
, read_only
, buffer
, stride
);
2528 static HRESULT WINAPI
video_accelerator_ReleaseBuffer(
2529 IAMVideoAccelerator
*iface
, DWORD type_index
, DWORD buffer_index
)
2531 FIXME("iface %p, type_index %lu, buffer_index %lu, stub!\n", iface
, type_index
, buffer_index
);
2535 static HRESULT WINAPI
video_accelerator_Execute(IAMVideoAccelerator
*iface
,
2536 DWORD function
, void *in_data
, DWORD in_size
, void *out_data
,
2537 DWORD out_size
, DWORD buffer_count
, const AMVABUFFERINFO
*buffers
)
2539 FIXME("iface %p, function %#lx, in_data %p, in_size %lu,"
2540 " out_data %p, out_size %lu, buffer_count %lu, buffers %p, stub!\n",
2541 iface
, function
, in_data
, in_size
, out_data
, out_size
, buffer_count
, buffers
);
2545 static HRESULT WINAPI
video_accelerator_QueryRenderStatus(IAMVideoAccelerator
*iface
,
2546 DWORD type_index
, DWORD buffer_index
, DWORD flags
)
2548 FIXME("iface %p, type_index %lu, buffer_index %lu, flags %#lx, stub!\n",
2549 iface
, type_index
, buffer_index
, flags
);
2553 static HRESULT WINAPI
video_accelerator_DisplayFrame(
2554 IAMVideoAccelerator
*iface
, DWORD index
, IMediaSample
*sample
)
2556 FIXME("iface %p, index %lu, sample %p, stub!\n", iface
, index
, sample
);
2560 static const IAMVideoAcceleratorVtbl video_accelerator_vtbl
=
2562 video_accelerator_QueryInterface
,
2563 video_accelerator_AddRef
,
2564 video_accelerator_Release
,
2565 video_accelerator_GetVideoAcceleratorGUIDs
,
2566 video_accelerator_GetUncompFormatsSupported
,
2567 video_accelerator_GetInternalMemInfo
,
2568 video_accelerator_GetCompBufferInfo
,
2569 video_accelerator_GetInternalCompBufferInfo
,
2570 video_accelerator_BeginFrame
,
2571 video_accelerator_EndFrame
,
2572 video_accelerator_GetBuffer
,
2573 video_accelerator_ReleaseBuffer
,
2574 video_accelerator_Execute
,
2575 video_accelerator_QueryRenderStatus
,
2576 video_accelerator_DisplayFrame
,
2579 static inline struct quartz_vmr
*impl_from_IOverlay(IOverlay
*iface
)
2581 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IOverlay_iface
);
2584 static HRESULT WINAPI
overlay_QueryInterface(IOverlay
*iface
, REFIID iid
, void **out
)
2586 struct quartz_vmr
*filter
= impl_from_IOverlay(iface
);
2587 return IPin_QueryInterface(&filter
->renderer
.sink
.pin
.IPin_iface
, iid
, out
);
2590 static ULONG WINAPI
overlay_AddRef(IOverlay
*iface
)
2592 struct quartz_vmr
*filter
= impl_from_IOverlay(iface
);
2593 return IPin_AddRef(&filter
->renderer
.sink
.pin
.IPin_iface
);
2596 static ULONG WINAPI
overlay_Release(IOverlay
*iface
)
2598 struct quartz_vmr
*filter
= impl_from_IOverlay(iface
);
2599 return IPin_Release(&filter
->renderer
.sink
.pin
.IPin_iface
);
2602 static HRESULT WINAPI
overlay_GetPalette(IOverlay
*iface
, DWORD
*count
, PALETTEENTRY
**palette
)
2604 FIXME("iface %p, count %p, palette %p, stub!\n", iface
, count
, palette
);
2608 static HRESULT WINAPI
overlay_SetPalette(IOverlay
*iface
, DWORD count
, PALETTEENTRY
*palette
)
2610 FIXME("iface %p, count %lu, palette %p, stub!\n", iface
, count
, palette
);
2614 static HRESULT WINAPI
overlay_GetDefaultColorKey(IOverlay
*iface
, COLORKEY
*key
)
2616 FIXME("iface %p, key %p, stub!\n", iface
, key
);
2620 static HRESULT WINAPI
overlay_GetColorKey(IOverlay
*iface
, COLORKEY
*key
)
2622 FIXME("iface %p, key %p, stub!\n", iface
, key
);
2626 static HRESULT WINAPI
overlay_SetColorKey(IOverlay
*iface
, COLORKEY
*key
)
2628 FIXME("iface %p, key %p, stub!\n", iface
, key
);
2632 static HRESULT WINAPI
overlay_GetWindowHandle(IOverlay
*iface
, HWND
*window
)
2634 struct quartz_vmr
*filter
= impl_from_IOverlay(iface
);
2636 TRACE("filter %p, window %p.\n", filter
, window
);
2638 if (!filter
->window
.hwnd
)
2639 return VFW_E_WRONG_STATE
;
2641 *window
= filter
->window
.hwnd
;
2645 static HRESULT WINAPI
overlay_GetClipList(IOverlay
*iface
, RECT
*source
, RECT
*dest
, RGNDATA
**region
)
2647 FIXME("iface %p, source %p, dest %p, region %p, stub!\n", iface
, source
, dest
, region
);
2651 static HRESULT WINAPI
overlay_GetVideoPosition(IOverlay
*iface
, RECT
*source
, RECT
*dest
)
2653 FIXME("iface %p, source %p, dest %p, stub!\n", iface
, source
, dest
);
2657 static HRESULT WINAPI
overlay_Advise(IOverlay
*iface
, IOverlayNotify
*sink
, DWORD flags
)
2659 FIXME("iface %p, sink %p, flags %#lx, stub!\n", iface
, sink
, flags
);
2663 static HRESULT WINAPI
overlay_Unadvise(IOverlay
*iface
)
2665 FIXME("iface %p, stub!\n", iface
);
2669 static const IOverlayVtbl overlay_vtbl
=
2671 overlay_QueryInterface
,
2676 overlay_GetDefaultColorKey
,
2677 overlay_GetColorKey
,
2678 overlay_SetColorKey
,
2679 overlay_GetWindowHandle
,
2680 overlay_GetClipList
,
2681 overlay_GetVideoPosition
,
2686 static HRESULT
vmr_create(IUnknown
*outer
, IUnknown
**out
, const CLSID
*clsid
)
2688 struct quartz_vmr
*object
;
2691 if (!(object
= calloc(1, sizeof(*object
))))
2692 return E_OUTOFMEMORY
;
2694 object
->hD3d9
= LoadLibraryA("d3d9.dll");
2697 WARN("Could not load d3d9.dll\n");
2699 return VFW_E_DDRAW_CAPS_NOT_SUITABLE
;
2702 strmbase_renderer_init(&object
->renderer
, outer
, clsid
, L
"VMR Input0", &renderer_ops
);
2703 object
->IAMCertifiedOutputProtection_iface
.lpVtbl
= &IAMCertifiedOutputProtection_Vtbl
;
2704 object
->IAMFilterMiscFlags_iface
.lpVtbl
= &IAMFilterMiscFlags_Vtbl
;
2705 object
->IVMRAspectRatioControl9_iface
.lpVtbl
= &aspect_ratio_control9_vtbl
;
2706 object
->IVMRFilterConfig_iface
.lpVtbl
= &VMR7_FilterConfig_Vtbl
;
2707 object
->IVMRFilterConfig9_iface
.lpVtbl
= &VMR9_FilterConfig_Vtbl
;
2708 object
->IVMRMixerBitmap9_iface
.lpVtbl
= &mixer_bitmap9_vtbl
;
2709 object
->IVMRMixerControl9_iface
.lpVtbl
= &mixer_control9_vtbl
;
2710 object
->IVMRMonitorConfig_iface
.lpVtbl
= &VMR7_MonitorConfig_Vtbl
;
2711 object
->IVMRMonitorConfig9_iface
.lpVtbl
= &VMR9_MonitorConfig_Vtbl
;
2712 object
->IVMRSurfaceAllocatorNotify_iface
.lpVtbl
= &VMR7_SurfaceAllocatorNotify_Vtbl
;
2713 object
->IVMRSurfaceAllocatorNotify9_iface
.lpVtbl
= &VMR9_SurfaceAllocatorNotify_Vtbl
;
2714 object
->IVMRWindowlessControl_iface
.lpVtbl
= &VMR7_WindowlessControl_Vtbl
;
2715 object
->IVMRWindowlessControl9_iface
.lpVtbl
= &VMR9_WindowlessControl_Vtbl
;
2717 object
->IAMVideoAccelerator_iface
.lpVtbl
= &video_accelerator_vtbl
;
2718 object
->IOverlay_iface
.lpVtbl
= &overlay_vtbl
;
2720 video_window_init(&object
->window
, &IVideoWindow_VTable
,
2721 &object
->renderer
.filter
, &object
->renderer
.sink
.pin
, &window_ops
);
2723 if (FAILED(hr
= video_window_create_window(&object
->window
)))
2725 video_window_cleanup(&object
->window
);
2726 strmbase_renderer_cleanup(&object
->renderer
);
2727 FreeLibrary(object
->hD3d9
);
2732 object
->mixing_prefs
= MixerPref9_NoDecimation
| MixerPref9_ARAdjustXorY
2733 | MixerPref9_BiLinearFiltering
| MixerPref9_RenderTargetRGB
;
2735 TRACE("Created VMR %p.\n", object
);
2736 *out
= &object
->renderer
.filter
.IUnknown_inner
;
2740 HRESULT
vmr7_create(IUnknown
*outer
, IUnknown
**out
)
2742 return vmr_create(outer
, out
, &CLSID_VideoMixingRenderer
);
2745 HRESULT
vmr9_create(IUnknown
*outer
, IUnknown
**out
)
2747 return vmr_create(outer
, out
, &CLSID_VideoMixingRenderer9
);
2751 static HRESULT WINAPI
VMR9_ImagePresenter_QueryInterface(IVMRImagePresenter9
*iface
, REFIID riid
, void **ppv
)
2753 struct default_presenter
*This
= impl_from_IVMRImagePresenter9(iface
);
2755 TRACE("(%p/%p)->(%s, %p)\n", This
, iface
, qzdebugstr_guid(riid
), ppv
);
2759 if (IsEqualIID(riid
, &IID_IUnknown
) || IsEqualIID(riid
, &IID_IVMRImagePresenter9
))
2760 *ppv
= &This
->IVMRImagePresenter9_iface
;
2761 else if (IsEqualIID(riid
, &IID_IVMRSurfaceAllocator9
))
2762 *ppv
= &This
->IVMRSurfaceAllocator9_iface
;
2766 IUnknown_AddRef((IUnknown
*)(*ppv
));
2770 FIXME("No interface for %s\n", debugstr_guid(riid
));
2772 return E_NOINTERFACE
;
2775 static ULONG WINAPI
VMR9_ImagePresenter_AddRef(IVMRImagePresenter9
*iface
)
2777 struct default_presenter
*presenter
= impl_from_IVMRImagePresenter9(iface
);
2778 ULONG refcount
= InterlockedIncrement(&presenter
->refCount
);
2780 TRACE("%p increasing refcount to %lu.\n", presenter
, refcount
);
2785 static ULONG WINAPI
VMR9_ImagePresenter_Release(IVMRImagePresenter9
*iface
)
2787 struct default_presenter
*This
= impl_from_IVMRImagePresenter9(iface
);
2788 ULONG refcount
= InterlockedDecrement(&This
->refCount
);
2790 TRACE("%p decreasing refcount to %lu.\n", This
, refcount
);
2796 IDirect3D9_Release(This
->d3d9_ptr
);
2798 for (i
= 0; i
< This
->num_surfaces
; ++i
)
2800 IDirect3DSurface9
*surface
= This
->d3d9_surfaces
[i
];
2802 IDirect3DSurface9_Release(surface
);
2806 IDirect3DDevice9_Release(This
->d3d9_dev
);
2807 free(This
->d3d9_surfaces
);
2808 This
->d3d9_surfaces
= NULL
;
2809 This
->num_surfaces
= 0;
2816 static HRESULT WINAPI
VMR9_ImagePresenter_StartPresenting(IVMRImagePresenter9
*iface
, DWORD_PTR cookie
)
2818 struct default_presenter
*presenter
= impl_from_IVMRImagePresenter9(iface
);
2820 TRACE("presenter %p, cookie %#Ix.\n", presenter
, cookie
);
2825 static HRESULT WINAPI
VMR9_ImagePresenter_StopPresenting(IVMRImagePresenter9
*iface
, DWORD_PTR cookie
)
2827 struct default_presenter
*presenter
= impl_from_IVMRImagePresenter9(iface
);
2829 TRACE("presenter %p, cookie %#Ix.\n", presenter
, cookie
);
2834 static HRESULT WINAPI
VMR9_ImagePresenter_PresentImage(IVMRImagePresenter9
*iface
,
2835 DWORD_PTR cookie
, VMR9PresentationInfo
*info
)
2837 struct default_presenter
*presenter
= impl_from_IVMRImagePresenter9(iface
);
2838 const struct quartz_vmr
*filter
= presenter
->pVMR9
;
2839 IDirect3DDevice9
*device
= presenter
->d3d9_dev
;
2840 const RECT src
= filter
->window
.src
;
2841 IDirect3DSurface9
*backbuffer
;
2842 RECT dst
= filter
->window
.dst
;
2845 TRACE("presenter %p, cookie %#Ix, info %p.\n", presenter
, cookie
, info
);
2847 /* This might happen if we don't have active focus (eg on a different virtual desktop) */
2851 if (FAILED(hr
= IDirect3DDevice9_Clear(device
, 0, NULL
, D3DCLEAR_TARGET
,
2852 D3DCOLOR_XRGB(0, 0, 0), 1.0f
, 0)))
2853 ERR("Failed to clear, hr %#lx.\n", hr
);
2855 if (FAILED(hr
= IDirect3DDevice9_BeginScene(device
)))
2856 ERR("Failed to begin scene, hr %#lx.\n", hr
);
2858 if (FAILED(hr
= IDirect3DDevice9_GetBackBuffer(device
, 0, 0, D3DBACKBUFFER_TYPE_MONO
, &backbuffer
)))
2860 ERR("Failed to get backbuffer, hr %#lx.\n", hr
);
2864 if (FAILED(hr
= IDirect3DDevice9_StretchRect(device
, info
->lpSurf
, NULL
, backbuffer
, NULL
, D3DTEXF_POINT
)))
2865 ERR("Failed to blit image, hr %#lx.\n", hr
);
2866 IDirect3DSurface9_Release(backbuffer
);
2868 if (FAILED(hr
= IDirect3DDevice9_EndScene(device
)))
2869 ERR("Failed to end scene, hr %#lx.\n", hr
);
2871 if (filter
->aspect_mode
== VMR9ARMode_LetterBox
)
2873 unsigned int src_width
= src
.right
- src
.left
, src_height
= src
.bottom
- src
.top
;
2874 unsigned int dst_width
= dst
.right
- dst
.left
, dst_height
= dst
.bottom
- dst
.top
;
2876 if (src_width
* dst_height
> dst_width
* src_height
)
2878 /* src is "wider" than dst. */
2879 unsigned int dst_center
= (dst
.top
+ dst
.bottom
) / 2;
2880 unsigned int scaled_height
= src_height
* dst_width
/ src_width
;
2882 dst
.top
= dst_center
- scaled_height
/ 2;
2883 dst
.bottom
= dst
.top
+ scaled_height
;
2885 else if (src_width
* dst_height
< dst_width
* src_height
)
2887 /* src is "taller" than dst. */
2888 unsigned int dst_center
= (dst
.left
+ dst
.right
) / 2;
2889 unsigned int scaled_width
= src_width
* dst_height
/ src_height
;
2891 dst
.left
= dst_center
- scaled_width
/ 2;
2892 dst
.right
= dst
.left
+ scaled_width
;
2896 if (FAILED(hr
= IDirect3DDevice9_Present(device
, &src
, &dst
, NULL
, NULL
)))
2897 ERR("Failed to present, hr %#lx.\n", hr
);
2902 static const IVMRImagePresenter9Vtbl VMR9_ImagePresenter
=
2904 VMR9_ImagePresenter_QueryInterface
,
2905 VMR9_ImagePresenter_AddRef
,
2906 VMR9_ImagePresenter_Release
,
2907 VMR9_ImagePresenter_StartPresenting
,
2908 VMR9_ImagePresenter_StopPresenting
,
2909 VMR9_ImagePresenter_PresentImage
2912 static HRESULT WINAPI
VMR9_SurfaceAllocator_QueryInterface(IVMRSurfaceAllocator9
*iface
, REFIID iid
, void **out
)
2914 struct default_presenter
*presenter
= impl_from_IVMRSurfaceAllocator9(iface
);
2915 return IVMRImagePresenter9_QueryInterface(&presenter
->IVMRImagePresenter9_iface
, iid
, out
);
2918 static ULONG WINAPI
VMR9_SurfaceAllocator_AddRef(IVMRSurfaceAllocator9
*iface
)
2920 struct default_presenter
*presenter
= impl_from_IVMRSurfaceAllocator9(iface
);
2921 return IVMRImagePresenter9_AddRef(&presenter
->IVMRImagePresenter9_iface
);
2924 static ULONG WINAPI
VMR9_SurfaceAllocator_Release(IVMRSurfaceAllocator9
*iface
)
2926 struct default_presenter
*presenter
= impl_from_IVMRSurfaceAllocator9(iface
);
2927 return IVMRImagePresenter9_Release(&presenter
->IVMRImagePresenter9_iface
);
2930 static void adjust_surface_size(const D3DCAPS9
*caps
, VMR9AllocationInfo
*allocinfo
)
2934 /* There are no restrictions on the size of offscreen surfaces. */
2935 if (!(allocinfo
->dwFlags
& VMR9AllocFlag_TextureSurface
))
2938 if (!(caps
->TextureCaps
& D3DPTEXTURECAPS_POW2
) || (caps
->TextureCaps
& D3DPTEXTURECAPS_SQUAREONLY
))
2940 width
= allocinfo
->dwWidth
;
2941 height
= allocinfo
->dwHeight
;
2946 while (width
< allocinfo
->dwWidth
)
2949 while (height
< allocinfo
->dwHeight
)
2951 FIXME("NPOW2 support missing, not using proper surfaces!\n");
2954 if (caps
->TextureCaps
& D3DPTEXTURECAPS_SQUAREONLY
)
2960 FIXME("Square texture support required..\n");
2963 allocinfo
->dwHeight
= height
;
2964 allocinfo
->dwWidth
= width
;
2967 static UINT
d3d9_adapter_from_hwnd(IDirect3D9
*d3d9
, HWND hwnd
, HMONITOR
*mon_out
)
2972 mon
= MonitorFromWindow(hwnd
, MONITOR_DEFAULTTONULL
);
2977 for (d3d9_adapter
= 0; d3d9_adapter
< IDirect3D9_GetAdapterCount(d3d9
); ++d3d9_adapter
)
2979 if (mon
== IDirect3D9_GetAdapterMonitor(d3d9
, d3d9_adapter
))
2982 if (d3d9_adapter
>= IDirect3D9_GetAdapterCount(d3d9
))
2987 return d3d9_adapter
;
2990 static HRESULT WINAPI
VMR9_SurfaceAllocator_InitializeDevice(IVMRSurfaceAllocator9
*iface
,
2991 DWORD_PTR cookie
, VMR9AllocationInfo
*info
, DWORD
*numbuffers
)
2993 struct default_presenter
*This
= impl_from_IVMRSurfaceAllocator9(iface
);
2994 D3DPRESENT_PARAMETERS d3dpp
;
2995 IDirect3DDevice9
*device
;
3001 TRACE("presenter %p, cookie %#Ix, info %p, numbuffers %p.\n", This
, cookie
, info
, numbuffers
);
3005 if (This
->pVMR9
->mode
== VMR9Mode_Windowed
)
3006 window
= This
->pVMR9
->window
.hwnd
;
3008 window
= This
->pVMR9
->clipping_window
;
3010 /* Obtain a monitor and d3d9 device */
3011 d3d9_adapter
= d3d9_adapter_from_hwnd(This
->d3d9_ptr
, window
, &This
->hMon
);
3013 /* Now try to create the d3d9 device */
3014 ZeroMemory(&d3dpp
, sizeof(d3dpp
));
3015 d3dpp
.Windowed
= TRUE
;
3016 d3dpp
.hDeviceWindow
= window
;
3017 d3dpp
.SwapEffect
= D3DSWAPEFFECT_COPY
;
3018 d3dpp
.BackBufferWidth
= info
->dwWidth
;
3019 d3dpp
.BackBufferHeight
= info
->dwHeight
;
3021 hr
= IDirect3D9_CreateDevice(This
->d3d9_ptr
, d3d9_adapter
, D3DDEVTYPE_HAL
,
3022 NULL
, D3DCREATE_MIXED_VERTEXPROCESSING
, &d3dpp
, &device
);
3025 ERR("Failed to create device, hr %#lx.\n", hr
);
3029 IDirect3DDevice9_GetDeviceCaps(device
, &caps
);
3030 if (!(caps
.DevCaps2
& D3DDEVCAPS2_CAN_STRETCHRECT_FROM_TEXTURES
))
3032 WARN("Device does not support blitting from textures.\n");
3033 IDirect3DDevice9_Release(device
);
3034 return VFW_E_DDRAW_CAPS_NOT_SUITABLE
;
3037 This
->d3d9_dev
= device
;
3038 IVMRSurfaceAllocatorNotify9_SetD3DDevice(This
->SurfaceAllocatorNotify
, This
->d3d9_dev
, This
->hMon
);
3040 if (!(This
->d3d9_surfaces
= calloc(*numbuffers
, sizeof(IDirect3DSurface9
*))))
3041 return E_OUTOFMEMORY
;
3043 adjust_surface_size(&caps
, info
);
3045 hr
= IVMRSurfaceAllocatorNotify9_AllocateSurfaceHelper(This
->SurfaceAllocatorNotify
,
3046 info
, numbuffers
, This
->d3d9_surfaces
);
3049 ERR("Failed to allocate surfaces, hr %#lx.\n", hr
);
3050 IVMRSurfaceAllocator9_TerminateDevice(This
->pVMR9
->allocator
, This
->pVMR9
->cookie
);
3054 This
->num_surfaces
= *numbuffers
;
3059 static HRESULT WINAPI
VMR9_SurfaceAllocator_TerminateDevice(IVMRSurfaceAllocator9
*iface
, DWORD_PTR cookie
)
3061 TRACE("iface %p, cookie %#Ix.\n", iface
, cookie
);
3066 static HRESULT WINAPI
VMR9_SurfaceAllocator_GetSurface(IVMRSurfaceAllocator9
*iface
,
3067 DWORD_PTR cookie
, DWORD surfaceindex
, DWORD flags
, IDirect3DSurface9
**surface
)
3069 struct default_presenter
*This
= impl_from_IVMRSurfaceAllocator9(iface
);
3071 /* Update everything first, this is needed because the surface might be destroyed in the reset */
3072 if (!This
->d3d9_dev
)
3074 TRACE("Device has left me!\n");
3078 if (surfaceindex
>= This
->num_surfaces
)
3080 ERR("surfaceindex is greater than num_surfaces\n");
3083 *surface
= This
->d3d9_surfaces
[surfaceindex
];
3084 IDirect3DSurface9_AddRef(*surface
);
3089 static HRESULT WINAPI
VMR9_SurfaceAllocator_AdviseNotify(IVMRSurfaceAllocator9
*iface
,
3090 IVMRSurfaceAllocatorNotify9
*notify
)
3092 struct default_presenter
*presenter
= impl_from_IVMRSurfaceAllocator9(iface
);
3094 TRACE("presenter %p, notify %p.\n", presenter
, notify
);
3096 /* No AddRef taken here or the base VMR9 filter would never be destroyed */
3097 presenter
->SurfaceAllocatorNotify
= notify
;
3101 static const IVMRSurfaceAllocator9Vtbl VMR9_SurfaceAllocator
=
3103 VMR9_SurfaceAllocator_QueryInterface
,
3104 VMR9_SurfaceAllocator_AddRef
,
3105 VMR9_SurfaceAllocator_Release
,
3106 VMR9_SurfaceAllocator_InitializeDevice
,
3107 VMR9_SurfaceAllocator_TerminateDevice
,
3108 VMR9_SurfaceAllocator_GetSurface
,
3109 VMR9_SurfaceAllocator_AdviseNotify
,
3112 static IDirect3D9
*init_d3d9(HMODULE d3d9_handle
)
3114 IDirect3D9
* (__stdcall
* d3d9_create
)(UINT SDKVersion
);
3116 d3d9_create
= (void *)GetProcAddress(d3d9_handle
, "Direct3DCreate9");
3117 if (!d3d9_create
) return NULL
;
3119 return d3d9_create(D3D_SDK_VERSION
);
3122 static HRESULT
default_presenter_create(struct quartz_vmr
*parent
, struct default_presenter
**presenter
)
3124 struct default_presenter
*object
;
3126 if (!(object
= calloc(1, sizeof(*object
))))
3127 return E_OUTOFMEMORY
;
3129 object
->d3d9_ptr
= init_d3d9(parent
->hD3d9
);
3130 if (!object
->d3d9_ptr
)
3132 WARN("Could not initialize d3d9.dll\n");
3134 return VFW_E_DDRAW_CAPS_NOT_SUITABLE
;
3137 object
->IVMRImagePresenter9_iface
.lpVtbl
= &VMR9_ImagePresenter
;
3138 object
->IVMRSurfaceAllocator9_iface
.lpVtbl
= &VMR9_SurfaceAllocator
;
3140 object
->refCount
= 1;
3141 object
->pVMR9
= parent
;
3143 TRACE("Created default presenter %p.\n", object
);
3144 *presenter
= object
;