merge the formfield patch from ooo-build
[ooovba.git] / sw / source / filter / ww8 / ww8glsy.cxx
blobfe7fb79e017860d131b6ac73da0c941096f5f77f
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: ww8glsy.cxx,v $
10 * $Revision: 1.30 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_sw.hxx"
34 /* -*- Mode: C; tab-width: 4; indent-tabs-mode: nil -*- */
35 #include <tools/urlobj.hxx>
36 #include <svtools/urihelper.hxx>
37 #include <rtl/tencinfo.h>
38 #include <swerror.h>
39 #ifndef _NDTXT
40 #include <ndtxt.hxx>
41 #endif
42 #include <pam.hxx>
43 #include <shellio.hxx>
44 #ifndef _DOCSH_HXX
45 #include <docsh.hxx>
46 #endif
47 #include <fmtanchr.hxx>
48 #include <frmfmt.hxx>
49 #include <doc.hxx>
50 #include <docary.hxx>
51 #include "ww8glsy.hxx"
52 #include "ww8par.hxx"
54 WW8Glossary::WW8Glossary(SvStorageStreamRef &refStrm, BYTE nVersion,
55 SvStorage *pStg)
56 : pGlossary(0), rStrm(refStrm), xStg(pStg), nStrings(0)
58 refStrm->SetNumberFormatInt(NUMBERFORMAT_INT_LITTLEENDIAN);
59 WW8Fib aWwFib(*refStrm, nVersion);
61 if (aWwFib.nFibBack >= 0x6A) //Word97
63 xTableStream = pStg->OpenSotStream(String::CreateFromAscii(
64 aWwFib.fWhichTblStm ? SL::a1Table : SL::a0Table), STREAM_STD_READ);
66 if (xTableStream.Is() && SVSTREAM_OK == xTableStream->GetError())
68 xTableStream->SetNumberFormatInt(NUMBERFORMAT_INT_LITTLEENDIAN);
69 pGlossary =
70 new WW8GlossaryFib(*refStrm, nVersion, *xTableStream, aWwFib);
75 bool WW8Glossary::HasBareGraphicEnd(SwDoc *pDoc,SwNodeIndex &rIdx)
77 bool bRet=false;
78 for( USHORT nCnt = pDoc->GetSpzFrmFmts()->Count(); nCnt; )
80 SwFrmFmt* pFrmFmt = (*pDoc->GetSpzFrmFmts())[ --nCnt ];
81 if ( RES_FLYFRMFMT != pFrmFmt->Which() &&
82 RES_DRAWFRMFMT != pFrmFmt->Which() )
83 continue;
84 const SwFmtAnchor& rAnchor = pFrmFmt->GetAnchor();
85 const SwPosition* pAPos;
86 if( ( FLY_AT_CNTNT == rAnchor.GetAnchorId() ||
87 FLY_AUTO_CNTNT == rAnchor.GetAnchorId() ) &&
88 0 != ( pAPos = rAnchor.GetCntntAnchor()) &&
89 rIdx == pAPos->nNode.GetIndex() )
91 bRet=true;
92 break;
95 return bRet;
98 bool WW8Glossary::MakeEntries(SwDoc *pD, SwTextBlocks &rBlocks,
99 bool bSaveRelFile, const std::vector<String>& rStrings,
100 const std::vector<ww::bytes>& rExtra)
102 // this code will be called after reading all text into the
103 // empty sections
104 const String aOldURL( rBlocks.GetBaseURL() );
105 bool bRet=false;
106 if( bSaveRelFile )
108 rBlocks.SetBaseURL(
109 URIHelper::SmartRel2Abs(
110 INetURLObject(), rBlocks.GetFileName(),
111 URIHelper::GetMaybeFileHdl()));
113 else
114 rBlocks.SetBaseURL( aEmptyStr );
116 SwNodeIndex aDocEnd( pD->GetNodes().GetEndOfContent() );
117 SwNodeIndex aStart( *aDocEnd.GetNode().StartOfSectionNode(), 1 );
119 // search the first NormalStartNode
120 while( !( aStart.GetNode().IsStartNode() && SwNormalStartNode ==
121 aStart.GetNode().GetStartNode()->GetStartNodeType()) &&
122 aStart < aDocEnd )
123 aStart++;
125 if( aStart < aDocEnd )
127 SwTxtFmtColl* pColl = pD->GetTxtCollFromPool
128 (RES_POOLCOLL_STANDARD, false);
129 USHORT nGlosEntry = 0;
130 SwCntntNode* pCNd = 0;
131 do {
132 SwPaM aPam( aStart );
134 SwNodeIndex& rIdx = aPam.GetPoint()->nNode;
135 rIdx++;
136 if( 0 == ( pCNd = rIdx.GetNode().GetTxtNode() ) )
138 pCNd = pD->GetNodes().MakeTxtNode( rIdx, pColl );
139 rIdx = *pCNd;
142 aPam.GetPoint()->nContent.Assign( pCNd, 0 );
143 aPam.SetMark();
145 SwNodeIndex& rIdx = aPam.GetPoint()->nNode;
146 rIdx = aStart.GetNode().EndOfSectionIndex() - 1;
147 if(( 0 == ( pCNd = rIdx.GetNode().GetCntntNode() ) )
148 || HasBareGraphicEnd(pD,rIdx))
150 rIdx++;
151 pCNd = pD->GetNodes().MakeTxtNode( rIdx, pColl );
152 rIdx = *pCNd;
155 aPam.GetPoint()->nContent.Assign( pCNd, pCNd->Len() );
157 // now we have the right selection for one entry. Copy this to
158 // the definied TextBlock, but only if it is not an autocorrection
159 // entry (== -1) otherwise the group indicates the group in the
160 // sttbfglsystyle list that this entry belongs to. Unused at the
161 // moment
162 const ww::bytes &rData = rExtra[nGlosEntry];
163 USHORT n = SVBT16ToShort( &(rData[2]) );
164 if(n != 0xFFFF)
166 rBlocks.ClearDoc();
167 const String &rLNm = rStrings[nGlosEntry];
169 String sShortcut = rLNm;
171 // Need to check make sure the shortcut is not already being used
172 xub_StrLen nStart = 0;
173 USHORT nCurPos = rBlocks.GetIndex( sShortcut );
174 xub_StrLen nLen = sShortcut.Len();
175 while( (USHORT)-1 != nCurPos )
177 sShortcut.Erase( nLen ) +=
178 String::CreateFromInt32( ++nStart ); // add an Number to it
179 nCurPos = rBlocks.GetIndex( sShortcut );
182 if( rBlocks.BeginPutDoc( sShortcut, sShortcut )) // Make the shortcut and the name the same
185 SwDoc* pGlDoc = rBlocks.GetDoc();
186 SwNodeIndex aIdx( pGlDoc->GetNodes().GetEndOfContent(),
187 -1 );
188 pCNd = aIdx.GetNode().GetCntntNode();
189 SwPosition aPos( aIdx, SwIndex( pCNd, pCNd->Len() ));
190 pD->CopyRange( aPam, aPos, false );
191 rBlocks.PutDoc();
194 aStart = aStart.GetNode().EndOfSectionIndex() + 1;
195 ++nGlosEntry;
196 } while( aStart.GetNode().IsStartNode() &&
197 SwNormalStartNode == aStart.GetNode().
198 GetStartNode()->GetStartNodeType());
199 bRet=true;
202 // this code will be called after reading all text into the empty sections
204 rBlocks.SetBaseURL( aOldURL );
205 return bRet;
209 bool WW8Glossary::Load( SwTextBlocks &rBlocks, bool bSaveRelFile )
211 bool bRet=false;
212 if (pGlossary && pGlossary->IsGlossaryFib() && rBlocks.StartPutMuchBlockEntries())
214 //read the names of the autotext entries
215 std::vector<String> aStrings;
216 std::vector<ww::bytes> aData;
218 rtl_TextEncoding eStructCharSet =
219 WW8Fib::GetFIBCharset(pGlossary->chseTables);
221 WW8ReadSTTBF(true, *xTableStream, pGlossary->fcSttbfglsy,
222 pGlossary->lcbSttbfglsy, 0, eStructCharSet, aStrings, &aData );
224 rStrm->Seek(0);
226 if ( 0 != (nStrings = static_cast< USHORT >(aStrings.size())))
228 SfxObjectShellRef xDocSh(new SwDocShell(SFX_CREATE_MODE_INTERNAL));
229 if (xDocSh->DoInitNew(0))
231 SwDoc *pD = ((SwDocShell*)(&xDocSh))->GetDoc();
232 SwWW8ImplReader* pRdr = new SwWW8ImplReader(pGlossary->nVersion,
233 xStg, &rStrm, *pD, rBlocks.GetBaseURL(), true);
235 SwNodeIndex aIdx(
236 *pD->GetNodes().GetEndOfContent().StartOfSectionNode(), 1);
237 if( !aIdx.GetNode().IsTxtNode() )
239 ASSERT( !this, "wo ist der TextNode?" );
240 pD->GetNodes().GoNext( &aIdx );
242 SwPaM aPamo( aIdx );
243 aPamo.GetPoint()->nContent.Assign(aIdx.GetNode().GetCntntNode(),
245 pRdr->LoadDoc(aPamo,this);
247 bRet = MakeEntries(pD, rBlocks, bSaveRelFile, aStrings, aData);
249 delete pRdr;
251 xDocSh->DoClose();
252 rBlocks.EndPutMuchBlockEntries();
255 return bRet;
259 bool WW8GlossaryFib::IsGlossaryFib()
261 // fGlsy will indicate whether this has AutoText or not
262 return fGlsy;
265 UINT32 WW8GlossaryFib::FindGlossaryFibOffset(SvStream & /* rTableStrm */,
266 SvStream & /* rStrm */,
267 const WW8Fib &rFib)
269 UINT32 nGlossaryFibOffset = 0;
270 if ( rFib.fDot ) // its a template
272 if ( rFib.pnNext )
273 nGlossaryFibOffset = ( rFib.pnNext * 512 );
275 return nGlossaryFibOffset;
278 /* vi:set tabstop=4 shiftwidth=4 expandtab: */