Program: 70618
Project: 70618
Buggy source:
/** 
 * Goals: 1. Adjust the two ends of the vertical axis to fit start/end labels 2. Compute the horizontal co-ordinate for the axis
 * @param dBlockX
 * @param dBlockWidth
 * @param aax
 * @return
 */
protected final double adjustHorizontal(double dBlockX,double dBlockWidth,AllAxes aax) throws ChartException, IllegalArgumentException {
  final OneAxis axPH=aax.areAxesSwapped() ? aax.getPrimaryOrthogonal() : aax.getPrimaryBase();
  final OneAxis axPV=aax.areAxesSwapped() ? aax.getPrimaryBase() : aax.getPrimaryOrthogonal();
  final AutoScale scX=axPH.getScale();
  final AutoScale scY=axPV.getScale();
  final int iXLabelLocation=axPH.getLabelPosition();
  final int iYLabelLocation=axPV.getLabelPosition();
  final int iYTitleLocation=axPV.getTitlePosition();
  final Label laXAxisLabels=axPH.getLabel();
  final Label laYAxisLabels=axPV.getLabel();
  final Label laYAxisTitle=axPV.getTitle();
  final int iYTickStyle=axPV.getCombinedTickStyle();
  final IntersectionValue iv=axPV.getIntersectionValue();
  final boolean bTicksLeft=(iYTickStyle & TICK_LEFT) == TICK_LEFT;
  final boolean bTicksRight=(iYTickStyle & TICK_RIGHT) == TICK_RIGHT;
  final double dAppliedYAxisPlotSpacing=(iv.iType == IConstants.MAX || iv.iType == IConstants.MIN) && !aax.getPrimaryOrthogonal().getModelAxis().isLabelWithinAxes() ? dYAxisPlotSpacing : 0;
  double dStart=scY.getStart(), dEnd=scY.getEnd();
  scY.computeTicks(ids,laYAxisLabels,iYLabelLocation,VERTICAL,dStart,dEnd,true,aax);
  if (!scY.isStepFixed()) {
    final Object[] oaMinMax=scY.getMinMax();
    while (!scY.checkFit(ids,laYAxisLabels,iYLabelLocation)) {
      if (!scY.zoomOut()) {
        break;
      }
      scY.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
      int tickCount=scY.computeTicks(ids,laYAxisLabels,iYLabelLocation,VERTICAL,dStart,dEnd,true,aax);
      if (scY.getUnit() != null && asInteger(scY.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
        break;
      }
    }
  }
  double dYAxisLabelsThickness=scY.computeAxisLabelThickness(ids,axPV.getLabel(),VERTICAL);
  double[] dDecorationThickness={0,0};
  Series[] sea=cwa.getSeries(IConstants.ORTHOGONAL);
  Map<Series,LegendItemRenderingHints> seriesRenderingHints=rtc.getSeriesRenderers();
  for (int i=0; i < sea.length; i++) {
    LegendItemRenderingHints lirh=seriesRenderingHints.get(sea[i]);
    if (lirh != null && lirh.getRenderer() instanceof AxesRenderer) {
      IAxesDecorator iad=((AxesRenderer)lirh.getRenderer()).getAxesDecorator(axPV);
      if (iad != null) {
        double[] thickness=iad.computeDecorationThickness(ids,axPV);
        if (thickness[0] > dDecorationThickness[0]) {
          dDecorationThickness[0]=thickness[0];
        }
        if (thickness[1] > dDecorationThickness[1]) {
          dDecorationThickness[1]=thickness[1];
        }
      }
    }
  }
  double dYAxisTitleThickness=0;
  if (laYAxisTitle.isVisible()) {
    final String sPreviousValue=laYAxisTitle.getCaption().getValue();
    laYAxisTitle.getCaption().setValue(rtc.externalizedMessage(sPreviousValue));
    double maxWidth=AXIS_TITLE_PERCENT * boPlot.getWidth();
    double maxHeight=boPlot.getHeight();
    LabelLimiter lblLimit=new LabelLimiter(maxWidth,maxHeight,0);
    lblLimit.computeWrapping(ids,laYAxisTitle);
    lblLimit=lblLimit.limitLabelSize(ids,laYAxisTitle,EnumSet.of(LabelLimiter.Option.FIX_HEIGHT));
    putLabelLimiter(axPV.getModelAxis().getTitle(),lblLimit);
    dYAxisTitleThickness=lblLimit.getMaxWidth();
    laYAxisTitle.getCaption().setValue(sPreviousValue);
  }
  double dX=getLocation(scX,iv), dX1=dX, dX2=dX;
  double dWTotal=Math.abs(scX.getStart() - scX.getEnd());
  if (axPV.getModelAxis().isSetLabelSpan()) {
    double dFixedLabelThickness=axPV.getModelAxis().getLabelSpan();
    if (dFixedLabelThickness < dWTotal - 2 * getTickSize()) {
      if (dYAxisLabelsThickness + dYAxisTitleThickness > dFixedLabelThickness) {
        axPV.setShowLabels(false);
      }
      if (dYAxisTitleThickness > dFixedLabelThickness) {
        laYAxisTitle.setVisible(false);
        dYAxisTitleThickness=0;
      }
      dYAxisLabelsThickness=dFixedLabelThickness;
    }
  }
  if (iv.iType == IConstants.MIN) {
    if (scX.getDirection() == BACKWARD) {
      dX=getLocation(scX,IntersectionValue.MAX_VALUE);
    }
    dX-=dAppliedYAxisPlotSpacing;
    dX1=dX;
    dX2=dX;
    double dTickSize=getTickSize();
    if (bTicksLeft && dTickSize <= dWTotal) {
      dX1-=getTickSize();
      dWTotal-=dTickSize;
    }
 else {
      dTickSize=0;
    }
    double dW1=0, dW2=0;
    if (iYLabelLocation == LEFT) {
      dW1=Math.max(dYAxisLabelsThickness,dDecorationThickness[0]);
      dW2=Math.max(bTicksRight ? getTickSize() : 0,dAppliedYAxisPlotSpacing);
    }
 else     if (iYLabelLocation == RIGHT) {
      dW1=dDecorationThickness[0];
      dW2=Math.max((bTicksRight ? getTickSize() : 0) + dYAxisLabelsThickness,dAppliedYAxisPlotSpacing);
    }
    if (dW1 + dW2 <= dWTotal) {
      dX1-=dW1;
      dX2+=dW2;
      dWTotal-=(dW1 + dW2);
    }
 else {
      axPV.setShowLabels(false);
    }
    if (iYTitleLocation == LEFT) {
      dX1-=dYAxisTitleThickness;
    }
 else     if (iYTitleLocation == RIGHT) {
      dX2+=dYAxisTitleThickness;
    }
    if (dX1 < dBlockX) {
      final double dDelta=(dBlockX - dX1);
      dX1=dBlockX;
      dX+=dDelta;
      dX2+=dDelta;
    }
    final double dDeltaX1=dX - dX1;
    final double dDeltaX2=dX2 - dX;
    if (iYLabelLocation == RIGHT) {
      dX2=(dX + dAppliedYAxisPlotSpacing);
    }
    dYAxisLabelsThickness=dX2 - dX1;
    scX.computeAxisStartEndShifts(ids,laXAxisLabels,HORIZONTAL,iXLabelLocation,aax);
    boolean startEndChanged=false;
    if (scX.getDirection() == BACKWARD) {
      if (dYAxisLabelsThickness > scX.getEndShift()) {
        dEnd=dX2;
        startEndChanged=true;
      }
 else {
        dEnd=scX.getEnd();
      }
      dStart=scX.getStart();
    }
 else {
      if (dYAxisLabelsThickness > scX.getStartShift()) {
        dStart=dX2;
        startEndChanged=true;
      }
 else {
        dStart=scX.getStart();
      }
      dEnd=scX.getEnd();
    }
    scX.resetShifts();
    scX.setEndPoints(dStart,dEnd);
    if (scX.getDirection() == BACKWARD) {
      scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,!startEndChanged,aax);
    }
 else {
      scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,!startEndChanged,true,aax);
    }
    if (!scX.isStepFixed()) {
      final Object[] oaMinMax=scX.getMinMax();
      while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
        if (!scX.zoomOut()) {
          break;
        }
        scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
        int tickCount;
        if (scX.getDirection() == BACKWARD) {
          tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,!startEndChanged,aax);
        }
 else {
          tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,!startEndChanged,true,aax);
        }
        if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
          break;
        }
      }
    }
    if (scX.getDirection() == BACKWARD) {
      if (dYAxisLabelsThickness < scX.getEndShift()) {
        dX=scX.getEnd() - (dX2 - dX);
      }
    }
 else {
      if (dYAxisLabelsThickness < scX.getStartShift()) {
        dX=scX.getStart() - (dX2 - dX);
      }
    }
    dX-=insCA.getLeft();
    dX2=dX + dDeltaX2;
    dX1=dX - dDeltaX1;
    axPV.setTitleCoordinate((iYTitleLocation == LEFT) ? dX1 - 1 : dX2 + 1 - dYAxisTitleThickness);
  }
 else   if (iv.iType == IConstants.MAX) {
    if (scX.getDirection() == BACKWARD) {
      dX=getLocation(scX,IntersectionValue.MIN_VALUE);
    }
    dX+=dAppliedYAxisPlotSpacing;
    dWTotal-=dAppliedYAxisPlotSpacing;
    dX1=dX;
    dX2=dX;
    if (bTicksRight && getTickSize() <= dWTotal) {
      dX2+=getTickSize();
      dWTotal-=getTickSize();
    }
 else {
    }
    double dW1=0, dW2=0;
    if (iYLabelLocation == RIGHT) {
      dW1=Math.max((bTicksLeft ? getTickSize() : 0) + dDecorationThickness[0],dAppliedYAxisPlotSpacing);
      dW2=Math.max(dYAxisLabelsThickness,dDecorationThickness[1]);
    }
 else     if (iYLabelLocation == LEFT) {
      dW1=Math.max((bTicksLeft ? getTickSize() : 0) + Math.max(dYAxisLabelsThickness,dDecorationThickness[0]),dAppliedYAxisPlotSpacing);
      dW2=dDecorationThickness[1];
    }
    if (dW1 + dW2 <= dWTotal) {
      dX1-=dW1;
      dX2+=dW2;
      dWTotal-=(dW1 + dW2);
    }
 else {
      axPV.setShowLabels(false);
    }
    if (iYTitleLocation == RIGHT) {
      dX2+=dYAxisTitleThickness;
    }
 else     if (iYTitleLocation == LEFT) {
      dX1-=dYAxisTitleThickness;
    }
    if (dX2 > dBlockX + dBlockWidth) {
      final double dDelta=dX2 - (dBlockX + dBlockWidth);
      dX2=dBlockX + dBlockWidth;
      dX-=dDelta;
      dX1-=dDelta;
    }
    final double dDeltaX1=dX - dX1;
    final double dDeltaX2=dX2 - dX;
    if (iYLabelLocation == LEFT) {
      dX1=(dX - dAppliedYAxisPlotSpacing);
    }
    dYAxisLabelsThickness=dX2 - dX1;
    scX.computeAxisStartEndShifts(ids,laXAxisLabels,HORIZONTAL,iXLabelLocation,aax);
    boolean startEndChanged=false;
    if (scX.getDirection() == BACKWARD) {
      if (dYAxisLabelsThickness > scX.getStartShift()) {
        dStart=dX1;
        startEndChanged=true;
      }
 else {
        dStart=scX.getStart();
      }
      dEnd=scX.getEnd();
    }
 else {
      if (dYAxisLabelsThickness > scX.getEndShift()) {
        dEnd=dX1;
        startEndChanged=true;
      }
 else {
        dEnd=scX.getEnd();
      }
      dStart=scX.getStart();
    }
    scX.resetShifts();
    scX.setEndPoints(dStart,dEnd);
    if (scX.getDirection() == BACKWARD) {
      scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,!startEndChanged,true,aax);
    }
 else {
      scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,!startEndChanged,aax);
    }
    if (!scX.isStepFixed()) {
      final Object[] oaMinMax=scX.getMinMax();
      while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
        if (!scX.zoomOut()) {
          break;
        }
        scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
        int tickCount;
        if (scX.getDirection() == BACKWARD) {
          tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,!startEndChanged,true,aax);
        }
 else {
          tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,!startEndChanged,aax);
        }
        if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
          break;
        }
      }
    }
    if (scX.getDirection() == BACKWARD) {
      if (dYAxisLabelsThickness < scX.getStartShift()) {
        dX=scX.getStart() - (dX1 - dX);
      }
    }
 else {
      if (dYAxisLabelsThickness < scX.getEndShift()) {
        dX=scX.getEnd() - (dX1 - dX);
      }
    }
    dX+=insCA.getRight();
    dX2=dX + dDeltaX2;
    dX1=dX - dDeltaX1;
    axPV.setTitleCoordinate((iYTitleLocation == LEFT) ? dX1 - 1 : dX2 + 1 - dYAxisTitleThickness);
  }
 else {
    double dDeltaX1=0, dDeltaX2=0;
    if (iYTitleLocation == RIGHT) {
      dX2+=dYAxisTitleThickness;
    }
 else     if (iYTitleLocation == LEFT) {
      dX1-=dYAxisTitleThickness;
    }
    double dW1=0, dW2=0;
    if (iYLabelLocation == LEFT) {
      dW1=(bTicksLeft ? getTickSize() : 0) + Math.max(dYAxisLabelsThickness,dDecorationThickness[0]);
      dW2=(bTicksRight ? getTickSize() : 0);
      if (dW1 + dW2 <= dWTotal) {
        dX1-=dW1;
        dX2+=dW2;
        dWTotal-=(dW1 + dW2);
      }
 else {
        axPV.setShowLabels(false);
      }
      dDeltaX1=dX - dX1;
      dDeltaX2=dX2 - dX;
      if (dX1 < dBlockX) {
        final Object[] oaMinMax=scX.getMinMax();
        boolean bForceBreak=false;
        do {
          scX.setEndPoints(scX.getStart() - scX.getStartShift(),scX.getEnd() + scX.getEndShift());
          scX.resetShifts();
          double[] da=scX.getEndPoints();
          double dT_RI=dBlockX - dX1;
          if (scX.getDirection() == BACKWARD) {
            double dAMin_AMax=da[0] - da[1];
            double dAMax_RI=Math.abs(da[0] - dX);
            double dDelta=(dT_RI / dAMax_RI) * dAMin_AMax;
            dEnd=da[1] + dDelta;
            dStart=da[0];
            if (dEnd < dBlockX) {
              dEnd=dBlockX;
              bForceBreak=true;
            }
          }
 else {
            double dAMin_AMax=da[1] - da[0];
            double dAMax_RI=Math.abs(da[1] - dX);
            double dDelta=(dT_RI / dAMax_RI) * dAMin_AMax;
            dStart=da[0] + dDelta;
            dEnd=da[1];
            if (dStart < dBlockX) {
              dStart=dBlockX;
              bForceBreak=true;
            }
          }
          scX.setEndPoints(dStart,dEnd);
          scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
          while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
            if (!scX.zoomOut()) {
              bForceBreak=true;
              break;
            }
            scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
            int tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
            if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
              bForceBreak=true;
              break;
            }
          }
          dX=getLocation(scX,iv);
          dX1=dX - dDeltaX1;
        }
 while (Math.abs(dX1 - dBlockX) > 1 && !bForceBreak);
      }
 else {
        dStart=scX.getStart();
        dEnd=scX.getEnd();
        scX.setEndPoints(dStart,dEnd);
        scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
        if (!scX.isStepFixed()) {
          final Object[] oaMinMax=scX.getMinMax();
          while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
            if (!scX.zoomOut()) {
              break;
            }
            scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
            int tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
            if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
              break;
            }
          }
        }
        dX=getLocation(scX,iv);
      }
      dX1=dX - dDeltaX1;
      dX2=dX + dDeltaX2;
    }
 else     if (iYLabelLocation == RIGHT) {
      dW1=(bTicksLeft ? getTickSize() : 0);
      dW2=(bTicksRight ? getTickSize() : 0) + Math.max(dYAxisLabelsThickness,dDecorationThickness[1]);
      if (dW1 + dW2 <= dWTotal) {
        dX1-=dW1;
        dX2+=dW2;
        dWTotal-=(dW1 + dW2);
      }
      dDeltaX1=dX - dX1;
      dDeltaX2=dX2 - dX;
      if (dX2 > dBlockX + dBlockWidth) {
        final Object[] oaMinMax=scX.getMinMax();
        boolean bForceBreak=false;
        do {
          scX.setEndPoints(scX.getStart() - scX.getStartShift(),scX.getEnd() + scX.getEndShift());
          scX.resetShifts();
          double[] da=scX.getEndPoints();
          double dT_RI=dX2 - (dBlockX + dBlockWidth);
          if (scX.getDirection() == BACKWARD) {
            double dAMin_AMax=da[0] - da[1];
            double dAMin_RI=Math.abs(dX - da[1]);
            double dDelta=Math.abs(dT_RI / dAMin_RI) * dAMin_AMax;
            dStart=da[0] - dDelta;
            dEnd=da[1];
            if (dStart > dBlockX + dBlockWidth) {
              dStart=dBlockX + dBlockWidth;
              bForceBreak=true;
            }
          }
 else {
            double dAMin_AMax=da[1] - da[0];
            double dAMin_RI=Math.abs(dX - da[0]);
            double dDelta=(dT_RI / dAMin_RI) * dAMin_AMax;
            dEnd=da[1] - dDelta;
            dStart=da[0];
            if (dEnd > dBlockX + dBlockWidth) {
              dEnd=dBlockX + dBlockWidth;
              bForceBreak=true;
            }
          }
          scX.setEndPoints(dStart,dEnd);
          scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
          if (!scX.isStepFixed()) {
            while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
              if (!scX.zoomOut()) {
                bForceBreak=true;
                break;
              }
              scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
              int tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
              if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
                bForceBreak=true;
                break;
              }
            }
          }
          dX=getLocation(scX,iv);
          dX2=dX + dDeltaX2;
        }
 while (Math.abs(dX2 - (dBlockX + dBlockWidth)) > 1 && !bForceBreak);
      }
 else {
        dStart=scX.getStart();
        dEnd=scX.getEnd();
        scX.setEndPoints(dStart,dEnd);
        scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
        if (!scX.isStepFixed()) {
          final Object[] oaMinMax=scX.getMinMax();
          while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
            if (!scX.zoomOut()) {
              break;
            }
            scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
            int tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
            if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
              break;
            }
          }
        }
        dX=getLocation(scX,iv);
      }
      dX2=dX + dDeltaX2;
      dX1=dX - dDeltaX1;
    }
    axPV.setTitleCoordinate((iYTitleLocation == LEFT) ? dX1 - 1 : dX2 + 1 - dYAxisTitleThickness);
  }
  return dX;
}

Fixed version (ground truth):
/** 
 * Goals: 1. Adjust the two ends of the vertical axis to fit start/end labels 2. Compute the horizontal co-ordinate for the axis
 * @param dBlockX
 * @param dBlockWidth
 * @param aax
 * @return
 */
protected final double adjustHorizontal(double dBlockX,double dBlockWidth,AllAxes aax) throws ChartException, IllegalArgumentException {
  final OneAxis axPH=aax.areAxesSwapped() ? aax.getPrimaryOrthogonal() : aax.getPrimaryBase();
  final OneAxis axPV=aax.areAxesSwapped() ? aax.getPrimaryBase() : aax.getPrimaryOrthogonal();
  final AutoScale scX=axPH.getScale();
  final AutoScale scY=axPV.getScale();
  final int iXLabelLocation=axPH.getLabelPosition();
  final int iYLabelLocation=axPV.getLabelPosition();
  final int iYTitleLocation=axPV.getTitlePosition();
  final Label laXAxisLabels=axPH.getLabel();
  final Label laYAxisLabels=axPV.getLabel();
  final Label laYAxisTitle=axPV.getTitle();
  final int iYTickStyle=axPV.getCombinedTickStyle();
  final IntersectionValue iv=axPV.getIntersectionValue();
  final boolean bTicksLeft=(iYTickStyle & TICK_LEFT) == TICK_LEFT;
  final boolean bTicksRight=(iYTickStyle & TICK_RIGHT) == TICK_RIGHT;
  final double dAppliedYAxisPlotSpacing=(iv.iType == IConstants.MAX || iv.iType == IConstants.MIN) && !aax.getPrimaryOrthogonal().getModelAxis().isLabelWithinAxes() ? dYAxisPlotSpacing : 0;
  double dStart=scY.getStart(), dEnd=scY.getEnd();
  scY.computeTicks(ids,laYAxisLabels,iYLabelLocation,VERTICAL,dStart,dEnd,true,aax);
  if (!scY.isStepFixed()) {
    final Object[] oaMinMax=scY.getMinMax();
    while (!scY.checkFit(ids,laYAxisLabels,iYLabelLocation)) {
      if (!scY.zoomOut()) {
        break;
      }
      scY.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
      int tickCount=scY.computeTicks(ids,laYAxisLabels,iYLabelLocation,VERTICAL,dStart,dEnd,true,aax);
      if (scY.getUnit() != null && asInteger(scY.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
        break;
      }
    }
  }
  double dYAxisLabelsThickness=scY.computeAxisLabelThickness(ids,axPV.getLabel(),VERTICAL);
  double[] dDecorationThickness={0,0};
  Series[] sea=cwa.getSeries(IConstants.ORTHOGONAL);
  Map<Series,LegendItemRenderingHints> seriesRenderingHints=rtc.getSeriesRenderers();
  for (int i=0; i < sea.length; i++) {
    LegendItemRenderingHints lirh=seriesRenderingHints.get(sea[i]);
    if (lirh != null && lirh.getRenderer() instanceof AxesRenderer) {
      IAxesDecorator iad=((AxesRenderer)lirh.getRenderer()).getAxesDecorator(axPV);
      if (iad != null) {
        double[] thickness=iad.computeDecorationThickness(ids,axPV);
        if (thickness[0] > dDecorationThickness[0]) {
          dDecorationThickness[0]=thickness[0];
        }
        if (thickness[1] > dDecorationThickness[1]) {
          dDecorationThickness[1]=thickness[1];
        }
      }
    }
  }
  double dYAxisTitleThickness=0;
  if (laYAxisTitle.isVisible()) {
    final String sPreviousValue=laYAxisTitle.getCaption().getValue();
    laYAxisTitle.getCaption().setValue(rtc.externalizedMessage(sPreviousValue));
    double maxWidth=AXIS_TITLE_PERCENT * boPlot.getWidth();
    double maxHeight=boPlot.getHeight();
    LabelLimiter lblLimit=new LabelLimiter(maxWidth,maxHeight,0);
    lblLimit.computeWrapping(ids,laYAxisTitle);
    lblLimit=lblLimit.limitLabelSize(ids,laYAxisTitle,EnumSet.of(LabelLimiter.Option.FIX_HEIGHT));
    putLabelLimiter(axPV.getModelAxis().getTitle(),lblLimit);
    dYAxisTitleThickness=lblLimit.getMaxWidth();
    laYAxisTitle.getCaption().setValue(sPreviousValue);
  }
  double dX=getLocation(scX,iv), dX1=dX, dX2=dX;
  double dWTotal=Math.abs(scX.getStart() - scX.getEnd());
  if (axPV.getModelAxis().isSetLabelSpan()) {
    double dFixedLabelThickness=axPV.getModelAxis().getLabelSpan() * dPointToPixel;
    if (dFixedLabelThickness < dWTotal - 2 * getTickSize()) {
      if (dYAxisLabelsThickness + dYAxisTitleThickness > dFixedLabelThickness) {
        axPV.setShowLabels(false);
      }
      if (dYAxisTitleThickness > dFixedLabelThickness) {
        laYAxisTitle.setVisible(false);
        dYAxisTitleThickness=0;
      }
      dYAxisLabelsThickness=dFixedLabelThickness;
    }
  }
  if (iv.iType == IConstants.MIN) {
    if (scX.getDirection() == BACKWARD) {
      dX=getLocation(scX,IntersectionValue.MAX_VALUE);
    }
    dX-=dAppliedYAxisPlotSpacing;
    dX1=dX;
    dX2=dX;
    double dTickSize=getTickSize();
    if (bTicksLeft && dTickSize <= dWTotal) {
      dX1-=getTickSize();
      dWTotal-=dTickSize;
    }
 else {
      dTickSize=0;
    }
    double dW1=0, dW2=0;
    if (iYLabelLocation == LEFT) {
      dW1=Math.max(dYAxisLabelsThickness,dDecorationThickness[0]);
      dW2=Math.max(bTicksRight ? getTickSize() : 0,dAppliedYAxisPlotSpacing);
    }
 else     if (iYLabelLocation == RIGHT) {
      dW1=dDecorationThickness[0];
      dW2=Math.max((bTicksRight ? getTickSize() : 0) + dYAxisLabelsThickness,dAppliedYAxisPlotSpacing);
    }
    if (dW1 + dW2 <= dWTotal) {
      dX1-=dW1;
      dX2+=dW2;
      dWTotal-=(dW1 + dW2);
    }
 else {
      axPV.setShowLabels(false);
    }
    if (iYTitleLocation == LEFT) {
      dX1-=dYAxisTitleThickness;
    }
 else     if (iYTitleLocation == RIGHT) {
      dX2+=dYAxisTitleThickness;
    }
    if (dX1 < dBlockX) {
      final double dDelta=(dBlockX - dX1);
      dX1=dBlockX;
      dX+=dDelta;
      dX2+=dDelta;
    }
    final double dDeltaX1=dX - dX1;
    final double dDeltaX2=dX2 - dX;
    if (iYLabelLocation == RIGHT) {
      dX2=(dX + dAppliedYAxisPlotSpacing);
    }
    dYAxisLabelsThickness=dX2 - dX1;
    scX.computeAxisStartEndShifts(ids,laXAxisLabels,HORIZONTAL,iXLabelLocation,aax);
    boolean startEndChanged=false;
    if (scX.getDirection() == BACKWARD) {
      if (dYAxisLabelsThickness > scX.getEndShift()) {
        dEnd=dX2;
        startEndChanged=true;
      }
 else {
        dEnd=scX.getEnd();
      }
      dStart=scX.getStart();
    }
 else {
      if (dYAxisLabelsThickness > scX.getStartShift()) {
        dStart=dX2;
        startEndChanged=true;
      }
 else {
        dStart=scX.getStart();
      }
      dEnd=scX.getEnd();
    }
    scX.resetShifts();
    scX.setEndPoints(dStart,dEnd);
    if (scX.getDirection() == BACKWARD) {
      scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,!startEndChanged,aax);
    }
 else {
      scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,!startEndChanged,true,aax);
    }
    if (!scX.isStepFixed()) {
      final Object[] oaMinMax=scX.getMinMax();
      while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
        if (!scX.zoomOut()) {
          break;
        }
        scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
        int tickCount;
        if (scX.getDirection() == BACKWARD) {
          tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,!startEndChanged,aax);
        }
 else {
          tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,!startEndChanged,true,aax);
        }
        if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
          break;
        }
      }
    }
    if (scX.getDirection() == BACKWARD) {
      if (dYAxisLabelsThickness < scX.getEndShift()) {
        dX=scX.getEnd() - (dX2 - dX);
      }
    }
 else {
      if (dYAxisLabelsThickness < scX.getStartShift()) {
        dX=scX.getStart() - (dX2 - dX);
      }
    }
    dX-=insCA.getLeft();
    dX2=dX + dDeltaX2;
    dX1=dX - dDeltaX1;
    axPV.setTitleCoordinate((iYTitleLocation == LEFT) ? dX1 - 1 : dX2 + 1 - dYAxisTitleThickness);
  }
 else   if (iv.iType == IConstants.MAX) {
    if (scX.getDirection() == BACKWARD) {
      dX=getLocation(scX,IntersectionValue.MIN_VALUE);
    }
    dX+=dAppliedYAxisPlotSpacing;
    dWTotal-=dAppliedYAxisPlotSpacing;
    dX1=dX;
    dX2=dX;
    if (bTicksRight && getTickSize() <= dWTotal) {
      dX2+=getTickSize();
      dWTotal-=getTickSize();
    }
 else {
    }
    double dW1=0, dW2=0;
    if (iYLabelLocation == RIGHT) {
      dW1=Math.max((bTicksLeft ? getTickSize() : 0) + dDecorationThickness[0],dAppliedYAxisPlotSpacing);
      dW2=Math.max(dYAxisLabelsThickness,dDecorationThickness[1]);
    }
 else     if (iYLabelLocation == LEFT) {
      dW1=Math.max((bTicksLeft ? getTickSize() : 0) + Math.max(dYAxisLabelsThickness,dDecorationThickness[0]),dAppliedYAxisPlotSpacing);
      dW2=dDecorationThickness[1];
    }
    if (dW1 + dW2 <= dWTotal) {
      dX1-=dW1;
      dX2+=dW2;
      dWTotal-=(dW1 + dW2);
    }
 else {
      axPV.setShowLabels(false);
    }
    if (iYTitleLocation == RIGHT) {
      dX2+=dYAxisTitleThickness;
    }
 else     if (iYTitleLocation == LEFT) {
      dX1-=dYAxisTitleThickness;
    }
    if (dX2 > dBlockX + dBlockWidth) {
      final double dDelta=dX2 - (dBlockX + dBlockWidth);
      dX2=dBlockX + dBlockWidth;
      dX-=dDelta;
      dX1-=dDelta;
    }
    final double dDeltaX1=dX - dX1;
    final double dDeltaX2=dX2 - dX;
    if (iYLabelLocation == LEFT) {
      dX1=(dX - dAppliedYAxisPlotSpacing);
    }
    dYAxisLabelsThickness=dX2 - dX1;
    scX.computeAxisStartEndShifts(ids,laXAxisLabels,HORIZONTAL,iXLabelLocation,aax);
    boolean startEndChanged=false;
    if (scX.getDirection() == BACKWARD) {
      if (dYAxisLabelsThickness > scX.getStartShift()) {
        dStart=dX1;
        startEndChanged=true;
      }
 else {
        dStart=scX.getStart();
      }
      dEnd=scX.getEnd();
    }
 else {
      if (dYAxisLabelsThickness > scX.getEndShift()) {
        dEnd=dX1;
        startEndChanged=true;
      }
 else {
        dEnd=scX.getEnd();
      }
      dStart=scX.getStart();
    }
    scX.resetShifts();
    scX.setEndPoints(dStart,dEnd);
    if (scX.getDirection() == BACKWARD) {
      scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,!startEndChanged,true,aax);
    }
 else {
      scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,!startEndChanged,aax);
    }
    if (!scX.isStepFixed()) {
      final Object[] oaMinMax=scX.getMinMax();
      while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
        if (!scX.zoomOut()) {
          break;
        }
        scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
        int tickCount;
        if (scX.getDirection() == BACKWARD) {
          tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,!startEndChanged,true,aax);
        }
 else {
          tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,!startEndChanged,aax);
        }
        if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
          break;
        }
      }
    }
    if (scX.getDirection() == BACKWARD) {
      if (dYAxisLabelsThickness < scX.getStartShift()) {
        dX=scX.getStart() - (dX1 - dX);
      }
    }
 else {
      if (dYAxisLabelsThickness < scX.getEndShift()) {
        dX=scX.getEnd() - (dX1 - dX);
      }
    }
    dX+=insCA.getRight();
    dX2=dX + dDeltaX2;
    dX1=dX - dDeltaX1;
    axPV.setTitleCoordinate((iYTitleLocation == LEFT) ? dX1 - 1 : dX2 + 1 - dYAxisTitleThickness);
  }
 else {
    double dDeltaX1=0, dDeltaX2=0;
    if (iYTitleLocation == RIGHT) {
      dX2+=dYAxisTitleThickness;
    }
 else     if (iYTitleLocation == LEFT) {
      dX1-=dYAxisTitleThickness;
    }
    double dW1=0, dW2=0;
    if (iYLabelLocation == LEFT) {
      dW1=(bTicksLeft ? getTickSize() : 0) + Math.max(dYAxisLabelsThickness,dDecorationThickness[0]);
      dW2=(bTicksRight ? getTickSize() : 0);
      if (dW1 + dW2 <= dWTotal) {
        dX1-=dW1;
        dX2+=dW2;
        dWTotal-=(dW1 + dW2);
      }
 else {
        axPV.setShowLabels(false);
      }
      dDeltaX1=dX - dX1;
      dDeltaX2=dX2 - dX;
      if (dX1 < dBlockX) {
        final Object[] oaMinMax=scX.getMinMax();
        boolean bForceBreak=false;
        do {
          scX.setEndPoints(scX.getStart() - scX.getStartShift(),scX.getEnd() + scX.getEndShift());
          scX.resetShifts();
          double[] da=scX.getEndPoints();
          double dT_RI=dBlockX - dX1;
          if (scX.getDirection() == BACKWARD) {
            double dAMin_AMax=da[0] - da[1];
            double dAMax_RI=Math.abs(da[0] - dX);
            double dDelta=(dT_RI / dAMax_RI) * dAMin_AMax;
            dEnd=da[1] + dDelta;
            dStart=da[0];
            if (dEnd < dBlockX) {
              dEnd=dBlockX;
              bForceBreak=true;
            }
          }
 else {
            double dAMin_AMax=da[1] - da[0];
            double dAMax_RI=Math.abs(da[1] - dX);
            double dDelta=(dT_RI / dAMax_RI) * dAMin_AMax;
            dStart=da[0] + dDelta;
            dEnd=da[1];
            if (dStart < dBlockX) {
              dStart=dBlockX;
              bForceBreak=true;
            }
          }
          scX.setEndPoints(dStart,dEnd);
          scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
          while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
            if (!scX.zoomOut()) {
              bForceBreak=true;
              break;
            }
            scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
            int tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
            if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
              bForceBreak=true;
              break;
            }
          }
          dX=getLocation(scX,iv);
          dX1=dX - dDeltaX1;
        }
 while (Math.abs(dX1 - dBlockX) > 1 && !bForceBreak);
      }
 else {
        dStart=scX.getStart();
        dEnd=scX.getEnd();
        scX.setEndPoints(dStart,dEnd);
        scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
        if (!scX.isStepFixed()) {
          final Object[] oaMinMax=scX.getMinMax();
          while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
            if (!scX.zoomOut()) {
              break;
            }
            scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
            int tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
            if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
              break;
            }
          }
        }
        dX=getLocation(scX,iv);
      }
      dX1=dX - dDeltaX1;
      dX2=dX + dDeltaX2;
    }
 else     if (iYLabelLocation == RIGHT) {
      dW1=(bTicksLeft ? getTickSize() : 0);
      dW2=(bTicksRight ? getTickSize() : 0) + Math.max(dYAxisLabelsThickness,dDecorationThickness[1]);
      if (dW1 + dW2 <= dWTotal) {
        dX1-=dW1;
        dX2+=dW2;
        dWTotal-=(dW1 + dW2);
      }
      dDeltaX1=dX - dX1;
      dDeltaX2=dX2 - dX;
      if (dX2 > dBlockX + dBlockWidth) {
        final Object[] oaMinMax=scX.getMinMax();
        boolean bForceBreak=false;
        do {
          scX.setEndPoints(scX.getStart() - scX.getStartShift(),scX.getEnd() + scX.getEndShift());
          scX.resetShifts();
          double[] da=scX.getEndPoints();
          double dT_RI=dX2 - (dBlockX + dBlockWidth);
          if (scX.getDirection() == BACKWARD) {
            double dAMin_AMax=da[0] - da[1];
            double dAMin_RI=Math.abs(dX - da[1]);
            double dDelta=Math.abs(dT_RI / dAMin_RI) * dAMin_AMax;
            dStart=da[0] - dDelta;
            dEnd=da[1];
            if (dStart > dBlockX + dBlockWidth) {
              dStart=dBlockX + dBlockWidth;
              bForceBreak=true;
            }
          }
 else {
            double dAMin_AMax=da[1] - da[0];
            double dAMin_RI=Math.abs(dX - da[0]);
            double dDelta=(dT_RI / dAMin_RI) * dAMin_AMax;
            dEnd=da[1] - dDelta;
            dStart=da[0];
            if (dEnd > dBlockX + dBlockWidth) {
              dEnd=dBlockX + dBlockWidth;
              bForceBreak=true;
            }
          }
          scX.setEndPoints(dStart,dEnd);
          scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
          if (!scX.isStepFixed()) {
            while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
              if (!scX.zoomOut()) {
                bForceBreak=true;
                break;
              }
              scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
              int tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
              if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
                bForceBreak=true;
                break;
              }
            }
          }
          dX=getLocation(scX,iv);
          dX2=dX + dDeltaX2;
        }
 while (Math.abs(dX2 - (dBlockX + dBlockWidth)) > 1 && !bForceBreak);
      }
 else {
        dStart=scX.getStart();
        dEnd=scX.getEnd();
        scX.setEndPoints(dStart,dEnd);
        scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
        if (!scX.isStepFixed()) {
          final Object[] oaMinMax=scX.getMinMax();
          while (!scX.checkFit(ids,laXAxisLabels,iXLabelLocation)) {
            if (!scX.zoomOut()) {
              break;
            }
            scX.updateAxisMinMax(oaMinMax[0],oaMinMax[1]);
            int tickCount=scX.computeTicks(ids,laXAxisLabels,iXLabelLocation,HORIZONTAL,dStart,dEnd,true,aax);
            if (scX.getUnit() != null && asInteger(scX.getUnit()) == Calendar.YEAR && tickCount <= 3 || isSharedScale()) {
              break;
            }
          }
        }
        dX=getLocation(scX,iv);
      }
      dX2=dX + dDeltaX2;
      dX1=dX - dDeltaX1;
    }
    axPV.setTitleCoordinate((iYTitleLocation == LEFT) ? dX1 - 1 : dX2 + 1 - dYAxisTitleThickness);
  }
  return dX;
}