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 "FilterConfigCache.hxx"
22 #include <vcl/graphicfilter.hxx>
23 #include <com/sun/star/uno/Any.h>
24 #include <comphelper/processfactory.hxx>
25 #include <com/sun/star/uno/Exception.hpp>
26 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
27 #include <com/sun/star/beans/XPropertySet.hpp>
28 #include <com/sun/star/configuration/theDefaultProvider.hpp>
29 #include <com/sun/star/container/XNameAccess.hpp>
31 using namespace ::com::sun::star::lang
; // XMultiServiceFactory
32 using namespace ::com::sun::star::container
; // XNameAccess
33 using namespace ::com::sun::star::uno
; // Reference
34 using namespace ::com::sun::star::beans
; // PropertyValue
35 using namespace ::com::sun::star::configuration
;
37 const char* FilterConfigCache::FilterConfigCacheEntry::InternalPixelFilterNameList
[] =
39 IMP_BMP
, IMP_GIF
, IMP_PNG
,IMP_JPEG
, IMP_XBM
, IMP_XPM
,
40 EXP_BMP
, EXP_JPEG
, EXP_PNG
, IMP_MOV
, nullptr
43 const char* FilterConfigCache::FilterConfigCacheEntry::InternalVectorFilterNameList
[] =
45 IMP_SVMETAFILE
, IMP_WMF
, IMP_EMF
, IMP_SVSGF
, IMP_SVSGV
, IMP_SVG
, IMP_PDF
,
46 EXP_SVMETAFILE
, EXP_WMF
, EXP_EMF
, EXP_SVG
, EXP_PDF
, nullptr
49 const char* FilterConfigCache::FilterConfigCacheEntry::ExternalPixelFilterNameList
[] =
51 "egi", "icd", "ipd", "ipx", "ipb", "epb", "epg",
52 "epp", "ira", "era", "itg", "iti", "eti", "exp", nullptr
55 bool FilterConfigCache::bInitialized
= false;
56 sal_Int32
FilterConfigCache::nIndType
= -1;
57 sal_Int32
FilterConfigCache::nIndUIName
= -1;
58 sal_Int32
FilterConfigCache::nIndDocumentService
= -1;
59 sal_Int32
FilterConfigCache::nIndFilterService
= -1;
60 sal_Int32
FilterConfigCache::nIndFlags
= -1;
61 sal_Int32
FilterConfigCache::nIndUserData
= -1;
62 sal_Int32
FilterConfigCache::nIndFileFormatVersion
= -1;
63 sal_Int32
FilterConfigCache::nIndTemplateName
= -1;
65 void FilterConfigCache::FilterConfigCacheEntry::CreateFilterName( const OUString
& rUserDataEntry
)
67 bIsPixelFormat
= bIsInternalFilter
= false;
68 sFilterName
= rUserDataEntry
;
70 for ( pPtr
= InternalPixelFilterNameList
; *pPtr
&& !bIsInternalFilter
; pPtr
++ )
72 if ( sFilterName
.equalsIgnoreAsciiCaseAscii( *pPtr
) )
74 bIsInternalFilter
= true;
75 bIsPixelFormat
= true;
78 for ( pPtr
= InternalVectorFilterNameList
; *pPtr
&& !bIsInternalFilter
; pPtr
++ )
80 if ( sFilterName
.equalsIgnoreAsciiCaseAscii( *pPtr
) )
81 bIsInternalFilter
= true;
83 if ( !bIsInternalFilter
)
85 for ( pPtr
= ExternalPixelFilterNameList
; *pPtr
&& !bIsPixelFormat
; pPtr
++ )
87 if ( sFilterName
.equalsIgnoreAsciiCaseAscii( *pPtr
) )
88 bIsPixelFormat
= true;
90 sExternalFilterName
= sFilterName
;
91 sFilterName
= SVLIBRARY("gie");
95 OUString
FilterConfigCache::FilterConfigCacheEntry::GetShortName()
98 if ( lExtensionList
.getLength() )
100 aShortName
= lExtensionList
[ 0 ];
101 if ( aShortName
.startsWith( "*." ) )
102 aShortName
= aShortName
.replaceAt( 0, 2, "" );
107 /** helper to open the configuration root of the underlying
111 specify, which config package should be opened.
112 Must be one of "types" or "filters"
114 @return A valid object if open was successful. The access on opened
115 data will be readonly. It returns NULL in case open failed.
117 @throws It let pass RuntimeExceptions only.
119 Reference
< XInterface
> openConfig(const char* sPackage
)
120 throw(RuntimeException
)
122 Reference
< XComponentContext
> xContext(
123 comphelper::getProcessComponentContext() );
124 Reference
< XInterface
> xCfg
;
127 // get access to config API (not to file!)
128 Reference
< XMultiServiceFactory
> xConfigProvider
= theDefaultProvider::get( xContext
);
130 Sequence
< Any
> lParams(1);
131 PropertyValue aParam
;
133 // define cfg path for open
134 aParam
.Name
= "nodepath";
135 if (rtl_str_compareIgnoreAsciiCase(sPackage
, "types") == 0)
136 aParam
.Value
<<= OUString( "/org.openoffice.TypeDetection.Types/Types" );
137 if (rtl_str_compareIgnoreAsciiCase(sPackage
, "filters") == 0)
138 aParam
.Value
<<= OUString( "/org.openoffice.TypeDetection.GraphicFilter/Filters" );
139 lParams
[0] = makeAny(aParam
);
141 // get access to file
142 xCfg
= xConfigProvider
->createInstanceWithArguments("com.sun.star.configuration.ConfigurationAccess", lParams
);
144 catch(const RuntimeException
&)
146 catch(const Exception
&)
152 void FilterConfigCache::ImplInit()
154 OUString
STYPE ( "Type" );
155 OUString
SUINAME ( "UIName" );
156 OUString
SFLAGS ( "Flags" );
157 OUString
SMEDIATYPE ( "MediaType" );
158 OUString
SEXTENSIONS ( "Extensions" );
159 OUString
SFORMATNAME ( "FormatName" );
160 OUString
SREALFILTERNAME ( "RealFilterName" );
162 // get access to config
163 Reference
< XNameAccess
> xTypeAccess ( openConfig("types" ), UNO_QUERY
);
164 Reference
< XNameAccess
> xFilterAccess( openConfig("filters"), UNO_QUERY
);
166 if ( xTypeAccess
.is() && xFilterAccess
.is() )
168 Sequence
< OUString
> lAllFilter
= xFilterAccess
->getElementNames();
169 sal_Int32 nAllFilterCount
= lAllFilter
.getLength();
171 for ( sal_Int32 i
= 0; i
< nAllFilterCount
; i
++ )
173 OUString sInternalFilterName
= lAllFilter
[ i
];
174 Reference
< XPropertySet
> xFilterSet
;
175 xFilterAccess
->getByName( sInternalFilterName
) >>= xFilterSet
;
176 if (!xFilterSet
.is())
179 FilterConfigCacheEntry aEntry
;
181 aEntry
.sInternalFilterName
= sInternalFilterName
;
182 xFilterSet
->getPropertyValue(STYPE
) >>= aEntry
.sType
;
183 xFilterSet
->getPropertyValue(SUINAME
) >>= aEntry
.sUIName
;
184 xFilterSet
->getPropertyValue(SREALFILTERNAME
) >>= aEntry
.sFilterType
;
185 Sequence
< OUString
> lFlags
;
186 xFilterSet
->getPropertyValue(SFLAGS
) >>= lFlags
;
187 if (lFlags
.getLength()!=1 || lFlags
[0].isEmpty())
189 if (lFlags
[0].equalsIgnoreAsciiCase("import"))
191 else if (lFlags
[0].equalsIgnoreAsciiCase("export"))
194 OUString sFormatName
;
195 xFilterSet
->getPropertyValue(SFORMATNAME
) >>= sFormatName
;
196 aEntry
.CreateFilterName( sFormatName
);
198 Reference
< XPropertySet
> xTypeSet
;
199 xTypeAccess
->getByName( aEntry
.sType
) >>= xTypeSet
;
203 xTypeSet
->getPropertyValue(SMEDIATYPE
) >>= aEntry
.sMediaType
;
204 xTypeSet
->getPropertyValue(SEXTENSIONS
) >>= aEntry
.lExtensionList
;
206 // The first extension will be used
207 // to generate our internal FilterType ( BMP, WMF ... )
208 OUString
aExtension( aEntry
.GetShortName() );
209 if (aExtension
.getLength() != 3)
212 if ( aEntry
.nFlags
& 1 )
213 aImport
.push_back( aEntry
);
214 if ( aEntry
.nFlags
& 2 )
215 aExport
.push_back( aEntry
);
217 // bFilterEntryCreated!?
218 if (!( aEntry
.nFlags
& 3 ))
219 continue; //? Entry was already inserted ... but following code will be suppressed?!
224 const char* FilterConfigCache::InternalFilterListForSvxLight
[] =
252 "svm","1","SVMETAFILE",
253 "svm","2","SVMETAFILE",
269 void FilterConfigCache::ImplInitSmart()
272 for ( pPtr
= InternalFilterListForSvxLight
; *pPtr
; pPtr
++ )
274 FilterConfigCacheEntry aEntry
;
276 OUString
sExtension( OUString::createFromAscii( *pPtr
++ ) );
278 aEntry
.lExtensionList
.realloc( 1 );
279 aEntry
.lExtensionList
[ 0 ] = sExtension
;
281 aEntry
.sType
= sExtension
;
282 aEntry
.sUIName
= sExtension
;
284 OString
sFlags( *pPtr
++ );
285 aEntry
.nFlags
= sFlags
.toInt32();
287 OUString
sUserData( OUString::createFromAscii( *pPtr
) );
288 aEntry
.CreateFilterName( sUserData
);
290 if ( aEntry
.nFlags
& 1 )
291 aImport
.push_back( aEntry
);
292 if ( aEntry
.nFlags
& 2 )
293 aExport
.push_back( aEntry
);
297 FilterConfigCache::FilterConfigCache( bool bConfig
) :
298 bUseConfig ( bConfig
)
306 FilterConfigCache::~FilterConfigCache()
310 OUString
FilterConfigCache::GetImportFilterName( sal_uInt16 nFormat
)
312 if( nFormat
< aImport
.size() )
313 return aImport
[ nFormat
].sFilterName
;
317 sal_uInt16
FilterConfigCache::GetImportFormatNumber( const OUString
& rFormatName
)
319 std::vector
< FilterConfigCacheEntry
>::const_iterator aIter
, aEnd
;
320 for (aIter
= aImport
.begin(), aEnd
= aImport
.end(); aIter
!= aEnd
; ++aIter
)
322 if ( aIter
->sUIName
.equalsIgnoreAsciiCase( rFormatName
) )
323 return sal::static_int_cast
< sal_uInt16
>(aIter
- aImport
.begin());
325 return GRFILTER_FORMAT_NOTFOUND
;
328 /// get the index of the filter that matches this extension
329 sal_uInt16
FilterConfigCache::GetImportFormatNumberForExtension( const OUString
& rExt
)
331 std::vector
< FilterConfigCacheEntry
>::const_iterator aIter
, aEnd
;
332 for (aIter
= aImport
.begin(), aEnd
= aImport
.end(); aIter
!= aEnd
; ++aIter
)
334 for ( sal_Int32 i
= 0; i
< aIter
->lExtensionList
.getLength(); i
++ )
336 if ( aIter
->lExtensionList
[i
].equalsIgnoreAsciiCase( rExt
) )
337 return sal::static_int_cast
< sal_uInt16
>( aIter
- aImport
.begin() );
340 return GRFILTER_FORMAT_NOTFOUND
;
343 sal_uInt16
FilterConfigCache::GetImportFormatNumberForShortName( const OUString
& rShortName
)
345 std::vector
< FilterConfigCacheEntry
>::const_iterator aEnd
;
346 std::vector
< FilterConfigCacheEntry
>::iterator aIter
;
347 for (aIter
= aImport
.begin(), aEnd
= aImport
.end(); aIter
!= aEnd
; ++aIter
)
349 if ( aIter
->GetShortName().equalsIgnoreAsciiCase( rShortName
) )
350 return sal::static_int_cast
< sal_uInt16
>(aIter
- aImport
.begin());
352 return GRFILTER_FORMAT_NOTFOUND
;
355 sal_uInt16
FilterConfigCache::GetImportFormatNumberForTypeName( const OUString
& rType
)
357 std::vector
< FilterConfigCacheEntry
>::const_iterator aIter
, aEnd
;
358 for (aIter
= aImport
.begin(), aEnd
= aImport
.end(); aIter
!= aEnd
; ++aIter
)
360 if ( aIter
->sType
.equalsIgnoreAsciiCase( rType
) )
361 return sal::static_int_cast
< sal_uInt16
>(aIter
- aImport
.begin());
363 return GRFILTER_FORMAT_NOTFOUND
;
366 OUString
FilterConfigCache::GetImportFormatName( sal_uInt16 nFormat
)
368 if( nFormat
< aImport
.size() )
369 return aImport
[ nFormat
].sUIName
;
373 OUString
FilterConfigCache::GetImportFormatMediaType( sal_uInt16 nFormat
)
375 if( nFormat
< aImport
.size() )
376 return aImport
[ nFormat
].sMediaType
;
380 OUString
FilterConfigCache::GetImportFormatShortName( sal_uInt16 nFormat
)
382 if( nFormat
< aImport
.size() )
383 return aImport
[ nFormat
].GetShortName();
387 OUString
FilterConfigCache::GetImportFormatExtension( sal_uInt16 nFormat
, sal_Int32 nEntry
)
389 if ( (nFormat
< aImport
.size()) && (nEntry
< aImport
[ nFormat
].lExtensionList
.getLength()) )
390 return aImport
[ nFormat
].lExtensionList
[ nEntry
];
394 OUString
FilterConfigCache::GetImportFilterType( sal_uInt16 nFormat
)
396 if( nFormat
< aImport
.size() )
397 return aImport
[ nFormat
].sType
;
401 OUString
FilterConfigCache::GetImportFilterTypeName( sal_uInt16 nFormat
)
403 if( nFormat
< aImport
.size() )
404 return aImport
[ nFormat
].sFilterType
;
408 OUString
FilterConfigCache::GetExternalFilterName(sal_uInt16 nFormat
, bool bExport
)
412 if (nFormat
< aExport
.size())
413 return aExport
[nFormat
].sExternalFilterName
;
417 if (nFormat
< aImport
.size())
418 return aImport
[nFormat
].sExternalFilterName
;
423 OUString
FilterConfigCache::GetImportWildcard(sal_uInt16 nFormat
, sal_Int32 nEntry
)
425 OUString
aWildcard( GetImportFormatExtension( nFormat
, nEntry
) );
426 if ( !aWildcard
.isEmpty() )
427 aWildcard
= aWildcard
.replaceAt( 0, 0, "*." );
431 bool FilterConfigCache::IsImportInternalFilter( sal_uInt16 nFormat
)
433 return (nFormat
< aImport
.size()) && aImport
[ nFormat
].bIsInternalFilter
;
436 OUString
FilterConfigCache::GetExportFilterName( sal_uInt16 nFormat
)
438 if( nFormat
< aExport
.size() )
439 return aExport
[ nFormat
].sFilterName
;
443 sal_uInt16
FilterConfigCache::GetExportFormatNumber(const OUString
& rFormatName
)
445 std::vector
< FilterConfigCacheEntry
>::const_iterator aIter
, aEnd
;
446 for (aIter
= aExport
.begin(), aEnd
= aExport
.end(); aIter
!= aEnd
; ++aIter
)
448 if ( aIter
->sUIName
.equalsIgnoreAsciiCase( rFormatName
) )
449 return sal::static_int_cast
< sal_uInt16
>(aIter
- aExport
.begin());
451 return GRFILTER_FORMAT_NOTFOUND
;
454 sal_uInt16
FilterConfigCache::GetExportFormatNumberForMediaType( const OUString
& rMediaType
)
456 std::vector
< FilterConfigCacheEntry
>::const_iterator aIter
, aEnd
;
457 for (aIter
= aExport
.begin(), aEnd
= aExport
.end(); aIter
!= aEnd
; ++aIter
)
459 if ( aIter
->sMediaType
.equalsIgnoreAsciiCase( rMediaType
) )
460 return sal::static_int_cast
< sal_uInt16
>(aIter
- aExport
.begin());
462 return GRFILTER_FORMAT_NOTFOUND
;
465 sal_uInt16
FilterConfigCache::GetExportFormatNumberForShortName( const OUString
& rShortName
)
467 std::vector
< FilterConfigCacheEntry
>::const_iterator aEnd
;
468 std::vector
< FilterConfigCacheEntry
>::iterator aIter
;
469 for (aIter
= aExport
.begin(), aEnd
= aExport
.end(); aIter
!= aEnd
; ++aIter
)
471 if ( aIter
->GetShortName().equalsIgnoreAsciiCase( rShortName
) )
472 return sal::static_int_cast
< sal_uInt16
>(aIter
- aExport
.begin());
474 return GRFILTER_FORMAT_NOTFOUND
;
477 sal_uInt16
FilterConfigCache::GetExportFormatNumberForTypeName( const OUString
& rType
)
479 std::vector
< FilterConfigCacheEntry
>::const_iterator aIter
, aEnd
;
480 for (aIter
= aExport
.begin(), aEnd
= aExport
.end(); aIter
!= aEnd
; ++aIter
)
482 if ( aIter
->sType
.equalsIgnoreAsciiCase( rType
) )
483 return sal::static_int_cast
< sal_uInt16
>(aIter
- aExport
.begin());
485 return GRFILTER_FORMAT_NOTFOUND
;
488 OUString
FilterConfigCache::GetExportFormatName( sal_uInt16 nFormat
)
490 if( nFormat
< aExport
.size() )
491 return aExport
[ nFormat
].sUIName
;
495 OUString
FilterConfigCache::GetExportFormatMediaType( sal_uInt16 nFormat
)
497 if( nFormat
< aExport
.size() )
498 return aExport
[ nFormat
].sMediaType
;
502 OUString
FilterConfigCache::GetExportFormatShortName( sal_uInt16 nFormat
)
504 if( nFormat
< aExport
.size() )
505 return aExport
[ nFormat
].GetShortName();
509 OUString
FilterConfigCache::GetExportFormatExtension( sal_uInt16 nFormat
, sal_Int32 nEntry
)
511 if ( (nFormat
< aExport
.size()) && (nEntry
< aExport
[ nFormat
].lExtensionList
.getLength()) )
512 return aExport
[ nFormat
].lExtensionList
[ nEntry
];
516 OUString
FilterConfigCache::GetExportInternalFilterName( sal_uInt16 nFormat
)
518 if( nFormat
< aExport
.size() )
519 return aExport
[ nFormat
].sInternalFilterName
;
523 OUString
FilterConfigCache::GetExportWildcard( sal_uInt16 nFormat
, sal_Int32 nEntry
)
525 OUString
aWildcard( GetExportFormatExtension( nFormat
, nEntry
) );
526 if ( !aWildcard
.isEmpty() )
527 aWildcard
= aWildcard
.replaceAt( 0, 0, "*." );
531 bool FilterConfigCache::IsExportInternalFilter( sal_uInt16 nFormat
)
533 return (nFormat
< aExport
.size()) && aExport
[ nFormat
].bIsInternalFilter
;
536 bool FilterConfigCache::IsExportPixelFormat( sal_uInt16 nFormat
)
538 return (nFormat
< aExport
.size()) && aExport
[ nFormat
].bIsPixelFormat
;
541 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */