Ejemplo n.º 1
0
  public float getCharacterAdvance(char curChar, char nextChar, float size) {
    BitmapCharacter c = charSet.getCharacter(curChar);
    if (c == null) return 0f;

    float advance = size * c.getXAdvance();
    advance += c.getKerning(nextChar) * size;
    return advance;
  }
Ejemplo n.º 2
0
  void setBitmapChar(BitmapCharacter bitmapChar) {
    x0 = Integer.MIN_VALUE;
    y0 = Integer.MIN_VALUE;
    width = Integer.MIN_VALUE;
    height = Integer.MIN_VALUE;
    alignX = 0;
    alignY = 0;

    BitmapCharacterSet charSet = font.getCharSet();
    this.bitmapChar = bitmapChar;
    if (bitmapChar != null) {
      u0 = (float) bitmapChar.getX() / charSet.getWidth();
      v0 = (float) bitmapChar.getY() / charSet.getHeight();
      u1 = u0 + (float) bitmapChar.getWidth() / charSet.getWidth();
      v1 = v0 + (float) bitmapChar.getHeight() / charSet.getHeight();
    } else {
      u0 = 0;
      v0 = 0;
      u1 = 0;
      v1 = 0;
    }
  }
Ejemplo n.º 3
0
  void update(StringBlock block) {
    final float[] tabs = block.getTabPosition();
    final float tabWidth = block.getTabWidth();
    final Rectangle bound = getBound(block);
    sizeScale = block.getSize() / font.getCharSet().getRenderedSize();
    lineY = computeLineY(block);

    if (isHead()) {
      x0 = getBound(block).x;
      y0 = lineY;
      width = 0;
      height = 0;
      xAdvance = 0;
    } else if (isTab()) {
      x0 = previous.getNextX();
      width = tabWidth;
      y0 = lineY;
      height = 0;
      if (tabs != null && x0 < tabs[tabs.length - 1]) {
        for (int i = 0; i < tabs.length - 1; i++) {
          if (x0 > tabs[i] && x0 < tabs[i + 1]) {
            width = tabs[i + 1] - x0;
          }
        }
      }
      xAdvance = width;
    } else if (bitmapChar == null) {
      x0 = getPrevious().getX1();
      y0 = lineY;
      width = 0;
      height = 0;
      xAdvance = 0;
    } else {
      float xOffset = bitmapChar.getXOffset() * sizeScale;
      float yOffset = bitmapChar.getYOffset() * sizeScale;
      xAdvance = bitmapChar.getXAdvance() * sizeScale;
      width = bitmapChar.getWidth() * sizeScale;
      height = bitmapChar.getHeight() * sizeScale;
      float incrScale = rightToLeft ? -1f : 1f;
      float kernAmount = 0f;

      if (previous.isHead() || previous.eol) {
        x0 = bound.x;

        // The first letter quad will be drawn right at the first
        // position... but it does not offset by the characters offset
        // amount.  This means that we've potentially accumulated extra
        // pixels and the next letter won't get drawn far enough unless
        // we add this offset back into xAdvance.. by subtracting it.
        // This is the same thing that's done below because we've
        // technically baked the offset in just like below.  It doesn't
        // look like it at first glance so I'm keeping it separate with
        // this comment.
        xAdvance -= xOffset * incrScale;

      } else {
        x0 = previous.getNextX() + xOffset * incrScale;

        // Since x0 will have offset baked into it then we
        // need to counteract that in xAdvance.  This is better
        // than removing it in getNextX() because we also need
        // to take kerning into account below... which will also
        // get baked in.
        // Without this, getNextX() will return values too far to
        // the left, for example.
        xAdvance -= xOffset * incrScale;
      }
      y0 = lineY + LINE_DIR * yOffset;

      // Adjust for kerning
      BitmapCharacter lastChar = previous.getBitmapChar();
      if (lastChar != null && block.isKerning()) {
        kernAmount = lastChar.getKerning(c) * sizeScale;
        x0 += kernAmount * incrScale;

        // Need to unbake the kerning from xAdvance since it
        // is baked into x0... see above.
        // xAdvance -= kernAmount * incrScale;
        // No, kerning is an inter-character spacing and _does_ affect
        // all subsequent cursor positions.
      }
    }
    if (isEndOfLine()) {
      xAdvance = bound.x - x0;
    }
  }
Ejemplo n.º 4
0
  public float getLineWidth(CharSequence text) {

    // This method will probably always be a bit of a maintenance
    // nightmare since it basis its calculation on a different
    // routine than the Letters class.  The ideal situation would
    // be to abstract out letter position and size into its own
    // class that both BitmapFont and Letters could use for
    // positioning.
    // If getLineWidth() here ever again returns a different value
    // than Letters does with the same text then it might be better
    // just to create a Letters object for the sole purpose of
    // getting a text size.  It's less efficient but at least it
    // would be accurate.

    // And here I am mucking around in here again...
    //
    // A font character has a few values that are pertinent to the
    // line width:
    //  xOffset
    //  xAdvance
    //  kerningAmount(nextChar)
    //
    // The way BitmapText ultimately works is that the first character
    // starts with xOffset included (ie: it is rendered at -xOffset).
    // Its xAdvance is wider to accomodate that initial offset.
    // The cursor position is advanced by xAdvance each time.
    //
    // So, a width should be calculated in a similar way.  Start with
    // -xOffset + xAdvance for the first character and then each subsequent
    // character is just xAdvance more 'width'.
    //
    // The kerning amount from one character to the next affects the
    // cursor position of that next character and thus the ultimate width
    // and so must be factored in also.

    float lineWidth = 0f;
    float maxLineWidth = 0f;
    char lastChar = 0;
    boolean firstCharOfLine = true;
    //        float sizeScale = (float) block.getSize() / charSet.getRenderedSize();
    float sizeScale = 1f;
    for (int i = 0; i < text.length(); i++) {
      char theChar = text.charAt(i);
      if (theChar == '\n') {
        maxLineWidth = Math.max(maxLineWidth, lineWidth);
        lineWidth = 0f;
        firstCharOfLine = true;
        continue;
      }
      BitmapCharacter c = charSet.getCharacter((int) theChar);
      if (c != null) {
        if (theChar == '\\' && i < text.length() - 1 && text.charAt(i + 1) == '#') {
          if (i + 5 < text.length() && text.charAt(i + 5) == '#') {
            i += 5;
            continue;
          } else if (i + 8 < text.length() && text.charAt(i + 8) == '#') {
            i += 8;
            continue;
          }
        }
        if (!firstCharOfLine) {
          lineWidth += findKerningAmount(lastChar, theChar) * sizeScale;
        } else {
          // The first character needs to add in its xOffset but it
          // is the only one... and negative offsets = postive width
          // because we're trying to account for the part that hangs
          // over the left.  So we subtract.
          lineWidth -= c.getXOffset() * sizeScale;
          firstCharOfLine = false;
        }
        float xAdvance = c.getXAdvance() * sizeScale;

        // If this is the last character, then we really should have
        // only add its width.  The advance may include extra spacing
        // that we don't care about.
        if (i == text.length() - 1) {
          lineWidth += c.getWidth() * sizeScale;

          // Since theh width includes the xOffset then we need
          // to take it out again by adding it, ie: offset the width
          // we just added by the appropriate amount.
          lineWidth += c.getXOffset() * sizeScale;
        } else {
          lineWidth += xAdvance;
        }
      }
    }
    return Math.max(maxLineWidth, lineWidth);
  }
Ejemplo n.º 5
0
 private int findKerningAmount(int newLineLastChar, int nextChar) {
   BitmapCharacter c = charSet.getCharacter(newLineLastChar);
   if (c == null) return 0;
   return c.getKerning(nextChar);
 }