我试图在3D场景中显示各种Text对象
问题在于,当我缩放到文本附近时,它看起来非常模糊。
这是我的应用
的屏幕截图问题:如何改善屏幕上文字的图像质量?
我已尝试在JavaFX 2D text with background in 3D scene 中设置缓存,因为它似乎可以提高答案屏幕截图的图像质量,但在我的情况下它并没有帮助我。
以下是从我的应用程序中删除的可编译示例。它只是创建一些带位置的随机Text对象,并为您提供移动方式。请注意缩放关闭时文本显示的可能性如何。
您 F10 和 F11 可放大和缩小,鼠标拖动可移动相机。
{{1}}
答案 0 :(得分:3)
您尝试做的事与被引用的question之间的主要区别在于相机移动:缓存在该问题中起作用,因为在旋转节点时,相机保持在同一位置。
但是在您的情况下,您在给定位置渲染Text节点,并且具有给定的质量,并且当您开始平移相机时,这些节点不会以不同的方式呈现(具有不同的大小或质量),因此它们变得模糊。
如果缓存不起作用,还有另一种可能性,正如其他question中所建议的那样:使用3D节点。
这具有处理3D对象的明显成本,比2D文本节点更重。
主要思想是:对于给定的文本,我们将文本写入图像,我们将使用此图像作为3D长方体的漫反射贴图。然后我们将长方体添加到子场景并转换为x,y,z坐标。
我们需要来自FXyz3D library的in
,因为内置的3D CuboidMesh
会将相同的图像放入每张脸,因此无效。我们也可以使用自定义Box
实现3D棱镜,但是长方体已经提供了它。
然后我们可以为长方体生成一个网络图像,并设置它以便我们有所需的卡:
TriangleMesh
卡片看起来很暗,但是在环境光线下,我们可以摆脱它的黑暗背景。
让我们生成100张卡片:
private CuboidMesh generateCard(String message) {
Text text5 = new Text(message);
text5.setFont(Font.font("Arial", FontWeight.BLACK, FontPosture.REGULAR, 60));
GridPane grid = new GridPane();
grid.setAlignment(Pos.CENTER);
CuboidMesh contentShape = new CuboidMesh(40, 8, 0.01);
PhongMaterial shader = new PhongMaterial();
GridPane.setHalignment(text5, HPos.CENTER);
grid.add(text5, 3, 1);
double w = contentShape.getWidth() * 10; // more resolution
double h = contentShape.getHeight() * 10;
double d = contentShape.getDepth() * 10;
final double W = 2 * d + 2 * w;
final double H = 2 * d + h;
ColumnConstraints col1 = new ColumnConstraints();
col1.setPercentWidth(d * 100 / W);
ColumnConstraints col2 = new ColumnConstraints();
col2.setPercentWidth(w * 100 / W);
ColumnConstraints col3 = new ColumnConstraints();
col3.setPercentWidth(d * 100 / W);
ColumnConstraints col4 = new ColumnConstraints();
col4.setPercentWidth(w * 100 / W);
grid.getColumnConstraints().addAll(col1, col2, col3, col4);
RowConstraints row1 = new RowConstraints();
row1.setPercentHeight(d * 100 / H);
RowConstraints row2 = new RowConstraints();
row2.setPercentHeight(h * 100 / H);
RowConstraints row3 = new RowConstraints();
row3.setPercentHeight(d * 100 / H);
grid.getRowConstraints().addAll(row1, row2, row3);
grid.setPrefSize(W, H);
grid.setBackground(new Background(new BackgroundFill(Color.WHITESMOKE, CornerRadii.EMPTY, Insets.EMPTY)));
new Scene(grid);
WritableImage image = grid.snapshot(null, null);
shader.setDiffuseMap(image);
contentShape.setMaterial(shader);
return contentShape;
}
最后设置subScene:
for (int i = 0; i <= 100; i++) {
CuboidMesh card = generateCard(randomText());
card.setTranslateX(Math.random() * width - width / 2);
card.setTranslateY(Math.random() * height - height / 2);
card.setTranslateZ(Math.random() * 750);
subSceneRoot.getChildren().add(card);
}
并运行它:
并使用相机进行缩放:
文字看起来不再模糊。如果您仍然需要更高的分辨率,则可以创建更大的快照,但这会带来内存成本。
还有一个小问题,因为卡片不透明并覆盖在它们后面(我试图尽可能地降低它们的高度)。