1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
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 #include <accelerators/presethandler.hxx>
21 #include <uiconfiguration/moduleimagemanager.hxx>
23 #include <uielement/constitemcontainer.hxx>
24 #include <uielement/rootitemcontainer.hxx>
25 #include <uielement/uielementtypenames.hxx>
26 #include <framework/menuconfiguration.hxx>
27 #include <framework/toolboxconfiguration.hxx>
29 #include <framework/statusbarconfiguration.hxx>
31 #include <com/sun/star/ui/UIElementType.hpp>
32 #include <com/sun/star/ui/ConfigurationEvent.hpp>
33 #include <com/sun/star/ui/ModuleAcceleratorConfiguration.hpp>
34 #include <com/sun/star/ui/XUIConfigurationPersistence.hpp>
35 #include <com/sun/star/ui/XModuleUIConfigurationManager2.hpp>
36 #include <com/sun/star/lang/DisposedException.hpp>
37 #include <com/sun/star/lang/WrappedTargetRuntimeException.hpp>
38 #include <com/sun/star/beans/XPropertySet.hpp>
39 #include <com/sun/star/embed/ElementModes.hpp>
40 #include <com/sun/star/embed/XTransactedObject.hpp>
41 #include <com/sun/star/container/XNameAccess.hpp>
42 #include <com/sun/star/container/XIndexContainer.hpp>
43 #include <com/sun/star/io/XStream.hpp>
44 #include <com/sun/star/lang/XServiceInfo.hpp>
45 #include <com/sun/star/lang/XComponent.hpp>
47 #include <cppuhelper/implbase3.hxx>
48 #include <cppuhelper/interfacecontainer.hxx>
49 #include <cppuhelper/supportsservice.hxx>
50 #include <vcl/svapp.hxx>
51 #include <rtl/ref.hxx>
52 #include <rtl/ustrbuf.hxx>
53 #include <comphelper/sequenceashashmap.hxx>
56 using namespace com::sun::star::uno
;
57 using namespace com::sun::star::io
;
58 using namespace com::sun::star::embed
;
59 using namespace com::sun::star::lang
;
60 using namespace com::sun::star::container
;
61 using namespace com::sun::star::beans
;
62 using namespace framework
;
64 #define RESOURCETYPE_MENUBAR "menubar"
65 #define RESOURCETYPE_TOOLBAR "toolbar"
66 #define RESOURCETYPE_STATUSBAR "statusbar"
70 class ModuleUIConfigurationManager
: public cppu::WeakImplHelper3
<
71 css::lang::XServiceInfo
,
72 css::lang::XComponent
,
73 css::ui::XModuleUIConfigurationManager2
>
76 ModuleUIConfigurationManager(
77 const css::uno::Reference
< css::uno::XComponentContext
>& xServiceManager
,
78 const css::uno::Sequence
< css::uno::Any
>& aArguments
);
80 virtual ~ModuleUIConfigurationManager();
82 virtual OUString SAL_CALL
getImplementationName()
83 throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
85 return OUString("com.sun.star.comp.framework.ModuleUIConfigurationManager");
88 virtual sal_Bool SAL_CALL
supportsService(OUString
const & ServiceName
)
89 throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
91 return cppu::supportsService(this, ServiceName
);
94 virtual css::uno::Sequence
<OUString
> SAL_CALL
getSupportedServiceNames()
95 throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
97 css::uno::Sequence
< OUString
> aSeq(1);
98 aSeq
[0] = "com.sun.star.ui.ModuleUIConfigurationManager";
103 virtual void SAL_CALL
dispose() throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
104 virtual void SAL_CALL
addEventListener( const css::uno::Reference
< css::lang::XEventListener
>& xListener
) throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
105 virtual void SAL_CALL
removeEventListener( const css::uno::Reference
< css::lang::XEventListener
>& aListener
) throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
108 virtual void SAL_CALL
addConfigurationListener( const css::uno::Reference
< css::ui::XUIConfigurationListener
>& Listener
) throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
109 virtual void SAL_CALL
removeConfigurationListener( const css::uno::Reference
< css::ui::XUIConfigurationListener
>& Listener
) throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
111 // XUIConfigurationManager
112 virtual void SAL_CALL
reset() throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
113 virtual css::uno::Sequence
< css::uno::Sequence
< css::beans::PropertyValue
> > SAL_CALL
getUIElementsInfo( sal_Int16 ElementType
) throw (css::lang::IllegalArgumentException
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
114 virtual css::uno::Reference
< css::container::XIndexContainer
> SAL_CALL
createSettings( ) throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
115 virtual sal_Bool SAL_CALL
hasSettings( const OUString
& ResourceURL
) throw (css::lang::IllegalArgumentException
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
116 virtual css::uno::Reference
< css::container::XIndexAccess
> SAL_CALL
getSettings( const OUString
& ResourceURL
, sal_Bool bWriteable
) throw (css::container::NoSuchElementException
, css::lang::IllegalArgumentException
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
117 virtual void SAL_CALL
replaceSettings( const OUString
& ResourceURL
, const css::uno::Reference
< css::container::XIndexAccess
>& aNewData
) throw (css::container::NoSuchElementException
, css::lang::IllegalArgumentException
, css::lang::IllegalAccessException
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
118 virtual void SAL_CALL
removeSettings( const OUString
& ResourceURL
) throw (css::container::NoSuchElementException
, css::lang::IllegalArgumentException
, css::lang::IllegalAccessException
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
119 virtual void SAL_CALL
insertSettings( const OUString
& NewResourceURL
, const css::uno::Reference
< css::container::XIndexAccess
>& aNewData
) throw (css::container::ElementExistException
, css::lang::IllegalArgumentException
, css::lang::IllegalAccessException
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
120 virtual css::uno::Reference
< css::uno::XInterface
> SAL_CALL
getImageManager() throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
121 virtual css::uno::Reference
< css::ui::XAcceleratorConfiguration
> SAL_CALL
getShortCutManager() throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
122 virtual css::uno::Reference
< css::uno::XInterface
> SAL_CALL
getEventsManager() throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
124 // XModuleUIConfigurationManager
125 virtual sal_Bool SAL_CALL
isDefaultSettings( const OUString
& ResourceURL
) throw (css::lang::IllegalArgumentException
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
126 virtual css::uno::Reference
< css::container::XIndexAccess
> SAL_CALL
getDefaultSettings( const OUString
& ResourceURL
) throw (css::container::NoSuchElementException
, css::lang::IllegalArgumentException
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
128 // XUIConfigurationPersistence
129 virtual void SAL_CALL
reload() throw (css::uno::Exception
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
130 virtual void SAL_CALL
store() throw (css::uno::Exception
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
131 virtual void SAL_CALL
storeToStorage( const css::uno::Reference
< css::embed::XStorage
>& Storage
) throw (css::uno::Exception
, css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
132 virtual sal_Bool SAL_CALL
isModified() throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
133 virtual sal_Bool SAL_CALL
isReadOnly() throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
;
136 // private data types
153 UIElementInfo( const OUString
& rResourceURL
, const OUString
& rUIName
) :
154 aResourceURL( rResourceURL
), aUIName( rUIName
) {}
155 OUString aResourceURL
;
161 UIElementData() : bModified( false ), bDefault( true ), bDefaultNode( true ) {};
163 OUString aResourceURL
;
165 bool bModified
; // has been changed since last storing
166 bool bDefault
; // default settings
167 bool bDefaultNode
; // this is a default layer element data
168 css::uno::Reference
< css::container::XIndexAccess
> xSettings
;
171 typedef std::unordered_map
< OUString
, UIElementData
, OUStringHash
, std::equal_to
< OUString
> > UIElementDataHashMap
;
175 UIElementType() : bModified( false ),
177 bDefaultLayer( false ),
178 nElementType( css::ui::UIElementType::UNKNOWN
) {}
183 sal_Int16 nElementType
;
184 UIElementDataHashMap aElementsHashMap
;
185 css::uno::Reference
< css::embed::XStorage
> xStorage
;
188 typedef std::vector
< UIElementType
> UIElementTypesVector
;
189 typedef std::vector
< css::ui::ConfigurationEvent
> ConfigEventNotifyContainer
;
190 typedef std::unordered_map
< OUString
, UIElementInfo
, OUStringHash
, std::equal_to
< OUString
> > UIElementInfoHashMap
;
192 void impl_Initialize();
193 void implts_notifyContainerListener( const css::ui::ConfigurationEvent
& aEvent
, NotifyOp eOp
);
194 void impl_fillSequenceWithElementTypeInfo( UIElementInfoHashMap
& aUIElementInfoCollection
, sal_Int16 nElementType
);
195 void impl_preloadUIElementTypeList( Layer eLayer
, sal_Int16 nElementType
);
196 UIElementData
* impl_findUIElementData( const OUString
& aResourceURL
, sal_Int16 nElementType
, bool bLoad
= true );
197 void impl_requestUIElementData( sal_Int16 nElementType
, Layer eLayer
, UIElementData
& aUIElementData
);
198 void impl_storeElementTypeData( css::uno::Reference
< css::embed::XStorage
> xStorage
, UIElementType
& rElementType
, bool bResetModifyState
= true );
199 void impl_resetElementTypeData( UIElementType
& rUserElementType
, UIElementType
& rDefaultElementType
, ConfigEventNotifyContainer
& rRemoveNotifyContainer
, ConfigEventNotifyContainer
& rReplaceNotifyContainer
);
200 void impl_reloadElementTypeData( UIElementType
& rUserElementType
, UIElementType
& rDefaultElementType
, ConfigEventNotifyContainer
& rRemoveNotifyContainer
, ConfigEventNotifyContainer
& rReplaceNotifyContainer
);
202 UIElementTypesVector m_aUIElements
[LAYER_COUNT
];
203 PresetHandler
* m_pStorageHandler
[css::ui::UIElementType::COUNT
];
204 css::uno::Reference
< css::embed::XStorage
> m_xDefaultConfigStorage
;
205 css::uno::Reference
< css::embed::XStorage
> m_xUserConfigStorage
;
210 OUString m_aXMLPostfix
;
211 OUString m_aPropUIName
;
212 OUString m_aPropResourceURL
;
213 OUString m_aModuleIdentifier
;
214 OUString m_aModuleShortName
;
215 css::uno::Reference
< css::embed::XTransactedObject
> m_xUserRootCommit
;
216 css::uno::Reference
< css::uno::XComponentContext
> m_xContext
;
218 ::cppu::OMultiTypeInterfaceContainerHelper m_aListenerContainer
; /// container for ALL Listener
219 css::uno::Reference
< css::lang::XComponent
> m_xModuleImageManager
;
220 css::uno::Reference
< css::ui::XAcceleratorConfiguration
> m_xModuleAcceleratorManager
;
223 // important: The order and position of the elements must match the constant
224 // definition of "::com::sun::star::ui::UIElementType"
225 static const char* UIELEMENTTYPENAMES
[] =
227 "", // Dummy value for unknown!
228 UIELEMENTTYPE_MENUBAR_NAME
,
229 UIELEMENTTYPE_POPUPMENU_NAME
,
230 UIELEMENTTYPE_TOOLBAR_NAME
,
231 UIELEMENTTYPE_STATUSBAR_NAME
,
232 UIELEMENTTYPE_FLOATINGWINDOW_NAME
,
233 UIELEMENTTYPE_PROGRESSBAR_NAME
,
234 UIELEMENTTYPE_TOOLPANEL_NAME
237 static const char RESOURCEURL_PREFIX
[] = "private:resource/";
238 static const sal_Int32 RESOURCEURL_PREFIX_SIZE
= 17;
239 static const char RESOURCEURL_CUSTOM_ELEMENT
[] = "custom_";
241 static sal_Int16
RetrieveTypeFromResourceURL( const OUString
& aResourceURL
)
244 if (( aResourceURL
.startsWith( RESOURCEURL_PREFIX
) ) &&
245 ( aResourceURL
.getLength() > RESOURCEURL_PREFIX_SIZE
))
247 OUString aTmpStr
= aResourceURL
.copy( RESOURCEURL_PREFIX_SIZE
);
248 sal_Int32 nIndex
= aTmpStr
.indexOf( '/' );
249 if (( nIndex
> 0 ) && ( aTmpStr
.getLength() > nIndex
))
251 OUString
aTypeStr( aTmpStr
.copy( 0, nIndex
));
252 for ( int i
= 0; i
< ui::UIElementType::COUNT
; i
++ )
254 if ( aTypeStr
.equalsAscii( UIELEMENTTYPENAMES
[i
] ))
255 return sal_Int16( i
);
260 return ui::UIElementType::UNKNOWN
;
263 static OUString
RetrieveNameFromResourceURL( const OUString
& aResourceURL
)
265 if (( aResourceURL
.startsWith( RESOURCEURL_PREFIX
) ) &&
266 ( aResourceURL
.getLength() > RESOURCEURL_PREFIX_SIZE
))
268 sal_Int32 nIndex
= aResourceURL
.lastIndexOf( '/' );
269 if (( nIndex
> 0 ) && (( nIndex
+1 ) < aResourceURL
.getLength()))
270 return aResourceURL
.copy( nIndex
+1 );
276 void ModuleUIConfigurationManager::impl_fillSequenceWithElementTypeInfo( UIElementInfoHashMap
& aUIElementInfoCollection
, sal_Int16 nElementType
)
278 // preload list of element types on demand
279 impl_preloadUIElementTypeList( LAYER_USERDEFINED
, nElementType
);
280 impl_preloadUIElementTypeList( LAYER_DEFAULT
, nElementType
);
282 UIElementDataHashMap
& rUserElements
= m_aUIElements
[LAYER_USERDEFINED
][nElementType
].aElementsHashMap
;
283 UIElementDataHashMap::const_iterator pUserIter
= rUserElements
.begin();
285 OUString
aCustomUrlPrefix( RESOURCEURL_CUSTOM_ELEMENT
);
286 while ( pUserIter
!= rUserElements
.end() )
288 sal_Int32 nIndex
= pUserIter
->second
.aResourceURL
.indexOf( aCustomUrlPrefix
, RESOURCEURL_PREFIX_SIZE
);
289 if ( nIndex
> RESOURCEURL_PREFIX_SIZE
)
291 // Performance: Retrieve user interface name only for custom user interface elements.
292 // It's only used by them!
293 UIElementData
* pDataSettings
= impl_findUIElementData( pUserIter
->second
.aResourceURL
, nElementType
);
296 // Retrieve user interface name from XPropertySet interface
298 Reference
< XPropertySet
> xPropSet( pDataSettings
->xSettings
, UNO_QUERY
);
301 Any a
= xPropSet
->getPropertyValue( m_aPropUIName
);
305 UIElementInfo
aInfo( pUserIter
->second
.aResourceURL
, aUIName
);
306 aUIElementInfoCollection
.insert( UIElementInfoHashMap::value_type( pUserIter
->second
.aResourceURL
, aInfo
));
311 // The user interface name for standard user interface elements is stored in the WindowState.xcu file
312 UIElementInfo
aInfo( pUserIter
->second
.aResourceURL
, OUString() );
313 aUIElementInfoCollection
.insert( UIElementInfoHashMap::value_type( pUserIter
->second
.aResourceURL
, aInfo
));
318 UIElementDataHashMap
& rDefaultElements
= m_aUIElements
[LAYER_DEFAULT
][nElementType
].aElementsHashMap
;
319 UIElementDataHashMap::const_iterator pDefIter
= rDefaultElements
.begin();
321 while ( pDefIter
!= rDefaultElements
.end() )
323 UIElementInfoHashMap::const_iterator pIterInfo
= aUIElementInfoCollection
.find( pDefIter
->second
.aResourceURL
);
324 if ( pIterInfo
== aUIElementInfoCollection
.end() )
326 sal_Int32 nIndex
= pDefIter
->second
.aResourceURL
.indexOf( aCustomUrlPrefix
, RESOURCEURL_PREFIX_SIZE
);
327 if ( nIndex
> RESOURCEURL_PREFIX_SIZE
)
329 // Performance: Retrieve user interface name only for custom user interface elements.
330 // It's only used by them!
331 UIElementData
* pDataSettings
= impl_findUIElementData( pDefIter
->second
.aResourceURL
, nElementType
);
334 // Retrieve user interface name from XPropertySet interface
336 Reference
< XPropertySet
> xPropSet( pDataSettings
->xSettings
, UNO_QUERY
);
339 Any a
= xPropSet
->getPropertyValue( m_aPropUIName
);
343 UIElementInfo
aInfo( pDefIter
->second
.aResourceURL
, aUIName
);
344 aUIElementInfoCollection
.insert( UIElementInfoHashMap::value_type( pDefIter
->second
.aResourceURL
, aInfo
));
349 // The user interface name for standard user interface elements is stored in the WindowState.xcu file
350 UIElementInfo
aInfo( pDefIter
->second
.aResourceURL
, OUString() );
351 aUIElementInfoCollection
.insert( UIElementInfoHashMap::value_type( pDefIter
->second
.aResourceURL
, aInfo
));
359 void ModuleUIConfigurationManager::impl_preloadUIElementTypeList( Layer eLayer
, sal_Int16 nElementType
)
361 UIElementType
& rElementTypeData
= m_aUIElements
[eLayer
][nElementType
];
363 if ( !rElementTypeData
.bLoaded
)
365 Reference
< XStorage
> xElementTypeStorage
= rElementTypeData
.xStorage
;
366 if ( xElementTypeStorage
.is() )
368 OUStringBuffer
aBuf( RESOURCEURL_PREFIX_SIZE
);
369 aBuf
.appendAscii( RESOURCEURL_PREFIX
);
370 aBuf
.appendAscii( UIELEMENTTYPENAMES
[ nElementType
] );
371 aBuf
.appendAscii( "/" );
372 OUString
aResURLPrefix( aBuf
.makeStringAndClear() );
374 UIElementDataHashMap
& rHashMap
= rElementTypeData
.aElementsHashMap
;
375 Sequence
< OUString
> aUIElementNames
= xElementTypeStorage
->getElementNames();
376 for ( sal_Int32 n
= 0; n
< aUIElementNames
.getLength(); n
++ )
378 UIElementData aUIElementData
;
380 // Resource name must be without ".xml"
381 sal_Int32 nIndex
= aUIElementNames
[n
].lastIndexOf( '.' );
382 if (( nIndex
> 0 ) && ( nIndex
< aUIElementNames
[n
].getLength() ))
384 OUString
aExtension( aUIElementNames
[n
].copy( nIndex
+1 ));
385 OUString
aUIElementName( aUIElementNames
[n
].copy( 0, nIndex
));
387 if (!aUIElementName
.isEmpty() &&
388 ( aExtension
.equalsIgnoreAsciiCase("xml")))
390 aUIElementData
.aResourceURL
= aResURLPrefix
+ aUIElementName
;
391 aUIElementData
.aName
= aUIElementNames
[n
];
393 if ( eLayer
== LAYER_USERDEFINED
)
395 aUIElementData
.bModified
= false;
396 aUIElementData
.bDefault
= false;
397 aUIElementData
.bDefaultNode
= false;
400 // Create std::unordered_map entries for all user interface elements inside the storage. We don't load the
401 // settings to speed up the process.
402 rHashMap
.insert( UIElementDataHashMap::value_type( aUIElementData
.aResourceURL
, aUIElementData
));
405 rElementTypeData
.bLoaded
= true;
412 void ModuleUIConfigurationManager::impl_requestUIElementData( sal_Int16 nElementType
, Layer eLayer
, UIElementData
& aUIElementData
)
414 UIElementType
& rElementTypeData
= m_aUIElements
[eLayer
][nElementType
];
416 Reference
< XStorage
> xElementTypeStorage
= rElementTypeData
.xStorage
;
417 if ( xElementTypeStorage
.is() && !aUIElementData
.aName
.isEmpty() )
421 Reference
< XStream
> xStream
= xElementTypeStorage
->openStreamElement( aUIElementData
.aName
, ElementModes::READ
);
422 Reference
< XInputStream
> xInputStream
= xStream
->getInputStream();
424 if ( xInputStream
.is() )
426 switch ( nElementType
)
428 case ::com::sun::star::ui::UIElementType::UNKNOWN
:
431 case ::com::sun::star::ui::UIElementType::MENUBAR
:
435 MenuConfiguration
aMenuCfg( m_xContext
);
436 Reference
< XIndexAccess
> xContainer( aMenuCfg
.CreateMenuBarConfigurationFromXML( xInputStream
));
437 RootItemContainer
* pRootItemContainer
= RootItemContainer::GetImplementation( xContainer
);
438 if ( pRootItemContainer
)
439 aUIElementData
.xSettings
= Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new ConstItemContainer( pRootItemContainer
, true ) ), UNO_QUERY
);
441 aUIElementData
.xSettings
= Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new ConstItemContainer( xContainer
, true ) ), UNO_QUERY
);
444 catch ( const ::com::sun::star::lang::WrappedTargetException
& )
450 case ::com::sun::star::ui::UIElementType::POPUPMENU
:
455 case ::com::sun::star::ui::UIElementType::TOOLBAR
:
459 Reference
< XIndexContainer
> xIndexContainer( static_cast< OWeakObject
* >( new RootItemContainer() ), UNO_QUERY
);
460 ToolBoxConfiguration::LoadToolBox( m_xContext
, xInputStream
, xIndexContainer
);
461 RootItemContainer
* pRootItemContainer
= RootItemContainer::GetImplementation( xIndexContainer
);
462 aUIElementData
.xSettings
= Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new ConstItemContainer( pRootItemContainer
, true ) ), UNO_QUERY
);
465 catch ( const ::com::sun::star::lang::WrappedTargetException
& )
472 case ::com::sun::star::ui::UIElementType::STATUSBAR
:
476 Reference
< XIndexContainer
> xIndexContainer( static_cast< OWeakObject
* >( new RootItemContainer() ), UNO_QUERY
);
477 StatusBarConfiguration::LoadStatusBar( m_xContext
, xInputStream
, xIndexContainer
);
478 RootItemContainer
* pRootItemContainer
= RootItemContainer::GetImplementation( xIndexContainer
);
479 aUIElementData
.xSettings
= Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new ConstItemContainer( pRootItemContainer
, true ) ), UNO_QUERY
);
482 catch ( const ::com::sun::star::lang::WrappedTargetException
& )
489 case ::com::sun::star::ui::UIElementType::FLOATINGWINDOW
:
496 catch ( const ::com::sun::star::embed::InvalidStorageException
& )
499 catch ( const ::com::sun::star::lang::IllegalArgumentException
& )
502 catch ( const ::com::sun::star::io::IOException
& )
505 catch ( const ::com::sun::star::embed::StorageWrappedTargetException
& )
510 // At least we provide an empty settings container!
511 aUIElementData
.xSettings
= Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new ConstItemContainer() ), UNO_QUERY
);
514 ModuleUIConfigurationManager::UIElementData
* ModuleUIConfigurationManager::impl_findUIElementData( const OUString
& aResourceURL
, sal_Int16 nElementType
, bool bLoad
)
516 // preload list of element types on demand
517 impl_preloadUIElementTypeList( LAYER_USERDEFINED
, nElementType
);
518 impl_preloadUIElementTypeList( LAYER_DEFAULT
, nElementType
);
520 // first try to look into our user-defined vector/unordered_map combination
521 UIElementDataHashMap
& rUserHashMap
= m_aUIElements
[LAYER_USERDEFINED
][nElementType
].aElementsHashMap
;
522 UIElementDataHashMap::iterator pIter
= rUserHashMap
.find( aResourceURL
);
523 if ( pIter
!= rUserHashMap
.end() )
525 // Default data settings data must be retrieved from the default layer!
526 if ( !pIter
->second
.bDefault
)
528 if ( !pIter
->second
.xSettings
.is() && bLoad
)
529 impl_requestUIElementData( nElementType
, LAYER_USERDEFINED
, pIter
->second
);
530 return &(pIter
->second
);
534 // Not successful, we have to look into our default vector/unordered_map combination
535 UIElementDataHashMap
& rDefaultHashMap
= m_aUIElements
[LAYER_DEFAULT
][nElementType
].aElementsHashMap
;
536 pIter
= rDefaultHashMap
.find( aResourceURL
);
537 if ( pIter
!= rDefaultHashMap
.end() )
539 if ( !pIter
->second
.xSettings
.is() && bLoad
)
540 impl_requestUIElementData( nElementType
, LAYER_DEFAULT
, pIter
->second
);
541 return &(pIter
->second
);
544 // Nothing has been found!
548 void ModuleUIConfigurationManager::impl_storeElementTypeData( Reference
< XStorage
> xStorage
, UIElementType
& rElementType
, bool bResetModifyState
)
550 UIElementDataHashMap
& rHashMap
= rElementType
.aElementsHashMap
;
551 UIElementDataHashMap::iterator pIter
= rHashMap
.begin();
553 while ( pIter
!= rHashMap
.end() )
555 UIElementData
& rElement
= pIter
->second
;
556 if ( rElement
.bModified
)
558 if ( rElement
.bDefault
)
560 xStorage
->removeElement( rElement
.aName
);
561 rElement
.bModified
= false; // mark as not modified
565 Reference
< XStream
> xStream( xStorage
->openStreamElement( rElement
.aName
, ElementModes::WRITE
|ElementModes::TRUNCATE
), UNO_QUERY
);
566 Reference
< XOutputStream
> xOutputStream( xStream
->getOutputStream() );
568 if ( xOutputStream
.is() )
570 switch( rElementType
.nElementType
)
572 case ::com::sun::star::ui::UIElementType::MENUBAR
:
576 MenuConfiguration
aMenuCfg( m_xContext
);
577 aMenuCfg
.StoreMenuBarConfigurationToXML( rElement
.xSettings
, xOutputStream
);
579 catch ( const ::com::sun::star::lang::WrappedTargetException
& )
585 case ::com::sun::star::ui::UIElementType::TOOLBAR
:
589 ToolBoxConfiguration::StoreToolBox( m_xContext
, xOutputStream
, rElement
.xSettings
);
591 catch ( const ::com::sun::star::lang::WrappedTargetException
& )
597 case ::com::sun::star::ui::UIElementType::STATUSBAR
:
601 StatusBarConfiguration::StoreStatusBar( m_xContext
, xOutputStream
, rElement
.xSettings
);
603 catch ( const ::com::sun::star::lang::WrappedTargetException
& )
614 // mark as not modified if we store to our own storage
615 if ( bResetModifyState
)
616 rElement
.bModified
= false;
623 // commit element type storage
624 Reference
< XTransactedObject
> xTransactedObject( xStorage
, UNO_QUERY
);
625 if ( xTransactedObject
.is() )
626 xTransactedObject
->commit();
628 // mark UIElementType as not modified if we store to our own storage
629 if ( bResetModifyState
)
630 rElementType
.bModified
= false;
633 // This is only allowed to be called on the LAYER_USER_DEFINED!
634 void ModuleUIConfigurationManager::impl_resetElementTypeData(
635 UIElementType
& rUserElementType
,
636 UIElementType
& rDefaultElementType
,
637 ConfigEventNotifyContainer
& rRemoveNotifyContainer
,
638 ConfigEventNotifyContainer
& rReplaceNotifyContainer
)
640 UIElementDataHashMap
& rHashMap
= rUserElementType
.aElementsHashMap
;
641 UIElementDataHashMap::iterator pIter
= rHashMap
.begin();
643 Reference
< XUIConfigurationManager
> xThis( static_cast< OWeakObject
* >( this ), UNO_QUERY
);
644 Reference
< XInterface
> xIfac( xThis
, UNO_QUERY
);
645 Reference
< XNameAccess
> xDefaultNameAccess( rDefaultElementType
.xStorage
, UNO_QUERY
);
646 sal_Int16 nType
= rUserElementType
.nElementType
;
648 // Make copies of the event structures to be thread-safe. We have to unlock our mutex before calling
650 while ( pIter
!= rHashMap
.end() )
652 UIElementData
& rElement
= pIter
->second
;
653 if ( !rElement
.bDefault
)
655 if ( xDefaultNameAccess
->hasByName( rElement
.aName
))
657 // Replace settings with data from default layer
658 Reference
< XIndexAccess
> xOldSettings( rElement
.xSettings
);
659 impl_requestUIElementData( nType
, LAYER_DEFAULT
, rElement
);
661 ui::ConfigurationEvent aReplaceEvent
;
662 aReplaceEvent
.ResourceURL
= rElement
.aResourceURL
;
663 aReplaceEvent
.Accessor
<<= xThis
;
664 aReplaceEvent
.Source
= xIfac
;
665 aReplaceEvent
.ReplacedElement
<<= xOldSettings
;
666 aReplaceEvent
.Element
<<= rElement
.xSettings
;
668 rReplaceNotifyContainer
.push_back( aReplaceEvent
);
670 // Mark element as default and not modified. That means "not active"
671 // in the user layer anymore.
672 rElement
.bModified
= false;
673 rElement
.bDefault
= true;
677 // Remove user-defined settings from user layer
678 ui::ConfigurationEvent aEvent
;
679 aEvent
.ResourceURL
= rElement
.aResourceURL
;
680 aEvent
.Accessor
<<= xThis
;
681 aEvent
.Source
= xIfac
;
682 aEvent
.Element
<<= rElement
.xSettings
;
684 rRemoveNotifyContainer
.push_back( aEvent
);
686 // Mark element as default and not modified. That means "not active"
687 // in the user layer anymore.
688 rElement
.bModified
= false;
689 rElement
.bDefault
= true;
696 // Remove all settings from our user interface elements
700 void ModuleUIConfigurationManager::impl_reloadElementTypeData(
701 UIElementType
& rUserElementType
,
702 UIElementType
& rDefaultElementType
,
703 ConfigEventNotifyContainer
& rRemoveNotifyContainer
,
704 ConfigEventNotifyContainer
& rReplaceNotifyContainer
)
706 UIElementDataHashMap
& rHashMap
= rUserElementType
.aElementsHashMap
;
707 UIElementDataHashMap::iterator pIter
= rHashMap
.begin();
708 Reference
< XStorage
> xUserStorage( rUserElementType
.xStorage
);
709 Reference
< XStorage
> xDefaultStorage( rDefaultElementType
.xStorage
);
710 Reference
< XNameAccess
> xUserNameAccess( rUserElementType
.xStorage
, UNO_QUERY
);
711 Reference
< XNameAccess
> xDefaultNameAccess( rDefaultElementType
.xStorage
, UNO_QUERY
);
713 Reference
< XUIConfigurationManager
> xThis( static_cast< OWeakObject
* >( this ), UNO_QUERY
);
714 Reference
< XInterface
> xIfac( xThis
, UNO_QUERY
);
715 sal_Int16 nType
= rUserElementType
.nElementType
;
717 while ( pIter
!= rHashMap
.end() )
719 UIElementData
& rElement
= pIter
->second
;
720 if ( rElement
.bModified
)
722 if ( xUserNameAccess
->hasByName( rElement
.aName
))
724 // Replace settings with data from user layer
725 Reference
< XIndexAccess
> xOldSettings( rElement
.xSettings
);
727 impl_requestUIElementData( nType
, LAYER_USERDEFINED
, rElement
);
729 ui::ConfigurationEvent aReplaceEvent
;
731 aReplaceEvent
.ResourceURL
= rElement
.aResourceURL
;
732 aReplaceEvent
.Accessor
<<= xThis
;
733 aReplaceEvent
.Source
= xIfac
;
734 aReplaceEvent
.ReplacedElement
<<= xOldSettings
;
735 aReplaceEvent
.Element
<<= rElement
.xSettings
;
736 rReplaceNotifyContainer
.push_back( aReplaceEvent
);
738 rElement
.bModified
= false;
740 else if ( xDefaultNameAccess
->hasByName( rElement
.aName
))
742 // Replace settings with data from default layer
743 Reference
< XIndexAccess
> xOldSettings( rElement
.xSettings
);
745 impl_requestUIElementData( nType
, LAYER_DEFAULT
, rElement
);
747 ui::ConfigurationEvent aReplaceEvent
;
749 aReplaceEvent
.ResourceURL
= rElement
.aResourceURL
;
750 aReplaceEvent
.Accessor
<<= xThis
;
751 aReplaceEvent
.Source
= xIfac
;
752 aReplaceEvent
.ReplacedElement
<<= xOldSettings
;
753 aReplaceEvent
.Element
<<= rElement
.xSettings
;
754 rReplaceNotifyContainer
.push_back( aReplaceEvent
);
756 // Mark element as default and not modified. That means "not active"
757 // in the user layer anymore.
758 rElement
.bModified
= false;
759 rElement
.bDefault
= true;
763 // Element settings are not in any storage => remove
764 ui::ConfigurationEvent aRemoveEvent
;
766 aRemoveEvent
.ResourceURL
= rElement
.aResourceURL
;
767 aRemoveEvent
.Accessor
<<= xThis
;
768 aRemoveEvent
.Source
= xIfac
;
769 aRemoveEvent
.Element
<<= rElement
.xSettings
;
771 rRemoveNotifyContainer
.push_back( aRemoveEvent
);
773 // Mark element as default and not modified. That means "not active"
774 // in the user layer anymore.
775 rElement
.bModified
= false;
776 rElement
.bDefault
= true;
782 rUserElementType
.bModified
= false;
785 void ModuleUIConfigurationManager::impl_Initialize()
787 // Initialize the top-level structures with the storage data
788 if ( m_xUserConfigStorage
.is() )
790 // Try to access our module sub folder
791 for ( sal_Int16 i
= 1; i
< ::com::sun::star::ui::UIElementType::COUNT
;
794 Reference
< XStorage
> xElementTypeStorage
;
797 if ( m_pStorageHandler
[i
] )
798 xElementTypeStorage
= m_pStorageHandler
[i
]->getWorkingStorageUser();
800 catch ( const com::sun::star::container::NoSuchElementException
& )
803 catch ( const ::com::sun::star::embed::InvalidStorageException
& )
806 catch ( const ::com::sun::star::lang::IllegalArgumentException
& )
809 catch ( const ::com::sun::star::io::IOException
& )
812 catch ( const ::com::sun::star::embed::StorageWrappedTargetException
& )
816 m_aUIElements
[LAYER_USERDEFINED
][i
].nElementType
= i
;
817 m_aUIElements
[LAYER_USERDEFINED
][i
].bModified
= false;
818 m_aUIElements
[LAYER_USERDEFINED
][i
].xStorage
= xElementTypeStorage
;
819 m_aUIElements
[LAYER_USERDEFINED
][i
].bDefaultLayer
= false;
823 if ( m_xDefaultConfigStorage
.is() )
825 Reference
< XNameAccess
> xNameAccess( m_xDefaultConfigStorage
, UNO_QUERY_THROW
);
827 // Try to access our module sub folder
828 for ( sal_Int16 i
= 1; i
< ::com::sun::star::ui::UIElementType::COUNT
;
831 Reference
< XStorage
> xElementTypeStorage
;
834 const OUString
sName( OUString::createFromAscii( UIELEMENTTYPENAMES
[i
] ) );
835 if( xNameAccess
->hasByName( sName
) )
836 xNameAccess
->getByName( sName
) >>= xElementTypeStorage
;
838 catch ( const com::sun::star::container::NoSuchElementException
& )
842 m_aUIElements
[LAYER_DEFAULT
][i
].nElementType
= i
;
843 m_aUIElements
[LAYER_DEFAULT
][i
].bModified
= false;
844 m_aUIElements
[LAYER_DEFAULT
][i
].xStorage
= xElementTypeStorage
;
845 m_aUIElements
[LAYER_DEFAULT
][i
].bDefaultLayer
= true;
850 ModuleUIConfigurationManager::ModuleUIConfigurationManager(
851 const Reference
< XComponentContext
>& xContext
,
852 const css::uno::Sequence
< css::uno::Any
>& aArguments
)
853 : m_xDefaultConfigStorage( 0 )
854 , m_xUserConfigStorage( 0 )
855 , m_bReadOnly( true )
856 , m_bModified( false )
857 , m_bConfigRead( false )
858 , m_bDisposed( false )
859 , m_aXMLPostfix( ".xml" )
860 , m_aPropUIName( "UIName" )
861 , m_aPropResourceURL( "ResourceURL" )
862 , m_xContext( xContext
)
863 , m_aListenerContainer( m_mutex
)
865 for ( int i
= 0; i
< ::com::sun::star::ui::UIElementType::COUNT
; i
++ )
866 m_pStorageHandler
[i
] = 0;
868 // Make sure we have a default initialized entry for every layer and user interface element type!
869 // The following code depends on this!
870 m_aUIElements
[LAYER_DEFAULT
].resize( ::com::sun::star::ui::UIElementType::COUNT
);
871 m_aUIElements
[LAYER_USERDEFINED
].resize( ::com::sun::star::ui::UIElementType::COUNT
);
875 if( aArguments
.getLength() == 2 && (aArguments
[0] >>= m_aModuleShortName
) && (aArguments
[1] >>= m_aModuleIdentifier
))
880 ::comphelper::SequenceAsHashMap
lArgs(aArguments
);
881 m_aModuleShortName
= lArgs
.getUnpackedValueOrDefault("ModuleShortName", OUString());
882 m_aModuleIdentifier
= lArgs
.getUnpackedValueOrDefault("ModuleIdentifier", OUString());
885 for ( int i
= 1; i
< ::com::sun::star::ui::UIElementType::COUNT
; i
++ )
887 OUString aResourceType
;
888 if ( i
== ::com::sun::star::ui::UIElementType::MENUBAR
)
889 aResourceType
= RESOURCETYPE_MENUBAR
;
890 else if ( i
== ::com::sun::star::ui::UIElementType::TOOLBAR
)
891 aResourceType
= RESOURCETYPE_TOOLBAR
;
892 else if ( i
== ::com::sun::star::ui::UIElementType::STATUSBAR
)
893 aResourceType
= RESOURCETYPE_STATUSBAR
;
895 if ( !aResourceType
.isEmpty() )
897 m_pStorageHandler
[i
] = new PresetHandler( m_xContext
);
898 m_pStorageHandler
[i
]->connectToResource( PresetHandler::E_MODULES
,
899 aResourceType
, // this path wont be used later ... seee next lines!
901 css::uno::Reference
< css::embed::XStorage
>()); // no document root used here!
905 // initialize root storages for all resource types
906 m_xUserRootCommit
= css::uno::Reference
< css::embed::XTransactedObject
>(
907 m_pStorageHandler
[::com::sun::star::ui::UIElementType::MENUBAR
]->getOrCreateRootStorageUser(), css::uno::UNO_QUERY
); // can be empty
908 m_xDefaultConfigStorage
= m_pStorageHandler
[::com::sun::star::ui::UIElementType::MENUBAR
]->getParentStorageShare(
909 m_pStorageHandler
[::com::sun::star::ui::UIElementType::MENUBAR
]->getWorkingStorageShare());
910 m_xUserConfigStorage
= m_pStorageHandler
[::com::sun::star::ui::UIElementType::MENUBAR
]->getParentStorageUser(
911 m_pStorageHandler
[::com::sun::star::ui::UIElementType::MENUBAR
]->getWorkingStorageUser());
913 if ( m_xUserConfigStorage
.is() )
915 Reference
< XPropertySet
> xPropSet( m_xUserConfigStorage
, UNO_QUERY
);
919 Any a
= xPropSet
->getPropertyValue("OpenMode");
920 if ( a
>>= nOpenMode
)
921 m_bReadOnly
= !( nOpenMode
& ElementModes::WRITE
);
928 ModuleUIConfigurationManager::~ModuleUIConfigurationManager()
930 for ( int i
= 0; i
< ::com::sun::star::ui::UIElementType::COUNT
; i
++ )
931 delete m_pStorageHandler
[i
];
935 void SAL_CALL
ModuleUIConfigurationManager::dispose() throw (::com::sun::star::uno::RuntimeException
, std::exception
)
937 Reference
< XComponent
> xThis( static_cast< OWeakObject
* >(this), UNO_QUERY
);
939 css::lang::EventObject
aEvent( xThis
);
940 m_aListenerContainer
.disposeAndClear( aEvent
);
942 /* SAFE AREA ----------------------------------------------------------------------------------------------- */
943 SolarMutexClearableGuard aGuard
;
944 Reference
< XComponent
> xModuleImageManager( m_xModuleImageManager
);
945 m_xModuleImageManager
.clear();
946 Reference
< XComponent
> xCompMAM( m_xModuleAcceleratorManager
, UNO_QUERY
);
949 m_xModuleAcceleratorManager
.clear();
950 m_aUIElements
[LAYER_USERDEFINED
].clear();
951 m_aUIElements
[LAYER_DEFAULT
].clear();
952 m_xDefaultConfigStorage
.clear();
953 m_xUserConfigStorage
.clear();
954 m_xUserRootCommit
.clear();
955 m_bConfigRead
= false;
959 /* SAFE AREA ----------------------------------------------------------------------------------------------- */
963 if ( xModuleImageManager
.is() )
964 xModuleImageManager
->dispose();
966 catch ( const Exception
& )
971 void SAL_CALL
ModuleUIConfigurationManager::addEventListener( const Reference
< XEventListener
>& xListener
) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
976 /* SAFE AREA ----------------------------------------------------------------------------------------------- */
978 throw DisposedException();
981 m_aListenerContainer
.addInterface( cppu::UnoType
<XEventListener
>::get(), xListener
);
984 void SAL_CALL
ModuleUIConfigurationManager::removeEventListener( const Reference
< XEventListener
>& xListener
) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
986 /* SAFE AREA ----------------------------------------------------------------------------------------------- */
987 m_aListenerContainer
.removeInterface( cppu::UnoType
<XEventListener
>::get(), xListener
);
991 void SAL_CALL
ModuleUIConfigurationManager::addConfigurationListener( const Reference
< ::com::sun::star::ui::XUIConfigurationListener
>& xListener
) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
996 /* SAFE AREA ----------------------------------------------------------------------------------------------- */
998 throw DisposedException();
1001 m_aListenerContainer
.addInterface( cppu::UnoType
<ui::XUIConfigurationListener
>::get(), xListener
);
1004 void SAL_CALL
ModuleUIConfigurationManager::removeConfigurationListener( const Reference
< ::com::sun::star::ui::XUIConfigurationListener
>& xListener
) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1006 /* SAFE AREA ----------------------------------------------------------------------------------------------- */
1007 m_aListenerContainer
.removeInterface( cppu::UnoType
<ui::XUIConfigurationListener
>::get(), xListener
);
1010 // XUIConfigurationManager
1011 void SAL_CALL
ModuleUIConfigurationManager::reset() throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1013 SolarMutexClearableGuard aGuard
;
1015 /* SAFE AREA ----------------------------------------------------------------------------------------------- */
1017 throw DisposedException();
1019 if ( !isReadOnly() )
1021 // Remove all elements from our user-defined storage!
1024 for ( int i
= 1; i
< ::com::sun::star::ui::UIElementType::COUNT
; i
++ )
1026 UIElementType
& rElementType
= m_aUIElements
[LAYER_USERDEFINED
][i
];
1027 Reference
< XStorage
> xSubStorage( rElementType
.xStorage
, UNO_QUERY
);
1029 if ( xSubStorage
.is() )
1031 bool bCommitSubStorage( false );
1032 Sequence
< OUString
> aUIElementStreamNames
= xSubStorage
->getElementNames();
1033 for ( sal_Int32 j
= 0; j
< aUIElementStreamNames
.getLength(); j
++ )
1035 xSubStorage
->removeElement( aUIElementStreamNames
[j
] );
1036 bCommitSubStorage
= true;
1039 if ( bCommitSubStorage
)
1041 Reference
< XTransactedObject
> xTransactedObject( xSubStorage
, UNO_QUERY
);
1042 if ( xTransactedObject
.is() )
1043 xTransactedObject
->commit();
1044 m_pStorageHandler
[i
]->commitUserChanges();
1049 // remove settings from user defined layer and notify listener about removed settings data!
1050 ConfigEventNotifyContainer aRemoveEventNotifyContainer
;
1051 ConfigEventNotifyContainer aReplaceEventNotifyContainer
;
1052 for ( sal_Int16 j
= 1; j
< ::com::sun::star::ui::UIElementType::COUNT
; j
++ )
1056 UIElementType
& rUserElementType
= m_aUIElements
[LAYER_USERDEFINED
][j
];
1057 UIElementType
& rDefaultElementType
= m_aUIElements
[LAYER_DEFAULT
][j
];
1059 impl_resetElementTypeData( rUserElementType
, rDefaultElementType
, aRemoveEventNotifyContainer
, aReplaceEventNotifyContainer
);
1060 rUserElementType
.bModified
= false;
1062 catch (const Exception
& e
)
1065 throw css::lang::WrappedTargetRuntimeException(
1066 OUString("ModuleUIConfigurationManager::reset exception"),
1067 css::uno::Reference
<css::uno::XInterface
>(*this), a
);
1071 m_bModified
= false;
1073 // Unlock mutex before notify our listeners
1076 // Notify our listeners
1078 for ( k
= 0; k
< aRemoveEventNotifyContainer
.size(); k
++ )
1079 implts_notifyContainerListener( aRemoveEventNotifyContainer
[k
], NotifyOp_Remove
);
1080 for ( k
= 0; k
< aReplaceEventNotifyContainer
.size(); k
++ )
1081 implts_notifyContainerListener( aReplaceEventNotifyContainer
[k
], NotifyOp_Replace
);
1083 catch ( const ::com::sun::star::lang::IllegalArgumentException
& )
1086 catch ( const ::com::sun::star::container::NoSuchElementException
& )
1089 catch ( const ::com::sun::star::embed::InvalidStorageException
& )
1092 catch ( const ::com::sun::star::embed::StorageWrappedTargetException
& )
1098 Sequence
< Sequence
< PropertyValue
> > SAL_CALL
ModuleUIConfigurationManager::getUIElementsInfo( sal_Int16 ElementType
)
1099 throw ( IllegalArgumentException
, RuntimeException
, std::exception
)
1101 if (( ElementType
< 0 ) || ( ElementType
>= ::com::sun::star::ui::UIElementType::COUNT
))
1102 throw IllegalArgumentException();
1106 throw DisposedException();
1108 Sequence
< Sequence
< PropertyValue
> > aElementInfoSeq
;
1109 UIElementInfoHashMap aUIElementInfoCollection
;
1111 if ( ElementType
== ::com::sun::star::ui::UIElementType::UNKNOWN
)
1113 for ( sal_Int16 i
= 0; i
< ::com::sun::star::ui::UIElementType::COUNT
; i
++ )
1114 impl_fillSequenceWithElementTypeInfo( aUIElementInfoCollection
, sal_Int16( i
) );
1117 impl_fillSequenceWithElementTypeInfo( aUIElementInfoCollection
, ElementType
);
1119 Sequence
< PropertyValue
> aUIElementInfo( 2 );
1120 aUIElementInfo
[0].Name
= m_aPropResourceURL
;
1121 aUIElementInfo
[1].Name
= m_aPropUIName
;
1123 aElementInfoSeq
.realloc( aUIElementInfoCollection
.size() );
1124 UIElementInfoHashMap::const_iterator pIter
= aUIElementInfoCollection
.begin();
1127 while ( pIter
!= aUIElementInfoCollection
.end() )
1129 aUIElementInfo
[0].Value
<<= pIter
->second
.aResourceURL
;
1130 aUIElementInfo
[1].Value
<<= pIter
->second
.aUIName
;
1131 aElementInfoSeq
[n
++] = aUIElementInfo
;
1135 return aElementInfoSeq
;
1138 Reference
< XIndexContainer
> SAL_CALL
ModuleUIConfigurationManager::createSettings() throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1143 throw DisposedException();
1145 // Creates an empty item container which can be filled from outside
1146 return Reference
< XIndexContainer
>( static_cast< OWeakObject
* >( new RootItemContainer() ), UNO_QUERY
);
1149 sal_Bool SAL_CALL
ModuleUIConfigurationManager::hasSettings( const OUString
& ResourceURL
)
1150 throw (::com::sun::star::lang::IllegalArgumentException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1152 sal_Int16 nElementType
= RetrieveTypeFromResourceURL( ResourceURL
);
1154 if (( nElementType
== ::com::sun::star::ui::UIElementType::UNKNOWN
) ||
1155 ( nElementType
>= ::com::sun::star::ui::UIElementType::COUNT
))
1156 throw IllegalArgumentException();
1162 throw DisposedException();
1164 UIElementData
* pDataSettings
= impl_findUIElementData( ResourceURL
, nElementType
, false );
1165 if ( pDataSettings
)
1172 Reference
< XIndexAccess
> SAL_CALL
ModuleUIConfigurationManager::getSettings( const OUString
& ResourceURL
, sal_Bool bWriteable
)
1173 throw (::com::sun::star::container::NoSuchElementException
, ::com::sun::star::lang::IllegalArgumentException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1175 sal_Int16 nElementType
= RetrieveTypeFromResourceURL( ResourceURL
);
1177 if (( nElementType
== ::com::sun::star::ui::UIElementType::UNKNOWN
) ||
1178 ( nElementType
>= ::com::sun::star::ui::UIElementType::COUNT
))
1179 throw IllegalArgumentException();
1185 throw DisposedException();
1187 UIElementData
* pDataSettings
= impl_findUIElementData( ResourceURL
, nElementType
);
1188 if ( pDataSettings
)
1190 // Create a copy of our data if someone wants to change the data.
1192 return Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new RootItemContainer( pDataSettings
->xSettings
) ), UNO_QUERY
);
1194 return pDataSettings
->xSettings
;
1198 throw NoSuchElementException();
1201 void SAL_CALL
ModuleUIConfigurationManager::replaceSettings( const OUString
& ResourceURL
, const Reference
< ::com::sun::star::container::XIndexAccess
>& aNewData
)
1202 throw (::com::sun::star::container::NoSuchElementException
, ::com::sun::star::lang::IllegalArgumentException
, ::com::sun::star::lang::IllegalAccessException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1204 sal_Int16 nElementType
= RetrieveTypeFromResourceURL( ResourceURL
);
1206 if (( nElementType
== ::com::sun::star::ui::UIElementType::UNKNOWN
) ||
1207 ( nElementType
>= ::com::sun::star::ui::UIElementType::COUNT
))
1208 throw IllegalArgumentException();
1209 else if ( m_bReadOnly
)
1210 throw IllegalAccessException();
1213 SolarMutexClearableGuard aGuard
;
1216 throw DisposedException();
1218 UIElementData
* pDataSettings
= impl_findUIElementData( ResourceURL
, nElementType
);
1219 if ( pDataSettings
)
1221 if ( !pDataSettings
->bDefaultNode
)
1223 // we have a settings entry in our user-defined layer - replace
1224 Reference
< XIndexAccess
> xOldSettings
= pDataSettings
->xSettings
;
1226 // Create a copy of the data if the container is not const
1227 Reference
< XIndexReplace
> xReplace( aNewData
, UNO_QUERY
);
1228 if ( xReplace
.is() )
1229 pDataSettings
->xSettings
= Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new ConstItemContainer( aNewData
) ), UNO_QUERY
);
1231 pDataSettings
->xSettings
= aNewData
;
1232 pDataSettings
->bDefault
= false;
1233 pDataSettings
->bModified
= true;
1236 // Modify type container
1237 UIElementType
& rElementType
= m_aUIElements
[LAYER_USERDEFINED
][nElementType
];
1238 rElementType
.bModified
= true;
1240 Reference
< XUIConfigurationManager
> xThis( static_cast< OWeakObject
* >( this ), UNO_QUERY
);
1241 Reference
< XInterface
> xIfac( xThis
, UNO_QUERY
);
1243 // Create event to notify listener about replaced element settings
1244 ui::ConfigurationEvent aEvent
;
1245 aEvent
.ResourceURL
= ResourceURL
;
1246 aEvent
.Accessor
<<= xThis
;
1247 aEvent
.Source
= xIfac
;
1248 aEvent
.ReplacedElement
<<= xOldSettings
;
1249 aEvent
.Element
<<= pDataSettings
->xSettings
;
1253 implts_notifyContainerListener( aEvent
, NotifyOp_Replace
);
1257 // we have no settings in our user-defined layer - insert
1258 UIElementData aUIElementData
;
1260 aUIElementData
.bDefault
= false;
1261 aUIElementData
.bDefaultNode
= false;
1262 aUIElementData
.bModified
= true;
1264 // Create a copy of the data if the container is not const
1265 Reference
< XIndexReplace
> xReplace( aNewData
, UNO_QUERY
);
1266 if ( xReplace
.is() )
1267 aUIElementData
.xSettings
= Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new ConstItemContainer( aNewData
) ), UNO_QUERY
);
1269 aUIElementData
.xSettings
= aNewData
;
1270 aUIElementData
.aName
= RetrieveNameFromResourceURL( ResourceURL
) + m_aXMLPostfix
;
1271 aUIElementData
.aResourceURL
= ResourceURL
;
1274 // Modify type container
1275 UIElementType
& rElementType
= m_aUIElements
[LAYER_USERDEFINED
][nElementType
];
1276 rElementType
.bModified
= true;
1278 UIElementDataHashMap
& rElements
= rElementType
.aElementsHashMap
;
1280 // Check our user element settings hash map as it can already contain settings that have been set to default!
1281 // If no node can be found, we have to insert it.
1282 UIElementDataHashMap::iterator pIter
= rElements
.find( ResourceURL
);
1283 if ( pIter
!= rElements
.end() )
1284 pIter
->second
= aUIElementData
;
1286 rElements
.insert( UIElementDataHashMap::value_type( ResourceURL
, aUIElementData
));
1288 Reference
< XUIConfigurationManager
> xThis( static_cast< OWeakObject
* >( this ), UNO_QUERY
);
1289 Reference
< XInterface
> xIfac( xThis
, UNO_QUERY
);
1291 // Create event to notify listener about replaced element settings
1292 ui::ConfigurationEvent aEvent
;
1294 aEvent
.ResourceURL
= ResourceURL
;
1295 aEvent
.Accessor
<<= xThis
;
1296 aEvent
.Source
= xIfac
;
1297 aEvent
.ReplacedElement
<<= pDataSettings
->xSettings
;
1298 aEvent
.Element
<<= aUIElementData
.xSettings
;
1302 implts_notifyContainerListener( aEvent
, NotifyOp_Replace
);
1306 throw NoSuchElementException();
1310 void SAL_CALL
ModuleUIConfigurationManager::removeSettings( const OUString
& ResourceURL
)
1311 throw ( NoSuchElementException
, IllegalArgumentException
, IllegalAccessException
, RuntimeException
, std::exception
)
1313 sal_Int16 nElementType
= RetrieveTypeFromResourceURL( ResourceURL
);
1315 if (( nElementType
== ::com::sun::star::ui::UIElementType::UNKNOWN
) ||
1316 ( nElementType
>= ::com::sun::star::ui::UIElementType::COUNT
))
1317 throw IllegalArgumentException();
1318 else if ( m_bReadOnly
)
1319 throw IllegalAccessException();
1322 SolarMutexClearableGuard aGuard
;
1325 throw DisposedException();
1327 UIElementData
* pDataSettings
= impl_findUIElementData( ResourceURL
, nElementType
);
1328 if ( pDataSettings
)
1330 // If element settings are default, we don't need to change anything!
1331 if ( pDataSettings
->bDefault
)
1335 Reference
< XIndexAccess
> xRemovedSettings
= pDataSettings
->xSettings
;
1336 pDataSettings
->bDefault
= true;
1338 // check if this is a default layer node
1339 if ( !pDataSettings
->bDefaultNode
)
1340 pDataSettings
->bModified
= true; // we have to remove this node from the user layer!
1341 pDataSettings
->xSettings
.clear();
1342 m_bModified
= true; // user layer must be written
1344 // Modify type container
1345 UIElementType
& rElementType
= m_aUIElements
[LAYER_USERDEFINED
][nElementType
];
1346 rElementType
.bModified
= true;
1348 Reference
< XUIConfigurationManager
> xThis( static_cast< OWeakObject
* >( this ), UNO_QUERY
);
1349 Reference
< XInterface
> xIfac( xThis
, UNO_QUERY
);
1351 // Check if we have settings in the default layer which replaces the user-defined one!
1352 UIElementData
* pDefaultDataSettings
= impl_findUIElementData( ResourceURL
, nElementType
);
1353 if ( pDefaultDataSettings
)
1355 // Create event to notify listener about replaced element settings
1356 ui::ConfigurationEvent aEvent
;
1358 aEvent
.ResourceURL
= ResourceURL
;
1359 aEvent
.Accessor
<<= xThis
;
1360 aEvent
.Source
= xIfac
;
1361 aEvent
.Element
<<= xRemovedSettings
;
1362 aEvent
.ReplacedElement
<<= pDefaultDataSettings
->xSettings
;
1366 implts_notifyContainerListener( aEvent
, NotifyOp_Replace
);
1370 // Create event to notify listener about removed element settings
1371 ui::ConfigurationEvent aEvent
;
1373 aEvent
.ResourceURL
= ResourceURL
;
1374 aEvent
.Accessor
<<= xThis
;
1375 aEvent
.Source
= xIfac
;
1376 aEvent
.Element
<<= xRemovedSettings
;
1380 implts_notifyContainerListener( aEvent
, NotifyOp_Remove
);
1385 throw NoSuchElementException();
1389 void SAL_CALL
ModuleUIConfigurationManager::insertSettings( const OUString
& NewResourceURL
, const Reference
< XIndexAccess
>& aNewData
)
1390 throw ( ElementExistException
, IllegalArgumentException
, IllegalAccessException
, RuntimeException
, std::exception
)
1392 sal_Int16 nElementType
= RetrieveTypeFromResourceURL( NewResourceURL
);
1394 if (( nElementType
== ::com::sun::star::ui::UIElementType::UNKNOWN
) ||
1395 ( nElementType
>= ::com::sun::star::ui::UIElementType::COUNT
))
1396 throw IllegalArgumentException();
1397 else if ( m_bReadOnly
)
1398 throw IllegalAccessException();
1401 SolarMutexClearableGuard aGuard
;
1404 throw DisposedException();
1406 UIElementData
* pDataSettings
= impl_findUIElementData( NewResourceURL
, nElementType
);
1407 if ( !pDataSettings
)
1409 UIElementData aUIElementData
;
1411 aUIElementData
.bDefault
= false;
1412 aUIElementData
.bDefaultNode
= false;
1413 aUIElementData
.bModified
= true;
1415 // Create a copy of the data if the container is not const
1416 Reference
< XIndexReplace
> xReplace( aNewData
, UNO_QUERY
);
1417 if ( xReplace
.is() )
1418 aUIElementData
.xSettings
= Reference
< XIndexAccess
>( static_cast< OWeakObject
* >( new ConstItemContainer( aNewData
) ), UNO_QUERY
);
1420 aUIElementData
.xSettings
= aNewData
;
1421 aUIElementData
.aName
= RetrieveNameFromResourceURL( NewResourceURL
) + m_aXMLPostfix
;
1422 aUIElementData
.aResourceURL
= NewResourceURL
;
1425 UIElementType
& rElementType
= m_aUIElements
[LAYER_USERDEFINED
][nElementType
];
1426 rElementType
.bModified
= true;
1428 UIElementDataHashMap
& rElements
= rElementType
.aElementsHashMap
;
1429 rElements
.insert( UIElementDataHashMap::value_type( NewResourceURL
, aUIElementData
));
1431 Reference
< XIndexAccess
> xInsertSettings( aUIElementData
.xSettings
);
1432 Reference
< XUIConfigurationManager
> xThis( static_cast< OWeakObject
* >( this ), UNO_QUERY
);
1434 // Create event to notify listener about removed element settings
1435 ui::ConfigurationEvent aEvent
;
1437 aEvent
.ResourceURL
= NewResourceURL
;
1438 aEvent
.Accessor
<<= xThis
;
1439 aEvent
.Source
= xThis
;
1440 aEvent
.Element
<<= xInsertSettings
;
1444 implts_notifyContainerListener( aEvent
, NotifyOp_Insert
);
1447 throw ElementExistException();
1451 Reference
< XInterface
> SAL_CALL
ModuleUIConfigurationManager::getImageManager() throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1456 throw DisposedException();
1458 if ( !m_xModuleImageManager
.is() )
1460 m_xModuleImageManager
= Reference
< XComponent
>( static_cast< cppu::OWeakObject
*>( new ModuleImageManager( m_xContext
)),
1462 Reference
< XInitialization
> xInit( m_xModuleImageManager
, UNO_QUERY
);
1464 Sequence
< Any
> aPropSeq( 3 );
1465 PropertyValue aPropValue
;
1466 aPropValue
.Name
= "UserConfigStorage";
1467 aPropValue
.Value
= makeAny( m_xUserConfigStorage
);
1468 aPropSeq
[0] = makeAny( aPropValue
);
1469 aPropValue
.Name
= "ModuleIdentifier";
1470 aPropValue
.Value
= makeAny( m_aModuleIdentifier
);
1471 aPropSeq
[1] = makeAny( aPropValue
);
1472 aPropValue
.Name
= "UserRootCommit";
1473 aPropValue
.Value
= makeAny( m_xUserRootCommit
);
1474 aPropSeq
[2] = makeAny( aPropValue
);
1476 xInit
->initialize( aPropSeq
);
1479 return Reference
< XInterface
>( m_xModuleImageManager
, UNO_QUERY
);
1482 Reference
< ui::XAcceleratorConfiguration
> SAL_CALL
ModuleUIConfigurationManager::getShortCutManager() throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1487 throw DisposedException();
1489 if ( !m_xModuleAcceleratorManager
.is() ) try
1491 m_xModuleAcceleratorManager
= ui::ModuleAcceleratorConfiguration::
1492 createWithModuleIdentifier(m_xContext
, m_aModuleIdentifier
);
1494 catch ( const css::uno::DeploymentException
& )
1496 SAL_WARN("fwk.uiconfiguration", "ModuleAcceleratorConfiguration"
1497 " not available. This should happen only on mobile platforms.");
1500 return m_xModuleAcceleratorManager
;
1503 Reference
< XInterface
> SAL_CALL
ModuleUIConfigurationManager::getEventsManager() throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1505 return Reference
< XInterface
>();
1508 // XModuleUIConfigurationManager
1509 sal_Bool SAL_CALL
ModuleUIConfigurationManager::isDefaultSettings( const OUString
& ResourceURL
)
1510 throw (::com::sun::star::lang::IllegalArgumentException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1512 sal_Int16 nElementType
= RetrieveTypeFromResourceURL( ResourceURL
);
1514 if (( nElementType
== ::com::sun::star::ui::UIElementType::UNKNOWN
) ||
1515 ( nElementType
>= ::com::sun::star::ui::UIElementType::COUNT
))
1516 throw IllegalArgumentException();
1522 throw DisposedException();
1524 UIElementData
* pDataSettings
= impl_findUIElementData( ResourceURL
, nElementType
, false );
1525 if ( pDataSettings
&& pDataSettings
->bDefaultNode
)
1532 Reference
< XIndexAccess
> SAL_CALL
ModuleUIConfigurationManager::getDefaultSettings( const OUString
& ResourceURL
)
1533 throw (::com::sun::star::container::NoSuchElementException
, ::com::sun::star::lang::IllegalArgumentException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1535 sal_Int16 nElementType
= RetrieveTypeFromResourceURL( ResourceURL
);
1537 if (( nElementType
== ::com::sun::star::ui::UIElementType::UNKNOWN
) ||
1538 ( nElementType
>= ::com::sun::star::ui::UIElementType::COUNT
))
1539 throw IllegalArgumentException();
1545 throw DisposedException();
1547 // preload list of element types on demand
1548 impl_preloadUIElementTypeList( LAYER_DEFAULT
, nElementType
);
1550 // Look into our default vector/unordered_map combination
1551 UIElementDataHashMap
& rDefaultHashMap
= m_aUIElements
[LAYER_DEFAULT
][nElementType
].aElementsHashMap
;
1552 UIElementDataHashMap::iterator pIter
= rDefaultHashMap
.find( ResourceURL
);
1553 if ( pIter
!= rDefaultHashMap
.end() )
1555 if ( !pIter
->second
.xSettings
.is() )
1556 impl_requestUIElementData( nElementType
, LAYER_DEFAULT
, pIter
->second
);
1557 return pIter
->second
.xSettings
;
1561 // Nothing has been found!
1562 throw NoSuchElementException();
1565 // XUIConfigurationPersistence
1566 void SAL_CALL
ModuleUIConfigurationManager::reload() throw (::com::sun::star::uno::Exception
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1568 SolarMutexClearableGuard aGuard
;
1571 throw DisposedException();
1573 if ( m_xUserConfigStorage
.is() && m_bModified
&& !m_bReadOnly
)
1575 // Try to access our module sub folder
1576 ConfigEventNotifyContainer aRemoveNotifyContainer
;
1577 ConfigEventNotifyContainer aReplaceNotifyContainer
;
1578 for ( sal_Int16 i
= 1; i
< ::com::sun::star::ui::UIElementType::COUNT
; i
++ )
1582 UIElementType
& rUserElementType
= m_aUIElements
[LAYER_USERDEFINED
][i
];
1583 UIElementType
& rDefaultElementType
= m_aUIElements
[LAYER_DEFAULT
][i
];
1585 if ( rUserElementType
.bModified
)
1586 impl_reloadElementTypeData( rUserElementType
, rDefaultElementType
, aRemoveNotifyContainer
, aReplaceNotifyContainer
);
1588 catch ( const Exception
& )
1590 throw IOException();
1594 m_bModified
= false;
1596 // Unlock mutex before notify our listeners
1599 // Notify our listeners
1600 for ( sal_uInt32 j
= 0; j
< aRemoveNotifyContainer
.size(); j
++ )
1601 implts_notifyContainerListener( aRemoveNotifyContainer
[j
], NotifyOp_Remove
);
1602 for ( sal_uInt32 k
= 0; k
< aReplaceNotifyContainer
.size(); k
++ )
1603 implts_notifyContainerListener( aReplaceNotifyContainer
[k
], NotifyOp_Replace
);
1607 void SAL_CALL
ModuleUIConfigurationManager::store() throw (::com::sun::star::uno::Exception
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1612 throw DisposedException();
1614 if ( m_xUserConfigStorage
.is() && m_bModified
&& !m_bReadOnly
)
1616 // Try to access our module sub folder
1617 for ( int i
= 1; i
< ::com::sun::star::ui::UIElementType::COUNT
; i
++ )
1621 UIElementType
& rElementType
= m_aUIElements
[LAYER_USERDEFINED
][i
];
1622 Reference
< XStorage
> xStorage( rElementType
.xStorage
, UNO_QUERY
);
1624 if ( rElementType
.bModified
&& xStorage
.is() )
1626 impl_storeElementTypeData( xStorage
, rElementType
);
1627 m_pStorageHandler
[i
]->commitUserChanges();
1630 catch ( const Exception
& )
1632 throw IOException();
1636 m_bModified
= false;
1640 void SAL_CALL
ModuleUIConfigurationManager::storeToStorage( const Reference
< XStorage
>& Storage
) throw (::com::sun::star::uno::Exception
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1645 throw DisposedException();
1647 if ( m_xUserConfigStorage
.is() && m_bModified
&& !m_bReadOnly
)
1649 // Try to access our module sub folder
1650 for ( int i
= 1; i
< ::com::sun::star::ui::UIElementType::COUNT
; i
++ )
1654 Reference
< XStorage
> xElementTypeStorage( Storage
->openStorageElement(
1655 OUString::createFromAscii( UIELEMENTTYPENAMES
[i
] ), ElementModes::READWRITE
));
1656 UIElementType
& rElementType
= m_aUIElements
[LAYER_USERDEFINED
][i
];
1658 if ( rElementType
.bModified
&& xElementTypeStorage
.is() )
1659 impl_storeElementTypeData( xElementTypeStorage
, rElementType
, false ); // store data to storage, but don't reset modify flag!
1661 catch ( const Exception
& )
1663 throw IOException();
1667 Reference
< XTransactedObject
> xTransactedObject( Storage
, UNO_QUERY
);
1668 if ( xTransactedObject
.is() )
1669 xTransactedObject
->commit();
1673 sal_Bool SAL_CALL
ModuleUIConfigurationManager::isModified() throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1680 sal_Bool SAL_CALL
ModuleUIConfigurationManager::isReadOnly() throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1687 void ModuleUIConfigurationManager::implts_notifyContainerListener( const ui::ConfigurationEvent
& aEvent
, NotifyOp eOp
)
1689 ::cppu::OInterfaceContainerHelper
* pContainer
= m_aListenerContainer
.getContainer( cppu::UnoType
<com::sun::star::ui::XUIConfigurationListener
>::get());
1690 if ( pContainer
!= NULL
)
1692 ::cppu::OInterfaceIteratorHelper
pIterator( *pContainer
);
1693 while ( pIterator
.hasMoreElements() )
1699 case NotifyOp_Replace
:
1700 static_cast< ::com::sun::star::ui::XUIConfigurationListener
*>(pIterator
.next())->elementReplaced( aEvent
);
1702 case NotifyOp_Insert
:
1703 static_cast< ::com::sun::star::ui::XUIConfigurationListener
*>(pIterator
.next())->elementInserted( aEvent
);
1705 case NotifyOp_Remove
:
1706 static_cast< ::com::sun::star::ui::XUIConfigurationListener
*>(pIterator
.next())->elementRemoved( aEvent
);
1710 catch( const css::uno::RuntimeException
& )
1720 extern "C" SAL_DLLPUBLIC_EXPORT
css::uno::XInterface
* SAL_CALL
1721 com_sun_star_comp_framework_ModuleUIConfigurationManager_get_implementation(
1722 css::uno::XComponentContext
*context
,
1723 css::uno::Sequence
<css::uno::Any
> const &arguments
)
1725 return cppu::acquire(new ModuleUIConfigurationManager(context
, arguments
));
1728 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */