0

我想为我正在尝试制作的游戏制作自定义字体,但我想将所有字符分成不同的文件。到目前为止,我已经制作了所有的字符图像,并设法让它打印出我想要打印的正确字符。问题是当我使用某些字符(例如小写字符和 J's)时,对齐方式是错误的。我不知道如何解决这个问题。另一个问题是我需要能够使用此字体获取字符串的宽度/高度,但要做到这一点,我还需要将字母的大小调整为正确的大小。

这是我的字体代码:

package org.simplecorporation.myengine.core.gui.font.image;

import java.util.LinkedList;

import org.lwjgl.opengl.GL11;
import org.simplecorporation.myengine.core.render.basic.BasicRenderer;
import org.simplecorporation.myengine.core.render.colour.Colour;
import org.simplecorporation.myengine.utils.file.FileUtils;


public class ImageFolderFont {

/* The font */
public LinkedList<ImageLetter> letters;

/* The font size */
public double size;

/* The constructor of the font */
public ImageFolderFont(String folder , String imageFormat , boolean inFolder , double size) {
    //Load the font

    //Create the letters linked list
    this.letters = new LinkedList<ImageLetter>();

    //The file text
    LinkedList<String> fileText = FileUtils.read(folder + "/font.txt");

    //Load all of the images in the font
    for (int a = 0; a < fileText.size(); a++) {
        //Split the current line
        String[] split = fileText.get(a).split(" ");
        //Create the letter
        ImageLetter letter = new ImageLetter(split[0].charAt(0) , folder + "/" + split[1] , imageFormat , inFolder);
        //Add the letter to the letters
        this.letters.add(letter);
    }

    //Set the size
    this.size = size;
}

/* The method that renders the font */
public void render(String text , double x , double y) {
    //Enable blending
    GL11.glEnable(GL11.GL_BLEND);
    GL11.glBlendFunc(GL11.GL_SRC_ALPHA , GL11.GL_ONE_MINUS_SRC_ALPHA);
    //Loop though the text
    for (int a = 0; a < text.length(); a++) {
        //Check if the current letter is a space
        if (text.charAt(a) == ' ') {
            x += this.size / 2;
        } else {
            //Set the colour, get the letter and render the letter image
            BasicRenderer.setColour(Colour.WHITE);
            ImageLetter letter = this.getLetter(text.charAt(a));
            //The width and height
            double width = 0;
            double height = 0;
            //Check the size
            if ((letter.getWidth() / letter.getHeight()) == 1) {
                width = size * (letter.getWidth() / letter.getHeight() * 1.5);
                height = size * (letter.getWidth() / letter.getHeight());
            } else {
                width = size * (letter.getHeight() / letter.getWidth());
                height = size * (letter.getHeight() / letter.getWidth());
            }
            BasicRenderer.renderImage(letter , x , y ,  width , height);
            //Add to the x position
            x += width / 2;
        }
    }
}

/* The method to get the width of a string */
public double getWidth(String text) {
    //The width of the text
    double width = 0;
    //Loop though the text
    for (int a = 0; a < text.length(); a++) {
        //Get the letter
        ImageLetter letter = this.getLetter(text.charAt(a));
        //Add to the width
        width += size * (letter.getHeight() / letter.getWidth()) + 4;
    }
    //Return the width
    return width;
}

/* The method to get the height of a string */
public double getHeight(String text) {
    //The height of the text
    double height = 0;
    //Loop though the text
    for (int a = 0; a < text.length(); a++) {
        //Get the letter
        ImageLetter letter = this.getLetter(text.charAt(a));
        //Check if the letters size is bigger
        if (letter.getWidth() * (letter.getHeight() / size) > height)
            height = letter.getWidth() * (letter.getHeight() / size);
    }
    //Return the height
    return height;
}

/* The method that returns a letter based on a char */
public ImageLetter getLetter(char character) {
    //The letter
    ImageLetter letter = this.letters.get(0);

    //Loop though the letters
    for (int a = 0; a < this.letters.size(); a ++) {
        //Check if the current letter is the right one
        if (this.letters.get(a).character == character) {
            //Set the letter
            letter = this.letters.get(a);
            //Exit the loop
            break;
        }
    }

    //Return the letter
    return letter;
}

}

ImageLetter 是一个带有 char 变量的图像,该变量包含它所代表的字符。

图片:https ://f.cloud.github.com/assets/3252552/1103273/041ac464-1898-11e3-8b53-1e81573eec97.png

提前谢谢了。

4

1 回答 1

0

排版是一门丰富的学科。自定义“字体”中的每个字母都应定义基线的 y 位置。基线基本上是字母底部应该位于的位置的定义。大多数字母完全位于基线之上,但有些字母,如 j 和 y,具有延伸到基线下方的称为“下降器”的部分。字体的字形不应渲染为使字母的顶部重合,而应使基线重合。

一个简单的替代方法是在字母图像的顶部添加足够的空白,以便它们从行的顶部(“上升高度”)延伸到字母的底部。这样,所有字母看起来都具有相同的基线。

于 2013-09-08T15:55:33.170 回答