fix baseline build (old cairo) - 'cairo_rectangle_int_t' does not name a type
[LibreOffice.git] / avmedia / source / win / player.cxx
bloba1f7e44d2c253ae501bf0b710e2f21a578814056
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 #include <uuids.h>
28 #include <evcode.h>
29 #ifdef _WIN32_WINNT_WINBLUE
30 #include <VersionHelpers.h>
31 #endif
32 #if defined _MSC_VER
33 #pragma warning(pop)
34 #endif
36 #include "player.hxx"
37 #include "framegrabber.hxx"
38 #include "window.hxx"
39 #include <cppuhelper/supportsservice.hxx>
41 #define AVMEDIA_WIN_PLAYER_IMPLEMENTATIONNAME "com.sun.star.comp.avmedia.Player_DirectX"
42 #define AVMEDIA_WIN_PLAYER_SERVICENAME "com.sun.star.media.Player_DirectX"
44 using namespace ::com::sun::star;
46 namespace avmedia { namespace win {
48 LRESULT CALLBACK MediaPlayerWndProc_2( HWND hWnd,UINT nMsg, WPARAM nPar1, LPARAM nPar2 )
50 Player* pPlayer = (Player*) ::GetWindowLong( hWnd, 0 );
51 bool bProcessed = true;
53 if( pPlayer )
55 switch( nMsg )
57 case( WM_GRAPHNOTIFY ):
58 pPlayer->processEvent();
59 break;
60 default:
61 bProcessed = false;
62 break;
65 else
66 bProcessed = false;
68 return( bProcessed ? 0 : DefWindowProc( hWnd, nMsg, nPar1, nPar2 ) );
72 bool isWindowsVistaOrHigher()
74 // the Win32 SDK 8.1 deprecates GetVersionEx()
75 #ifdef _WIN32_WINNT_WINBLUE
76 return IsWindowsVistaOrGreater() ? true : false;
77 #else
78 // POST: return true if we are at least on Windows Vista
79 OSVERSIONINFO osvi;
80 ZeroMemory(&osvi, sizeof(osvi));
81 osvi.dwOSVersionInfoSize = sizeof(osvi);
82 GetVersionEx(&osvi);
83 return osvi.dwMajorVersion >= 6;
84 #endif
88 // - Player -
91 Player::Player( const uno::Reference< lang::XMultiServiceFactory >& rxMgr ) :
92 Player_BASE(m_aMutex),
93 mxMgr( rxMgr ),
94 mpGB( NULL ),
95 mpOMF( NULL ),
96 mpMC( NULL ),
97 mpME( NULL ),
98 mpMS( NULL ),
99 mpMP( NULL ),
100 mpBA( NULL ),
101 mpBV( NULL ),
102 mpVW( NULL ),
103 mpEV( NULL ),
104 mnUnmutedVolume( 0 ),
105 mnFrameWnd( 0 ),
106 mbMuted( false ),
107 mbLooping( false ),
108 mbAddWindow( true )
110 ::CoInitialize( NULL );
113 Player::~Player()
115 if( mnFrameWnd )
116 ::DestroyWindow( (HWND) mnFrameWnd );
118 ::CoUninitialize();
121 void SAL_CALL Player::disposing()
123 ::osl::MutexGuard aGuard(m_aMutex);
124 stop();
125 if( mpBA )
126 mpBA->Release();
128 if( mpBV )
129 mpBV->Release();
131 if( mpVW )
132 mpVW->Release();
134 if( mpMP )
135 mpMP->Release();
137 if( mpMS )
138 mpMS->Release();
140 if( mpME )
142 mpME->SetNotifyWindow( 0, WM_GRAPHNOTIFY, 0);
143 mpME->Release();
146 if( mpMC )
147 mpMC->Release();
149 if( mpEV )
150 mpEV->Release();
152 if( mpOMF )
153 mpOMF->Release();
155 if( mpGB )
156 mpGB->Release();
159 bool Player::create( const OUString& rURL )
161 HRESULT hR;
162 bool bRet = false;
164 if( SUCCEEDED( hR = CoCreateInstance( CLSID_FilterGraph, NULL, CLSCTX_INPROC_SERVER, IID_IGraphBuilder, (void**) &mpGB ) ) )
166 // Don't use the overlay mixer on Windows Vista
167 // It disables the desktop composition as soon as RenderFile is called
168 // also causes some other problems: video rendering is not reliable
169 if( !isWindowsVistaOrHigher() && SUCCEEDED( CoCreateInstance( CLSID_OverlayMixer, NULL, CLSCTX_INPROC_SERVER, IID_IBaseFilter, (void**) &mpOMF ) ) )
171 mpGB->AddFilter( mpOMF, L"com_sun_star_media_OverlayMixerFilter" );
173 if( !SUCCEEDED( mpOMF->QueryInterface( IID_IDDrawExclModeVideo, (void**) &mpEV ) ) )
174 mpEV = NULL;
177 if( SUCCEEDED( hR = mpGB->RenderFile( reinterpret_cast<LPCWSTR>(rURL.getStr()), NULL ) ) &&
178 SUCCEEDED( hR = mpGB->QueryInterface( IID_IMediaControl, (void**) &mpMC ) ) &&
179 SUCCEEDED( hR = mpGB->QueryInterface( IID_IMediaEventEx, (void**) &mpME ) ) &&
180 SUCCEEDED( hR = mpGB->QueryInterface( IID_IMediaSeeking, (void**) &mpMS ) ) &&
181 SUCCEEDED( hR = mpGB->QueryInterface( IID_IMediaPosition, (void**) &mpMP ) ) )
183 // Video interfaces
184 mpGB->QueryInterface( IID_IVideoWindow, (void**) &mpVW );
185 mpGB->QueryInterface( IID_IBasicVideo, (void**) &mpBV );
187 // Audio interface
188 mpGB->QueryInterface( IID_IBasicAudio, (void**) &mpBA );
190 if( mpBA )
191 mpBA->put_Volume( mnUnmutedVolume );
193 bRet = true;
197 if( bRet )
198 maURL = rURL;
199 else
200 maURL.clear();
202 return bRet;
205 const IVideoWindow* Player::getVideoWindow() const
207 return mpVW;
210 void Player::setNotifyWnd( int nNotifyWnd )
212 mbAddWindow = false;
213 if( mpME )
214 mpME->SetNotifyWindow( (OAHWND) nNotifyWnd, WM_GRAPHNOTIFY, reinterpret_cast< LONG_PTR>( this ) );
217 long Player::processEvent()
219 long nCode;
220 LONG_PTR nParam1, nParam2;
222 while( mpME && SUCCEEDED( mpME->GetEvent( &nCode, &nParam1, &nParam2, 0 ) ) )
224 if( EC_COMPLETE == nCode )
226 if( mbLooping )
228 setMediaTime( 0.0 );
229 start();
231 else
233 setMediaTime( getDuration() );
234 stop();
238 mpME->FreeEventParams( nCode, nParam1, nParam2 );
241 return 0;
244 void SAL_CALL Player::start( )
245 throw (uno::RuntimeException)
247 ::osl::MutexGuard aGuard(m_aMutex);
248 if( mpMC )
250 if ( mbAddWindow )
252 static WNDCLASS* mpWndClass = NULL;
253 if ( !mpWndClass )
255 mpWndClass = new WNDCLASS;
257 memset( mpWndClass, 0, sizeof( *mpWndClass ) );
258 mpWndClass->hInstance = GetModuleHandle( NULL );
259 mpWndClass->cbWndExtra = sizeof( DWORD );
260 mpWndClass->lpfnWndProc = MediaPlayerWndProc_2;
261 mpWndClass->lpszClassName = "com_sun_star_media_Sound_Player";
262 mpWndClass->hbrBackground = (HBRUSH) ::GetStockObject( BLACK_BRUSH );
263 mpWndClass->hCursor = ::LoadCursor( NULL, IDC_ARROW );
265 ::RegisterClass( mpWndClass );
267 if ( !mnFrameWnd )
269 mnFrameWnd = (int) ::CreateWindow( mpWndClass->lpszClassName, NULL,
271 0, 0, 0, 0,
272 (HWND) NULL, NULL, mpWndClass->hInstance, 0 );
273 if ( mnFrameWnd )
275 ::ShowWindow((HWND) mnFrameWnd, SW_HIDE);
276 ::SetWindowLong( (HWND) mnFrameWnd, 0, (DWORD) this );
277 // mpVW->put_Owner( (OAHWND) mnFrameWnd );
278 setNotifyWnd( mnFrameWnd );
283 mpMC->Run();
287 void SAL_CALL Player::stop( )
288 throw (uno::RuntimeException)
290 ::osl::MutexGuard aGuard(m_aMutex);
291 if( mpMC )
292 mpMC->Stop();
295 sal_Bool SAL_CALL Player::isPlaying()
296 throw (uno::RuntimeException)
298 ::osl::MutexGuard aGuard(m_aMutex);
300 OAFilterState eFilterState;
301 bool bRet = false;
303 if( mpMC && SUCCEEDED( mpMC->GetState( 10, &eFilterState ) ) )
304 bRet = ( State_Running == eFilterState );
306 return bRet;
309 double SAL_CALL Player::getDuration( )
310 throw (uno::RuntimeException)
312 ::osl::MutexGuard aGuard(m_aMutex);
314 REFTIME aRefTime( 0.0 );
316 if( mpMP )
317 mpMP->get_Duration( &aRefTime );
319 return aRefTime;
322 void SAL_CALL Player::setMediaTime( double fTime )
323 throw (uno::RuntimeException)
325 ::osl::MutexGuard aGuard(m_aMutex);
327 if( mpMP )
329 const bool bPlaying = isPlaying();
331 mpMP->put_CurrentPosition( fTime );
333 if( !bPlaying && mpMC )
334 mpMC->StopWhenReady();
338 double SAL_CALL Player::getMediaTime( )
339 throw (uno::RuntimeException)
341 ::osl::MutexGuard aGuard(m_aMutex);
343 REFTIME aRefTime( 0.0 );
345 if( mpMP )
346 mpMP->get_CurrentPosition( &aRefTime );
348 return aRefTime;
351 void SAL_CALL Player::setPlaybackLoop( sal_Bool bSet )
352 throw (uno::RuntimeException)
354 ::osl::MutexGuard aGuard(m_aMutex);
356 mbLooping = bSet;
359 sal_Bool SAL_CALL Player::isPlaybackLoop( )
360 throw (uno::RuntimeException)
362 ::osl::MutexGuard aGuard(m_aMutex);
364 return mbLooping;
367 void SAL_CALL Player::setMute( sal_Bool bSet )
368 throw (uno::RuntimeException)
370 ::osl::MutexGuard aGuard(m_aMutex);
372 if (mpBA && (mbMuted != static_cast<bool>(bSet)))
374 mbMuted = bSet;
375 mpBA->put_Volume( mbMuted ? -10000 : mnUnmutedVolume );
379 sal_Bool SAL_CALL Player::isMute( )
380 throw (uno::RuntimeException)
382 ::osl::MutexGuard aGuard(m_aMutex);
384 return mbMuted;
387 void SAL_CALL Player::setVolumeDB( sal_Int16 nVolumeDB )
388 throw (uno::RuntimeException)
390 ::osl::MutexGuard aGuard(m_aMutex);
392 mnUnmutedVolume = static_cast< long >( nVolumeDB ) * 100;
394 if( !mbMuted && mpBA )
395 mpBA->put_Volume( mnUnmutedVolume );
398 sal_Int16 SAL_CALL Player::getVolumeDB( )
399 throw (uno::RuntimeException)
401 ::osl::MutexGuard aGuard(m_aMutex);
403 return( static_cast< sal_Int16 >( mnUnmutedVolume / 100 ) );
406 awt::Size SAL_CALL Player::getPreferredPlayerWindowSize( )
407 throw (uno::RuntimeException)
409 ::osl::MutexGuard aGuard(m_aMutex);
411 awt::Size aSize( 0, 0 );
413 if( mpBV )
415 long nWidth = 0, nHeight = 0;
417 mpBV->GetVideoSize( &nWidth, &nHeight );
418 aSize.Width = nWidth;
419 aSize.Height = nHeight;
422 return aSize;
425 uno::Reference< ::media::XPlayerWindow > SAL_CALL Player::createPlayerWindow( const uno::Sequence< uno::Any >& aArguments )
426 throw (uno::RuntimeException)
428 ::osl::MutexGuard aGuard(m_aMutex);
430 uno::Reference< ::media::XPlayerWindow > xRet;
431 awt::Size aSize( getPreferredPlayerWindowSize() );
433 if( mpVW && aSize.Width > 0 && aSize.Height > 0 )
435 ::avmedia::win::Window* pWindow = new ::avmedia::win::Window( mxMgr, *this );
437 xRet = pWindow;
439 if( !pWindow->create( aArguments ) )
440 xRet = uno::Reference< ::media::XPlayerWindow >();
443 return xRet;
446 uno::Reference< media::XFrameGrabber > SAL_CALL Player::createFrameGrabber( )
447 throw (uno::RuntimeException)
449 uno::Reference< media::XFrameGrabber > xRet;
451 if( !maURL.isEmpty() )
453 FrameGrabber* pGrabber = new FrameGrabber( mxMgr );
455 xRet = pGrabber;
457 if( !pGrabber->create( maURL ) )
458 xRet.clear();
461 return xRet;
464 OUString SAL_CALL Player::getImplementationName( )
465 throw (uno::RuntimeException)
467 return OUString( AVMEDIA_WIN_PLAYER_IMPLEMENTATIONNAME );
470 sal_Bool SAL_CALL Player::supportsService( const OUString& ServiceName )
471 throw (uno::RuntimeException)
473 return cppu::supportsService(this, ServiceName);
476 uno::Sequence< OUString > SAL_CALL Player::getSupportedServiceNames( )
477 throw (uno::RuntimeException)
479 uno::Sequence< OUString > aRet(1);
480 aRet[0] = AVMEDIA_WIN_PLAYER_SERVICENAME ;
482 return aRet;
485 } // namespace win
486 } // namespace avmedia
488 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */