/**************************************************************
 *
 * 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
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 *
 *************************************************************/



// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_xmloff.hxx"


#include <com/sun/star/util/XStringSubstitution.hpp>
#include <xmloff/DocumentSettingsContext.hxx>
#include <xmloff/xmlimp.hxx>
#include <xmloff/xmltoken.hxx>
#include "xmloff/xmlnmspe.hxx"
#include <xmloff/nmspmap.hxx>
#include <xmloff/xmluconv.hxx>
#include <tools/debug.hxx>

#ifndef __SGI_STL_LIST
#include <list>
#endif
#include <com/sun/star/i18n/XForbiddenCharacters.hpp>
#include <com/sun/star/container/XIndexContainer.hpp>
#include <com/sun/star/lang/XMultiServiceFactory.hpp>
#include <com/sun/star/formula/SymbolDescriptor.hpp>
#include <comphelper/processfactory.hxx>
#include <com/sun/star/util/DateTime.hpp>
#include <com/sun/star/document/XViewDataSupplier.hpp>
#include <com/sun/star/document/PrinterIndependentLayout.hpp>
#include <comphelper/configurationhelper.hxx>
#include <rtl/ustrbuf.hxx>
#include <xmlenums.hxx>

using namespace com::sun::star;
using namespace ::xmloff::token;

#define C2U(cChar) ::rtl::OUString::createFromAscii(cChar)

//------------------------------------------------------------------

class XMLMyList
{
	std::list<beans::PropertyValue>	aProps;
	sal_uInt32						nCount;

	// #110680#
	::com::sun::star::uno::Reference< ::com::sun::star::lang::XMultiServiceFactory > mxServiceFactory;

public:
	// #110680#
	XMLMyList(const uno::Reference<lang::XMultiServiceFactory>& xServiceFactory);
	~XMLMyList();

	void push_back(beans::PropertyValue& aProp) { aProps.push_back(aProp); nCount++; }
	uno::Sequence<beans::PropertyValue> GetSequence();
	uno::Reference<container::XNameContainer> GetNameContainer();
	uno::Reference<container::XIndexContainer> GetIndexContainer();
};

// #110680#
XMLMyList::XMLMyList(const uno::Reference<lang::XMultiServiceFactory>& xServiceFactory)
:	nCount(0),
	mxServiceFactory(xServiceFactory)
{
	DBG_ASSERT( mxServiceFactory.is(), "got no service manager" );
}

// #110680#
XMLMyList::~XMLMyList()
{
}

uno::Sequence<beans::PropertyValue> XMLMyList::GetSequence()
{
	uno::Sequence<beans::PropertyValue> aSeq;
	if(nCount)
	{
		DBG_ASSERT(nCount == aProps.size(), "wrong count of PropertyValue");
		aSeq.realloc(nCount);
		beans::PropertyValue* pProps = aSeq.getArray();
		std::list<beans::PropertyValue>::iterator aItr = aProps.begin();
		while (aItr != aProps.end())
		{
			*pProps = *aItr;
			pProps++;
			aItr++;
		}
	}
	return aSeq;
}

uno::Reference<container::XNameContainer> XMLMyList::GetNameContainer()
{
	uno::Reference<container::XNameContainer> xNameContainer;

	// #110680#
	// uno::Reference<lang::XMultiServiceFactory> xServiceFactory = comphelper::getProcessServiceFactory();
	// DBG_ASSERT( xServiceFactory.is(), "got no service manager" );

	if( mxServiceFactory.is() )
	{
		rtl::OUString sName(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.document.NamedPropertyValues"));
		xNameContainer = uno::Reference<container::XNameContainer>(mxServiceFactory->createInstance(sName), uno::UNO_QUERY);
		if (xNameContainer.is())
		{
			std::list<beans::PropertyValue>::iterator aItr = aProps.begin();
			while (aItr != aProps.end())
			{
				xNameContainer->insertByName(aItr->Name, aItr->Value);
				aItr++;
			}
		}
	}
	return xNameContainer;
}

uno::Reference<container::XIndexContainer> XMLMyList::GetIndexContainer()
{
	uno::Reference<container::XIndexContainer> xIndexContainer;
	// #110680#
	// uno::Reference<lang::XMultiServiceFactory> xServiceFactory = comphelper::getProcessServiceFactory();
	// DBG_ASSERT( xServiceFactory.is(), "got no service manager" );

	if( mxServiceFactory.is() )
	{
		rtl::OUString sName(RTL_CONSTASCII_USTRINGPARAM("com.sun.star.document.IndexedPropertyValues"));
		xIndexContainer = uno::Reference<container::XIndexContainer>(mxServiceFactory->createInstance(sName), uno::UNO_QUERY);
		if (xIndexContainer.is())
		{
			std::list<beans::PropertyValue>::iterator aItr = aProps.begin();
			sal_uInt32 i(0);
			while (aItr != aProps.end())
			{
				xIndexContainer->insertByIndex(i, aItr->Value);
				aItr++;
				i++;
			}
		}
	}
	return xIndexContainer;
}

//=============================================================================

class XMLConfigBaseContext : public SvXMLImportContext
{
protected:
	XMLMyList					maProps;
	beans::PropertyValue		maProp;
	com::sun::star::uno::Any&	mrAny;
	XMLConfigBaseContext*		mpBaseContext;
public:
	XMLConfigBaseContext(SvXMLImport& rImport, sal_uInt16 nPrfx, const rtl::OUString& rLName,
									com::sun::star::uno::Any& rAny,
									XMLConfigBaseContext* pBaseContext);
	virtual ~XMLConfigBaseContext();

	void AddPropertyValue() { maProps.push_back(maProp); }
};

//=============================================================================

class XMLConfigItemContext : public SvXMLImportContext
{
	rtl::OUString				msType;
	rtl::OUString				msValue;
	uno::Sequence<sal_Int8>		maDecoded;
	com::sun::star::uno::Any&	mrAny;
    const rtl::OUString         mrItemName;
	XMLConfigBaseContext*		mpBaseContext;

public:
	XMLConfigItemContext(SvXMLImport& rImport, sal_uInt16 nPrfx, const rtl::OUString& rLName,
									const ::com::sun::star::uno::Reference<
									::com::sun::star::xml::sax::XAttributeList>& xAttrList,
									com::sun::star::uno::Any& rAny,
                                    const rtl::OUString& rItemName,
									XMLConfigBaseContext* pBaseContext);
	virtual ~XMLConfigItemContext();

	virtual SvXMLImportContext *CreateChildContext( sal_uInt16 nPrefix,
													const rtl::OUString& rLocalName,
													const ::com::sun::star::uno::Reference<
									  	::com::sun::star::xml::sax::XAttributeList>& xAttrList );
	virtual void Characters( const ::rtl::OUString& rChars );

	virtual void EndElement();

    virtual void ManipulateConfigItem();
};

//=============================================================================

class XMLConfigItemSetContext : public XMLConfigBaseContext
{
public:
	XMLConfigItemSetContext(SvXMLImport& rImport, sal_uInt16 nPrfx, const rtl::OUString& rLName,
									const ::com::sun::star::uno::Reference<
									::com::sun::star::xml::sax::XAttributeList>& xAttrList,
									com::sun::star::uno::Any& rAny,
									XMLConfigBaseContext* pBaseContext);
	virtual ~XMLConfigItemSetContext();

	virtual SvXMLImportContext *CreateChildContext( sal_uInt16 nPrefix,
													const rtl::OUString& rLocalName,
													const ::com::sun::star::uno::Reference<
									  	::com::sun::star::xml::sax::XAttributeList>& xAttrList );

	virtual void EndElement();
};

//=============================================================================

class XMLConfigItemMapNamedContext : public XMLConfigBaseContext
{
public:
	XMLConfigItemMapNamedContext(SvXMLImport& rImport, sal_uInt16 nPrfx, const rtl::OUString& rLName,
									const ::com::sun::star::uno::Reference<
									::com::sun::star::xml::sax::XAttributeList>& xAttrList,
									com::sun::star::uno::Any& rAny,
									XMLConfigBaseContext* pBaseContext);
	virtual ~XMLConfigItemMapNamedContext();

	virtual SvXMLImportContext *CreateChildContext( sal_uInt16 nPrefix,
													const rtl::OUString& rLocalName,
													const ::com::sun::star::uno::Reference<
									  	::com::sun::star::xml::sax::XAttributeList>& xAttrList );

	virtual void EndElement();
};

//=============================================================================

class XMLConfigItemMapIndexedContext : public XMLConfigBaseContext
{
private:
	rtl::OUString maConfigItemName;

public:
	XMLConfigItemMapIndexedContext(SvXMLImport& rImport, sal_uInt16 nPrfx,
									const rtl::OUString& rLName,
									const ::com::sun::star::uno::Reference<
									::com::sun::star::xml::sax::XAttributeList>& xAttrList,
									com::sun::star::uno::Any& rAny,
									const rtl::OUString& rConfigItemName,
									XMLConfigBaseContext* pBaseContext);
	virtual ~XMLConfigItemMapIndexedContext();

	virtual SvXMLImportContext *CreateChildContext( sal_uInt16 nPrefix,
													const rtl::OUString& rLocalName,
													const ::com::sun::star::uno::Reference<
										::com::sun::star::xml::sax::XAttributeList>& xAttrList );

	virtual void EndElement();
};

//=============================================================================

SvXMLImportContext *CreateSettingsContext(SvXMLImport& rImport, sal_uInt16 p_nPrefix,
						const rtl::OUString& rLocalName,
						const uno::Reference<xml::sax::XAttributeList>& xAttrList,
						beans::PropertyValue& rProp, XMLConfigBaseContext* pBaseContext)
{
	SvXMLImportContext *pContext = 0;

	rProp.Name = rtl::OUString();
	sal_Int16 nAttrCount = xAttrList.is() ? xAttrList->getLength() : 0;
	for( sal_Int16 i=0; i < nAttrCount; i++ )
	{
		rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
		rtl::OUString aLocalName;
		sal_uInt16 nPrefix = rImport.GetNamespaceMap().GetKeyByAttrName(
											sAttrName, &aLocalName );
		rtl::OUString sValue = xAttrList->getValueByIndex( i );

		if (nPrefix == XML_NAMESPACE_CONFIG)
		{
			if (IsXMLToken(aLocalName, XML_NAME))
				rProp.Name = sValue;
		}
	}

	if (p_nPrefix == XML_NAMESPACE_CONFIG)
	{
		if (IsXMLToken(rLocalName, XML_CONFIG_ITEM))
			pContext = new XMLConfigItemContext(rImport, p_nPrefix, rLocalName, xAttrList, rProp.Value, rProp.Name, pBaseContext);
		else if((IsXMLToken(rLocalName, XML_CONFIG_ITEM_SET)) ||
				(IsXMLToken(rLocalName, XML_CONFIG_ITEM_MAP_ENTRY)) )
			pContext = new XMLConfigItemSetContext(rImport, p_nPrefix, rLocalName, xAttrList, rProp.Value, pBaseContext);
		else if(IsXMLToken(rLocalName, XML_CONFIG_ITEM_MAP_NAMED))
			pContext = new XMLConfigItemMapNamedContext(rImport, p_nPrefix, rLocalName, xAttrList, rProp.Value, pBaseContext);
		else if(IsXMLToken(rLocalName, XML_CONFIG_ITEM_MAP_INDEXED))
			pContext = new XMLConfigItemMapIndexedContext(rImport, p_nPrefix, rLocalName, xAttrList, rProp.Value, rProp.Name, pBaseContext);
	}

	if( !pContext )
		pContext = new SvXMLImportContext( rImport, p_nPrefix, rLocalName );

	return pContext;
}

//=============================================================================
namespace
{
    struct SettingsGroup
    {
        ::rtl::OUString sGroupName;
        uno::Any        aSettings;

        SettingsGroup()
            :sGroupName()
            ,aSettings()
        {
        }

        SettingsGroup( const ::rtl::OUString& _rGroupName, const uno::Any& _rSettings )
            :sGroupName( _rGroupName )
            ,aSettings( _rSettings )
        {
        }
    };
}

struct XMLDocumentSettingsContext_Data
{
	com::sun::star::uno::Any	    aViewProps;
	com::sun::star::uno::Any	    aConfigProps;
    ::std::list< SettingsGroup >    aDocSpecificSettings;
};

//=============================================================================

XMLDocumentSettingsContext::XMLDocumentSettingsContext(SvXMLImport& rImport, sal_uInt16 nPrfx, const rtl::OUString& rLName,
					const uno::Reference<xml::sax::XAttributeList>& )
	: SvXMLImportContext( rImport, nPrfx, rLName )
    , m_pData( new XMLDocumentSettingsContext_Data )
{
	// here are no attributes
}

XMLDocumentSettingsContext::~XMLDocumentSettingsContext()
{
}

SvXMLImportContext *XMLDocumentSettingsContext::CreateChildContext( sal_uInt16 p_nPrefix,
									 const rtl::OUString& rLocalName,
									 const ::com::sun::star::uno::Reference<
									  	::com::sun::star::xml::sax::XAttributeList>& xAttrList )
{
	SvXMLImportContext *pContext = 0;
	rtl::OUString sName;

	sal_Int16 nAttrCount = xAttrList.is() ? xAttrList->getLength() : 0;
	for( sal_Int16 i=0; i < nAttrCount; i++ )
	{
		rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
		rtl::OUString aLocalName;
		sal_uInt16 nPrefix = GetImport().GetNamespaceMap().GetKeyByAttrName(
											sAttrName, &aLocalName );
		rtl::OUString sValue = xAttrList->getValueByIndex( i );

		if (nPrefix == XML_NAMESPACE_CONFIG)
		{
			if (IsXMLToken(aLocalName, XML_NAME))
				sName = sValue;
		}
	}

	if (p_nPrefix == XML_NAMESPACE_CONFIG)
	{
		if (IsXMLToken(rLocalName, XML_CONFIG_ITEM_SET))
		{
			::rtl::OUString aLocalConfigName;
			sal_uInt16 nConfigPrefix =
				GetImport().GetNamespaceMap().GetKeyByAttrName(
											sName, &aLocalConfigName );

			if( XML_NAMESPACE_OOO == nConfigPrefix )
			{
				if (IsXMLToken(aLocalConfigName, XML_VIEW_SETTINGS))
					pContext = new XMLConfigItemSetContext(GetImport(),
										p_nPrefix, rLocalName, xAttrList,
										m_pData->aViewProps, NULL);
				else if (IsXMLToken(aLocalConfigName,
												XML_CONFIGURATION_SETTINGS))
					pContext = new XMLConfigItemSetContext(GetImport(),
										p_nPrefix, rLocalName, xAttrList,
										m_pData->aConfigProps, NULL);
                else
                {
                    m_pData->aDocSpecificSettings.push_back( SettingsGroup( aLocalConfigName, uno::Any() ) );

                    ::std::list< SettingsGroup >::reverse_iterator settingsPos =
                        m_pData->aDocSpecificSettings.rbegin();

                    pContext = new XMLConfigItemSetContext(GetImport(),
										p_nPrefix, rLocalName, xAttrList,
										settingsPos->aSettings, NULL);
                }
			}
		}
	}

	if( !pContext )
		pContext = new SvXMLImportContext( GetImport(), p_nPrefix, rLocalName );

	return pContext;
}

void XMLDocumentSettingsContext::EndElement()
{
	uno::Sequence<beans::PropertyValue> aSeqViewProps;
	if (m_pData->aViewProps >>= aSeqViewProps)
	{
		GetImport().SetViewSettings(aSeqViewProps);
		sal_Int32 i(aSeqViewProps.getLength() - 1);
		sal_Bool bFound(sal_False);
		while((i >= 0) && !bFound)
		{
			if (aSeqViewProps[i].Name.compareToAscii("Views") == 0)
			{
				bFound = sal_True;
				uno::Reference<container::XIndexAccess> xIndexAccess;
				if (aSeqViewProps[i].Value >>= xIndexAccess)
				{
					uno::Reference<document::XViewDataSupplier> xViewDataSupplier(GetImport().GetModel(), uno::UNO_QUERY);
					if (xViewDataSupplier.is())
						xViewDataSupplier->setViewData(xIndexAccess);
				}
			}
			else
				i--;
		}
	}

    sal_Bool bLoadDocPrinter( sal_True );
    ::comphelper::ConfigurationHelper::readDirectKey(
        ::comphelper::getProcessServiceFactory(),
        C2U("org.openoffice.Office.Common/"), C2U("Save/Document"), C2U("LoadPrinter"),
        ::comphelper::ConfigurationHelper::E_READONLY ) >>= bLoadDocPrinter;
    uno::Sequence<beans::PropertyValue> aSeqConfigProps;
    if ( m_pData->aConfigProps >>= aSeqConfigProps )
    {
        if ( !bLoadDocPrinter )
        {
            sal_Int32 i = aSeqConfigProps.getLength() - 1;
            int nFound = 0;

            while ( ( i >= 0 ) && nFound < 2 )
            {
                rtl::OUString sProp( aSeqConfigProps[i].Name );

                if ( sProp.compareToAscii("PrinterName") == 0 )
                {
                    rtl::OUString sEmpty;
                    aSeqConfigProps[i].Value = uno::makeAny( sEmpty );
                    nFound++;
                }
                else if ( sProp.compareToAscii("PrinterSetup") == 0 )
                {
                    uno::Sequence< sal_Int8 > aEmpty;
                    aSeqConfigProps[i].Value = uno::makeAny( aEmpty );
                    nFound++;
                }

                i--;
            }
        }

        GetImport().SetConfigurationSettings( aSeqConfigProps );
    }

    for (   ::std::list< SettingsGroup >::const_iterator settings = m_pData->aDocSpecificSettings.begin();
            settings != m_pData->aDocSpecificSettings.end();
            ++settings
        )
    {
        uno::Sequence< beans::PropertyValue > aDocSettings;
        OSL_VERIFY( settings->aSettings >>= aDocSettings );
        GetImport().SetDocumentSpecificSettings( settings->sGroupName, aDocSettings );
    }
}

//=============================================================================

XMLConfigBaseContext::XMLConfigBaseContext(SvXMLImport& rImport, sal_uInt16 nPrfx,
		const rtl::OUString& rLName, com::sun::star::uno::Any& rTempAny,
		XMLConfigBaseContext* pTempBaseContext)
	: SvXMLImportContext( rImport, nPrfx, rLName ),
	// #110680#
	maProps(rImport.getServiceFactory()),
	maProp(),
	mrAny(rTempAny),
	mpBaseContext(pTempBaseContext)
{
}

XMLConfigBaseContext::~XMLConfigBaseContext()
{
}

//=============================================================================

XMLConfigItemSetContext::XMLConfigItemSetContext(SvXMLImport& rImport, sal_uInt16 nPrfx,
									const rtl::OUString& rLName,
									const ::com::sun::star::uno::Reference<
									::com::sun::star::xml::sax::XAttributeList>&,
									com::sun::star::uno::Any& rAny,
									XMLConfigBaseContext* pBaseContext)
	: XMLConfigBaseContext( rImport, nPrfx, rLName, rAny, pBaseContext )
{
	// here are no attributes
}

XMLConfigItemSetContext::~XMLConfigItemSetContext()
{
}

SvXMLImportContext *XMLConfigItemSetContext::CreateChildContext( sal_uInt16 nPrefix,
									 const rtl::OUString& rLocalName,
									 const ::com::sun::star::uno::Reference<
									  	::com::sun::star::xml::sax::XAttributeList>& xAttrList )
{
	return CreateSettingsContext(GetImport(), nPrefix, rLocalName, xAttrList, maProp, this);
}

void XMLConfigItemSetContext::EndElement()
{
	mrAny <<= maProps.GetSequence();
	if (mpBaseContext)
		mpBaseContext->AddPropertyValue();
}

//=============================================================================

XMLConfigItemContext::XMLConfigItemContext(SvXMLImport& rImport, sal_uInt16 nPrfx, const rtl::OUString& rLName,
									const ::com::sun::star::uno::Reference<
									::com::sun::star::xml::sax::XAttributeList>& xAttrList,
									com::sun::star::uno::Any& rTempAny,
                                    const rtl::OUString& rTempItemName,
									XMLConfigBaseContext* pTempBaseContext)
	: SvXMLImportContext(rImport, nPrfx, rLName),
	mrAny(rTempAny),
    mrItemName(rTempItemName),
	mpBaseContext(pTempBaseContext)
{
	sal_Int16 nAttrCount = xAttrList.is() ? xAttrList->getLength() : 0;
	for( sal_Int16 i=0; i < nAttrCount; i++ )
	{
		rtl::OUString sAttrName = xAttrList->getNameByIndex( i );
		rtl::OUString aLocalName;
		sal_uInt16 nPrefix = GetImport().GetNamespaceMap().GetKeyByAttrName(
											sAttrName, &aLocalName );
		rtl::OUString sValue = xAttrList->getValueByIndex( i );

		if (nPrefix == XML_NAMESPACE_CONFIG)
		{
			if (IsXMLToken(aLocalName, XML_TYPE))
				msType = sValue;
		}
	}
}

XMLConfigItemContext::~XMLConfigItemContext()
{
}

SvXMLImportContext *XMLConfigItemContext::CreateChildContext( sal_uInt16 nPrefix,
													const rtl::OUString& rLocalName,
													const ::com::sun::star::uno::Reference<
									  	::com::sun::star::xml::sax::XAttributeList>& )
{
	SvXMLImportContext* pContext = new SvXMLImportContext(GetImport(), nPrefix, rLocalName);
	return pContext;
}

void XMLConfigItemContext::Characters( const ::rtl::OUString& rChars )
{
	if (IsXMLToken(msType, XML_BASE64BINARY))
	{
		rtl::OUString sTrimmedChars( rChars.trim() );
		if( sTrimmedChars.getLength() )
		{
			rtl::OUString sChars;
			if( !msValue.isEmpty() )
			{
				sChars = msValue;
				sChars += sTrimmedChars;
				msValue = rtl::OUString();
			}
			else
			{
				sChars = sTrimmedChars;
			}
			uno::Sequence<sal_Int8> aBuffer((sChars.getLength() / 4) * 3 );
			sal_Int32 nCharsDecoded =
				GetImport().GetMM100UnitConverter().
					decodeBase64SomeChars( aBuffer, sChars );
			sal_uInt32 nStartPos(maDecoded.getLength());
			sal_uInt32 nCount(aBuffer.getLength());
			maDecoded.realloc(nStartPos + nCount);
			sal_Int8* pDecoded = maDecoded.getArray();
			sal_Int8* pBuffer = aBuffer.getArray();
			for (sal_uInt32 i = 0; i < nCount; i++, pBuffer++)
				pDecoded[nStartPos + i] = *pBuffer;
			if( nCharsDecoded != sChars.getLength() )
				msValue = sChars.copy( nCharsDecoded );
		}
	}
	else
		msValue += rChars;
}


void XMLConfigItemContext::EndElement()
{
	if (mpBaseContext)
	{
		if (IsXMLToken(msType, XML_BOOLEAN))
		{
			sal_Bool bValue(sal_False);
			if (IsXMLToken(msValue, XML_TRUE))
				bValue = sal_True;
			mrAny <<= bValue;
		}
		else if (IsXMLToken(msType, XML_BYTE))
		{
			sal_Int32 nValue(0);
			SvXMLUnitConverter::convertNumber(nValue, msValue);
			mrAny <<= static_cast<sal_Int8>(nValue);
		}
		else if (IsXMLToken(msType, XML_SHORT))
		{
			sal_Int32 nValue(0);
			SvXMLUnitConverter::convertNumber(nValue, msValue);
			mrAny <<= static_cast<sal_Int16>(nValue);
		}
		else if (IsXMLToken(msType, XML_INT))
		{
			sal_Int32 nValue(0);
			SvXMLUnitConverter::convertNumber(nValue, msValue);
			mrAny <<= nValue;
		}
		else if (IsXMLToken(msType, XML_LONG))
		{
			sal_Int64 nValue(msValue.toInt64());
			mrAny <<= nValue;
		}
		else if (IsXMLToken(msType, XML_DOUBLE))
		{
			double fValue(0.0);
			SvXMLUnitConverter::convertDouble(fValue, msValue);
			mrAny <<= fValue;
		}
		else if (IsXMLToken(msType, XML_STRING))
		{
			mrAny <<= msValue;
		}
		else if (IsXMLToken(msType, XML_DATETIME))
		{
			util::DateTime aDateTime;
			SvXMLUnitConverter::convertDateTime(aDateTime, msValue);
			mrAny <<= aDateTime;
		}
		else if (IsXMLToken(msType, XML_BASE64BINARY))
		{
			mrAny <<= maDecoded;
		}
		else {
			DBG_ERROR("wrong type");
        }

        ManipulateConfigItem();

		mpBaseContext->AddPropertyValue();
	}
	else {
		DBG_ERROR("no BaseContext");
    }
}

/** There are some instances where there is a mismatch between API and
 * XML mapping of a setting. In this case, this method allows us to
 * manipulate the values accordingly. */
void XMLConfigItemContext::ManipulateConfigItem()
{
    if( mrItemName.equalsAsciiL(
            RTL_CONSTASCII_STRINGPARAM( "PrinterIndependentLayout" ) ) )
    {
        rtl::OUString sValue;
        mrAny >>= sValue;

        sal_Int16 nTmp = document::PrinterIndependentLayout::HIGH_RESOLUTION;

        if( sValue.equalsAsciiL(RTL_CONSTASCII_STRINGPARAM("enabled")) ||
            sValue.equalsAsciiL(RTL_CONSTASCII_STRINGPARAM("low-resolution")) )
        {
            nTmp = document::PrinterIndependentLayout::LOW_RESOLUTION;
        }
        else if( sValue.equalsAsciiL(RTL_CONSTASCII_STRINGPARAM("disabled")) )
        {
            nTmp = document::PrinterIndependentLayout::DISABLED;
        }
        // else: default to high_resolution

        mrAny <<= nTmp;
    }
	else if( (mrItemName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "ColorTableURL" ) ) ) ||
			 (mrItemName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "LineEndTableURL" ) ) ) ||
			 (mrItemName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "HatchTableURL" ) ) ) ||
			 (mrItemName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "DashTableURL" ) ) ) ||
			 (mrItemName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "GradientTableURL") ) ) ||
			 (mrItemName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "BitmapTableURL" ) ) ) )
	{
		if( GetImport().getServiceFactory().is() ) try
		{
			uno::Reference< util::XStringSubstitution > xStringSubsitution(
				GetImport().getServiceFactory()->
					createInstance(::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.util.PathSubstitution" ) ) ), uno::UNO_QUERY );

			if( xStringSubsitution.is() )
			{
				rtl::OUString aURL;
				mrAny >>= aURL;
				aURL = xStringSubsitution->substituteVariables( aURL, sal_False );
				mrAny <<= aURL;
			}
		}
		catch( uno::Exception& )
		{
		}
	}
}


//=============================================================================

XMLConfigItemMapNamedContext::XMLConfigItemMapNamedContext(SvXMLImport& rImport, sal_uInt16 nPrfx, const rtl::OUString& rLName,
									const ::com::sun::star::uno::Reference<
									::com::sun::star::xml::sax::XAttributeList>&,
									com::sun::star::uno::Any& rAny,
									XMLConfigBaseContext* pBaseContext)
	: XMLConfigBaseContext(rImport, nPrfx, rLName, rAny, pBaseContext)
{
}

XMLConfigItemMapNamedContext::~XMLConfigItemMapNamedContext()
{
}

SvXMLImportContext *XMLConfigItemMapNamedContext::CreateChildContext( sal_uInt16 nPrefix,
													const rtl::OUString& rLocalName,
													const ::com::sun::star::uno::Reference<
									  	::com::sun::star::xml::sax::XAttributeList>& xAttrList )
{
	return CreateSettingsContext(GetImport(), nPrefix, rLocalName, xAttrList, maProp, this);
}

void XMLConfigItemMapNamedContext::EndElement()
{
	if (mpBaseContext)
	{
		mrAny <<= maProps.GetNameContainer();
		mpBaseContext->AddPropertyValue();
	}
	else {
		DBG_ERROR("no BaseContext");
    }
}

//=============================================================================

XMLConfigItemMapIndexedContext::XMLConfigItemMapIndexedContext(SvXMLImport& rImport, sal_uInt16 nPrfx,
									const rtl::OUString& rLName,
									const ::com::sun::star::uno::Reference<
									::com::sun::star::xml::sax::XAttributeList>&,
									com::sun::star::uno::Any& rAny,
									const ::rtl::OUString& rConfigItemName,
									XMLConfigBaseContext* pBaseContext)
	: XMLConfigBaseContext(rImport, nPrfx, rLName, rAny, pBaseContext),
	  maConfigItemName( rConfigItemName )
{
}

XMLConfigItemMapIndexedContext::~XMLConfigItemMapIndexedContext()
{
}

SvXMLImportContext *XMLConfigItemMapIndexedContext::CreateChildContext( sal_uInt16 nPrefix,
													const rtl::OUString& rLocalName,
													const ::com::sun::star::uno::Reference<
										::com::sun::star::xml::sax::XAttributeList>& xAttrList )
{
	return CreateSettingsContext(GetImport(), nPrefix, rLocalName, xAttrList, maProp, this);
}

void XMLConfigItemMapIndexedContext::EndElement()
{
	if (mpBaseContext)
	{
		if( maConfigItemName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "ForbiddenCharacters" ) ) )
		{
			uno::Reference< i18n::XForbiddenCharacters > xForbChars;

			// get the forbidden characters from the document
			uno::Reference< lang::XMultiServiceFactory > xFac( GetImport().GetModel(), uno::UNO_QUERY );
			if( xFac.is() )
			{
				uno::Reference< beans::XPropertySet > xProps( xFac->createInstance( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.document.Settings" ) ) ), uno::UNO_QUERY );
				if( xProps.is() && xProps->getPropertySetInfo()->hasPropertyByName( maConfigItemName ) )
				{
					xProps->getPropertyValue( maConfigItemName ) >>= xForbChars;
				}
			}

			if( xForbChars.is() )
			{

				uno::Reference< container::XIndexAccess > xIndex( maProps.GetIndexContainer(), uno::UNO_QUERY );

				const sal_Int32 nCount = xIndex->getCount();
				uno::Sequence < beans::PropertyValue > aProps;
				for (sal_Int32 i = 0; i < nCount; i++)
				{
					if ((xIndex->getByIndex( i ) >>= aProps) && (aProps.getLength() == XML_FORBIDDEN_CHARACTER_MAX ) )
					{
						beans::PropertyValue *pForChar = aProps.getArray();
						i18n::ForbiddenCharacters aForbid;
						lang::Locale aLocale;
						const rtl::OUString sLanguage  ( RTL_CONSTASCII_USTRINGPARAM ( "Language" ) );
						const rtl::OUString sCountry   ( RTL_CONSTASCII_USTRINGPARAM ( "Country" ) );
						const rtl::OUString sVariant   ( RTL_CONSTASCII_USTRINGPARAM ( "Variant" ) );
						const rtl::OUString sBeginLine ( RTL_CONSTASCII_USTRINGPARAM ( "BeginLine" ) );
						const rtl::OUString sEndLine   ( RTL_CONSTASCII_USTRINGPARAM ( "EndLine" ) );
						sal_Bool bHaveLanguage = sal_False, bHaveCountry = sal_False, bHaveVariant = sal_False,
								 bHaveBegin = sal_False, bHaveEnd = sal_False;

						for ( sal_Int32 j = 0 ; j < XML_FORBIDDEN_CHARACTER_MAX ; j++ )
						{
							if (pForChar->Name.equals (sLanguage ) )
							{
								pForChar->Value >>= aLocale.Language;
								bHaveLanguage = sal_True;
							}
							else if (pForChar->Name.equals (sCountry ) )
							{
								pForChar->Value >>= aLocale.Country;
								bHaveCountry = sal_True;
							}
							else if (pForChar->Name.equals (sVariant ) )
							{
								pForChar->Value >>= aLocale.Variant;
								bHaveVariant = sal_True;
							}
							else if (pForChar->Name.equals (sBeginLine ) )
							{
								pForChar->Value >>= aForbid.beginLine;
								bHaveBegin = sal_True;
							}
							else if (pForChar->Name.equals (sEndLine ) )
							{
								pForChar->Value >>= aForbid.endLine;
								bHaveEnd = sal_True;
							}
							pForChar++;
						}

						if ( bHaveLanguage && bHaveCountry && bHaveVariant && bHaveBegin && bHaveEnd )
						{
							try
							{
								xForbChars->setForbiddenCharacters( aLocale, aForbid );
							}
							catch( uno::Exception& )
							{
								DBG_ERROR( "Exception while importing forbidden characters" );
							}
						}
					}
				}
			}
			else
			{
				DBG_ERROR( "could not get the XForbiddenCharacters from document!" );
				mrAny <<= maProps.GetIndexContainer();
			}
		}
		else if( maConfigItemName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM( "Symbols" ) ) )
		{
			uno::Reference< container::XIndexAccess > xIndex( maProps.GetIndexContainer(), uno::UNO_QUERY );

			const sal_Int32 nCount = xIndex->getCount();
			uno::Sequence < beans::PropertyValue > aProps;
			uno::Sequence < formula::SymbolDescriptor > aSymbolList ( nCount );

			formula::SymbolDescriptor *pDescriptor = aSymbolList.getArray();

			const rtl::OUString sName     ( RTL_CONSTASCII_USTRINGPARAM ( "Name" ) );
			const rtl::OUString sExportName ( RTL_CONSTASCII_USTRINGPARAM ( "ExportName" ) );
			const rtl::OUString sFontName ( RTL_CONSTASCII_USTRINGPARAM ( "FontName" ) );
			const rtl::OUString sSymbolSet ( RTL_CONSTASCII_USTRINGPARAM ( "SymbolSet" ) );
			const rtl::OUString sCharacter ( RTL_CONSTASCII_USTRINGPARAM ( "Character" ) );
			const rtl::OUString sCharSet  ( RTL_CONSTASCII_USTRINGPARAM ( "CharSet" ) );
			const rtl::OUString sFamily   ( RTL_CONSTASCII_USTRINGPARAM ( "Family" ) );
			const rtl::OUString sPitch    ( RTL_CONSTASCII_USTRINGPARAM ( "Pitch" ) );
			const rtl::OUString sWeight   ( RTL_CONSTASCII_USTRINGPARAM ( "Weight" ) );
			const rtl::OUString sItalic   ( RTL_CONSTASCII_USTRINGPARAM ( "Italic" ) );
			sal_Int16 nNumFullEntries = 0;

			for ( sal_Int32 i = 0; i < nCount; i++ )
			{
				if ((xIndex->getByIndex( i ) >>= aProps) && (aProps.getLength() == XML_SYMBOL_DESCRIPTOR_MAX ) )
				{
					sal_Bool bHaveName = sal_False, bHaveExportName = sal_False, bHaveCharSet = sal_False,
					 		 bHaveFontName = sal_False, bHaveFamily = sal_False, bHavePitch = sal_False,
					 		 bHaveWeight = sal_False, bHaveItalic = sal_False, bHaveSymbolSet = sal_False,
							 bHaveCharacter = sal_False;
					beans::PropertyValue *pSymbol = aProps.getArray();

					for ( sal_Int32 j = 0 ; j < XML_SYMBOL_DESCRIPTOR_MAX ; j++ )
					{
						if (pSymbol->Name.equals ( sName ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].sName;
							bHaveName = sal_True;
						}
						else if (pSymbol->Name.equals (sExportName ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].sExportName;
							bHaveExportName = sal_True;
						}
						else if (pSymbol->Name.equals (sFontName ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].sFontName;
							bHaveFontName = sal_True;
						}
						else if (pSymbol->Name.equals (sCharSet ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].nCharSet;
							bHaveCharSet = sal_True;
						}
						else if (pSymbol->Name.equals (sFamily ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].nFamily;
							bHaveFamily = sal_True;
						}
						else if (pSymbol->Name.equals (sPitch ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].nPitch;
							bHavePitch = sal_True;
						}
						else if (pSymbol->Name.equals (sWeight ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].nWeight;
							bHaveWeight = sal_True;
						}
						else if (pSymbol->Name.equals (sItalic ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].nItalic;
							bHaveItalic = sal_True;
						}
						else if (pSymbol->Name.equals (sSymbolSet ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].sSymbolSet;
							bHaveSymbolSet = sal_True;
						}
						else if (pSymbol->Name.equals (sCharacter ) )
						{
							pSymbol->Value >>= pDescriptor[nNumFullEntries].nCharacter;
							bHaveCharacter = sal_True;
						}
						pSymbol++;
					}
					if ( bHaveName && bHaveExportName && bHaveCharSet && bHaveFontName && bHaveCharacter
						 && bHaveFamily && bHavePitch && bHaveWeight && bHaveItalic && bHaveSymbolSet)
						nNumFullEntries++;
				}
			}
			aSymbolList.realloc (nNumFullEntries);
			mrAny <<= aSymbolList;
		}
		else
		{
			mrAny <<= maProps.GetIndexContainer();
		}
		mpBaseContext->AddPropertyValue();
	}
	else {
		DBG_ERROR("no BaseContext");
    }
}
