Files
loongoffice/xmlhelp/source/treeview/tvread.cxx
Thomas Arnhold ba0a57702c remove OUString wrap for string literals
For some functions and all kinds of Exceptions.

CannotConvertException
CloseVetoException
DisposedException
EmptyUndoStackException
ErrorCodeIOException
Exception
GridInvalidDataException
GridInvalidModelException
IOException
IllegalAccessException
IllegalArgumentException
IllegalTypeException
IndexOutOfBoundsException
NoMasterException
NoSuchElementException
NoSupportException
PropertyVetoException
RuntimeException
SAXException
ScannerException
StorageWrappedTargetException
UnsupportedFlavorException
VetoException
WrappedTargetException
ZipIOException
throwGenericSQLException
throwIllegallArgumentException

createInstance
createInstanceWithContext
forName
getByName
getPackageManager
getPropertyValue
getUnpackedValueOrDefault
getValueByName
hasPropertyByName
openKey
setName
setPropertyValue
supportsService

bash command:

for i in `cat list`; do git grep "$i\s*(\s*OUString(\s*\"" -- '*.[hc]xx'
	| cut -d ':' -f1 | sort -u
	| xargs sed -i
		-e "s/\(\<$i\s*(\)\s*OUString(\s*\(\"[^\")\\]*\"\)\s*)\s*/\1\2/g"
		-e "s/\($i.*\)\"+ /\1\" + /g";
done

Change-Id: Iaf8e641b0abf28c082906014f87a183517630535
Reviewed-on: https://gerrit.libreoffice.org/4624
Tested-by: LibreOffice gerrit bot <gerrit@libreoffice.org>
Reviewed-by: Thomas Arnhold <thomas@arnhold.org>
Tested-by: Thomas Arnhold <thomas@arnhold.org>
2013-06-29 21:52:54 +00:00

1261 lines
38 KiB
C++

