|
|
#include "dnutils.h"
#include "dninfo.h"
#include "iobj.h"
#include "lsdnode.h"
#include "lscbk.h"
#include "qheap.h"
#include "lstext.h"
#include "lsmem.h" /* memset() prototype */
#define FIsOutOfLine(plsc, plsdn) \
(((plsdn) == NULL) || \ (((plsc)->plslineCur->lslinfo.cpLim != 0) && ((plsc)->plslineCur->lslinfo.cpLim <= (plsdn)->cpFirst)))
/* F I N D L I S T D U P */ /*----------------------------------------------------------------------------
%%Function: FindListDup %%Contact: igorzv
Visit each node in the list of DNODES, until reaching cpLim Compute dup between start and end points. ----------------------------------------------------------------------------*/ void FindListDup(PLSDNODE plsdnFirst, LSCP cpLim, long *pdup) { PLSDNODE plsdn;
/* tolerate pldnFirst == NULL */
*pdup = 0; plsdn = plsdnFirst;
while (plsdn != NULL && plsdn->cpLimOriginal <= cpLim) { Assert(FIsLSDNODE(plsdn)); *pdup += DupFromDnode(plsdn); plsdn = plsdn->plsdnNext; }
}
/* F I N D L I S T F I N A L P E N M O V E M E N T*/ /*----------------------------------------------------------------------------
%%Function: FindListFinalPenMovement %%Contact: igorzv
Visit each node in the list of DNODES, until reaching cpLim Compute dur dvr dvp between start and end points. ----------------------------------------------------------------------------*/ void FindListFinalPenMovement(PLSDNODE plsdnFirst, PLSDNODE plsdnLast, long *pdur, long *pdvr, long *pdvp) { PLSDNODE plsdn;
/* tolerate pldnFirst == NULL */
*pdur = 0; *pdvr = 0; *pdvp = 0; plsdn = plsdnFirst;
while (plsdn != NULL && plsdn->plsdnPrev != plsdnLast) { Assert(FIsLSDNODE(plsdn)); *pdur += DurFromDnode(plsdn); *pdvr += DvrFromDnode(plsdn); *pdvp += DvpFromDnode(plsdn); plsdn = plsdn->plsdnNext; }
}
/* F I N D L I S T D I M S */ /*----------------------------------------------------------------------------
%%Function: FindListDims %%Contact: igorzv
Visit each node in the list of DNODES, until reaching plsdnLast. Compute OBJDIM which describes the list. ----------------------------------------------------------------------------*/ LSERR FindListDims(PLSDNODE plsdnFirst, PLSDNODE plsdnLast, OBJDIM* pobjdimList) { PLSDNODE plsdn; long urPen = 0; long urLim = 0; long vpPen = 0; long vrPen = 0; OBJDIM objdimFound; long dvpNode, dvrNode, durNode; long dvpAscentNext; long dvrAscentNext; long dvpDescentNext; long dvrDescentNext; long dvpLineHeight; long dvrLineHeight; POBJDIM pobjdimNode; BOOL fFindLast; OBJDIM* pobjdimLastSkiped = NULL;
/* N.B. Tolerate an empty input list! */ Assert(((plsdnFirst == NULL) && (plsdnLast == NULL)) || (FIsLSDNODE(plsdnFirst) && FIsLSDNODE(plsdnLast)));
/* the most efficient way to put zeroes in heights */ memset(&objdimFound, 0, sizeof objdimFound);
/* quick return if list is empty */ if (plsdnFirst == NULL) { *pobjdimList = objdimFound; /* in objdim will be zeroes */ return lserrNone; }
fFindLast = fFalse; for (plsdn = plsdnFirst; !fFindLast ; plsdn = plsdn->plsdnNext) { if (plsdn == NULL) /* we dont found plsdnLast, so return error */ return lserrInvalidParameter;
if (plsdn == plsdnLast) fFindLast = fTrue;
if (plsdn->klsdn == klsdnReal) { pobjdimNode = &plsdn->u.real.objdim; durNode = pobjdimNode->dur; Assert(durNode >= 0); dvrNode = 0; dvpNode = 0;
dvpAscentNext = pobjdimNode->heightsPres.dvAscent + vpPen; dvrAscentNext = pobjdimNode->heightsRef.dvAscent + vrPen; dvpDescentNext = pobjdimNode->heightsPres.dvDescent - vpPen; dvrDescentNext = pobjdimNode->heightsRef.dvDescent - vrPen; dvpLineHeight = pobjdimNode->heightsPres.dvMultiLineHeight; dvrLineHeight = pobjdimNode->heightsRef.dvMultiLineHeight;
if (dvrLineHeight != dvHeightIgnore) /* dvrLineHeight == dvHeightIgnore */ /* for us is sign that we */ { /* should not take into account for height calculation
this dnode */ if (objdimFound.heightsPres.dvAscent < dvpAscentNext) objdimFound.heightsPres.dvAscent = dvpAscentNext; if (objdimFound.heightsRef.dvAscent < dvrAscentNext) objdimFound.heightsRef.dvAscent = dvrAscentNext; if (objdimFound.heightsPres.dvDescent < dvpDescentNext) objdimFound.heightsPres.dvDescent = dvpDescentNext; if (objdimFound.heightsRef.dvDescent < dvrDescentNext) objdimFound.heightsRef.dvDescent = dvrDescentNext; if (objdimFound.heightsPres.dvMultiLineHeight < dvpLineHeight) objdimFound.heightsPres.dvMultiLineHeight = dvpLineHeight; if (objdimFound.heightsRef.dvMultiLineHeight < dvrLineHeight) objdimFound.heightsRef.dvMultiLineHeight = dvrLineHeight; }
else /* if final heights is 0, we will take ascent and desent from
this dnode */ { pobjdimLastSkiped = pobjdimNode; }
} else /* klsdnPenOrBorder*/ { dvpNode = plsdn->u.pen.dvp; durNode = plsdn->u.pen.dur; dvrNode = plsdn->u.pen.dvr; }
vpPen += dvpNode; urPen += durNode; vrPen += dvrNode; if (urLim < urPen) urLim = urPen; }
if (objdimFound.heightsRef.dvAscent == 0 && objdimFound.heightsRef.dvDescent == 0 && pobjdimLastSkiped != NULL) { objdimFound.heightsPres.dvAscent = pobjdimLastSkiped->heightsPres.dvAscent + vpPen; objdimFound.heightsRef.dvAscent = pobjdimLastSkiped->heightsRef.dvAscent + vrPen; objdimFound.heightsPres.dvDescent = pobjdimLastSkiped->heightsPres.dvDescent - vpPen; objdimFound.heightsRef.dvDescent = pobjdimLastSkiped->heightsRef.dvDescent - vrPen; objdimFound.heightsPres.dvMultiLineHeight = dvHeightIgnore; objdimFound.heightsRef.dvMultiLineHeight = dvHeightIgnore; }
*pobjdimList = objdimFound; pobjdimList->dur = urLim; return lserrNone; }
/* D E S T R O Y D N O D E L I S T */ /*----------------------------------------------------------------------------
%%Function: DestroyDnodeList %%Contact: igorzv
Parameters: plscbk - (IN) callbacks pols - (IN) pols to pass for callbacks plsiobjcontext - (IN) object handlers plsdn - (IN) first dnode in list fDontReleaseRuns - (IN) not to call release run ----------------------------------------------------------------------------*/ LSERR DestroyDnodeList(LSCBK* plscbk, POLS pols, PLSIOBJCONTEXT plsiobjcontext, PLSDNODE plsdn, BOOL fDontReleaseRuns) { LSERR lserr, lserrFinal = lserrNone; PLSDNODE plsdnNext; PDOBJ pdobj; PLSRUN plsrun; DWORD iobj;
if (plsdn == NULL) return lserrNone;
Assert(FIsLSDNODE(plsdn));
/* link with this dnode should be broken before */ Assert(plsdn->plsdnPrev == NULL || plsdn->plsdnPrev->plsdnNext != plsdn );
for (; plsdn != NULL; plsdn = plsdnNext) {
Assert(FIsLSDNODE(plsdn));
if (plsdn->klsdn == klsdnReal) { if (plsdn->u.real.pinfosubl != NULL) { if (plsdn->u.real.pinfosubl->rgpsubl != NULL) { plscbk->pfnDisposePtr(pols, plsdn->u.real.pinfosubl->rgpsubl); }
plscbk->pfnDisposePtr(pols, plsdn->u.real.pinfosubl); }
iobj = plsdn->u.real.lschp.idObj; plsrun = plsdn->u.real.plsrun; pdobj = plsdn->u.real.pdobj; } else { Assert (FIsDnodePen(plsdn) || FIsDnodeBorder(plsdn)); iobj = 0; plsrun = NULL; pdobj = NULL; }
if (plsrun != NULL && !fDontReleaseRuns) { lserr = plscbk->pfnReleaseRun(pols, plsrun); if (lserr != lserrNone && lserrFinal == lserrNone) lserrFinal = lserr; }
if (pdobj != NULL) { lserr = (PLsimFromLsc(plsiobjcontext, iobj))->pfnDestroyDObj (pdobj); if (lserr != lserrNone && lserrFinal == lserrNone) lserrFinal = lserr; }
plsdn->tag = tagInvalid; plsdnNext = plsdn->plsdnNext; }
return lserrFinal; }
/* ---------------------------------------------------------------------- */
/* D U R B O R D E R F R O M D N O D E I N S I D E*/ /*----------------------------------------------------------------------------
%%Function: DurBorderFromDnodeInside %%Contact: igorzv Parameters: plsdn - (IN) dnode inside borders ----------------------------------------------------------------------------*/ long DurBorderFromDnodeInside(PLSDNODE plsdn) /* IN: dnode inside borders */ { PLSDNODE plsdnBorder = plsdn; while (!FIsDnodeBorder(plsdnBorder)) { plsdnBorder = plsdnBorder->plsdnPrev; Assert(FIsLSDNODE(plsdnBorder)); } Assert(FIsDnodeBorder(plsdnBorder)); Assert(plsdnBorder->fOpenBorder); return plsdnBorder->u.pen.dur; }
/* ---------------------------------------------------------------------- */
/* F S P A C E S O N L Y*/ /*----------------------------------------------------------------------------
%%Function: FSpacesOnly %%Contact: igorzv Parameters: plsdn - (IN) dnode iObjText- (IN) id for text dnode ----------------------------------------------------------------------------*/ BOOL FSpacesOnly(PLSDNODE plsdn, DWORD iObjText) { DWORD dcpTrailing; long durTrailing;
if (FIsDnodeSplat(plsdn)) return fTrue; else if (FIsDnodeReal(plsdn) && (IdObjFromDnode(plsdn) == iObjText) && !(plsdn->fTab)) { GetTrailInfoText(PdobjFromDnode(plsdn), plsdn->dcp, &dcpTrailing, &durTrailing); if (dcpTrailing == plsdn->dcp) return fTrue; } return fFalse; }
|