fix baseline build (old cairo) - 'cairo_rectangle_int_t' does not name a type
[LibreOffice.git] / avmedia / source / win / window.cxx
blobc6823db8cd56c1390f9ed13e5f6c36fae4210ca1
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #if defined _MSC_VER
21 #pragma warning(push, 1)
22 #pragma warning(disable: 4917)
23 #endif
24 #include <objbase.h>
25 #include <strmif.h>
26 #include <control.h>
27 #define STRSAFE_NO_DEPRECATE
28 #include <dshow.h>
29 #if defined _MSC_VER
30 #pragma warning(pop)
31 #endif
32 #include <com/sun/star/awt/SystemPointer.hpp>
33 #include <cppuhelper/supportsservice.hxx>
35 #include "window.hxx"
36 #include "player.hxx"
38 #define AVMEDIA_WIN_WINDOW_IMPLEMENTATIONNAME "com.sun.star.comp.avmedia.Window_DirectX"
39 #define AVMEDIA_WIN_WINDOW_SERVICENAME "com.sun.star.media.Window_DirectX"
41 using namespace ::com::sun::star;
43 namespace avmedia { namespace win {
45 static ::osl::Mutex& ImplGetOwnStaticMutex()
47 static ::osl::Mutex* pMutex = NULL;
49 if( pMutex == NULL )
51 ::osl::MutexGuard aGuard( ::osl::Mutex::getGlobalMutex() );
53 if( pMutex == NULL )
55 static ::osl::Mutex aMutex;
56 pMutex = &aMutex;
60 return *pMutex;
63 LRESULT CALLBACK MediaPlayerWndProc( HWND hWnd,UINT nMsg, WPARAM nPar1, LPARAM nPar2 )
65 Window* pWindow = (Window*) ::GetWindowLong( hWnd, 0 );
66 bool bProcessed = true;
68 if( pWindow )
70 switch( nMsg )
72 case( WM_SETCURSOR ):
73 pWindow->updatePointer();
74 break;
76 case( WM_GRAPHNOTIFY ):
77 pWindow->processGraphEvent();
78 break;
80 case( WM_MOUSEMOVE ):
81 case( WM_LBUTTONDOWN ):
82 case( WM_MBUTTONDOWN ):
83 case( WM_RBUTTONDOWN ):
84 case( WM_LBUTTONUP ):
85 case( WM_MBUTTONUP ):
86 case( WM_RBUTTONUP ):
88 awt::MouseEvent aUNOEvt;
89 POINT aWinPoint;
91 if( !::GetCursorPos( &aWinPoint ) || !::ScreenToClient( hWnd, &aWinPoint ) )
93 aWinPoint.x = GET_X_LPARAM( nPar2 );
94 aWinPoint.y = GET_Y_LPARAM( nPar2 );
96 aUNOEvt.Modifiers = 0;
97 aUNOEvt.Buttons = 0;
98 aUNOEvt.X = aWinPoint.x;
99 aUNOEvt.Y = aWinPoint.y;
100 aUNOEvt.PopupTrigger = false;
102 // Modifiers
103 if( nPar1 & MK_SHIFT )
104 aUNOEvt.Modifiers |= awt::KeyModifier::SHIFT;
106 if( nPar1 & MK_CONTROL )
107 aUNOEvt.Modifiers |= awt::KeyModifier::MOD1;
109 // Buttons
110 if( WM_LBUTTONDOWN == nMsg || WM_LBUTTONUP == nMsg )
111 aUNOEvt.Buttons |= awt::MouseButton::LEFT;
113 if( WM_MBUTTONDOWN == nMsg || WM_MBUTTONUP == nMsg )
114 aUNOEvt.Buttons |= awt::MouseButton::MIDDLE;
116 if( WM_RBUTTONDOWN == nMsg || WM_RBUTTONUP == nMsg )
117 aUNOEvt.Buttons |= awt::MouseButton::RIGHT;
119 // event type
120 if( WM_LBUTTONDOWN == nMsg ||
121 WM_MBUTTONDOWN == nMsg ||
122 WM_RBUTTONDOWN == nMsg )
124 aUNOEvt.ClickCount = 1;
125 pWindow->fireMousePressedEvent( aUNOEvt );
127 else if( WM_LBUTTONUP == nMsg ||
128 WM_MBUTTONUP == nMsg ||
129 WM_RBUTTONUP == nMsg )
131 aUNOEvt.ClickCount = 1;
132 pWindow->fireMouseReleasedEvent( aUNOEvt );
134 else if( WM_MOUSEMOVE == nMsg )
136 aUNOEvt.ClickCount = 0;
137 pWindow->fireMouseMovedEvent( aUNOEvt );
138 pWindow->updatePointer();
141 break;
143 case( WM_SETFOCUS ):
145 const awt::FocusEvent aUNOEvt;
146 pWindow->fireSetFocusEvent( aUNOEvt );
148 break;
150 default:
151 bProcessed = false;
152 break;
155 else
156 bProcessed = false;
158 return( bProcessed ? 0 : DefWindowProc( hWnd, nMsg, nPar1, nPar2 ) );
161 WNDCLASS* lcl_getWndClass()
163 static WNDCLASS* s_pWndClass = NULL;
164 if ( !s_pWndClass )
166 s_pWndClass = new WNDCLASS;
168 memset( s_pWndClass, 0, sizeof( *s_pWndClass ) );
169 s_pWndClass->hInstance = GetModuleHandle( NULL );
170 s_pWndClass->cbWndExtra = sizeof( DWORD );
171 s_pWndClass->lpfnWndProc = MediaPlayerWndProc;
172 s_pWndClass->lpszClassName = "com_sun_star_media_PlayerWnd";
173 s_pWndClass->hbrBackground = (HBRUSH) ::GetStockObject( BLACK_BRUSH );
174 s_pWndClass->hCursor = ::LoadCursor( NULL, IDC_ARROW );
176 ::RegisterClass( s_pWndClass );
178 return s_pWndClass;
181 Window::Window( const uno::Reference< lang::XMultiServiceFactory >& rxMgr, Player& rPlayer ) :
182 mxMgr( rxMgr ),
183 mrPlayer( rPlayer ),
184 meZoomLevel( media::ZoomLevel_NOT_AVAILABLE ),
185 mnParentWnd( 0 ),
186 mnFrameWnd( 0 ),
187 maListeners( maMutex ),
188 mnPointerType( awt::SystemPointer::ARROW )
190 ::osl::MutexGuard aGuard( ImplGetOwnStaticMutex() );
192 lcl_getWndClass();
195 Window::~Window()
197 if( mnFrameWnd )
198 ::DestroyWindow( (HWND) mnFrameWnd );
201 void Window::ImplLayoutVideoWindow()
203 if( media::ZoomLevel_NOT_AVAILABLE != meZoomLevel )
205 awt::Size aPrefSize( mrPlayer.getPreferredPlayerWindowSize() );
206 awt::Rectangle aRect = getPosSize();
207 int nW = aRect.Width, nH = aRect.Height;
208 int nVideoW = nW, nVideoH = nH;
209 int nX = 0, nY = 0, nWidth = 0, nHeight = 0;
210 bool bDone = false, bZoom = false;
212 if( media::ZoomLevel_ORIGINAL == meZoomLevel )
214 bZoom = true;
216 else if( media::ZoomLevel_ZOOM_1_TO_4 == meZoomLevel )
218 aPrefSize.Width >>= 2;
219 aPrefSize.Height >>= 2;
220 bZoom = true;
222 else if( media::ZoomLevel_ZOOM_1_TO_2 == meZoomLevel )
224 aPrefSize.Width >>= 1;
225 aPrefSize.Height >>= 1;
226 bZoom = true;
228 else if( media::ZoomLevel_ZOOM_2_TO_1 == meZoomLevel )
230 aPrefSize.Width <<= 1;
231 aPrefSize.Height <<= 1;
232 bZoom = true;
234 else if( media::ZoomLevel_ZOOM_4_TO_1 == meZoomLevel )
236 aPrefSize.Width <<= 2;
237 aPrefSize.Height <<= 2;
238 bZoom = true;
240 else if( media::ZoomLevel_FIT_TO_WINDOW == meZoomLevel )
242 nWidth = nVideoW;
243 nHeight = nVideoH;
244 bDone = true;
247 if( bZoom )
249 if( ( aPrefSize.Width <= nVideoW ) && ( aPrefSize.Height <= nVideoH ) )
251 nX = ( nVideoW - aPrefSize.Width ) >> 1;
252 nY = ( nVideoH - aPrefSize.Height ) >> 1;
253 nWidth = aPrefSize.Width;
254 nHeight = aPrefSize.Height;
255 bDone = true;
259 if( !bDone )
261 if( aPrefSize.Width > 0 && aPrefSize.Height > 0 && nVideoW > 0 && nVideoH > 0 )
263 double fPrefWH = (double) aPrefSize.Width / aPrefSize.Height;
265 if( fPrefWH < ( (double) nVideoW / nVideoH ) )
266 nVideoW = (int)( nVideoH * fPrefWH );
267 else
268 nVideoH = (int)( nVideoW / fPrefWH );
270 nX = ( nW - nVideoW ) >> 1;
271 nY = ( nH - nVideoH ) >> 1;
272 nWidth = nVideoW;
273 nHeight = nVideoH;
275 else
276 nX = nY = nWidth = nHeight = 0;
279 IVideoWindow* pVideoWindow = const_cast< IVideoWindow* >( mrPlayer.getVideoWindow() );
281 if( pVideoWindow )
282 pVideoWindow->SetWindowPosition( nX, nY, nWidth, nHeight );
286 bool Window::create( const uno::Sequence< uno::Any >& rArguments )
288 IVideoWindow* pVideoWindow = const_cast< IVideoWindow* >( mrPlayer.getVideoWindow() );
289 WNDCLASS* mpWndClass = lcl_getWndClass();
291 if( !mnFrameWnd && pVideoWindow && mpWndClass )
293 awt::Rectangle aRect;
294 sal_IntPtr nWnd;
296 rArguments[ 0 ] >>= nWnd;
297 rArguments[ 1 ] >>= aRect;
299 mnParentWnd = static_cast<int>(nWnd);
301 mnFrameWnd = (int) ::CreateWindow( mpWndClass->lpszClassName, NULL,
302 WS_VISIBLE | WS_CHILD | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
303 aRect.X, aRect.Y, aRect.Width, aRect.Height,
304 (HWND) mnParentWnd, NULL, mpWndClass->hInstance, 0 );
306 if( mnFrameWnd )
308 ::SetWindowLong( (HWND) mnFrameWnd, 0, (DWORD) this );
310 pVideoWindow->put_Owner( (OAHWND) mnFrameWnd );
311 pVideoWindow->put_MessageDrain( (OAHWND) mnFrameWnd );
312 pVideoWindow->put_WindowStyle( WS_VISIBLE | WS_CHILD | WS_CLIPSIBLINGS | WS_CLIPCHILDREN );
314 mrPlayer.setNotifyWnd( mnFrameWnd );
316 meZoomLevel = media::ZoomLevel_FIT_TO_WINDOW;
317 ImplLayoutVideoWindow();
321 return( mnFrameWnd != 0 );
324 void Window::processGraphEvent()
326 mrPlayer.processEvent();
329 void Window::updatePointer()
331 char* pCursorName;
333 switch( mnPointerType )
335 case( awt::SystemPointer::CROSS ): pCursorName = IDC_CROSS; break;
336 case( awt::SystemPointer::MOVE ): pCursorName = IDC_SIZEALL; break;
337 case( awt::SystemPointer::WAIT ): pCursorName = IDC_WAIT; break;
339 default:
340 pCursorName = IDC_ARROW;
341 break;
344 ::SetCursor( ::LoadCursor( NULL, pCursorName ) );
347 void SAL_CALL Window::update( )
348 throw (uno::RuntimeException)
350 ::RedrawWindow( (HWND) mnFrameWnd, NULL, NULL, RDW_ALLCHILDREN | RDW_INVALIDATE | RDW_UPDATENOW | RDW_ERASE );
353 sal_Bool SAL_CALL Window::setZoomLevel( media::ZoomLevel eZoomLevel )
354 throw (uno::RuntimeException)
356 boolean bRet = false;
358 if( media::ZoomLevel_NOT_AVAILABLE != meZoomLevel &&
359 media::ZoomLevel_NOT_AVAILABLE != eZoomLevel )
361 if( eZoomLevel != meZoomLevel )
363 meZoomLevel = eZoomLevel;
364 ImplLayoutVideoWindow();
367 bRet = true;
370 return bRet;
373 media::ZoomLevel SAL_CALL Window::getZoomLevel( )
374 throw (uno::RuntimeException)
376 return meZoomLevel;
379 void SAL_CALL Window::setPointerType( sal_Int32 nPointerType )
380 throw (uno::RuntimeException)
382 mnPointerType = nPointerType;
385 void SAL_CALL Window::setPosSize( sal_Int32 X, sal_Int32 Y, sal_Int32 Width, sal_Int32 Height, sal_Int16 )
386 throw (uno::RuntimeException)
388 if( mnFrameWnd )
390 ::SetWindowPos( (HWND) mnFrameWnd, HWND_TOP, X, Y, Width, Height, 0 );
391 ImplLayoutVideoWindow();
395 awt::Rectangle SAL_CALL Window::getPosSize()
396 throw (uno::RuntimeException)
398 awt::Rectangle aRet;
400 if( mnFrameWnd )
402 ::RECT aWndRect;
404 if( ::GetClientRect( (HWND) mnFrameWnd, &aWndRect ) )
406 aRet.X = aWndRect.left;
407 aRet.Y = aWndRect.top;
408 aRet.Width = aWndRect.right - aWndRect.left + 1;
409 aRet.Height = aWndRect.bottom - aWndRect.top + 1;
413 return aRet;
416 void SAL_CALL Window::setVisible( sal_Bool bVisible )
417 throw (uno::RuntimeException)
419 if( mnFrameWnd )
421 IVideoWindow* pVideoWindow = const_cast< IVideoWindow* >( mrPlayer.getVideoWindow() );
423 if( pVideoWindow )
424 pVideoWindow->put_Visible( bVisible ? OATRUE : OAFALSE );
426 ::ShowWindow( (HWND) mnFrameWnd, bVisible ? SW_SHOW : SW_HIDE );
430 void SAL_CALL Window::setEnable( sal_Bool bEnable )
431 throw (uno::RuntimeException)
433 if( mnFrameWnd )
434 ::EnableWindow( (HWND) mnFrameWnd, bEnable );
437 void SAL_CALL Window::setFocus( )
438 throw (uno::RuntimeException)
440 if( mnFrameWnd )
441 ::SetFocus( (HWND) mnFrameWnd );
444 void SAL_CALL Window::addWindowListener( const uno::Reference< awt::XWindowListener >& xListener )
445 throw (uno::RuntimeException)
447 maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
450 void SAL_CALL Window::removeWindowListener( const uno::Reference< awt::XWindowListener >& xListener )
451 throw (uno::RuntimeException)
453 maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
456 void SAL_CALL Window::addFocusListener( const uno::Reference< awt::XFocusListener >& xListener )
457 throw (uno::RuntimeException)
459 maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
462 void SAL_CALL Window::removeFocusListener( const uno::Reference< awt::XFocusListener >& xListener )
463 throw (uno::RuntimeException)
465 maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
468 void SAL_CALL Window::addKeyListener( const uno::Reference< awt::XKeyListener >& xListener )
469 throw (uno::RuntimeException)
471 maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
474 void SAL_CALL Window::removeKeyListener( const uno::Reference< awt::XKeyListener >& xListener )
475 throw (uno::RuntimeException)
477 maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
480 void SAL_CALL Window::addMouseListener( const uno::Reference< awt::XMouseListener >& xListener )
481 throw (uno::RuntimeException)
483 maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
486 void SAL_CALL Window::removeMouseListener( const uno::Reference< awt::XMouseListener >& xListener )
487 throw (uno::RuntimeException)
489 maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
492 void SAL_CALL Window::addMouseMotionListener( const uno::Reference< awt::XMouseMotionListener >& xListener )
493 throw (uno::RuntimeException)
495 maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
498 void SAL_CALL Window::removeMouseMotionListener( const uno::Reference< awt::XMouseMotionListener >& xListener )
499 throw (uno::RuntimeException)
501 maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
504 void SAL_CALL Window::addPaintListener( const uno::Reference< awt::XPaintListener >& xListener )
505 throw (uno::RuntimeException)
507 maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
510 void SAL_CALL Window::removePaintListener( const uno::Reference< awt::XPaintListener >& xListener )
511 throw (uno::RuntimeException)
513 maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
516 void SAL_CALL Window::dispose( )
517 throw (uno::RuntimeException)
521 void SAL_CALL Window::addEventListener( const uno::Reference< lang::XEventListener >& xListener )
522 throw (uno::RuntimeException)
524 maListeners.addInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
527 void SAL_CALL Window::removeEventListener( const uno::Reference< lang::XEventListener >& xListener )
528 throw (uno::RuntimeException)
530 maListeners.removeInterface( cppu::UnoType<decltype(xListener)>::get(), xListener );
533 void Window::fireMousePressedEvent( const ::com::sun::star::awt::MouseEvent& rEvt )
535 ::cppu::OInterfaceContainerHelper* pContainer = maListeners.getContainer( cppu::UnoType<awt::XMouseListener>::get());
537 if( pContainer )
539 ::cppu::OInterfaceIteratorHelper aIter( *pContainer );
541 while( aIter.hasMoreElements() )
542 uno::Reference< awt::XMouseListener >( aIter.next(), uno::UNO_QUERY )->mousePressed( rEvt );
546 void Window::fireMouseReleasedEvent( const ::com::sun::star::awt::MouseEvent& rEvt )
548 ::cppu::OInterfaceContainerHelper* pContainer = maListeners.getContainer( cppu::UnoType<awt::XMouseListener>::get());
550 if( pContainer )
552 ::cppu::OInterfaceIteratorHelper aIter( *pContainer );
554 while( aIter.hasMoreElements() )
555 uno::Reference< awt::XMouseListener >( aIter.next(), uno::UNO_QUERY )->mouseReleased( rEvt );
559 void Window::fireMouseMovedEvent( const ::com::sun::star::awt::MouseEvent& rEvt )
561 ::cppu::OInterfaceContainerHelper* pContainer = maListeners.getContainer( cppu::UnoType<awt::XMouseMotionListener>::get());
563 if( pContainer )
565 ::cppu::OInterfaceIteratorHelper aIter( *pContainer );
567 while( aIter.hasMoreElements() )
568 uno::Reference< awt::XMouseMotionListener >( aIter.next(), uno::UNO_QUERY )->mouseMoved( rEvt );
572 void Window::fireSetFocusEvent( const ::com::sun::star::awt::FocusEvent& rEvt )
574 ::cppu::OInterfaceContainerHelper* pContainer = maListeners.getContainer( cppu::UnoType<awt::XFocusListener>::get());
576 if( pContainer )
578 ::cppu::OInterfaceIteratorHelper aIter( *pContainer );
580 while( aIter.hasMoreElements() )
581 uno::Reference< awt::XFocusListener >( aIter.next(), uno::UNO_QUERY )->focusGained( rEvt );
585 OUString SAL_CALL Window::getImplementationName( )
586 throw (uno::RuntimeException)
588 return OUString( AVMEDIA_WIN_WINDOW_IMPLEMENTATIONNAME );
591 sal_Bool SAL_CALL Window::supportsService( const OUString& ServiceName )
592 throw (uno::RuntimeException)
594 return cppu::supportsService(this, ServiceName);
597 uno::Sequence< OUString > SAL_CALL Window::getSupportedServiceNames( )
598 throw (uno::RuntimeException)
600 uno::Sequence< OUString > aRet(1);
601 aRet[0] = AVMEDIA_WIN_WINDOW_SERVICENAME ;
603 return aRet;
606 } // namespace win
607 } // namespace avmedia
609 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */