xref: /aoo41x/main/sw/source/filter/html/htmlctxt.cxx (revision efeef26f)
1*efeef26fSAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3*efeef26fSAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4*efeef26fSAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5*efeef26fSAndrew Rist  * distributed with this work for additional information
6*efeef26fSAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7*efeef26fSAndrew Rist  * to you under the Apache License, Version 2.0 (the
8*efeef26fSAndrew Rist  * "License"); you may not use this file except in compliance
9*efeef26fSAndrew Rist  * with the License.  You may obtain a copy of the License at
10*efeef26fSAndrew Rist  *
11*efeef26fSAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12*efeef26fSAndrew Rist  *
13*efeef26fSAndrew Rist  * Unless required by applicable law or agreed to in writing,
14*efeef26fSAndrew Rist  * software distributed under the License is distributed on an
15*efeef26fSAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*efeef26fSAndrew Rist  * KIND, either express or implied.  See the License for the
17*efeef26fSAndrew Rist  * specific language governing permissions and limitations
18*efeef26fSAndrew Rist  * under the License.
19*efeef26fSAndrew Rist  *
20*efeef26fSAndrew Rist  *************************************************************/
21*efeef26fSAndrew Rist 
22*efeef26fSAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_sw.hxx"
26cdf0e10cSrcweir 
27cdf0e10cSrcweir 
28cdf0e10cSrcweir #include "hintids.hxx"
29cdf0e10cSrcweir #include <svl/itemiter.hxx>
30cdf0e10cSrcweir #include <editeng/lrspitem.hxx>
31cdf0e10cSrcweir #include <editeng/ulspitem.hxx>
32cdf0e10cSrcweir #include <editeng/brshitem.hxx>
33cdf0e10cSrcweir #include <editeng/fhgtitem.hxx>
34cdf0e10cSrcweir #include <svtools/htmltokn.h>
35cdf0e10cSrcweir 
36cdf0e10cSrcweir #include "doc.hxx"
37cdf0e10cSrcweir #include "pam.hxx"
38cdf0e10cSrcweir #include "ndtxt.hxx"
39cdf0e10cSrcweir #include "shellio.hxx"
40cdf0e10cSrcweir #include "paratr.hxx"
41cdf0e10cSrcweir #include "htmlnum.hxx"
42cdf0e10cSrcweir #include "css1kywd.hxx"
43cdf0e10cSrcweir #include "swcss1.hxx"
44cdf0e10cSrcweir #include "swhtml.hxx"
45cdf0e10cSrcweir 
46cdf0e10cSrcweir using namespace ::com::sun::star;
47cdf0e10cSrcweir 
48cdf0e10cSrcweir 
49cdf0e10cSrcweir /*  */
50cdf0e10cSrcweir 
51cdf0e10cSrcweir 
52cdf0e10cSrcweir class _HTMLAttrContext_SaveDoc
53cdf0e10cSrcweir {
54cdf0e10cSrcweir 	SwHTMLNumRuleInfo aNumRuleInfo;	// In Umgebung gueltige Numerierung
55cdf0e10cSrcweir 	SwPosition  *pPos;				// hierhin beim verlassen den
56cdf0e10cSrcweir 									// Kontexts zurueckgesprungen
57cdf0e10cSrcweir 	_HTMLAttrTable *pAttrTab;		// In Umgebung gueltige Attribute,
58cdf0e10cSrcweir 									// wenn Attributierung nicht
59cdf0e10cSrcweir 									// beibehalten werden soll.
60cdf0e10cSrcweir 
61cdf0e10cSrcweir 	sal_uInt16 nContextStMin;			// In Umgebung gueltige Stack-
62cdf0e10cSrcweir 									// Untergrenze, wenn der Stack
63cdf0e10cSrcweir 									// geschuetzt werden soll.
64cdf0e10cSrcweir 	sal_uInt16 nContextStAttrMin;		// In Umgebung gueltige Stack-
65cdf0e10cSrcweir 									// Untergrenze, wenn die Attribute
66cdf0e10cSrcweir 									// nicht beibehalten werden sollen.
67cdf0e10cSrcweir 
68cdf0e10cSrcweir 	sal_Bool bStripTrailingPara : 1;	// letzen Absatz entfernen?
69cdf0e10cSrcweir 	sal_Bool bKeepNumRules : 1;			// Numerierung beibehalten?
70cdf0e10cSrcweir 	sal_Bool bPopStack : 1;				// Stack-Elemente oberhalb des
71cdf0e10cSrcweir 									// zu schliessenden entfernen?
72cdf0e10cSrcweir 	sal_Bool bFixHeaderDist : 1;
73cdf0e10cSrcweir 	sal_Bool bFixFooterDist : 1;
74cdf0e10cSrcweir 
75cdf0e10cSrcweir public:
76cdf0e10cSrcweir 
_HTMLAttrContext_SaveDoc()77cdf0e10cSrcweir 	_HTMLAttrContext_SaveDoc() :
78cdf0e10cSrcweir 		pPos( 0 ), pAttrTab( 0 ),
79cdf0e10cSrcweir 		nContextStMin( USHRT_MAX ), nContextStAttrMin( USHRT_MAX ),
80cdf0e10cSrcweir 		bStripTrailingPara( sal_False ), bKeepNumRules( sal_False ),
81cdf0e10cSrcweir 		bPopStack( sal_False ),
82cdf0e10cSrcweir 		bFixHeaderDist( sal_False ), bFixFooterDist( sal_False )
83cdf0e10cSrcweir 	{}
84cdf0e10cSrcweir 
~_HTMLAttrContext_SaveDoc()85cdf0e10cSrcweir 	~_HTMLAttrContext_SaveDoc() { delete pPos; delete pAttrTab; }
86cdf0e10cSrcweir 
87cdf0e10cSrcweir 	// Die Position gehoert uns, muss also angelegt und zerstoert werden
SetPos(const SwPosition & rPos)88cdf0e10cSrcweir 	void SetPos( const SwPosition& rPos ) { pPos = new SwPosition(rPos); }
GetPos() const89cdf0e10cSrcweir 	const SwPosition *GetPos() const { return pPos; }
90cdf0e10cSrcweir 
91cdf0e10cSrcweir 	// Der Index gehoert uns nicht. Kein Anlgen und Zerstoeren.
SetNumInfo(const SwHTMLNumRuleInfo & rInf)92cdf0e10cSrcweir 	void SetNumInfo( const SwHTMLNumRuleInfo& rInf ) { aNumRuleInfo.Set(rInf); }
GetNumInfo() const93cdf0e10cSrcweir 	const SwHTMLNumRuleInfo& GetNumInfo() const { return aNumRuleInfo; }
94cdf0e10cSrcweir 
95cdf0e10cSrcweir 	_HTMLAttrTable *GetAttrTab( sal_Bool bCreate= sal_False );
96cdf0e10cSrcweir 
SetContextStMin(sal_uInt16 nMin)97cdf0e10cSrcweir 	void SetContextStMin( sal_uInt16 nMin ) { nContextStMin = nMin; }
GetContextStMin() const98cdf0e10cSrcweir 	sal_uInt16 GetContextStMin() const { return nContextStMin; }
99cdf0e10cSrcweir 
SetContextStAttrMin(sal_uInt16 nMin)100cdf0e10cSrcweir 	void SetContextStAttrMin( sal_uInt16 nMin ) { nContextStAttrMin = nMin; }
GetContextStAttrMin() const101cdf0e10cSrcweir 	sal_uInt16 GetContextStAttrMin() const { return nContextStAttrMin; }
102cdf0e10cSrcweir 
SetStripTrailingPara(sal_Bool bSet)103cdf0e10cSrcweir 	void SetStripTrailingPara( sal_Bool bSet ) { bStripTrailingPara = bSet; }
GetStripTrailingPara() const104cdf0e10cSrcweir 	sal_Bool GetStripTrailingPara() const { return bStripTrailingPara; }
105cdf0e10cSrcweir 
SetKeepNumRules(sal_Bool bSet)106cdf0e10cSrcweir 	void SetKeepNumRules( sal_Bool bSet ) { bKeepNumRules = bSet; }
GetKeepNumRules() const107cdf0e10cSrcweir 	sal_Bool GetKeepNumRules() const { return bKeepNumRules; }
108cdf0e10cSrcweir 
SetFixHeaderDist(sal_Bool bSet)109cdf0e10cSrcweir 	void SetFixHeaderDist( sal_Bool bSet ) { bFixHeaderDist = bSet; }
GetFixHeaderDist() const110cdf0e10cSrcweir 	sal_Bool GetFixHeaderDist() const { return bFixHeaderDist; }
111cdf0e10cSrcweir 
SetFixFooterDist(sal_Bool bSet)112cdf0e10cSrcweir 	void SetFixFooterDist( sal_Bool bSet ) { bFixFooterDist = bSet; }
GetFixFooterDist() const113cdf0e10cSrcweir 	sal_Bool GetFixFooterDist() const { return bFixFooterDist; }
114cdf0e10cSrcweir };
115cdf0e10cSrcweir 
GetAttrTab(sal_Bool bCreate)116cdf0e10cSrcweir _HTMLAttrTable *_HTMLAttrContext_SaveDoc::GetAttrTab( sal_Bool bCreate )
117cdf0e10cSrcweir {
118cdf0e10cSrcweir 	if( !pAttrTab && bCreate )
119cdf0e10cSrcweir 	{
120cdf0e10cSrcweir 		pAttrTab = new _HTMLAttrTable;
121cdf0e10cSrcweir 		memset( pAttrTab, 0, sizeof( _HTMLAttrTable ));
122cdf0e10cSrcweir 	}
123cdf0e10cSrcweir 	return pAttrTab;
124cdf0e10cSrcweir }
125cdf0e10cSrcweir 
126cdf0e10cSrcweir /*  */
127cdf0e10cSrcweir 
GetSaveDocContext(sal_Bool bCreate)128cdf0e10cSrcweir _HTMLAttrContext_SaveDoc *_HTMLAttrContext::GetSaveDocContext( sal_Bool bCreate )
129cdf0e10cSrcweir {
130cdf0e10cSrcweir 	if( !pSaveDocContext && bCreate )
131cdf0e10cSrcweir 		pSaveDocContext = new _HTMLAttrContext_SaveDoc;
132cdf0e10cSrcweir 
133cdf0e10cSrcweir 	return pSaveDocContext;
134cdf0e10cSrcweir }
135cdf0e10cSrcweir 
ClearSaveDocContext()136cdf0e10cSrcweir void _HTMLAttrContext::ClearSaveDocContext()
137cdf0e10cSrcweir {
138cdf0e10cSrcweir 	delete pSaveDocContext;
139cdf0e10cSrcweir 	pSaveDocContext = 0;
140cdf0e10cSrcweir }
141cdf0e10cSrcweir 
142cdf0e10cSrcweir /*  */
143cdf0e10cSrcweir 
SplitAttrTab(const SwPosition & rNewPos)144cdf0e10cSrcweir void SwHTMLParser::SplitAttrTab( const SwPosition& rNewPos )
145cdf0e10cSrcweir {
146cdf0e10cSrcweir 	// Hier darf es keine vorlauefigen Absatz-Attribute geben, den die
147cdf0e10cSrcweir 	// koennten jetzt gesetzt werden und dann sind die Zeiger ungueltig!!!
148cdf0e10cSrcweir 	ASSERT( !aParaAttrs.Count(),
149cdf0e10cSrcweir 		"Hoechste Gefahr: Es gibt noch nicht-endgueltige Absatz-Attribute" );
150cdf0e10cSrcweir 	if( aParaAttrs.Count() )
151cdf0e10cSrcweir 		aParaAttrs.Remove( 0, aParaAttrs.Count() );
152cdf0e10cSrcweir 
153cdf0e10cSrcweir 	const SwNodeIndex* pOldEndPara = &pPam->GetPoint()->nNode;
154cdf0e10cSrcweir 	xub_StrLen nOldEndCnt = pPam->GetPoint()->nContent.GetIndex();
155cdf0e10cSrcweir 
156cdf0e10cSrcweir 	const SwNodeIndex& rNewSttPara = rNewPos.nNode;
157cdf0e10cSrcweir 	xub_StrLen nNewSttCnt = rNewPos.nContent.GetIndex();
158cdf0e10cSrcweir 
159cdf0e10cSrcweir 	sal_Bool bMoveBack = sal_False;
160cdf0e10cSrcweir 
161cdf0e10cSrcweir 	// alle noch offenen Attribute beenden und hinter der Tabelle
162cdf0e10cSrcweir 	// neu aufspannen
163cdf0e10cSrcweir 	_HTMLAttr** pTbl = (_HTMLAttr**)&aAttrTab;
164cdf0e10cSrcweir 	for( sal_uInt16 nCnt = sizeof( _HTMLAttrTable ) / sizeof( _HTMLAttr* );
165cdf0e10cSrcweir 			nCnt--; ++pTbl )
166cdf0e10cSrcweir 	{
167cdf0e10cSrcweir 		_HTMLAttr *pAttr = *pTbl;
168cdf0e10cSrcweir 		while( pAttr )
169cdf0e10cSrcweir 		{
170cdf0e10cSrcweir 			_HTMLAttr *pNext = pAttr->GetNext();
171cdf0e10cSrcweir 			_HTMLAttr *pPrev = pAttr->GetPrev();
172cdf0e10cSrcweir 
173cdf0e10cSrcweir 			sal_uInt16 nWhich = pAttr->pItem->Which();
174cdf0e10cSrcweir 			if( !nOldEndCnt && RES_PARATR_BEGIN <= nWhich &&
175cdf0e10cSrcweir 				pAttr->GetSttParaIdx() < pOldEndPara->GetIndex() )
176cdf0e10cSrcweir 			{
177cdf0e10cSrcweir 				// Das Attribut muss eine Content-Position weiter vorne
178cdf0e10cSrcweir 				// beendet werden
179cdf0e10cSrcweir 				if( !bMoveBack )
180cdf0e10cSrcweir 				{
181cdf0e10cSrcweir 					bMoveBack = pPam->Move( fnMoveBackward );
182cdf0e10cSrcweir 					nOldEndCnt = pPam->GetPoint()->nContent.GetIndex();
183cdf0e10cSrcweir 				}
184cdf0e10cSrcweir 			}
185cdf0e10cSrcweir 			else if( bMoveBack )
186cdf0e10cSrcweir 			{
187cdf0e10cSrcweir 				pPam->Move( fnMoveForward );
188cdf0e10cSrcweir 				nOldEndCnt = pPam->GetPoint()->nContent.GetIndex();
189cdf0e10cSrcweir 			}
190cdf0e10cSrcweir 
191cdf0e10cSrcweir 			if( (RES_PARATR_BEGIN <= nWhich && bMoveBack) ||
192cdf0e10cSrcweir 				pAttr->GetSttParaIdx() < pOldEndPara->GetIndex() ||
193cdf0e10cSrcweir 				(pAttr->GetSttPara() == *pOldEndPara &&
194cdf0e10cSrcweir 				 pAttr->GetSttCnt() != nOldEndCnt) )
195cdf0e10cSrcweir 			{
196cdf0e10cSrcweir 				// Das Attribut muss gesetzt werden. Da wir
197cdf0e10cSrcweir 				// das Original noch brauchen, weil Zeiger auf das Attribut
198cdf0e10cSrcweir 				// noch in den Kontexten existieren, muessen wir es clonen.
199cdf0e10cSrcweir 				// Die Next-Liste geht dabei verloren, aber die
200cdf0e10cSrcweir 				// Previous-Liste bleibt erhalten
201cdf0e10cSrcweir 				_HTMLAttr *pSetAttr = pAttr->Clone( *pOldEndPara, nOldEndCnt );
202cdf0e10cSrcweir 
203cdf0e10cSrcweir 				if( pNext )
204cdf0e10cSrcweir 					pNext->InsertPrev( pSetAttr );
205cdf0e10cSrcweir 				else
206cdf0e10cSrcweir 				{
207cdf0e10cSrcweir 					sal_uInt16 nTmp =
208cdf0e10cSrcweir 						pSetAttr->bInsAtStart ? 0 : aSetAttrTab.Count();
209cdf0e10cSrcweir 					aSetAttrTab.Insert( pSetAttr, nTmp );
210cdf0e10cSrcweir 				}
211cdf0e10cSrcweir 			}
212cdf0e10cSrcweir 			else if( pPrev )
213cdf0e10cSrcweir 			{
214cdf0e10cSrcweir 				// Wenn das Attribut nicht gesetzt vor der Tabelle
215cdf0e10cSrcweir 				// gesetzt werden muss, muessen der Previous-Attribute
216cdf0e10cSrcweir 				// trotzdem gesetzt werden.
217cdf0e10cSrcweir 				if( pNext )
218cdf0e10cSrcweir 					pNext->InsertPrev( pPrev );
219cdf0e10cSrcweir 				else
220cdf0e10cSrcweir 				{
221cdf0e10cSrcweir 					sal_uInt16 nTmp = pPrev->bInsAtStart ? 0 : aSetAttrTab.Count();
222cdf0e10cSrcweir 					aSetAttrTab.Insert( pPrev, nTmp );
223cdf0e10cSrcweir 				}
224cdf0e10cSrcweir 			}
225cdf0e10cSrcweir 
226cdf0e10cSrcweir 			// den Start des Attributs neu setzen
227cdf0e10cSrcweir 			pAttr->nSttPara = rNewSttPara;
228cdf0e10cSrcweir 			pAttr->nEndPara = rNewSttPara;
229cdf0e10cSrcweir 			pAttr->nSttCntnt = nNewSttCnt;
230cdf0e10cSrcweir 			pAttr->nEndCntnt = nNewSttCnt;
231cdf0e10cSrcweir 			pAttr->pPrev = 0;
232cdf0e10cSrcweir 
233cdf0e10cSrcweir 			pAttr = pNext;
234cdf0e10cSrcweir 		}
235cdf0e10cSrcweir 	}
236cdf0e10cSrcweir 
237cdf0e10cSrcweir 	if( bMoveBack )
238cdf0e10cSrcweir 		pPam->Move( fnMoveForward );
239cdf0e10cSrcweir 
240cdf0e10cSrcweir }
241cdf0e10cSrcweir 
SaveDocContext(_HTMLAttrContext * pCntxt,sal_uInt16 nFlags,const SwPosition * pNewPos)242cdf0e10cSrcweir void SwHTMLParser::SaveDocContext( _HTMLAttrContext *pCntxt,
243cdf0e10cSrcweir 								   sal_uInt16 nFlags,
244cdf0e10cSrcweir 								   const SwPosition *pNewPos )
245cdf0e10cSrcweir {
246cdf0e10cSrcweir 	_HTMLAttrContext_SaveDoc *pSave = pCntxt->GetSaveDocContext( sal_True );
247cdf0e10cSrcweir 	pSave->SetStripTrailingPara( (HTML_CNTXT_STRIP_PARA & nFlags) != 0 );
248cdf0e10cSrcweir 	pSave->SetKeepNumRules( (HTML_CNTXT_KEEP_NUMRULE & nFlags) != 0 );
249cdf0e10cSrcweir 	pSave->SetFixHeaderDist( (HTML_CNTXT_HEADER_DIST & nFlags) != 0 );
250cdf0e10cSrcweir 	pSave->SetFixFooterDist( (HTML_CNTXT_FOOTER_DIST & nFlags) != 0 );
251cdf0e10cSrcweir 
252cdf0e10cSrcweir 	if( pNewPos )
253cdf0e10cSrcweir 	{
254cdf0e10cSrcweir 		// Wenn der PaM an eine andere Position gesetzt wird, muss
255cdf0e10cSrcweir 		// die Numerierung gerettet werden..
256cdf0e10cSrcweir 		if( !pSave->GetKeepNumRules() )
257cdf0e10cSrcweir 		{
258cdf0e10cSrcweir 			// Die Numerierung soll nicht beibehalten werden. Also muss
259cdf0e10cSrcweir 			// der aktuelle Zustand gerettet und die Numerierung
260cdf0e10cSrcweir 			// anschliessend ausgeschaltet werden.
261cdf0e10cSrcweir 			pSave->SetNumInfo( GetNumInfo() );
262cdf0e10cSrcweir 			GetNumInfo().Clear();
263cdf0e10cSrcweir 		}
264cdf0e10cSrcweir 
265cdf0e10cSrcweir 		if( (HTML_CNTXT_KEEP_ATTRS & nFlags) != 0 )
266cdf0e10cSrcweir 		{
267cdf0e10cSrcweir 			// Attribute an aktueller Position beenden und an neuer neu anfangen
268cdf0e10cSrcweir 			SplitAttrTab( *pNewPos );
269cdf0e10cSrcweir 		}
270cdf0e10cSrcweir 		else
271cdf0e10cSrcweir 		{
272cdf0e10cSrcweir 			_HTMLAttrTable *pSaveAttrTab = pSave->GetAttrTab( sal_True );
273cdf0e10cSrcweir 			SaveAttrTab( *pSaveAttrTab );
274cdf0e10cSrcweir 		}
275cdf0e10cSrcweir 
276cdf0e10cSrcweir 
277cdf0e10cSrcweir 		pSave->SetPos( *pPam->GetPoint() );
278cdf0e10cSrcweir 		*pPam->GetPoint() = *pNewPos;
279cdf0e10cSrcweir 	}
280cdf0e10cSrcweir 
281cdf0e10cSrcweir 	// Mit dem Setzen von nContextStMin koennen automatisch auch
282cdf0e10cSrcweir 	// keine gerade offenen Listen (DL/OL/UL) mehr beendet werden.
283cdf0e10cSrcweir 	if( (HTML_CNTXT_PROTECT_STACK & nFlags) != 0  )
284cdf0e10cSrcweir 	{
285cdf0e10cSrcweir 		pSave->SetContextStMin( nContextStMin );
286cdf0e10cSrcweir 		nContextStMin = aContexts.Count();
287cdf0e10cSrcweir 
288cdf0e10cSrcweir 		if( (HTML_CNTXT_KEEP_ATTRS & nFlags) == 0 )
289cdf0e10cSrcweir 		{
290cdf0e10cSrcweir 			pSave->SetContextStAttrMin( nContextStAttrMin );
291cdf0e10cSrcweir 			nContextStAttrMin = aContexts.Count();
292cdf0e10cSrcweir 		}
293cdf0e10cSrcweir 	}
294cdf0e10cSrcweir }
295cdf0e10cSrcweir 
RestoreDocContext(_HTMLAttrContext * pCntxt)296cdf0e10cSrcweir void SwHTMLParser::RestoreDocContext( _HTMLAttrContext *pCntxt )
297cdf0e10cSrcweir {
298cdf0e10cSrcweir 	_HTMLAttrContext_SaveDoc *pSave = pCntxt->GetSaveDocContext();
299cdf0e10cSrcweir 	if( !pSave )
300cdf0e10cSrcweir 		return;
301cdf0e10cSrcweir 
302cdf0e10cSrcweir 	if( pSave->GetStripTrailingPara() )
303cdf0e10cSrcweir 		StripTrailingPara();
304cdf0e10cSrcweir 
305cdf0e10cSrcweir 	if( pSave->GetPos() )
306cdf0e10cSrcweir 	{
307cdf0e10cSrcweir 		if( pSave->GetFixHeaderDist() || pSave->GetFixFooterDist() )
308cdf0e10cSrcweir 			FixHeaderFooterDistance( pSave->GetFixHeaderDist(),
309cdf0e10cSrcweir 									 pSave->GetPos() );
310cdf0e10cSrcweir 
311cdf0e10cSrcweir 		_HTMLAttrTable *pSaveAttrTab = pSave->GetAttrTab();
312cdf0e10cSrcweir 		if( !pSaveAttrTab )
313cdf0e10cSrcweir 		{
314cdf0e10cSrcweir 			// Attribute an aktueller Position beenden und an alter neu
315cdf0e10cSrcweir 			// anfangen.
316cdf0e10cSrcweir 			SplitAttrTab( *pSave->GetPos() );
317cdf0e10cSrcweir 		}
318cdf0e10cSrcweir 		else
319cdf0e10cSrcweir 		{
320cdf0e10cSrcweir 			RestoreAttrTab( *pSaveAttrTab );
321cdf0e10cSrcweir 		}
322cdf0e10cSrcweir 
323cdf0e10cSrcweir 		*pPam->GetPoint() = *pSave->GetPos();
324cdf0e10cSrcweir 
325cdf0e10cSrcweir 		// Die bisherigen Attribute koennen wir schonmal setzen.
326cdf0e10cSrcweir 		SetAttr();
327cdf0e10cSrcweir 	}
328cdf0e10cSrcweir 
329cdf0e10cSrcweir 	if( USHRT_MAX != pSave->GetContextStMin() )
330cdf0e10cSrcweir 	{
331cdf0e10cSrcweir 		nContextStMin = pSave->GetContextStMin();
332cdf0e10cSrcweir 		if( USHRT_MAX != pSave->GetContextStAttrMin() )
333cdf0e10cSrcweir 			nContextStAttrMin = pSave->GetContextStAttrMin();
334cdf0e10cSrcweir 	}
335cdf0e10cSrcweir 
336cdf0e10cSrcweir 	if( !pSave->GetKeepNumRules() )
337cdf0e10cSrcweir 	{
338cdf0e10cSrcweir 		// Die bisherige gemerkte Numerierung wieder setzen
339cdf0e10cSrcweir 		GetNumInfo().Set( pSave->GetNumInfo() );
340cdf0e10cSrcweir 	}
341cdf0e10cSrcweir 
342cdf0e10cSrcweir 	pCntxt->ClearSaveDocContext();
343cdf0e10cSrcweir }
344cdf0e10cSrcweir 
345cdf0e10cSrcweir /*  */
346cdf0e10cSrcweir 
EndContext(_HTMLAttrContext * pContext)347cdf0e10cSrcweir void SwHTMLParser::EndContext( _HTMLAttrContext *pContext )
348cdf0e10cSrcweir {
349cdf0e10cSrcweir 	if( pContext->GetPopStack() )
350cdf0e10cSrcweir 	{
351cdf0e10cSrcweir 		// Alle noch offenen Kontexte beenden. Der eigene
352cdf0e10cSrcweir 		// Kontext muss bereits geloscht sein!
353cdf0e10cSrcweir 		while( aContexts.Count() > nContextStMin )
354cdf0e10cSrcweir 		{
355cdf0e10cSrcweir 			_HTMLAttrContext *pCntxt = PopContext();
356cdf0e10cSrcweir 			ASSERT( pCntxt != pContext,
357cdf0e10cSrcweir 					"Kontext noch im Stack" );
358cdf0e10cSrcweir 			if( pCntxt == pContext )
359cdf0e10cSrcweir 				break;
360cdf0e10cSrcweir 
361cdf0e10cSrcweir 			EndContext( pCntxt );
362cdf0e10cSrcweir 			delete pCntxt;
363cdf0e10cSrcweir 		}
364cdf0e10cSrcweir 	}
365cdf0e10cSrcweir 
366cdf0e10cSrcweir 	// Alle noch offenen Attribute beenden
367cdf0e10cSrcweir 	if( pContext->HasAttrs() )
368cdf0e10cSrcweir 		EndContextAttrs( pContext );
369cdf0e10cSrcweir 
370cdf0e10cSrcweir 	// Falls ein Bereich geoeffnet wurde, den verlassen. Da Bereiche
371cdf0e10cSrcweir 	// auch innerhalb von absolut positionierten Objekten angelegt werden,
372cdf0e10cSrcweir 	// muss das passieren, bever ein alter Dokument-Kontext restauriert wird.
373cdf0e10cSrcweir 	if( pContext->GetSpansSection() )
374cdf0e10cSrcweir 		EndSection();
375cdf0e10cSrcweir 
376cdf0e10cSrcweir 	// Rahmen und sonstige Sonderbereiche verlassen.
377cdf0e10cSrcweir 	if( pContext->HasSaveDocContext() )
378cdf0e10cSrcweir 		RestoreDocContext( pContext );
379cdf0e10cSrcweir 
380cdf0e10cSrcweir 	// Ggf. noch einen Ansatz-Umbruch einfuegen
381cdf0e10cSrcweir 	if( AM_NONE != pContext->GetAppendMode() &&
382cdf0e10cSrcweir 		pPam->GetPoint()->nContent.GetIndex() )
383cdf0e10cSrcweir 		AppendTxtNode( pContext->GetAppendMode() );
384cdf0e10cSrcweir 
385cdf0e10cSrcweir 	// PRE-/LISTING- und XMP-Umgebungen wieder starten
386cdf0e10cSrcweir 	if( pContext->IsFinishPREListingXMP() )
387cdf0e10cSrcweir 		FinishPREListingXMP();
388cdf0e10cSrcweir 
389cdf0e10cSrcweir 	if( pContext->IsRestartPRE() )
390cdf0e10cSrcweir 		StartPRE();
391cdf0e10cSrcweir 
392cdf0e10cSrcweir 	if( pContext->IsRestartXMP() )
393cdf0e10cSrcweir 		StartXMP();
394cdf0e10cSrcweir 
395cdf0e10cSrcweir 	if( pContext->IsRestartListing() )
396cdf0e10cSrcweir 		StartListing();
397cdf0e10cSrcweir }
398cdf0e10cSrcweir 
ClearContext(_HTMLAttrContext * pContext)399cdf0e10cSrcweir void SwHTMLParser::ClearContext( _HTMLAttrContext *pContext )
400cdf0e10cSrcweir {
401cdf0e10cSrcweir 	_HTMLAttrs &rAttrs = pContext->GetAttrs();
402cdf0e10cSrcweir 	for( sal_uInt16 i=0; i<rAttrs.Count(); i++ )
403cdf0e10cSrcweir 	{
404cdf0e10cSrcweir 		// einfaches Loeschen reicht hier nicht, weil das
405cdf0e10cSrcweir 		// Attribut auch aus seiner Liste ausgetragen werden
406cdf0e10cSrcweir 		// muss. Theoretisch koennt man natuerlich auch die Liste
407cdf0e10cSrcweir 		// und die Attribute getrennt loeschen, aber wenn man
408cdf0e10cSrcweir 		// dann was falsch gemacht hat, sieht es uebel aus.
409cdf0e10cSrcweir 		DeleteAttr( rAttrs[i] );
410cdf0e10cSrcweir 	}
411cdf0e10cSrcweir 
412cdf0e10cSrcweir 	ASSERT( !pContext->GetSpansSection(),
413cdf0e10cSrcweir 			"Bereich kann nicht mehr verlassen werden" );
414cdf0e10cSrcweir 
415cdf0e10cSrcweir 	ASSERT( !pContext->HasSaveDocContext(),
416cdf0e10cSrcweir 			"Rahmen kann nicht mehr verlassen werden" );
417cdf0e10cSrcweir 
418cdf0e10cSrcweir 	// PRE-/LISTING- und XMP-Umgebungen wieder starten
419cdf0e10cSrcweir 	if( pContext->IsFinishPREListingXMP() )
420cdf0e10cSrcweir 		FinishPREListingXMP();
421cdf0e10cSrcweir 
422cdf0e10cSrcweir 	if( pContext->IsRestartPRE() )
423cdf0e10cSrcweir 		StartPRE();
424cdf0e10cSrcweir 
425cdf0e10cSrcweir 	if( pContext->IsRestartXMP() )
426cdf0e10cSrcweir 		StartXMP();
427cdf0e10cSrcweir 
428cdf0e10cSrcweir 	if( pContext->IsRestartListing() )
429cdf0e10cSrcweir 		StartListing();
430cdf0e10cSrcweir }
431cdf0e10cSrcweir 
432cdf0e10cSrcweir /*  */
433cdf0e10cSrcweir 
DoPositioning(SfxItemSet & rItemSet,SvxCSS1PropertyInfo & rPropInfo,_HTMLAttrContext * pContext)434cdf0e10cSrcweir sal_Bool SwHTMLParser::DoPositioning( SfxItemSet &rItemSet,
435cdf0e10cSrcweir 								  SvxCSS1PropertyInfo &rPropInfo,
436cdf0e10cSrcweir 								  _HTMLAttrContext *pContext )
437cdf0e10cSrcweir {
438cdf0e10cSrcweir 	sal_Bool bRet = sal_False;
439cdf0e10cSrcweir 
440cdf0e10cSrcweir 	// Unter folgenden Umstaenden wird jetzt ein Rahmen aufgemacht:
441cdf0e10cSrcweir 	// - das Tag wird absolut positioniert und left/top sind beide
442cdf0e10cSrcweir 	//   gegeben und enthalten auch keine %-Angabe, oder
443cdf0e10cSrcweir 	// - das Tag soll fliessen, und
444cdf0e10cSrcweir 	// - es wurde eine Breite angegeben (in beiden Faellen noetig)
445cdf0e10cSrcweir 	if( SwCSS1Parser::MayBePositioned( rPropInfo ) )
446cdf0e10cSrcweir 	{
447cdf0e10cSrcweir 		SfxItemSet aFrmItemSet( pDoc->GetAttrPool(),
448cdf0e10cSrcweir 								RES_FRMATR_BEGIN, RES_FRMATR_END-1 );
449cdf0e10cSrcweir 		if( !IsNewDoc() )
450cdf0e10cSrcweir 			Reader::ResetFrmFmtAttrs(aFrmItemSet );
451cdf0e10cSrcweir 
452cdf0e10cSrcweir 		// Ausrichtung setzen
453cdf0e10cSrcweir         SetAnchorAndAdjustment( text::VertOrientation::NONE, text::HoriOrientation::NONE, rItemSet, rPropInfo,
454cdf0e10cSrcweir 								aFrmItemSet );
455cdf0e10cSrcweir 
456cdf0e10cSrcweir 		// Groesse setzen
457cdf0e10cSrcweir 		SetVarSize( rItemSet, rPropInfo, aFrmItemSet );
458cdf0e10cSrcweir 
459cdf0e10cSrcweir 		// Abstaende setzen
460cdf0e10cSrcweir 		SetSpace( Size(0,0), rItemSet, rPropInfo, aFrmItemSet );
461cdf0e10cSrcweir 
462cdf0e10cSrcweir 		// Sonstige CSS1-Attribute Setzen
463cdf0e10cSrcweir 		SetFrmFmtAttrs( rItemSet, rPropInfo,
464cdf0e10cSrcweir 						HTML_FF_BOX|HTML_FF_PADDING|HTML_FF_BACKGROUND|HTML_FF_DIRECTION,
465cdf0e10cSrcweir 						aFrmItemSet );
466cdf0e10cSrcweir 
467cdf0e10cSrcweir 		InsertFlyFrame( aFrmItemSet, pContext, rPropInfo.aId,
468cdf0e10cSrcweir 						CONTEXT_FLAGS_ABSPOS );
469cdf0e10cSrcweir 		pContext->SetPopStack( sal_True );
470cdf0e10cSrcweir 		rPropInfo.aId.Erase();
471cdf0e10cSrcweir 		bRet = sal_True;
472cdf0e10cSrcweir 	}
473cdf0e10cSrcweir 
474cdf0e10cSrcweir 	return bRet;
475cdf0e10cSrcweir }
476cdf0e10cSrcweir 
CreateContainer(const String & rClass,SfxItemSet & rItemSet,SvxCSS1PropertyInfo & rPropInfo,_HTMLAttrContext * pContext)477cdf0e10cSrcweir sal_Bool SwHTMLParser::CreateContainer( const String& rClass,
478cdf0e10cSrcweir 									SfxItemSet &rItemSet,
479cdf0e10cSrcweir 									SvxCSS1PropertyInfo &rPropInfo,
480cdf0e10cSrcweir 									_HTMLAttrContext *pContext )
481cdf0e10cSrcweir {
482cdf0e10cSrcweir 	sal_Bool bRet = sal_False;
483cdf0e10cSrcweir 	if( rClass.EqualsIgnoreCaseAscii(sCSS1_class_abs_pos) &&
484cdf0e10cSrcweir 		pCSS1Parser->MayBePositioned( rPropInfo ) )
485cdf0e10cSrcweir 	{
486cdf0e10cSrcweir 		// Container-Klasse
487cdf0e10cSrcweir 		SfxItemSet *pFrmItemSet = pContext->GetFrmItemSet( pDoc );
488cdf0e10cSrcweir 		if( !IsNewDoc() )
489cdf0e10cSrcweir 			Reader::ResetFrmFmtAttrs( *pFrmItemSet );
490cdf0e10cSrcweir 
491cdf0e10cSrcweir         SetAnchorAndAdjustment( text::VertOrientation::NONE, text::HoriOrientation::NONE,
492cdf0e10cSrcweir 								rItemSet, rPropInfo, *pFrmItemSet );
493cdf0e10cSrcweir 		Size aDummy(0,0);
494cdf0e10cSrcweir 		SetFixSize( aDummy, aDummy, sal_False, sal_False, rItemSet, rPropInfo,
495cdf0e10cSrcweir 					*pFrmItemSet );
496cdf0e10cSrcweir 		SetSpace( aDummy, rItemSet, rPropInfo, *pFrmItemSet );
497cdf0e10cSrcweir 		SetFrmFmtAttrs( rItemSet, rPropInfo, HTML_FF_BOX|HTML_FF_BACKGROUND|HTML_FF_DIRECTION,
498cdf0e10cSrcweir 						*pFrmItemSet );
499cdf0e10cSrcweir 
500cdf0e10cSrcweir 		bRet = sal_True;
501cdf0e10cSrcweir 	}
502cdf0e10cSrcweir 
503cdf0e10cSrcweir 	return bRet;
504cdf0e10cSrcweir }
505cdf0e10cSrcweir 
506cdf0e10cSrcweir /*  */
507cdf0e10cSrcweir 
InsertAttrs(SfxItemSet & rItemSet,SvxCSS1PropertyInfo & rPropInfo,_HTMLAttrContext * pContext,sal_Bool bCharLvl)508cdf0e10cSrcweir void SwHTMLParser::InsertAttrs( SfxItemSet &rItemSet,
509cdf0e10cSrcweir 								SvxCSS1PropertyInfo &rPropInfo,
510cdf0e10cSrcweir 								_HTMLAttrContext *pContext,
511cdf0e10cSrcweir 								sal_Bool bCharLvl )
512cdf0e10cSrcweir {
513cdf0e10cSrcweir 	// Ein DropCap-Attribut basteln, wenn auf Zeichen-Ebene vor dem
514cdf0e10cSrcweir 	// ersten Zeichen ein float: left vorkommt
515cdf0e10cSrcweir 	if( bCharLvl && !pPam->GetPoint()->nContent.GetIndex() &&
516cdf0e10cSrcweir 		SVX_ADJUST_LEFT == rPropInfo.eFloat )
517cdf0e10cSrcweir 	{
518cdf0e10cSrcweir 		SwFmtDrop aDrop;
519cdf0e10cSrcweir 		aDrop.GetChars() = 1;
520cdf0e10cSrcweir 
521cdf0e10cSrcweir 		pCSS1Parser->FillDropCap( aDrop, rItemSet );
522cdf0e10cSrcweir 
523cdf0e10cSrcweir 		// Nur wenn das Initial auch ueber mehrere Zeilen geht, wird das
524cdf0e10cSrcweir 		// DropCap-Attribut gesetzt. Sonst setzten wir die Attribute hart.
525cdf0e10cSrcweir 		if( aDrop.GetLines() > 1 )
526cdf0e10cSrcweir 		{
527cdf0e10cSrcweir 			NewAttr( &aAttrTab.pDropCap, aDrop );
528cdf0e10cSrcweir 
529cdf0e10cSrcweir 			_HTMLAttrs &rAttrs = pContext->GetAttrs();
530cdf0e10cSrcweir 			rAttrs.Insert( aAttrTab.pDropCap, rAttrs.Count() );
531cdf0e10cSrcweir 
532cdf0e10cSrcweir 			return;
533cdf0e10cSrcweir 		}
534cdf0e10cSrcweir 	}
535cdf0e10cSrcweir 
536cdf0e10cSrcweir // Feature: PrintExt
537cdf0e10cSrcweir 	if( !bCharLvl )
538cdf0e10cSrcweir 		pCSS1Parser->SetFmtBreak( rItemSet, rPropInfo );
539cdf0e10cSrcweir // /Feature: PrintExt
540cdf0e10cSrcweir 
541cdf0e10cSrcweir 	ASSERT( aContexts.Count() <= nContextStAttrMin ||
542cdf0e10cSrcweir 			aContexts[aContexts.Count()-1] != pContext,
543cdf0e10cSrcweir 			"SwHTMLParser::InsertAttrs: Kontext doch schon auf dem Stack" );
544cdf0e10cSrcweir 
545cdf0e10cSrcweir 	SfxItemIter aIter( rItemSet );
546cdf0e10cSrcweir 
547cdf0e10cSrcweir 	const SfxPoolItem *pItem = aIter.FirstItem();
548cdf0e10cSrcweir 	while( pItem )
549cdf0e10cSrcweir 	{
550cdf0e10cSrcweir 		_HTMLAttr **ppAttr = 0;
551cdf0e10cSrcweir 
552cdf0e10cSrcweir 		switch( pItem->Which() )
553cdf0e10cSrcweir 		{
554cdf0e10cSrcweir 		case RES_LR_SPACE:
555cdf0e10cSrcweir 			{
556cdf0e10cSrcweir 				// Absatz-Einzuege muessen addiert werden und werden immer
557cdf0e10cSrcweir 				// nur absatzweise gesetzt (fuer den ersten Absatz hier,
558cdf0e10cSrcweir 				// fuer alle folgenden in SetTxtCollAttrs)
559cdf0e10cSrcweir 
560cdf0e10cSrcweir 				const SvxLRSpaceItem *pLRItem =
561cdf0e10cSrcweir 					(const SvxLRSpaceItem *)pItem;
562cdf0e10cSrcweir 
563cdf0e10cSrcweir 				// die bisherigen Absatz-Abstaende holen (ohne die vom
564cdf0e10cSrcweir 				// obersten Kontext, denn den veraendern wir ja gerade) ...
565cdf0e10cSrcweir 				sal_uInt16 nOldLeft = 0, nOldRight = 0;
566cdf0e10cSrcweir 				short nOldIndent = 0;
567cdf0e10cSrcweir 				sal_Bool bIgnoreTop = aContexts.Count() > nContextStMin &&
568cdf0e10cSrcweir 								  aContexts[aContexts.Count()-1] == pContext;
569cdf0e10cSrcweir 				GetMarginsFromContext( nOldLeft, nOldRight, nOldIndent,
570cdf0e10cSrcweir 									   bIgnoreTop  );
571cdf0e10cSrcweir 
572cdf0e10cSrcweir 
573cdf0e10cSrcweir 				// und noch die aktuell gueltigen
574cdf0e10cSrcweir 				sal_uInt16 nLeft = nOldLeft, nRight = nOldRight;
575cdf0e10cSrcweir 				short nIndent = nOldIndent;
576cdf0e10cSrcweir 				pContext->GetMargins( nLeft, nRight, nIndent );
577cdf0e10cSrcweir 
578cdf0e10cSrcweir 				// ... und die neuen Abstaende zu den alten addieren
579cdf0e10cSrcweir 				// Hier werden nicht die aus dem Item genommen, sondern die
580cdf0e10cSrcweir 				// extra gemerkten, weil die auch negativ sein koennen. Die
581cdf0e10cSrcweir 				// Abfrage ueber das Item funktioniert aber trotzdem, denn
582cdf0e10cSrcweir 				// fuer negative Werte wird das Item (mit Wert 0) auch
583cdf0e10cSrcweir 				// eingefuegt.
584cdf0e10cSrcweir 				if( rPropInfo.bLeftMargin )
585cdf0e10cSrcweir 				{
586cdf0e10cSrcweir 					ASSERT( rPropInfo.nLeftMargin < 0 ||
587cdf0e10cSrcweir 							rPropInfo.nLeftMargin == pLRItem->GetTxtLeft(),
588cdf0e10cSrcweir 							"linker Abstand stimmt nicht mit Item ueberein" );
589cdf0e10cSrcweir 					if( rPropInfo.nLeftMargin < 0 &&
590cdf0e10cSrcweir 						-rPropInfo.nLeftMargin > nOldLeft )
591cdf0e10cSrcweir 						nLeft = 0;
592cdf0e10cSrcweir 					else
593cdf0e10cSrcweir                         nLeft = nOldLeft + static_cast< sal_uInt16 >(rPropInfo.nLeftMargin);
594cdf0e10cSrcweir 				}
595cdf0e10cSrcweir 				if( rPropInfo.bRightMargin )
596cdf0e10cSrcweir 				{
597cdf0e10cSrcweir 					ASSERT( rPropInfo.nRightMargin < 0 ||
598cdf0e10cSrcweir 							rPropInfo.nRightMargin == pLRItem->GetRight(),
599cdf0e10cSrcweir 							"rechter Abstand stimmt nicht mit Item ueberein" );
600cdf0e10cSrcweir 					if( rPropInfo.nRightMargin < 0 &&
601cdf0e10cSrcweir 						-rPropInfo.nRightMargin > nOldRight )
602cdf0e10cSrcweir 						nRight = 0;
603cdf0e10cSrcweir 					else
604cdf0e10cSrcweir                         nRight = nOldRight + static_cast< sal_uInt16 >(rPropInfo.nRightMargin);
605cdf0e10cSrcweir 				}
606cdf0e10cSrcweir 				if( rPropInfo.bTextIndent )
607cdf0e10cSrcweir 					nIndent = pLRItem->GetTxtFirstLineOfst();
608cdf0e10cSrcweir 
609cdf0e10cSrcweir 				// und die Werte fuer nachfolgende Absaetze merken
610cdf0e10cSrcweir 				pContext->SetMargins( nLeft, nRight, nIndent );
611cdf0e10cSrcweir 
612cdf0e10cSrcweir 				// das Attribut noch am aktuellen Absatz setzen
613cdf0e10cSrcweir 				SvxLRSpaceItem aLRItem( *pLRItem );
614cdf0e10cSrcweir 				aLRItem.SetTxtFirstLineOfst( nIndent );
615cdf0e10cSrcweir 				aLRItem.SetTxtLeft( nLeft );
616cdf0e10cSrcweir 				aLRItem.SetRight( nRight );
617cdf0e10cSrcweir 				NewAttr( &aAttrTab.pLRSpace, aLRItem );
618cdf0e10cSrcweir 				EndAttr( aAttrTab.pLRSpace, 0, sal_False );
619cdf0e10cSrcweir 			}
620cdf0e10cSrcweir 			break;
621cdf0e10cSrcweir 
622cdf0e10cSrcweir 		case RES_UL_SPACE:
623cdf0e10cSrcweir 			if( !rPropInfo.bTopMargin || !rPropInfo.bBottomMargin )
624cdf0e10cSrcweir 			{
625cdf0e10cSrcweir 				sal_uInt16 nUpper = 0, nLower = 0;
626cdf0e10cSrcweir 				GetULSpaceFromContext( nUpper, nLower );
627cdf0e10cSrcweir 				SvxULSpaceItem aULSpace( *((const SvxULSpaceItem *)pItem) );
628cdf0e10cSrcweir 				if( !rPropInfo.bTopMargin )
629cdf0e10cSrcweir 					aULSpace.SetUpper( nUpper );
630cdf0e10cSrcweir 				if( !rPropInfo.bBottomMargin )
631cdf0e10cSrcweir 					aULSpace.SetLower( nLower );
632cdf0e10cSrcweir 
633cdf0e10cSrcweir 				NewAttr( &aAttrTab.pULSpace, aULSpace );
634cdf0e10cSrcweir 
635cdf0e10cSrcweir 				// ... und noch die Kontext-Information speichern
636cdf0e10cSrcweir 				_HTMLAttrs &rAttrs = pContext->GetAttrs();
637cdf0e10cSrcweir 				rAttrs.Insert( aAttrTab.pULSpace, rAttrs.Count() );
638cdf0e10cSrcweir 
639cdf0e10cSrcweir 				pContext->SetULSpace( aULSpace.GetUpper(), aULSpace.GetLower() );
640cdf0e10cSrcweir 			}
641cdf0e10cSrcweir 			else
642cdf0e10cSrcweir 			{
643cdf0e10cSrcweir 				ppAttr = &aAttrTab.pULSpace;
644cdf0e10cSrcweir 			}
645cdf0e10cSrcweir 			break;
646cdf0e10cSrcweir 		case RES_CHRATR_FONTSIZE:
647cdf0e10cSrcweir 			// es werden keine Attribute mit %-Angaben gesetzt
648cdf0e10cSrcweir 			if( ((const SvxFontHeightItem *)pItem)->GetProp() == 100 )
649cdf0e10cSrcweir 				ppAttr = &aAttrTab.pFontHeight;
650cdf0e10cSrcweir 			break;
651cdf0e10cSrcweir 		case RES_CHRATR_CJK_FONTSIZE:
652cdf0e10cSrcweir 			// es werden keine Attribute mit %-Angaben gesetzt
653cdf0e10cSrcweir 			if( ((const SvxFontHeightItem *)pItem)->GetProp() == 100 )
654cdf0e10cSrcweir 				ppAttr = &aAttrTab.pFontHeightCJK;
655cdf0e10cSrcweir 			break;
656cdf0e10cSrcweir 		case RES_CHRATR_CTL_FONTSIZE:
657cdf0e10cSrcweir 			// es werden keine Attribute mit %-Angaben gesetzt
658cdf0e10cSrcweir 			if( ((const SvxFontHeightItem *)pItem)->GetProp() == 100 )
659cdf0e10cSrcweir 				ppAttr = &aAttrTab.pFontHeightCTL;
660cdf0e10cSrcweir 			break;
661cdf0e10cSrcweir 
662cdf0e10cSrcweir 		case RES_BACKGROUND:
663cdf0e10cSrcweir 			if( bCharLvl )
664cdf0e10cSrcweir 			{
665cdf0e10cSrcweir 				// das Frame-Attr ggf. in ein Char-Attr umwandeln
666cdf0e10cSrcweir 				SvxBrushItem aBrushItem( *(const SvxBrushItem *)pItem );
667cdf0e10cSrcweir 				aBrushItem.SetWhich( RES_CHRATR_BACKGROUND );
668cdf0e10cSrcweir 
669cdf0e10cSrcweir 				// Das Attribut setzen ...
670cdf0e10cSrcweir 				NewAttr( &aAttrTab.pCharBrush, aBrushItem );
671cdf0e10cSrcweir 
672cdf0e10cSrcweir 				// ... und noch die Kontext-Information speichern
673cdf0e10cSrcweir 				_HTMLAttrs &rAttrs = pContext->GetAttrs();
674cdf0e10cSrcweir 				rAttrs.Insert( aAttrTab.pCharBrush, rAttrs.Count() );
675cdf0e10cSrcweir 			}
676cdf0e10cSrcweir 			else if( pContext->GetToken() != HTML_TABLEHEADER_ON &&
677cdf0e10cSrcweir 					 pContext->GetToken() != HTML_TABLEDATA_ON )
678cdf0e10cSrcweir 			{
679cdf0e10cSrcweir 				ppAttr = &aAttrTab.pBrush;
680cdf0e10cSrcweir 			}
681cdf0e10cSrcweir 			break;
682cdf0e10cSrcweir 
683cdf0e10cSrcweir 		default:
684cdf0e10cSrcweir 			// den zu dem Item gehoehrenden Tabellen-Eintrag ermitteln ...
685cdf0e10cSrcweir 			ppAttr = GetAttrTabEntry( pItem->Which() );
686cdf0e10cSrcweir 			break;
687cdf0e10cSrcweir 		}
688cdf0e10cSrcweir 
689cdf0e10cSrcweir 		if( ppAttr )
690cdf0e10cSrcweir 		{
691cdf0e10cSrcweir 			// Das Attribut setzen ...
692cdf0e10cSrcweir 			NewAttr( ppAttr, *pItem );
693cdf0e10cSrcweir 
694cdf0e10cSrcweir 			// ... und noch die Kontext-Information speichern
695cdf0e10cSrcweir 			_HTMLAttrs &rAttrs = pContext->GetAttrs();
696cdf0e10cSrcweir 			rAttrs.Insert( *ppAttr, rAttrs.Count() );
697cdf0e10cSrcweir 		}
698cdf0e10cSrcweir 
699cdf0e10cSrcweir 		// auf zum naechsten Item
700cdf0e10cSrcweir 		pItem = aIter.NextItem();
701cdf0e10cSrcweir 	}
702cdf0e10cSrcweir 
703cdf0e10cSrcweir 	if( rPropInfo.aId.Len() )
704cdf0e10cSrcweir 		InsertBookmark( rPropInfo.aId );
705cdf0e10cSrcweir }
706cdf0e10cSrcweir 
InsertAttr(_HTMLAttr ** ppAttr,const SfxPoolItem & rItem,_HTMLAttrContext * pCntxt)707cdf0e10cSrcweir void SwHTMLParser::InsertAttr( _HTMLAttr **ppAttr, const SfxPoolItem & rItem,
708cdf0e10cSrcweir 							   _HTMLAttrContext *pCntxt )
709cdf0e10cSrcweir {
710cdf0e10cSrcweir 	if( !ppAttr )
711cdf0e10cSrcweir 	{
712cdf0e10cSrcweir 		ppAttr = GetAttrTabEntry( rItem.Which() );
713cdf0e10cSrcweir 		if( !ppAttr )
714cdf0e10cSrcweir 			return;
715cdf0e10cSrcweir 	}
716cdf0e10cSrcweir 
717cdf0e10cSrcweir 	// das Attribut setzen
718cdf0e10cSrcweir 	NewAttr( ppAttr, rItem );
719cdf0e10cSrcweir 
720cdf0e10cSrcweir 	// und im Kontext merken
721cdf0e10cSrcweir 	_HTMLAttrs &rAttrs = pCntxt->GetAttrs();
722cdf0e10cSrcweir 	rAttrs.Insert( *ppAttr, rAttrs.Count() );
723cdf0e10cSrcweir }
724cdf0e10cSrcweir 
SplitPREListingXMP(_HTMLAttrContext * pCntxt)725cdf0e10cSrcweir void SwHTMLParser::SplitPREListingXMP( _HTMLAttrContext *pCntxt )
726cdf0e10cSrcweir {
727cdf0e10cSrcweir 	// PRE/Listing/XMP soll beim beenden des Kontexts beendet werden.
728cdf0e10cSrcweir 	pCntxt->SetFinishPREListingXMP( sal_True );
729cdf0e10cSrcweir 
730cdf0e10cSrcweir 	// Und die jetzt gueltigen Flags sollen wieder gesetzt werden.
731cdf0e10cSrcweir 	if( IsReadPRE() )
732cdf0e10cSrcweir 		pCntxt->SetRestartPRE( sal_True );
733cdf0e10cSrcweir 	if( IsReadXMP() )
734cdf0e10cSrcweir 		pCntxt->SetRestartXMP( sal_True );
735cdf0e10cSrcweir 	if( IsReadListing() )
736cdf0e10cSrcweir 		pCntxt->SetRestartListing( sal_True );
737cdf0e10cSrcweir 
738cdf0e10cSrcweir 	// PRE/Listing/XMP wird auuserdem sofort beendet
739cdf0e10cSrcweir 	FinishPREListingXMP();
740cdf0e10cSrcweir }
741cdf0e10cSrcweir 
GetFrmItemSet(SwDoc * pCreateDoc)742cdf0e10cSrcweir SfxItemSet *_HTMLAttrContext::GetFrmItemSet( SwDoc *pCreateDoc )
743cdf0e10cSrcweir {
744cdf0e10cSrcweir 	if( !pFrmItemSet && pCreateDoc )
745cdf0e10cSrcweir 		pFrmItemSet = new SfxItemSet( pCreateDoc->GetAttrPool(),
746cdf0e10cSrcweir 						RES_FRMATR_BEGIN, RES_FRMATR_END-1 );
747cdf0e10cSrcweir 	return pFrmItemSet;
748cdf0e10cSrcweir }
749