quartz: Merge the BaseWindow structure into video_window.

Signed-off-by: Zebediah Figura <z.figura12@gmail.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Zebediah Figura 2020-04-02 23:20:48 -05:00 committed by Alexandre Julliard
parent f9653494a9
commit e3160986d0
4 changed files with 240 additions and 310 deletions

View File

@ -87,50 +87,33 @@ extern void video_unregister_windowclass(void) DECLSPEC_HIDDEN;
BOOL get_media_type(const WCHAR *filename, GUID *majortype, GUID *subtype, GUID *source_clsid) DECLSPEC_HIDDEN; BOOL get_media_type(const WCHAR *filename, GUID *majortype, GUID *subtype, GUID *source_clsid) DECLSPEC_HIDDEN;
typedef struct tagBaseWindow
{
HWND hWnd;
LONG Width;
LONG Height;
const struct video_window_ops *pFuncsTable;
} BaseWindow;
typedef RECT (WINAPI *BaseWindow_GetDefaultRect)(BaseWindow *This);
typedef BOOL (WINAPI *BaseWindow_OnSize)(BaseWindow *This, LONG Height, LONG Width);
struct video_window_ops
{
/* Required */
BaseWindow_GetDefaultRect pfnGetDefaultRect;
/* Optional, WinProc Related */
BaseWindow_OnSize pfnOnSize;
};
HRESULT WINAPI BaseWindow_Init(BaseWindow *pBaseWindow, const struct video_window_ops *pFuncsTable) DECLSPEC_HIDDEN;
HRESULT WINAPI BaseWindow_Destroy(BaseWindow *pBaseWindow) DECLSPEC_HIDDEN;
HRESULT WINAPI BaseWindowImpl_PrepareWindow(BaseWindow *This) DECLSPEC_HIDDEN;
HRESULT WINAPI BaseWindowImpl_DoneWithWindow(BaseWindow *This) DECLSPEC_HIDDEN;
struct video_window struct video_window
{ {
BaseWindow baseWindow;
IVideoWindow IVideoWindow_iface; IVideoWindow IVideoWindow_iface;
HWND hwnd;
LONG width, height;
BOOL AutoShow; BOOL AutoShow;
HWND hwndDrain; HWND hwndDrain;
HWND hwndOwner; HWND hwndOwner;
struct strmbase_filter *pFilter; struct strmbase_filter *pFilter;
struct strmbase_pin *pPin; struct strmbase_pin *pPin;
const struct video_window_ops *ops;
}; };
struct video_window_ops
{
/* Required */
RECT (*get_default_rect)(struct video_window *window);
/* Optional, WinProc Related */
BOOL (*resize)(struct video_window *window, LONG height, LONG width);
};
void video_window_cleanup(struct video_window *window) DECLSPEC_HIDDEN;
HRESULT video_window_create_window(struct video_window *window) DECLSPEC_HIDDEN;
HRESULT video_window_init(struct video_window *window, const IVideoWindowVtbl *vtbl, HRESULT video_window_init(struct video_window *window, const IVideoWindowVtbl *vtbl,
struct strmbase_filter *filter, struct strmbase_pin *pin, const struct video_window_ops *ops) DECLSPEC_HIDDEN; struct strmbase_filter *filter, struct strmbase_pin *pin, const struct video_window_ops *ops) DECLSPEC_HIDDEN;
void video_window_unregister_class(void) DECLSPEC_HIDDEN; void video_window_unregister_class(void) DECLSPEC_HIDDEN;
HRESULT WINAPI BaseControlWindow_Destroy(struct video_window *window) DECLSPEC_HIDDEN;
BOOL WINAPI BaseControlWindowImpl_PossiblyEatMessage(BaseWindow *This, UINT uMsg, WPARAM wParam, LPARAM lParam) DECLSPEC_HIDDEN;
HRESULT WINAPI BaseControlWindowImpl_QueryInterface(IVideoWindow *iface, REFIID iid, void **out) DECLSPEC_HIDDEN; HRESULT WINAPI BaseControlWindowImpl_QueryInterface(IVideoWindow *iface, REFIID iid, void **out) DECLSPEC_HIDDEN;
ULONG WINAPI BaseControlWindowImpl_AddRef(IVideoWindow *iface) DECLSPEC_HIDDEN; ULONG WINAPI BaseControlWindowImpl_AddRef(IVideoWindow *iface) DECLSPEC_HIDDEN;

View File