/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/*
* This file is part of the LibreOffice project.
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* This file incorporates work covered by the following license notice:
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed
* with this work for additional information regarding copyright
* ownership. The ASF licenses this file to you under the Apache
* License, Version 2.0 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy of
* the License at http://www.apache.org/licenses/LICENSE-2.0 .
*/
#include <string.h>
#include <rtl/ustrbuf.hxx>
#include <osl/diagnose.h>
#include "tvread.hxx"
#include <expat.h>
#include <osl/file.hxx>
#include <unotools/configmgr.hxx>
#include <com/sun/star/configuration/theDefaultProvider.hpp>
#include <com/sun/star/ucb/SimpleFileAccess.hpp>
#include <com/sun/star/frame/XConfigManager.hpp>
#include <com/sun/star/beans/PropertyValue.hpp>
#include <comphelper/processfactory.hxx>
#include "com/sun/star/deployment/thePackageManagerFactory.hpp"
#include <com/sun/star/util/theMacroExpander.hpp>
#include <com/sun/star/uri/UriReferenceFactory.hpp>
#include <com/sun/star/uri/XVndSunStarExpandUrl.hpp>
#include <i18nlangtag/languagetag.hxx>
#include <comphelper/string.hxx>
#include <unotools/pathoptions.hxx>
namespace treeview {
class TVDom
{
friend class TVChildTarget;
friend class TVRead;
public:
TVDom( TVDom* arent = 0 )
: kind( other ),
parent( arent ),
children( 0 )
{
}
~TVDom()
{
for( unsigned i = 0; i < children.size(); ++i )
delete children[i];
}
TVDom* newChild()
{
children.push_back( new TVDom( this ) );
return children.back();
}
TVDom* newChild(TVDom* p)
{
children.push_back( p );
p->parent = this;
return children.back();
}
TVDom* getParent() const
{
if( parent )
return parent;
else
return const_cast<TVDom*>(this); // I am my own parent, if I am the root
}
enum Kind {
tree_view,
tree_node,
tree_leaf,
other
};
bool isLeaf() const { return kind == TVDom::tree_leaf; }
void setKind( Kind ind ) { kind = ind; }
Kind getKind( ) const { return kind; }
void setApplication( const char* appl )
{
application = OUString( (sal_Char*)(appl),
strlen( appl ),
RTL_TEXTENCODING_UTF8 );
}
void setTitle( const char* itle )
{
title += OUString( (sal_Char*)(itle),
strlen( itle ),
RTL_TEXTENCODING_UTF8 );
}
void setTitle( const XML_Char* itle,int len )
{
title += OUString( (sal_Char*)(itle),
len,
RTL_TEXTENCODING_UTF8 );
}
void setId( const char* d )
{
id = OUString( (sal_Char*)(d),
strlen( d ),
RTL_TEXTENCODING_UTF8 );
}
void setAnchor( const char* nchor )
{
anchor = OUString( (sal_Char*)(nchor),
strlen( nchor ),
RTL_TEXTENCODING_UTF8 );
}
OUString getTargetURL()
{
if( targetURL.isEmpty() )
{
sal_Int32 len;
for ( const TVDom* p = this;; p = p->parent )
{
len = p->application.getLength();
if ( len != 0 )
break;
}
OUStringBuffer strBuff( 22 + len + id.getLength() );
strBuff.appendAscii(
"vnd.sun.star.help://"
).append(id);
targetURL = strBuff.makeStringAndClear();
}
return targetURL;
}
private:
Kind kind;
OUString application;
OUString title;
OUString id;
OUString anchor;
OUString targetURL;
TVDom *parent;
std::vector< TVDom* > children;
};
}
using namespace treeview;
using namespace com::sun::star;
using namespace com::sun::star::uno;
using namespace com::sun::star::beans;
using namespace com::sun::star::configuration;
using namespace com::sun::star::lang;
using namespace com::sun::star::util;
using namespace com::sun::star::frame;
using namespace com::sun::star::container;
using namespace com::sun::star::deployment;
ConfigData::ConfigData()
: prodName("%PRODUCTNAME"),
prodVersion("%PRODUCTVERSION"),
vendName("%VENDORNAME"),
vendVersion("%VENDORVERSION"),
vendShort("%VENDORSHORT")
{
}
void SAL_CALL ConfigData::replaceName( OUString& oustring ) const
{
sal_Int32 idx = -1,k = 0,off;
bool cap = false;
OUStringBuffer aStrBuf( 0 );
while( ( idx = oustring.indexOf( sal_Unicode('%'),++idx ) ) != -1 )
{
if( oustring.indexOf( prodName,idx ) == idx )
off = PRODUCTNAME;
else if( oustring.indexOf( prodVersion,idx ) == idx )
off = PRODUCTVERSION;
else if( oustring.indexOf( vendName,idx ) == idx )
off = VENDORNAME;
else if( oustring.indexOf( vendVersion,idx ) == idx )
off = VENDORVERSION;
else if( oustring.indexOf( vendShort,idx ) == idx )
off = VENDORSHORT;
else
off = -1;
if( off != -1 )
{
if( ! cap )
{
cap = true;
aStrBuf.ensureCapacity( 256 );
}
aStrBuf.append( &oustring.getStr()[k],idx - k );
aStrBuf.append( m_vReplacement[off] );
k = idx + m_vAdd[off];
}
}
if( cap )
{
if( k < oustring.getLength() )
aStrBuf.append( &oustring.getStr()[k],oustring.getLength()-k );
oustring = aStrBuf.makeStringAndClear();
}
}
//////////////////////////////////////////////////////////////////////////
// XInterface
//////////////////////////////////////////////////////////////////////////
void SAL_CALL
TVBase::acquire(
void )
throw()
{
OWeakObject::acquire();
}
void SAL_CALL
TVBase::release(
void )
throw()
{
OWeakObject::release();
}
Any SAL_CALL
TVBase::queryInterface(
const Type& rType )
throw( RuntimeException )
{
Any aRet = cppu::queryInterface( rType,
(static_cast< XTypeProvider* >(this)),
(static_cast< XNameAccess* >(this)),
(static_cast< XHierarchicalNameAccess* >(this)),
(static_cast< XChangesNotifier* >(this)),
(static_cast< XComponent* >(this)) );
return aRet.hasValue() ? aRet : OWeakObject::queryInterface( rType );
}
////////////////////////////////////////////////////////////////////////////////
//
// XTypeProvider methods.
XTYPEPROVIDER_IMPL_5( TVBase,
XTypeProvider,
XNameAccess,
XHierarchicalNameAccess,
XChangesNotifier,
XComponent );
// TVRead
TVRead::TVRead( const ConfigData& configData,TVDom* tvDom )
{
if( ! tvDom )
return;
Title = tvDom->title;
configData.replaceName( Title );
if( tvDom->isLeaf() )
{
TargetURL = ( tvDom->getTargetURL() + configData.appendix );
if( !tvDom->anchor.isEmpty() )
TargetURL += ( OUString( "#" ) +
tvDom->anchor );
}
else
Children = new TVChildTarget( configData,tvDom );
}
TVRead::~TVRead()
{
}
// XNameAccess
Any SAL_CALL
TVRead::getByName( const OUString& aName )
throw( NoSuchElementException,
WrappedTargetException,
RuntimeException )
{
bool found( true );
Any aAny;
if( aName.compareToAscii( "Title" ) == 0 )
aAny <<= Title;
else if( aName.compareToAscii( "TargetURL" ) == 0 )
aAny <<= TargetURL;
else if( aName.compareToAscii( "Children" ) == 0 )
{
cppu::OWeakObject* p = Children.get();
aAny <<= Reference< XInterface >( p );
}
else
found = false;
if( found )
return aAny;
throw NoSuchElementException();
}
Sequence< OUString > SAL_CALL
TVRead::getElementNames( )
throw( RuntimeException )
{
Sequence< OUString > seq( 3 );
seq[0] = OUString( "Title" );
seq[1] = OUString( "TargetURL" );
seq[2] = OUString( "Children" );
return seq;
}
sal_Bool SAL_CALL
TVRead::hasByName( const OUString& aName )
throw( RuntimeException )
{
if( aName.compareToAscii( "Title" ) == 0 ||
aName.compareToAscii( "TargetURL" ) == 0 ||
aName.compareToAscii( "Children" ) == 0 )
return true;
return false;
}
// XHierarchicalNameAccess
Any SAL_CALL
TVRead::getByHierarchicalName( const OUString& aName )
throw( NoSuchElementException,
RuntimeException )
{
sal_Int32 idx;
OUString name( aName );
if( ( idx = name.indexOf( sal_Unicode( '/' ) ) ) != -1 &&
name.copy( 0,idx ).compareToAscii( "Children" ) == 0 )
return Children->getByHierarchicalName( name.copy( 1 + idx ) );
return getByName( name );
}
sal_Bool SAL_CALL
TVRead::hasByHierarchicalName( const OUString& aName )
throw( RuntimeException )
{
sal_Int32 idx;
OUString name( aName );
if( ( idx = name.indexOf( sal_Unicode( '/' ) ) ) != -1 &&
name.copy( 0,idx ).compareToAscii( "Children" ) == 0 )
return Children->hasByHierarchicalName( name.copy( 1 + idx ) );
return hasByName( name );
}
/**************************************************************************/
/* */
/* TVChildTarget */
/* */
/**************************************************************************/
extern "C" void start_handler(void *userData,
const XML_Char *name,
const XML_Char **atts)
{
TVDom::Kind kind;
if( strcmp( name,"help_section" ) == 0 ||
strcmp( name,"node" ) == 0 )
kind = TVDom::tree_node;
else if( strcmp( name,"topic" ) == 0 )
kind = TVDom::tree_leaf;
else
return;
TVDom **tvDom = static_cast< TVDom** >( userData );
TVDom *p;
p = *tvDom;
*tvDom = p->newChild();
p = *tvDom;
p->setKind( kind );
while( *atts )
{
if( strcmp( *atts,"application" ) == 0 )
p->setApplication( *(atts+1) );
else if( strcmp( *atts,"title" ) == 0 )
p->setTitle( *(atts+1) );
else if( strcmp( *atts,"id" ) == 0 )
p->setId( *(atts+1) );
else if( strcmp( *atts,"anchor" ) == 0 )
p->setAnchor( *(atts+1) );
atts+=2;
}
}
extern "C" void end_handler(void *userData,
const XML_Char *name )
{
(void)name;
TVDom **tvDom = static_cast< TVDom** >( userData );
*tvDom = (*tvDom)->getParent();
}
extern "C" void data_handler( void *userData,
const XML_Char *s,
int len)
{
TVDom **tvDom = static_cast< TVDom** >( userData );
if( (*tvDom)->isLeaf() )
(*tvDom)->setTitle( s,len );
}
TVChildTarget::TVChildTarget( const ConfigData& configData,TVDom* tvDom )
{
Elements.resize( tvDom->children.size() );
for( unsigned i = 0; i < Elements.size(); ++i )
Elements[i] = new TVRead( configData,tvDom->children[i] );
}
TVChildTarget::TVChildTarget( const Reference< XComponentContext >& xContext )
{
ConfigData configData = init( xContext );
if( configData.locale.isEmpty() || configData.system.isEmpty() )
return;
sal_uInt64 ret,len = 0;
int j = configData.vFileURL.size();
TVDom tvDom;
TVDom* pTVDom = &tvDom;
while( j )
{
len = configData.vFileLen[--j];
char* s = new char[ int(len) ]; // the buffer to hold the installed files
osl::File aFile( configData.vFileURL[j] );
aFile.open( osl_File_OpenFlag_Read );
aFile.read( s,len,ret );
aFile.close();
XML_Parser parser = XML_ParserCreate( 0 );
XML_SetElementHandler( parser,
start_handler,
end_handler );
XML_SetCharacterDataHandler( parser,
data_handler);
XML_SetUserData( parser,&pTVDom ); // does not return this
XML_Status const parsed = XML_Parse(parser, s, int(len), j==0);
SAL_WARN_IF(XML_STATUS_ERROR == parsed, "xmlhelp",
"TVChildTarget::TVChildTarget(): Tree file parsing failed");
XML_ParserFree( parser );
delete[] s;
Check(pTVDom);
}
// now TVDom holds the relevant information
Elements.resize( tvDom.children.size() );
for( unsigned i = 0; i < Elements.size(); ++i )
Elements[i] = new TVRead( configData,tvDom.children[i] );
}
TVChildTarget::~TVChildTarget()
{
}
void TVChildTarget::Check(TVDom* tvDom)
{
if (tvDom->children.empty())
{
return;
}
unsigned i = 0;
bool h = false;
while((i<tvDom->children.size()-1) && (!h))
{
if (((tvDom->children[i])->application == (tvDom->children[tvDom->children.size()-1])->application) &&
((tvDom->children[i])->id == (tvDom->children[tvDom->children.size()-1])->id))
{
TVDom* p = tvDom->children[tvDom->children.size()-1];
for(unsigned k=0; k<p->children.size(); ++k)
if (!SearchAndInsert(p->children[k], tvDom->children[i])) tvDom->children[i]->newChild(p->children[k]);
tvDom->children.pop_back();
h = true;
}
++i;
}
}
bool TVChildTarget::SearchAndInsert(TVDom* p, TVDom* tvDom)
{
if (p->isLeaf()) return false;
bool h = false;
sal_Int32 max = 0;
std::vector< TVDom* >::iterator max_It, i;
max_It = tvDom->children.begin();
sal_Int32 c_int;
sal_Int32 p_int = p->id.toInt32();
////////////////////////////////check this level in the tree
for(i = tvDom->children.begin(); i!=tvDom->children.end(); ++i)
if (!((*i)->isLeaf()) &&
((*i)->id.getLength() == p->id.getLength()) &&
(p->id.replaceAt((*i)->parent->id.getLength(), p->id.getLength()-(*i)->parent->id.getLength(), OUString("")) == (*i)->parent->id)) //prefix check
{
h = true;
c_int = (*i)->id.toInt32();
if (p_int==c_int)
{
(*(tvDom->children.insert(i+1, p)))->parent = tvDom;
return true;
}
else if(c_int>max && c_int < p_int)
{
max = c_int;
max_It = i+1;
}
}
////////////////////////////////recursive call if necessary
if (h) (*(tvDom->children.insert(max_It, p)))->parent = tvDom;
else
{
i = tvDom->children.begin();
while ((i!=tvDom->children.end()) && (!h))
{
h = SearchAndInsert(p, *i);
++i;
}
}
return h;
}
Any SAL_CALL
TVChildTarget::getByName( const OUString& aName )
throw( NoSuchElementException,
WrappedTargetException,
RuntimeException )
{
OUString num( aName.getStr()+2,aName.getLength()-4 );
sal_Int32 idx = num.toInt32() - 1;
if( idx < 0 || Elements.size() <= sal_uInt32( idx ) )
throw NoSuchElementException();
Any aAny;
cppu::OWeakObject* p = Elements[idx].get();
aAny <<= Reference< XInterface >( p );
return aAny;
}
Sequence< OUString > SAL_CALL
TVChildTarget::getElementNames( )
throw( RuntimeException )
{
Sequence< OUString > seq( Elements.size() );
for( unsigned i = 0; i < Elements.size(); ++i )
seq[i] = OUString::valueOf( sal_Int32( 1+i ) );
return seq;
}
sal_Bool SAL_CALL
TVChildTarget::hasByName( const OUString& aName )
throw( RuntimeException )
{
OUString num( aName.getStr()+2,aName.getLength()-4 );
sal_Int32 idx = num.toInt32() - 1;
if( idx < 0 || Elements.size() <= sal_uInt32( idx ) )
return false;
return true;
}
// XHierarchicalNameAccess
Any SAL_CALL
TVChildTarget::getByHierarchicalName( const OUString& aName )
throw( NoSuchElementException,
RuntimeException )
{
sal_Int32 idx;
OUString name( aName );
if( ( idx = name.indexOf( sal_Unicode( '/' ) ) ) != -1 )
{
OUString num( name.getStr()+2,idx-4 );
sal_Int32 pref = num.toInt32() - 1;
if( pref < 0 || Elements.size() <= sal_uInt32( pref ) )
throw NoSuchElementException();
return Elements[pref]->getByHierarchicalName( name.copy( 1 + idx ) );
}
else
return getByName( name );
}
sal_Bool SAL_CALL
TVChildTarget::hasByHierarchicalName( const OUString& aName )
throw( RuntimeException )
{
sal_Int32 idx;
OUString name( aName );
if( ( idx = name.indexOf( sal_Unicode( '/' ) ) ) != -1 )
{
OUString num( name.getStr()+2,idx-4 );
sal_Int32 pref = num.toInt32() - 1;
if( pref < 0 || Elements.size() <= sal_uInt32( pref ) )
return false;
return Elements[pref]->hasByHierarchicalName( name.copy( 1 + idx ) );
}
else
return hasByName( name );
}
ConfigData TVChildTarget::init( const Reference< XComponentContext >& xContext )
{
ConfigData configData;
Reference< XMultiServiceFactory > sProvider( getConfiguration(xContext) );
/**********************************************************************/
/* reading Office.Common */
/**********************************************************************/
Reference< XHierarchicalNameAccess > xHierAccess( getHierAccess( sProvider,
"org.openoffice.Office.Common" ) );
OUString system( getKey( xHierAccess,"Help/System" ) );
sal_Bool showBasic( getBooleanKey(xHierAccess,"Help/ShowBasic") );
OUString instPath( getKey( xHierAccess,"Path/Current/Help" ) );
if( instPath.isEmpty() )
// try to determine path from default
instPath = OUString( "$(instpath)/help" );
// replace anything like $(instpath);
subst( instPath );
/**********************************************************************/
/* reading setup */
/**********************************************************************/
xHierAccess = getHierAccess( sProvider,
"org.openoffice.Setup" );
OUString setupversion( getKey( xHierAccess,"Product/ooSetupVersion" ) );
OUString setupextension;
try
{
Reference< lang::XMultiServiceFactory > xConfigProvider = theDefaultProvider::get( xContext );
uno::Sequence < uno::Any > lParams(1);
beans::PropertyValue aParam ;
aParam.Name = OUString("nodepath");
aParam.Value <<= OUString("/org.openoffice.Setup/Product");
lParams[0] = uno::makeAny(aParam);
// open it
uno::Reference< uno::XInterface > xCFG( xConfigProvider->createInstanceWithArguments(
OUString("com.sun.star.configuration.ConfigurationAccess"),
lParams) );
uno::Reference< container::XNameAccess > xDirectAccess(xCFG, uno::UNO_QUERY);
uno::Any aRet = xDirectAccess->getByName("ooSetupExtension");
aRet >>= setupextension;
}
catch ( uno::Exception& )
{
}
OUString productVersion( setupversion +
OUString( " " ) +
setupextension );
OUString locale( getKey( xHierAccess,"L10N/ooLocale" ) );
// Determine fileurl from url and locale
OUString url;
osl::FileBase::RC errFile = osl::FileBase::getFileURLFromSystemPath( instPath,url );
if( errFile != osl::FileBase::E_None ) return configData;
if( url.lastIndexOf( sal_Unicode( '/' ) ) != url.getLength() - 1 )
url += OUString( "/" );
OUString ret;
sal_Int32 idx;
osl::DirectoryItem aDirItem;
if( osl::FileBase::E_None == osl::DirectoryItem::get( url + locale,aDirItem ) )
ret = locale;
else if( ( ( idx = locale.indexOf( '-' ) ) != -1 ||
( idx = locale.indexOf( '_' ) ) != -1 ) &&
osl::FileBase::E_None == osl::DirectoryItem::get( url + locale.copy( 0,idx ),
aDirItem ) )
ret = locale.copy( 0,idx );
else
{
locale = OUString( "en-US" );
ret = OUString("en");
}
url = url + ret;
// first of all, try do determine whether there are any *.tree files present
// Start with extensions to set them at the end of the list
TreeFileIterator aTreeIt( locale );
OUString aTreeFile;
sal_Int32 nFileSize;
while( !(aTreeFile = aTreeIt.nextTreeFile( nFileSize ) ).isEmpty() )
{
configData.vFileLen.push_back( nFileSize );
configData.vFileURL.push_back( aTreeFile );
}
osl::Directory aDirectory( url );
osl::FileStatus aFileStatus(
osl_FileStatus_Mask_FileName | osl_FileStatus_Mask_FileURL );
if( osl::Directory::E_None == aDirectory.open() )
{
int idx_ = 0;
OUString aFileUrl, aFileName;
while( aDirectory.getNextItem( aDirItem ) == osl::FileBase::E_None &&
aDirItem.getFileStatus( aFileStatus ) == osl::FileBase::E_None &&
aFileStatus.isValid( osl_FileStatus_Mask_FileURL ) &&
aFileStatus.isValid( osl_FileStatus_Mask_FileName ) )
{
aFileUrl = aFileStatus.getFileURL();
aFileName = aFileStatus.getFileName();
idx_ = aFileName.lastIndexOf( sal_Unicode( '.' ) );
if( idx_ == -1 )
continue;
const sal_Unicode* str = aFileName.getStr();
if( aFileName.getLength() == idx_ + 5 &&
( str[idx_ + 1] == 't' || str[idx_ + 1] == 'T' ) &&
( str[idx_ + 2] == 'r' || str[idx_ + 2] == 'R' ) &&
( str[idx_ + 3] == 'e' || str[idx_ + 3] == 'E' ) &&
( str[idx_ + 4] == 'e' || str[idx_ + 4] == 'E' ) )
{
OUString baseName = aFileName.copy(0,idx_).toAsciiLowerCase();
if(! showBasic && baseName.compareToAscii("sbasic") == 0 )
continue;
osl::File aFile( aFileUrl );
if( osl::FileBase::E_None == aFile.open( osl_File_OpenFlag_Read ) )
{
// use the file size, not aFileStatus size, in case the
// tree file is a symlink
sal_uInt64 nSize;
aFile.getSize( nSize );
configData.vFileLen.push_back( nSize );
configData.vFileURL.push_back( aFileUrl );
aFile.close();
}
}
}
aDirectory.close();
}
configData.m_vAdd[0] = 12;
configData.m_vAdd[1] = 15;
configData.m_vAdd[2] = 11;
configData.m_vAdd[3] = 14;
configData.m_vAdd[4] = 12;
configData.m_vReplacement[0] = utl::ConfigManager::getProductName();
configData.m_vReplacement[1] = productVersion;
// m_vReplacement[2...4] (vendorName/-Version/-Short) are empty strings
configData.system = system;
configData.locale = locale;
configData.appendix =
OUString( "?Language=" ) +
configData.locale +
OUString( "&System=" ) +
configData.system +
OUString( "&UseDB=no" ) ;
return configData;
}
Reference< XMultiServiceFactory >
TVChildTarget::getConfiguration(const Reference< XComponentContext >& rxContext) const
{
Reference< XMultiServiceFactory > xProvider;
if( rxContext.is() )
{
try
{
xProvider = theDefaultProvider::get( rxContext );
}
catch( const com::sun::star::uno::Exception& )
{
OSL_ENSURE( xProvider.is(),"cant instantiate configuration" );
}
}
return xProvider;
}
Reference< XHierarchicalNameAccess >
TVChildTarget::getHierAccess( const Reference< XMultiServiceFactory >& sProvider,
const char* file ) const
{
Reference< XHierarchicalNameAccess > xHierAccess;
if( sProvider.is() )
{
Sequence< Any > seq(1);
OUString sReaderService =
OUString( "com.sun.star.configuration.ConfigurationAccess" );
seq[0] <<= OUString::createFromAscii( file );
try
{
xHierAccess =
Reference< XHierarchicalNameAccess >
( sProvider->createInstanceWithArguments( sReaderService,seq ),
UNO_QUERY );
}
catch( const com::sun::star::uno::Exception& )
{
}
}
return xHierAccess;
}
OUString
TVChildTarget::getKey( const Reference< XHierarchicalNameAccess >& xHierAccess,
const char* key ) const
{
OUString instPath;
if( xHierAccess.is() )
{
Any aAny;
try
{
aAny =
xHierAccess->getByHierarchicalName( OUString::createFromAscii( key ) );
}
catch( const com::sun::star::container::NoSuchElementException& )
{
}
aAny >>= instPath;
}
return instPath;
}
sal_Bool
TVChildTarget::getBooleanKey(const Reference<
XHierarchicalNameAccess >& xHierAccess,
const char* key) const
{
sal_Bool ret = sal_False;
if( xHierAccess.is() )
{
Any aAny;
try
{
aAny =
xHierAccess->getByHierarchicalName(
OUString::createFromAscii(key));
}
catch( const com::sun::star::container::NoSuchElementException& )
{
}
aAny >>= ret;
}
return ret;
}
void TVChildTarget::subst( OUString& instpath ) const
{
SvtPathOptions aOptions;
instpath = aOptions.SubstituteVariable( instpath );
}
//===================================================================
// class ExtensionIteratorBase
static OUString aSlash("/");
static OUString aHelpFilesBaseName("help");
static OUString aHelpMediaType("application/vnd.sun.star.help");
ExtensionIteratorBase::ExtensionIteratorBase( const OUString& aLanguage )
: m_eState( USER_EXTENSIONS )
, m_aLanguage( aLanguage )
{
init();
}
void ExtensionIteratorBase::init()
{
m_xContext = ::comphelper::getProcessComponentContext();
if( !m_xContext.is() )
{
throw RuntimeException(
OUString( "ExtensionIteratorBase::init(), no XComponentContext" ),
Reference< XInterface >() );
}
m_xSFA = ucb::SimpleFileAccess::create(m_xContext);
m_bUserPackagesLoaded = false;
m_bSharedPackagesLoaded = false;
m_bBundledPackagesLoaded = false;
m_iUserPackage = 0;
m_iSharedPackage = 0;
m_iBundledPackage = 0;
}
Reference< deployment::XPackage > ExtensionIteratorBase::implGetHelpPackageFromPackage
( Reference< deployment::XPackage > xPackage, Reference< deployment::XPackage >& o_xParentPackageBundle )
{
o_xParentPackageBundle.clear();
Reference< deployment::XPackage > xHelpPackage;
if( !xPackage.is() )
return xHelpPackage;
// Check if parent package is registered
beans::Optional< beans::Ambiguous<sal_Bool> > option( xPackage->isRegistered
( Reference<task::XAbortChannel>(), Reference<ucb::XCommandEnvironment>() ) );
bool bRegistered = false;
if( option.IsPresent )
{
beans::Ambiguous<sal_Bool> const & reg = option.Value;
if( !reg.IsAmbiguous && reg.Value )
bRegistered = true;
}
if( !bRegistered )
return xHelpPackage;
if( xPackage->isBundle() )
{
Sequence< Reference< deployment::XPackage > > aPkgSeq = xPackage->getBundle
( Reference<task::XAbortChannel>(), Reference<ucb::XCommandEnvironment>() );
sal_Int32 nPkgCount = aPkgSeq.getLength();
const Reference< deployment::XPackage >* pSeq = aPkgSeq.getConstArray();
for( sal_Int32 iPkg = 0 ; iPkg < nPkgCount ; ++iPkg )
{
const Reference< deployment::XPackage > xSubPkg = pSeq[ iPkg ];
const Reference< deployment::XPackageTypeInfo > xPackageTypeInfo = xSubPkg->getPackageType();
OUString aMediaType = xPackageTypeInfo->getMediaType();
if( aMediaType.equals( aHelpMediaType ) )
{
xHelpPackage = xSubPkg;
o_xParentPackageBundle = xPackage;
break;
}
}
}
else
{
const Reference< deployment::XPackageTypeInfo > xPackageTypeInfo = xPackage->getPackageType();
OUString aMediaType = xPackageTypeInfo->getMediaType();
if( aMediaType.equals( aHelpMediaType ) )
xHelpPackage = xPackage;
}
return xHelpPackage;
}
Reference< deployment::XPackage > ExtensionIteratorBase::implGetNextUserHelpPackage
( Reference< deployment::XPackage >& o_xParentPackageBundle )
{
Reference< deployment::XPackage > xHelpPackage;
if( !m_bUserPackagesLoaded )
{
Reference< XPackageManager > xUserManager =
thePackageManagerFactory::get( m_xContext )->getPackageManager("user");
m_aUserPackagesSeq = xUserManager->getDeployedPackages
( Reference< task::XAbortChannel >(), Reference< ucb::XCommandEnvironment >() );
m_bUserPackagesLoaded = true;
}
if( m_iUserPackage == m_aUserPackagesSeq.getLength() )
{
m_eState = SHARED_EXTENSIONS; // Later: SHARED_MODULE
}
else
{
const Reference< deployment::XPackage >* pUserPackages = m_aUserPackagesSeq.getConstArray();
Reference< deployment::XPackage > xPackage = pUserPackages[ m_iUserPackage++ ];
OSL_ENSURE( xPackage.is(), "ExtensionIteratorBase::implGetNextUserHelpPackage(): Invalid package" );
xHelpPackage = implGetHelpPackageFromPackage( xPackage, o_xParentPackageBundle );
}
return xHelpPackage;
}
Reference< deployment::XPackage > ExtensionIteratorBase::implGetNextSharedHelpPackage
( Reference< deployment::XPackage >& o_xParentPackageBundle )
{
Reference< deployment::XPackage > xHelpPackage;
if( !m_bSharedPackagesLoaded )
{
Reference< XPackageManager > xSharedManager =
thePackageManagerFactory::get( m_xContext )->getPackageManager("shared");
m_aSharedPackagesSeq = xSharedManager->getDeployedPackages
( Reference< task::XAbortChannel >(), Reference< ucb::XCommandEnvironment >() );
m_bSharedPackagesLoaded = true;
}
if( m_iSharedPackage == m_aSharedPackagesSeq.getLength() )
{
m_eState = BUNDLED_EXTENSIONS;
}
else
{
const Reference< deployment::XPackage >* pSharedPackages = m_aSharedPackagesSeq.getConstArray();
Reference< deployment::XPackage > xPackage = pSharedPackages[ m_iSharedPackage++ ];
OSL_ENSURE( xPackage.is(), "ExtensionIteratorBase::implGetNextSharedHelpPackage(): Invalid package" );
xHelpPackage = implGetHelpPackageFromPackage( xPackage, o_xParentPackageBundle );
}
return xHelpPackage;
}
Reference< deployment::XPackage > ExtensionIteratorBase::implGetNextBundledHelpPackage
( Reference< deployment::XPackage >& o_xParentPackageBundle )
{
Reference< deployment::XPackage > xHelpPackage;
if( !m_bBundledPackagesLoaded )
{
Reference< XPackageManager > xBundledManager =
thePackageManagerFactory::get( m_xContext )->getPackageManager("bundled");
m_aBundledPackagesSeq = xBundledManager->getDeployedPackages
( Reference< task::XAbortChannel >(), Reference< ucb::XCommandEnvironment >() );
m_bBundledPackagesLoaded = true;
}
if( m_iBundledPackage == m_aBundledPackagesSeq.getLength() )
{
m_eState = END_REACHED;
}
else
{
const Reference< deployment::XPackage >* pBundledPackages = m_aBundledPackagesSeq.getConstArray();
Reference< deployment::XPackage > xPackage = pBundledPackages[ m_iBundledPackage++ ];
OSL_ENSURE( xPackage.is(), "ExtensionIteratorBase::implGetNextBundledHelpPackage(): Invalid package" );
xHelpPackage = implGetHelpPackageFromPackage( xPackage, o_xParentPackageBundle );
}
return xHelpPackage;
}
inline bool isLetter( sal_Unicode c )
{
return comphelper::string::isalphaAscii(c);
}
void ExtensionIteratorBase::implGetLanguageVectorFromPackage( ::std::vector< OUString > &rv,
com::sun::star::uno::Reference< com::sun::star::deployment::XPackage > xPackage )
{
rv.clear();
OUString aExtensionPath = xPackage->getURL();
Sequence< OUString > aEntrySeq = m_xSFA->getFolderContents( aExtensionPath, true );
const OUString* pSeq = aEntrySeq.getConstArray();
sal_Int32 nCount = aEntrySeq.getLength();
for( sal_Int32 i = 0 ; i < nCount ; ++i )
{
OUString aEntry = pSeq[i];
if( m_xSFA->isFolder( aEntry ) )
{
sal_Int32 nLastSlash = aEntry.lastIndexOf( '/' );
if( nLastSlash != -1 )
{
OUString aPureEntry = aEntry.copy( nLastSlash + 1 );
// Check language sceme
int nLen = aPureEntry.getLength();
const sal_Unicode* pc = aPureEntry.getStr();
bool bStartCanBeLanguage = ( nLen >= 2 && isLetter( pc[0] ) && isLetter( pc[1] ) );
bool bIsLanguage = bStartCanBeLanguage &&
( nLen == 2 || (nLen == 5 && pc[2] == '-' && isLetter( pc[3] ) && isLetter( pc[4] )) );
if( bIsLanguage )
rv.push_back( aPureEntry );
}
}
}
}
//===================================================================
// class TreeFileIterator
OUString TreeFileIterator::nextTreeFile( sal_Int32& rnFileSize )
{
OUString aRetFile;
while( aRetFile.isEmpty() && m_eState != END_REACHED )
{
switch( m_eState )
{
case USER_EXTENSIONS:
{
Reference< deployment::XPackage > xParentPackageBundle;
Reference< deployment::XPackage > xHelpPackage = implGetNextUserHelpPackage( xParentPackageBundle );
if( !xHelpPackage.is() )
break;
aRetFile = implGetTreeFileFromPackage( rnFileSize, xHelpPackage );
break;
}
case SHARED_EXTENSIONS:
{
Reference< deployment::XPackage > xParentPackageBundle;
Reference< deployment::XPackage > xHelpPackage = implGetNextSharedHelpPackage( xParentPackageBundle );
if( !xHelpPackage.is() )
break;
aRetFile = implGetTreeFileFromPackage( rnFileSize, xHelpPackage );
break;
}
case BUNDLED_EXTENSIONS:
{
Reference< deployment::XPackage > xParentPackageBundle;
Reference< deployment::XPackage > xHelpPackage = implGetNextBundledHelpPackage( xParentPackageBundle );
if( !xHelpPackage.is() )
break;
aRetFile = implGetTreeFileFromPackage( rnFileSize, xHelpPackage );
break;
}
case END_REACHED:
OSL_FAIL( "DataBaseIterator::nextTreeFile(): Invalid case END_REACHED" );
break;
}
}
return aRetFile;
}
OUString TreeFileIterator::expandURL( const OUString& aURL )
{
static Reference< util::XMacroExpander > xMacroExpander;
static Reference< uri::XUriReferenceFactory > xFac;
osl::MutexGuard aGuard( m_aMutex );
if( !xMacroExpander.is() || !xFac.is() )
{
xFac = uri::UriReferenceFactory::create( m_xContext );
xMacroExpander = util::theMacroExpander::get(m_xContext);
}
OUString aRetURL = aURL;
Reference< uri::XUriReference > uriRef;
for (;;)
{
uriRef = Reference< uri::XUriReference >( xFac->parse( aRetURL ), UNO_QUERY );
if ( uriRef.is() )
{
Reference < uri::XVndSunStarExpandUrl > sxUri( uriRef, UNO_QUERY );
if( !sxUri.is() )
break;
aRetURL = sxUri->expand( xMacroExpander );
}
}
return aRetURL;
}
OUString TreeFileIterator::implGetTreeFileFromPackage
( sal_Int32& rnFileSize, Reference< deployment::XPackage > xPackage )
{
OUString aRetFile;
OUString aLanguage = m_aLanguage;
for( sal_Int32 iPass = 0 ; iPass < 2 ; ++iPass )
{
OUStringBuffer aStrBuf;
aStrBuf.append( xPackage->getURL() );
aStrBuf.append( aSlash );
aStrBuf.append( aLanguage );
aStrBuf.append( aSlash );
aStrBuf.append( aHelpFilesBaseName );
aStrBuf.appendAscii( ".tree" );
aRetFile = expandURL( aStrBuf.makeStringAndClear() );
if( iPass == 0 )
{
if( m_xSFA->exists( aRetFile ) )
break;
::std::vector< OUString > av;
implGetLanguageVectorFromPackage( av, xPackage );
::std::vector< OUString >::const_iterator pFound = LanguageTag::getFallback( av, m_aLanguage );
if( pFound != av.end() )
aLanguage = *pFound;
}
}
rnFileSize = 0;
if( m_xSFA->exists( aRetFile ) )
rnFileSize = m_xSFA->getSize( aRetFile );
else
aRetFile = OUString();
return aRetFile;
}
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */