1*d119d52dSAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3*d119d52dSAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4*d119d52dSAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5*d119d52dSAndrew Rist  * distributed with this work for additional information
6*d119d52dSAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7*d119d52dSAndrew Rist  * to you under the Apache License, Version 2.0 (the
8*d119d52dSAndrew Rist  * "License"); you may not use this file except in compliance
9*d119d52dSAndrew Rist  * with the License.  You may obtain a copy of the License at
10*d119d52dSAndrew Rist  *
11*d119d52dSAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12*d119d52dSAndrew Rist  *
13*d119d52dSAndrew Rist  * Unless required by applicable law or agreed to in writing,
14*d119d52dSAndrew Rist  * software distributed under the License is distributed on an
15*d119d52dSAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*d119d52dSAndrew Rist  * KIND, either express or implied.  See the License for the
17*d119d52dSAndrew Rist  * specific language governing permissions and limitations
18*d119d52dSAndrew Rist  * under the License.
19*d119d52dSAndrew Rist  *
20*d119d52dSAndrew Rist  *************************************************************/
21*d119d52dSAndrew Rist 
22*d119d52dSAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_sfx2.hxx"
26cdf0e10cSrcweir #include "sfx2/sfxmodelfactory.hxx"
27cdf0e10cSrcweir 
28cdf0e10cSrcweir /** === begin UNO includes === **/
29cdf0e10cSrcweir #include <com/sun/star/lang/XServiceInfo.hpp>
30cdf0e10cSrcweir #include <com/sun/star/beans/NamedValue.hpp>
31cdf0e10cSrcweir #include <com/sun/star/lang/XInitialization.hpp>
32cdf0e10cSrcweir /** === end UNO includes === **/
33cdf0e10cSrcweir 
34cdf0e10cSrcweir #include <comphelper/namedvaluecollection.hxx>
35cdf0e10cSrcweir #include <cppuhelper/implbase2.hxx>
36cdf0e10cSrcweir 
37cdf0e10cSrcweir #include <algorithm>
38cdf0e10cSrcweir #include <functional>
39cdf0e10cSrcweir 
40cdf0e10cSrcweir //........................................................................
41cdf0e10cSrcweir namespace sfx2
42cdf0e10cSrcweir {
43cdf0e10cSrcweir //........................................................................
44cdf0e10cSrcweir 
45cdf0e10cSrcweir 	/** === begin UNO using === **/
46cdf0e10cSrcweir 	using ::com::sun::star::uno::Reference;
47cdf0e10cSrcweir 	using ::com::sun::star::uno::XInterface;
48cdf0e10cSrcweir 	using ::com::sun::star::uno::UNO_QUERY;
49cdf0e10cSrcweir 	using ::com::sun::star::uno::UNO_QUERY_THROW;
50cdf0e10cSrcweir 	using ::com::sun::star::uno::UNO_SET_THROW;
51cdf0e10cSrcweir 	using ::com::sun::star::uno::Exception;
52cdf0e10cSrcweir 	using ::com::sun::star::uno::RuntimeException;
53cdf0e10cSrcweir 	using ::com::sun::star::uno::Any;
54cdf0e10cSrcweir 	using ::com::sun::star::uno::makeAny;
55cdf0e10cSrcweir     using ::com::sun::star::lang::XMultiServiceFactory;
56cdf0e10cSrcweir     using ::com::sun::star::uno::Sequence;
57cdf0e10cSrcweir     using ::com::sun::star::lang::XSingleServiceFactory;
58cdf0e10cSrcweir     using ::com::sun::star::lang::XServiceInfo;
59cdf0e10cSrcweir     using ::com::sun::star::beans::NamedValue;
60cdf0e10cSrcweir     using ::com::sun::star::beans::PropertyValue;
61cdf0e10cSrcweir     using ::com::sun::star::lang::XInitialization;
62cdf0e10cSrcweir 	/** === end UNO using === **/
63cdf0e10cSrcweir 
64cdf0e10cSrcweir 	//====================================================================
65cdf0e10cSrcweir 	//= SfxModelFactory - declaration
66cdf0e10cSrcweir 	//====================================================================
67cdf0e10cSrcweir     typedef ::cppu::WeakImplHelper2 <   XSingleServiceFactory
68cdf0e10cSrcweir                                     ,   XServiceInfo
69cdf0e10cSrcweir                                     >   SfxModelFactory_Base;
70cdf0e10cSrcweir     /** implements a XSingleServiceFactory which can be used to created instances
71cdf0e10cSrcweir         of classes derived from SfxBaseModel
72cdf0e10cSrcweir 
73cdf0e10cSrcweir         In opposite to the default implementations from module cppuhelper, this
74cdf0e10cSrcweir         factory evaluates certain creation arguments (passed to createInstanceWithArguments)
75cdf0e10cSrcweir         and passes them to the factory function of the derived class.
76cdf0e10cSrcweir     */
77cdf0e10cSrcweir     class SfxModelFactory : public SfxModelFactory_Base
78cdf0e10cSrcweir 	{
79cdf0e10cSrcweir     public:
80cdf0e10cSrcweir         SfxModelFactory(
81cdf0e10cSrcweir             const Reference< XMultiServiceFactory >& _rxServiceFactory,
82cdf0e10cSrcweir             const ::rtl::OUString& _rImplementationName,
83cdf0e10cSrcweir             const SfxModelFactoryFunc _pComponentFactoryFunc,
84cdf0e10cSrcweir             const Sequence< ::rtl::OUString >& _rServiceNames
85cdf0e10cSrcweir         );
86cdf0e10cSrcweir 
87cdf0e10cSrcweir         // XSingleServiceFactory
88cdf0e10cSrcweir         virtual Reference< XInterface > SAL_CALL createInstance(  ) throw (Exception, RuntimeException);
89cdf0e10cSrcweir         virtual Reference< XInterface > SAL_CALL createInstanceWithArguments( const Sequence< Any >& aArguments ) throw (Exception, RuntimeException);
90cdf0e10cSrcweir 
91cdf0e10cSrcweir         // XServiceInfo
92cdf0e10cSrcweir         virtual ::rtl::OUString SAL_CALL getImplementationName(  ) throw (RuntimeException);
93cdf0e10cSrcweir         virtual ::sal_Bool SAL_CALL supportsService( const ::rtl::OUString& ServiceName ) throw (RuntimeException);
94cdf0e10cSrcweir         virtual Sequence< ::rtl::OUString > SAL_CALL getSupportedServiceNames(  ) throw (RuntimeException);
95cdf0e10cSrcweir 
96cdf0e10cSrcweir     protected:
97cdf0e10cSrcweir         virtual ~SfxModelFactory();
98cdf0e10cSrcweir 
99cdf0e10cSrcweir     private:
100cdf0e10cSrcweir         Reference< XInterface > impl_createInstance( const sal_uInt64 _nCreationFlags ) const;
101cdf0e10cSrcweir 
102cdf0e10cSrcweir     private:
103cdf0e10cSrcweir         const Reference< XMultiServiceFactory >     m_xServiceFactory;
104cdf0e10cSrcweir         const ::rtl::OUString                       m_sImplementationName;
105cdf0e10cSrcweir         const Sequence< ::rtl::OUString >           m_aServiceNames;
106cdf0e10cSrcweir         const SfxModelFactoryFunc                   m_pComponentFactoryFunc;
107cdf0e10cSrcweir 	};
108cdf0e10cSrcweir 
109cdf0e10cSrcweir 	//====================================================================
110cdf0e10cSrcweir 	//= SfxModelFactory - implementation
111cdf0e10cSrcweir 	//====================================================================
112cdf0e10cSrcweir 	//--------------------------------------------------------------------
113cdf0e10cSrcweir     SfxModelFactory::SfxModelFactory( const Reference< XMultiServiceFactory >& _rxServiceFactory,
114cdf0e10cSrcweir             const ::rtl::OUString& _rImplementationName, const SfxModelFactoryFunc _pComponentFactoryFunc,
115cdf0e10cSrcweir             const Sequence< ::rtl::OUString >& _rServiceNames )
116cdf0e10cSrcweir         :m_xServiceFactory( _rxServiceFactory )
117cdf0e10cSrcweir         ,m_sImplementationName( _rImplementationName )
118cdf0e10cSrcweir         ,m_aServiceNames( _rServiceNames )
119cdf0e10cSrcweir         ,m_pComponentFactoryFunc( _pComponentFactoryFunc )
120cdf0e10cSrcweir     {
121cdf0e10cSrcweir     }
122cdf0e10cSrcweir 
123cdf0e10cSrcweir 	//--------------------------------------------------------------------
124cdf0e10cSrcweir     SfxModelFactory::~SfxModelFactory()
125cdf0e10cSrcweir     {
126cdf0e10cSrcweir     }
127cdf0e10cSrcweir 
128cdf0e10cSrcweir     //--------------------------------------------------------------------
129cdf0e10cSrcweir     Reference< XInterface > SfxModelFactory::impl_createInstance( const sal_uInt64 _nCreationFlags ) const
130cdf0e10cSrcweir     {
131cdf0e10cSrcweir         return (*m_pComponentFactoryFunc)( m_xServiceFactory, _nCreationFlags );
132cdf0e10cSrcweir     }
133cdf0e10cSrcweir 
134cdf0e10cSrcweir     //--------------------------------------------------------------------
135cdf0e10cSrcweir     Reference< XInterface > SAL_CALL SfxModelFactory::createInstance(  ) throw (Exception, RuntimeException)
136cdf0e10cSrcweir     {
137cdf0e10cSrcweir         return createInstanceWithArguments( Sequence< Any >() );
138cdf0e10cSrcweir     }
139cdf0e10cSrcweir 
140cdf0e10cSrcweir     //--------------------------------------------------------------------
141cdf0e10cSrcweir     namespace
142cdf0e10cSrcweir     {
143cdf0e10cSrcweir         struct IsSpecialArgument : public ::std::unary_function< Any, bool >
144cdf0e10cSrcweir         {
145cdf0e10cSrcweir             static bool isSpecialArgumentName( const ::rtl::OUString& _rValueName )
146cdf0e10cSrcweir             {
147cdf0e10cSrcweir                 return  _rValueName.equalsAscii( "EmbeddedObject" )
148cdf0e10cSrcweir                     ||  _rValueName.equalsAscii( "EmbeddedScriptSupport" )
149cdf0e10cSrcweir                     ||  _rValueName.equalsAscii( "DocumentRecoverySupport" );
150cdf0e10cSrcweir             }
151cdf0e10cSrcweir 
152cdf0e10cSrcweir             bool operator()( const Any& _rArgument ) const
153cdf0e10cSrcweir             {
154cdf0e10cSrcweir                 NamedValue aNamedValue;
155cdf0e10cSrcweir                 if ( ( _rArgument >>= aNamedValue ) && isSpecialArgumentName( aNamedValue.Name ) )
156cdf0e10cSrcweir                     return true;
157cdf0e10cSrcweir                 PropertyValue aPropertyValue;
158cdf0e10cSrcweir                 if ( ( _rArgument >>= aPropertyValue ) && isSpecialArgumentName( aPropertyValue.Name ) )
159cdf0e10cSrcweir                     return true;
160cdf0e10cSrcweir                 return false;
161cdf0e10cSrcweir             }
162cdf0e10cSrcweir         };
163cdf0e10cSrcweir     }
164cdf0e10cSrcweir 
165cdf0e10cSrcweir     //--------------------------------------------------------------------
166cdf0e10cSrcweir     Reference< XInterface > SAL_CALL SfxModelFactory::createInstanceWithArguments( const Sequence< Any >& _rArguments ) throw (Exception, RuntimeException)
167cdf0e10cSrcweir     {
168cdf0e10cSrcweir         ::comphelper::NamedValueCollection aArgs( _rArguments );
169cdf0e10cSrcweir         const sal_Bool bEmbeddedObject = aArgs.getOrDefault( "EmbeddedObject", sal_False );
170cdf0e10cSrcweir         const sal_Bool bScriptSupport = aArgs.getOrDefault( "EmbeddedScriptSupport", sal_True );
171cdf0e10cSrcweir         const sal_Bool bDocRecoverySupport = aArgs.getOrDefault( "DocumentRecoverySupport", sal_True );
172cdf0e10cSrcweir 
173cdf0e10cSrcweir         sal_uInt64 nCreationFlags =
174cdf0e10cSrcweir                 ( bEmbeddedObject ? SFXMODEL_EMBEDDED_OBJECT : 0 )
175cdf0e10cSrcweir             |   ( bScriptSupport ? 0 : SFXMODEL_DISABLE_EMBEDDED_SCRIPTS )
176cdf0e10cSrcweir             |   ( bDocRecoverySupport ? 0 : SFXMODEL_DISABLE_DOCUMENT_RECOVERY );
177cdf0e10cSrcweir 
178cdf0e10cSrcweir         Reference< XInterface > xInstance( impl_createInstance( nCreationFlags ) );
179cdf0e10cSrcweir 
180cdf0e10cSrcweir         // to mimic the bahaviour of the default factory's createInstanceWithArguments, we initialize
181cdf0e10cSrcweir         // the object with the given arguments, stripped by the three special ones
182cdf0e10cSrcweir         Sequence< Any > aStrippedArguments( _rArguments.getLength() );
183cdf0e10cSrcweir         Any* pStrippedArgs = aStrippedArguments.getArray();
184cdf0e10cSrcweir         Any* pStrippedArgsEnd = ::std::remove_copy_if(
185cdf0e10cSrcweir             _rArguments.getConstArray(),
186cdf0e10cSrcweir             _rArguments.getConstArray() + _rArguments.getLength(),
187cdf0e10cSrcweir             pStrippedArgs,
188cdf0e10cSrcweir             IsSpecialArgument()
189cdf0e10cSrcweir         );
190cdf0e10cSrcweir         aStrippedArguments.realloc( pStrippedArgsEnd - pStrippedArgs );
191cdf0e10cSrcweir 
192cdf0e10cSrcweir         if ( aStrippedArguments.getLength() )
193cdf0e10cSrcweir         {
194cdf0e10cSrcweir             Reference< XInitialization > xModelInit( xInstance, UNO_QUERY );
195cdf0e10cSrcweir             OSL_ENSURE( xModelInit.is(), "SfxModelFactory::createInstanceWithArguments: no XInitialization!" );
196cdf0e10cSrcweir             if ( xModelInit.is() )
197cdf0e10cSrcweir                 xModelInit->initialize( aStrippedArguments );
198cdf0e10cSrcweir         }
199cdf0e10cSrcweir 
200cdf0e10cSrcweir         return xInstance;
201cdf0e10cSrcweir     }
202cdf0e10cSrcweir 
203cdf0e10cSrcweir     //--------------------------------------------------------------------
204cdf0e10cSrcweir     ::rtl::OUString SAL_CALL SfxModelFactory::getImplementationName(  ) throw (RuntimeException)
205cdf0e10cSrcweir     {
206cdf0e10cSrcweir         return m_sImplementationName;
207cdf0e10cSrcweir     }
208cdf0e10cSrcweir 
209cdf0e10cSrcweir     //--------------------------------------------------------------------
210cdf0e10cSrcweir     ::sal_Bool SAL_CALL SfxModelFactory::supportsService( const ::rtl::OUString& _rServiceName ) throw (RuntimeException)
211cdf0e10cSrcweir     {
212cdf0e10cSrcweir         return ::std::find(
213cdf0e10cSrcweir             m_aServiceNames.getConstArray(),
214cdf0e10cSrcweir             m_aServiceNames.getConstArray() + m_aServiceNames.getLength(),
215cdf0e10cSrcweir             _rServiceName
216cdf0e10cSrcweir         )  != m_aServiceNames.getConstArray() + m_aServiceNames.getLength();
217cdf0e10cSrcweir     }
218cdf0e10cSrcweir 
219cdf0e10cSrcweir     //--------------------------------------------------------------------
220cdf0e10cSrcweir     Sequence< ::rtl::OUString > SAL_CALL SfxModelFactory::getSupportedServiceNames(  ) throw (RuntimeException)
221cdf0e10cSrcweir     {
222cdf0e10cSrcweir         return m_aServiceNames;
223cdf0e10cSrcweir     }
224cdf0e10cSrcweir 
225cdf0e10cSrcweir     //--------------------------------------------------------------------
226cdf0e10cSrcweir     Reference< XSingleServiceFactory > createSfxModelFactory( const Reference< XMultiServiceFactory >& _rxServiceFactory,
227cdf0e10cSrcweir             const ::rtl::OUString& _rImplementationName, const SfxModelFactoryFunc _pComponentFactoryFunc,
228cdf0e10cSrcweir             const Sequence< ::rtl::OUString >& _rServiceNames )
229cdf0e10cSrcweir     {
230cdf0e10cSrcweir         return new SfxModelFactory( _rxServiceFactory, _rImplementationName, _pComponentFactoryFunc, _rServiceNames );
231cdf0e10cSrcweir     }
232cdf0e10cSrcweir 
233cdf0e10cSrcweir //........................................................................
234cdf0e10cSrcweir } // namespace sfx2
235cdf0e10cSrcweir //........................................................................
236