xref: /trunk/main/avmedia/source/framework/soundhandler.cxx (revision cdf0e10c4e3984b49a9502b011690b615761d4a3)
1*cdf0e10cSrcweir /*************************************************************************
2*cdf0e10cSrcweir  *
3*cdf0e10cSrcweir  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4*cdf0e10cSrcweir  *
5*cdf0e10cSrcweir  * Copyright 2000, 2010 Oracle and/or its affiliates.
6*cdf0e10cSrcweir  *
7*cdf0e10cSrcweir  * OpenOffice.org - a multi-platform office productivity suite
8*cdf0e10cSrcweir  *
9*cdf0e10cSrcweir  * This file is part of OpenOffice.org.
10*cdf0e10cSrcweir  *
11*cdf0e10cSrcweir  * OpenOffice.org is free software: you can redistribute it and/or modify
12*cdf0e10cSrcweir  * it under the terms of the GNU Lesser General Public License version 3
13*cdf0e10cSrcweir  * only, as published by the Free Software Foundation.
14*cdf0e10cSrcweir  *
15*cdf0e10cSrcweir  * OpenOffice.org is distributed in the hope that it will be useful,
16*cdf0e10cSrcweir  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17*cdf0e10cSrcweir  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18*cdf0e10cSrcweir  * GNU Lesser General Public License version 3 for more details
19*cdf0e10cSrcweir  * (a copy is included in the LICENSE file that accompanied this code).
20*cdf0e10cSrcweir  *
21*cdf0e10cSrcweir  * You should have received a copy of the GNU Lesser General Public License
22*cdf0e10cSrcweir  * version 3 along with OpenOffice.org.  If not, see
23*cdf0e10cSrcweir  * <http://www.openoffice.org/license.html>
24*cdf0e10cSrcweir  * for a copy of the LGPLv3 License.
25*cdf0e10cSrcweir  *
26*cdf0e10cSrcweir  ************************************************************************/
27*cdf0e10cSrcweir 
28*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
29*cdf0e10cSrcweir //  my own includes
30*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
31*cdf0e10cSrcweir 
32*cdf0e10cSrcweir #ifndef __FRAMEWORK_DISPATCH_SOUNDHANDLER_HXX_
33*cdf0e10cSrcweir #include "soundhandler.hxx"
34*cdf0e10cSrcweir #endif
35*cdf0e10cSrcweir 
36*cdf0e10cSrcweir #ifndef __COMPHELPER_MEDIADESCRIPTOR_HXX_
37*cdf0e10cSrcweir #include <comphelper/mediadescriptor.hxx>
38*cdf0e10cSrcweir #endif
39*cdf0e10cSrcweir 
40*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
41*cdf0e10cSrcweir //  interface includes
42*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
43*cdf0e10cSrcweir #include <com/sun/star/io/XInputStream.hpp>
44*cdf0e10cSrcweir #include <com/sun/star/frame/DispatchResultState.hpp>
45*cdf0e10cSrcweir 
46*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
47*cdf0e10cSrcweir //  includes of other projects
48*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
49*cdf0e10cSrcweir #include <comphelper/sequenceashashmap.hxx>
50*cdf0e10cSrcweir #include <rtl/ustrbuf.hxx>
51*cdf0e10cSrcweir 
52*cdf0e10cSrcweir #include <cppuhelper/typeprovider.hxx>
53*cdf0e10cSrcweir #include <cppuhelper/factory.hxx>
54*cdf0e10cSrcweir 
55*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
56*cdf0e10cSrcweir //  namespace
57*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
58*cdf0e10cSrcweir 
59*cdf0e10cSrcweir namespace avmedia{
60*cdf0e10cSrcweir 
61*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
62*cdf0e10cSrcweir //  non exported const
63*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
64*cdf0e10cSrcweir 
65*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
66*cdf0e10cSrcweir //  non exported definitions
67*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
68*cdf0e10cSrcweir 
69*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
70*cdf0e10cSrcweir //  declarations
71*cdf0e10cSrcweir //_________________________________________________________________________________________________________________
72*cdf0e10cSrcweir 
73*cdf0e10cSrcweir //*****************************************************************************************************************
74*cdf0e10cSrcweir //  XInterface, XTypeProvider, XServiceInfo
75*cdf0e10cSrcweir //*****************************************************************************************************************
76*cdf0e10cSrcweir 
77*cdf0e10cSrcweir void SAL_CALL SoundHandler::acquire() throw()
78*cdf0e10cSrcweir {
79*cdf0e10cSrcweir        /* Don't use mutex in methods of XInterface! */
80*cdf0e10cSrcweir        OWeakObject::acquire();
81*cdf0e10cSrcweir }
82*cdf0e10cSrcweir 
83*cdf0e10cSrcweir void SAL_CALL SoundHandler::release() throw()
84*cdf0e10cSrcweir {
85*cdf0e10cSrcweir        /* Don't use mutex in methods of XInterface! */
86*cdf0e10cSrcweir        OWeakObject::release();
87*cdf0e10cSrcweir }
88*cdf0e10cSrcweir 
89*cdf0e10cSrcweir css::uno::Any SAL_CALL SoundHandler::queryInterface( const css::uno::Type& aType ) throw( css::uno::RuntimeException )
90*cdf0e10cSrcweir {
91*cdf0e10cSrcweir        /* Attention: Don't use mutex or guard in this method!!! Is a method of XInterface.     */
92*cdf0e10cSrcweir         /* Ask for my own supported interfaces ...*/
93*cdf0e10cSrcweir        css::uno::Any aReturn( ::cppu::queryInterface( aType,
94*cdf0e10cSrcweir                static_cast< css::lang::XTypeProvider* >(this),
95*cdf0e10cSrcweir                static_cast< css::lang::XServiceInfo* >(this),
96*cdf0e10cSrcweir                static_cast< css::frame::XNotifyingDispatch* >(this),
97*cdf0e10cSrcweir                static_cast< css::frame::XDispatch* >(this),
98*cdf0e10cSrcweir                static_cast< css::document::XExtendedFilterDetection* >(this)));
99*cdf0e10cSrcweir        /* If searched interface not supported by this class ... */
100*cdf0e10cSrcweir        if ( aReturn.hasValue() == sal_False )
101*cdf0e10cSrcweir        {
102*cdf0e10cSrcweir                /* ... ask baseclass for interfaces! */
103*cdf0e10cSrcweir                aReturn = OWeakObject::queryInterface( aType );
104*cdf0e10cSrcweir        }
105*cdf0e10cSrcweir         /* Return result of this search. */
106*cdf0e10cSrcweir        return aReturn;
107*cdf0e10cSrcweir }
108*cdf0e10cSrcweir 
109*cdf0e10cSrcweir css::uno::Sequence< sal_Int8 > SAL_CALL SoundHandler::getImplementationId() throw( css::uno::RuntimeException )
110*cdf0e10cSrcweir {
111*cdf0e10cSrcweir     /* Create one Id for all instances of this class.                                               */
112*cdf0e10cSrcweir     /* Use ethernet address to do this! (sal_True)                                                  */
113*cdf0e10cSrcweir     /* Optimize this method                                                                         */
114*cdf0e10cSrcweir     /* We initialize a static variable only one time. And we don't must use a mutex at every call!  */
115*cdf0e10cSrcweir     /* For the first call; pID is NULL - for the second call pID is different from NULL!            */
116*cdf0e10cSrcweir     static ::cppu::OImplementationId* pID = NULL ;
117*cdf0e10cSrcweir     if ( pID == NULL )
118*cdf0e10cSrcweir     {
119*cdf0e10cSrcweir         /* Ready for multithreading; get global mutex for first call of this method only! see before   */
120*cdf0e10cSrcweir         ::osl::MutexGuard aGuard( ::osl::Mutex::getGlobalMutex() );
121*cdf0e10cSrcweir         /* Control these pointer again ... it can be, that another instance will be faster then these! */
122*cdf0e10cSrcweir         if ( pID == NULL )
123*cdf0e10cSrcweir         {
124*cdf0e10cSrcweir             /* Create a new static ID ... */
125*cdf0e10cSrcweir             static ::cppu::OImplementationId aID( sal_False );
126*cdf0e10cSrcweir             /* ... and set his address to static pointer! */
127*cdf0e10cSrcweir             pID = &aID ;
128*cdf0e10cSrcweir         }
129*cdf0e10cSrcweir     }
130*cdf0e10cSrcweir     return pID->getImplementationId();
131*cdf0e10cSrcweir }
132*cdf0e10cSrcweir 
133*cdf0e10cSrcweir css::uno::Sequence< css::uno::Type > SAL_CALL SoundHandler::getTypes() throw( css::uno::RuntimeException )
134*cdf0e10cSrcweir {
135*cdf0e10cSrcweir     /* Optimize this method !                                       */
136*cdf0e10cSrcweir     /* We initialize a static variable only one time.               */
137*cdf0e10cSrcweir     /* And we don't must use a mutex at every call!                 */
138*cdf0e10cSrcweir     /* For the first call; pTypeCollection is NULL -                */
139*cdf0e10cSrcweir     /* for the second call pTypeCollection is different from NULL!  */
140*cdf0e10cSrcweir     static ::cppu::OTypeCollection* pTypeCollection = NULL ;
141*cdf0e10cSrcweir     if ( pTypeCollection == NULL )
142*cdf0e10cSrcweir     {
143*cdf0e10cSrcweir         /* Ready for multithreading; get global mutex for first call of this method only! see before   */
144*cdf0e10cSrcweir         ::osl::MutexGuard aGuard( ::osl::Mutex::getGlobalMutex() );
145*cdf0e10cSrcweir         /* Control these pointer again ... it can be, that another instance will be faster then these! */
146*cdf0e10cSrcweir         if ( pTypeCollection == NULL )
147*cdf0e10cSrcweir         {
148*cdf0e10cSrcweir             /* Create a static typecollection ...           */
149*cdf0e10cSrcweir             static ::cppu::OTypeCollection aTypeCollection
150*cdf0e10cSrcweir                 (
151*cdf0e10cSrcweir                     ::getCppuType(( const ::com::sun::star::uno::Reference< css::lang::XTypeProvider >*)NULL ),
152*cdf0e10cSrcweir                     ::getCppuType(( const ::com::sun::star::uno::Reference< css::lang::XServiceInfo >*)NULL ),
153*cdf0e10cSrcweir                     ::getCppuType(( const ::com::sun::star::uno::Reference< css::frame::XNotifyingDispatch >*)NULL ),
154*cdf0e10cSrcweir                     ::getCppuType(( const ::com::sun::star::uno::Reference< css::frame::XDispatch >*)NULL ),
155*cdf0e10cSrcweir                     ::getCppuType(( const ::com::sun::star::uno::Reference< css::document::XExtendedFilterDetection >*)NULL )
156*cdf0e10cSrcweir                 );
157*cdf0e10cSrcweir             /* ... and set his address to static pointer! */
158*cdf0e10cSrcweir             pTypeCollection = &aTypeCollection ;
159*cdf0e10cSrcweir         }
160*cdf0e10cSrcweir     }
161*cdf0e10cSrcweir     return pTypeCollection->getTypes();
162*cdf0e10cSrcweir }
163*cdf0e10cSrcweir 
164*cdf0e10cSrcweir #define DECLARE_ASCII( SASCIIVALUE ) \
165*cdf0e10cSrcweir         ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( SASCIIVALUE ) )
166*cdf0e10cSrcweir 
167*cdf0e10cSrcweir #define IMPLEMENTATIONNAME_SOUNDHANDLER DECLARE_ASCII("com.sun.star.comp.framework.SoundHandler")
168*cdf0e10cSrcweir #define SERVICENAME_CONTENTHANDLER DECLARE_ASCII("com.sun.star.frame.ContentHandler")
169*cdf0e10cSrcweir 
170*cdf0e10cSrcweir /*===========================================================================================================*/
171*cdf0e10cSrcweir /* XServiceInfo */
172*cdf0e10cSrcweir /*===========================================================================================================*/
173*cdf0e10cSrcweir ::rtl::OUString SAL_CALL SoundHandler::getImplementationName() throw( css::uno::RuntimeException )
174*cdf0e10cSrcweir {
175*cdf0e10cSrcweir     return impl_getStaticImplementationName();
176*cdf0e10cSrcweir }
177*cdf0e10cSrcweir 
178*cdf0e10cSrcweir /*===========================================================================================================*/
179*cdf0e10cSrcweir /* XServiceInfo */
180*cdf0e10cSrcweir /*===========================================================================================================*/
181*cdf0e10cSrcweir sal_Bool SAL_CALL SoundHandler::supportsService( const ::rtl::OUString& sServiceName ) throw( css::uno::RuntimeException )
182*cdf0e10cSrcweir {
183*cdf0e10cSrcweir     /* Set default return value. */
184*cdf0e10cSrcweir     sal_Bool bReturn = sal_False ;
185*cdf0e10cSrcweir     /* Get names of all supported servicenames. */
186*cdf0e10cSrcweir     css::uno::Sequence< ::rtl::OUString >  seqServiceNames =   getSupportedServiceNames();
187*cdf0e10cSrcweir     const ::rtl::OUString*                 pArray          =   seqServiceNames.getConstArray();
188*cdf0e10cSrcweir     sal_Int32                              nCounter        =   0;
189*cdf0e10cSrcweir     sal_Int32                              nLength         =   seqServiceNames.getLength();
190*cdf0e10cSrcweir     /* Search for right name in list. */
191*cdf0e10cSrcweir     while   (
192*cdf0e10cSrcweir               ( nCounter      <       nLength         )       &&
193*cdf0e10cSrcweir               ( bReturn       ==      sal_False       )
194*cdf0e10cSrcweir             )
195*cdf0e10cSrcweir     {
196*cdf0e10cSrcweir         /* Is name was found, say "YES, SERVICE IS SUPPORTED." and break loop. */
197*cdf0e10cSrcweir         if ( pArray[nCounter] == sServiceName )
198*cdf0e10cSrcweir         {
199*cdf0e10cSrcweir             bReturn = sal_True ;
200*cdf0e10cSrcweir         }
201*cdf0e10cSrcweir         /* Else step to next element in list. */
202*cdf0e10cSrcweir         ++nCounter;
203*cdf0e10cSrcweir     }
204*cdf0e10cSrcweir     /* Return state of search. */
205*cdf0e10cSrcweir     return bReturn;
206*cdf0e10cSrcweir }
207*cdf0e10cSrcweir 
208*cdf0e10cSrcweir /*===========================================================================================================*/
209*cdf0e10cSrcweir /* XServiceInfo */
210*cdf0e10cSrcweir /*===========================================================================================================*/
211*cdf0e10cSrcweir css::uno::Sequence< ::rtl::OUString > SAL_CALL SoundHandler::getSupportedServiceNames() throw( css::uno::RuntimeException )
212*cdf0e10cSrcweir {
213*cdf0e10cSrcweir     return impl_getStaticSupportedServiceNames();
214*cdf0e10cSrcweir }
215*cdf0e10cSrcweir 
216*cdf0e10cSrcweir /*===========================================================================================================*/
217*cdf0e10cSrcweir /* Helper for XServiceInfo                                                                                   */
218*cdf0e10cSrcweir /*===========================================================================================================*/
219*cdf0e10cSrcweir css::uno::Sequence< ::rtl::OUString > SoundHandler::impl_getStaticSupportedServiceNames()
220*cdf0e10cSrcweir {
221*cdf0e10cSrcweir     css::uno::Sequence< ::rtl::OUString > seqServiceNames( 1 );
222*cdf0e10cSrcweir     seqServiceNames.getArray() [0] = SERVICENAME_CONTENTHANDLER;
223*cdf0e10cSrcweir     return seqServiceNames;
224*cdf0e10cSrcweir }
225*cdf0e10cSrcweir 
226*cdf0e10cSrcweir /*===========================================================================================================*/
227*cdf0e10cSrcweir /* Helper for XServiceInfo */
228*cdf0e10cSrcweir /*===========================================================================================================*/
229*cdf0e10cSrcweir ::rtl::OUString SoundHandler::impl_getStaticImplementationName()
230*cdf0e10cSrcweir {
231*cdf0e10cSrcweir     return IMPLEMENTATIONNAME_SOUNDHANDLER;
232*cdf0e10cSrcweir }
233*cdf0e10cSrcweir 
234*cdf0e10cSrcweir css::uno::Reference< css::uno::XInterface > SAL_CALL SoundHandler::impl_createInstance( const css::uno::Reference< css::lang::XMultiServiceFactory >& xServiceManager ) throw( css::uno::Exception )
235*cdf0e10cSrcweir {
236*cdf0e10cSrcweir     /* create new instance of service */
237*cdf0e10cSrcweir     SoundHandler* pClass = new SoundHandler( xServiceManager );
238*cdf0e10cSrcweir     /* hold it alive by increasing his ref count!!! */
239*cdf0e10cSrcweir     css::uno::Reference< css::uno::XInterface > xService( static_cast< ::cppu::OWeakObject* >(pClass), css::uno::UNO_QUERY );
240*cdf0e10cSrcweir     /* initialize new service instance ... he can use his own refcount ... we hold it! */
241*cdf0e10cSrcweir     pClass->impl_initService();
242*cdf0e10cSrcweir     /* return new created service as reference */
243*cdf0e10cSrcweir     return xService;
244*cdf0e10cSrcweir }
245*cdf0e10cSrcweir 
246*cdf0e10cSrcweir css::uno::Reference< css::lang::XSingleServiceFactory > SoundHandler::impl_createFactory( const css::uno::Reference< css::lang::XMultiServiceFactory >& xServiceManager )
247*cdf0e10cSrcweir {
248*cdf0e10cSrcweir     css::uno::Reference< css::lang::XSingleServiceFactory > xReturn ( cppu::createSingleFactory (
249*cdf0e10cSrcweir        xServiceManager,
250*cdf0e10cSrcweir         SoundHandler::impl_getStaticImplementationName(),
251*cdf0e10cSrcweir         SoundHandler::impl_createInstance,
252*cdf0e10cSrcweir         SoundHandler::impl_getStaticSupportedServiceNames()
253*cdf0e10cSrcweir         )
254*cdf0e10cSrcweir     );
255*cdf0e10cSrcweir     return xReturn;
256*cdf0e10cSrcweir }
257*cdf0e10cSrcweir 
258*cdf0e10cSrcweir void SAL_CALL SoundHandler::impl_initService()
259*cdf0e10cSrcweir {
260*cdf0e10cSrcweir }
261*cdf0e10cSrcweir 
262*cdf0e10cSrcweir 
263*cdf0e10cSrcweir /*-************************************************************************************************************//**
264*cdf0e10cSrcweir     @short      standard ctor
265*cdf0e10cSrcweir     @descr      These initialize a new instance of this class with needed informations for work.
266*cdf0e10cSrcweir 
267*cdf0e10cSrcweir     @seealso    using at owner
268*cdf0e10cSrcweir 
269*cdf0e10cSrcweir     @param      "xFactory", reference to service manager for creation of new services
270*cdf0e10cSrcweir     @return     -
271*cdf0e10cSrcweir 
272*cdf0e10cSrcweir     @onerror    Show an assertion and do nothing else.
273*cdf0e10cSrcweir     @threadsafe yes
274*cdf0e10cSrcweir *//*-*************************************************************************************************************/
275*cdf0e10cSrcweir SoundHandler::SoundHandler( const css::uno::Reference< css::lang::XMultiServiceFactory >& xFactory )
276*cdf0e10cSrcweir         //  Init baseclasses first
277*cdf0e10cSrcweir         :   ThreadHelpBase      (          )
278*cdf0e10cSrcweir         ,   ::cppu::OWeakObject (          )
279*cdf0e10cSrcweir         // Init member
280*cdf0e10cSrcweir     ,   m_bError        ( false    )
281*cdf0e10cSrcweir         ,   m_xFactory          ( xFactory )
282*cdf0e10cSrcweir {
283*cdf0e10cSrcweir     m_aUpdateTimer.SetTimeoutHdl(LINK(this, SoundHandler, implts_PlayerNotify));
284*cdf0e10cSrcweir }
285*cdf0e10cSrcweir 
286*cdf0e10cSrcweir /*-************************************************************************************************************//**
287*cdf0e10cSrcweir     @short      standard dtor
288*cdf0e10cSrcweir     @descr      -
289*cdf0e10cSrcweir 
290*cdf0e10cSrcweir     @seealso    -
291*cdf0e10cSrcweir 
292*cdf0e10cSrcweir     @param      -
293*cdf0e10cSrcweir     @return     -
294*cdf0e10cSrcweir 
295*cdf0e10cSrcweir     @onerror    -
296*cdf0e10cSrcweir     @threadsafe -
297*cdf0e10cSrcweir *//*-*************************************************************************************************************/
298*cdf0e10cSrcweir SoundHandler::~SoundHandler()
299*cdf0e10cSrcweir {
300*cdf0e10cSrcweir     if (m_xListener.is())
301*cdf0e10cSrcweir     {
302*cdf0e10cSrcweir         css::frame::DispatchResultEvent aEvent;
303*cdf0e10cSrcweir         aEvent.State = css::frame::DispatchResultState::FAILURE;
304*cdf0e10cSrcweir         m_xListener->dispatchFinished(aEvent);
305*cdf0e10cSrcweir         m_xListener = css::uno::Reference< css::frame::XDispatchResultListener >();
306*cdf0e10cSrcweir     }
307*cdf0e10cSrcweir }
308*cdf0e10cSrcweir 
309*cdf0e10cSrcweir /*-************************************************************************************************************//**
310*cdf0e10cSrcweir     @interface  ::com::sun::star::frame::XDispatch
311*cdf0e10cSrcweir 
312*cdf0e10cSrcweir     @short      try to load audio file
313*cdf0e10cSrcweir     @descr      This method try to load given audio file by URL and play it. We use vcl/Sound class to do that.
314*cdf0e10cSrcweir                 Playing of sound is asynchron everytime.
315*cdf0e10cSrcweir 
316*cdf0e10cSrcweir     @attention  We must hold us alive by ourself ... because we use async. vcl sound player ... but playing is started
317*cdf0e10cSrcweir                 in async interface call "dispatch()" too. And caller forget us imediatly. But then our uno ref count
318*cdf0e10cSrcweir                 will decreased to 0 and will die. The only solution is to use own reference to our implementation.
319*cdf0e10cSrcweir                 But we do it for realy started jobs only and release it during call back of vcl.
320*cdf0e10cSrcweir 
321*cdf0e10cSrcweir     @seealso    class vcl/Sound
322*cdf0e10cSrcweir     @seealso    method implts_PlayerNotify()
323*cdf0e10cSrcweir 
324*cdf0e10cSrcweir     @param      "aURL"      , URL to dispatch.
325*cdf0e10cSrcweir     @param      "lArguments", list of optional arguments.
326*cdf0e10cSrcweir     @return     -
327*cdf0e10cSrcweir 
328*cdf0e10cSrcweir     @onerror    We do nothing.
329*cdf0e10cSrcweir     @threadsafe yes
330*cdf0e10cSrcweir *//*-*************************************************************************************************************/
331*cdf0e10cSrcweir void SAL_CALL SoundHandler::dispatchWithNotification(const css::util::URL&                                             aURL      ,
332*cdf0e10cSrcweir                                                      const css::uno::Sequence< css::beans::PropertyValue >&            lDescriptor,
333*cdf0e10cSrcweir                                                      const css::uno::Reference< css::frame::XDispatchResultListener >& xListener ) throw(css::uno::RuntimeException)
334*cdf0e10cSrcweir {
335*cdf0e10cSrcweir     // SAFE {
336*cdf0e10cSrcweir     const ::vos::OGuard aLock( m_aLock );
337*cdf0e10cSrcweir 
338*cdf0e10cSrcweir     {
339*cdf0e10cSrcweir     //close streams otherwise on windows we can't reopen the file in the
340*cdf0e10cSrcweir     //media player when we pass the url to directx as it'll already be open
341*cdf0e10cSrcweir         ::comphelper::MediaDescriptor aDescriptor(lDescriptor);
342*cdf0e10cSrcweir 
343*cdf0e10cSrcweir     css::uno::Reference< css::io::XInputStream > xInputStream =
344*cdf0e10cSrcweir         aDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_INPUTSTREAM(),
345*cdf0e10cSrcweir         css::uno::Reference< css::io::XInputStream >());
346*cdf0e10cSrcweir     if (xInputStream.is()) xInputStream->closeInput();
347*cdf0e10cSrcweir     }
348*cdf0e10cSrcweir 
349*cdf0e10cSrcweir     // If player currently used for other dispatch() requests ...
350*cdf0e10cSrcweir     // cancel it by calling stop()!
351*cdf0e10cSrcweir     m_aUpdateTimer.Stop();
352*cdf0e10cSrcweir     if (m_xPlayer.is())
353*cdf0e10cSrcweir     {
354*cdf0e10cSrcweir         if (m_xPlayer->isPlaying())
355*cdf0e10cSrcweir             m_xPlayer->stop();
356*cdf0e10cSrcweir         m_xPlayer.clear();
357*cdf0e10cSrcweir     }
358*cdf0e10cSrcweir 
359*cdf0e10cSrcweir     // Try to initialize player.
360*cdf0e10cSrcweir     m_xListener = xListener;
361*cdf0e10cSrcweir     try
362*cdf0e10cSrcweir     {
363*cdf0e10cSrcweir         m_bError = false;
364*cdf0e10cSrcweir         m_xPlayer.set( avmedia::MediaWindow::createPlayer( aURL.Complete ), css::uno::UNO_QUERY_THROW );
365*cdf0e10cSrcweir         // OK- we can start async playing ...
366*cdf0e10cSrcweir         // Count this request and initialize self-holder against dieing by uno ref count ...
367*cdf0e10cSrcweir         m_xSelfHold = css::uno::Reference< css::uno::XInterface >(static_cast< ::cppu::OWeakObject* >(this), css::uno::UNO_QUERY);
368*cdf0e10cSrcweir         m_xPlayer->start();
369*cdf0e10cSrcweir         m_aUpdateTimer.SetTimeout( 200 );
370*cdf0e10cSrcweir         m_aUpdateTimer.Start();
371*cdf0e10cSrcweir     }
372*cdf0e10cSrcweir     catch( css::uno::Exception& e )
373*cdf0e10cSrcweir     {
374*cdf0e10cSrcweir         m_bError = true;
375*cdf0e10cSrcweir         (void)e;
376*cdf0e10cSrcweir         m_xPlayer.clear();
377*cdf0e10cSrcweir     }
378*cdf0e10cSrcweir 
379*cdf0e10cSrcweir     // } SAFE
380*cdf0e10cSrcweir }
381*cdf0e10cSrcweir 
382*cdf0e10cSrcweir void SAL_CALL SoundHandler::dispatch( const css::util::URL&                                  aURL       ,
383*cdf0e10cSrcweir                                       const css::uno::Sequence< css::beans::PropertyValue >& lArguments ) throw( css::uno::RuntimeException )
384*cdf0e10cSrcweir {
385*cdf0e10cSrcweir     dispatchWithNotification(aURL, lArguments, css::uno::Reference< css::frame::XDispatchResultListener >());
386*cdf0e10cSrcweir }
387*cdf0e10cSrcweir 
388*cdf0e10cSrcweir /*-************************************************************************************************************//**
389*cdf0e10cSrcweir     @interface  ::com::sun::star::document::XExtendedFilterDetection
390*cdf0e10cSrcweir 
391*cdf0e10cSrcweir     @short      try to detect file (given as argument included in "lDescriptor")
392*cdf0e10cSrcweir     @descr      We try to detect, if given file could be handled by this class and is a well known one.
393*cdf0e10cSrcweir                 If it is - we return right internal type name - otherwise we return nothing!
394*cdf0e10cSrcweir                 So call can search for another detect service and ask him too.
395*cdf0e10cSrcweir 
396*cdf0e10cSrcweir     @attention  a) We don't need any mutex here ... because we don't use any member!
397*cdf0e10cSrcweir                 b) Dont' use internal player instance "m_pPlayer" to detect given sound file!
398*cdf0e10cSrcweir                    It's not neccessary to do that ... and we can use temp. variable to do the same.
399*cdf0e10cSrcweir                    This way is easy - we don't must synchronize it with currently played sounds!
400*cdf0e10cSrcweir                    Another reason to do so ... We are a listener on our internal ma_Player object.
401*cdf0e10cSrcweir                    If you would call "IsSoundFile()" on this instance, he would call us back and
402*cdf0e10cSrcweir                    we make some uneccssary things ...
403*cdf0e10cSrcweir 
404*cdf0e10cSrcweir     @seealso    -
405*cdf0e10cSrcweir 
406*cdf0e10cSrcweir     @param      "lDescriptor", description of file to detect
407*cdf0e10cSrcweir     @return     Internal type name which match this file ... or nothing if it is unknown.
408*cdf0e10cSrcweir 
409*cdf0e10cSrcweir     @onerror    We return nothing.
410*cdf0e10cSrcweir     @threadsafe yes
411*cdf0e10cSrcweir *//*-*************************************************************************************************************/
412*cdf0e10cSrcweir ::rtl::OUString SAL_CALL SoundHandler::detect( css::uno::Sequence< css::beans::PropertyValue >& lDescriptor ) throw( css::uno::RuntimeException )
413*cdf0e10cSrcweir {
414*cdf0e10cSrcweir     // Our default is "nothing". So we can return it, if detection failed or fily type is realy unknown.
415*cdf0e10cSrcweir     ::rtl::OUString sTypeName;
416*cdf0e10cSrcweir 
417*cdf0e10cSrcweir     // Analyze given descriptor to find filename or input stream or ...
418*cdf0e10cSrcweir     ::comphelper::MediaDescriptor aDescriptor(lDescriptor);
419*cdf0e10cSrcweir     ::rtl::OUString               sURL       = aDescriptor.getUnpackedValueOrDefault(::comphelper::MediaDescriptor::PROP_URL(), ::rtl::OUString());
420*cdf0e10cSrcweir 
421*cdf0e10cSrcweir     if (
422*cdf0e10cSrcweir         (sURL.getLength()           ) &&
423*cdf0e10cSrcweir         (avmedia::MediaWindow::isMediaURL(sURL))
424*cdf0e10cSrcweir        )
425*cdf0e10cSrcweir     {
426*cdf0e10cSrcweir         // If the file type is supported depends on the OS, so...
427*cdf0e10cSrcweir         // I think we can the following ones:
428*cdf0e10cSrcweir         //  a) look for given extension of url to map our type decision HARD CODED!!!
429*cdf0e10cSrcweir         //  b) return preferred type every time... it's easy :-)
430*cdf0e10cSrcweir         sTypeName = ::rtl::OUString::createFromAscii("wav_Wave_Audio_File");
431*cdf0e10cSrcweir         aDescriptor[::comphelper::MediaDescriptor::PROP_TYPENAME()] <<= sTypeName;
432*cdf0e10cSrcweir         aDescriptor >> lDescriptor;
433*cdf0e10cSrcweir     }
434*cdf0e10cSrcweir 
435*cdf0e10cSrcweir     // Return our decision.
436*cdf0e10cSrcweir     return sTypeName;
437*cdf0e10cSrcweir }
438*cdf0e10cSrcweir 
439*cdf0e10cSrcweir /*-************************************************************************************************************//**
440*cdf0e10cSrcweir     @short      call back of sound player
441*cdf0e10cSrcweir     @descr      Our player call us back to give us some informations.
442*cdf0e10cSrcweir                 We use this informations to callback our might existing listener.
443*cdf0e10cSrcweir 
444*cdf0e10cSrcweir     @seealso    method dispatchWithNotification()
445*cdf0e10cSrcweir 
446*cdf0e10cSrcweir     @param      -
447*cdf0e10cSrcweir     @return     0 everytime ... it doesnt matter for us.
448*cdf0e10cSrcweir 
449*cdf0e10cSrcweir     @onerror    -
450*cdf0e10cSrcweir     @threadsafe yes
451*cdf0e10cSrcweir *//*-*************************************************************************************************************/
452*cdf0e10cSrcweir IMPL_LINK( SoundHandler, implts_PlayerNotify, void*, EMPTYARG )
453*cdf0e10cSrcweir {
454*cdf0e10cSrcweir     // SAFE {
455*cdf0e10cSrcweir     ::vos::OClearableGuard aLock( m_aLock );
456*cdf0e10cSrcweir 
457*cdf0e10cSrcweir     if (m_xPlayer.is() && m_xPlayer->isPlaying() && m_xPlayer->getMediaTime() < m_xPlayer->getDuration())
458*cdf0e10cSrcweir     {
459*cdf0e10cSrcweir         m_aUpdateTimer.Start();
460*cdf0e10cSrcweir         return 0L;
461*cdf0e10cSrcweir     }
462*cdf0e10cSrcweir     m_xPlayer.clear();
463*cdf0e10cSrcweir 
464*cdf0e10cSrcweir     // We use m_xSelfHold to let us die ... but we must live till real finishing of this method too!!!
465*cdf0e10cSrcweir     // So we SHOULD use another "self-holder" temp. to provide that ...
466*cdf0e10cSrcweir     css::uno::Reference< css::uno::XInterface > xOperationHold = m_xSelfHold;
467*cdf0e10cSrcweir     m_xSelfHold = css::uno::Reference< css::uno::XInterface >();
468*cdf0e10cSrcweir 
469*cdf0e10cSrcweir     // notify might existing listener
470*cdf0e10cSrcweir     // And forget this listener!
471*cdf0e10cSrcweir     // Because the corresponding dispatch was finished.
472*cdf0e10cSrcweir     if (m_xListener.is())
473*cdf0e10cSrcweir     {
474*cdf0e10cSrcweir         css::frame::DispatchResultEvent aEvent;
475*cdf0e10cSrcweir         if (!m_bError)
476*cdf0e10cSrcweir             aEvent.State = css::frame::DispatchResultState::SUCCESS;
477*cdf0e10cSrcweir         else
478*cdf0e10cSrcweir             aEvent.State = css::frame::DispatchResultState::FAILURE;
479*cdf0e10cSrcweir         m_xListener->dispatchFinished(aEvent);
480*cdf0e10cSrcweir         m_xListener = css::uno::Reference< css::frame::XDispatchResultListener >();
481*cdf0e10cSrcweir     }
482*cdf0e10cSrcweir 
483*cdf0e10cSrcweir     // } SAFE
484*cdf0e10cSrcweir     //release aLock before end of method at which point xOperationHold goes out of scope and pThis dies
485*cdf0e10cSrcweir     aLock.clear();
486*cdf0e10cSrcweir     return 0;
487*cdf0e10cSrcweir }
488*cdf0e10cSrcweir 
489*cdf0e10cSrcweir } // namespace framework
490*cdf0e10cSrcweir 
491*cdf0e10cSrcweir // ------------------------------------------
492*cdf0e10cSrcweir // - component_getImplementationEnvironment -
493*cdf0e10cSrcweir // ------------------------------------------
494*cdf0e10cSrcweir 
495*cdf0e10cSrcweir extern "C" void SAL_CALL component_getImplementationEnvironment( const sal_Char ** ppEnvTypeName, uno_Environment ** /*ppEnv*/ )
496*cdf0e10cSrcweir {
497*cdf0e10cSrcweir        *ppEnvTypeName = CPPU_CURRENT_LANGUAGE_BINDING_NAME;
498*cdf0e10cSrcweir }
499*cdf0e10cSrcweir 
500*cdf0e10cSrcweir // ------------------------
501*cdf0e10cSrcweir // - component_getFactory -
502*cdf0e10cSrcweir // ------------------------
503*cdf0e10cSrcweir 
504*cdf0e10cSrcweir extern "C" void* SAL_CALL component_getFactory(const sal_Char* pImplementationName, void* pServiceManager, void* /*pRegistryKey*/ )
505*cdf0e10cSrcweir {
506*cdf0e10cSrcweir     void* pReturn = NULL;
507*cdf0e10cSrcweir     if  (pServiceManager !=  NULL )
508*cdf0e10cSrcweir     {
509*cdf0e10cSrcweir         /* Define variables which are used in following macros. */
510*cdf0e10cSrcweir         css::uno::Reference< ::com::sun::star::lang::XSingleServiceFactory > xFactory;
511*cdf0e10cSrcweir         css::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory > xServiceManager;
512*cdf0e10cSrcweir             xServiceManager = reinterpret_cast< ::com::sun::star::lang::XMultiServiceFactory* >( pServiceManager )  ;
513*cdf0e10cSrcweir 
514*cdf0e10cSrcweir         if ( avmedia::SoundHandler::impl_getStaticImplementationName().equals( ::rtl::OUString::createFromAscii( pImplementationName ) ) )
515*cdf0e10cSrcweir             xFactory = avmedia::SoundHandler::impl_createFactory( xServiceManager );
516*cdf0e10cSrcweir 
517*cdf0e10cSrcweir         if ( xFactory.is() == sal_True )
518*cdf0e10cSrcweir         {
519*cdf0e10cSrcweir             xFactory->acquire();
520*cdf0e10cSrcweir             pReturn = xFactory.get();
521*cdf0e10cSrcweir         }
522*cdf0e10cSrcweir     }
523*cdf0e10cSrcweir     /* Return with result of this operation. */
524*cdf0e10cSrcweir     return pReturn;
525*cdf0e10cSrcweir }
526