@ -59,9 +59,9 @@ struct video_renderer
IMediaSample *current_sample; IMediaSample *current_sample;
}; };
static inline struct video_renderer *impl_from_BaseWindow(BaseWindow *iface) static inline struct video_renderer *impl_from_video_window(struct video_window *iface)
{ {
return CONTAINING_RECORD(iface, struct video_renderer, baseControlWindow.baseWindow); return CONTAINING_RECORD(iface, struct video_renderer, baseControlWindow);
} }
static inline struct video_renderer *impl_from_strmbase_renderer(struct strmbase_renderer *iface) static inline struct video_renderer *impl_from_strmbase_renderer(struct strmbase_renderer *iface)
@ -83,8 +83,8 @@ static void VideoRenderer_AutoShowWindow(struct video_renderer *This)
{ {
if (!This->init && (!This->WindowPos.right || !This->WindowPos.top)) if (!This->init && (!This->WindowPos.right || !This->WindowPos.top))
{ {
DWORD style = GetWindowLongW(This->baseControlWindow.baseWindow.hWnd, GWL_STYLE); DWORD style = GetWindowLongW(This->baseControlWindow.hwnd, GWL_STYLE);
DWORD style_ex = GetWindowLongW(This->baseControlWindow.baseWindow.hWnd, GWL_EXSTYLE); DWORD style_ex = GetWindowLongW(This->baseControlWindow.hwnd, GWL_EXSTYLE);
if (!This->WindowPos.right) if (!This->WindowPos.right)
{ {
@ -116,20 +116,20 @@ static void VideoRenderer_AutoShowWindow(struct video_renderer *This)
AdjustWindowRectEx(&This->WindowPos, style, FALSE, style_ex); AdjustWindowRectEx(&This->WindowPos, style, FALSE, style_ex);
TRACE("WindowPos: %s\n", wine_dbgstr_rect(&This->WindowPos)); TRACE("WindowPos: %s\n", wine_dbgstr_rect(&This->WindowPos));
SetWindowPos(This->baseControlWindow.baseWindow.hWnd, NULL, SetWindowPos(This->baseControlWindow.hwnd, NULL,
This->WindowPos.left, This->WindowPos.left,
This->WindowPos.top, This->WindowPos.top,
This->WindowPos.right - This->WindowPos.left, This->WindowPos.right - This->WindowPos.left,
This->WindowPos.bottom - This->WindowPos.top, This->WindowPos.bottom - This->WindowPos.top,
SWP_NOZORDER|SWP_NOMOVE|SWP_DEFERERASE); SWP_NOZORDER|SWP_NOMOVE|SWP_DEFERERASE);
GetClientRect(This->baseControlWindow.baseWindow.hWnd, &This->DestRect); GetClientRect(This->baseControlWindow.hwnd, &This->DestRect);
} }
else if (!This->init) else if (!This->init)
This->DestRect = This->WindowPos; This->DestRect = This->WindowPos;
This->init = TRUE; This->init = TRUE;
if (This->baseControlWindow.AutoShow) if (This->baseControlWindow.AutoShow)
ShowWindow(This->baseControlWindow.baseWindow.hWnd, SW_SHOW); ShowWindow(This->baseControlWindow.hwnd, SW_SHOW);
} }
static HRESULT WINAPI VideoRenderer_ShouldDrawSampleNow(struct strmbase_renderer *filter, static HRESULT WINAPI VideoRenderer_ShouldDrawSampleNow(struct strmbase_renderer *filter,
@ -164,7 +164,7 @@ static HRESULT WINAPI VideoRenderer_DoRenderSample(struct strmbase_renderer *ifa
else else
bih = &((VIDEOINFOHEADER2 *)mt->pbFormat)->bmiHeader; bih = &((VIDEOINFOHEADER2 *)mt->pbFormat)->bmiHeader;
dc = GetDC(filter->baseControlWindow.baseWindow.hWnd); dc = GetDC(filter->baseControlWindow.hwnd);
StretchDIBits(dc, filter->DestRect.left, filter->DestRect.top, StretchDIBits(dc, filter->DestRect.left, filter->DestRect.top,
filter->DestRect.right - filter->DestRect.left, filter->DestRect.right - filter->DestRect.left,
filter->DestRect.bottom - filter->DestRect.top, filter->DestRect.bottom - filter->DestRect.top,
@ -172,7 +172,7 @@ static HRESULT WINAPI VideoRenderer_DoRenderSample(struct strmbase_renderer *ifa
filter->SourceRect.right - filter->SourceRect.left, filter->SourceRect.right - filter->SourceRect.left,
filter->SourceRect.bottom - filter->SourceRect.top, filter->SourceRect.bottom - filter->SourceRect.top,
pbSrcStream, (BITMAPINFO *)bih, DIB_RGB_COLORS, SRCCOPY); pbSrcStream, (BITMAPINFO *)bih, DIB_RGB_COLORS, SRCCOPY);
ReleaseDC(filter->baseControlWindow.baseWindow.hWnd, dc); ReleaseDC(filter->baseControlWindow.hwnd, dc);
if (filter->renderer.filter.state == State_Paused) if (filter->renderer.filter.state == State_Paused)
{ {
@ -243,7 +243,7 @@ static void video_renderer_destroy(struct strmbase_renderer *iface)
{ {
struct video_renderer *filter = impl_from_strmbase_renderer(iface); struct video_renderer *filter = impl_from_strmbase_renderer(iface);
BaseControlWindow_Destroy(&filter->baseControlWindow); video_window_cleanup(&filter->baseControlWindow);
CloseHandle(filter->run_event); CloseHandle(filter->run_event);
strmbase_renderer_cleanup(&filter->renderer); strmbase_renderer_cleanup(&filter->renderer);
free(filter); free(filter);
@ -294,7 +294,7 @@ static void video_renderer_stop_stream(struct strmbase_renderer *iface)
if (This->baseControlWindow.AutoShow) if (This->baseControlWindow.AutoShow)
/* Black it out */ /* Black it out */
RedrawWindow(This->baseControlWindow.baseWindow.hWnd, NULL, NULL, RDW_INVALIDATE|RDW_ERASE); RedrawWindow(This->baseControlWindow.hwnd, NULL, NULL, RDW_INVALIDATE | RDW_ERASE);
ResetEvent(This->run_event); ResetEvent(This->run_event);
} }
@ -306,9 +306,9 @@ static void video_renderer_init_stream(struct strmbase_renderer *iface)
VideoRenderer_AutoShowWindow(filter); VideoRenderer_AutoShowWindow(filter);
} }
static RECT WINAPI VideoRenderer_GetDefaultRect(BaseWindow *iface) static RECT video_renderer_get_default_rect(struct video_window *iface)
{ {
struct video_renderer *This = impl_from_BaseWindow(iface); struct video_renderer *This = impl_from_video_window(iface);
static RECT defRect; static RECT defRect;
SetRect(&defRect, 0, 0, This->VideoWidth, This->VideoHeight); SetRect(&defRect, 0, 0, This->VideoWidth, This->VideoHeight);
@ -316,12 +316,12 @@ static RECT WINAPI VideoRenderer_GetDefaultRect(BaseWindow *iface)
return defRect; return defRect;
} }
static BOOL WINAPI VideoRenderer_OnSize(BaseWindow *iface, LONG Width, LONG Height) static BOOL video_renderer_resize(struct video_window *iface, LONG Width, LONG Height)
{ {
struct video_renderer *This = impl_from_BaseWindow(iface); struct video_renderer *This = impl_from_video_window(iface);
TRACE("WM_SIZE %d %d\n", Width, Height); TRACE("WM_SIZE %d %d\n", Width, Height);
GetClientRect(iface->hWnd, &This->DestRect); GetClientRect(iface->hwnd, &This->DestRect);
TRACE("WM_SIZING: DestRect=(%d,%d),(%d,%d)\n", TRACE("WM_SIZING: DestRect=(%d,%d),(%d,%d)\n",
This->DestRect.left, This->DestRect.left,
This->DestRect.top, This->DestRect.top,
@ -346,8 +346,8 @@ static const struct strmbase_renderer_ops renderer_ops =
static const struct video_window_ops window_ops = static const struct video_window_ops window_ops =
{ {
VideoRenderer_GetDefaultRect, .get_default_rect = video_renderer_get_default_rect,
VideoRenderer_OnSize .resize = video_renderer_resize,
}; };
static HRESULT WINAPI VideoRenderer_GetSourceRect(BaseControlVideo* iface, RECT *pSourceRect) static HRESULT WINAPI VideoRenderer_GetSourceRect(BaseControlVideo* iface, RECT *pSourceRect)
@ -467,7 +467,7 @@ static HRESULT WINAPI VideoRenderer_SetDefaultTargetRect(BaseControlVideo* iface
struct video_renderer *This = impl_from_BaseControlVideo(iface); struct video_renderer *This = impl_from_BaseControlVideo(iface);
RECT rect; RECT rect;
if (!GetClientRect(This->baseControlWindow.baseWindow.hWnd, &rect)) if (!GetClientRect(This->baseControlWindow.hwnd, &rect))
return E_FAIL; return E_FAIL;
SetRect(&This->DestRect, 0, 0, rect.right, rect.bottom); SetRect(&This->DestRect, 0, 0, rect.right, rect.bottom);
@ -517,30 +517,34 @@ static HRESULT WINAPI VideoWindow_get_FullScreenMode(IVideoWindow *iface,
return S_OK; return S_OK;
} }
static HRESULT WINAPI VideoWindow_put_FullScreenMode(IVideoWindow *iface, static HRESULT WINAPI VideoWindow_put_FullScreenMode(IVideoWindow *iface, LONG fullscreen)
LONG FullScreenMode)
{ {
struct video_renderer *This = impl_from_IVideoWindow(iface); struct video_renderer *filter = impl_from_IVideoWindow(iface);
FIXME("(%p/%p)->(%d): stub !!!\n", This, iface, FullScreenMode); FIXME("filter %p, fullscreen %d.\n", filter, fullscreen);
if (FullScreenMode) { if (fullscreen)
This->saved_style = GetWindowLongW(This->baseControlWindow.baseWindow.hWnd, GWL_STYLE); {
ShowWindow(This->baseControlWindow.baseWindow.hWnd, SW_HIDE); filter->saved_style = GetWindowLongW(filter->baseControlWindow.hwnd, GWL_STYLE);
SetParent(This->baseControlWindow.baseWindow.hWnd, 0); ShowWindow(filter->baseControlWindow.hwnd, SW_HIDE);
SetWindowLongW(This->baseControlWindow.baseWindow.hWnd, GWL_STYLE, WS_POPUP); SetParent(filter->baseControlWindow.hwnd, NULL);
SetWindowPos(This->baseControlWindow.baseWindow.hWnd,HWND_TOP,0,0,GetSystemMetrics(SM_CXSCREEN),GetSystemMetrics(SM_CYSCREEN),SWP_SHOWWINDOW); SetWindowLongW(filter->baseControlWindow.hwnd, GWL_STYLE, WS_POPUP);
GetWindowRect(This->baseControlWindow.baseWindow.hWnd, &This->DestRect); SetWindowPos(filter->baseControlWindow.hwnd, HWND_TOP, 0, 0,
This->WindowPos = This->DestRect; GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN), SWP_SHOWWINDOW);
} else { GetWindowRect(filter->baseControlWindow.hwnd, &filter->DestRect);
ShowWindow(This->baseControlWindow.baseWindow.hWnd, SW_HIDE); filter->WindowPos = filter->DestRect;
SetParent(This->baseControlWindow.baseWindow.hWnd, This->baseControlWindow.hwndOwner);
SetWindowLongW(This->baseControlWindow.baseWindow.hWnd, GWL_STYLE, This->saved_style);
GetClientRect(This->baseControlWindow.baseWindow.hWnd, &This->DestRect);
SetWindowPos(This->baseControlWindow.baseWindow.hWnd,0,This->DestRect.left,This->DestRect.top,This->DestRect.right,This->DestRect.bottom,SWP_NOZORDER|SWP_SHOWWINDOW);
This->WindowPos = This->DestRect;
} }
This->FullScreenMode = FullScreenMode; else
{
ShowWindow(filter->baseControlWindow.hwnd, SW_HIDE);
SetParent(filter->baseControlWindow.hwnd, filter->baseControlWindow.hwndOwner);
SetWindowLongW(filter->baseControlWindow.hwnd, GWL_STYLE, filter->saved_style);
GetClientRect(filter->baseControlWindow.hwnd, &filter->DestRect);
SetWindowPos(filter->baseControlWindow.hwnd, 0, filter->DestRect.left, filter->DestRect.top,
filter->DestRect.right, filter->DestRect.bottom, SWP_NOZORDER | SWP_SHOWWINDOW);
filter->WindowPos = filter->DestRect;
}
filter->FullScreenMode = fullscreen;
return S_OK; return S_OK;
} }
@ -654,7 +658,7 @@ static HRESULT WINAPI overlay_GetWindowHandle(IOverlay *iface, HWND *window)
TRACE("filter %p, window %p.\n", filter, window); TRACE("filter %p, window %p.\n", filter, window);
*window = filter->baseControlWindow.baseWindow.hWnd; *window = filter->baseControlWindow.hwnd;
return S_OK; return S_OK;
} }
@ -718,7 +722,7 @@ HRESULT video_renderer_create(IUnknown *outer, IUnknown **out)
basic_video_init(&object->baseControlVideo, &object->renderer.filter, basic_video_init(&object->baseControlVideo, &object->renderer.filter,
&object->renderer.sink.pin, &renderer_BaseControlVideoFuncTable); &object->renderer.sink.pin, &renderer_BaseControlVideoFuncTable);
if (FAILED(hr = BaseWindowImpl_PrepareWindow(&object->baseControlWindow.baseWindow))) if (FAILED(hr = video_window_create_window(&object->baseControlWindow)))
goto fail; goto fail;
object->run_event = CreateEventW(NULL, TRUE, FALSE, NULL); object->run_event = CreateEventW(NULL, TRUE, FALSE, NULL);

View File

@ -91,9 +91,9 @@ struct quartz_vmr
HANDLE run_event; HANDLE run_event;
}; };
static inline struct quartz_vmr *impl_from_BaseWindow(BaseWindow *wnd) static inline struct quartz_vmr *impl_from_video_window(struct video_window *iface)
{ {
return CONTAINING_RECORD(wnd, struct quartz_vmr, baseControlWindow.baseWindow); return CONTAINING_RECORD(iface, struct quartz_vmr, baseControlWindow);
} }
static inline struct quartz_vmr *impl_from_BaseControlVideo(BaseControlVideo *cvid) static inline struct quartz_vmr *impl_from_BaseControlVideo(BaseControlVideo *cvid)
@ -412,7 +412,7 @@ static HRESULT VMR9_maybe_init(struct quartz_vmr *filter, BOOL force, const AM_M
}; };
TRACE("Initializing in mode %u, our window %p, clipping window %p.\n", TRACE("Initializing in mode %u, our window %p, clipping window %p.\n",
filter->mode, filter->baseControlWindow.baseWindow.hWnd, filter->hWndClippingWindow); filter->mode, filter->baseControlWindow.hwnd, filter->hWndClippingWindow);
if (filter->num_surfaces) if (filter->num_surfaces)
return S_OK; return S_OK;
@ -487,14 +487,14 @@ static void vmr_start_stream(struct strmbase_renderer *iface)
if (This->renderer.sink.pin.peer) if (This->renderer.sink.pin.peer)
VMR9_maybe_init(This, TRUE, &This->renderer.sink.pin.mt); VMR9_maybe_init(This, TRUE, &This->renderer.sink.pin.mt);
IVMRImagePresenter9_StartPresenting(This->presenter, This->cookie); IVMRImagePresenter9_StartPresenting(This->presenter, This->cookie);
SetWindowPos(This->baseControlWindow.baseWindow.hWnd, NULL, SetWindowPos(This->baseControlWindow.hwnd, NULL,
This->source_rect.left, This->source_rect.left,
This->source_rect.top, This->source_rect.top,
This->source_rect.right - This->source_rect.left, This->source_rect.right - This->source_rect.left,
This->source_rect.bottom - This->source_rect.top, This->source_rect.bottom - This->source_rect.top,
SWP_NOZORDER|SWP_NOMOVE|SWP_DEFERERASE); SWP_NOZORDER|SWP_NOMOVE|SWP_DEFERERASE);
ShowWindow(This->baseControlWindow.baseWindow.hWnd, SW_SHOW); ShowWindow(This->baseControlWindow.hwnd, SW_SHOW);
GetClientRect(This->baseControlWindow.baseWindow.hWnd, &This->target_rect); GetClientRect(This->baseControlWindow.hwnd, &This->target_rect);
SetEvent(This->run_event); SetEvent(This->run_event);
} }
@ -579,7 +579,7 @@ static void vmr_destroy(struct strmbase_renderer *iface)
{ {
struct quartz_vmr *filter = impl_from_IBaseFilter(&iface->filter.IBaseFilter_iface); struct quartz_vmr *filter = impl_from_IBaseFilter(&iface->filter.IBaseFilter_iface);
BaseControlWindow_Destroy(&filter->baseControlWindow); video_window_cleanup(&filter->baseControlWindow);
if (filter->allocator) if (filter->allocator)
IVMRSurfaceAllocatorEx9_Release(filter->allocator); IVMRSurfaceAllocatorEx9_Release(filter->allocator);
@ -595,7 +595,6 @@ static void vmr_destroy(struct strmbase_renderer *iface)
CloseHandle(filter->run_event); CloseHandle(filter->run_event);
FreeLibrary(filter->hD3d9); FreeLibrary(filter->hD3d9);
BaseControlWindow_Destroy(&filter->baseControlWindow);
strmbase_renderer_cleanup(&filter->renderer); strmbase_renderer_cleanup(&filter->renderer);
free(filter); free(filter);
@ -664,9 +663,9 @@ static const struct strmbase_renderer_ops renderer_ops =
.renderer_pin_query_interface = vmr_pin_query_interface, .renderer_pin_query_interface = vmr_pin_query_interface,
}; };
static RECT WINAPI VMR9_GetDefaultRect(BaseWindow *This) static RECT vmr_get_default_rect(struct video_window *This)
{ {
struct quartz_vmr* pVMR9 = impl_from_BaseWindow(This); struct quartz_vmr *pVMR9 = impl_from_video_window(This);
static RECT defRect; static RECT defRect;
SetRect(&defRect, 0, 0, pVMR9->VideoWidth, pVMR9->VideoHeight); SetRect(&defRect, 0, 0, pVMR9->VideoWidth, pVMR9->VideoHeight);
@ -674,12 +673,12 @@ static RECT WINAPI VMR9_GetDefaultRect(BaseWindow *This)
return defRect; return defRect;
} }
static BOOL WINAPI VMR9_OnSize(BaseWindow *This, LONG Width, LONG Height) static BOOL vmr_resize(struct video_window *This, LONG Width, LONG Height)
{ {
struct quartz_vmr* pVMR9 = impl_from_BaseWindow(This); struct quartz_vmr *pVMR9 = impl_from_video_window(This);
TRACE("WM_SIZE %d %d\n", Width, Height); TRACE("WM_SIZE %d %d\n", Width, Height);
GetClientRect(This->hWnd, &pVMR9->target_rect); GetClientRect(This->hwnd, &pVMR9->target_rect);
TRACE("WM_SIZING: DestRect=(%d,%d),(%d,%d)\n", TRACE("WM_SIZING: DestRect=(%d,%d),(%d,%d)\n",
pVMR9->target_rect.left, pVMR9->target_rect.left,
pVMR9->target_rect.top, pVMR9->target_rect.top,
@ -691,8 +690,8 @@ static BOOL WINAPI VMR9_OnSize(BaseWindow *This, LONG Width, LONG Height)
static const struct video_window_ops window_ops = static const struct video_window_ops window_ops =
{ {
VMR9_GetDefaultRect, .get_default_rect = vmr_get_default_rect,
VMR9_OnSize, .resize = vmr_resize,
}; };
static HRESULT WINAPI VMR9_GetSourceRect(BaseControlVideo* This, RECT *pSourceRect) static HRESULT WINAPI VMR9_GetSourceRect(BaseControlVideo* This, RECT *pSourceRect)
@ -828,7 +827,7 @@ static HRESULT WINAPI VMR9_SetDefaultTargetRect(BaseControlVideo* This)
RECT rect; RECT rect;
struct quartz_vmr* pVMR9 = impl_from_BaseControlVideo(This); struct quartz_vmr* pVMR9 = impl_from_BaseControlVideo(This);
if (!GetClientRect(pVMR9->baseControlWindow.baseWindow.hWnd, &rect)) if (!GetClientRect(pVMR9->baseControlWindow.hwnd, &rect))
return E_FAIL; return E_FAIL;
SetRect(&pVMR9->target_rect, 0, 0, rect.right, rect.bottom); SetRect(&pVMR9->target_rect, 0, 0, rect.right, rect.bottom);
@ -1602,7 +1601,7 @@ static HRESULT WINAPI VMR7WindowlessControl_SetVideoPosition(IVMRWindowlessContr
{ {
This->target_rect = *dest; This->target_rect = *dest;
FIXME("Output rectangle: %s.\n", wine_dbgstr_rect(dest)); FIXME("Output rectangle: %s.\n", wine_dbgstr_rect(dest));
SetWindowPos(This->baseControlWindow.baseWindow.hWnd, NULL, SetWindowPos(This->baseControlWindow.hwnd, NULL,
dest->left, dest->top, dest->right - dest->left, dest->bottom-dest->top, dest->left, dest->top, dest->right - dest->left, dest->bottom-dest->top,
SWP_NOACTIVATE | SWP_NOCOPYBITS | SWP_NOOWNERZORDER | SWP_NOREDRAW); SWP_NOACTIVATE | SWP_NOCOPYBITS | SWP_NOOWNERZORDER | SWP_NOREDRAW);
} }
@ -1803,7 +1802,7 @@ static HRESULT WINAPI VMR9WindowlessControl_SetVideoPosition(IVMRWindowlessContr
{ {
This->target_rect = *dest; This->target_rect = *dest;
FIXME("Output rectangle: %s.\n", wine_dbgstr_rect(dest)); FIXME("Output rectangle: %s.\n", wine_dbgstr_rect(dest));
SetWindowPos(This->baseControlWindow.baseWindow.hWnd, NULL, SetWindowPos(This->baseControlWindow.hwnd, NULL,
dest->left, dest->top, dest->right - dest->left, dest->bottom - dest->top, dest->left, dest->top, dest->right - dest->left, dest->bottom - dest->top,
SWP_NOACTIVATE | SWP_NOCOPYBITS | SWP_NOOWNERZORDER | SWP_NOREDRAW); SWP_NOACTIVATE | SWP_NOCOPYBITS | SWP_NOOWNERZORDER | SWP_NOREDRAW);
} }
@ -1867,7 +1866,7 @@ static HRESULT WINAPI VMR9WindowlessControl_RepaintVideo(IVMRWindowlessControl9
FIXME("(%p/%p)->(...) semi-stub\n", iface, This); FIXME("(%p/%p)->(...) semi-stub\n", iface, This);
EnterCriticalSection(&This->renderer.filter.csFilter); EnterCriticalSection(&This->renderer.filter.csFilter);
if (hwnd != This->hWndClippingWindow && hwnd != This->baseControlWindow.baseWindow.hWnd) if (hwnd != This->hWndClippingWindow && hwnd != This->baseControlWindow.hwnd)
{ {
ERR("Not handling changing windows yet!!!\n"); ERR("Not handling changing windows yet!!!\n");
LeaveCriticalSection(&This->renderer.filter.csFilter); LeaveCriticalSection(&This->renderer.filter.csFilter);
@ -1882,7 +1881,7 @@ static HRESULT WINAPI VMR9WindowlessControl_RepaintVideo(IVMRWindowlessControl9
} }
/* Windowless extension */ /* Windowless extension */
hr = IDirect3DDevice9_Present(This->allocator_d3d9_dev, NULL, NULL, This->baseControlWindow.baseWindow.hWnd, NULL); hr = IDirect3DDevice9_Present(This->allocator_d3d9_dev, NULL, NULL, This->baseControlWindow.hwnd, NULL);
LeaveCriticalSection(&This->renderer.filter.csFilter); LeaveCriticalSection(&This->renderer.filter.csFilter);
return hr; return hr;
@ -2245,7 +2244,7 @@ static HRESULT WINAPI overlay_GetWindowHandle(IOverlay *iface, HWND *window)
TRACE("filter %p, window %p.\n", filter, window); TRACE("filter %p, window %p.\n", filter, window);
*window = filter->baseControlWindow.baseWindow.hWnd; *window = filter->baseControlWindow.hwnd;
return S_OK; return S_OK;
} }
@ -2324,7 +2323,7 @@ static HRESULT vmr_create(IUnknown *outer, IUnknown **out, const CLSID *clsid)
if (FAILED(hr)) if (FAILED(hr))
goto fail; goto fail;
if (FAILED(hr = BaseWindowImpl_PrepareWindow(&object->baseControlWindow.baseWindow))) if (FAILED(hr = video_window_create_window(&object->baseControlWindow)))
goto fail; goto fail;
basic_video_init(&object->baseControlVideo, &object->renderer.filter, basic_video_init(&object->baseControlVideo, &object->renderer.filter,
@ -2337,7 +2336,6 @@ static HRESULT vmr_create(IUnknown *outer, IUnknown **out, const CLSID *clsid)
return hr; return hr;
fail: fail:
BaseWindowImpl_DoneWithWindow(&object->baseControlWindow.baseWindow);
strmbase_renderer_cleanup(&object->renderer); strmbase_renderer_cleanup(&object->renderer);
FreeLibrary(object->hD3d9); FreeLibrary(object->hD3d9);
free(object); free(object);
@ -2520,7 +2518,7 @@ static HRESULT WINAPI VMR9_ImagePresenter_PresentImage(IVMRImagePresenter9 *ifac
BOOL render = FALSE; BOOL render = FALSE;
TRACE("(%p/%p/%p)->(...) stub\n", iface, This, This->pVMR9); TRACE("(%p/%p/%p)->(...) stub\n", iface, This, This->pVMR9);
GetWindowRect(This->pVMR9->baseControlWindow.baseWindow.hWnd, &output); GetWindowRect(This->pVMR9->baseControlWindow.hwnd, &output);
TRACE("Output rectangle: %s\n", wine_dbgstr_rect(&output)); TRACE("Output rectangle: %s\n", wine_dbgstr_rect(&output));
/* This might happen if we don't have active focus (eg on a different virtual desktop) */ /* This might happen if we don't have active focus (eg on a different virtual desktop) */
@ -2545,7 +2543,7 @@ static HRESULT WINAPI VMR9_ImagePresenter_PresentImage(IVMRImagePresenter9 *ifac
hr = IDirect3DDevice9_EndScene(This->d3d9_dev); hr = IDirect3DDevice9_EndScene(This->d3d9_dev);
if (render && SUCCEEDED(hr)) if (render && SUCCEEDED(hr))
{ {
hr = IDirect3DDevice9_Present(This->d3d9_dev, NULL, NULL, This->pVMR9->baseControlWindow.baseWindow.hWnd, NULL); hr = IDirect3DDevice9_Present(This->d3d9_dev, NULL, NULL, This->pVMR9->baseControlWindow.hwnd, NULL);
if (FAILED(hr)) if (FAILED(hr))
FIXME("Presenting image: %08x\n", hr); FIXME("Presenting image: %08x\n", hr);
} }
@ -2669,12 +2667,12 @@ static BOOL CreateRenderingWindow(struct default_presenter *This, VMR9Allocation
TRACE("(%p)->()\n", This); TRACE("(%p)->()\n", This);
/* Obtain a monitor and d3d9 device */ /* Obtain a monitor and d3d9 device */
d3d9_adapter = d3d9_adapter_from_hwnd(This->d3d9_ptr, This->pVMR9->baseControlWindow.baseWindow.hWnd, &This->hMon); d3d9_adapter = d3d9_adapter_from_hwnd(This->d3d9_ptr, This->pVMR9->baseControlWindow.hwnd, &This->hMon);
/* Now try to create the d3d9 device */ /* Now try to create the d3d9 device */
ZeroMemory(&d3dpp, sizeof(d3dpp)); ZeroMemory(&d3dpp, sizeof(d3dpp));
d3dpp.Windowed = TRUE; d3dpp.Windowed = TRUE;
d3dpp.hDeviceWindow = This->pVMR9->baseControlWindow.baseWindow.hWnd; d3dpp.hDeviceWindow = This->pVMR9->baseControlWindow.hwnd;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD; d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferHeight = This->pVMR9->target_rect.bottom - This->pVMR9->target_rect.top; d3dpp.BackBufferHeight = This->pVMR9->target_rect.bottom - This->pVMR9->target_rect.top;
d3dpp.BackBufferWidth = This->pVMR9->target_rect.right - This->pVMR9->target_rect.left; d3dpp.BackBufferWidth = This->pVMR9->target_rect.right - This->pVMR9->target_rect.left;
@ -2773,16 +2771,20 @@ static HRESULT VMR9_SurfaceAllocator_UpdateDeviceReset(struct default_presenter
/* Now try to create the d3d9 device */ /* Now try to create the d3d9 device */
ZeroMemory(&d3dpp, sizeof(d3dpp)); ZeroMemory(&d3dpp, sizeof(d3dpp));
d3dpp.Windowed = TRUE; d3dpp.Windowed = TRUE;
d3dpp.hDeviceWindow = This->pVMR9->baseControlWindow.baseWindow.hWnd; d3dpp.hDeviceWindow = This->pVMR9->baseControlWindow.hwnd;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD; d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
if (This->d3d9_dev) if (This->d3d9_dev)
IDirect3DDevice9_Release(This->d3d9_dev); IDirect3DDevice9_Release(This->d3d9_dev);
This->d3d9_dev = NULL; This->d3d9_dev = NULL;
hr = IDirect3D9_CreateDevice(This->d3d9_ptr, d3d9_adapter_from_hwnd(This->d3d9_ptr, This->pVMR9->baseControlWindow.baseWindow.hWnd, &This->hMon), D3DDEVTYPE_HAL, NULL, D3DCREATE_HARDWARE_VERTEXPROCESSING, &d3dpp, &This->d3d9_dev); hr = IDirect3D9_CreateDevice(This->d3d9_ptr, d3d9_adapter_from_hwnd(This->d3d9_ptr,
This->pVMR9->baseControlWindow.hwnd, &This->hMon), D3DDEVTYPE_HAL, NULL,
D3DCREATE_HARDWARE_VERTEXPROCESSING, &d3dpp, &This->d3d9_dev);
if (FAILED(hr)) if (FAILED(hr))
{ {
hr = IDirect3D9_CreateDevice(This->d3d9_ptr, d3d9_adapter_from_hwnd(This->d3d9_ptr, This->pVMR9->baseControlWindow.baseWindow.hWnd, &This->hMon), D3DDEVTYPE_HAL, NULL, D3DCREATE_MIXED_VERTEXPROCESSING, &d3dpp, &This->d3d9_dev); hr = IDirect3D9_CreateDevice(This->d3d9_ptr, d3d9_adapter_from_hwnd(This->d3d9_ptr,
This->pVMR9->baseControlWindow.hwnd, &This->hMon), D3DDEVTYPE_HAL, NULL,
D3DCREATE_MIXED_VERTEXPROCESSING, &d3dpp, &This->d3d9_dev);
if (FAILED(hr)) if (FAILED(hr))
{ {
ERR("--> Creating device: %08x\n", hr); ERR("--> Creating device: %08x\n", hr);

View File

@ -29,17 +29,11 @@ static inline struct video_window *impl_from_IVideoWindow(IVideoWindow *iface)
return CONTAINING_RECORD(iface, struct video_window, IVideoWindow_iface); return CONTAINING_RECORD(iface, struct video_window, IVideoWindow_iface);
} }
static inline struct video_window *impl_from_BaseWindow(BaseWindow *iface)
{
return CONTAINING_RECORD(iface, struct video_window, baseWindow);
}
static LRESULT CALLBACK WndProcW(HWND hwnd, UINT message, WPARAM wparam, LPARAM lparam) static LRESULT CALLBACK WndProcW(HWND hwnd, UINT message, WPARAM wparam, LPARAM lparam)
{ {
BaseWindow* This = (BaseWindow*)GetWindowLongPtrW(hwnd, 0); struct video_window *window = (struct video_window *)GetWindowLongPtrW(hwnd, 0);
struct video_window *window = impl_from_BaseWindow(This);
if (!This) if (!window)
return DefWindowProcW(hwnd, message, wparam, lparam); return DefWindowProcW(hwnd, message, wparam, lparam);
switch (message) switch (message)
@ -74,42 +68,22 @@ static LRESULT CALLBACK WndProcW(HWND hwnd, UINT message, WPARAM wparam, LPARAM
} }
break; break;
case WM_SIZE: case WM_SIZE:
if (This->pFuncsTable->pfnOnSize) if (window->ops->resize)
return This->pFuncsTable->pfnOnSize(This, LOWORD(lparam), HIWORD(lparam)); return window->ops->resize(window, LOWORD(lparam), HIWORD(lparam));
This->Width = LOWORD(lparam); window->width = LOWORD(lparam);
This->Height = HIWORD(lparam); window->height = HIWORD(lparam);
} }
return DefWindowProcW(hwnd, message, wparam, lparam); return DefWindowProcW(hwnd, message, wparam, lparam);
} }
HRESULT WINAPI BaseWindow_Init(BaseWindow *pBaseWindow, const struct video_window_ops *pFuncsTable) HRESULT video_window_create_window(struct video_window *window)
{
if (!pFuncsTable)
return E_INVALIDARG;
ZeroMemory(pBaseWindow,sizeof(BaseWindow));
pBaseWindow->pFuncsTable = pFuncsTable;
return S_OK;
}
HRESULT WINAPI BaseWindow_Destroy(BaseWindow *This)
{
if (This->hWnd)
BaseWindowImpl_DoneWithWindow(This);
HeapFree(GetProcessHeap(), 0, This);
return S_OK;
}
HRESULT WINAPI BaseWindowImpl_PrepareWindow(BaseWindow *This)
{ {
WNDCLASSW winclass = {0}; WNDCLASSW winclass = {0};
winclass.lpfnWndProc = WndProcW; winclass.lpfnWndProc = WndProcW;
winclass.cbWndExtra = sizeof(BaseWindow*); winclass.cbWndExtra = sizeof(window);
winclass.hbrBackground = GetStockObject(BLACK_BRUSH); winclass.hbrBackground = GetStockObject(BLACK_BRUSH);
winclass.lpszClassName = class_name; winclass.lpszClassName = class_name;
if (!RegisterClassW(&winclass) && GetLastError() != ERROR_CLASS_ALREADY_EXISTS) if (!RegisterClassW(&winclass) && GetLastError() != ERROR_CLASS_ALREADY_EXISTS)
@ -118,64 +92,20 @@ HRESULT WINAPI BaseWindowImpl_PrepareWindow(BaseWindow *This)
return E_FAIL; return E_FAIL;
} }
This->hWnd = CreateWindowExW(0, class_name, L"ActiveMovie Window", if (!(window->hwnd = CreateWindowExW(0, class_name, L"ActiveMovie Window",
WS_OVERLAPPEDWINDOW | WS_CLIPSIBLINGS | WS_CLIPCHILDREN, WS_OVERLAPPEDWINDOW | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT,
NULL, NULL, NULL, NULL); NULL, NULL, NULL, NULL)))
if (!This->hWnd)
{ {
ERR("Unable to create window\n"); ERR("Unable to create window\n");
return E_FAIL; return E_FAIL;
} }
SetWindowLongPtrW(This->hWnd, 0, (LONG_PTR)This); SetWindowLongPtrW(window->hwnd, 0, (LONG_PTR)window);
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseWindowImpl_DoneWithWindow(BaseWindow *This)
{
if (!This->hWnd)
return S_OK;
/* Media Player Classic deadlocks if WM_PARENTNOTIFY is sent, so clear
* the child style first. Just like Windows, we don't actually unparent
* the window, to prevent extra focus events from being generated since
* it would become top-level for a brief period before being destroyed. */
SetWindowLongW(This->hWnd, GWL_STYLE, GetWindowLongW(This->hWnd, GWL_STYLE) & ~WS_CHILD);
SendMessageW(This->hWnd, WM_CLOSE, 0, 0);
This->hWnd = NULL;
return S_OK;
}
HRESULT video_window_init(struct video_window *pControlWindow,
const IVideoWindowVtbl *lpVtbl, struct strmbase_filter *owner,
struct strmbase_pin *pPin, const struct video_window_ops *pFuncsTable)
{
HRESULT hr;
hr = BaseWindow_Init(&pControlWindow->baseWindow, pFuncsTable);
if (SUCCEEDED(hr))
{
pControlWindow->IVideoWindow_iface.lpVtbl = lpVtbl;
pControlWindow->AutoShow = OATRUE;
pControlWindow->hwndDrain = NULL;
pControlWindow->hwndOwner = NULL;
pControlWindow->pFilter = owner;
pControlWindow->pPin = pPin;
}
return hr;
}
HRESULT WINAPI BaseControlWindow_Destroy(struct video_window *pControlWindow)
{
BaseWindowImpl_DoneWithWindow(&pControlWindow->baseWindow);
return S_OK;
}
HRESULT WINAPI BaseControlWindowImpl_QueryInterface(IVideoWindow *iface, REFIID iid, void **out) HRESULT WINAPI BaseControlWindowImpl_QueryInterface(IVideoWindow *iface, REFIID iid, void **out)
{ {
struct video_window *window = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
@ -242,13 +172,13 @@ HRESULT WINAPI BaseControlWindowImpl_Invoke(IVideoWindow *iface, DISPID id, REFI
return hr; return hr;
} }
HRESULT WINAPI BaseControlWindowImpl_put_Caption(IVideoWindow *iface, BSTR strCaption) HRESULT WINAPI BaseControlWindowImpl_put_Caption(IVideoWindow *iface, BSTR caption)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%s (%p))\n", This, iface, debugstr_w(strCaption), strCaption); TRACE("window %p, caption %s.\n", window, debugstr_w(caption));
if (!SetWindowTextW(This->baseWindow.hWnd, strCaption)) if (!SetWindowTextW(window->hwnd, caption))
return E_FAIL; return E_FAIL;
return S_OK; return S_OK;
@ -264,32 +194,28 @@ HRESULT WINAPI BaseControlWindowImpl_get_Caption(IVideoWindow *iface, BSTR *capt
*caption = NULL; *caption = NULL;
len = GetWindowTextLengthW(window->baseWindow.hWnd) + 1; len = GetWindowTextLengthW(window->hwnd) + 1;
if (!(str = heap_alloc(len * sizeof(WCHAR)))) if (!(str = heap_alloc(len * sizeof(WCHAR))))
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
GetWindowTextW(window->baseWindow.hWnd, str, len); GetWindowTextW(window->hwnd, str, len);
*caption = SysAllocString(str); *caption = SysAllocString(str);
heap_free(str); heap_free(str);
return *caption ? S_OK : E_OUTOFMEMORY; return *caption ? S_OK : E_OUTOFMEMORY;
} }
HRESULT WINAPI BaseControlWindowImpl_put_WindowStyle(IVideoWindow *iface, LONG WindowStyle) HRESULT WINAPI BaseControlWindowImpl_put_WindowStyle(IVideoWindow *iface, LONG style)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
LONG old;
old = GetWindowLongW(This->baseWindow.hWnd, GWL_STYLE); TRACE("window %p, style %#x.\n", window, style);
TRACE("(%p/%p)->(%x -> %x)\n", This, iface, old, WindowStyle); if (style & (WS_DISABLED|WS_HSCROLL|WS_MAXIMIZE|WS_MINIMIZE|WS_VSCROLL))
if (WindowStyle & (WS_DISABLED|WS_HSCROLL|WS_MAXIMIZE|WS_MINIMIZE|WS_VSCROLL))
return E_INVALIDARG; return E_INVALIDARG;
SetWindowLongW(This->baseWindow.hWnd, GWL_STYLE, WindowStyle); SetWindowLongW(window->hwnd, GWL_STYLE, style);
SetWindowPos(This->baseWindow.hWnd, 0, 0, 0, 0, 0, SetWindowPos(window->hwnd, 0, 0, 0, 0, 0,
SWP_NOSIZE | SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED); SWP_NOSIZE | SWP_NOMOVE | SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED);
return S_OK; return S_OK;
} }
@ -299,31 +225,28 @@ HRESULT WINAPI BaseControlWindowImpl_get_WindowStyle(IVideoWindow *iface, LONG *
TRACE("window %p, style %p.\n", window, style); TRACE("window %p, style %p.\n", window, style);
*style = GetWindowLongW(window->baseWindow.hWnd, GWL_STYLE); *style = GetWindowLongW(window->hwnd, GWL_STYLE);
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_put_WindowStyleEx(IVideoWindow *iface, LONG WindowStyleEx) HRESULT WINAPI BaseControlWindowImpl_put_WindowStyleEx(IVideoWindow *iface, LONG style)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%d)\n", This, iface, WindowStyleEx); TRACE("window %p, style %#x.\n", window, style);
if (!SetWindowLongW(This->baseWindow.hWnd, GWL_EXSTYLE, WindowStyleEx)) if (!SetWindowLongW(window->hwnd, GWL_EXSTYLE, style))
return E_FAIL; return E_FAIL;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_get_WindowStyleEx(IVideoWindow *iface, LONG *WindowStyleEx) HRESULT WINAPI BaseControlWindowImpl_get_WindowStyleEx(IVideoWindow *iface, LONG *style)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%p)\n", This, iface, WindowStyleEx); TRACE("window %p, style %p.\n", window, style);
*WindowStyleEx = GetWindowLongW(This->baseWindow.hWnd, GWL_EXSTYLE);
*style = GetWindowLongW(window->hwnd, GWL_EXSTYLE);
return S_OK; return S_OK;
} }
@ -349,12 +272,13 @@ HRESULT WINAPI BaseControlWindowImpl_get_AutoShow(IVideoWindow *iface, LONG *Aut
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_put_WindowState(IVideoWindow *iface, LONG WindowState) HRESULT WINAPI BaseControlWindowImpl_put_WindowState(IVideoWindow *iface, LONG state)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%d)\n", This, iface, WindowState); TRACE("window %p, state %#x.\n", window, state);
ShowWindow(This->baseWindow.hWnd, WindowState);
ShowWindow(window->hwnd, state);
return S_OK; return S_OK;
} }
@ -365,7 +289,7 @@ HRESULT WINAPI BaseControlWindowImpl_get_WindowState(IVideoWindow *iface, LONG *
TRACE("window %p, state %p.\n", window, state); TRACE("window %p, state %p.\n", window, state);
style = GetWindowLongPtrW(window->baseWindow.hWnd, GWL_STYLE); style = GetWindowLongPtrW(window->hwnd, GWL_STYLE);
if (!(style & WS_VISIBLE)) if (!(style & WS_VISIBLE))
*state = SW_HIDE; *state = SW_HIDE;
else if (style & WS_MINIMIZE) else if (style & WS_MINIMIZE)
@ -396,140 +320,132 @@ HRESULT WINAPI BaseControlWindowImpl_get_BackgroundPalette(IVideoWindow *iface,
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_put_Visible(IVideoWindow *iface, LONG Visible) HRESULT WINAPI BaseControlWindowImpl_put_Visible(IVideoWindow *iface, LONG visible)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%d)\n", This, iface, Visible); TRACE("window %p, visible %d.\n", window, visible);
ShowWindow(This->baseWindow.hWnd, Visible ? SW_SHOW : SW_HIDE);
ShowWindow(window->hwnd, visible ? SW_SHOW : SW_HIDE);
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_get_Visible(IVideoWindow *iface, LONG *pVisible) HRESULT WINAPI BaseControlWindowImpl_get_Visible(IVideoWindow *iface, LONG *visible)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%p)\n", This, iface, pVisible); TRACE("window %p, visible %p.\n", window, visible);
*pVisible = IsWindowVisible(This->baseWindow.hWnd) ? OATRUE : OAFALSE;
*visible = IsWindowVisible(window->hwnd) ? OATRUE : OAFALSE;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_put_Left(IVideoWindow *iface, LONG Left) HRESULT WINAPI BaseControlWindowImpl_put_Left(IVideoWindow *iface, LONG left)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
RECT WindowPos; RECT rect;
TRACE("(%p/%p)->(%d)\n", This, iface, Left); TRACE("window %p, left %d.\n", window, left);
GetWindowRect(This->baseWindow.hWnd, &WindowPos); GetWindowRect(window->hwnd, &rect);
if (!SetWindowPos(This->baseWindow.hWnd, NULL, Left, WindowPos.top, 0, 0, if (!SetWindowPos(window->hwnd, NULL, left, rect.top, 0, 0,
SWP_NOACTIVATE | SWP_NOZORDER | SWP_NOSIZE)) SWP_NOACTIVATE | SWP_NOZORDER | SWP_NOSIZE))
return E_FAIL; return E_FAIL;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_get_Left(IVideoWindow *iface, LONG *pLeft) HRESULT WINAPI BaseControlWindowImpl_get_Left(IVideoWindow *iface, LONG *left)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
RECT WindowPos; RECT rect;
TRACE("(%p/%p)->(%p)\n", This, iface, pLeft); TRACE("window %p, left %p.\n", window, left);
GetWindowRect(This->baseWindow.hWnd, &WindowPos);
*pLeft = WindowPos.left;
GetWindowRect(window->hwnd, &rect);
*left = rect.left;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_put_Width(IVideoWindow *iface, LONG Width) HRESULT WINAPI BaseControlWindowImpl_put_Width(IVideoWindow *iface, LONG width)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%d)\n", This, iface, Width); TRACE("window %p, width %d.\n", window, width);
if (!SetWindowPos(This->baseWindow.hWnd, NULL, 0, 0, Width, This->baseWindow.Height, if (!SetWindowPos(window->hwnd, NULL, 0, 0, width, window->height,
SWP_NOACTIVATE | SWP_NOZORDER | SWP_NOMOVE)) SWP_NOACTIVATE | SWP_NOZORDER | SWP_NOMOVE))
return E_FAIL; return E_FAIL;
This->baseWindow.Width = Width; window->width = width;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_get_Width(IVideoWindow *iface, LONG *pWidth) HRESULT WINAPI BaseControlWindowImpl_get_Width(IVideoWindow *iface, LONG *width)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%p)\n", This, iface, pWidth); TRACE("window %p, width %p.\n", window, width);
*pWidth = This->baseWindow.Width;
*width = window->width;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_put_Top(IVideoWindow *iface, LONG Top) HRESULT WINAPI BaseControlWindowImpl_put_Top(IVideoWindow *iface, LONG top)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
RECT WindowPos; RECT rect;
TRACE("(%p/%p)->(%d)\n", This, iface, Top); TRACE("window %p, top %d.\n", window, top);
GetWindowRect(This->baseWindow.hWnd, &WindowPos);
if (!SetWindowPos(This->baseWindow.hWnd, NULL, WindowPos.left, Top, 0, 0, GetWindowRect(window->hwnd, &rect);
if (!SetWindowPos(window->hwnd, NULL, rect.left, top, 0, 0,
SWP_NOACTIVATE | SWP_NOZORDER | SWP_NOSIZE)) SWP_NOACTIVATE | SWP_NOZORDER | SWP_NOSIZE))
return E_FAIL; return E_FAIL;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_get_Top(IVideoWindow *iface, LONG *pTop) HRESULT WINAPI BaseControlWindowImpl_get_Top(IVideoWindow *iface, LONG *top)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
RECT WindowPos; RECT rect;
TRACE("(%p/%p)->(%p)\n", This, iface, pTop); TRACE("window %p, top %p.\n", window, top);
GetWindowRect(This->baseWindow.hWnd, &WindowPos);
*pTop = WindowPos.top;
GetWindowRect(window->hwnd, &rect);
*top = rect.top;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_put_Height(IVideoWindow *iface, LONG Height) HRESULT WINAPI BaseControlWindowImpl_put_Height(IVideoWindow *iface, LONG height)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%d)\n", This, iface, Height); TRACE("window %p, height %d.\n", window, height);
if (!SetWindowPos(This->baseWindow.hWnd, NULL, 0, 0, This->baseWindow.Width, if (!SetWindowPos(window->hwnd, NULL, 0, 0, window->width,
Height, SWP_NOACTIVATE | SWP_NOZORDER | SWP_NOMOVE)) height, SWP_NOACTIVATE | SWP_NOZORDER | SWP_NOMOVE))
return E_FAIL; return E_FAIL;
This->baseWindow.Height = Height; window->height = height;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_get_Height(IVideoWindow *iface, LONG *pHeight) HRESULT WINAPI BaseControlWindowImpl_get_Height(IVideoWindow *iface, LONG *height)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%p)\n", This, iface, pHeight); TRACE("window %p, height %p.\n", window, height);
*pHeight = This->baseWindow.Height;
*height = window->height;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_put_Owner(IVideoWindow *iface, OAHWND owner) HRESULT WINAPI BaseControlWindowImpl_put_Owner(IVideoWindow *iface, OAHWND owner)
{ {
struct video_window *window = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
HWND hwnd = window->baseWindow.hWnd; HWND hwnd = window->hwnd;
TRACE("window %p, owner %#lx.\n", window, owner); TRACE("window %p, owner %#lx.\n", window, owner);
@ -625,39 +541,39 @@ HRESULT WINAPI BaseControlWindowImpl_SetWindowForeground(IVideoWindow *iface, LO
if (!focus) if (!focus)
flags |= SWP_NOACTIVATE; flags |= SWP_NOACTIVATE;
SetWindowPos(window->baseWindow.hWnd, HWND_TOP, 0, 0, 0, 0, flags); SetWindowPos(window->hwnd, HWND_TOP, 0, 0, 0, 0, flags);
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_SetWindowPosition(IVideoWindow *iface, LONG Left, LONG Top, LONG Width, LONG Height) HRESULT WINAPI BaseControlWindowImpl_SetWindowPosition(IVideoWindow *iface,
LONG left, LONG top, LONG width, LONG height)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
TRACE("(%p/%p)->(%d, %d, %d, %d)\n", This, iface, Left, Top, Width, Height); TRACE("window %p, left %d, top %d, width %d, height %d.\n", window, left, top, width, height);
if (!SetWindowPos(This->baseWindow.hWnd, NULL, Left, Top, Width, Height, SWP_NOACTIVATE | SWP_NOZORDER)) if (!SetWindowPos(window->hwnd, NULL, left, top, width, height, SWP_NOACTIVATE | SWP_NOZORDER))
return E_FAIL; return E_FAIL;
This->baseWindow.Width = Width; window->width = width;
This->baseWindow.Height = Height; window->height = height;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_GetWindowPosition(IVideoWindow *iface, LONG *pLeft, LONG *pTop, LONG *pWidth, LONG *pHeight) HRESULT WINAPI BaseControlWindowImpl_GetWindowPosition(IVideoWindow *iface,
LONG *left, LONG *top, LONG *width, LONG *height)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
RECT WindowPos; RECT rect;
TRACE("(%p/%p)->(%p, %p, %p, %p)\n", This, iface, pLeft, pTop, pWidth, pHeight); TRACE("window %p, left %p, top %p, width %p, height %p.\n", window, left, top, width, height);
GetWindowRect(This->baseWindow.hWnd, &WindowPos);
*pLeft = WindowPos.left;
*pTop = WindowPos.top;
*pWidth = This->baseWindow.Width;
*pHeight = This->baseWindow.Height;
GetWindowRect(window->hwnd, &rect);
*left = rect.left;
*top = rect.top;
*width = window->width;
*height = window->height;
return S_OK; return S_OK;
} }
@ -680,38 +596,36 @@ HRESULT WINAPI BaseControlWindowImpl_NotifyOwnerMessage(IVideoWindow *iface,
case WM_PALETTEISCHANGING: case WM_PALETTEISCHANGING:
case WM_QUERYNEWPALETTE: case WM_QUERYNEWPALETTE:
case WM_SYSCOLORCHANGE: case WM_SYSCOLORCHANGE:
SendMessageW(window->baseWindow.hWnd, message, wparam, lparam); SendMessageW(window->hwnd, message, wparam, lparam);
break; break;
} }
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_GetMinIdealImageSize(IVideoWindow *iface, LONG *pWidth, LONG *pHeight) HRESULT WINAPI BaseControlWindowImpl_GetMinIdealImageSize(IVideoWindow *iface, LONG *width, LONG *height)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
RECT defaultRect; RECT rect;
TRACE("(%p/%p)->(%p, %p)\n", This, iface, pWidth, pHeight); TRACE("window %p, width %p, height %p.\n", window, width, height);
defaultRect = This->baseWindow.pFuncsTable->pfnGetDefaultRect(&This->baseWindow);
*pWidth = defaultRect.right - defaultRect.left;
*pHeight = defaultRect.bottom - defaultRect.top;
rect = window->ops->get_default_rect(window);
*width = rect.right - rect.left;
*height = rect.bottom - rect.top;
return S_OK; return S_OK;
} }
HRESULT WINAPI BaseControlWindowImpl_GetMaxIdealImageSize(IVideoWindow *iface, LONG *pWidth, LONG *pHeight) HRESULT WINAPI BaseControlWindowImpl_GetMaxIdealImageSize(IVideoWindow *iface, LONG *width, LONG *height)
{ {
struct video_window *This = impl_from_IVideoWindow(iface); struct video_window *window = impl_from_IVideoWindow(iface);
RECT defaultRect; RECT rect;
TRACE("(%p/%p)->(%p, %p)\n", This, iface, pWidth, pHeight); TRACE("window %p, width %p, height %p.\n", window, width, height);
defaultRect = This->baseWindow.pFuncsTable->pfnGetDefaultRect(&This->baseWindow);
*pWidth = defaultRect.right - defaultRect.left;
*pHeight = defaultRect.bottom - defaultRect.top;
rect = window->ops->get_default_rect(window);
*width = rect.right - rect.left;
*height = rect.bottom - rect.top;
return S_OK; return S_OK;
} }
@ -747,3 +661,30 @@ void video_window_unregister_class(void)
if (!UnregisterClassW(class_name, NULL) && GetLastError() != ERROR_CLASS_DOES_NOT_EXIST) if (!UnregisterClassW(class_name, NULL) && GetLastError() != ERROR_CLASS_DOES_NOT_EXIST)
ERR("Failed to unregister class, error %u.\n", GetLastError()); ERR("Failed to unregister class, error %u.\n", GetLastError());
} }
HRESULT video_window_init(struct video_window *window, const IVideoWindowVtbl *vtbl,
struct strmbase_filter *owner, struct strmbase_pin *pin, const struct video_window_ops *ops)
{
memset(window, 0, sizeof(*window));
window->ops = ops;
window->IVideoWindow_iface.lpVtbl = vtbl;
window->AutoShow = OATRUE;
window->pFilter = owner;
window->pPin = pin;
return S_OK;
}
void video_window_cleanup(struct video_window *window)
{
if (window->hwnd)
{
/* Media Player Classic deadlocks if WM_PARENTNOTIFY is sent, so clear
* the child style first. Just like Windows, we don't actually unparent
* the window, to prevent extra focus events from being generated since
* it would become top-level for a brief period before being destroyed. */
SetWindowLongW(window->hwnd, GWL_STYLE, GetWindowLongW(window->hwnd, GWL_STYLE) & ~WS_CHILD);
SendMessageW(window->hwnd, WM_CLOSE, 0, 0);
window->hwnd = NULL;
}
}