如何在JavaFX中绘制Lower-Etched-Border
类似于Swing标签中的内容?
答案 0 :(得分:3)
我为JavaFX研究了Lowered-Etched-Border
,但我没有找到任何有效的文档。我还测试了InnerShadow
和其他效果,但那些效果并不合适。所以我用这种边框样式创建了LEBLabel
(Label
的子类)。
public class LoweredEtchedBorderLabelDemo extends Application {
@Override
public void start(Stage primaryStage) {
LEBLabel text = new LEBLabel("Testing", 200, 30);
StackPane root = new StackPane();
root.getChildren().add(text);
root.setStyle("-fx-background-color:lightgrey");
Scene scene = new Scene(root, 300, 250);
primaryStage.setTitle("Lowered-Etched-Border Demo");
primaryStage.setScene(scene);
primaryStage.show();
}
//Lowered Etched Borderd Label
private class LEBLabel extends Label {
private HBox[] borders = new HBox[3];
private String border_styles[] = {"-fx-border-width:0 1 1 0; -fx-border-color: white",
"-fx-border-width:1; -fx-border-color:grey",
"-fx-border-width:1 0 0 1; -fx-border-color:white"};
public LEBLabel(String text, double width, double height) {
super(text);
for(int i = 0; i < borders.length; i++) {
borders[i] = new HBox();
borders[i].setStyle(border_styles[i]);
//decrement of border-size for inner-border, prevents from the overlapping of border
borders[i].setMaxSize(width - (1.5 *i), height - (1.5 * i));
borders[i].setMinSize(width - (1.5 *i), height - (1.5 * i));
borders[i].setSpacing(0);
}
this.setContentDisplay(ContentDisplay.CENTER);
this.borders[1].getChildren().add(borders[2]);
this.borders[0].getChildren().add(borders[1]);
this.setGraphic(borders[0]);
}
}
public static void main(String[] args) {
launch(args);
}
}
注意:此
LEBLabel
仅在中心一侧显示文字,因此忽略了Text-Alignment Properties
。
答案 1 :(得分:2)
基于Region扩展名和外部CSS文件的示例。
如果需要,此实现允许边框包含任意可调整大小的内容(包括父布局窗格)。例如,您可以在BorderPane中放置一个包含StackPane内容的内容,并使用StackPane的“可选布局约束”来对齐内容并为BorderPane中的内容定义边距(有关示例,请参阅链接的StackPane javadoc)如何实现这一点)。
此外,边框本身的样式可以从外部CSS文件中自定义,因此应该可以相对轻松地复制standard Swing borders(以及其他边框样式)中的任何一种。
边界pane.css
.border-pane {
-fx-border-base: gray;
-fx-border-shadow: white;
-fx-light-border: derive(-fx-border-base, 25%);
-fx-border-color: -fx-light-border -fx-border-base -fx-border-base -fx-light-border;
-fx-border-insets: 0 1 1 0;
-fx-background-color: -fx-border-shadow, -fx-background;
-fx-background-insets: 1 0 0 1, 2;
-fx-padding: 2;
}
LoweredEtchedBorderLabelBackgroundDemo.java
import javafx.application.Application;
import javafx.geometry.*;
import javafx.scene.Node;
import javafx.scene.Scene;
import javafx.scene.control.Label;
import javafx.scene.layout.*;
import javafx.scene.shape.Rectangle;
import javafx.stage.Stage;
public class LoweredEtchedBorderDemo extends Application {
@Override
public void start(Stage stage) {
Label label = new Label("Testing");
label.setPadding(new Insets(10));
// uncomment to see the area that the content node is taking up within the border.
//label.setStyle("-fx-background-color: palegreen;");
BorderPane borderPane = new BorderPane(new StackPane(label));
// uncomment these two lines if you would like the border to resize to fit available space.
borderPane.setMinSize(Region.USE_COMPUTED_SIZE, Region.USE_COMPUTED_SIZE);
borderPane.setMaxSize(Region.USE_COMPUTED_SIZE, Region.USE_COMPUTED_SIZE);
VBox layout = new VBox(borderPane);
layout.setPadding(new Insets( 10));
layout.setStyle("-fx-base: lightgrey;");
VBox.setVgrow(borderPane, Priority.ALWAYS);
Scene scene = new Scene(layout);
stage.setScene(scene);
stage.show();
}
private class BorderPane extends Region {
// clip the bordered content within the bordered area.
Rectangle clipRect = new Rectangle(getWidth(), getHeight());
public BorderPane(Node content) {
super();
getChildren().add(content);
getStylesheets().add(getClass().getResource(
"border-pane.css"
).toExternalForm());
getStyleClass().add("border-pane");
// by default size the border to the preferred size of the content.
setMinSize(Region.USE_PREF_SIZE, Region.USE_PREF_SIZE);
setMaxSize(Region.USE_PREF_SIZE, Region.USE_PREF_SIZE);
content.setClip(clipRect);
}
@Override protected void layoutChildren() {
final double width = getWidth();
double height = getHeight();
double top = getInsets().getTop();
double right = getInsets().getRight();
double left = getInsets().getLeft();
double bottom = getInsets().getBottom();
double contentWidth = width - left - right;
double contentHeight = height - top - bottom;
Node child = getManagedChildren().get(0);
layoutInArea(child, left, top,
contentWidth, contentHeight,
0, null,
HPos.LEFT,
VPos.TOP);
clipRect.setWidth(contentWidth);
clipRect.setHeight(contentHeight);
}
}
public static void main(String[] args) {
launch(args);
}
}
相关问题