1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 #ifndef __FRAMEWORK_MACROS_XSERVICEINFO_HXX_
29 #define __FRAMEWORK_MACROS_XSERVICEINFO_HXX_
30 
31 //_________________________________________________________________________________________________________________
32 //	my own includes
33 //_________________________________________________________________________________________________________________
34 
35 #include <general.h>
36 
37 //_________________________________________________________________________________________________________________
38 //	interface includes
39 //_________________________________________________________________________________________________________________
40 #include <com/sun/star/uno/Exception.hpp>
41 #include <com/sun/star/uno/RuntimeException.hpp>
42 #include <com/sun/star/lang/XSingleServiceFactory.hpp>
43 #include <com/sun/star/lang/XServiceInfo.hpp>
44 
45 //_________________________________________________________________________________________________________________
46 //	other includes
47 //_________________________________________________________________________________________________________________
48 #include <com/sun/star/uno/Any.hxx>
49 #include <com/sun/star/uno/Reference.hxx>
50 #include <com/sun/star/uno/Sequence.hxx>
51 #include <com/sun/star/uno/Type.hxx>
52 #include <com/sun/star/uno/XComponentContext.hpp>
53 #include <com/sun/star/beans/XPropertySet.hpp>
54 #include <cppuhelper/factory.hxx>
55 #include <comphelper/sequence.hxx>
56 #include <rtl/ustring.hxx>
57 #include <rtl/logfile.hxx>
58 
59 //_________________________________________________________________________________________________________________
60 //	namespace
61 //_________________________________________________________________________________________________________________
62 
63 namespace framework{
64 
65 /*_________________________________________________________________________________________________________________
66 
67 	macros for declaration and definition of XServiceInfo
68 	Please use follow public macros only!
69 
70     1)  DECLARE_XSERVICEINFO                                                                                => use it to declare XServiceInfo in your header
71     2)  DEFINE_XSERVICEINFO_MULTISERVICE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )          => use it to define XServiceInfo for multi service mode
72     3)  DEFINE_XSERVICEINFO_ONEINSTANCESERVICE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )    => use it to define XServiceInfo for one instance service mode
73     4)  DEFINE_INIT_SERVICE( CLASS )                                                                        => use it to implement your own impl_initService() method, which is neccessary for initializeing object by using his own reference!
74 
75 _________________________________________________________________________________________________________________*/
76 
77 //*****************************************************************************************************************
78 //	private
79 //	implementation of XServiceInfo and helper functions
80 //*****************************************************************************************************************
81 #define PRIVATE_DEFINE_XSERVICEINFO_BASE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )                                                  \
82 	/*===========================================================================================================*/									\
83 	/* XServiceInfo																								 */									\
84 	/*===========================================================================================================*/									\
85     ::rtl::OUString SAL_CALL CLASS::getImplementationName() throw( css::uno::RuntimeException )                                                     \
86 	{																																				\
87 		return impl_getStaticImplementationName();																									\
88 	}																																				\
89 																																					\
90 	/*===========================================================================================================*/									\
91 	/* XServiceInfo																								 */									\
92 	/*===========================================================================================================*/									\
93     sal_Bool SAL_CALL CLASS::supportsService( const ::rtl::OUString& sServiceName ) throw( css::uno::RuntimeException )                             \
94 	{																																				\
95         return ::comphelper::findValue(getSupportedServiceNames(), sServiceName, sal_True).getLength() != 0;                                        \
96     }																																				\
97 																																					\
98 	/*===========================================================================================================*/									\
99 	/* XServiceInfo																								 */									\
100 	/*===========================================================================================================*/									\
101     css::uno::Sequence< ::rtl::OUString > SAL_CALL CLASS::getSupportedServiceNames() throw( css::uno::RuntimeException )                            \
102 	{																																				\
103 		return impl_getStaticSupportedServiceNames();																								\
104 	}																																				\
105 																																					\
106 	/*===========================================================================================================*/									\
107     /* Helper for XServiceInfo                                                                                   */                                 \
108 	/*===========================================================================================================*/									\
109     css::uno::Sequence< ::rtl::OUString > CLASS::impl_getStaticSupportedServiceNames()                                                              \
110 	{																																				\
111         css::uno::Sequence< ::rtl::OUString > seqServiceNames( 1 );                                                                                 \
112     	seqServiceNames.getArray() [0] = SERVICENAME ;																								\
113     	return seqServiceNames;																														\
114 	}																																				\
115 																																					\
116 	/*===========================================================================================================*/									\
117 	/* Helper for XServiceInfo																					 */									\
118 	/*===========================================================================================================*/									\
119 	::rtl::OUString CLASS::impl_getStaticImplementationName()																						\
120 	{																																				\
121 		return IMPLEMENTATIONNAME ;																													\
122 	}
123 
124 #define PRIVATE_DEFINE_XSERVICEINFO_OLDSTYLE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )                                              \
125 	PRIVATE_DEFINE_XSERVICEINFO_BASE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )														\
126 	/*===========================================================================================================*/									\
127 	/* Helper for registry																						 */									\
128     /* Attention: To avoid against wrong ref counts during our own initialize procedure, we must                 */                                 \
129     /*            use right EXTERNAL handling of them. That's why you should do nothing in your ctor, which could*/                                 \
130     /*            work on your ref count! All other things are allowed. Do work with your own reference - please */                                 \
131     /*            use "impl_initService()" method.                                                               */                                 \
132 	/*===========================================================================================================*/									\
133     css::uno::Reference< css::uno::XInterface > SAL_CALL CLASS::impl_createInstance( const css::uno::Reference< css::lang::XMultiServiceFactory >& xServiceManager ) throw( css::uno::Exception )  \
134     {                                                                                                                                                                                              \
135         RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework","Ocke.Janssen@sun.com",U2B(IMPLEMENTATIONNAME).getStr());                                                                                                               \
136         /* create new instance of service */                                                                                                                                                       \
137         CLASS* pClass = new CLASS( xServiceManager );                                                                                                                                              \
138         /* hold it alive by increasing his ref count!!! */                                                                                                                                         \
139         css::uno::Reference< css::uno::XInterface > xService( static_cast< XINTERFACECAST* >(pClass), css::uno::UNO_QUERY );                                                                       \
140         /* initialize new service instance ... he can use his own refcount ... we hold it! */                                                                                                      \
141         pClass->impl_initService();                                                                                                                                                                \
142         /* return new created service as reference */                                                                                                                                              \
143         return xService;                                                                                                                                                                           \
144 	}
145 
146 #define PRIVATE_DEFINE_XSERVICEINFO_NEWSTYLE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )                                              \
147 	PRIVATE_DEFINE_XSERVICEINFO_BASE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )														\
148 	/*===========================================================================================================*/									\
149 	/* Helper for registry																						 */									\
150     /* Attention: To avoid against wrong ref counts during our own initialize procedure, we must                 */                                 \
151     /*            use right EXTERNAL handling of them. That's why you should do nothing in your ctor, which could*/                                 \
152     /*            work on your ref count! All other things are allowed. Do work with your own reference - please */                                 \
153     /*            use "impl_initService()" method.                                                               */                                 \
154 	/*===========================================================================================================*/									\
155     css::uno::Reference< css::uno::XInterface > SAL_CALL CLASS::impl_createInstance( const css::uno::Reference< css::lang::XMultiServiceFactory >& xServiceManager )\
156 		throw( css::uno::Exception )																																\
157     {																																								\
158 		/* retrieve component context from the given service manager */																								\
159 		static const ::rtl::OUString PROP_DEFAULTCONTEXT = ::rtl::OUString::createFromAscii("DefaultContext");														\
160 		css::uno::Reference< css::beans::XPropertySet >    xSMGRProps(xServiceManager, css::uno::UNO_QUERY_THROW);													\
161 		css::uno::Reference< css::uno::XComponentContext > xComponentContext;																						\
162 		xSMGRProps->getPropertyValue( PROP_DEFAULTCONTEXT ) >>= xComponentContext;																					\
163         /* create new instance of service */                                                                                                                        \
164         CLASS* pClass = new CLASS( xComponentContext );                                                                                                             \
165         /* hold it alive by increasing his ref count!!! */                                                                                                          \
166         css::uno::Reference< css::uno::XInterface > xService( static_cast< XINTERFACECAST* >(pClass), css::uno::UNO_QUERY );                                        \
167         /* initialize new service instance ... he can use his own refcount ... we hold it! */                                                                       \
168         pClass->impl_initService();                                                                                                                                 \
169         /* return new created service as reference */                                                                                                               \
170         return xService;                                                                                                                                            \
171 	}
172 
173 //*****************************************************************************************************************
174 //	private
175 //	definition of helper function createFactory() for multiple services
176 //*****************************************************************************************************************
177 #define PRIVATE_DEFINE_SINGLEFACTORY( CLASS )                                                                                                                           \
178     css::uno::Reference< css::lang::XSingleServiceFactory > CLASS::impl_createFactory( const css::uno::Reference< css::lang::XMultiServiceFactory >& xServiceManager )  \
179     {                                                                                                                                                                   \
180         css::uno::Reference< css::lang::XSingleServiceFactory > xReturn ( cppu::createSingleFactory (   xServiceManager                             ,                   \
181                                                                                                         CLASS::impl_getStaticImplementationName()   ,                   \
182                                                                                                         CLASS::impl_createInstance                  ,                   \
183                                                                                                         CLASS::impl_getStaticSupportedServiceNames()                    \
184                                                                                                     )                                                                   \
185                                                                         );                                                                                              \
186         return xReturn;                                                                                                                                                 \
187 	}
188 
189 //*****************************************************************************************************************
190 //	private
191 //	definition of helper function createFactory() for one instance services
192 //*****************************************************************************************************************
193 #define PRIVATE_DEFINE_ONEINSTANCEFACTORY( CLASS )                                                                                                                      \
194     css::uno::Reference< css::lang::XSingleServiceFactory > CLASS::impl_createFactory( const css::uno::Reference< css::lang::XMultiServiceFactory >& xServiceManager )  \
195     {                                                                                                                                                                   \
196         css::uno::Reference< css::lang::XSingleServiceFactory > xReturn ( cppu::createOneInstanceFactory    (   xServiceManager                             ,           \
197                                                                                                                 CLASS::impl_getStaticImplementationName()   ,           \
198                                                                                                                 CLASS::impl_createInstance                  ,           \
199                                                                                                                 CLASS::impl_getStaticSupportedServiceNames()            \
200                                                                                                             )                                                           \
201                                                                         );                                                                                              \
202         return xReturn;                                                                                                                                                 \
203 	}
204 
205 //*****************************************************************************************************************
206 //	public
207 //	declaration of XServiceInfo and helper functions
208 //*****************************************************************************************************************
209 #define DECLARE_XSERVICEINFO                                                                                                                                                                                                            \
210     /* interface XServiceInfo */                                                                                                                                                                                                        \
211     virtual ::rtl::OUString                                        SAL_CALL getImplementationName              (                                                                               ) throw( css::uno::RuntimeException );   \
212     virtual sal_Bool                                               SAL_CALL supportsService                    ( const ::rtl::OUString&                                        sServiceName    ) throw( css::uno::RuntimeException );   \
213     virtual css::uno::Sequence< ::rtl::OUString >                  SAL_CALL getSupportedServiceNames           (                                                                               ) throw( css::uno::RuntimeException );   \
214     /* Helper for XServiceInfo */                                                                                                                                                                                                       \
215     static css::uno::Sequence< ::rtl::OUString >                   SAL_CALL impl_getStaticSupportedServiceNames(                                                                               );                                       \
216     static ::rtl::OUString                                         SAL_CALL impl_getStaticImplementationName   (                                                                               );                                       \
217     /* Helper for registry */                                                                                                                                                                                                           \
218     static css::uno::Reference< css::uno::XInterface >             SAL_CALL impl_createInstance                ( const css::uno::Reference< css::lang::XMultiServiceFactory >& xServiceManager ) throw( css::uno::Exception );          \
219     static css::uno::Reference< css::lang::XSingleServiceFactory > SAL_CALL impl_createFactory                 ( const css::uno::Reference< css::lang::XMultiServiceFactory >& xServiceManager );                                       \
220     /* Helper for initialization of service by using own reference! */                                                                                                                                                                  \
221     virtual void                                                   SAL_CALL impl_initService                   (                                                                               );                                       \
222 
223 //*****************************************************************************************************************
224 //	public
225 //	implementation of XServiceInfo
226 //*****************************************************************************************************************
227 #define DEFINE_XSERVICEINFO_MULTISERVICE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )              \
228     PRIVATE_DEFINE_XSERVICEINFO_OLDSTYLE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )              \
229 	PRIVATE_DEFINE_SINGLEFACTORY( CLASS )
230 
231 #define DEFINE_XSERVICEINFO_ONEINSTANCESERVICE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )        \
232     PRIVATE_DEFINE_XSERVICEINFO_OLDSTYLE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )              \
233 	PRIVATE_DEFINE_ONEINSTANCEFACTORY( CLASS )
234 
235 #define DEFINE_XSERVICEINFO_MULTISERVICE_2( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )            \
236     PRIVATE_DEFINE_XSERVICEINFO_NEWSTYLE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )              \
237 	PRIVATE_DEFINE_SINGLEFACTORY( CLASS )
238 
239 #define DEFINE_XSERVICEINFO_ONEINSTANCESERVICE_2( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )      \
240     PRIVATE_DEFINE_XSERVICEINFO_NEWSTYLE( CLASS, XINTERFACECAST, SERVICENAME, IMPLEMENTATIONNAME )              \
241 	PRIVATE_DEFINE_ONEINSTANCEFACTORY( CLASS )
242 
243 //*****************************************************************************************************************
244 //	public
245 //  implementation of service initialize!
246 //  example of using:   DEFINE_INIT_SERVICE( MyClassName,
247 //                          {
248 //                              ...
249 //                              Reference< XInterface > xThis( this, UNO_QUERY );
250 //                              myMember* pMember = new myMember( xThis );
251 //                              ...
252 //                          }
253 //                      )
254 //*****************************************************************************************************************
255 #define DEFINE_INIT_SERVICE( CLASS, FUNCTIONBODY )                                                              \
256     void SAL_CALL CLASS::impl_initService()                                                                     \
257     {                                                                                                           \
258         FUNCTIONBODY                                                                                            \
259     }
260 
261 #define DEFINE_INIT_SERVICE_WITH_BASECLASS( CLASS, BASECLASS, FUNCTIONBODY )                                    \
262     void SAL_CALL CLASS::impl_initService()                                                                     \
263     {                                                                                                           \
264         BASECLASS::impl_initService();                                                                          \
265         {                                                                                                       \
266             FUNCTIONBODY                                                                                        \
267         }                                                                                                       \
268     }
269 
270 }		//	namespace framework
271 
272 #endif	//	#ifndef __FRAMEWORK_MACROS_XSERVICEINFO_HXX_
273