From dff3d8ca4c17a649d2ac6ced448df9c784497d41 Mon Sep 17 00:00:00 2001 From: Szymon Kłos Date: Thu, 20 Apr 2017 18:42:56 +0200 Subject: AutoText: importing docx content MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - passing "ReadGlossaries" flag to the WriterFilter - if set - WriterFilter reads glossary document instead of the main content - updated model.xml to read docParts and docPart nodes - SwDOCXReader adds document content as an AutoText entry Change-Id: I9a0cc91c793d6accc8461e1c3aca791c5997d497 Reviewed-on: https://gerrit.libreoffice.org/36753 Tested-by: Jenkins Reviewed-by: Szymon Kłos Tested-by: Szymon Kłos --- sw/source/filter/docx/swdocxreader.cxx | 165 +++++++++++++++++++++------------ sw/source/filter/docx/swdocxreader.hxx | 3 +- 2 files changed, 105 insertions(+), 63 deletions(-) (limited to 'sw/source/filter/docx') diff --git a/sw/source/filter/docx/swdocxreader.cxx b/sw/source/filter/docx/swdocxreader.cxx index b8ea965d3504..419d0bc142fb 100644 --- a/sw/source/filter/docx/swdocxreader.cxx +++ b/sw/source/filter/docx/swdocxreader.cxx @@ -29,6 +29,10 @@ #include #include #include +#include +#include +#include +#include #include #include #include @@ -58,34 +62,6 @@ bool SwDOCXReader::HasGlossaries() const } bool SwDOCXReader::ReadGlossaries( SwTextBlocks& rBlocks, bool /* bSaveRelFiles */ ) const -{ - bool bRet = false; - - uno::Reference xDoc = OpenDocument(); - - if( xDoc.is() ) - { - uno::Reference xList = xDoc->getElementsByTagName( "docPartBody" ); - for( int i = 0; i < xList->getLength(); i++ ) - { - uno::Reference xBody = xList->item( i ); - uno::Reference xP = xBody->getFirstChild(); - uno::Reference xR = xP->getFirstChild(); - uno::Reference xT = xR->getFirstChild(); - uno::Reference xText = xT->getFirstChild(); - OUString aText = xText->getNodeValue(); - if( !aText.isEmpty() ) - { - rBlocks.PutText( aText, aText, aText ); - bRet = true; - } - } - } - - return bRet; -} - -uno::Reference SwDOCXReader::OpenDocument() const { uno::Reference xMultiServiceFactory( comphelper::getProcessServiceFactory() ); @@ -98,54 +74,121 @@ uno::Reference SwDOCXReader::OpenDocument() const uno::Reference xImporter( xFilter, uno::UNO_QUERY_THROW ); SfxObjectShellLock xDocSh( new SwDocShell( SfxObjectCreateMode::INTERNAL ) ); - xDocSh->DoInitNew(); - - uno::Reference xDstDoc( xDocSh->GetModel(), uno::UNO_QUERY_THROW ); - xImporter->setTargetDocument( xDstDoc ); + if( xDocSh->DoInitNew() ) + { + uno::Reference xDstDoc( xDocSh->GetModel(), uno::UNO_QUERY_THROW ); + xImporter->setTargetDocument( xDstDoc ); - uno::Sequence aDescriptor( 1 ); - aDescriptor[0].Name = "InputStream"; - uno::Reference xStream( new utl::OStreamWrapper( *pMedium->GetInStream() ) ); - aDescriptor[0].Value <<= xStream; + uno::Reference xStream( new utl::OStreamWrapper( *pMedium->GetInStream() ) ); - uno::Reference xDoc; + uno::Sequence aDescriptor( 2 ); + aDescriptor[0].Name = "InputStream"; + aDescriptor[0].Value <<= xStream; + aDescriptor[1].Name = "ReadGlossaries"; + aDescriptor[1].Value <<= true; - try - { - xFilter->filter( aDescriptor ); + try + { + xFilter->filter( aDescriptor ); + } + catch( uno::Exception const& e ) + { + SAL_WARN("sw.docx", "SwDOCXReader::ReadGlossaries(): exception: " << e.Message); + } - comphelper::SequenceAsHashMap aGrabBag = GetGrabBag( xDstDoc ); - aGrabBag["OOXGlossary"] >>= xDoc; - } - catch (uno::Exception const& e) - { - SAL_WARN("sw.docx", "SwDOCXReader::OpenDocument(): exception: " << e.Message); + return MakeEntries( static_cast( &xDocSh )->GetDoc(), rBlocks ); } - return xDoc; + return false; } -comphelper::SequenceAsHashMap SwDOCXReader::GetGrabBag( const uno::Reference& xDocument ) +bool SwDOCXReader::MakeEntries( SwDoc *pD, SwTextBlocks &rBlocks ) { - if( xDocument.is() ) + const OUString aOldURL( rBlocks.GetBaseURL() ); + rBlocks.SetBaseURL( OUString() ); + + bool bRet = false; + + SwNodeIndex aDocEnd( pD->GetNodes().GetEndOfContent() ); + SwNodeIndex aStart( *aDocEnd.GetNode().StartOfSectionNode() ); + + if( aStart < aDocEnd && ( aDocEnd.GetIndex() - aStart.GetIndex() > 2 ) ) { - // get glossar document from the GrabBag - uno::Reference xDocProps( xDocument, uno::UNO_QUERY ); - if( xDocProps.is() ) - { - uno::Reference xPropsInfo = xDocProps->getPropertySetInfo(); + SwTextFormatColl* pColl = pD->getIDocumentStylePoolAccess().GetTextCollFromPool + (RES_POOLCOLL_STANDARD, false); + sal_uInt16 nGlosEntry = 0; + SwContentNode* pCNd = nullptr; + do { + SwPaM aPam( aStart ); + { + SwNodeIndex& rIdx = aPam.GetPoint()->nNode; + ++rIdx; + if( nullptr == ( pCNd = rIdx.GetNode().GetTextNode() ) ) + { + pCNd = pD->GetNodes().MakeTextNode( rIdx, pColl ); + rIdx = *pCNd; + } + } - const OUString aGrabBagPropName = "InteropGrabBag"; - if( xPropsInfo.is() && xPropsInfo->hasPropertyByName( aGrabBagPropName ) ) + aPam.GetPoint()->nContent.Assign( pCNd, 0 ); + aPam.SetMark(); { - // get existing grab bag - comphelper::SequenceAsHashMap aGrabBag( xDocProps->getPropertyValue( aGrabBagPropName ) ); - return aGrabBag; + SwNodeIndex& rIdx = aPam.GetPoint()->nNode; + rIdx = aStart.GetNode().EndOfSectionIndex() - 1; + if( ( nullptr == ( pCNd = rIdx.GetNode().GetContentNode() ) ) ) + { + ++rIdx; + pCNd = pD->GetNodes().MakeTextNode( rIdx, pColl ); + rIdx = *pCNd; + } } - } + aPam.GetPoint()->nContent.Assign( pCNd, pCNd->Len() ); + + rBlocks.ClearDoc(); + + // TODO: correct entry name + const OUString rLNm = "ImportedAutoText"; + + OUString sShortcut = rLNm; + + // Need to check make sure the shortcut is not already being used + sal_Int32 nStart = 0; + sal_uInt16 nCurPos = rBlocks.GetIndex( sShortcut ); + sal_Int32 nLen = sShortcut.getLength(); + + while( (sal_uInt16)-1 != nCurPos ) + { + sShortcut = sShortcut.copy( 0, nLen ); + // add an Number to it + sShortcut += OUString::number( ++nStart ); + nCurPos = rBlocks.GetIndex( sShortcut ); + } + + if( rBlocks.BeginPutDoc( sShortcut, sShortcut ) ) + { + SwDoc* pGlDoc = rBlocks.GetDoc(); + SwNodeIndex aIdx( pGlDoc->GetNodes().GetEndOfContent(), -1 ); + pCNd = aIdx.GetNode().GetContentNode(); + SwPosition aPos( aIdx, SwIndex( pCNd, ( pCNd ) ? pCNd->Len() : 0 ) ); + pD->getIDocumentContentOperations().CopyRange( aPam, aPos, /*bCopyAll=*/false, /*bCheckPos=*/true ); + rBlocks.PutDoc(); + } + + if( aStart.GetNodes().Count() <= aStart.GetNode().GetIndex() ) + aStart = aStart.GetNode().EndOfSectionIndex() + 1; + else + break; + + ++nGlosEntry; + + } while( aStart < aDocEnd ); + + bRet = true; } - return comphelper::SequenceAsHashMap(); + rBlocks.SetBaseURL( aOldURL ); + + return bRet; } /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/sw/source/filter/docx/swdocxreader.hxx b/sw/source/filter/docx/swdocxreader.hxx index 2646a963523f..6c6dab0b2d1b 100644 --- a/sw/source/filter/docx/swdocxreader.hxx +++ b/sw/source/filter/docx/swdocxreader.hxx @@ -37,8 +37,7 @@ public: private: virtual sal_uLong Read( SwDoc&, const OUString&, SwPaM&, const OUString& ) override; - uno::Reference OpenDocument() const; - static comphelper::SequenceAsHashMap GetGrabBag( const uno::Reference& xDocument ); + static bool MakeEntries( SwDoc *pD, SwTextBlocks &rBlocks ); }; #endif -- cgit v1.2.3