Kaydet (Commit) 20e0afa7 authored tarafından Eike Rathke's avatar Eike Rathke

resolved fdo#56209 reviving FilterFormulaParser

First it was moved from oox to sc without carrying over the component
factory bits, then subsequent commits removed the remaining bits in
steps as it appeared to be unused:

8ada1cd2
887d7945
effda59a
f2fd2a66

Change-Id: I445b11c95daff6f30b3654936d0f22a113158f97
üst 60a32377
......@@ -191,6 +191,7 @@ $(eval $(call gb_Library_add_exception_objects,scfilt,\
sc/source/filter/oox/formulabuffer \
sc/source/filter/oox/formulaparser \
sc/source/filter/oox/numberformatsbuffer \
sc/source/filter/oox/ooxformulaparser \
sc/source/filter/oox/pagesettings \
sc/source/filter/oox/pivotcachebuffer \
sc/source/filter/oox/pivotcachefragment \
......
/* -*- 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 .
*/
#ifndef OOX_XLS_OOXFORMULAPARSER_HXX
#define OOX_XLS_OOXFORMULAPARSER_HXX
#include <boost/shared_ptr.hpp>
#include <com/sun/star/lang/XComponent.hpp>
#include <com/sun/star/uno/XComponentContext.hpp>
#include <com/sun/star/lang/XInitialization.hpp>
#include <com/sun/star/lang/XServiceInfo.hpp>
#include <com/sun/star/sheet/XFilterFormulaParser.hpp>
#include <cppuhelper/implbase3.hxx>
namespace oox {
namespace xls {
class OOXMLFormulaParserImpl;
// ============================================================================
typedef ::cppu::WeakImplHelper3<
::com::sun::star::lang::XServiceInfo,
::com::sun::star::lang::XInitialization,
::com::sun::star::sheet::XFilterFormulaParser > OOXMLFormulaParser_BASE;
/** OOXML formula parser/compiler service for usage in ODF filters. */
class OOXMLFormulaParser : public OOXMLFormulaParser_BASE
{
public:
explicit OOXMLFormulaParser();
virtual ~OOXMLFormulaParser();
// com.sun.star.lang.XServiceInfo interface -------------------------------
virtual ::rtl::OUString SAL_CALL
getImplementationName() throw( ::com::sun::star::uno::RuntimeException );
virtual sal_Bool SAL_CALL
supportsService( const ::rtl::OUString& rService )
throw( ::com::sun::star::uno::RuntimeException );
virtual ::com::sun::star::uno::Sequence< ::rtl::OUString > SAL_CALL
getSupportedServiceNames() throw( ::com::sun::star::uno::RuntimeException );
// com.sun.star.lang.XInitialization interface ----------------------------
virtual void SAL_CALL initialize(
const ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Any >& rArgs )
throw( ::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException );
// com.sun.star.sheet.XFilterFormulaParser interface ----------------------
virtual ::rtl::OUString SAL_CALL
getSupportedNamespace()
throw( ::com::sun::star::uno::RuntimeException );
// com.sun.star.sheet.XFormulaParser interface ----------------------------
virtual ::com::sun::star::uno::Sequence< ::com::sun::star::sheet::FormulaToken > SAL_CALL
parseFormula(
const ::rtl::OUString& rFormula,
const ::com::sun::star::table::CellAddress& rReferencePos )
throw( ::com::sun::star::uno::RuntimeException );
virtual ::rtl::OUString SAL_CALL
printFormula(
const ::com::sun::star::uno::Sequence< ::com::sun::star::sheet::FormulaToken >& rTokens,
const ::com::sun::star::table::CellAddress& rReferencePos )
throw( ::com::sun::star::uno::RuntimeException );
private:
typedef ::boost::shared_ptr< OOXMLFormulaParserImpl > ParserImplRef;
::com::sun::star::uno::Reference< ::com::sun::star::lang::XComponent >
mxComponent;
ParserImplRef mxParserImpl; /// Implementation of import parser.
};
css::uno::Reference< css::uno::XInterface > SAL_CALL OOXMLFormulaParser_create(
css::uno::Reference< css::uno::XComponentContext > const & context);
OUString SAL_CALL OOXMLFormulaParser_getImplementationName();
css::uno::Sequence< OUString > SAL_CALL OOXMLFormulaParser_getSupportedServiceNames();
// ============================================================================
} // namespace xls
} // namespace oox
#endif
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
/* -*- 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 "ooxformulaparser.hxx"
#include <com/sun/star/uno/XComponentContext.hpp>
#include "formulaparser.hxx"
namespace oox {
namespace xls {
// ============================================================================
using namespace ::com::sun::star::lang;
using namespace ::com::sun::star::sheet;
using namespace ::com::sun::star::table;
using namespace ::com::sun::star::uno;
using ::rtl::OUString;
// ============================================================================
class OOXMLFormulaParserImpl : private FormulaFinalizer
{
public:
explicit OOXMLFormulaParserImpl( const Reference< XMultiServiceFactory >& rxModelFactory );
Sequence< FormulaToken > parseFormula( const OUString& rFormula, const CellAddress& rReferencePos );
protected:
virtual const FunctionInfo* resolveBadFuncName( const OUString& rTokenData ) const;
private:
ApiParserWrapper maApiParser;
};
// ----------------------------------------------------------------------------
OOXMLFormulaParserImpl::OOXMLFormulaParserImpl( const Reference< XMultiServiceFactory >& rxModelFactory ) :
FormulaFinalizer( OpCodeProvider( rxModelFactory, FILTER_OOXML, BIFF_UNKNOWN, true ) ),
maApiParser( rxModelFactory, *this )
{
}
Sequence< FormulaToken > OOXMLFormulaParserImpl::parseFormula( const OUString& rFormula, const CellAddress& rReferencePos )
{
return finalizeTokenArray( maApiParser.parseFormula( rFormula, rReferencePos ) );
}
const FunctionInfo* OOXMLFormulaParserImpl::resolveBadFuncName( const OUString& rTokenData ) const
{
/* Try to parse calls to library functions. The format of such a function
call is assumed to be
"'<path-to-office-install>\Library\<libname>'!<funcname>". */
// the string has to start with an apostroph (followed by the library URL)
if( (rTokenData.getLength() >= 6) && (rTokenData[ 0 ] == '\'') )
{
// library URL and function name are separated by an exclamation mark
sal_Int32 nExclamPos = rTokenData.lastIndexOf( '!' );
if( (1 < nExclamPos) && (nExclamPos + 1 < rTokenData.getLength()) && (rTokenData[ nExclamPos - 1 ] == '\'') )
{
// find the last backslash that separates library path and name
sal_Int32 nFileSep = rTokenData.lastIndexOf( '\\', nExclamPos - 2 );
if( nFileSep > 1 )
{
// find preceding backslash that separates the last directory name
sal_Int32 nDirSep = rTokenData.lastIndexOf( '\\', nFileSep - 1 );
// function library is located in a directory called 'library'
if( (nDirSep > 0) && rTokenData.matchIgnoreAsciiCaseAsciiL( RTL_CONSTASCII_STRINGPARAM( "\\LIBRARY\\" ), nDirSep ) )
{
// try to find a function info for the function name
OUString aFuncName = rTokenData.copy( nExclamPos + 1 ).toAsciiUpperCase();
const FunctionInfo* pFuncInfo = getFuncInfoFromOoxFuncName( aFuncName );
if( pFuncInfo && (pFuncInfo->meFuncLibType != FUNCLIB_UNKNOWN) )
{
// check that the name of the library matches
OUString aLibName = rTokenData.copy( nFileSep + 1, nExclamPos - nFileSep - 2 );
if( pFuncInfo->meFuncLibType == getFuncLibTypeFromLibraryName( aLibName ) )
return pFuncInfo;
}
}
}
}
}
return 0;
}
// ============================================================================
Sequence< OUString > OOXMLFormulaParser_getSupportedServiceNames()
{
Sequence< OUString > aServiceNames( 1 );
aServiceNames[ 0 ] = "com.sun.star.sheet.FilterFormulaParser";
return aServiceNames;
}
OUString OOXMLFormulaParser_getImplementationName()
{
return OUString( "com.sun.star.comp.oox.xls.FormulaParser");
}
Reference< XInterface > OOXMLFormulaParser_create( const Reference< XComponentContext >& )
{
return static_cast< ::cppu::OWeakObject* >( new OOXMLFormulaParser );
}
// ============================================================================
OOXMLFormulaParser::OOXMLFormulaParser()
{
}
OOXMLFormulaParser::~OOXMLFormulaParser()
{
}
// com.sun.star.lang.XServiceInfo interface -----------------------------------
OUString SAL_CALL OOXMLFormulaParser::getImplementationName() throw( RuntimeException )
{
return OOXMLFormulaParser_getImplementationName();
}
sal_Bool SAL_CALL OOXMLFormulaParser::supportsService( const OUString& rService ) throw( RuntimeException )
{
const Sequence< OUString > aServices( OOXMLFormulaParser_getSupportedServiceNames() );
const OUString* pArray = aServices.getConstArray();
const OUString* pArrayEnd = pArray + aServices.getLength();
return ::std::find( pArray, pArrayEnd, rService ) != pArrayEnd;
}
Sequence< OUString > SAL_CALL OOXMLFormulaParser::getSupportedServiceNames() throw( RuntimeException )
{
return OOXMLFormulaParser_getSupportedServiceNames();
}
// com.sun.star.lang.XInitialization interface --------------------------------
void SAL_CALL OOXMLFormulaParser::initialize( const Sequence< Any >& rArgs ) throw( Exception, RuntimeException )
{
OSL_ENSURE( rArgs.hasElements(), "OOXMLFormulaParser::initialize - missing arguments" );
if( !rArgs.hasElements() )
throw RuntimeException();
mxComponent.set( rArgs[ 0 ], UNO_QUERY_THROW );
}
// com.sun.star.sheet.XFilterFormulaParser interface --------------------------
OUString SAL_CALL OOXMLFormulaParser::getSupportedNamespace() throw( RuntimeException )
{
return OUString( "http://schemas.microsoft.com/office/excel/formula");
}
// com.sun.star.sheet.XFormulaParser interface --------------------------------
Sequence< FormulaToken > SAL_CALL OOXMLFormulaParser::parseFormula(
const OUString& rFormula, const CellAddress& rReferencePos ) throw( RuntimeException )
{
if( !mxParserImpl )
{
Reference< XMultiServiceFactory > xModelFactory( mxComponent, UNO_QUERY_THROW );
mxParserImpl.reset( new OOXMLFormulaParserImpl( xModelFactory ) );
}
return mxParserImpl->parseFormula( rFormula, rReferencePos );
}
OUString SAL_CALL OOXMLFormulaParser::printFormula(
const Sequence< FormulaToken >& /*rTokens*/, const CellAddress& /*rReferencePos*/ ) throw( RuntimeException )
{
// not implemented
throw RuntimeException();
}
// ============================================================================
} // namespace xls
} // namespace oox
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
......@@ -24,15 +24,17 @@
#include "sal/types.h"
#include "excelfilter.hxx"
#include "ooxformulaparser.hxx"
#define IMPLEMENTATION_ENTRY( className ) \
{ &className##_create, &className##_getImplementationName, &className##_getSupportedServiceNames, ::cppu::createSingleComponentFactory, 0, 0 }
extern "C" SAL_DLLPUBLIC_EXPORT void * SAL_CALL scfilt_component_getFactory(
char const * pImplName, void * pServiceManager, void * pRegistryKey)
{
static cppu::ImplementationEntry const services[] = {
{ oox::xls::ExcelFilter_create,
oox::xls::ExcelFilter_getImplementationName,
oox::xls::ExcelFilter_getSupportedServiceNames,
cppu::createSingleComponentFactory, 0, 0 },
IMPLEMENTATION_ENTRY( oox::xls::ExcelFilter ),
IMPLEMENTATION_ENTRY( oox::xls::OOXMLFormulaParser ),
{ 0, 0, 0, 0, 0, 0 }
};
return cppu::component_getFactoryHelper(
......
......@@ -23,4 +23,7 @@
<service name="com.sun.star.document.ImportFilter"/>
<service name="com.sun.star.document.ExportFilter"/>
</implementation>
<implementation name="com.sun.star.comp.oox.xls.FormulaParser">
<service name="com.sun.star.sheet.FilterFormulaParser"/>
</implementation>
</component>
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment