gpt4 book ai didi

java - 如何增加高斯模糊的不透明度

转载 作者:行者123 更新时间:2023-11-29 09:14:54 25 4
gpt4 key购买 nike

我有一个 Java 应用程序,我需要在其中在图像上绘制文本。文本、字体和图像都是在运行时确定的。文字需要看起来漂亮,但在图像顶部可读(足够对比)。

为了满足这些要求,我创建了一个投影。这是通过在空白/透明 BufferedImage 上绘制不透明黑色文本,然后应用高斯模糊滤镜来完成的。然后,我再次在投影顶部以不透明的白色绘制文本。所以我有不透明的白色文本,周围有一个黑色模糊的阴影,很快就会消失到完全透明。然后我可以在背景图像之上绘制此图像。

我要解决的问题是投影看起来太透明了。因此,在明亮、繁忙的背景下,它没有给白色文本足够的分隔。

那么如何增加阴影的不透明度呢?我试过增加高斯模糊的半径,这会使阴影变宽,但不会使其更不透明。

我使用的代码基于 this DropShadowDemo罗曼盖伊。我使用他的 createDropShadow() 和 gaussianBlurFilter()。但是,我没有在 paintComponent() 期间分别绘制阴影和文本,而是提前将它们都绘制到 BufferedImage 上;我在 paintComponent() 期间在背景之上绘制了这个 BufferedImage。也许那是我的问题?但我看不出这会如何降低阴影的不透明度。我在 paintComponent() 期间没有使用 g2.setComposite()

我研究过使用某种 BufferedImageOp 来调整投影的不透明度。 ,例如 LookupOp。但是对于一个简单的调整来说似乎需要做很多工作(我猜是创建四个数字数组)。我不认为 RescaleOp 会起作用,因为我希望结果 alpha 与源 alpha 落在相同的范围内(0 到 1)。如果我可以指定一个 BufferedImageOp 来设置 new alpha = sqrt(old alpha) 或类似的东西,那将是理想的。但我不知道一个简单的方法来做到这一点。

代码的细节可以在这里看到:

我会在这里包含相关的代码块,但似乎相关的代码量太大(代码墙)......不妨只提供源文件的链接。

更新

看起来像Change the alpha value of a BufferedImage?将是一种改变阴影不透明度的方法……基本上是逐个重新计算每个像素的 alpha 值。待定:它是否可移植(例如,64 位机器),以及它是否足够快。如果我对每个像素执行 a = sqrt(a)a = sin(a * pi * 0.5) (考虑 a范围从 0 到 1),那会很慢吗?我很高兴知道是否有一种更简单的方法可以利用可用的优化,就像内置的 BufferedImageOps 大概做的那样。也许答案毕竟是为 LookupOp 构建数组。有人知道一些示例代码吗?

最后更新

使用 LookupOp 解决;请参阅下面的代码。

最佳答案

下面是我最终使 BufferedImage 更加不透明的代码。我决定继续使用 LookupOp,而不是在每个像素上对 getRGB/setRGB 进行潜在的不可移植且缓慢的循环。设置查找数组的工作还不错。

/* Make alpha channel more opaque.
* Modify the alpha (opacity) channel so that values are higher, but still
* continuous and monotonically increasing.
*/
private static void adjustOpacity(BufferedImage shadowImage) {
// Use a lookup table with four arrays;
// the three for RGB are identity arrays (no change).
byte identityArray[] = new byte[256];
for (int i=0; i < 256; i++)
identityArray[i] = (byte)i;

byte alphaArray[] = new byte[256];
// map the range (0..256] to (0..pi/2]
double mapTo90Deg = Math.PI / 2.0 / 256.0;
for (int i=0; i < 256; i++) {
alphaArray[i] = (byte)(Math.sin(i * mapTo90Deg) * 256);
}

byte[][] tables = {
identityArray,
identityArray,
identityArray,
alphaArray
};
ByteLookupTable blut = new ByteLookupTable(0, tables);
LookupOp op = new LookupOp(blut, null);

// With LookupOp, it's ok for src and dest to be the same image.
op.filter(shadowImage, shadowImage);
}

它似乎有效(虽然我没有拍摄前后屏幕截图进行比较)。

关于java - 如何增加高斯模糊的不透明度,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10088237/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com