1 /* -*- mode: C++; tab-width: 4; c-basic-offset: 4; -*- */
2 
3 /* AbiWord
4  * Copyright (C) 1998,1999 AbiSource, Inc.
5  * BIDI Copyright (c) 2001,2002 Tomas Frydrych
6  *
7  * This program is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 2
10  * of the License, or (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
20  * 02110-1301 USA.
21  */
22 
23 #ifndef FL_BLOCKLAYOUT_H
24 #define FL_BLOCKLAYOUT_H
25 
26 #ifdef HAVE_CONFIG_H
27 #include "config.h"
28 #endif
29 
30 #ifdef FMT_TEST
31 #include <stdio.h>
32 #endif
33 
34 #include "ut_misc.h"
35 #include "ut_types.h"
36 #include "ut_vector.h"
37 #include "ut_growbuf.h"
38 #include "ut_xml.h"
39 #include "pt_Types.h"
40 #include "fl_Layout.h"
41 #include "fl_DocLayout.h"		// FIXME: this is needed for the friend'ed function
42 #include "fg_Graphic.h"
43 #include "fl_AutoLists.h"
44 #include "pp_Property.h"
45 #include "fl_ContainerLayout.h"
46 #include "fl_SectionLayout.h"
47 #include "fl_PartOfBlock.h"
48 #include "fb_LineBreaker.h"
49 #include "ut_string_class.h"
50 #include "ut_misc.h"
51 #include "pp_PropertyMap.h"
52 
53 // number of DocPositions occupied by the block strux
54 #define fl_BLOCK_STRUX_OFFSET	1
55 
56 class fl_Squiggles;
57 class fl_SpellSquiggles;
58 class fl_GrammarSquiggles;
59 class FL_DocLayout;
60 class fl_SectionLayout;
61 class fl_ContainerLayout;
62 class fb_LineBreaker;
63 class fb_Alignment;
64 class fp_Line;
65 class fp_Run;
66 class GR_Graphics;
67 class PD_Document;
68 class PP_Property;
69 class PX_ChangeRecord_FmtMark;
70 class PX_ChangeRecord_FmtMarkChange;
71 class PX_ChangeRecord_Object;
72 class PX_ChangeRecord_ObjectChange;
73 class PX_ChangeRecord_Span;
74 class PX_ChangeRecord_SpanChange;
75 class PX_ChangeRecord_Strux;
76 class PX_ChangeRecord_StruxChange;
77 class pf_Frag_Strux;
78 class pf_Frag_Object;
79 class fl_AutoNum;
80 class fp_VerticalContainer;
81 class fp_HyperlinkRun;
82 
83 // Tab types and leaders
84 typedef enum {
85 	FL_TAB_NONE = 0,
86 	FL_TAB_LEFT,
87 	FL_TAB_CENTER,
88 	FL_TAB_RIGHT,
89 	FL_TAB_DECIMAL,
90 	FL_TAB_BAR,
91 	__FL_TAB_MAX
92 } eTabType;
93 
94 typedef enum {
95 	FL_LEADER_NONE = 0,
96 	FL_LEADER_DOT,
97 	FL_LEADER_HYPHEN,
98 	FL_LEADER_UNDERLINE,
99 	FL_LEADER_THICKLINE,
100 	FL_LEADER_EQUALSIGN,
101 	__FL_LEADER_MAX
102 } eTabLeader;
103 
104 
105 /*
106 	Blocks are stored in a linked list which contains all of the blocks in
107 	the normal flow, in order.
108 */
109 
110 class SpellChecker;
111 class fl_TabStop;
112 ABI_EXPORT void buildTabStops(const char* pszTabStops, UT_GenericVector<fl_TabStop*> &m_vecTabs);
113 
114 class ABI_EXPORT fl_BlockLayout : public fl_ContainerLayout
115 {
116 	friend class fl_Squiggles;
117 	friend class fl_SpellSquiggles;
118 	friend class fl_GrammarSquiggles;
119 	friend class fl_DocListener;
120 	friend class fl_TOCLayout;
121 	friend class fb_LineBreaker;
122 
123 #ifdef ENABLE_SPELL
124 	// TODO: shack - code should be moved from toggleAuto to a function in
125 	// here - to handle the squiggles
126 	friend void FL_DocLayout::_toggleAutoSpell(bool bSpell);
127 #endif
128 
129 public:
130 	fl_BlockLayout(pf_Frag_Strux* sdh,
131 				   fl_ContainerLayout* pPrev, fl_SectionLayout*,
132 				   PT_AttrPropIndex indexAP, bool bIsHdrFtr = false);
133 	~fl_BlockLayout();
134 
135 	typedef enum _eSpacingPolicy
136 	{
137 		spacing_MULTIPLE,
138 		spacing_EXACT,
139 		spacing_ATLEAST
140 	} eSpacingPolicy;
141 
142     void                formatAll(void);
143 	virtual void        format(void);
144 	void                formatWrappedFromHere(fp_Line * pLine,fp_Page * pPage);
145 	fp_Line *           getNextWrappedLine(UT_sint32 iX,
146 											  UT_sint32 iHeight,
147 										   fp_Page * pPage);
148 	void                getLeftRightForWrapping(UT_sint32 iX,
149 												UT_sint32 iHeight,
150 												UT_sint32 & iMinLeft,
151 												UT_sint32 & iMinRight,
152 												UT_sint32 & iMinWidth);
153 	virtual bool		recalculateFields(UT_uint32 iUpdateCount);
154 
155 	virtual void		redrawUpdate();
updateLayout(bool)156 	virtual void        updateLayout(bool /*bDoAll*/) {}
157 	virtual fp_Container * getNewContainer(fp_Container * pCon = NULL);
getView(void)158 	FV_View *		getView(void) const {
159 		UT_return_val_if_fail( m_pLayout, NULL );
160 		return m_pLayout->getView();
161 	}
162 
163 	const char* getProperty(const gchar * pszName, bool bExpandStyles = true) const;
164 	const PP_PropertyType * getPropertyType(const gchar * szName,
165 											tProperty_type Type, bool bExpandStyles = true) const;
166 	void setAlignment(UT_uint32 iAlignCmd);
167 	UT_sint32       getLength(void) const;
168 	bool            isEmbeddedType(void) const;
169 	bool            isNotTOCable(void) const;
170 	bool            isLastRunInBlock(fp_Run * pRun) const;
171 	void            updateOffsets(PT_DocPosition posEmbedded,
172 								  UT_uint32 iEmebbedSize, UT_sint32 iSuggestedDiff);
173 	void            updateEnclosingBlockIfNeeded(void);
174 	fl_BlockLayout * getEnclosingBlock(void) const;
175 	UT_sint32       getEmbeddedOffset(UT_sint32 startOffset, fl_ContainerLayout *& pEmbedCL) const;
176 	void            shuffleEmbeddedIfNeeded(fl_BlockLayout * pBlock, UT_uint32 blockOffset);
177 
178 	bool            getXYOffsetToLine(UT_sint32 & xoff, UT_sint32 & yoff, fp_Line * pLine) const;
179 	bool            setFramesOnPage(fp_Line * pLastLine);
180 	UT_sint32       getMinWrapWidth(void) const;
181 	UT_sint32       getHeightOfBlock(bool b_withMargins = true);
182 	fp_Line *       findLineWithFootnotePID(UT_uint32 pid) const;
183 	UT_sint32 getMaxNonBreakableRun(void) const;
184 	fp_Line* findPrevLineInDocument(fp_Line*) const;
185 	fp_Line* findNextLineInDocument(fp_Line*) const;
186 	virtual void     appendTextToBuf(UT_GrowBuf & buf) const;
187 	void             appendUTF8String(UT_UTF8String & sText) const;
getFirstRun(void)188 	virtual fp_Run* getFirstRun(void) const { return m_pFirstRun; }
setFirstRun(fp_Run * pRun)189 	inline void setFirstRun(fp_Run* pRun) { m_pFirstRun = pRun; }
190 	void        clearPrint(void) const;
isListItem(void)191 	inline bool isListItem(void) const { return m_bListItem; }
192 	bool isFirstInList(void) const;
193 //	inline fl_AutoNum * getAutoNum(void) const { return m_pAutoNum; }
194 	void	getListAttributesVector(UT_GenericVector<const gchar*> * va) const;
195 	void  getListPropertyVector(UT_GenericVector<const gchar*> * vp) const;
196 
197 	void  refreshRunProperties(void) const;
198 	char *	getFormatFromListType(FL_ListType iListType) const;
199 	void remItemFromList(void);
200 	virtual void listUpdate(void);
201 	void resumeList( fl_BlockLayout * prevList);
202 	void prependList( fl_BlockLayout * nextList);
203 	FL_ListType decodeListType(char * listformat) const;
204 	FL_ListType getListType(void) const;
205 	gchar* getListStyleString( FL_ListType iListType) const;
206 	FL_ListType getListTypeFromStyle( const gchar * style) const;
207 	fl_BlockLayout * getNextList(UT_uint32 id) const;
208 	bool isListLabelInBlock(void) const;
209 	void StartList( const gchar * style, pf_Frag_Strux* prevSDH = NULL);
210 
211 	void StartList( FL_ListType lType, UT_uint32 start,
212 					const gchar * lDelim, const gchar * lDecimal,
213 					const gchar * fFont, float Align, float indent,
214 					UT_uint32 iParentID = 0, UT_uint32 level=0 );
215 
216 	void StopListInBlock(void);
217 	void deleteListLabel(void);
218 	UT_UCSChar * getListLabel(void) const;
219 	void transferListFlags(void);
220 	UT_uint32 getLevel(void) const;
221 	void setStarting( bool bValue);
222 	void setStopping( bool bValue);
223 	fl_BlockLayout * getPreviousList(UT_uint32 id) const;
224 	fl_BlockLayout * getPreviousList(void) const;
225 	fl_BlockLayout * getPreviousListOfSameMargin(void) const;
226 	fl_BlockLayout * getParentItem(void) const;
227 
228 #ifdef ENABLE_SPELL
229 	void findSpellSquigglesForRun(fp_Run* pRun) const;
230 	void drawGrammarSquiggles(void) const;
231 	void findGrammarSquigglesForRun(fp_Run* pRun) const;
232 #endif
233 
234 	UT_uint32 canSlurp(fp_Line* pLine) const;
235 
236 	PT_DocPosition getPosition(bool bActualBlockPos=false) const;
237 	fp_Run* findPointCoords(PT_DocPosition position, bool bEOL,
238 							UT_sint32& x, UT_sint32& y, UT_sint32& x2,
239 							UT_sint32& y2, UT_sint32& height, bool& bDirection) const;
240 
241 	fp_Run* findRunAtOffset(UT_uint32 offset) const;
242 
243 	bool	getBlockBuf(UT_GrowBuf * pgb) const;
244 
245 	void clearScreen(GR_Graphics*) const;
246 
247 
248 	void                getStyle(UT_UTF8String & sStyle) const;
249 	UT_sint32	        getTextIndent(void) const;
getLeftMargin(void)250 	inline UT_sint32	getLeftMargin(void) const { return m_iLeftMargin; }
getRightMargin(void)251 	inline UT_sint32	getRightMargin(void) const { return m_iRightMargin; }
getTopMargin(void)252 	inline UT_sint32	getTopMargin(void) const { return m_iTopMargin; }
getBottomMargin(void)253 	inline UT_sint32	getBottomMargin(void) const { return m_iBottomMargin; }
getAlignment(void)254 	inline fb_Alignment *		getAlignment(void) const { return m_pAlignment; }
getDocLayout(void)255 	virtual FL_DocLayout*		getDocLayout(void) const { return m_pLayout; }
getSectionLayout(void)256 	virtual fl_SectionLayout*	getSectionLayout(void) const { return m_pSectionLayout;}
257 	fl_DocSectionLayout * getDocSectionLayout(void) const;
258 
259 	void setSectionLayout(fl_SectionLayout* pSectionLayout);
260 
261 	void getLineSpacing(double& dSpacing,
262 						eSpacingPolicy& eSpacing) const;
263 
getProp_Orphans(void)264 	inline UT_uint32 getProp_Orphans(void) const { return m_iOrphansProperty; }
getProp_Widows(void)265 	inline UT_uint32 getProp_Widows(void) const { return m_iWidowsProperty; }
getProp_KeepTogether(void)266 	inline bool getProp_KeepTogether(void) const { return m_bKeepTogether; }
getProp_KeepWithNext(void)267 	inline bool getProp_KeepWithNext(void) const { return m_bKeepWithNext; }
268 
getDominantDirection(void)269 	inline UT_BidiCharType getDominantDirection(void) const { return m_iDomDirection; }
270 	void setDominantDirection(UT_BidiCharType iDirection);
271 
272 #ifdef ENABLE_SPELL
getSpellSquiggles(void)273 	inline fl_SpellSquiggles* getSpellSquiggles(void) const { return m_pSpellSquiggles; }
getGrammarSquiggles(void)274 	inline fl_GrammarSquiggles* getGrammarSquiggles(void) const { return  m_pGrammarSquiggles; }
275 #endif
276 
277 	bool isHdrFtr(void) const;
setHdrFtr(void)278 	void setHdrFtr(void) { m_bIsHdrFtr = true;}
clearHdrFtr(void)279 	void clearHdrFtr(void) { m_bIsHdrFtr = false;}
280 
281 #ifdef ENABLE_SPELL
282 	bool checkSpelling(void);
283 #endif
284 	void debugFlashing(void);
285 	bool	findNextTabStop(UT_sint32 iStartX, UT_sint32 iMaxX,
286 							UT_sint32& iPosition, eTabType& iType,
287 							eTabLeader &iLeader ) const;
288 	bool	findPrevTabStop(UT_sint32 iStartX, UT_sint32 iMaxX,
289 							UT_sint32& iPosition, eTabType& iType,
290 							eTabLeader &iLeader ) const;
hasUpdatableField(void)291 	bool    hasUpdatableField(void) { return m_bHasUpdatableField;}
setUpdatableField(bool bValue)292 	void    setUpdatableField(bool bValue) { m_bHasUpdatableField = bValue;}
getDefaultTabInterval(void)293 	inline UT_sint32 getDefaultTabInterval(void) const { return m_iDefaultTabInterval; }
getTabsCount(void)294 	inline UT_sint32 getTabsCount(void) const {
295 		return m_vecTabs.getItemCount();
296 	}
297 
298 	bool doclistener_populateSpan(const PX_ChangeRecord_Span * pcrs, PT_BlockOffset blockOffset, UT_uint32 len);
299 	bool doclistener_populateObject(PT_BlockOffset blockOffset, const PX_ChangeRecord_Object * pcro);
300 
301 	bool doclistener_insertSpan(const PX_ChangeRecord_Span * pcrs);
302 	bool doclistener_deleteSpan(const PX_ChangeRecord_Span * pcrs);
303 	bool doclistener_changeSpan(const PX_ChangeRecord_SpanChange * pcrsc);
304 	bool doclistener_deleteStrux(const PX_ChangeRecord_Strux * pcrx);
305 	bool doclistener_changeStrux(const PX_ChangeRecord_StruxChange * pcrxc);
306 	bool doclistener_insertFirstBlock(const PX_ChangeRecord_Strux * pcrx,
307 									  pf_Frag_Strux* sdh,
308 									  PL_ListenerId lid,
309 									  void (* pfnBindHandles)(pf_Frag_Strux* sdhNew,
310 															  PL_ListenerId lid,
311 															  fl_ContainerLayout* sfhNew));
312 	bool doclistener_insertBlock(const PX_ChangeRecord_Strux * pcrx,
313 								 pf_Frag_Strux* sdh,
314 								 PL_ListenerId lid,
315 								 void (* pfnBindHandles)(pf_Frag_Strux* sdhNew,
316 														 PL_ListenerId lid,
317 														 fl_ContainerLayout* sfhNew));
318 	bool doclistener_insertSection(const PX_ChangeRecord_Strux * pcrx,
319 								   SectionType iType,
320 								   pf_Frag_Strux* sdh,
321 								   PL_ListenerId lid,
322 								   void (* pfnBindHandles)(pf_Frag_Strux* sdhNew,
323 														   PL_ListenerId lid,
324 														   fl_ContainerLayout* sfhNew));
325 
326 	fl_SectionLayout *  doclistener_insertTable(const PX_ChangeRecord_Strux * pcrx,
327 								   SectionType iType,
328 								   pf_Frag_Strux* sdh,
329 								   PL_ListenerId lid,
330 								   void (* pfnBindHandles)(pf_Frag_Strux* sdhNew,
331 														   PL_ListenerId lid,
332 														   fl_ContainerLayout* sfhNew));
333 	fl_SectionLayout *  doclistener_insertFrame(const PX_ChangeRecord_Strux * pcrx,
334 								   SectionType iType,
335 								   pf_Frag_Strux* sdh,
336 								   PL_ListenerId lid,
337 								   void (* pfnBindHandles)(pf_Frag_Strux* sdhNew,
338 														   PL_ListenerId lid,
339 														   fl_ContainerLayout* sfhNew));
340 
341 	bool doclistener_insertObject(const PX_ChangeRecord_Object * pcro);
342 	bool doclistener_deleteObject(const PX_ChangeRecord_Object * pcro);
343 	bool doclistener_changeObject(const PX_ChangeRecord_ObjectChange * pcroc);
344 
345 	bool doclistener_insertFmtMark(const PX_ChangeRecord_FmtMark * pcrfm);
346 	bool doclistener_deleteFmtMark(const PX_ChangeRecord_FmtMark * pcrfm);
347 	bool doclistener_changeFmtMark(const PX_ChangeRecord_FmtMarkChange * pcrfmc);
348 
349 	void					purgeLayout(void);
350 	virtual void			collapse(void);
isCollapsed(void)351 	virtual bool			isCollapsed(void) const
352 		{return m_bIsCollapsed;}
353 	void					coalesceRuns(void) const;
354 	virtual void			setNeedsReformat(fl_ContainerLayout * pCL, UT_uint32 offset = 0);
needsReformat(void)355 	inline bool 		    needsReformat(void) const
356 		{ return (m_iNeedsReformat >= 0); }
357 	virtual void			setNeedsRedraw(void);
needsRedraw(void)358 	virtual bool 		    needsRedraw(void) const
359 		{ return m_bNeedsRedraw; }
360 	virtual void			markAllRunsDirty(void);
361 	UT_sint32               findLineInBlock(fp_Line * pLine) const;
362 
363 	bool                    isWordDelimiter(UT_UCS4Char c, UT_UCS4Char next, UT_UCS4Char prev, UT_uint32 iBlockPos) const;
364 	bool                    isSentenceSeparator(UT_UCS4Char c, UT_uint32 iBlockPos) const;
365 #ifdef ENABLE_SPELL
366 	bool					checkWord(const fl_PartOfBlockPtr& pPOB) const;
367 	void					recheckIgnoredWords();
368 #endif
setStyleInTOC(bool b)369 	void                    setStyleInTOC(bool b)
370 	{	m_bStyleInTOC = b;}
371 	void                    forceSectionBreak(void);
isContainedByTOC(void)372 	bool                    isContainedByTOC(void) const
373 	    { return m_bIsTOC;}
374 	FootnoteType            getTOCNumType(void) const;
375 	eTabLeader              getTOCTabLeader(UT_sint32 iOff) const;
376 	UT_sint32               getTOCTabPosition(UT_sint32 iOff) const;
setAccumHeight(UT_sint32 i)377 	void                    setAccumHeight(UT_sint32 i)
378 	{ m_iAccumulatedHeight =i;}
getAccumHeight(void)379 	UT_sint32               getAccumHeight(void) const
380 	{ return m_iAccumulatedHeight;}
381 	static bool 		s_EnumTabStops(void * myThis, UT_uint32 k, fl_TabStop *pTabInfo);
382 
addBackgroundCheckReason(UT_uint32 reason)383 	inline void 		addBackgroundCheckReason(UT_uint32 reason) {m_uBackgroundCheckReasons |= reason;}
removeBackgroundCheckReason(UT_uint32 reason)384 	inline void 		removeBackgroundCheckReason(UT_uint32 reason) {m_uBackgroundCheckReasons &= ~reason;}
hasBackgroundCheckReason(UT_uint32 reason)385 	inline bool 	hasBackgroundCheckReason(UT_uint32 reason) const {return ((m_uBackgroundCheckReasons & reason) ? true : false);}
386 
387 	// The following is a set of bit flags giving the reason this block is
388 	// queued for background checking.	See specific values in fl_DocLayout.h
389 	UT_uint32				m_uBackgroundCheckReasons;
setPrevListLabel(bool b)390 	void                    setPrevListLabel(bool b)
391 	{ m_bPrevListLabel = b;}
392 	bool                    getNextTableElement(UT_GrowBuf * buf,
393 												PT_DocPosition startPos,
394 												PT_DocPosition & begPos,
395 												PT_DocPosition & endPos,
396 												UT_UTF8String & sWord,
397 												UT_uint32 iDelim) const;
398 	bool                   itemizeSpan(PT_BlockOffset blockOffset, UT_uint32 len,GR_Itemization & I);
399 	const UT_RGBColor      getShadingingForeColor(void) const;
400 	const UT_RGBColor      getShadingingBackColor(void) const;
401 	UT_sint32              getPattern(void) const;
402 
getBottom()403 	const PP_PropertyMap::Line & getBottom () const { return m_lineBottom; }
getLeft()404 	const PP_PropertyMap::Line & getLeft ()   const { return m_lineLeft; }
getRight()405 	const PP_PropertyMap::Line & getRight ()  const { return m_lineRight; }
getTop()406 	const PP_PropertyMap::Line & getTop ()    const { return m_lineTop; }
407 
408 	bool                   hasBorders(void) const;
409 	bool                   canMergeBordersWithPrev(void) const;
410 	bool                   canMergeBordersWithNext(void) const;
411 	void                   setLineHeightBlockWithBorders(int whichLine = 0);
412 
413 #ifdef ENABLE_SPELL
414 	/** put in queue for spellchecking after prev. If prev == NULL is put at the head */
415 	void enqueueToSpellCheckAfter(fl_BlockLayout *prev);
416 	/** remove from the spellchecking queue */
417 	void dequeueFromSpellCheck(void);
418 	/** call to clear the queue. Warning, you can mess up things */
clearQueueing(void)419 	void clearQueueing(void)
420 	{
421 		m_prevToSpell = m_nextToSpell = NULL;
422 	}
nextToSpell(void)423 	fl_BlockLayout *nextToSpell(void) const
424 	{
425 		return m_nextToSpell;
426 	}
427 	/** return true if the block is queued */
isQueued(void)428 	bool isQueued(void) const
429 	{
430 		return (m_prevToSpell != NULL)
431 			|| (m_pLayout->spellQueueHead() == this);
432 	}
433 #endif
434 
435 #ifdef FMT_TEST
436 	void					__dump(FILE * fp) const;
437 #endif
438 
439 private:
440 	virtual bool            _canContainPoint() const;
441 
442 protected:
443 
444 	void					_recalcPendingWord(UT_uint32 iOffset, UT_sint32 chg) const;
445 	bool					_doCheckWord(const fl_PartOfBlockPtr& pPOB,
446 										 const UT_UCSChar* pBlockText,
447 										 UT_sint32 iLength,
448 										 bool bAddSquiggle = true,
449 										 bool bClearScreen = true) const;
450 
451 #ifdef ENABLE_SPELL
452 	bool					_spellCheckWord(const UT_UCSChar * word, UT_uint32 len, UT_uint32 blockPos) const;
453 	SpellChecker * _getSpellChecker (UT_uint32 blockPos) const;
454 #endif
455 
456 	bool					_truncateLayout(fp_Run* pTruncRun);
457 
458 #ifndef NDEBUG
459 	void					_assertRunListIntegrityImpl(void) const;
460 #endif
461 	void             			_assertRunListIntegrity(void) const;
462 
463 	void					_mergeRuns(fp_Run* pFirstRunToMerge, fp_Run* pLastRunToMerge) const;
464 
465 	bool					_doInsertRun(fp_Run* pNewRun);
466 	bool					_delete(PT_BlockOffset blockOffset, UT_uint32 len);
467 	bool					_doInsertTextSpan(PT_BlockOffset blockOffset, UT_uint32 len);
468 	bool					_doInsertForcedLineBreakRun(PT_BlockOffset blockOffset);
469 	bool					_doInsertFieldStartRun(PT_BlockOffset blockOffset);
470 	bool					_doInsertFieldEndRun(PT_BlockOffset blockOffset);
471 	bool					_doInsertBookmarkRun(PT_BlockOffset blockOffset);
472 	bool					_doInsertHyperlinkRun(PT_BlockOffset blockOffset);
473 	bool					_doInsertAnnotationRun(PT_BlockOffset blockOffset);
474 	bool					_doInsertRDFAnchorRun(PT_BlockOffset blockOffset);
475     void                    _finishInsertHyperlinkedNewRun( PT_BlockOffset blockOffset, fp_HyperlinkRun* pNewRun );
476 	bool					_doInsertMathRun(PT_BlockOffset blockOffset,PT_AttrPropIndex indexAP,pf_Frag_Object* oh);
477 	bool					_doInsertEmbedRun(PT_BlockOffset blockOffset,PT_AttrPropIndex indexAP,pf_Frag_Object* oh);
478 //	bool					_deleteBookmarkRun(PT_BlockOffset blockOffset);
479 	bool					_doInsertForcedColumnBreakRun(PT_BlockOffset blockOffset);
480 	bool					_doInsertForcedPageBreakRun(PT_BlockOffset blockOffset);
481 	bool					_doInsertTabRun(PT_BlockOffset blockOffset);
482 	bool					_doInsertTOCTabRun(PT_BlockOffset blockOffset);
483 	bool					_doInsertTOCListLabelRun(PT_BlockOffset blockOffset);
484 	bool					_doInsertTOCHeadingRun(PT_BlockOffset blockOffset);
485 	bool                    _doInsertTOCListTabRun(PT_BlockOffset blockOffset);
486 	bool					_doInsertImageRun(PT_BlockOffset blockOffset, FG_Graphic* pFG, pf_Frag_Object* oh);
487 	bool					_doInsertFieldRun(PT_BlockOffset blockOffset, const PX_ChangeRecord_Object * pcro);
488 	bool					_doInsertFieldTOCRun(PT_BlockOffset blockOffset);
489 	bool                    _doInsertDirectionMarkerRun(PT_BlockOffset blockOffset, UT_UCS4Char iM);
490 	bool					_deleteFmtMark(PT_BlockOffset blockOffset);
491 
492 	virtual void			_lookupProperties(const PP_AttrProp* pAP);
493 	virtual void			_lookupMarginProperties(const PP_AttrProp* pAP);
494 	void					_removeLine(fp_Line*, bool bRemoveFromContainer, bool bReCalc);
495 	void                    _purgeLine(fp_Line*);
496 	void					_removeAllEmptyLines(void);
497 
498 	bool					_checkMultiWord(UT_sint32 iStart,
499 											UT_sint32 eor,
500 											bool bToggleIP) const;
501 
502 	UT_uint32				_getLastChar();
503 	void					_stuffAllRunsOnALine(void);
504 	void					_insertEndOfParagraphRun(void);
505 	void					_purgeEndOfParagraphRun(void);
506 	void					_breakLineAfterRun(fp_Run* /*pRun*/);
507 
508 	static void 			_prefsListener(XAP_Prefs *pPrefs, UT_StringPtrMap * /*phChanges*/, void * data);
509 
510 	void					_createListLabel(void);
511 	void					_deleteListLabel(void);
512 	inline void 			_addBlockToPrevList( fl_BlockLayout * prevBlockInList, UT_uint32 level);
513 	inline void 			_prependBlockToPrevList( fl_BlockLayout * nextBlockInList);
514 	UT_sint32 				m_iNeedsReformat; // will store offset
515 											  // from which reformat
516 											  // is need, -1 if not
517 	bool					m_bNeedsRedraw;
518 	bool				    m_bIsHdrFtr;
519 
520 	FL_DocLayout*			m_pLayout;
521 	fb_LineBreaker 		    m_Breaker;
522 
523 	fp_Run* 				m_pFirstRun;
524 	fl_SectionLayout*		m_pSectionLayout;
525 
526 	UT_GenericVector<fl_TabStop*>	m_vecTabs;
527 	UT_sint32				m_iDefaultTabInterval;
528 	// read-only caches of the underlying properties
529 	UT_uint32				m_iOrphansProperty;
530 	UT_uint32				m_iWidowsProperty;
531 	UT_sint32				m_iTopMargin;
532 	UT_sint32				m_iBottomMargin;
533 	UT_sint32				m_iLeftMargin;
534 	UT_sint32				m_iRightMargin;
535 	UT_sint32				m_iTextIndent;
536 	fb_Alignment *			m_pAlignment;
537 	double					m_dLineSpacing;
538 	//bool					m_bExactSpacing;
539 	eSpacingPolicy			m_eSpacingPolicy;
540 	bool					m_bKeepTogether;
541 	bool					m_bKeepWithNext;
542 
543 	bool                    m_bStartList;
544 	bool                    m_bStopList;
545     bool                    m_bListLabelCreated;
546 #ifdef ENABLE_SPELL
547 	fl_SpellSquiggles *     m_pSpellSquiggles;
548 	fl_GrammarSquiggles *   m_pGrammarSquiggles;
549 	fl_BlockLayout          *m_nextToSpell;
550 	fl_BlockLayout          *m_prevToSpell;
551 #endif
552 	bool                    m_bListItem;
553 	const gchar *		m_szStyle;
554 	bool                    m_bIsCollapsed;
555 	bool                    m_bHasUpdatableField;
556 
557 	UT_BidiCharType 		m_iDomDirection;
558 	UT_BidiCharType 		m_iDirOverride;
559 
560 	bool                    m_bIsTOC;
561 	bool                    m_bStyleInTOC;
562 	UT_sint32               m_iTOCLevel;
563 
564 	bool                    m_bSameYAsPrevious;
565 	UT_sint32               m_iAccumulatedHeight;
566 	fp_VerticalContainer *  m_pVertContainer;
567 	UT_sint32               m_iLinePosInContainer;
568 	bool                    m_bForceSectionBreak;
569 	bool                    m_bPrevListLabel;
570     UT_sint32               m_iAdditionalMarginAfter;
571 	UT_RGBColor             m_ShadingForeColor;
572 	UT_RGBColor             m_ShadingBackColor;
573 	UT_sint32               m_iPattern;
574 
575 	PP_PropertyMap::Line    m_lineBottom;
576 	PP_PropertyMap::Line    m_lineLeft;
577 	PP_PropertyMap::Line    m_lineRight;
578 	PP_PropertyMap::Line    m_lineTop;
579 	bool                    m_bCanMergeBordersWithNext;
580 	bool                    m_bHasBorders;
581 };
582 
583 class ABI_EXPORT fl_TabStop
584 {
585 public:
586 
587 	fl_TabStop();
588 
getPosition()589 	UT_sint32		getPosition() const { return iPosition;}
setPosition(UT_sint32 value)590 	void			setPosition(UT_sint32 value) { iPosition = value;}
getType()591 	eTabType		getType() { return iType;}
setType(eTabType type)592 	void			setType(eTabType type) { iType = type;}
getLeader()593 	eTabLeader		getLeader() { return iLeader;};
setLeader(eTabLeader leader)594 	void			setLeader(eTabLeader leader) { iLeader = leader;}
getOffset()595 	UT_uint32		getOffset() { return iOffset;}
setOffset(UT_uint32 value)596 	void			setOffset(UT_uint32 value) { iOffset = value;}
597 
598 	fl_TabStop& operator = (const fl_TabStop &Other)
599 		{
600 			iPosition = Other.iPosition;
601 			iType = Other.iType;
602 			iLeader = Other.iLeader;
603 			iOffset = Other.iOffset;
604 			return *this;
605 		}
606 
607 protected:
608 
609 	UT_sint32		iPosition;
610 	eTabType		iType;
611 	eTabLeader		iLeader;
612 	UT_uint32		iOffset;
613 };
614 
615 #ifdef ENABLE_SPELL
616 class ABI_EXPORT fl_BlockSpellIterator
617 {
618 	friend class fl_BlockLayout;
619 
620 	UT_GrowBuf*     m_pgb;
621 
622 	const fl_BlockLayout* m_pBL;
623 
624 	UT_sint32       m_iWordOffset;
625 	UT_sint32       m_iWordLength;
626 
627 	UT_sint32       m_iStartIndex;
628 	UT_sint32       m_iPrevStartIndex;
629 	UT_UCSChar*     m_pText;
630 	UT_sint32       m_iLength;
631 
632 	UT_UCSChar*     m_pMutatedString;
633 
634 	UT_sint32       m_iSentenceStart;
635 	UT_sint32       m_iSentenceEnd;
636 
637     bool            _ignoreFirstWordCharacter(const UT_UCSChar c) const;
638     bool            _ignoreLastWordCharacter(const UT_UCSChar c) const;
639 
640 public:
641 	fl_BlockSpellIterator(const fl_BlockLayout* pBL, UT_sint32 iPos = 0);
642 	~fl_BlockSpellIterator();
643 
644 	bool            nextWordForSpellChecking(const UT_UCSChar*& pWord,
645 											 UT_sint32& iLength,
646 											 UT_sint32& iBlockPos,
647 											 UT_sint32& iPTLength);
648 	void              updateBlock(void);
649 	void              updateSentenceBoundaries(void);
650 
651 	UT_sint32         getBlockLength(void) const;
652 
653 	void              revertToPreviousWord(void);
654 
655     const UT_UCSChar* getCurrentWord(UT_sint32& iLength) const;
656     const UT_UCSChar* getPreWord(UT_sint32& iLength) const;
657     const UT_UCSChar* getPostWord(UT_sint32& iLength) const;
658 };
659 #endif
660 
661 #endif /* FL_BLOCKLAYOUT_H */
662