如何创建背景网格

时间:2015-03-05 05:11:29

标签: css background javafx

我想创建一个网格作为我的JavaFX应用程序的背景。我目前的解决方案是在画布上绘制一个矩形,从中创建一个图像模式并将其设置为填充。

问题:有没有更好的方法来解决这个问题,最好是通过CSS?

当前版本:

public class BackgroundGrid extends Application {

    double gridSize = 20;

    @Override
    public void start(Stage primaryStage) {

        Scene scene = new Scene(new Group(), 800, 600);
        primaryStage.setScene(scene);
        primaryStage.show();

        scene.setFill(createGridPattern());

    }

    public ImagePattern createGridPattern() {

        double w = gridSize;
        double h = gridSize;

        Canvas canvas = new Canvas(w, h);
        GraphicsContext gc = canvas.getGraphicsContext2D();

        gc.setStroke(Color.BLACK);
        gc.setFill(Color.LIGHTGRAY.deriveColor(1, 1, 1, 0.2));
        gc.fillRect(0, 0, w, h);
        gc.strokeRect(0, 0, w, h);

        Image image = canvas.snapshot(new SnapshotParameters(), null);
        ImagePattern pattern = new ImagePattern(image, 0, 0, w, h, false);

        return pattern;

    }

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

enter image description here

非常感谢!

编辑:为了获得清晰的网格线,只需使用

gc.strokeRect(0.5, 0.5, w, h);

我认为在CSS中不可行,不是吗?

enter image description here

3 个答案:

答案 0 :(得分:4)

您也可以使用CSS。这就是你所需要的:

.root {
    -fx-background-color: #D3D3D333,
        linear-gradient(from 0.5px 0px to 10.5px 0px, repeat, black 5%, transparent 5%),
        linear-gradient(from 0px 0.5px to 0px 10.5px, repeat, black 5%, transparent 5%);
}

gradient

当从0px设置为10px时,0.5px偏移解决了一些错误行为,并且某些行使用两个像素而不是一个像素进行渲染:

wrong gradient

答案 1 :(得分:1)

以下是从旧Oracle forum post转载的答案。

基于GridPane的方法

一些方法(基于GridPane布局):

  1. 单个单元格的边框样式(并确保它们填充 他们的整个网格位置)或
  2. 风格整体的背景 网格留下填充整个网格的单元格之间的间隙 如下所示的位置或
  3. 用行添加新的网格节点然后 设置添加的线条。
  4. 我为下面的代码选择了方法2(为网格背景设计样式)。该示例使用内联CSS样式(因为我很懒),但它可以使用外部CSS样式表来设置网格样式(并且更好)。

    grid

    import javafx.application.Application;
    import javafx.geometry.HPos;
    import javafx.geometry.VPos;
    import javafx.scene.*;
    import javafx.scene.control.*;
    import javafx.scene.layout.*;
    import javafx.stage.Stage;
    
    public class GridPaneStyle extends Application {
        @Override
        public void start(final Stage stage) {
            // create a grid with some sample data.
            GridPane grid = new GridPane();
            grid.addRow(0, new Label("1"), new Label("2"), new Label("3"));
            grid.addRow(1, new Label("A"), new Label("B"), new Label("C"));
    
            // make all of the Controls and Panes inside the grid fill their grid cell, 
            // align them in the center and give them a filled background.
            // you could also place each of them in their own centered StackPane with 
            // a styled background to achieve the same effect.
            for (Node n : grid.getChildren()) {
                if (n instanceof Control) {
                    Control control = (Control) n;
                    control.setMaxSize(Double.MAX_VALUE, Double.MAX_VALUE);
                    control.setStyle("-fx-background-color: cornsilk; -fx-alignment: center;");
                }
                if (n instanceof Pane) {
                    Pane pane = (Pane) n;
                    pane.setMaxSize(Double.MAX_VALUE, Double.MAX_VALUE);
                    pane.setStyle("-fx-background-color: cornsilk; -fx-alignment: center;");
                }
            }
    
            // style the grid so that it has a background and gaps around the grid and between the 
            // grid cells so that the background will show through as grid lines.
            grid.setStyle("-fx-background-color: palegreen; -fx-padding: 2; -fx-hgap: 2; -fx-vgap: 2;");
            // turn layout pixel snapping off on the grid so that grid lines will be an even width.
            grid.setSnapToPixel(false);
    
            // set some constraints so that the grid will fill the available area.
            ColumnConstraints oneThird = new ColumnConstraints();
            oneThird.setPercentWidth(100 / 3.0);
            oneThird.setHalignment(HPos.CENTER);
            grid.getColumnConstraints().addAll(oneThird, oneThird, oneThird);
            RowConstraints oneHalf = new RowConstraints();
            oneHalf.setPercentHeight(100 / 2.0);
            oneHalf.setValignment(VPos.CENTER);
            grid.getRowConstraints().addAll(oneHalf, oneHalf);
    
            // layout the scene in a stackpane with some padding so that the grid is centered 
            // and it is easy to see the outer grid lines.
            StackPane layout = new StackPane();
            layout.setStyle("-fx-background-color: whitesmoke; -fx-padding: 10;");
            layout.getChildren().addAll(grid);
            stage.setScene(new Scene(layout, 600, 400));
            stage.show();
    
            // can be uncommented to show the grid lines for debugging purposes, but not particularly useful for styling purposes.
            //grid.setGridLinesVisible(true);
        }
    
        public static void main(String[] args) {
            launch();
        }
    }
    

    基于替代画布的方法

    另见FXExperience博客文章Resizable Grid using Canvas

答案 2 :(得分:0)

获得真正清晰的网格线的建议并不适用于所有系统。在Retina显示器上,您必须使用0.5的线宽,然后使用整数线坐标的0.25的偏移量。因此,在实践中,您必须确定应用程序正在运行的系统,然后使用不同的线宽和偏移量。