2

I need to convert a text into a image. The image must have:

  • A white background which fill all image.
  • The text in black color.
  • Text needs to be wordwrap if width/height is less than text length (can be variable depend on font size)
  • Image size 125x125

I create this function which do some of above requeriments:

public static Image crearImagenDesdeTexto(String texto) throws IOException {
    BufferedImage img = new BufferedImage(1, 1, BufferedImage.TYPE_INT_ARGB);
    Graphics2D g2d = img.createGraphics();
    FontMetrics fm = g2d.getFontMetrics();
    int width = fm.stringWidth(texto);
    int height = fm.getHeight();
    g2d.setColor(java.awt.Color.WHITE);
    g2d.fillRect(0, 0, width, height);
    g2d.setColor(java.awt.Color.BLACK);
    Font font = new Font("Arial", Font.PLAIN, 12);
    g2d.setFont(font);
    g2d.dispose();

    img = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
    g2d = img.createGraphics();
    g2d.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY);
    g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
    g2d.setRenderingHint(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
    g2d.setRenderingHint(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
    g2d.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_ON);
    g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
    g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
    g2d.setRenderingHint(RenderingHints.KEY_STROKE_CONTROL, RenderingHints.VALUE_STROKE_PURE);
    g2d.setFont(font);
    fm = g2d.getFontMetrics();
    g2d.setColor(java.awt.Color.BLACK);
    g2d.drawString(texto, 0, fm.getAscent());
    g2d.dispose();

    ByteArrayOutputStream out = new ByteArrayOutputStream();
    ImageIO.write((RenderedImage) img, "png", out);
    out.flush();
    ByteArrayInputStream in = new ByteArrayInputStream(out.toByteArray());
    return new javafx.scene.image.Image(in);
}

I don't know if exists a better way to apply the conversion of it's correct that way.

James_D
  • 201,275
  • 16
  • 291
  • 322
Marcos
  • 4,827
  • 3
  • 20
  • 28

1 Answers1

5

How about

import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.image.WritableImage ;
import javafx.scene.control.Label;

// ...

private static Image textToImage(String text) {
    Label label = new Label(text);
    label.setMinSize(125, 125);
    label.setMaxSize(125, 125);
    label.setPrefSize(125, 125);
    label.setStyle("-fx-background-color: white; -fx-text-fill:black;");
    label.setWrapText(true);
    Scene scene = new Scene(new Group(label));
    WritableImage img = new WritableImage(125, 125) ;
    scene.snapshot(img);
    return img ;
}

Since you want to return a javafx.scene.image.Image, it's probably better to keep as much of it in the JavaFX API as possible.

James_D
  • 201,275
  • 16
  • 291
  • 322