在Java中以亚像素精度绘制图像

问题描述 投票:0回答:1

如何在Java中以亚像素精度绘制图像?

我在这里发现了类似的问题:

Drawing an image using sub-pixel level accuracy using Graphics2D

Sub-pixel Image rendering

很遗憾,答案中提供的解决方案对我不起作用。

public void paintComponent(Graphics g) {
    super.paintComponent(g);
    Graphics2D g2 = (Graphics2D) g;
    g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
    g2.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
    g2.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
    g2.translate(50.5, 50.5);
    g2.fillRect(0, 0, 15, 25);
}

使用g2.translate(50.5, 50.5);填充具有子像素精度的简单矩形效果很好。

public void paintComponent(Graphics g) {
    super.paintComponent(g);
    Graphics2D g2 = (Graphics2D) g;
    g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
    g2.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
    g2.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
    g2.translate(50.5, 50.5);
    g2.drawImage(image, 0, 0, null);
}

但是,当我使用g2.translate(double x, double y)绘制具有亚像素精度的图像时,它不起作用。结果与带有整数位置的图形完全相同。

为什么这不起作用?我用双值转换了图形,但是像素之间没有任何插值。

java image graphics2d subpixel
1个回答
1
投票

这可能取决于OS或Java版本,但对我来说*,使用TexturePaint(我认为有些hack):

protected void paintComponent(Graphics g) {
    super.paintComponent(g);
    Graphics2D g2 = (Graphics2D) g;
    g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
    g2.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
    g2.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
    g2.translate(50.5, 50.5);
    // g2.drawImage(image, 0, 0, null); // Original code
    g2.setPaint(new TexturePaint(image, new Rectangle(image.getWidth(), image.getHeight())));
    g2.fillRect(0, 0, image.getWidth(), image.getHeight());

    // Added orange rect for reference, as the difference is hard to spot...
    g2.setPaint(Color.ORANGE);
    g2.fillRect(0, 0, 15, 25);
}

**在MacOS 10.15上,已通过Java 8和11进行了测试。

您可能需要放大才能看到差异,因为它有点细微...但是在第一张图像(drawImage)中,您会看到橙色矩形未完全重叠,并且形象是坚实的。在第二张图像(TexturePaintfillRect)中,您将看到图像的边缘是半透明的,并且橙色矩形完美重叠。

screenshot of running program

这是在MacBooks内部“视网膜”屏幕上运行的同一应用程序:

screenshot of running program on high res screen

© www.soinside.com 2019 - 2024. All rights reserved.