线性渐变的边界计算考虑了父项的边界,而不是应用它的节点 [英] Linear gradient's bounds computation takes parent's bounds in account, not the node on which it is applied on

查看:162
本文介绍了线性渐变的边界计算考虑了父项的边界,而不是应用它的节点的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想在一条直线上放置一个线性渐变(宽度方向,即横跨它的笔划宽度)。此行是Group节点的子节点。当我在线上应用线性渐变时,使用组的边界而不是线条边界计算颜色停止。
在我的下面的代码中,线性渐变将在添加长度方式时正确显示,即向下,但不是在宽度方面添加时,即向右。
有谁能告诉我这可以解决什么问题?
这是SSCCE

I want to put a linear gradient on a line(width wise ie across it's stroke width). This line is a child of a Group node. When I apply linear gradient on line, the color stops are calculated using Group's bounds not the lines bounds. In my code below, linear gradient will show up properly when added length-wise ie "to bottom", but not when added width wise, ie "to right". Can anyone tell me what can be work around for this? Here is the SSCCE

import javafx.application.Application;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.shape.Line;
import javafx.stage.Stage;

public class Test extends Application {

@Override
public void start(Stage primaryStage) throws Exception {
    Group group = new Group();
    primaryStage.setScene(new Scene(group, 200, 350));

    Line line = new Line(100, 50, 100, 300);
    group.getChildren().add(line);
    line.setStyle("-fx-stroke-width:3em; -fx-stroke:linear-gradient(to right, red, green);");
    //line.setStyle("-fx-stroke-width:3em; -fx-stroke:linear-gradient(to bottom, red, green);");

    primaryStage.show();
}

public static void main(String[] args) {
    launch();
}

}


推荐答案

小组界限的假设是不正确的。事实上,它正在走线。这就是问题所在。

The assumption it takes the group's bounds is not correct. In fact, it's taking the line's bound. And here is the problem.

如果你去 com.sun.prism.j2d.J2DPrismGraphics 你会看到对于带有渐变的形状,这就是 fill()的完成方式:

If you go to com.sun.prism.j2d.J2DPrismGraphics you'll see that for a shape with a gradient, this is how fill() is done:

void fill(java.awt.Shape shape) {
    if (paintWasProportional) {
        if (nodeBounds != null) {
            g2d.setPaint(toJ2DPaint(paint, nodeBounds));
        } else {
            g2d.setPaint(toJ2DPaint(paint, shape.getBounds2D()));
        }
    }
    g2d.fill(shape);
}

paintWasProportional 检查给了我一个提示,以另一种观点来解决你的问题。

The paintWasProportional check gave me a hint to approach your problem with another perspective.

让我们首先使用 LinearGradient 对象,按代码而不是使用CSS。然后这将是你的起点:

Let's start by using a LinearGradient object, by code instead of using CSS. Then this will be your starting point:

@Override
public void start(Stage primaryStage) throws Exception {
    Group group = new Group();
    primaryStage.setScene(new Scene(group, 200, 350));

    Line line = new Line(100, 50, 100, 300);
    LinearGradient linearGradient = new LinearGradient(0d, 0d, 0d, 1d, true,
      CycleMethod.NO_CYCLE, new Stop(0,Color.RED),new Stop(1,Color.GREEN));
line.setStrokeWidth(36); // 3em
    line.setStroke(linearGradient);
    group.getChildren().add(line);
    primaryStage.show();
}

预期结果(黑线仅供参考):

With the expected result (the black line is just for reference):

现在,为了使渐变到达,让我们使用非proporcional 改变我们创建渐变的方式:

Now, to get the gradient to right, let's change the way we create the gradient, using a non proporcional one:

LinearGradient linearGradient = new LinearGradient(0d, 50d, 0d, 300d,
       false, CycleMethod.REFLECT,new Stop(0,Color.RED), new Stop(1,Color.GREEN));   

这将产生相同的结果。

如果你想改变方向,这就是你需要的:

And if you want to change the direction, this is what you need:

LinearGradient linearGradient = new LinearGradient(100-18d, 0d, 100+18d, 0d,
 false, CycleMethod.REFLECT,new Stop(0,Color.RED), new Stop(1,Color.GREEN));

结果如下:

请注意,您现在可以尝试完成此操作也是通过CSS。

Note you could try now to get this done also by CSS.

这篇关于线性渐变的边界计算考虑了父项的边界,而不是应用它的节点的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