Rendering di testo utilizzando TrueType Font | Java

Rendering Testo

Al fine di rendere il testo, il sottosistema di rendering richiede l’implementazione di Aspose.Font.Rendering.IGlyphOutlinePainter Interfaccia per disegnare glifo. Questo può essere ottenuto utilizzando i seguenti passaggi.

  1. Crea metodo DrawText() che disegna il testo specificato in System.Drawing.Bitmap e salva la bitmap risultante sul disco. Ciò includerà i seguenti passaggi:

Passaggi ausiliari per questa strategia

L’implementazione del metodo DrawText è come mostrato di seguito.

 1private static final class GlyphOutlinePainter implements IGlyphOutlinePainter {
 2    private final GeneralPath path;
 3
 4    private GlyphOutlinePainter(GeneralPath path) {
 5        this.path = path;
 6    }
 7
 8    @Override
 9    public void moveTo(MoveTo moveTo) {
10        path.moveTo(moveTo.getX(), moveTo.getY());
11    }
12
13    @Override
14    public void lineTo(LineTo lineTo) {
15        path.lineTo(lineTo.getX(), lineTo.getY());
16    }
17
18    @Override
19    public void curveTo(CurveTo curveTo) {
20        path.curveTo(curveTo.getX1(), curveTo.getY1(), curveTo.getX2(), curveTo.getY2(),
21                curveTo.getX3(), curveTo.getY3());
22    }
23
24    @Override
25    public void closePath() {
26        path.closePath();
27    }
28}
 1private static void drawText(String text, IFont font, double fontSize,
 2        Paint backgroundBrush, Paint textBrush, String outputFile) throws IOException {
 3    GlyphId[] glyphIds = new GlyphId[text.length()];
 4    for (int i = 0; i < text.length(); i++) {
 5        glyphIds[i] = font.getEncoding().decodeToGid(text.charAt(i));
 6    }
 7    double dpi = 300;
 8    double resolutionCorrection = dpi / 72;
 9    BufferedImage outputBitmap = new BufferedImage(960, 720, BufferedImage.TYPE_INT_RGB);
10    Graphics2D graphics = outputBitmap.createGraphics();
11    try {
12        graphics.setPaint(backgroundBrush);
13        graphics.fillRect(0, 0, outputBitmap.getWidth(), outputBitmap.getHeight());
14        graphics.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
15        GlyphId previousGlyphId = null;
16        double glyphXCoordinate = 0;
17        double glyphYCoordinate = fontSize * resolutionCorrection;
18        for (GlyphId glyphId : glyphIds) {
19            if (glyphId == null) {
20                continue;
21            }
22            Glyph glyph = font.getGlyphAccessor().getGlyphById(glyphId);
23            if (glyph == null) {
24                continue;
25            }
26            if (previousGlyphId != null) {
27                double kerning = font.getMetrics().getKerningValue(previousGlyphId, glyphId)
28                        / glyph.getSourceResolution() * fontSize * resolutionCorrection;
29                double advance = fontWidthToImageWidth(font.getMetrics().getGlyphWidth(previousGlyphId),
30                        glyph.getSourceResolution(), fontSize, dpi);
31                glyphXCoordinate += kerning + advance;
32            }
33            GeneralPath path = new GeneralPath();
34            IGlyphRenderer renderer = new GlyphOutlineRenderer(new GlyphOutlinePainter(path));
35            TransformationMatrix matrix = new TransformationMatrix(new double[] {
36                    fontSize * resolutionCorrection, 0, 0, -fontSize * resolutionCorrection,
37                    glyphXCoordinate, glyphYCoordinate
38            });
39            renderer.renderGlyph(font, glyphId, matrix);
40            path.setWindingRule(GeneralPath.WIND_NON_ZERO);
41            graphics.setPaint(textBrush);
42            graphics.fill(path);
43            previousGlyphId = glyphId;
44        }
45    } finally {
46        graphics.dispose();
47    }
48    if (!ImageIO.write(outputBitmap, "png", new File(outputFile))) {
49        throw new IOException("No PNG writer is available.");
50    }
51}
  1. Crea metodo di utilità per calcolare la larghezza del carattere alla larghezza dell’immagine come mostrato nel campione di codice seguente
1private static double fontWidthToImageWidth(double width, int fontSourceResolution,
2        double fontSize, double dpi) {
3    return width / fontSourceResolution * fontSize * (dpi / 72);
4}

Chiamare la funzionalità di testo di rendering

Per utilizzare le implementazioni di cui sopra, il seguente codice di esempio può essere eseguito dal metodo principale di un’applicazione basata sulla console.

 1String firstFontPath = Paths.get(getDataDir(), "..", "TTF", "montserrat-bold.ttf")
 2        .normalize().toString();
 3String secondFontPath = Paths.get(getDataDir(), "..", "TTF", "LatoWeb-Regular.ttf")
 4        .normalize().toString();
 5TtfFont firstFont = (TtfFont) Font.open(new FontDefinition(FontType.TTF,
 6        new FontFileDefinition("ttf", new FileSystemStreamSource(firstFontPath))));
 7TtfFont secondFont = (TtfFont) Font.open(new FontDefinition(FontType.TTF,
 8        new FontFileDefinition("ttf", new FileSystemStreamSource(secondFontPath))));
 9
10String firstOutput = Paths.get(getOutputDir(), "hello1_montserrat_out.png").toString();
11String secondOutput = Paths.get(getOutputDir(), "hello2_lato_out.png").toString();
12drawText("Hello world", firstFont, 14, Color.WHITE, Color.BLACK, firstOutput);
13drawText("Hello world", secondFont, 14, Color.YELLOW, Color.RED, secondOutput);