nsIFrame* spanNextInFlow; spanFrame->GetNextInFlow(&spanNextInFlow); nsIFrame* spanPrevInFlow; spanFrame->GetPrevInFlow(&spanPrevInFlow);
nsIFrame* spanNextInFlow = spanFrame->GetNextInFlow(); nsIFrame* spanPrevInFlow = spanFrame->GetPrevInFlow();
nsLineLayout::VerticalAlignFrames(PerSpanData* psd){  // Get parent frame info  PerFrameData* spanFramePFD = psd->mFrame;  nsIFrame* spanFrame = spanFramePFD->mFrame;  // Get the parent frame's font for all of the frames in this span  nsStyleContext* styleContext = spanFrame->GetStyleContext();  nsIRenderingContext* rc = mBlockReflowState->rendContext;  SetFontFromStyle(mBlockReflowState->rendContext, styleContext);  nsCOMPtr<nsIFontMetrics> fm;  rc->GetFontMetrics(*getter_AddRefs(fm));  PRBool preMode = (mStyleText->mWhiteSpace == NS_STYLE_WHITESPACE_PRE) ||    (mStyleText->mWhiteSpace == NS_STYLE_WHITESPACE_MOZ_PRE_WRAP);  // See if the span is an empty continuation. It's an empty continuation iff:  // - it has a prev-in-flow  // - it has no next in flow  // - it's zero sized  nsIFrame* spanNextInFlow;  spanFrame->GetNextInFlow(&spanNextInFlow);  nsIFrame* spanPrevInFlow;  spanFrame->GetPrevInFlow(&spanPrevInFlow);  PRBool emptyContinuation = spanPrevInFlow && !spanNextInFlow &&    (0 == spanFramePFD->mBounds.width) && (0 == spanFramePFD->mBounds.height);#ifdef NOISY_VERTICAL_ALIGN  printf("[%sSpan]", (psd == mRootSpan)?"Root":"");  nsFrame::ListTag(stdout, spanFrame);  printf(": preMode=%s strictMode=%s w/h=%d,%d emptyContinuation=%s",         preMode ? "yes" : "no",         InStrictMode() ? "yes" : "no",         spanFramePFD->mBounds.width, spanFramePFD->mBounds.height,         emptyContinuation ? "yes" : "no");  if (psd != mRootSpan) {    printf(" bp=%d,%d,%d,%d margin=%d,%d,%d,%d",           spanFramePFD->mBorderPadding.top,           spanFramePFD->mBorderPadding.right,           spanFramePFD->mBorderPadding.bottom,           spanFramePFD->mBorderPadding.left,           spanFramePFD->mMargin.top,           spanFramePFD->mMargin.right,           spanFramePFD->mMargin.bottom,           spanFramePFD->mMargin.left);  }  printf("\n");#endif  // Compute the span's mZeroEffectiveSpanBox flag. What we are trying  // to determine is how we should treat the span: should it act  // "normally" according to css2 or should it effectively  // "disappear".  //  // In general, if the document being processed is in full standards  // mode then it should act normally (with one exception). The  // exception case is when a span is continued and yet the span is  // empty (e.g. compressed whitespace). For this kind of span we treat  // it as if it were not there so that it doesn't impact the  // line-height.  //  // In almost standards mode or quirks mode, we should sometimes make  // it disappear. The cases that matter are those where the span  // contains no real text elements that would provide an ascent and  // descent and height. However, if css style elements have been  // applied to the span (border/padding/margin) so that it's clear the  // document author is intending css2 behavior then we act as if strict  // mode is set.  //  // This code works correctly for preMode, because a blank line  // in PRE mode is encoded as a text node with a LF in it, since  // text nodes with only whitespace are considered in preMode.  //  // Much of this logic is shared with the various implementations of  // nsIFrame::IsEmpty since they need to duplicate the way it makes  // some lines empty.  However, nsIFrame::IsEmpty can't be reused here  // since this code sets zeroEffectiveSpanBox even when there are  // non-empty children.  PRBool zeroEffectiveSpanBox = PR_FALSE;  // XXXldb If we really have empty continuations, then all these other  // checks don't make sense for them.  if ((emptyContinuation || mCompatMode != eCompatibility_FullStandards) &&      ((psd == mRootSpan) ||       ((0 == spanFramePFD->mBorderPadding.top) &&        (0 == spanFramePFD->mBorderPadding.right) &&        (0 == spanFramePFD->mBorderPadding.bottom) &&        (0 == spanFramePFD->mBorderPadding.left) &&        (0 == spanFramePFD->mMargin.top) &&        (0 == spanFramePFD->mMargin.right) &&        (0 == spanFramePFD->mMargin.bottom) &&        (0 == spanFramePFD->mMargin.left)))) {    // This code handles an issue with compatability with non-css    // conformant browsers. In particular, there are some cases    // where the font-size and line-height for a span must be    // ignored and instead the span must *act* as if it were zero    // sized. In general, if the span contains any non-compressed    // text then we don't use this logic.    // However, this is not propagated outwards, since (in compatibility    // mode) we don't want big line heights for things like    // <p><font size="-1">Text</font></p>    // We shouldn't include any whitespace that collapses, unless we're    // preformatted (in which case it shouldn't, but the width=0 test is    // perhaps incorrect).  This includes whitespace at the beginning of    // a line and whitespace preceded (?) by other whitespace.    // See bug 134580 and bug 155333.    zeroEffectiveSpanBox = PR_TRUE;    for (PerFrameData* pfd = psd->mFirstFrame; pfd; pfd = pfd->mNext) {      if (pfd->GetFlag(PFD_ISTEXTFRAME) &&          (pfd->GetFlag(PFD_ISNONWHITESPACETEXTFRAME) || preMode ||           pfd->mBounds.width != 0)) {        zeroEffectiveSpanBox = PR_FALSE;        break;      }    }  }  psd->mZeroEffectiveSpanBox = zeroEffectiveSpanBox;  // Setup baselineY, minY, and maxY  nscoord baselineY, minY, maxY;  if (psd == mRootSpan) {    // Use a zero baselineY since we don't yet know where the baseline    // will be (until we know how tall the line is; then we will    // know). In addition, use extreme values for the minY and maxY    // values so that only the child frames will impact their values    // (since these are children of the block, there is no span box to    // provide initial values).    baselineY = 0;    minY = VERTICAL_ALIGN_FRAMES_NO_MINIMUM;    maxY = VERTICAL_ALIGN_FRAMES_NO_MAXIMUM;#ifdef NOISY_VERTICAL_ALIGN    printf("[RootSpan]");    nsFrame::ListTag(stdout, spanFrame);    printf(": pass1 valign frames: topEdge=%d minLineHeight=%d zeroEffectiveSpanBox=%s\n",           mTopEdge, mMinLineHeight,           zeroEffectiveSpanBox ? "yes" : "no");#endif  }  else {    // Compute the logical height for this span. The logical height    // is based on the line-height value, not the font-size. Also    // compute the top leading.    nscoord logicalHeight =      nsHTMLReflowState::CalcLineHeight(mPresContext, rc, spanFrame);    nscoord contentHeight = spanFramePFD->mBounds.height -      spanFramePFD->mBorderPadding.top - spanFramePFD->mBorderPadding.bottom;    nscoord leading = logicalHeight - contentHeight;    psd->mTopLeading = leading / 2;    psd->mBottomLeading = leading - psd->mTopLeading;    psd->mLogicalHeight = logicalHeight;    if (zeroEffectiveSpanBox) {      // When the span-box is to be ignored, zero out the initial      // values so that the span doesn't impact the final line      // height. The contents of the span can impact the final line      // height.      // Note that things are readjusted for this span after its children      // are reflowed      minY = VERTICAL_ALIGN_FRAMES_NO_MINIMUM;      maxY = VERTICAL_ALIGN_FRAMES_NO_MAXIMUM;    }    else {      // The initial values for the min and max Y values are in the spans      // coordinate space, and cover the logical height of the span. If      // there are child frames in this span that stick out of this area      // then the minY and maxY are updated by the amount of logical      // height that is outside this range.      minY = spanFramePFD->mBorderPadding.top - psd->mTopLeading;      maxY = minY + psd->mLogicalHeight;    }    // This is the distance from the top edge of the parents visual    // box to the baseline. The span already computed this for us,    // so just use it.    baselineY = spanFramePFD->mAscent;#ifdef NOISY_VERTICAL_ALIGN    printf("[%sSpan]", (psd == mRootSpan)?"Root":"");    nsFrame::ListTag(stdout, spanFrame);    printf(": baseLine=%d logicalHeight=%d topLeading=%d h=%d bp=%d,%d zeroEffectiveSpanBox=%s\n",           baselineY, psd->mLogicalHeight, psd->mTopLeading,           spanFramePFD->mBounds.height,           spanFramePFD->mBorderPadding.top, spanFramePFD->mBorderPadding.bottom,           zeroEffectiveSpanBox ? "yes" : "no");#endif  }  nscoord maxTopBoxHeight = 0;  nscoord maxBottomBoxHeight = 0;  PerFrameData* pfd = psd->mFirstFrame;  while (nsnull != pfd) {    nsIFrame* frame = pfd->mFrame;    // sanity check (see bug 105168, non-reproducable crashes from null frame)    NS_ASSERTION(frame, "null frame in PerFrameData - something is very very bad");    if (!frame) {      return;    }    // Compute the logical height of the frame    nscoord logicalHeight;    nscoord topLeading;    PerSpanData* frameSpan = pfd->mSpan;    if (frameSpan) {      // For span frames the logical-height and top-leading was      // pre-computed when the span was reflowed.      logicalHeight = frameSpan->mLogicalHeight;      topLeading = frameSpan->mTopLeading;    }    else {      // For other elements the logical height is the same as the      // frames height plus its margins.      logicalHeight = pfd->mBounds.height + pfd->mMargin.top +        pfd->mMargin.bottom;      topLeading = 0;    }    // Get vertical-align property    const nsStyleTextReset* textStyle = frame->GetStyleTextReset();    nsStyleUnit verticalAlignUnit = textStyle->mVerticalAlign.GetUnit();#ifdef NOISY_VERTICAL_ALIGN    printf("  [frame]");    nsFrame::ListTag(stdout, frame);    printf(": verticalAlignUnit=%d (enum == %d)\n",           verticalAlignUnit,           ((eStyleUnit_Enumerated == verticalAlignUnit)            ? textStyle->mVerticalAlign.GetIntValue()            : -1));#endif    PRUint8 verticalAlignEnum;    nscoord parentAscent, parentDescent, parentXHeight;    nscoord parentSuperscript, parentSubscript;    nscoord coordOffset, percentOffset, elementLineHeight;    nscoord revisedBaselineY;    switch (verticalAlignUnit) {      case eStyleUnit_Enumerated:      default:        if (eStyleUnit_Enumerated == verticalAlignUnit) {          verticalAlignEnum = textStyle->mVerticalAlign.GetIntValue();        }        else {          verticalAlignEnum = NS_STYLE_VERTICAL_ALIGN_BASELINE;        }        switch (verticalAlignEnum) {          default:          case NS_STYLE_VERTICAL_ALIGN_BASELINE:            // The elements baseline is aligned with the baseline of            // the parent.            if (frameSpan) {              // XXX explain              pfd->mBounds.y = baselineY - pfd->mAscent;            }            else {              // For non-span elements the borders, padding and              // margins are significant. Use the visual box height              // and the bottom margin as the distance off of the              // baseline.              pfd->mBounds.y = baselineY - pfd->mAscent - pfd->mMargin.bottom;            }            pfd->mVerticalAlign = VALIGN_OTHER;            break;          case NS_STYLE_VERTICAL_ALIGN_SUB:            // Lower the baseline of the box to the subscript offset            // of the parent's box. This is identical to the baseline            // alignment except for the addition of the subscript            // offset to the baseline Y.            fm->GetSubscriptOffset(parentSubscript);            revisedBaselineY = baselineY + parentSubscript;            if (frameSpan) {              pfd->mBounds.y = revisedBaselineY - pfd->mAscent;            }            else {              pfd->mBounds.y = revisedBaselineY - pfd->mAscent -                pfd->mMargin.bottom;            }            pfd->mVerticalAlign = VALIGN_OTHER;            break;          case NS_STYLE_VERTICAL_ALIGN_SUPER:            // Raise the baseline of the box to the superscript offset            // of the parent's box. This is identical to the baseline            // alignment except for the subtraction of the superscript            // offset to the baseline Y.            fm->GetSuperscriptOffset(parentSuperscript);            revisedBaselineY = baselineY - parentSuperscript;            if (frameSpan) {              pfd->mBounds.y = revisedBaselineY - pfd->mAscent;            }            else {              pfd->mBounds.y = revisedBaselineY - pfd->mAscent -                pfd->mMargin.bottom;            }            pfd->mVerticalAlign = VALIGN_OTHER;            break;          case NS_STYLE_VERTICAL_ALIGN_TOP:            pfd->mVerticalAlign = VALIGN_TOP;            if (logicalHeight > maxTopBoxHeight) {              maxTopBoxHeight = logicalHeight;            }            break;          case NS_STYLE_VERTICAL_ALIGN_BOTTOM:            pfd->mVerticalAlign = VALIGN_BOTTOM;            if (logicalHeight > maxBottomBoxHeight) {              maxBottomBoxHeight = logicalHeight;            }            break;          case NS_STYLE_VERTICAL_ALIGN_MIDDLE:            // Align the midpoint of the frame with 1/2 the parents            // x-height above the baseline.            fm->GetXHeight(parentXHeight);            if (frameSpan) {              pfd->mBounds.y = baselineY -                (parentXHeight + pfd->mBounds.height)/2;            }            else {              pfd->mBounds.y = baselineY - (parentXHeight + logicalHeight)/2 +                pfd->mMargin.top;            }            pfd->mVerticalAlign = VALIGN_OTHER;            break;          case NS_STYLE_VERTICAL_ALIGN_TEXT_TOP:            // The top of the logical box is aligned with the top of            // the parent elements text.            fm->GetMaxAscent(parentAscent);            if (frameSpan) {              pfd->mBounds.y = baselineY - parentAscent -                pfd->mBorderPadding.top + frameSpan->mTopLeading;            }            else {              pfd->mBounds.y = baselineY - parentAscent + pfd->mMargin.top;            }            pfd->mVerticalAlign = VALIGN_OTHER;            break;          case NS_STYLE_VERTICAL_ALIGN_TEXT_BOTTOM:            // The bottom of the logical box is aligned with the            // bottom of the parent elements text.            fm->GetMaxDescent(parentDescent);            if (frameSpan) {              pfd->mBounds.y = baselineY + parentDescent -                pfd->mBounds.height + pfd->mBorderPadding.bottom -                frameSpan->mBottomLeading;            }            else {              pfd->mBounds.y = baselineY + parentDescent -                pfd->mBounds.height - pfd->mMargin.bottom;            }            pfd->mVerticalAlign = VALIGN_OTHER;            break;        }        break;      case eStyleUnit_Coord:        // According to the CSS2 spec (10.8.1), a positive value        // "raises" the box by the given distance while a negative value        // "lowers" the box by the given distance (with zero being the        // baseline). Since Y coordinates increase towards the bottom of        // the screen we reverse the sign.        coordOffset = textStyle->mVerticalAlign.GetCoordValue();        revisedBaselineY = baselineY - coordOffset;        if (frameSpan) {          pfd->mBounds.y = revisedBaselineY - pfd->mAscent;        }        else {          pfd->mBounds.y = revisedBaselineY - pfd->mAscent -            pfd->mMargin.bottom;        }        pfd->mVerticalAlign = VALIGN_OTHER;        break;      case eStyleUnit_Percent:        // Similar to a length value (eStyleUnit_Coord) except that the        // percentage is a function of the elements line-height value.        elementLineHeight =          nsHTMLReflowState::CalcLineHeight(mPresContext, rc, frame);        percentOffset = nscoord(          textStyle->mVerticalAlign.GetPercentValue() * elementLineHeight          );        revisedBaselineY = baselineY - percentOffset;        if (frameSpan) {          pfd->mBounds.y = revisedBaselineY - pfd->mAscent;        }        else {          pfd->mBounds.y = revisedBaselineY - pfd->mAscent -            pfd->mMargin.bottom;        }        pfd->mVerticalAlign = VALIGN_OTHER;        break;    }    // Update minY/maxY for frames that we just placed. Do not factor    // text into the equation.    if (pfd->mVerticalAlign == VALIGN_OTHER) {      // Text frames do not contribute to the min/max Y values for the      // line (instead their parent frame's font-size contributes).      // XXXrbs -- relax this restriction because it causes text frames      //           to jam together when 'font-size-adjust' is enabled      //           and layout is using dynamic font heights (bug 20394)      //        -- Note #1: With this code enabled and with the fact that we are not      //           using Em[Ascent|Descent] as nsDimensions for text metrics in      //           GFX mean that the discussion in bug 13072 cannot hold.      //        -- Note #2: We still don't want empty-text frames to interfere.      //           For example in quirks mode, avoiding empty text frames prevents      //           "tall" lines around elements like <hr> since the rules of <hr>      //           in quirks.css have pseudo text contents with LF in them.#if 0      if (!pfd->GetFlag(PFD_ISTEXTFRAME)) {#else      // Only consider non empty text frames when line-height=normal      PRBool canUpdate = !pfd->GetFlag(PFD_ISTEXTFRAME);      if (!canUpdate && pfd->GetFlag(PFD_ISNONWHITESPACETEXTFRAME)) {        nsStyleUnit lhUnit = frame->GetStyleText()->mLineHeight.GetUnit();        canUpdate = lhUnit == eStyleUnit_Normal || lhUnit == eStyleUnit_Null;      }      if (canUpdate) {#endif        nscoord yTop, yBottom;        if (frameSpan) {          // For spans that were are now placing, use their position          // plus their already computed min-Y and max-Y values for          // computing yTop and yBottom.          yTop = pfd->mBounds.y + frameSpan->mMinY;          yBottom = pfd->mBounds.y + frameSpan->mMaxY;        }        else {          yTop = pfd->mBounds.y - pfd->mMargin.top;          yBottom = yTop + logicalHeight;        }        if (!preMode &&            GetCompatMode() != eCompatibility_FullStandards &&            !logicalHeight) {          // Check if it's a BR frame that is not alone on its line (it          // is given a height of zero to indicate this), and if so reset          // yTop and yBottom so that BR frames don't influence the line.          if (nsLayoutAtoms::brFrame == frame->GetType()) {            yTop = VERTICAL_ALIGN_FRAMES_NO_MINIMUM;            yBottom = VERTICAL_ALIGN_FRAMES_NO_MAXIMUM;          }        }        if (yTop < minY) minY = yTop;        if (yBottom > maxY) maxY = yBottom;#ifdef NOISY_VERTICAL_ALIGN        printf("     [frame]raw: a=%d d=%d h=%d bp=%d,%d logical: h=%d leading=%d y=%d minY=%d maxY=%d\n",               pfd->mAscent, pfd->mDescent, pfd->mBounds.height,               pfd->mBorderPadding.top, pfd->mBorderPadding.bottom,               logicalHeight,               pfd->mSpan ? topLeading : 0,               pfd->mBounds.y, minY, maxY);#endif      }      if (psd != mRootSpan) {        frame->SetRect(pfd->mBounds);      }    }    pfd = pfd->mNext;  }  // Factor in the minimum line-height when handling the root-span for  // the block.  if (psd == mRootSpan) {    // We should factor in the block element's minimum line-height (as    // defined in section 10.8.1 of the css2 spec) assuming that    // mZeroEffectiveSpanBox is not set on the root span.  This only happens    // in some cases in quirks mode:    //  (1) if the root span contains non-whitespace text directly (this    //      is handled by mZeroEffectiveSpanBox    //  (2) if this is the first line of an LI element (whether or not    //      there is a bullet (NN4/IE5 quirk)    //  (3) if this is the last line of an LI, DT, or DD element    //      (The last line before a block also counts, but not before a    //      BR) (NN4/IE5 quirk)    PRBool applyMinLH = !(psd->mZeroEffectiveSpanBox); // (1) above    PRBool isFirstLine = !mLineNumber; // if the line number is 0    PRBool isLastLine = (!mLineBox->IsLineWrapped() && !GetFlag(LL_LINEENDSINBR));    PRBool foundLI = PR_FALSE;  // hack to fix bug 50480.    //XXX: rather than remembering if we've found an LI, we really should be checking    //     for the existence of a bullet frame.  Likewise, the code below should not    //     be checking for any particular content tag type, but rather should    //     be checking for the existence of a bullet frame to determine if it's a list element or not.    if (!applyMinLH && (isFirstLine || isLastLine)) {      nsIContent* blockContent = mRootSpan->mFrame->mFrame->GetContent();      if (blockContent) {        nsIAtom *blockTagAtom = blockContent->Tag();        // (2) above, if the first line of LI        if (isFirstLine && blockTagAtom == nsHTMLAtoms::li) {          // if the line is empty, then don't force the min height          // (see bug 75963)          if (!IsZeroHeight()) {            applyMinLH = PR_TRUE;            foundLI = PR_TRUE;          }        }        // (3) above, if the last line of LI, DT, or DD        else if (!applyMinLH && isLastLine &&                 ((blockTagAtom == nsHTMLAtoms::li) ||                  (blockTagAtom == nsHTMLAtoms::dt) ||                  (blockTagAtom == nsHTMLAtoms::dd))) {          applyMinLH = PR_TRUE;        }      }    }    if (applyMinLH) {      if ((psd->mX != psd->mLeftEdge) || preMode || foundLI) {#ifdef NOISY_VERTICAL_ALIGN        printf("  [span]==> adjusting min/maxY: currentValues: %d,%d", minY, maxY);#endif        nscoord minimumLineHeight = mMinLineHeight;        nscoord fontAscent, fontHeight;        fm->GetMaxAscent(fontAscent);        if (nsHTMLReflowState::UseComputedHeight()) {          fontHeight = spanFrame->GetStyleFont()->mFont.size;        }        else         {          fm->GetHeight(fontHeight);        }        nscoord leading = minimumLineHeight - fontHeight;        nscoord yTop = -fontAscent - leading/2;        nscoord yBottom = yTop + minimumLineHeight;        if (yTop < minY) minY = yTop;        if (yBottom > maxY) maxY = yBottom;#ifdef NOISY_VERTICAL_ALIGN        printf(" new values: %d,%d\n", minY, maxY);#endif      }      else {        // XXX issues:        // [1] BR's on empty lines stop working        // [2] May not honor css2's notion of handling empty elements        // [3] blank lines in a pre-section ("\n") (handled with preMode)        // XXX Are there other problems with this?#ifdef NOISY_VERTICAL_ALIGN        printf("  [span]==> zapping min/maxY: currentValues: %d,%d newValues: 0,0\n",               minY, maxY);#endif        minY = maxY = 0;      }    }  }  if ((minY == VERTICAL_ALIGN_FRAMES_NO_MINIMUM) ||      (maxY == VERTICAL_ALIGN_FRAMES_NO_MINIMUM)) {    minY = maxY = baselineY;  }  if ((psd != mRootSpan) && (psd->mZeroEffectiveSpanBox)) {#ifdef NOISY_VERTICAL_ALIGN    printf("   [span]adjusting for zeroEffectiveSpanBox\n");    printf("     Original: minY=%d, maxY=%d, height=%d, ascent=%d, descent=%d, logicalHeight=%d, topLeading=%d, bottomLeading=%d\n",           minY, maxY, spanFramePFD->mBounds.height,           spanFramePFD->mAscent, spanFramePFD->mDescent,           psd->mLogicalHeight, psd->mTopLeading, psd->mBottomLeading);#endif    nscoord goodMinY = spanFramePFD->mBorderPadding.top - psd->mTopLeading;    nscoord goodMaxY = goodMinY + psd->mLogicalHeight;    if (minY > goodMinY) {      nscoord adjust = minY - goodMinY; // positive      // shrink the logical extents      psd->mLogicalHeight -= adjust;      psd->mTopLeading -= adjust;    }    if (maxY < goodMaxY) {      nscoord adjust = goodMaxY - maxY;      psd->mLogicalHeight -= adjust;      psd->mBottomLeading -= adjust;    }    if (minY > 0) {      // shrink the content by moving its top down.  This is tricky, since      // the top is the 0 for many coordinates, so what we do is      // move everything else up.      spanFramePFD->mAscent -= minY; // move the baseline up      spanFramePFD->mBounds.height -= minY; // move the bottom up      psd->mTopLeading += minY;      pfd = psd->mFirstFrame;      while (nsnull != pfd) {        pfd->mBounds.y -= minY; // move all the children back up        pfd->mFrame->SetRect(pfd->mBounds);        pfd = pfd->mNext;      }      maxY -= minY; // since minY is in the frame's own coordinate system      minY = 0;    }    if (maxY < spanFramePFD->mBounds.height) {      nscoord adjust = spanFramePFD->mBounds.height - maxY;      spanFramePFD->mBounds.height -= adjust; // move the bottom up      spanFramePFD->mDescent -= adjust;      psd->mBottomLeading += adjust;    }#ifdef NOISY_VERTICAL_ALIGN    printf("     New: minY=%d, maxY=%d, height=%d, ascent=%d, descent=%d, logicalHeight=%d, topLeading=%d, bottomLeading=%d\n",           minY, maxY, spanFramePFD->mBounds.height,           spanFramePFD->mAscent, spanFramePFD->mDescent,           psd->mLogicalHeight, psd->mTopLeading, psd->mBottomLeading);#endif  }  psd->mMinY = minY;  psd->mMaxY = maxY;#ifdef NOISY_VERTICAL_ALIGN  printf("  [span]==> minY=%d maxY=%d delta=%d maxTopBoxHeight=%d maxBottomBoxHeight=%d\n",         minY, maxY, maxY - minY, maxTopBoxHeight, maxBottomBoxHeight);#endif  if (maxTopBoxHeight > mMaxTopBoxHeight) {    mMaxTopBoxHeight = maxTopBoxHeight;  }  if (maxBottomBoxHeight > mMaxBottomBoxHeight) {    mMaxBottomBoxHeight = maxBottomBoxHeight;  }}