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"
38 #include "wine/debug.h"
40 WINE_DEFAULT_DEBUG_CHANNEL(quartz
);
42 static inline const char *debugstr_normalized_rect(const VMR9NormalizedRect
*rect
)
44 if (!rect
) return "(null)";
45 return wine_dbg_sprintf("(%.8e,%.8e)-(%.8e,%.8e)", rect
->left
, rect
->top
, rect
->right
, rect
->bottom
);
48 static const BITMAPINFOHEADER
*get_bitmap_header(const AM_MEDIA_TYPE
*mt
)
50 if (IsEqualGUID(&mt
->formattype
, &FORMAT_VideoInfo
))
51 return &((VIDEOINFOHEADER
*)mt
->pbFormat
)->bmiHeader
;
53 return &((VIDEOINFOHEADER2
*)mt
->pbFormat
)->bmiHeader
;
58 struct strmbase_renderer renderer
;
59 struct video_window window
;
61 IAMCertifiedOutputProtection IAMCertifiedOutputProtection_iface
;
62 IAMFilterMiscFlags IAMFilterMiscFlags_iface
;
63 IVMRAspectRatioControl9 IVMRAspectRatioControl9_iface
;
64 IVMRFilterConfig IVMRFilterConfig_iface
;
65 IVMRFilterConfig9 IVMRFilterConfig9_iface
;
66 IVMRMixerBitmap9 IVMRMixerBitmap9_iface
;
67 IVMRMixerControl9 IVMRMixerControl9_iface
;
68 IVMRMonitorConfig IVMRMonitorConfig_iface
;
69 IVMRMonitorConfig9 IVMRMonitorConfig9_iface
;
70 IVMRSurfaceAllocatorNotify IVMRSurfaceAllocatorNotify_iface
;
71 IVMRSurfaceAllocatorNotify9 IVMRSurfaceAllocatorNotify9_iface
;
72 IVMRWindowlessControl IVMRWindowlessControl_iface
;
73 IVMRWindowlessControl9 IVMRWindowlessControl9_iface
;
75 /* Devil May Cry 3 releases the last IBaseFilter reference while still
76 * holding an IVMRSurfaceAllocatorNotify9 reference, and depends on
77 * IVMRSurfaceAllocator9::TerminateDevice() being called as a result.
78 * Native uses a separate reference count for IVMRSurfaceAllocatorNotify9. */
79 LONG IVMRSurfaceAllocatorNotify9_refcount
;
81 IOverlay IOverlay_iface
;
83 IVMRSurfaceAllocator9
*allocator
;
84 IVMRImagePresenter9
*presenter
;
90 * The Video Mixing Renderer supports 3 modes, renderless, windowless and windowed
91 * What I do is implement windowless as a special case of renderless, and then
92 * windowed also as a special case of windowless. This is probably the easiest way.
95 BITMAPINFOHEADER bmiheader
;
99 /* Presentation related members */
100 IDirect3DDevice9
*allocator_d3d9_dev
;
101 IDirect3DSurface9
**surfaces
;
106 HWND clipping_window
;
110 VMR9AspectRatioMode aspect_mode
;
113 static inline BOOL
is_vmr9(const struct quartz_vmr
*filter
)
115 return IsEqualGUID(&filter
->renderer
.filter
.clsid
, &CLSID_VideoMixingRenderer9
);
118 static inline struct quartz_vmr
*impl_from_video_window(struct video_window
*iface
)
120 return CONTAINING_RECORD(iface
, struct quartz_vmr
, window
);
123 static inline struct quartz_vmr
*impl_from_IAMCertifiedOutputProtection(IAMCertifiedOutputProtection
*iface
)
125 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IAMCertifiedOutputProtection_iface
);
128 static inline struct quartz_vmr
*impl_from_IAMFilterMiscFlags(IAMFilterMiscFlags
*iface
)
130 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IAMFilterMiscFlags_iface
);
133 static inline struct quartz_vmr
*impl_from_IVMRFilterConfig(IVMRFilterConfig
*iface
)
135 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRFilterConfig_iface
);
138 static inline struct quartz_vmr
*impl_from_IVMRFilterConfig9(IVMRFilterConfig9
*iface
)
140 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRFilterConfig9_iface
);
143 static inline struct quartz_vmr
*impl_from_IVMRMonitorConfig(IVMRMonitorConfig
*iface
)
145 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRMonitorConfig_iface
);
148 static inline struct quartz_vmr
*impl_from_IVMRMonitorConfig9(IVMRMonitorConfig9
*iface
)
150 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRMonitorConfig9_iface
);
153 static inline struct quartz_vmr
*impl_from_IVMRSurfaceAllocatorNotify(IVMRSurfaceAllocatorNotify
*iface
)
155 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRSurfaceAllocatorNotify_iface
);
158 static inline struct quartz_vmr
*impl_from_IVMRSurfaceAllocatorNotify9(IVMRSurfaceAllocatorNotify9
*iface
)
160 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRSurfaceAllocatorNotify9_iface
);
163 static inline struct quartz_vmr
*impl_from_IVMRWindowlessControl(IVMRWindowlessControl
*iface
)
165 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRWindowlessControl_iface
);
168 static inline struct quartz_vmr
*impl_from_IVMRWindowlessControl9(IVMRWindowlessControl9
*iface
)
170 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRWindowlessControl9_iface
);
173 struct default_presenter
175 IVMRImagePresenter9 IVMRImagePresenter9_iface
;
176 IVMRSurfaceAllocator9 IVMRSurfaceAllocator9_iface
;
180 IDirect3DDevice9
*d3d9_dev
;
181 IDirect3D9
*d3d9_ptr
;
182 IDirect3DSurface9
**d3d9_surfaces
;
186 VMR9AllocationInfo info
;
188 struct quartz_vmr
* pVMR9
;
189 IVMRSurfaceAllocatorNotify9
*SurfaceAllocatorNotify
;
192 static inline struct default_presenter
*impl_from_IVMRImagePresenter9(IVMRImagePresenter9
*iface
)
194 return CONTAINING_RECORD(iface
, struct default_presenter
, IVMRImagePresenter9_iface
);
197 static inline struct default_presenter
*impl_from_IVMRSurfaceAllocator9(IVMRSurfaceAllocator9
*iface
)
199 return CONTAINING_RECORD(iface
, struct default_presenter
, IVMRSurfaceAllocator9_iface
);
202 static HRESULT
VMR9DefaultAllocatorPresenterImpl_create(struct quartz_vmr
*parent
, LPVOID
* ppv
);
204 static inline struct quartz_vmr
*impl_from_IBaseFilter(IBaseFilter
*iface
)
206 return CONTAINING_RECORD(iface
, struct quartz_vmr
, renderer
.filter
.IBaseFilter_iface
);
209 static HRESULT
vmr_render(struct strmbase_renderer
*iface
, IMediaSample
*sample
)
211 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
212 unsigned int data_size
, width
, depth
, src_pitch
;
213 const BITMAPINFOHEADER
*bitmap_header
;
214 REFERENCE_TIME start_time
, end_time
;
215 VMR9PresentationInfo info
= {};
216 D3DLOCKED_RECT locked_rect
;
221 TRACE("filter %p, sample %p.\n", filter
, sample
);
223 /* It is possible that there is no device at this point */
225 if (!filter
->allocator
|| !filter
->presenter
)
227 ERR("NO PRESENTER!!\n");
231 info
.dwFlags
= VMR9Sample_SrcDstRectsValid
;
233 if (SUCCEEDED(hr
= IMediaSample_GetTime(sample
, &start_time
, &end_time
)))
234 info
.dwFlags
|= VMR9Sample_TimeValid
;
236 if (IMediaSample_IsDiscontinuity(sample
) == S_OK
)
237 info
.dwFlags
|= VMR9Sample_Discontinuity
;
239 if (IMediaSample_IsPreroll(sample
) == S_OK
)
240 info
.dwFlags
|= VMR9Sample_Preroll
;
242 if (IMediaSample_IsSyncPoint(sample
) == S_OK
)
243 info
.dwFlags
|= VMR9Sample_SyncPoint
;
245 if (FAILED(hr
= IMediaSample_GetPointer(sample
, &data
)))
247 ERR("Failed to get pointer to sample data, hr %#x.\n", hr
);
250 data_size
= IMediaSample_GetActualDataLength(sample
);
252 bitmap_header
= get_bitmap_header(&filter
->renderer
.sink
.pin
.mt
);
253 width
= bitmap_header
->biWidth
;
254 height
= bitmap_header
->biHeight
;
255 depth
= bitmap_header
->biBitCount
;
256 if (bitmap_header
->biCompression
== mmioFOURCC('N','V','1','2')
257 || bitmap_header
->biCompression
== mmioFOURCC('Y','V','1','2'))
259 else /* packed YUV (UYVY or YUY2) or RGB */
260 src_pitch
= ((width
* depth
/ 8) + 3) & ~3;
262 info
.rtStart
= start_time
;
263 info
.rtEnd
= end_time
;
264 info
.szAspectRatio
.cx
= width
;
265 info
.szAspectRatio
.cy
= height
;
266 info
.lpSurf
= filter
->surfaces
[(++filter
->cur_surface
) % filter
->num_surfaces
];
268 if (FAILED(hr
= IDirect3DSurface9_LockRect(info
.lpSurf
, &locked_rect
, NULL
, D3DLOCK_DISCARD
)))
270 ERR("Failed to lock surface, hr %#x.\n", hr
);
274 if (height
> 0 && bitmap_header
->biCompression
== BI_RGB
)
276 BYTE
*dst
= (BYTE
*)locked_rect
.pBits
+ (height
* locked_rect
.Pitch
);
277 const BYTE
*src
= data
;
279 TRACE("Inverting image.\n");
283 dst
-= locked_rect
.Pitch
;
284 memcpy(dst
, src
, width
* depth
/ 8);
288 else if (locked_rect
.Pitch
!= src_pitch
)
290 BYTE
*dst
= locked_rect
.pBits
;
291 const BYTE
*src
= data
;
293 height
= abs(height
);
295 TRACE("Source pitch %u does not match dest pitch %u; copying manually.\n",
296 src_pitch
, locked_rect
.Pitch
);
300 memcpy(dst
, src
, width
* depth
/ 8);
302 dst
+= locked_rect
.Pitch
;
307 memcpy(locked_rect
.pBits
, data
, data_size
);
310 IDirect3DSurface9_UnlockRect(info
.lpSurf
);
312 return IVMRImagePresenter9_PresentImage(filter
->presenter
, filter
->cookie
, &info
);
315 static HRESULT
vmr_query_accept(struct strmbase_renderer
*iface
, const AM_MEDIA_TYPE
*mt
)
317 if (!IsEqualIID(&mt
->majortype
, &MEDIATYPE_Video
) || !mt
->pbFormat
)
320 if (!IsEqualGUID(&mt
->formattype
, &FORMAT_VideoInfo
)
321 && !IsEqualGUID(&mt
->formattype
, &FORMAT_VideoInfo2
))
327 static HRESULT
initialize_device(struct quartz_vmr
*filter
, VMR9AllocationInfo
*info
, DWORD count
)
332 if (FAILED(hr
= IVMRSurfaceAllocator9_InitializeDevice(filter
->allocator
,
333 filter
->cookie
, info
, &count
)))
335 WARN("Failed to initialize device (flags %#x), hr %#x.\n", info
->dwFlags
, hr
);
339 for (i
= 0; i
< count
; ++i
)
341 if (FAILED(hr
= IVMRSurfaceAllocator9_GetSurface(filter
->allocator
,
342 filter
->cookie
, i
, 0, &filter
->surfaces
[i
])))
344 ERR("Failed to get surface %u, hr %#x.\n", i
, hr
);
346 IDirect3DSurface9_Release(filter
->surfaces
[i
]);
347 IVMRSurfaceAllocator9_TerminateDevice(filter
->allocator
, filter
->cookie
);
355 static HRESULT
allocate_surfaces(struct quartz_vmr
*filter
, const AM_MEDIA_TYPE
*mt
)
357 VMR9AllocationInfo info
= {};
370 {&MEDIASUBTYPE_ARGB1555
, D3DFMT_A1R5G5B5
, VMR9AllocFlag_TextureSurface
},
371 {&MEDIASUBTYPE_ARGB32
, D3DFMT_A8R8G8B8
, VMR9AllocFlag_TextureSurface
},
372 {&MEDIASUBTYPE_ARGB4444
, D3DFMT_A4R4G4B4
, VMR9AllocFlag_TextureSurface
},
374 {&MEDIASUBTYPE_RGB24
, D3DFMT_R8G8B8
, VMR9AllocFlag_TextureSurface
| VMR9AllocFlag_OffscreenSurface
},
375 {&MEDIASUBTYPE_RGB32
, D3DFMT_X8R8G8B8
, VMR9AllocFlag_TextureSurface
| VMR9AllocFlag_OffscreenSurface
},
376 {&MEDIASUBTYPE_RGB555
, D3DFMT_X1R5G5B5
, VMR9AllocFlag_TextureSurface
| VMR9AllocFlag_OffscreenSurface
},
377 {&MEDIASUBTYPE_RGB565
, D3DFMT_R5G6B5
, VMR9AllocFlag_TextureSurface
| VMR9AllocFlag_OffscreenSurface
},
379 {&MEDIASUBTYPE_NV12
, MAKEFOURCC('N','V','1','2'), VMR9AllocFlag_OffscreenSurface
},
380 {&MEDIASUBTYPE_UYVY
, D3DFMT_UYVY
, VMR9AllocFlag_OffscreenSurface
},
381 {&MEDIASUBTYPE_YUY2
, D3DFMT_YUY2
, VMR9AllocFlag_OffscreenSurface
},
382 {&MEDIASUBTYPE_YV12
, MAKEFOURCC('Y','V','1','2'), VMR9AllocFlag_OffscreenSurface
},
385 TRACE("Initializing in mode %u, our window %p, clipping window %p.\n",
386 filter
->mode
, filter
->window
.hwnd
, filter
->clipping_window
);
388 if (filter
->mode
== VMR9Mode_Windowless
&& !filter
->clipping_window
)
391 info
.Pool
= D3DPOOL_DEFAULT
;
392 info
.MinBuffers
= count
;
393 info
.dwWidth
= info
.szAspectRatio
.cx
= info
.szNativeSize
.cx
= filter
->bmiheader
.biWidth
;
394 info
.dwHeight
= info
.szAspectRatio
.cy
= info
.szNativeSize
.cy
= filter
->bmiheader
.biHeight
;
396 if (!(filter
->surfaces
= calloc(count
, sizeof(IDirect3DSurface9
*))))
397 return E_OUTOFMEMORY
;
398 filter
->num_surfaces
= count
;
399 filter
->cur_surface
= 0;
401 if (!is_vmr9(filter
))
403 switch (filter
->bmiheader
.biCompression
)
406 switch (filter
->bmiheader
.biBitCount
)
408 case 24: info
.Format
= D3DFMT_R8G8B8
; break;
409 case 32: info
.Format
= D3DFMT_X8R8G8B8
; break;
411 FIXME("Unhandled bit depth %u.\n", filter
->bmiheader
.biBitCount
);
412 free(filter
->surfaces
);
413 return VFW_E_TYPE_NOT_ACCEPTED
;
416 info
.dwFlags
= VMR9AllocFlag_TextureSurface
;
419 case mmioFOURCC('N','V','1','2'):
420 case mmioFOURCC('U','Y','V','Y'):
421 case mmioFOURCC('Y','U','Y','2'):
422 case mmioFOURCC('Y','V','1','2'):
423 info
.Format
= filter
->bmiheader
.biCompression
;
424 info
.dwFlags
= VMR9AllocFlag_OffscreenSurface
;
428 WARN("Unhandled video compression %#x.\n", filter
->bmiheader
.biCompression
);
429 free(filter
->surfaces
);
430 return VFW_E_TYPE_NOT_ACCEPTED
;
432 if (FAILED(hr
= initialize_device(filter
, &info
, count
)))
433 free(filter
->surfaces
);
437 for (i
= 0; i
< ARRAY_SIZE(formats
); ++i
)
439 if (IsEqualGUID(&mt
->subtype
, formats
[i
].subtype
))
441 info
.Format
= formats
[i
].format
;
443 if (formats
[i
].flags
& VMR9AllocFlag_TextureSurface
)
445 info
.dwFlags
= VMR9AllocFlag_TextureSurface
;
446 if (SUCCEEDED(hr
= initialize_device(filter
, &info
, count
)))
450 if (formats
[i
].flags
& VMR9AllocFlag_OffscreenSurface
)
452 info
.dwFlags
= VMR9AllocFlag_OffscreenSurface
;
453 if (SUCCEEDED(hr
= initialize_device(filter
, &info
, count
)))
459 free(filter
->surfaces
);
460 return VFW_E_TYPE_NOT_ACCEPTED
;
463 static void vmr_init_stream(struct strmbase_renderer
*iface
)
465 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
467 if (filter
->window
.hwnd
&& filter
->window
.AutoShow
)
468 ShowWindow(filter
->window
.hwnd
, SW_SHOW
);
471 static void vmr_start_stream(struct strmbase_renderer
*iface
)
473 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
475 IVMRImagePresenter9_StartPresenting(filter
->presenter
, filter
->cookie
);
478 static void vmr_stop_stream(struct strmbase_renderer
*iface
)
480 struct quartz_vmr
*This
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
482 TRACE("(%p)\n", This
);
484 if (This
->renderer
.filter
.state
== State_Running
)
485 IVMRImagePresenter9_StopPresenting(This
->presenter
, This
->cookie
);
488 static HRESULT
vmr_connect(struct strmbase_renderer
*iface
, const AM_MEDIA_TYPE
*mt
)
490 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
491 const BITMAPINFOHEADER
*bitmap_header
= get_bitmap_header(mt
);
492 HWND window
= filter
->window
.hwnd
;
496 filter
->bmiheader
= *bitmap_header
;
497 filter
->VideoWidth
= bitmap_header
->biWidth
;
498 filter
->VideoHeight
= bitmap_header
->biHeight
;
499 SetRect(&rect
, 0, 0, filter
->VideoWidth
, filter
->VideoHeight
);
500 filter
->window
.src
= rect
;
502 AdjustWindowRectEx(&rect
, GetWindowLongW(window
, GWL_STYLE
), FALSE
,
503 GetWindowLongW(window
, GWL_EXSTYLE
));
504 SetWindowPos(window
, NULL
, 0, 0, rect
.right
- rect
.left
, rect
.bottom
- rect
.top
,
505 SWP_NOMOVE
| SWP_NOZORDER
| SWP_NOACTIVATE
);
506 GetClientRect(window
, &filter
->window
.dst
);
509 || SUCCEEDED(hr
= IVMRFilterConfig9_SetRenderingMode(&filter
->IVMRFilterConfig9_iface
, VMR9Mode_Windowed
)))
510 hr
= allocate_surfaces(filter
, mt
);
515 static void vmr_disconnect(struct strmbase_renderer
*This
)
517 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&This
->filter
.IBaseFilter_iface
);
520 if (filter
->mode
&& filter
->allocator
&& filter
->presenter
)
522 for (i
= 0; i
< filter
->num_surfaces
; ++i
)
523 IDirect3DSurface9_Release(filter
->surfaces
[i
]);
524 free(filter
->surfaces
);
526 IVMRSurfaceAllocator9_TerminateDevice(filter
->allocator
, filter
->cookie
);
527 filter
->num_surfaces
= 0;
531 static void vmr_free(struct quartz_vmr
*filter
)
534 InterlockedDecrement(&object_locks
);
537 static void vmr_destroy(struct strmbase_renderer
*iface
)
539 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
541 video_window_cleanup(&filter
->window
);
543 /* Devil May Cry 3 releases the IVMRSurfaceAllocatorNotify9 interface from
544 * TerminateDevice(). Artificially increase the reference count so that we
545 * don't free the filter yet. */
546 InterlockedIncrement(&filter
->renderer
.filter
.refcount
);
548 if (filter
->allocator
)
550 IVMRSurfaceAllocator9_TerminateDevice(filter
->allocator
, filter
->cookie
);
551 IVMRSurfaceAllocator9_Release(filter
->allocator
);
553 if (filter
->presenter
)
554 IVMRImagePresenter9_Release(filter
->presenter
);
556 filter
->num_surfaces
= 0;
557 if (filter
->allocator_d3d9_dev
)
559 IDirect3DDevice9_Release(filter
->allocator_d3d9_dev
);
560 filter
->allocator_d3d9_dev
= NULL
;
563 FreeLibrary(filter
->hD3d9
);
564 strmbase_renderer_cleanup(&filter
->renderer
);
565 if (!filter
->IVMRSurfaceAllocatorNotify9_refcount
)
569 static HRESULT
vmr_query_interface(struct strmbase_renderer
*iface
, REFIID iid
, void **out
)
571 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
573 if (IsEqualGUID(iid
, &IID_IVideoWindow
))
574 *out
= &filter
->window
.IVideoWindow_iface
;
575 else if (IsEqualGUID(iid
, &IID_IBasicVideo
))
576 *out
= &filter
->window
.IBasicVideo_iface
;
577 else if (IsEqualGUID(iid
, &IID_IAMCertifiedOutputProtection
))
578 *out
= &filter
->IAMCertifiedOutputProtection_iface
;
579 else if (IsEqualGUID(iid
, &IID_IAMFilterMiscFlags
))
580 *out
= &filter
->IAMFilterMiscFlags_iface
;
581 else if (IsEqualGUID(iid
, &IID_IVMRAspectRatioControl9
) && is_vmr9(filter
))
582 *out
= &filter
->IVMRAspectRatioControl9_iface
;
583 else if (IsEqualGUID(iid
, &IID_IVMRFilterConfig
) && !is_vmr9(filter
))
584 *out
= &filter
->IVMRFilterConfig_iface
;
585 else if (IsEqualGUID(iid
, &IID_IVMRFilterConfig9
) && is_vmr9(filter
))
586 *out
= &filter
->IVMRFilterConfig9_iface
;
587 else if (IsEqualGUID(iid
, &IID_IVMRMixerBitmap9
) && is_vmr9(filter
))
588 *out
= &filter
->IVMRMixerBitmap9_iface
;
589 else if (IsEqualGUID(iid
, &IID_IVMRMixerControl9
) && is_vmr9(filter
) && filter
->stream_count
)
590 *out
= &filter
->IVMRMixerControl9_iface
;
591 else if (IsEqualGUID(iid
, &IID_IVMRMonitorConfig
) && !is_vmr9(filter
))
592 *out
= &filter
->IVMRMonitorConfig_iface
;
593 else if (IsEqualGUID(iid
, &IID_IVMRMonitorConfig9
)
594 && filter
->mode
!= VMR9Mode_Renderless
&& is_vmr9(filter
))
595 *out
= &filter
->IVMRMonitorConfig9_iface
;
596 else if (IsEqualGUID(iid
, &IID_IVMRSurfaceAllocatorNotify
)
597 && filter
->mode
== (VMR9Mode
)VMRMode_Renderless
&& !is_vmr9(filter
))
598 *out
= &filter
->IVMRSurfaceAllocatorNotify_iface
;
599 else if (IsEqualGUID(iid
, &IID_IVMRSurfaceAllocatorNotify9
)
600 && filter
->mode
== VMR9Mode_Renderless
&& is_vmr9(filter
))
601 *out
= &filter
->IVMRSurfaceAllocatorNotify9_iface
;
602 else if (IsEqualGUID(iid
, &IID_IVMRWindowlessControl
)
603 && filter
->mode
== (VMR9Mode
)VMRMode_Windowless
&& !is_vmr9(filter
))
604 *out
= &filter
->IVMRWindowlessControl_iface
;
605 else if (IsEqualGUID(iid
, &IID_IVMRWindowlessControl9
)
606 && filter
->mode
== VMR9Mode_Windowless
&& is_vmr9(filter
))
607 *out
= &filter
->IVMRWindowlessControl9_iface
;
609 return E_NOINTERFACE
;
611 IUnknown_AddRef((IUnknown
*)*out
);
615 static HRESULT
vmr_pin_query_interface(struct strmbase_renderer
*iface
, REFIID iid
, void **out
)
617 struct quartz_vmr
*filter
= impl_from_IBaseFilter(&iface
->filter
.IBaseFilter_iface
);
619 if (IsEqualGUID(iid
, &IID_IOverlay
))
620 *out
= &filter
->IOverlay_iface
;
622 return E_NOINTERFACE
;
624 IUnknown_AddRef((IUnknown
*)*out
);
628 static const struct strmbase_renderer_ops renderer_ops
=
630 .renderer_query_accept
= vmr_query_accept
,
631 .renderer_render
= vmr_render
,
632 .renderer_init_stream
= vmr_init_stream
,
633 .renderer_start_stream
= vmr_start_stream
,
634 .renderer_stop_stream
= vmr_stop_stream
,
635 .renderer_connect
= vmr_connect
,
636 .renderer_disconnect
= vmr_disconnect
,
637 .renderer_destroy
= vmr_destroy
,
638 .renderer_query_interface
= vmr_query_interface
,
639 .renderer_pin_query_interface
= vmr_pin_query_interface
,
642 static RECT
vmr_get_default_rect(struct video_window
*This
)
644 struct quartz_vmr
*pVMR9
= impl_from_video_window(This
);
647 SetRect(&defRect
, 0, 0, pVMR9
->VideoWidth
, pVMR9
->VideoHeight
);
652 static HRESULT
vmr_get_current_image(struct video_window
*iface
, LONG
*size
, LONG
*image
)
654 struct quartz_vmr
*filter
= impl_from_video_window(iface
);
655 IDirect3DSurface9
*rt
= NULL
, *surface
= NULL
;
656 D3DLOCKED_RECT locked_rect
;
657 IDirect3DDevice9
*device
;
658 unsigned int row_size
;
659 BITMAPINFOHEADER bih
;
664 EnterCriticalSection(&filter
->renderer
.filter
.stream_cs
);
665 device
= filter
->allocator_d3d9_dev
;
667 bih
= *get_bitmap_header(&filter
->renderer
.sink
.pin
.mt
);
668 bih
.biSizeImage
= bih
.biWidth
* bih
.biHeight
* bih
.biBitCount
/ 8;
672 *size
= sizeof(BITMAPINFOHEADER
) + bih
.biSizeImage
;
673 LeaveCriticalSection(&filter
->renderer
.filter
.stream_cs
);
677 if (FAILED(hr
= IDirect3DDevice9_GetRenderTarget(device
, 0, &rt
)))
680 if (FAILED(hr
= IDirect3DDevice9_CreateOffscreenPlainSurface(device
, bih
.biWidth
,
681 bih
.biHeight
, D3DFMT_X8R8G8B8
, D3DPOOL_SYSTEMMEM
, &surface
, NULL
)))
684 if (FAILED(hr
= IDirect3DDevice9_GetRenderTargetData(device
, rt
, surface
)))
687 if (FAILED(hr
= IDirect3DSurface9_LockRect(surface
, &locked_rect
, NULL
, D3DLOCK_READONLY
)))
691 memcpy(image
, &bih
, min(size_left
, sizeof(BITMAPINFOHEADER
)));
692 size_left
-= sizeof(BITMAPINFOHEADER
);
694 dst
= (char *)image
+ sizeof(BITMAPINFOHEADER
);
695 row_size
= bih
.biWidth
* bih
.biBitCount
/ 8;
697 for (i
= 0; i
< bih
.biHeight
&& size_left
> 0; ++i
)
699 memcpy(dst
, (char *)locked_rect
.pBits
+ (i
* locked_rect
.Pitch
), min(row_size
, size_left
));
701 size_left
-= row_size
;
704 IDirect3DSurface9_UnlockRect(surface
);
707 if (surface
) IDirect3DSurface9_Release(surface
);
708 if (rt
) IDirect3DSurface9_Release(rt
);
709 LeaveCriticalSection(&filter
->renderer
.filter
.stream_cs
);
713 static const struct video_window_ops window_ops
=
715 .get_default_rect
= vmr_get_default_rect
,
716 .get_current_image
= vmr_get_current_image
,
719 static const IVideoWindowVtbl IVideoWindow_VTable
=
721 BaseControlWindowImpl_QueryInterface
,
722 BaseControlWindowImpl_AddRef
,
723 BaseControlWindowImpl_Release
,
724 BaseControlWindowImpl_GetTypeInfoCount
,
725 BaseControlWindowImpl_GetTypeInfo
,
726 BaseControlWindowImpl_GetIDsOfNames
,
727 BaseControlWindowImpl_Invoke
,
728 BaseControlWindowImpl_put_Caption
,
729 BaseControlWindowImpl_get_Caption
,
730 BaseControlWindowImpl_put_WindowStyle
,
731 BaseControlWindowImpl_get_WindowStyle
,
732 BaseControlWindowImpl_put_WindowStyleEx
,
733 BaseControlWindowImpl_get_WindowStyleEx
,
734 BaseControlWindowImpl_put_AutoShow
,
735 BaseControlWindowImpl_get_AutoShow
,
736 BaseControlWindowImpl_put_WindowState
,
737 BaseControlWindowImpl_get_WindowState
,
738 BaseControlWindowImpl_put_BackgroundPalette
,
739 BaseControlWindowImpl_get_BackgroundPalette
,
740 BaseControlWindowImpl_put_Visible
,
741 BaseControlWindowImpl_get_Visible
,
742 BaseControlWindowImpl_put_Left
,
743 BaseControlWindowImpl_get_Left
,
744 BaseControlWindowImpl_put_Width
,
745 BaseControlWindowImpl_get_Width
,
746 BaseControlWindowImpl_put_Top
,
747 BaseControlWindowImpl_get_Top
,
748 BaseControlWindowImpl_put_Height
,
749 BaseControlWindowImpl_get_Height
,
750 BaseControlWindowImpl_put_Owner
,
751 BaseControlWindowImpl_get_Owner
,
752 BaseControlWindowImpl_put_MessageDrain
,
753 BaseControlWindowImpl_get_MessageDrain
,
754 BaseControlWindowImpl_get_BorderColor
,
755 BaseControlWindowImpl_put_BorderColor
,
756 BaseControlWindowImpl_get_FullScreenMode
,
757 BaseControlWindowImpl_put_FullScreenMode
,
758 BaseControlWindowImpl_SetWindowForeground
,
759 BaseControlWindowImpl_NotifyOwnerMessage
,
760 BaseControlWindowImpl_SetWindowPosition
,
761 BaseControlWindowImpl_GetWindowPosition
,
762 BaseControlWindowImpl_GetMinIdealImageSize
,
763 BaseControlWindowImpl_GetMaxIdealImageSize
,
764 BaseControlWindowImpl_GetRestorePosition
,
765 BaseControlWindowImpl_HideCursor
,
766 BaseControlWindowImpl_IsCursorHidden
769 static HRESULT WINAPI
AMCertifiedOutputProtection_QueryInterface(IAMCertifiedOutputProtection
*iface
,
770 REFIID riid
, void **ppv
)
772 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
773 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
776 static ULONG WINAPI
AMCertifiedOutputProtection_AddRef(IAMCertifiedOutputProtection
*iface
)
778 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
779 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
782 static ULONG WINAPI
AMCertifiedOutputProtection_Release(IAMCertifiedOutputProtection
*iface
)
784 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
785 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
788 static HRESULT WINAPI
AMCertifiedOutputProtection_KeyExchange(IAMCertifiedOutputProtection
*iface
,
789 GUID
* pRandom
, BYTE
** VarLenCertGH
,
790 DWORD
* pdwLengthCertGH
)
792 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
794 FIXME("(%p/%p)->(%p, %p, %p) stub\n", iface
, This
, pRandom
, VarLenCertGH
, pdwLengthCertGH
);
795 return VFW_E_NO_COPP_HW
;
798 static HRESULT WINAPI
AMCertifiedOutputProtection_SessionSequenceStart(IAMCertifiedOutputProtection
*iface
,
799 AMCOPPSignature
* pSig
)
801 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
803 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pSig
);
804 return VFW_E_NO_COPP_HW
;
807 static HRESULT WINAPI
AMCertifiedOutputProtection_ProtectionCommand(IAMCertifiedOutputProtection
*iface
,
808 const AMCOPPCommand
* cmd
)
810 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
812 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, cmd
);
813 return VFW_E_NO_COPP_HW
;
816 static HRESULT WINAPI
AMCertifiedOutputProtection_ProtectionStatus(IAMCertifiedOutputProtection
*iface
,
817 const AMCOPPStatusInput
* pStatusInput
,
818 AMCOPPStatusOutput
* pStatusOutput
)
820 struct quartz_vmr
*This
= impl_from_IAMCertifiedOutputProtection(iface
);
822 FIXME("(%p/%p)->(%p, %p) stub\n", iface
, This
, pStatusInput
, pStatusOutput
);
823 return VFW_E_NO_COPP_HW
;
826 static const IAMCertifiedOutputProtectionVtbl IAMCertifiedOutputProtection_Vtbl
=
828 AMCertifiedOutputProtection_QueryInterface
,
829 AMCertifiedOutputProtection_AddRef
,
830 AMCertifiedOutputProtection_Release
,
831 AMCertifiedOutputProtection_KeyExchange
,
832 AMCertifiedOutputProtection_SessionSequenceStart
,
833 AMCertifiedOutputProtection_ProtectionCommand
,
834 AMCertifiedOutputProtection_ProtectionStatus
837 static HRESULT WINAPI
AMFilterMiscFlags_QueryInterface(IAMFilterMiscFlags
*iface
, REFIID riid
, void **ppv
) {
838 struct quartz_vmr
*This
= impl_from_IAMFilterMiscFlags(iface
);
839 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
842 static ULONG WINAPI
AMFilterMiscFlags_AddRef(IAMFilterMiscFlags
*iface
) {
843 struct quartz_vmr
*This
= impl_from_IAMFilterMiscFlags(iface
);
844 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
847 static ULONG WINAPI
AMFilterMiscFlags_Release(IAMFilterMiscFlags
*iface
) {
848 struct quartz_vmr
*This
= impl_from_IAMFilterMiscFlags(iface
);
849 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
852 static ULONG WINAPI
AMFilterMiscFlags_GetMiscFlags(IAMFilterMiscFlags
*iface
) {
853 return AM_FILTER_MISC_FLAGS_IS_RENDERER
;
856 static const IAMFilterMiscFlagsVtbl IAMFilterMiscFlags_Vtbl
= {
857 AMFilterMiscFlags_QueryInterface
,
858 AMFilterMiscFlags_AddRef
,
859 AMFilterMiscFlags_Release
,
860 AMFilterMiscFlags_GetMiscFlags
863 static HRESULT WINAPI
VMR7FilterConfig_QueryInterface(IVMRFilterConfig
*iface
, REFIID riid
,
866 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
867 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
870 static ULONG WINAPI
VMR7FilterConfig_AddRef(IVMRFilterConfig
*iface
)
872 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
873 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
876 static ULONG WINAPI
VMR7FilterConfig_Release(IVMRFilterConfig
*iface
)
878 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
879 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
882 static HRESULT WINAPI
VMR7FilterConfig_SetImageCompositor(IVMRFilterConfig
*iface
,
883 IVMRImageCompositor
*compositor
)
885 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
887 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, compositor
);
891 static HRESULT WINAPI
VMR7FilterConfig_SetNumberOfStreams(IVMRFilterConfig
*iface
, DWORD max
)
893 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
895 FIXME("(%p/%p)->(%u) stub\n", iface
, This
, max
);
899 static HRESULT WINAPI
VMR7FilterConfig_GetNumberOfStreams(IVMRFilterConfig
*iface
, DWORD
*max
)
901 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
903 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, max
);
907 static HRESULT WINAPI
VMR7FilterConfig_SetRenderingPrefs(IVMRFilterConfig
*iface
, DWORD renderflags
)
909 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
911 FIXME("(%p/%p)->(%u) stub\n", iface
, This
, renderflags
);
915 static HRESULT WINAPI
VMR7FilterConfig_GetRenderingPrefs(IVMRFilterConfig
*iface
, DWORD
*renderflags
)
917 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
919 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, renderflags
);
923 static HRESULT WINAPI
VMR7FilterConfig_SetRenderingMode(IVMRFilterConfig
*iface
, DWORD mode
)
925 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig(iface
);
927 TRACE("iface %p, mode %#x.\n", iface
, mode
);
929 return IVMRFilterConfig9_SetRenderingMode(&filter
->IVMRFilterConfig9_iface
, mode
);
932 static HRESULT WINAPI
VMR7FilterConfig_GetRenderingMode(IVMRFilterConfig
*iface
, DWORD
*mode
)
934 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig(iface
);
936 TRACE("(%p/%p)->(%p)\n", iface
, This
, mode
);
937 if (!mode
) return E_POINTER
;
942 *mode
= VMRMode_Windowed
;
947 static const IVMRFilterConfigVtbl VMR7_FilterConfig_Vtbl
=
949 VMR7FilterConfig_QueryInterface
,
950 VMR7FilterConfig_AddRef
,
951 VMR7FilterConfig_Release
,
952 VMR7FilterConfig_SetImageCompositor
,
953 VMR7FilterConfig_SetNumberOfStreams
,
954 VMR7FilterConfig_GetNumberOfStreams
,
955 VMR7FilterConfig_SetRenderingPrefs
,
956 VMR7FilterConfig_GetRenderingPrefs
,
957 VMR7FilterConfig_SetRenderingMode
,
958 VMR7FilterConfig_GetRenderingMode
961 struct get_available_monitors_args
963 VMRMONITORINFO
*info7
;
964 VMR9MonitorInfo
*info9
;
969 static BOOL CALLBACK
get_available_monitors_proc(HMONITOR hmon
, HDC hdc
, LPRECT lprc
, LPARAM lparam
)
971 struct get_available_monitors_args
*args
= (struct get_available_monitors_args
*)lparam
;
974 if (args
->info7
|| args
->info9
)
977 if (!args
->arraysize
)
980 mi
.cbSize
= sizeof(mi
);
981 if (!GetMonitorInfoW(hmon
, (MONITORINFO
*)&mi
))
984 /* fill VMRMONITORINFO struct */
987 VMRMONITORINFO
*info
= args
->info7
++;
988 memset(info
, 0, sizeof(*info
));
990 if (args
->numdev
> 0)
992 info
->guid
.pGUID
= &info
->guid
.GUID
;
993 info
->guid
.GUID
.Data4
[7] = args
->numdev
;
996 info
->guid
.pGUID
= NULL
;
998 info
->rcMonitor
= mi
.rcMonitor
;
1000 info
->dwFlags
= mi
.dwFlags
;
1002 lstrcpynW(info
->szDevice
, mi
.szDevice
, ARRAY_SIZE(info
->szDevice
));
1004 /* FIXME: how to get these values? */
1005 info
->szDescription
[0] = 0;
1008 /* fill VMR9MonitorInfo struct */
1011 VMR9MonitorInfo
*info
= args
->info9
++;
1012 memset(info
, 0, sizeof(*info
));
1014 info
->uDevID
= 0; /* FIXME */
1015 info
->rcMonitor
= mi
.rcMonitor
;
1017 info
->dwFlags
= mi
.dwFlags
;
1019 lstrcpynW(info
->szDevice
, mi
.szDevice
, ARRAY_SIZE(info
->szDevice
));
1021 /* FIXME: how to get these values? */
1022 info
->szDescription
[0] = 0;
1023 info
->dwVendorId
= 0;
1024 info
->dwDeviceId
= 0;
1025 info
->dwSubSysId
= 0;
1026 info
->dwRevision
= 0;
1036 static HRESULT WINAPI
VMR7MonitorConfig_QueryInterface(IVMRMonitorConfig
*iface
, REFIID riid
,
1039 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1040 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1043 static ULONG WINAPI
VMR7MonitorConfig_AddRef(IVMRMonitorConfig
*iface
)
1045 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1046 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1049 static ULONG WINAPI
VMR7MonitorConfig_Release(IVMRMonitorConfig
*iface
)
1051 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1052 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1055 static HRESULT WINAPI
VMR7MonitorConfig_SetMonitor(IVMRMonitorConfig
*iface
, const VMRGUID
*pGUID
)
1057 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1059 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pGUID
);
1067 static HRESULT WINAPI
VMR7MonitorConfig_GetMonitor(IVMRMonitorConfig
*iface
, VMRGUID
*pGUID
)
1069 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1071 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pGUID
);
1076 pGUID
->pGUID
= NULL
; /* default DirectDraw device */
1080 static HRESULT WINAPI
VMR7MonitorConfig_SetDefaultMonitor(IVMRMonitorConfig
*iface
,
1081 const VMRGUID
*pGUID
)
1083 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1085 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pGUID
);
1093 static HRESULT WINAPI
VMR7MonitorConfig_GetDefaultMonitor(IVMRMonitorConfig
*iface
, VMRGUID
*pGUID
)
1095 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1097 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, pGUID
);
1102 pGUID
->pGUID
= NULL
; /* default DirectDraw device */
1106 static HRESULT WINAPI
VMR7MonitorConfig_GetAvailableMonitors(IVMRMonitorConfig
*iface
,
1107 VMRMONITORINFO
*info
, DWORD arraysize
,
1110 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig(iface
);
1111 struct get_available_monitors_args args
;
1113 FIXME("(%p/%p)->(%p, %u, %p) semi-stub\n", iface
, This
, info
, arraysize
, numdev
);
1118 if (info
&& arraysize
== 0)
1119 return E_INVALIDARG
;
1123 args
.arraysize
= arraysize
;
1125 EnumDisplayMonitors(NULL
, NULL
, get_available_monitors_proc
, (LPARAM
)&args
);
1127 *numdev
= args
.numdev
;
1131 static const IVMRMonitorConfigVtbl VMR7_MonitorConfig_Vtbl
=
1133 VMR7MonitorConfig_QueryInterface
,
1134 VMR7MonitorConfig_AddRef
,
1135 VMR7MonitorConfig_Release
,
1136 VMR7MonitorConfig_SetMonitor
,
1137 VMR7MonitorConfig_GetMonitor
,
1138 VMR7MonitorConfig_SetDefaultMonitor
,
1139 VMR7MonitorConfig_GetDefaultMonitor
,
1140 VMR7MonitorConfig_GetAvailableMonitors
1143 static HRESULT WINAPI
VMR9MonitorConfig_QueryInterface(IVMRMonitorConfig9
*iface
, REFIID riid
,
1146 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1147 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1150 static ULONG WINAPI
VMR9MonitorConfig_AddRef(IVMRMonitorConfig9
*iface
)
1152 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1153 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1156 static ULONG WINAPI
VMR9MonitorConfig_Release(IVMRMonitorConfig9
*iface
)
1158 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1159 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1162 static HRESULT WINAPI
VMR9MonitorConfig_SetMonitor(IVMRMonitorConfig9
*iface
, UINT uDev
)
1164 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1166 FIXME("(%p/%p)->(%u) stub\n", iface
, This
, uDev
);
1171 static HRESULT WINAPI
VMR9MonitorConfig_GetMonitor(IVMRMonitorConfig9
*iface
, UINT
*uDev
)
1173 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1175 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, uDev
);
1184 static HRESULT WINAPI
VMR9MonitorConfig_SetDefaultMonitor(IVMRMonitorConfig9
*iface
, UINT uDev
)
1186 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1188 FIXME("(%p/%p)->(%u) stub\n", iface
, This
, uDev
);
1193 static HRESULT WINAPI
VMR9MonitorConfig_GetDefaultMonitor(IVMRMonitorConfig9
*iface
, UINT
*uDev
)
1195 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1197 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, uDev
);
1206 static HRESULT WINAPI
VMR9MonitorConfig_GetAvailableMonitors(IVMRMonitorConfig9
*iface
,
1207 VMR9MonitorInfo
*info
, DWORD arraysize
,
1210 struct quartz_vmr
*This
= impl_from_IVMRMonitorConfig9(iface
);
1211 struct get_available_monitors_args args
;
1213 FIXME("(%p/%p)->(%p, %u, %p) semi-stub\n", iface
, This
, info
, arraysize
, numdev
);
1218 if (info
&& arraysize
== 0)
1219 return E_INVALIDARG
;
1223 args
.arraysize
= arraysize
;
1225 EnumDisplayMonitors(NULL
, NULL
, get_available_monitors_proc
, (LPARAM
)&args
);
1227 *numdev
= args
.numdev
;
1231 static const IVMRMonitorConfig9Vtbl VMR9_MonitorConfig_Vtbl
=
1233 VMR9MonitorConfig_QueryInterface
,
1234 VMR9MonitorConfig_AddRef
,
1235 VMR9MonitorConfig_Release
,
1236 VMR9MonitorConfig_SetMonitor
,
1237 VMR9MonitorConfig_GetMonitor
,
1238 VMR9MonitorConfig_SetDefaultMonitor
,
1239 VMR9MonitorConfig_GetDefaultMonitor
,
1240 VMR9MonitorConfig_GetAvailableMonitors
1243 static HRESULT WINAPI
VMR9FilterConfig_QueryInterface(IVMRFilterConfig9
*iface
, REFIID riid
, LPVOID
* ppv
)
1245 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1246 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1249 static ULONG WINAPI
VMR9FilterConfig_AddRef(IVMRFilterConfig9
*iface
)
1251 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1252 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1255 static ULONG WINAPI
VMR9FilterConfig_Release(IVMRFilterConfig9
*iface
)
1257 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1258 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1261 static HRESULT WINAPI
VMR9FilterConfig_SetImageCompositor(IVMRFilterConfig9
*iface
, IVMRImageCompositor9
*compositor
)
1263 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1265 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, compositor
);
1269 static HRESULT WINAPI
VMR9FilterConfig_SetNumberOfStreams(IVMRFilterConfig9
*iface
, DWORD count
)
1271 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig9(iface
);
1273 FIXME("iface %p, count %u, stub!\n", iface
, count
);
1277 WARN("Application requested zero streams; returning E_INVALIDARG.\n");
1278 return E_INVALIDARG
;
1281 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1283 if (filter
->stream_count
)
1285 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1286 WARN("Stream count is already set; returning VFW_E_WRONG_STATE.\n");
1287 return VFW_E_WRONG_STATE
;
1290 filter
->stream_count
= count
;
1292 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1296 static HRESULT WINAPI
VMR9FilterConfig_GetNumberOfStreams(IVMRFilterConfig9
*iface
, DWORD
*count
)
1298 struct quartz_vmr
*filter
= impl_from_IVMRFilterConfig9(iface
);
1300 TRACE("filter %p, count %p.\n", filter
, count
);
1302 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1304 if (!filter
->stream_count
)
1306 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1307 return VFW_E_VMR_NOT_IN_MIXER_MODE
;
1310 *count
= filter
->stream_count
;
1312 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1316 static HRESULT WINAPI
VMR9FilterConfig_SetRenderingPrefs(IVMRFilterConfig9
*iface
, DWORD renderflags
)
1318 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1320 FIXME("(%p/%p)->(%u) stub\n", iface
, This
, renderflags
);
1324 static HRESULT WINAPI
VMR9FilterConfig_GetRenderingPrefs(IVMRFilterConfig9
*iface
, DWORD
*renderflags
)
1326 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1328 FIXME("(%p/%p)->(%p) stub\n", iface
, This
, renderflags
);
1332 static HRESULT WINAPI
VMR9FilterConfig_SetRenderingMode(IVMRFilterConfig9
*iface
, DWORD mode
)
1335 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1337 TRACE("(%p/%p)->(%u)\n", iface
, This
, mode
);
1339 EnterCriticalSection(&This
->renderer
.filter
.filter_cs
);
1342 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1343 return VFW_E_WRONG_STATE
;
1346 if (This
->allocator
)
1347 IVMRSurfaceAllocator9_Release(This
->allocator
);
1348 if (This
->presenter
)
1349 IVMRImagePresenter9_Release(This
->presenter
);
1351 This
->allocator
= NULL
;
1352 This
->presenter
= NULL
;
1356 case VMR9Mode_Windowed
:
1357 case VMR9Mode_Windowless
:
1360 if (FAILED(hr
= VMR9DefaultAllocatorPresenterImpl_create(This
, (void **)&This
->presenter
)))
1362 ERR("Failed to create default presenter, hr %#x.\n", hr
);
1366 if (FAILED(hr
= IVMRImagePresenter9_QueryInterface(This
->presenter
,
1367 &IID_IVMRSurfaceAllocator9
, (void **)&This
->allocator
)))
1369 ERR("Failed to query for IVMRSurfaceAllocator9, hr %#x.\n", hr
);
1370 IVMRImagePresenter9_Release(This
->presenter
);
1371 This
->allocator
= NULL
;
1372 This
->presenter
= NULL
;
1376 hr
= IVMRSurfaceAllocator9_AdviseNotify(This
->allocator
, &This
->IVMRSurfaceAllocatorNotify9_iface
);
1378 case VMR9Mode_Renderless
:
1381 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1382 return E_INVALIDARG
;
1385 if (mode
!= VMR9Mode_Windowed
)
1386 video_window_cleanup(&This
->window
);
1389 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1393 static HRESULT WINAPI
VMR9FilterConfig_GetRenderingMode(IVMRFilterConfig9
*iface
, DWORD
*mode
)
1395 struct quartz_vmr
*This
= impl_from_IVMRFilterConfig9(iface
);
1397 TRACE("(%p/%p)->(%p)\n", iface
, This
, mode
);
1404 *mode
= VMR9Mode_Windowed
;
1409 static const IVMRFilterConfig9Vtbl VMR9_FilterConfig_Vtbl
=
1411 VMR9FilterConfig_QueryInterface
,
1412 VMR9FilterConfig_AddRef
,
1413 VMR9FilterConfig_Release
,
1414 VMR9FilterConfig_SetImageCompositor
,
1415 VMR9FilterConfig_SetNumberOfStreams
,
1416 VMR9FilterConfig_GetNumberOfStreams
,
1417 VMR9FilterConfig_SetRenderingPrefs
,
1418 VMR9FilterConfig_GetRenderingPrefs
,
1419 VMR9FilterConfig_SetRenderingMode
,
1420 VMR9FilterConfig_GetRenderingMode
1423 static HRESULT WINAPI
VMR7WindowlessControl_QueryInterface(IVMRWindowlessControl
*iface
, REFIID riid
,
1426 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1427 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1430 static ULONG WINAPI
VMR7WindowlessControl_AddRef(IVMRWindowlessControl
*iface
)
1432 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1433 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1436 static ULONG WINAPI
VMR7WindowlessControl_Release(IVMRWindowlessControl
*iface
)
1438 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1439 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1442 static HRESULT WINAPI
VMR7WindowlessControl_GetNativeVideoSize(IVMRWindowlessControl
*iface
,
1443 LONG
*width
, LONG
*height
, LONG
*aspect_width
, LONG
*aspect_height
)
1445 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl(iface
);
1447 TRACE("filter %p, width %p, height %p, aspect_width %p, aspect_height %p.\n",
1448 filter
, width
, height
, aspect_width
, aspect_height
);
1450 if (!width
|| !height
)
1453 *width
= filter
->bmiheader
.biWidth
;
1454 *height
= filter
->bmiheader
.biHeight
;
1456 *aspect_width
= filter
->bmiheader
.biWidth
;
1458 *aspect_height
= filter
->bmiheader
.biHeight
;
1463 static HRESULT WINAPI
VMR7WindowlessControl_GetMinIdealVideoSize(IVMRWindowlessControl
*iface
,
1464 LONG
*width
, LONG
*height
)
1466 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1468 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1472 static HRESULT WINAPI
VMR7WindowlessControl_GetMaxIdealVideoSize(IVMRWindowlessControl
*iface
,
1473 LONG
*width
, LONG
*height
)
1475 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1477 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1481 static HRESULT WINAPI
VMR7WindowlessControl_SetVideoPosition(IVMRWindowlessControl
*iface
,
1482 const RECT
*source
, const RECT
*dest
)
1484 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1486 TRACE("(%p/%p)->(%p, %p)\n", iface
, This
, source
, dest
);
1488 EnterCriticalSection(&This
->renderer
.filter
.filter_cs
);
1491 This
->window
.src
= *source
;
1493 This
->window
.dst
= *dest
;
1495 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1500 static HRESULT WINAPI
VMR7WindowlessControl_GetVideoPosition(IVMRWindowlessControl
*iface
,
1501 RECT
*source
, RECT
*dest
)
1503 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1506 *source
= This
->window
.src
;
1509 *dest
= This
->window
.dst
;
1511 FIXME("(%p/%p)->(%p/%p) stub\n", iface
, This
, source
, dest
);
1515 static HRESULT WINAPI
VMR7WindowlessControl_GetAspectRatioMode(IVMRWindowlessControl
*iface
,
1518 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1520 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1524 static HRESULT WINAPI
VMR7WindowlessControl_SetAspectRatioMode(IVMRWindowlessControl
*iface
,
1527 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1529 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1533 static HRESULT WINAPI
VMR7WindowlessControl_SetVideoClippingWindow(IVMRWindowlessControl
*iface
, HWND window
)
1535 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl(iface
);
1537 TRACE("iface %p, window %p.\n", iface
, window
);
1539 return IVMRWindowlessControl9_SetVideoClippingWindow(&filter
->IVMRWindowlessControl9_iface
, window
);
1542 static HRESULT WINAPI
VMR7WindowlessControl_RepaintVideo(IVMRWindowlessControl
*iface
,
1545 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1547 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1551 static HRESULT WINAPI
VMR7WindowlessControl_DisplayModeChanged(IVMRWindowlessControl
*iface
)
1553 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1555 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1559 static HRESULT WINAPI
VMR7WindowlessControl_GetCurrentImage(IVMRWindowlessControl
*iface
,
1562 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1564 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1568 static HRESULT WINAPI
VMR7WindowlessControl_SetBorderColor(IVMRWindowlessControl
*iface
,
1571 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1573 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1577 static HRESULT WINAPI
VMR7WindowlessControl_GetBorderColor(IVMRWindowlessControl
*iface
,
1580 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1582 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1586 static HRESULT WINAPI
VMR7WindowlessControl_SetColorKey(IVMRWindowlessControl
*iface
, COLORREF color
)
1588 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1590 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1594 static HRESULT WINAPI
VMR7WindowlessControl_GetColorKey(IVMRWindowlessControl
*iface
, COLORREF
*color
)
1596 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl(iface
);
1598 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1602 static const IVMRWindowlessControlVtbl VMR7_WindowlessControl_Vtbl
=
1604 VMR7WindowlessControl_QueryInterface
,
1605 VMR7WindowlessControl_AddRef
,
1606 VMR7WindowlessControl_Release
,
1607 VMR7WindowlessControl_GetNativeVideoSize
,
1608 VMR7WindowlessControl_GetMinIdealVideoSize
,
1609 VMR7WindowlessControl_GetMaxIdealVideoSize
,
1610 VMR7WindowlessControl_SetVideoPosition
,
1611 VMR7WindowlessControl_GetVideoPosition
,
1612 VMR7WindowlessControl_GetAspectRatioMode
,
1613 VMR7WindowlessControl_SetAspectRatioMode
,
1614 VMR7WindowlessControl_SetVideoClippingWindow
,
1615 VMR7WindowlessControl_RepaintVideo
,
1616 VMR7WindowlessControl_DisplayModeChanged
,
1617 VMR7WindowlessControl_GetCurrentImage
,
1618 VMR7WindowlessControl_SetBorderColor
,
1619 VMR7WindowlessControl_GetBorderColor
,
1620 VMR7WindowlessControl_SetColorKey
,
1621 VMR7WindowlessControl_GetColorKey
1624 static HRESULT WINAPI
VMR9WindowlessControl_QueryInterface(IVMRWindowlessControl9
*iface
, REFIID riid
, LPVOID
* ppv
)
1626 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1627 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1630 static ULONG WINAPI
VMR9WindowlessControl_AddRef(IVMRWindowlessControl9
*iface
)
1632 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1633 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1636 static ULONG WINAPI
VMR9WindowlessControl_Release(IVMRWindowlessControl9
*iface
)
1638 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1639 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1642 static HRESULT WINAPI
VMR9WindowlessControl_GetNativeVideoSize(IVMRWindowlessControl9
*iface
,
1643 LONG
*width
, LONG
*height
, LONG
*aspect_width
, LONG
*aspect_height
)
1645 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1647 TRACE("filter %p, width %p, height %p, aspect_width %p, aspect_height %p.\n",
1648 filter
, width
, height
, aspect_width
, aspect_height
);
1650 if (!width
|| !height
)
1653 *width
= filter
->bmiheader
.biWidth
;
1654 *height
= filter
->bmiheader
.biHeight
;
1656 *aspect_width
= filter
->bmiheader
.biWidth
;
1658 *aspect_height
= filter
->bmiheader
.biHeight
;
1663 static HRESULT WINAPI
VMR9WindowlessControl_GetMinIdealVideoSize(IVMRWindowlessControl9
*iface
, LONG
*width
, LONG
*height
)
1665 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1667 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1671 static HRESULT WINAPI
VMR9WindowlessControl_GetMaxIdealVideoSize(IVMRWindowlessControl9
*iface
, LONG
*width
, LONG
*height
)
1673 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1675 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1679 static HRESULT WINAPI
VMR9WindowlessControl_SetVideoPosition(IVMRWindowlessControl9
*iface
,
1680 const RECT
*src
, const RECT
*dst
)
1682 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1684 TRACE("filter %p, src %s, dst %s.\n", filter
, wine_dbgstr_rect(src
), wine_dbgstr_rect(dst
));
1686 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1689 filter
->window
.src
= *src
;
1691 filter
->window
.dst
= *dst
;
1693 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1698 static HRESULT WINAPI
VMR9WindowlessControl_GetVideoPosition(IVMRWindowlessControl9
*iface
, RECT
*src
, RECT
*dst
)
1700 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1702 TRACE("filter %p, src %p, dst %p.\n", filter
, src
, dst
);
1705 *src
= filter
->window
.src
;
1708 *dst
= filter
->window
.dst
;
1713 static HRESULT WINAPI
VMR9WindowlessControl_GetAspectRatioMode(IVMRWindowlessControl9
*iface
, DWORD
*mode
)
1715 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1717 TRACE("filter %p, mode %p.\n", filter
, mode
);
1719 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1720 *mode
= filter
->aspect_mode
;
1721 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1725 static HRESULT WINAPI
VMR9WindowlessControl_SetAspectRatioMode(IVMRWindowlessControl9
*iface
, DWORD mode
)
1727 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1729 TRACE("filter %p, mode %u.\n", filter
, mode
);
1731 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1732 filter
->aspect_mode
= mode
;
1733 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1737 static HRESULT WINAPI
VMR9WindowlessControl_SetVideoClippingWindow(IVMRWindowlessControl9
*iface
, HWND window
)
1739 struct quartz_vmr
*filter
= impl_from_IVMRWindowlessControl9(iface
);
1742 TRACE("filter %p, window %p.\n", filter
, window
);
1744 if (!IsWindow(window
))
1746 WARN("Invalid window %p, returning E_INVALIDARG.\n", window
);
1747 return E_INVALIDARG
;
1750 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1752 if (filter
->renderer
.sink
.pin
.peer
)
1754 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1755 WARN("Attempt to set the clipping window while connected; returning VFW_E_WRONG_STATE.\n");
1756 return VFW_E_WRONG_STATE
;
1759 filter
->clipping_window
= window
;
1761 hr
= IVMRFilterConfig9_SetNumberOfStreams(&filter
->IVMRFilterConfig9_iface
, 4);
1763 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1767 static HRESULT WINAPI
VMR9WindowlessControl_RepaintVideo(IVMRWindowlessControl9
*iface
, HWND hwnd
, HDC hdc
)
1769 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1772 FIXME("(%p/%p)->(...) semi-stub\n", iface
, This
);
1774 EnterCriticalSection(&This
->renderer
.filter
.filter_cs
);
1775 if (hwnd
!= This
->clipping_window
)
1777 ERR("Not handling changing windows yet!!!\n");
1778 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1782 if (!This
->allocator_d3d9_dev
)
1784 ERR("No d3d9 device!\n");
1785 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1786 return VFW_E_WRONG_STATE
;
1789 /* Windowless extension */
1790 hr
= IDirect3DDevice9_Present(This
->allocator_d3d9_dev
, NULL
, NULL
, NULL
, NULL
);
1791 LeaveCriticalSection(&This
->renderer
.filter
.filter_cs
);
1796 static HRESULT WINAPI
VMR9WindowlessControl_DisplayModeChanged(IVMRWindowlessControl9
*iface
)
1798 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1800 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1804 static HRESULT WINAPI
VMR9WindowlessControl_GetCurrentImage(IVMRWindowlessControl9
*iface
, BYTE
**dib
)
1806 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1808 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1812 static HRESULT WINAPI
VMR9WindowlessControl_SetBorderColor(IVMRWindowlessControl9
*iface
, COLORREF color
)
1814 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1816 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1820 static HRESULT WINAPI
VMR9WindowlessControl_GetBorderColor(IVMRWindowlessControl9
*iface
, COLORREF
*color
)
1822 struct quartz_vmr
*This
= impl_from_IVMRWindowlessControl9(iface
);
1824 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1828 static const IVMRWindowlessControl9Vtbl VMR9_WindowlessControl_Vtbl
=
1830 VMR9WindowlessControl_QueryInterface
,
1831 VMR9WindowlessControl_AddRef
,
1832 VMR9WindowlessControl_Release
,
1833 VMR9WindowlessControl_GetNativeVideoSize
,
1834 VMR9WindowlessControl_GetMinIdealVideoSize
,
1835 VMR9WindowlessControl_GetMaxIdealVideoSize
,
1836 VMR9WindowlessControl_SetVideoPosition
,
1837 VMR9WindowlessControl_GetVideoPosition
,
1838 VMR9WindowlessControl_GetAspectRatioMode
,
1839 VMR9WindowlessControl_SetAspectRatioMode
,
1840 VMR9WindowlessControl_SetVideoClippingWindow
,
1841 VMR9WindowlessControl_RepaintVideo
,
1842 VMR9WindowlessControl_DisplayModeChanged
,
1843 VMR9WindowlessControl_GetCurrentImage
,
1844 VMR9WindowlessControl_SetBorderColor
,
1845 VMR9WindowlessControl_GetBorderColor
1848 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_QueryInterface(IVMRSurfaceAllocatorNotify
*iface
,
1849 REFIID riid
, LPVOID
* ppv
)
1851 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1852 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1855 static ULONG WINAPI
VMR7SurfaceAllocatorNotify_AddRef(IVMRSurfaceAllocatorNotify
*iface
)
1857 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1858 return IUnknown_AddRef(This
->renderer
.filter
.outer_unk
);
1861 static ULONG WINAPI
VMR7SurfaceAllocatorNotify_Release(IVMRSurfaceAllocatorNotify
*iface
)
1863 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1864 return IUnknown_Release(This
->renderer
.filter
.outer_unk
);
1867 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_AdviseSurfaceAllocator(IVMRSurfaceAllocatorNotify
*iface
,
1869 IVMRSurfaceAllocator
*alloc
)
1871 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1873 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1877 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_SetDDrawDevice(IVMRSurfaceAllocatorNotify
*iface
,
1878 IDirectDraw7
*device
, HMONITOR monitor
)
1880 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1882 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1886 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_ChangeDDrawDevice(IVMRSurfaceAllocatorNotify
*iface
,
1887 IDirectDraw7
*device
, HMONITOR monitor
)
1889 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1891 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1895 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_RestoreDDrawSurfaces(IVMRSurfaceAllocatorNotify
*iface
)
1897 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1899 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1903 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_NotifyEvent(IVMRSurfaceAllocatorNotify
*iface
, LONG code
,
1904 LONG_PTR param1
, LONG_PTR param2
)
1906 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1908 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1912 static HRESULT WINAPI
VMR7SurfaceAllocatorNotify_SetBorderColor(IVMRSurfaceAllocatorNotify
*iface
,
1915 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify(iface
);
1917 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
1921 static const IVMRSurfaceAllocatorNotifyVtbl VMR7_SurfaceAllocatorNotify_Vtbl
=
1923 VMR7SurfaceAllocatorNotify_QueryInterface
,
1924 VMR7SurfaceAllocatorNotify_AddRef
,
1925 VMR7SurfaceAllocatorNotify_Release
,
1926 VMR7SurfaceAllocatorNotify_AdviseSurfaceAllocator
,
1927 VMR7SurfaceAllocatorNotify_SetDDrawDevice
,
1928 VMR7SurfaceAllocatorNotify_ChangeDDrawDevice
,
1929 VMR7SurfaceAllocatorNotify_RestoreDDrawSurfaces
,
1930 VMR7SurfaceAllocatorNotify_NotifyEvent
,
1931 VMR7SurfaceAllocatorNotify_SetBorderColor
1934 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_QueryInterface(IVMRSurfaceAllocatorNotify9
*iface
, REFIID riid
, LPVOID
* ppv
)
1936 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
1937 return IUnknown_QueryInterface(This
->renderer
.filter
.outer_unk
, riid
, ppv
);
1940 static ULONG WINAPI
VMR9SurfaceAllocatorNotify_AddRef(IVMRSurfaceAllocatorNotify9
*iface
)
1942 struct quartz_vmr
*filter
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
1943 ULONG refcount
= InterlockedIncrement(&filter
->IVMRSurfaceAllocatorNotify9_refcount
);
1945 TRACE("%p increasing refcount to %u.\n", iface
, refcount
);
1950 static ULONG WINAPI
VMR9SurfaceAllocatorNotify_Release(IVMRSurfaceAllocatorNotify9
*iface
)
1952 struct quartz_vmr
*filter
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
1953 ULONG refcount
= InterlockedDecrement(&filter
->IVMRSurfaceAllocatorNotify9_refcount
);
1955 TRACE("%p decreasing refcount to %u.\n", iface
, refcount
);
1957 if (!refcount
&& !filter
->renderer
.filter
.refcount
)
1963 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_AdviseSurfaceAllocator(
1964 IVMRSurfaceAllocatorNotify9
*iface
, DWORD_PTR cookie
, IVMRSurfaceAllocator9
*allocator
)
1966 struct quartz_vmr
*filter
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
1967 IVMRImagePresenter9
*presenter
;
1969 TRACE("filter %p, cookie %#Ix, allocator %p.\n", filter
, cookie
, allocator
);
1971 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1973 filter
->cookie
= cookie
;
1975 if (filter
->renderer
.sink
.pin
.peer
)
1977 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1978 WARN("Attempt to set allocator while connected; returning VFW_E_WRONG_STATE.\n");
1979 return VFW_E_WRONG_STATE
;
1982 if (FAILED(IVMRSurfaceAllocator9_QueryInterface(allocator
, &IID_IVMRImagePresenter9
, (void **)&presenter
)))
1984 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
1985 return E_NOINTERFACE
;
1988 if (filter
->allocator
)
1990 IVMRImagePresenter9_Release(filter
->presenter
);
1991 IVMRSurfaceAllocator9_Release(filter
->allocator
);
1993 filter
->allocator
= allocator
;
1994 filter
->presenter
= presenter
;
1995 IVMRSurfaceAllocator9_AddRef(allocator
);
1997 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2001 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_SetD3DDevice(IVMRSurfaceAllocatorNotify9
*iface
,
2002 IDirect3DDevice9
*device
, HMONITOR monitor
)
2004 struct quartz_vmr
*filter
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
2006 TRACE("filter %p, device %p, monitor %p.\n", filter
, device
, monitor
);
2008 if (filter
->allocator_d3d9_dev
)
2009 IDirect3DDevice9_Release(filter
->allocator_d3d9_dev
);
2010 filter
->allocator_d3d9_dev
= device
;
2011 IDirect3DDevice9_AddRef(device
);
2016 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_ChangeD3DDevice(IVMRSurfaceAllocatorNotify9
*iface
, IDirect3DDevice9
*device
, HMONITOR monitor
)
2018 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
2020 FIXME("(%p/%p)->(...) semi-stub\n", iface
, This
);
2021 if (This
->allocator_d3d9_dev
)
2022 IDirect3DDevice9_Release(This
->allocator_d3d9_dev
);
2023 This
->allocator_d3d9_dev
= device
;
2024 IDirect3DDevice9_AddRef(This
->allocator_d3d9_dev
);
2029 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_AllocateSurfaceHelper(IVMRSurfaceAllocatorNotify9
*iface
, VMR9AllocationInfo
*allocinfo
, DWORD
*numbuffers
, IDirect3DSurface9
**surface
)
2031 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
2035 TRACE("filter %p, allocinfo %p, numbuffers %p, surface %p.\n", This
, numbuffers
, allocinfo
, surface
);
2037 if (!allocinfo
|| !numbuffers
|| !surface
)
2040 TRACE("Flags %#x, size %ux%u, format %u (%#x), pool %u, minimum buffers %u.\n",
2041 allocinfo
->dwFlags
, allocinfo
->dwWidth
, allocinfo
->dwHeight
,
2042 allocinfo
->Format
, allocinfo
->Format
, allocinfo
->Pool
, allocinfo
->MinBuffers
);
2044 if ((allocinfo
->dwFlags
& VMR9AllocFlag_TextureSurface
)
2045 && (allocinfo
->dwFlags
& VMR9AllocFlag_OffscreenSurface
))
2047 WARN("Invalid flags specified; returning E_INVALIDARG.\n");
2048 return E_INVALIDARG
;
2051 if (!allocinfo
->Format
)
2053 IDirect3DSurface9
*backbuffer
;
2054 D3DSURFACE_DESC desc
;
2056 IDirect3DDevice9_GetBackBuffer(This
->allocator_d3d9_dev
, 0, 0,
2057 D3DBACKBUFFER_TYPE_MONO
, &backbuffer
);
2058 IDirect3DSurface9_GetDesc(backbuffer
, &desc
);
2059 IDirect3DSurface9_Release(backbuffer
);
2060 allocinfo
->Format
= desc
.Format
;
2063 if (!*numbuffers
|| *numbuffers
< allocinfo
->MinBuffers
)
2065 WARN("%u surfaces requested (minimum %u); returning E_INVALIDARG.\n",
2066 *numbuffers
, allocinfo
->MinBuffers
);
2067 return E_INVALIDARG
;
2070 if (!This
->allocator_d3d9_dev
)
2072 WARN("No Direct3D device; returning VFW_E_WRONG_STATE.\n");
2073 return VFW_E_WRONG_STATE
;
2076 if (allocinfo
->dwFlags
== VMR9AllocFlag_OffscreenSurface
)
2078 for (i
= 0; i
< *numbuffers
; ++i
)
2080 hr
= IDirect3DDevice9_CreateOffscreenPlainSurface(This
->allocator_d3d9_dev
, allocinfo
->dwWidth
, allocinfo
->dwHeight
,
2081 allocinfo
->Format
, allocinfo
->Pool
, &surface
[i
], NULL
);
2086 else if (allocinfo
->dwFlags
== VMR9AllocFlag_TextureSurface
)
2088 for (i
= 0; i
< *numbuffers
; ++i
)
2090 IDirect3DTexture9
*texture
;
2092 hr
= IDirect3DDevice9_CreateTexture(This
->allocator_d3d9_dev
, allocinfo
->dwWidth
, allocinfo
->dwHeight
, 1, D3DUSAGE_DYNAMIC
,
2093 allocinfo
->Format
, allocinfo
->Pool
, &texture
, NULL
);
2096 IDirect3DTexture9_GetSurfaceLevel(texture
, 0, &surface
[i
]);
2097 IDirect3DTexture9_Release(texture
);
2100 else if (allocinfo
->dwFlags
== VMR9AllocFlag_3DRenderTarget
)
2102 for (i
= 0; i
< *numbuffers
; ++i
)
2104 if (FAILED(hr
= IDirect3DDevice9_CreateRenderTarget(This
->allocator_d3d9_dev
,
2105 allocinfo
->dwWidth
, allocinfo
->dwHeight
, allocinfo
->Format
,
2106 D3DMULTISAMPLE_NONE
, 0, FALSE
, &surface
[i
], NULL
)))
2112 FIXME("Unhandled flags %#x.\n", allocinfo
->dwFlags
);
2117 WARN("%u/%u surfaces allocated, hr %#x.\n", i
, *numbuffers
, hr
);
2119 if (i
>= allocinfo
->MinBuffers
)
2126 for ( ; i
> 0; --i
) IDirect3DSurface9_Release(surface
[i
- 1]);
2132 static HRESULT WINAPI
VMR9SurfaceAllocatorNotify_NotifyEvent(IVMRSurfaceAllocatorNotify9
*iface
, LONG code
, LONG_PTR param1
, LONG_PTR param2
)
2134 struct quartz_vmr
*This
= impl_from_IVMRSurfaceAllocatorNotify9(iface
);
2136 FIXME("(%p/%p)->(...) stub\n", iface
, This
);
2140 static const IVMRSurfaceAllocatorNotify9Vtbl VMR9_SurfaceAllocatorNotify_Vtbl
=
2142 VMR9SurfaceAllocatorNotify_QueryInterface
,
2143 VMR9SurfaceAllocatorNotify_AddRef
,
2144 VMR9SurfaceAllocatorNotify_Release
,
2145 VMR9SurfaceAllocatorNotify_AdviseSurfaceAllocator
,
2146 VMR9SurfaceAllocatorNotify_SetD3DDevice
,
2147 VMR9SurfaceAllocatorNotify_ChangeD3DDevice
,
2148 VMR9SurfaceAllocatorNotify_AllocateSurfaceHelper
,
2149 VMR9SurfaceAllocatorNotify_NotifyEvent
2152 static inline struct quartz_vmr
*impl_from_IVMRMixerControl9(IVMRMixerControl9
*iface
)
2154 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRMixerControl9_iface
);
2157 static HRESULT WINAPI
mixer_control9_QueryInterface(IVMRMixerControl9
*iface
, REFIID iid
, void **out
)
2159 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2160 return IUnknown_QueryInterface(filter
->renderer
.filter
.outer_unk
, iid
, out
);
2163 static ULONG WINAPI
mixer_control9_AddRef(IVMRMixerControl9
*iface
)
2165 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2166 return IUnknown_AddRef(filter
->renderer
.filter
.outer_unk
);
2169 static ULONG WINAPI
mixer_control9_Release(IVMRMixerControl9
*iface
)
2171 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2172 return IUnknown_Release(filter
->renderer
.filter
.outer_unk
);
2175 static HRESULT WINAPI
mixer_control9_SetAlpha(IVMRMixerControl9
*iface
, DWORD stream
, float alpha
)
2177 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2179 FIXME("filter %p, stream %u, alpha %.8e, stub!\n", filter
, stream
, alpha
);
2184 static HRESULT WINAPI
mixer_control9_GetAlpha(IVMRMixerControl9
*iface
, DWORD stream
, float *alpha
)
2186 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2188 FIXME("filter %p, stream %u, alpha %p, stub!\n", filter
, stream
, alpha
);
2193 static HRESULT WINAPI
mixer_control9_SetZOrder(IVMRMixerControl9
*iface
, DWORD stream
, DWORD z
)
2195 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2197 FIXME("filter %p, stream %u, z %u, stub!\n", filter
, stream
, z
);
2202 static HRESULT WINAPI
mixer_control9_GetZOrder(IVMRMixerControl9
*iface
, DWORD stream
, DWORD
*z
)
2204 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2206 FIXME("filter %p, stream %u, z %p, stub!\n", filter
, stream
, z
);
2211 static HRESULT WINAPI
mixer_control9_SetOutputRect(IVMRMixerControl9
*iface
,
2212 DWORD stream
, const VMR9NormalizedRect
*rect
)
2214 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2216 FIXME("filter %p, stream %u, rect %s, stub!\n", filter
, stream
, debugstr_normalized_rect(rect
));
2221 static HRESULT WINAPI
mixer_control9_GetOutputRect(IVMRMixerControl9
*iface
,
2222 DWORD stream
, VMR9NormalizedRect
*rect
)
2224 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2226 FIXME("filter %p, stream %u, rect %p, stub!\n", filter
, stream
, rect
);
2231 static HRESULT WINAPI
mixer_control9_SetBackgroundClr(IVMRMixerControl9
*iface
, COLORREF color
)
2233 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2235 FIXME("filter %p, color #%06x, stub!\n", filter
, color
);
2240 static HRESULT WINAPI
mixer_control9_GetBackgroundClr(IVMRMixerControl9
*iface
, COLORREF
*color
)
2242 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2244 FIXME("filter %p, color %p, stub!\n", filter
, color
);
2249 static HRESULT WINAPI
mixer_control9_SetMixingPrefs(IVMRMixerControl9
*iface
, DWORD flags
)
2251 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2253 FIXME("filter %p, flags %#x, stub!\n", filter
, flags
);
2255 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2256 filter
->mixing_prefs
= flags
;
2257 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2261 static HRESULT WINAPI
mixer_control9_GetMixingPrefs(IVMRMixerControl9
*iface
, DWORD
*flags
)
2263 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2265 FIXME("filter %p, flags %p, stub!\n", filter
, flags
);
2267 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2268 *flags
= filter
->mixing_prefs
;
2269 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2273 static HRESULT WINAPI
mixer_control9_SetProcAmpControl(IVMRMixerControl9
*iface
,
2274 DWORD stream
, VMR9ProcAmpControl
*settings
)
2276 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2278 FIXME("filter %p, settings %p, stub!\n", filter
, settings
);
2283 static HRESULT WINAPI
mixer_control9_GetProcAmpControl(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_GetProcAmpControlRange(IVMRMixerControl9
*iface
,
2294 DWORD stream
, VMR9ProcAmpControlRange
*settings
)
2296 struct quartz_vmr
*filter
= impl_from_IVMRMixerControl9(iface
);
2298 FIXME("filter %p, settings %p, stub!\n", filter
, settings
);
2303 static const IVMRMixerControl9Vtbl mixer_control9_vtbl
=
2305 mixer_control9_QueryInterface
,
2306 mixer_control9_AddRef
,
2307 mixer_control9_Release
,
2308 mixer_control9_SetAlpha
,
2309 mixer_control9_GetAlpha
,
2310 mixer_control9_SetZOrder
,
2311 mixer_control9_GetZOrder
,
2312 mixer_control9_SetOutputRect
,
2313 mixer_control9_GetOutputRect
,
2314 mixer_control9_SetBackgroundClr
,
2315 mixer_control9_GetBackgroundClr
,
2316 mixer_control9_SetMixingPrefs
,
2317 mixer_control9_GetMixingPrefs
,
2318 mixer_control9_SetProcAmpControl
,
2319 mixer_control9_GetProcAmpControl
,
2320 mixer_control9_GetProcAmpControlRange
,
2323 static inline struct quartz_vmr
*impl_from_IVMRMixerBitmap9(IVMRMixerBitmap9
*iface
)
2325 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRMixerBitmap9_iface
);
2328 static HRESULT WINAPI
mixer_bitmap9_QueryInterface(IVMRMixerBitmap9
*iface
, REFIID iid
, void **out
)
2330 struct quartz_vmr
*filter
= impl_from_IVMRMixerBitmap9(iface
);
2331 return IUnknown_QueryInterface(filter
->renderer
.filter
.outer_unk
, iid
, out
);
2334 static ULONG WINAPI
mixer_bitmap9_AddRef(IVMRMixerBitmap9
*iface
)
2336 struct quartz_vmr
*filter
= impl_from_IVMRMixerBitmap9(iface
);
2337 return IUnknown_AddRef(filter
->renderer
.filter
.outer_unk
);
2340 static ULONG WINAPI
mixer_bitmap9_Release(IVMRMixerBitmap9
*iface
)
2342 struct quartz_vmr
*filter
= impl_from_IVMRMixerBitmap9(iface
);
2343 return IUnknown_Release(filter
->renderer
.filter
.outer_unk
);
2346 static HRESULT WINAPI
mixer_bitmap9_SetAlphaBitmap(IVMRMixerBitmap9
*iface
,
2347 const VMR9AlphaBitmap
*bitmap
)
2349 FIXME("iface %p, bitmap %p, stub!\n", iface
, bitmap
);
2350 TRACE("dwFlags %#x, hdc %p, pDDS %p, rSrc %s, rDest %s, fAlpha %.8e, clrSrcKey #%06x, dwFilterMode %#x.\n",
2351 bitmap
->dwFlags
, bitmap
->hdc
, bitmap
->pDDS
, wine_dbgstr_rect(&bitmap
->rSrc
),
2352 debugstr_normalized_rect(&bitmap
->rDest
), bitmap
->fAlpha
, bitmap
->clrSrcKey
, bitmap
->dwFilterMode
);
2356 static HRESULT WINAPI
mixer_bitmap9_UpdateAlphaBitmapParameters(IVMRMixerBitmap9
*iface
,
2357 const VMR9AlphaBitmap
*bitmap
)
2359 FIXME("iface %p, bitmap %p, stub!\n", iface
, bitmap
);
2363 static HRESULT WINAPI
mixer_bitmap9_GetAlphaBitmapParameters(IVMRMixerBitmap9
*iface
,
2364 VMR9AlphaBitmap
*bitmap
)
2366 FIXME("iface %p, bitmap %p, stub!\n", iface
, bitmap
);
2370 static const IVMRMixerBitmap9Vtbl mixer_bitmap9_vtbl
=
2372 mixer_bitmap9_QueryInterface
,
2373 mixer_bitmap9_AddRef
,
2374 mixer_bitmap9_Release
,
2375 mixer_bitmap9_SetAlphaBitmap
,
2376 mixer_bitmap9_UpdateAlphaBitmapParameters
,
2377 mixer_bitmap9_GetAlphaBitmapParameters
,
2380 static inline struct quartz_vmr
*impl_from_IVMRAspectRatioControl9(IVMRAspectRatioControl9
*iface
)
2382 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IVMRAspectRatioControl9_iface
);
2385 static HRESULT WINAPI
aspect_ratio_control9_QueryInterface(IVMRAspectRatioControl9
*iface
, REFIID iid
, void **out
)
2387 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2388 return IUnknown_QueryInterface(filter
->renderer
.filter
.outer_unk
, iid
, out
);
2391 static ULONG WINAPI
aspect_ratio_control9_AddRef(IVMRAspectRatioControl9
*iface
)
2393 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2394 return IUnknown_AddRef(filter
->renderer
.filter
.outer_unk
);
2397 static ULONG WINAPI
aspect_ratio_control9_Release(IVMRAspectRatioControl9
*iface
)
2399 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2400 return IUnknown_Release(filter
->renderer
.filter
.outer_unk
);
2403 static HRESULT WINAPI
aspect_ratio_control9_GetAspectRatioMode(IVMRAspectRatioControl9
*iface
, DWORD
*mode
)
2405 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2407 TRACE("filter %p, mode %p.\n", filter
, mode
);
2409 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2410 *mode
= filter
->aspect_mode
;
2411 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2415 static HRESULT WINAPI
aspect_ratio_control9_SetAspectRatioMode(IVMRAspectRatioControl9
*iface
, DWORD mode
)
2417 struct quartz_vmr
*filter
= impl_from_IVMRAspectRatioControl9(iface
);
2419 TRACE("filter %p, mode %u.\n", filter
, mode
);
2421 EnterCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2422 filter
->aspect_mode
= mode
;
2423 LeaveCriticalSection(&filter
->renderer
.filter
.filter_cs
);
2427 static const IVMRAspectRatioControl9Vtbl aspect_ratio_control9_vtbl
=
2429 aspect_ratio_control9_QueryInterface
,
2430 aspect_ratio_control9_AddRef
,
2431 aspect_ratio_control9_Release
,
2432 aspect_ratio_control9_GetAspectRatioMode
,
2433 aspect_ratio_control9_SetAspectRatioMode
,
2436 static inline struct quartz_vmr
*impl_from_IOverlay(IOverlay
*iface
)
2438 return CONTAINING_RECORD(iface
, struct quartz_vmr
, IOverlay_iface
);
2441 static HRESULT WINAPI
overlay_QueryInterface(IOverlay
*iface
, REFIID iid
, void **out
)
2443 struct quartz_vmr
*filter
= impl_from_IOverlay(iface
);
2444 return IPin_QueryInterface(&filter
->renderer
.sink
.pin
.IPin_iface
, iid
, out
);
2447 static ULONG WINAPI
overlay_AddRef(IOverlay
*iface
)
2449 struct quartz_vmr
*filter
= impl_from_IOverlay(iface
);
2450 return IPin_AddRef(&filter
->renderer
.sink
.pin
.IPin_iface
);
2453 static ULONG WINAPI
overlay_Release(IOverlay
*iface
)
2455 struct quartz_vmr
*filter
= impl_from_IOverlay(iface
);
2456 return IPin_Release(&filter
->renderer
.sink
.pin
.IPin_iface
);
2459 static HRESULT WINAPI
overlay_GetPalette(IOverlay
*iface
, DWORD
*count
, PALETTEENTRY
**palette
)
2461 FIXME("iface %p, count %p, palette %p, stub!\n", iface
, count
, palette
);
2465 static HRESULT WINAPI
overlay_SetPalette(IOverlay
*iface
, DWORD count
, PALETTEENTRY
*palette
)
2467 FIXME("iface %p, count %u, palette %p, stub!\n", iface
, count
, palette
);
2471 static HRESULT WINAPI
overlay_GetDefaultColorKey(IOverlay
*iface
, COLORKEY
*key
)
2473 FIXME("iface %p, key %p, stub!\n", iface
, key
);
2477 static HRESULT WINAPI
overlay_GetColorKey(IOverlay
*iface
, COLORKEY
*key
)
2479 FIXME("iface %p, key %p, stub!\n", iface
, key
);
2483 static HRESULT WINAPI
overlay_SetColorKey(IOverlay
*iface
, COLORKEY
*key
)
2485 FIXME("iface %p, key %p, stub!\n", iface
, key
);
2489 static HRESULT WINAPI
overlay_GetWindowHandle(IOverlay
*iface
, HWND
*window
)
2491 struct quartz_vmr
*filter
= impl_from_IOverlay(iface
);
2493 TRACE("filter %p, window %p.\n", filter
, window
);
2495 if (!filter
->window
.hwnd
)
2496 return VFW_E_WRONG_STATE
;
2498 *window
= filter
->window
.hwnd
;
2502 static HRESULT WINAPI
overlay_GetClipList(IOverlay
*iface
, RECT
*source
, RECT
*dest
, RGNDATA
**region
)
2504 FIXME("iface %p, source %p, dest %p, region %p, stub!\n", iface
, source
, dest
, region
);
2508 static HRESULT WINAPI
overlay_GetVideoPosition(IOverlay
*iface
, RECT
*source
, RECT
*dest
)
2510 FIXME("iface %p, source %p, dest %p, stub!\n", iface
, source
, dest
);
2514 static HRESULT WINAPI
overlay_Advise(IOverlay
*iface
, IOverlayNotify
*sink
, DWORD flags
)
2516 FIXME("iface %p, sink %p, flags %#x, stub!\n", iface
, sink
, flags
);
2520 static HRESULT WINAPI
overlay_Unadvise(IOverlay
*iface
)
2522 FIXME("iface %p, stub!\n", iface
);
2526 static const IOverlayVtbl overlay_vtbl
=
2528 overlay_QueryInterface
,
2533 overlay_GetDefaultColorKey
,
2534 overlay_GetColorKey
,
2535 overlay_SetColorKey
,
2536 overlay_GetWindowHandle
,
2537 overlay_GetClipList
,
2538 overlay_GetVideoPosition
,
2543 static HRESULT
vmr_create(IUnknown
*outer
, IUnknown
**out
, const CLSID
*clsid
)
2545 struct quartz_vmr
*object
;
2548 if (!(object
= calloc(1, sizeof(*object
))))
2549 return E_OUTOFMEMORY
;
2551 object
->hD3d9
= LoadLibraryA("d3d9.dll");
2554 WARN("Could not load d3d9.dll\n");
2556 return VFW_E_DDRAW_CAPS_NOT_SUITABLE
;
2559 strmbase_renderer_init(&object
->renderer
, outer
, clsid
, L
"VMR Input0", &renderer_ops
);
2560 object
->IAMCertifiedOutputProtection_iface
.lpVtbl
= &IAMCertifiedOutputProtection_Vtbl
;
2561 object
->IAMFilterMiscFlags_iface
.lpVtbl
= &IAMFilterMiscFlags_Vtbl
;
2562 object
->IVMRAspectRatioControl9_iface
.lpVtbl
= &aspect_ratio_control9_vtbl
;
2563 object
->IVMRFilterConfig_iface
.lpVtbl
= &VMR7_FilterConfig_Vtbl
;
2564 object
->IVMRFilterConfig9_iface
.lpVtbl
= &VMR9_FilterConfig_Vtbl
;
2565 object
->IVMRMixerBitmap9_iface
.lpVtbl
= &mixer_bitmap9_vtbl
;
2566 object
->IVMRMixerControl9_iface
.lpVtbl
= &mixer_control9_vtbl
;
2567 object
->IVMRMonitorConfig_iface
.lpVtbl
= &VMR7_MonitorConfig_Vtbl
;
2568 object
->IVMRMonitorConfig9_iface
.lpVtbl
= &VMR9_MonitorConfig_Vtbl
;
2569 object
->IVMRSurfaceAllocatorNotify_iface
.lpVtbl
= &VMR7_SurfaceAllocatorNotify_Vtbl
;
2570 object
->IVMRSurfaceAllocatorNotify9_iface
.lpVtbl
= &VMR9_SurfaceAllocatorNotify_Vtbl
;
2571 object
->IVMRWindowlessControl_iface
.lpVtbl
= &VMR7_WindowlessControl_Vtbl
;
2572 object
->IVMRWindowlessControl9_iface
.lpVtbl
= &VMR9_WindowlessControl_Vtbl
;
2573 object
->IOverlay_iface
.lpVtbl
= &overlay_vtbl
;
2575 video_window_init(&object
->window
, &IVideoWindow_VTable
,
2576 &object
->renderer
.filter
, &object
->renderer
.sink
.pin
, &window_ops
);
2578 if (FAILED(hr
= video_window_create_window(&object
->window
)))
2580 video_window_cleanup(&object
->window
);
2581 strmbase_renderer_cleanup(&object
->renderer
);
2582 FreeLibrary(object
->hD3d9
);
2587 object
->mixing_prefs
= MixerPref9_NoDecimation
| MixerPref9_ARAdjustXorY
2588 | MixerPref9_BiLinearFiltering
| MixerPref9_RenderTargetRGB
;
2590 TRACE("Created VMR %p.\n", object
);
2591 *out
= &object
->renderer
.filter
.IUnknown_inner
;
2595 HRESULT
vmr7_create(IUnknown
*outer
, IUnknown
**out
)
2597 return vmr_create(outer
, out
, &CLSID_VideoMixingRenderer
);
2600 HRESULT
vmr9_create(IUnknown
*outer
, IUnknown
**out
)
2602 return vmr_create(outer
, out
, &CLSID_VideoMixingRenderer9
);
2606 static HRESULT WINAPI
VMR9_ImagePresenter_QueryInterface(IVMRImagePresenter9
*iface
, REFIID riid
, void **ppv
)
2608 struct default_presenter
*This
= impl_from_IVMRImagePresenter9(iface
);
2610 TRACE("(%p/%p)->(%s, %p)\n", This
, iface
, qzdebugstr_guid(riid
), ppv
);
2614 if (IsEqualIID(riid
, &IID_IUnknown
) || IsEqualIID(riid
, &IID_IVMRImagePresenter9
))
2615 *ppv
= &This
->IVMRImagePresenter9_iface
;
2616 else if (IsEqualIID(riid
, &IID_IVMRSurfaceAllocator9
))
2617 *ppv
= &This
->IVMRSurfaceAllocator9_iface
;
2621 IUnknown_AddRef((IUnknown
*)(*ppv
));
2625 FIXME("No interface for %s\n", debugstr_guid(riid
));
2627 return E_NOINTERFACE
;
2630 static ULONG WINAPI
VMR9_ImagePresenter_AddRef(IVMRImagePresenter9
*iface
)
2632 struct default_presenter
*This
= impl_from_IVMRImagePresenter9(iface
);
2633 ULONG refCount
= InterlockedIncrement(&This
->refCount
);
2635 TRACE("(%p)->() AddRef from %d\n", iface
, refCount
- 1);
2640 static ULONG WINAPI
VMR9_ImagePresenter_Release(IVMRImagePresenter9
*iface
)
2642 struct default_presenter
*This
= impl_from_IVMRImagePresenter9(iface
);
2643 ULONG refCount
= InterlockedDecrement(&This
->refCount
);
2645 TRACE("(%p)->() Release from %d\n", iface
, refCount
+ 1);
2650 TRACE("Destroying\n");
2651 IDirect3D9_Release(This
->d3d9_ptr
);
2653 TRACE("Number of surfaces: %u\n", This
->num_surfaces
);
2654 for (i
= 0; i
< This
->num_surfaces
; ++i
)
2656 IDirect3DSurface9
*surface
= This
->d3d9_surfaces
[i
];
2657 TRACE("Releasing surface %p\n", surface
);
2659 IDirect3DSurface9_Release(surface
);
2663 IDirect3DDevice9_Release(This
->d3d9_dev
);
2664 free(This
->d3d9_surfaces
);
2665 This
->d3d9_surfaces
= NULL
;
2666 This
->num_surfaces
= 0;
2673 static HRESULT WINAPI
VMR9_ImagePresenter_StartPresenting(IVMRImagePresenter9
*iface
, DWORD_PTR cookie
)
2675 struct default_presenter
*presenter
= impl_from_IVMRImagePresenter9(iface
);
2677 TRACE("presenter %p, cookie %#Ix.\n", presenter
, cookie
);
2682 static HRESULT WINAPI
VMR9_ImagePresenter_StopPresenting(IVMRImagePresenter9
*iface
, DWORD_PTR cookie
)
2684 struct default_presenter
*presenter
= impl_from_IVMRImagePresenter9(iface
);
2686 TRACE("presenter %p, cookie %#Ix.\n", presenter
, cookie
);
2691 static HRESULT WINAPI
VMR9_ImagePresenter_PresentImage(IVMRImagePresenter9
*iface
,
2692 DWORD_PTR cookie
, VMR9PresentationInfo
*info
)
2694 struct default_presenter
*presenter
= impl_from_IVMRImagePresenter9(iface
);
2695 const struct quartz_vmr
*filter
= presenter
->pVMR9
;
2696 IDirect3DDevice9
*device
= presenter
->d3d9_dev
;
2697 const RECT src
= filter
->window
.src
;
2698 IDirect3DSurface9
*backbuffer
;
2699 RECT dst
= filter
->window
.dst
;
2702 TRACE("presenter %p, cookie %#Ix, info %p.\n", presenter
, cookie
, info
);
2704 /* This might happen if we don't have active focus (eg on a different virtual desktop) */
2708 if (FAILED(hr
= IDirect3DDevice9_Clear(device
, 0, NULL
, D3DCLEAR_TARGET
,
2709 D3DCOLOR_XRGB(0, 0, 0), 1.0f
, 0)))
2710 ERR("Failed to clear, hr %#x.\n", hr
);
2712 if (FAILED(hr
= IDirect3DDevice9_BeginScene(device
)))
2713 ERR("Failed to begin scene, hr %#x.\n", hr
);
2715 if (FAILED(hr
= IDirect3DDevice9_GetBackBuffer(device
, 0, 0, D3DBACKBUFFER_TYPE_MONO
, &backbuffer
)))
2717 ERR("Failed to get backbuffer, hr %#x.\n", hr
);
2721 if (FAILED(hr
= IDirect3DDevice9_StretchRect(device
, info
->lpSurf
, NULL
, backbuffer
, NULL
, D3DTEXF_POINT
)))
2722 ERR("Failed to blit image, hr %#x.\n", hr
);
2723 IDirect3DSurface9_Release(backbuffer
);
2725 if (FAILED(hr
= IDirect3DDevice9_EndScene(device
)))
2726 ERR("Failed to end scene, hr %#x.\n", hr
);
2728 if (filter
->aspect_mode
== VMR9ARMode_LetterBox
)
2730 unsigned int src_width
= src
.right
- src
.left
, src_height
= src
.bottom
- src
.top
;
2731 unsigned int dst_width
= dst
.right
- dst
.left
, dst_height
= dst
.bottom
- dst
.top
;
2733 if (src_width
* dst_height
> dst_width
* src_height
)
2735 /* src is "wider" than dst. */
2736 unsigned int dst_center
= (dst
.top
+ dst
.bottom
) / 2;
2737 unsigned int scaled_height
= src_height
* dst_width
/ src_width
;
2739 dst
.top
= dst_center
- scaled_height
/ 2;
2740 dst
.bottom
= dst
.top
+ scaled_height
;
2742 else if (src_width
* dst_height
< dst_width
* src_height
)
2744 /* src is "taller" than dst. */
2745 unsigned int dst_center
= (dst
.left
+ dst
.right
) / 2;
2746 unsigned int scaled_width
= src_width
* dst_height
/ src_height
;
2748 dst
.left
= dst_center
- scaled_width
/ 2;
2749 dst
.right
= dst
.left
+ scaled_width
;
2753 if (FAILED(hr
= IDirect3DDevice9_Present(device
, &src
, &dst
, NULL
, NULL
)))
2754 ERR("Failed to present, hr %#x.\n", hr
);
2759 static const IVMRImagePresenter9Vtbl VMR9_ImagePresenter
=
2761 VMR9_ImagePresenter_QueryInterface
,
2762 VMR9_ImagePresenter_AddRef
,
2763 VMR9_ImagePresenter_Release
,
2764 VMR9_ImagePresenter_StartPresenting
,
2765 VMR9_ImagePresenter_StopPresenting
,
2766 VMR9_ImagePresenter_PresentImage
2769 static HRESULT WINAPI
VMR9_SurfaceAllocator_QueryInterface(IVMRSurfaceAllocator9
*iface
, REFIID iid
, void **out
)
2771 struct default_presenter
*presenter
= impl_from_IVMRSurfaceAllocator9(iface
);
2772 return IVMRImagePresenter9_QueryInterface(&presenter
->IVMRImagePresenter9_iface
, iid
, out
);
2775 static ULONG WINAPI
VMR9_SurfaceAllocator_AddRef(IVMRSurfaceAllocator9
*iface
)
2777 struct default_presenter
*presenter
= impl_from_IVMRSurfaceAllocator9(iface
);
2778 return IVMRImagePresenter9_AddRef(&presenter
->IVMRImagePresenter9_iface
);
2781 static ULONG WINAPI
VMR9_SurfaceAllocator_Release(IVMRSurfaceAllocator9
*iface
)
2783 struct default_presenter
*presenter
= impl_from_IVMRSurfaceAllocator9(iface
);
2784 return IVMRImagePresenter9_Release(&presenter
->IVMRImagePresenter9_iface
);
2787 static HRESULT
VMR9_SurfaceAllocator_SetAllocationSettings(struct default_presenter
*This
, VMR9AllocationInfo
*allocinfo
)
2793 if (!(allocinfo
->dwFlags
& VMR9AllocFlag_TextureSurface
))
2794 /* Only needed for texture surfaces */
2797 hr
= IDirect3DDevice9_GetDeviceCaps(This
->d3d9_dev
, &caps
);
2801 if (!(caps
.TextureCaps
& D3DPTEXTURECAPS_POW2
) || (caps
.TextureCaps
& D3DPTEXTURECAPS_SQUAREONLY
))
2803 width
= allocinfo
->dwWidth
;
2804 height
= allocinfo
->dwHeight
;
2809 while (width
< allocinfo
->dwWidth
)
2812 while (height
< allocinfo
->dwHeight
)
2814 FIXME("NPOW2 support missing, not using proper surfaces!\n");
2817 if (caps
.TextureCaps
& D3DPTEXTURECAPS_SQUAREONLY
)
2823 FIXME("Square texture support required..\n");
2826 allocinfo
->dwHeight
= height
;
2827 allocinfo
->dwWidth
= width
;
2832 static UINT
d3d9_adapter_from_hwnd(IDirect3D9
*d3d9
, HWND hwnd
, HMONITOR
*mon_out
)
2837 mon
= MonitorFromWindow(hwnd
, MONITOR_DEFAULTTONULL
);
2842 for (d3d9_adapter
= 0; d3d9_adapter
< IDirect3D9_GetAdapterCount(d3d9
); ++d3d9_adapter
)
2844 if (mon
== IDirect3D9_GetAdapterMonitor(d3d9
, d3d9_adapter
))
2847 if (d3d9_adapter
>= IDirect3D9_GetAdapterCount(d3d9
))
2852 return d3d9_adapter
;
2855 static HRESULT WINAPI
VMR9_SurfaceAllocator_InitializeDevice(IVMRSurfaceAllocator9
*iface
,
2856 DWORD_PTR cookie
, VMR9AllocationInfo
*info
, DWORD
*numbuffers
)
2858 struct default_presenter
*This
= impl_from_IVMRSurfaceAllocator9(iface
);
2859 D3DPRESENT_PARAMETERS d3dpp
;
2860 IDirect3DDevice9
*device
;
2866 TRACE("presenter %p, cookie %#Ix, info %p, numbuffers %p.\n", This
, cookie
, info
, numbuffers
);
2870 if (This
->pVMR9
->mode
== VMR9Mode_Windowed
)
2871 window
= This
->pVMR9
->window
.hwnd
;
2873 window
= This
->pVMR9
->clipping_window
;
2875 /* Obtain a monitor and d3d9 device */
2876 d3d9_adapter
= d3d9_adapter_from_hwnd(This
->d3d9_ptr
, window
, &This
->hMon
);
2878 /* Now try to create the d3d9 device */
2879 ZeroMemory(&d3dpp
, sizeof(d3dpp
));
2880 d3dpp
.Windowed
= TRUE
;
2881 d3dpp
.hDeviceWindow
= window
;
2882 d3dpp
.SwapEffect
= D3DSWAPEFFECT_COPY
;
2883 d3dpp
.BackBufferWidth
= info
->dwWidth
;
2884 d3dpp
.BackBufferHeight
= info
->dwHeight
;
2886 hr
= IDirect3D9_CreateDevice(This
->d3d9_ptr
, d3d9_adapter
, D3DDEVTYPE_HAL
,
2887 NULL
, D3DCREATE_MIXED_VERTEXPROCESSING
, &d3dpp
, &device
);
2890 ERR("Could not create device: %08x\n", hr
);
2894 IDirect3DDevice9_GetDeviceCaps(device
, &caps
);
2895 if (!(caps
.DevCaps2
& D3DDEVCAPS2_CAN_STRETCHRECT_FROM_TEXTURES
))
2897 WARN("Device does not support blitting from textures.\n");
2898 IDirect3DDevice9_Release(device
);
2899 return VFW_E_DDRAW_CAPS_NOT_SUITABLE
;
2902 This
->d3d9_dev
= device
;
2903 IVMRSurfaceAllocatorNotify9_SetD3DDevice(This
->SurfaceAllocatorNotify
, This
->d3d9_dev
, This
->hMon
);
2905 if (!(This
->d3d9_surfaces
= calloc(*numbuffers
, sizeof(IDirect3DSurface9
*))))
2906 return E_OUTOFMEMORY
;
2908 hr
= VMR9_SurfaceAllocator_SetAllocationSettings(This
, info
);
2910 ERR("Setting allocation settings failed: %08x\n", hr
);
2914 hr
= IVMRSurfaceAllocatorNotify9_AllocateSurfaceHelper(This
->SurfaceAllocatorNotify
, info
, numbuffers
, This
->d3d9_surfaces
);
2916 ERR("Allocating surfaces failed: %08x\n", hr
);
2921 IVMRSurfaceAllocator9_TerminateDevice(This
->pVMR9
->allocator
, This
->pVMR9
->cookie
);
2925 This
->num_surfaces
= *numbuffers
;
2930 static HRESULT WINAPI
VMR9_SurfaceAllocator_TerminateDevice(IVMRSurfaceAllocator9
*iface
, DWORD_PTR cookie
)
2932 TRACE("iface %p, cookie %#lx.\n", iface
, cookie
);
2937 static HRESULT WINAPI
VMR9_SurfaceAllocator_GetSurface(IVMRSurfaceAllocator9
*iface
,
2938 DWORD_PTR cookie
, DWORD surfaceindex
, DWORD flags
, IDirect3DSurface9
**surface
)
2940 struct default_presenter
*This
= impl_from_IVMRSurfaceAllocator9(iface
);
2942 /* Update everything first, this is needed because the surface might be destroyed in the reset */
2943 if (!This
->d3d9_dev
)
2945 TRACE("Device has left me!\n");
2949 if (surfaceindex
>= This
->num_surfaces
)
2951 ERR("surfaceindex is greater than num_surfaces\n");
2954 *surface
= This
->d3d9_surfaces
[surfaceindex
];
2955 IDirect3DSurface9_AddRef(*surface
);
2960 static HRESULT WINAPI
VMR9_SurfaceAllocator_AdviseNotify(IVMRSurfaceAllocator9
*iface
,
2961 IVMRSurfaceAllocatorNotify9
*notify
)
2963 struct default_presenter
*presenter
= impl_from_IVMRSurfaceAllocator9(iface
);
2965 TRACE("presenter %p, notify %p.\n", presenter
, notify
);
2967 /* No AddRef taken here or the base VMR9 filter would never be destroyed */
2968 presenter
->SurfaceAllocatorNotify
= notify
;
2972 static const IVMRSurfaceAllocator9Vtbl VMR9_SurfaceAllocator
=
2974 VMR9_SurfaceAllocator_QueryInterface
,
2975 VMR9_SurfaceAllocator_AddRef
,
2976 VMR9_SurfaceAllocator_Release
,
2977 VMR9_SurfaceAllocator_InitializeDevice
,
2978 VMR9_SurfaceAllocator_TerminateDevice
,
2979 VMR9_SurfaceAllocator_GetSurface
,
2980 VMR9_SurfaceAllocator_AdviseNotify
,
2983 static IDirect3D9
*init_d3d9(HMODULE d3d9_handle
)
2985 IDirect3D9
* (__stdcall
* d3d9_create
)(UINT SDKVersion
);
2987 d3d9_create
= (void *)GetProcAddress(d3d9_handle
, "Direct3DCreate9");
2988 if (!d3d9_create
) return NULL
;
2990 return d3d9_create(D3D_SDK_VERSION
);
2993 static HRESULT
VMR9DefaultAllocatorPresenterImpl_create(struct quartz_vmr
*parent
, LPVOID
* ppv
)
2995 struct default_presenter
*object
;
2999 if (!(object
= calloc(1, sizeof(*object
))))
3000 return E_OUTOFMEMORY
;
3002 object
->d3d9_ptr
= init_d3d9(parent
->hD3d9
);
3003 if (!object
->d3d9_ptr
)
3005 WARN("Could not initialize d3d9.dll\n");
3007 return VFW_E_DDRAW_CAPS_NOT_SUITABLE
;
3013 D3DDISPLAYMODE mode
;
3015 hr
= IDirect3D9_EnumAdapterModes(object
->d3d9_ptr
, i
++, D3DFMT_X8R8G8B8
, 0, &mode
);
3016 if (hr
== D3DERR_INVALIDCALL
) break; /* out of adapters */
3017 } while (FAILED(hr
));
3019 ERR("HR: %08x\n", hr
);
3020 if (hr
== D3DERR_NOTAVAILABLE
)
3022 ERR("Format not supported\n");
3023 IDirect3D9_Release(object
->d3d9_ptr
);
3025 return VFW_E_DDRAW_CAPS_NOT_SUITABLE
;
3028 object
->IVMRImagePresenter9_iface
.lpVtbl
= &VMR9_ImagePresenter
;
3029 object
->IVMRSurfaceAllocator9_iface
.lpVtbl
= &VMR9_SurfaceAllocator
;
3031 object
->refCount
= 1;
3032 object
->pVMR9
= parent
;
3034 TRACE("Created default presenter %p.\n", object
);
3035 *ppv
= &object
->IVMRImagePresenter9_iface
;