I am trying to add images in the GUI I ve created using JavaFx. My JavaFx is the following:
StackPane layoutTSignUp = new StackPane();
layoutTSignUp.setStyle("-fx-background-color: #FFFF;");
How can I instead of having a color I can add images. Furthermore how can I achieve the same in my buttons:
teacherButton.setStyle("-fx-font: 45 Arial; -fx-base: #FFFF");
Programatically
For your StackPane you can use BackgroundImage class:
BackgroundImage backgroundImage= new BackgroundImage(new Image(getClass().getResource("thinking-man.jpg").toExternalForm(),32,32,false,true),
BackgroundRepeat.NO_REPEAT, BackgroundRepeat.NO_REPEAT, BackgroundPosition.DEFAULT,
BackgroundSize.DEFAULT);
stackPane.setBackground(new Background(backgroundImage));
For buttons: Buttons have a graphic property:
button.setGraphic(new ImageView(new Image(getClass().getResource("thinking-man.jpg").toExternalForm())));
Using CSS
If you would prefer to use stylesheets to set background images you can use:
-fx-background-image, -fx-background-repeat, -fx-background-position and -fx-background-size.
For details you can read the JavaFX CSS reference for Region class.
Using the same example with StackPane:
stackPane.getStylesheets().add(getClass().getResource("application.css").toExternalForm());
stackPane.getStyleClass().add("stackpane-with-background");
In application.css:
.stackpane-with-background{
-fx-background-image: url("thinking-man.jpg");
-fx-background-repeat: stretch;
-fx-background-size: 900 506;
-fx-background-position: center center;
-fx-effect: dropshadow(three-pass-box, black, 30, 0.5, 0, 0);
}
Hope this helps.
Related
I'm making some function in my application with JavaFX and Scene Builder
I can pick a color when clicking on JFoenix Color Picker and then this color applies to my label background
I made JFOenix Color Picker look like an icon. I had changed the standart appearence of Color Picker to my image
Problem #1:
Color Picker is totally filled with white color when I lanch a program first time and then it become looks like my icon when I move the mouse over it.
Problem #2:When I click my icon with Color Picker ripple effect works, but I don't need any ripple effect or animation when I click on Color Picker
Problem #3: JFoenix Color Picker also applies chosen color to it's own background and it's appearence become to icon image again when I move mouse over it again
Problem #4:
When Color Picker is placed in Stack Pane The Color Picker dialog window appears only when I click on left side of the icon, it looks like right side of Color Picker icon is disabled, but I need Color Picker dialog window to be appeared when I click to any part of Color Picker icon
I was searching into CSS files of JFoniex Color Picker, but there is no any documentation how to customize properly Color Picker in CSS.
Please, help me as much as you can
*I had an idea to use toggle button(I know how to customize it to my own needs) and place Color Picker backward this toggle button and make opacity 0. But I don't know how to make Color Picker dialog window open When I click on toggle button. Any ideas?
I use method that is called when I click Color Picker to fill label's background with color.
Controller class:
#FXML private Label category1;
#FXML private JFXColorPicker colorPickerCategory;
#FXML
void changeCategoryColor(ActionEvent event) {
Color selectedColor = colorPickerCategory.getValue();
category1.setBackground(new Background(new BackgroundFill(Paint.valueOf(selectedColor.toString()), CornerRadii.EMPTY, Insets.EMPTY)));
}
CSS:
.jfx-color-picker .color-box {
-fx-background-image: url("resources/palette.png");
-fx-background-color: transparent;
-fx-background-repeat: no-repeat;
-fx-background-position: center;
-fx-background-size: contain;
}
.jfx-color-picker:armed,
.jfx-color-picker:hover,
.jfx-color-picker:focused,
.jfx-color-picker {
-fx-background-color: transparent, transparent, transparent, transparent;
-fx-background-insets: 0px;
}
.color-picker > .color-picker-label > .picker-color > .picker-color-rect {
-fx-stroke: null;
-fx-fill : null;
}
.color-picker {
-fx-background-color: transparent;
-fx-color-label-visible: false;
}
.color-picker .color-picker-label .picker-color {
-fx-alignment: center;
}
.color-picker .color-picker-label .text {
-fx-fill: transparent;
}
.jfx-color-picker:default{
-fx-background-color: transparent;
}
Video
Scene Builder Screen
The skin-class of the JFXColorPicker contains a pane and a label which have the style classes color-label and color-box, respectively. The label is contained in the pane.
The following css displays the icon without background (=selected color) and without text (=hex value of selected color)
.jfx-color-picker {
-fx-focus-traversable: false;
-fx-color-label-visible: false;
}
.jfx-color-picker .color-label {
-fx-background-image: url("resources/palette.png");
-fx-background-color: transparent;
-fx-background-repeat: no-repeat;
-fx-background-position: center;
-fx-background-size: contain;
}
.jfx-color-picker .color-box {
visibility: hidden;
}
The first part disables the text. The middle part is responsible for the display of the icon. The last part disables the background.
With that css the observed problems don't occur:
No white color, no hidden icon
Ripple-effect can be disabled optionally (programmatically)
Chosen color optionally not displayed in the background
No problems in StackPanes
My testcase consists of a BorderPane containing a StackPane in the center. The StackPane contains the JFXColorPicker and 3 buttons. The right part of the BorderPane contains a pane whose color is controlled by the color picker.
The following figures show the FXML in Scenebuilder (Fig. 1), the application immediately after the start (Fig. 2), the application after the color picker is clicked (Fig. 3) and the application after a color change (Fig. 4):
Fig. 1:
Fig. 2:
Fig. 3:
Fig. 4:
The following css displays the icon with background (=selected color) and with ripple but without text (=hex value of selected color)
.jfx-color-picker {
-fx-focus-traversable: false;
-fx-color-label-visible: false;
}
.jfx-color-picker .color-label {
-fx-background-image: url("resources/palette.png");
-fx-background-color: transparent;
-fx-background-repeat: no-repeat;
-fx-background-position: center;
-fx-background-size: contain;
}
The following figure shows the application after a color change.
Fig. 5:
In order to display the icon with background (=selected color), but without ripple and without text (=hex value of selected color),
the following method has to be added to the controller:
public void disableRipple() {
JFXRippler rippler = (JFXRippler) jfxColorPicker.lookup("JFXRippler");
rippler.setDisable(true);
}
where jfxColorPicker denotes the color picker in the FXML.
The method has to be called in the main-method after the execution of the show-method:
FXMLLoader loader = new FXMLLoader(getClass().getResource("<path to FXML>"));
...
primaryStage.show();
...
Controller controller = loader.getController();
controller.disableRipple();
The skin-class of the JFXColorPicker is located at JFoenix-master\jfoenix\src\main\java\com\jfoenix\skins\JFXColorPickerSkin.java.
Here the interaction of the controls can be studied.
EDIT: #Topaco wrote solution above, but I solved my problems in other way: I made toggle button and it's style to look like an icon. I placed JFOenix Color Picker above that toggle button and made Color PIcker's opacity to 0. It looks like I click on toggle button with icon, but I actually click on Color Picker because it is placed ABOVE toggle button.
JFoenix Color Picker is not wrapped into any Pane. It is placed just in Grid Pane as Stack Pane of toggle buttons. Color Picker is broght forward. Toggle Button is placed backward
I tried giving the pane a background image through SceneBuilder CSS but that simply didn't work.
File NavImg = new File("Navigation.png");
Image NavigationImage = new Image(NavImg.toURI().toURL().toExternalForm());
BackgroundImage NavigationBack = new BackgroundImage(NavigationImage, BackgroundRepeat.NO_REPEAT, BackgroundRepeat.NO_REPEAT, BackgroundPosition.CENTER, BackgroundSize.DEFAULT);
Navigation.setBackground(new Background(NavigationBack));
Now I tried this code but it doesn't work either, what do I do?
Navigation is correctly selected in the Controller class. It being the fx:id of the Pane I want to change the background image.
#FXML
private Pane Navigation;
Having a Node for example VBox I am trying to add a border and there are 2 ways I can think of - using css or using new Border () etc..
How can I remove part of the border ? i.e remove the bottom part of the border
You can specify different styles for the borders on different sides
Using Border
#Override
public void start(Stage primaryStage) {
Region root = new Region();
root.setBorder(new Border(new BorderStroke(Color.RED, Color.RED, Color.RED, Color.RED,
BorderStrokeStyle.SOLID, BorderStrokeStyle.SOLID, BorderStrokeStyle.NONE, BorderStrokeStyle.SOLID,
CornerRadii.EMPTY, new BorderWidths(5), Insets.EMPTY)));
Scene scene = new Scene(root, 300, 300);
primaryStage.setScene(scene);
primaryStage.show();
}
Using inline css
root.setStyle("-fx-border-style: solid solid none solid; -fx-border-width: 5; -fx-border-color: red;");
Using a css stylesheet
.root { /* modify the selector according to your needs */
-fx-border-style: solid solid none solid;
-fx-border-width: 5;
-fx-border-color: red;
}
none doesnt work on javafx 13. I tried changing it to hidden and it works.
.root { /* modify the selector according to your needs */
-fx-border-style: solid solid hidden solid;
-fx-border-width: 5;
-fx-border-color: red;
}
Setting border-width to 0 worked (JavaFX 17): Example:
#header
{
-fx-border-width: 0 0 2px 0;
-fx-border-color: black;
-fx-border-style: solid;
}
Here you can get border only at bottom - order: Top, right, bottom, left.
I'm making a GUI in JavaFX, and I've stripped the window of the decorations that Windows did and I have made my own controls for close, minimize, and maximize.
The controls work great, but it seems that when I press one of them, it's neighbors change vertical size, increasing it by one or two pixels, as you can see in this image.
Why is this happening?
Im also attaching the code I have so far in the start() method.
public void start(Stage primaryStage) throws Exception {
window = primaryStage;
window.setTitle("Menu Example");
MenuBar file = new MenuBar();
file.setId("file");
Menu fileMenu = new Menu("File");
fileMenu.getItems().addAll(
new MenuItem("New File..."),
new MenuItem("Open file..."),
new MenuItem("Save file"));
fileMenu.setId("#fileMenu");
Menu editMenu = new Menu("Edit");
editMenu.getItems().addAll(
new MenuItem("Undo"),
new MenuItem("Redo"),
new MenuItem("Cut"),
new MenuItem("Copy"),
new MenuItem("Paste")
);
Button closeButton = new Button("X");
closeButton.setId("closeButton");
closeButton.setOnAction(event -> {
window.close();
});
Button minimizeButton = new Button("_");
minimizeButton.setId("minimizeButton");
minimizeButton.setOnAction(event -> {
window.setIconified(true);
});
Button maximizeButton = new Button("?");
maximizeButton.setId("maximizeButton");
maximizeButton.setOnAction(event -> {
if(!window.isMaximized())
window.setMaximized(true);
else
window.setMaximized(false);
});
file.getMenus().addAll(
fileMenu,
editMenu
);
HBox.setHgrow(file, Priority.ALWAYS);
HBox.setHgrow(closeButton, Priority.NEVER);
HBox.setHgrow(minimizeButton, Priority.NEVER);
HBox.setHgrow(maximizeButton, Priority.NEVER);
VBox.setVgrow(closeButton, Priority.NEVER);
hBox = new HBox();
buttonBox = new HBox();
buttonBox.getChildren().addAll(minimizeButton, maximizeButton, closeButton);
hBox.getChildren().addAll(file, buttonBox);
layout = new BorderPane();
layout.setTop(hBox);
Scene scene = new Scene(layout, 400, 400);
scene.getStylesheets().add("Viper.css");
window.setScene(scene);
// window.setMaximized(true);
window.initStyle(StageStyle.UNDECORATED);
window.show();
}
This is my stylesheet:
.root{
-fx-background-color: #2D2E32;
-fx-font-size: 11px;
}
#file{
-fx-background-color: #3E3F43;
}
#file .label{
-fx-text-fill: #EAEAEA;
}
.context-menu{
-fx-background-color: #3E3F43;
}
#closeButton, #minimizeButton, #maximizeButton{
-fx-background-radius: 0;
-fx-background-color: #3E3F43;
-fx-text-fill: #ffffff;
-fx-font-weight: bold;
}
#closeButton:hover{
-fx-background-color: #E46458;
}
#minimizeButton:hover{
-fx-background-color: #80B1E0;
}
#maximizeButton:hover{
-fx-background-color: #80E089;
}
Based on your CSS stylesheet, adding the following selectors will solve problem :
#closeButton:armed, #closeButton:focused,
#minimizeButton:armed, #minimizeButton:focused,
#maximizeButton:armed, #maximizeButton:focused {
-fx-background-insets: 0 0 -1 0, 0, 1, 2;
}
Reason:
The default styleheet modena.css defines the background insets of a Button like -fx-background-insets: 0 0 -1 0, 0, 1, 2;, but if the Button is in one of the pseudo-states of focused or armed, the insets are modified as -fx-background-insets: -0.2, 1, 2, -1.4, 2.6;.
So actually not the vertical size of the neighbours will be increased but the "vertical size" of the armed or focused Button will be decreased.
This is what the selectors above prevent.
Note: If you create a new CSS class like
.windowbutton:armed, .windowbutton:focused {
-fx-background-insets: 0 0 -1 0, 0, 1, 2;
}
then in the code you assign this class to each Button:
closeButton.getStyleClass().add("windowbutton"); // Similar to other buttons
the CSS structure will be a little but more clean.
I'm trying to learn JavaFX 2, but I've been stumbling a lot trying to style my application. I've found this document which tries to document controls and the css properties that apply to them. I can't tell if it's incomplete, if I should be using some unknown selectors or JavaFX's CSS support just isn't powerful enough for my needs.
Here are a couple of examples:
How would I change the background color for the area behind a TabPane without coloring every other child component (is there a selector for that, or perhaps a property?)
How would I change the color of non-selected tabs?
Have you tried something like this?
This uses an ID selector as shown in the "Skinning JavaFX Applications with CSS" document. You could also leave off the "#MyTabPane" selector and have it apply to all TabPane's. (It looks like the .tab and .tab-content-area selectors are not discussed in the reference guide. I went to the "caspian.css" file contained in jfxrt.jar file to find them.)
TabExample.css
#MyTabPane .tab {
-fx-background-color: blue;
}
#MyTabPane .tab:selected {
-fx-background-color: red;
}
#MyTabPane .tab-content-area {
-fx-background-color: cyan;
}
#MyTabPane .tab *.tab-label {
-fx-text-fill: white;
}
TabPaneEx.java
#Override
public void start(Stage primaryStage) {
primaryStage.setTitle("Hello World");
StackPane root = new StackPane();
TabPane pane = new TabPane();
pane.setId(("MyTabPane"));
Tab tab1 = new Tab("ONE");
Tab tab2 = new Tab("TWO");
Tab tab3 = new Tab("THREE");
pane.getTabs().addAll(tab1,tab2,tab3);
Scene scene = new Scene(root, 300, 250);
root.getChildren().add(pane);
scene.getStylesheets().add(
this.getClass().getClassLoader().getResource("tabpaneex/TabExample.css").toString());
primaryStage.setScene(scene);
primaryStage.show();
}
JavaFX CSS Reference Guide
Skinning JavaFX Applications with CSS