I'm currently working on a capstone project for a Java class and a problem I'm coming across frequently is displaying a variable's value in a JavaFX scene. I need a kickstart to get me moving, my google searches aren't bearing any fruit.
Thanks all :)
You can use a Label. Attach it to your scene and call Label.setText(String text) with the string representation of your variable value. Here's a complete example, using a Label:
import javafx.application.Application;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.control.Label;
import javafx.scene.text.Font;
import javafx.stage.Stage;
public class main3 extends Application {
static Integer variable = 250; // The value will be displayed in the window
#Override public void start(Stage primaryStage) {
Label variableLabel = new Label();
variableLabel.setFont(new Font(30));
variableLabel.setText("" + variable);
variableLabel.setLayoutX(175);
variableLabel.setLayoutY(125);
Group group = new Group(variableLabel);
Scene scene = new Scene(group, 400, 300);
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args){
launch();
}
}
Result
Related
In JavaFX, is there a way to "autofit" elements on a page so they take up the entire thing?
Currently, I'm trying to make the window have two buttons that together take up the entire canvas, but I am not sure how to do that, given that it is possible to stretch the window, etc. I've tried playing around with Button.setPrefSize, but the button size stays the same, it just shows you a window with two outsized buttons, the text of which is not visible.
What I currently have
What I want (but for any window size)
Here's one way (code here but also possible in Scene Builder and FXML):
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.layout.AnchorPane;
import javafx.scene.layout.HBox;
import javafx.scene.layout.Priority;
import javafx.stage.Stage;
public class TestApplication extends Application {
#Override
public void start(Stage stage) throws Exception {
Button button1 = new Button("Button1");
HBox.setHgrow(button1, Priority.SOMETIMES);
button1.setMaxWidth(Double.MAX_VALUE);
button1.setMaxHeight(Double.MAX_VALUE);
Button button2 = new Button("Button2");
HBox.setHgrow(button2, Priority.SOMETIMES);
button2.setMaxWidth(Double.MAX_VALUE);
button2.setMaxHeight(Double.MAX_VALUE);
HBox hBox = new HBox(button1, button2);
AnchorPane.setLeftAnchor(hBox, 0.0);
AnchorPane.setRightAnchor(hBox, 0.0);
AnchorPane.setTopAnchor(hBox, 0.0);
AnchorPane.setBottomAnchor(hBox, 0.0);
AnchorPane rootContainer = new AnchorPane(hBox);
Scene scene = new Scene(rootContainer, 600, 600);
stage.setScene(scene);
stage.show();
}
public static void main(String[] args) {
launch();
}
}
I am new in this forum and also to programming. Furthermore, my English is not the best, but I hope you can understand what I mean and help me out.
I want to program a GUI and using JavaFX and the Gauges from the medusa- library. What I need to do is changing the maxValue and the minValue of the Gauge while the program is running. I can change the values, but the scale of the Gauge does not rearrange the ticks properly. For example, when I create a Gauge from 0 to 10 and then set the maxValue to 100, the scale shows all numbers as a major tick and the scale becomes unreadable. Because I could not find how to fix this, I have tried to delete the original Gauge and create simply a new one.
Here is what I have tried(I deleted the rest of the class, because it has over 800 lines):
package application;
import eu.hansolo.medusa.Gauge;
import eu.hansolo.medusa.Gauge.SkinType;
import eu.hansolo.medusa.GaugeBuilder;
import javafx.beans.property.SimpleObjectProperty;
import javafx.fxml.FXML;
import javafx.scene.control.Button;
import javafx.scene.layout.StackPane;
import javafx.scene.paint.Color;
public class Controller {
#FXML
StackPane stackPane;
private Gauge gauge;
private Button button;
#FXML
private void initialize() {
gauge = GaugeBuilder.create().skinType(SkinType.QUARTER).barBackgroundColor(Color.LIGHTGREY)
.needleColor(Color.RED).decimals(0).valueVisible(true).valueColor(Color.BLACK).title("Stromstärke")
.unit("[mA]").subTitle("Phase 1").minValue(0).maxValue(10).build();
stackPane.getChildren().add(gauge);
}
public void setMaxValueGauge(StackPane pStackPane, Gauge pGauge, int intMinValue, int pMaxValue) {
pStackPane.getChildren().remove(pGauge);
Gauge newGauge = GaugeBuilder.create().skinType(pGauge.getSkinType()).barBackgroundColor(pGauge.getBarColor())
.needleColor(pGauge.getNeedleColor()).decimals(0).valueVisible(true).valueColor(Color.BLACK)
.title(pGauge.getTitle()).unit(pGauge.getUnit()).subTitle(pGauge.getSubTitle()).minValue(intMinValue)
.maxValue(pMaxValue).build();
pGauge = null;
pGauge = newGauge;
pStackPane.getChildren().add(pGauge);
}
#FXML
public void testButton() {
setMaxValueGauge(stackPane, gauge, 0, 30);
}
}
The method testButton() is only for testing. When I call testButton() the first time, it works well, but when I use it twice or more, it seems that the old Gauge is not replaced. Instead the new one stacks on top of the old one.
Can you please help me. I need either to fix the ticks of the scale, when I set a new maxValue, or to properly replace the old Gauge in the Stackpane.
You appear to be doing too much to set the max-value.
Here is an MCVE that changes the maxValue.
import eu.hansolo.medusa.Gauge;
import eu.hansolo.medusa.Gauge.SkinType;
import eu.hansolo.medusa.GaugeBuilder;
import javafx.animation.KeyFrame;
import javafx.animation.Timeline;
import javafx.application.Application;
import javafx.event.ActionEvent;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.layout.VBox;
import javafx.scene.paint.Color;
import javafx.stage.Stage;
import javafx.util.Duration;
/**
*
* #author blj0011
*/
public class MedusaGaugeTest extends Application
{
#Override
public void start(Stage primaryStage)
{
Gauge gauge = GaugeBuilder.create().skinType(SkinType.QUARTER).barBackgroundColor(Color.LIGHTGREY)
.needleColor(Color.RED).decimals(0).valueVisible(true).valueColor(Color.BLACK).title("Stromstärke")
.unit("[mA]").subTitle("Phase 1").minValue(0).maxValue(10).build();;
Timeline timeline = new Timeline(new KeyFrame(Duration.seconds(1), (ActionEvent event) -> {
if (gauge.getValue() <= gauge.getMaxValue()) {
gauge.setValue(gauge.getValue() + 1);
}
}));
timeline.setCycleCount(Timeline.INDEFINITE);
Button btn = new Button();
btn.setText("Start");
btn.setOnAction((ActionEvent event) -> {
timeline.play();
});
Button btn2 = new Button();
btn2.setText("Increase MaxValue");
btn2.setOnAction((ActionEvent event) -> {
gauge.setMaxValue(15);
});
VBox root = new VBox(gauge, new VBox(btn, btn2));
Scene scene = new Scene(root, 300, 250);
primaryStage.setTitle("Hello World!");
primaryStage.setScene(scene);
primaryStage.show();
}
/**
* #param args the command line arguments
*/
public static void main(String[] args)
{
launch(args);
}
}
I have a code. It has errors, I want to know how to fix the error. The error is corresponding to this line: public void start(Stage primaryStage)
The code is shown as follows:
import javafx.application.Application;
import javafx.geometry.Insets;
import javafx.scene.control.Label;
import javafx.scene.control.ContentDisplay;
import javafx.scene.control.ScrollPane;
import javafx.scene.control.TextArea;
import javafx.scene.image.ImageView;
import javafx.scene.layout.BorderPane;
import javafx.scene.Scene;
import javafx.scene.text.Font;
import javafx.stage.Stage;
public class DescriptionPane extends BorderPane{
/** Label for displaying an image and a title */
private Label lblImageTitle = new Label();
/** Text area for displaying text */
private TextArea taDescription = new TextArea();
public DescriptionPane() {
// Center the icon and text and place the text under the icon
lblImageTitle.setContentDisplay(ContentDisplay.TOP);
lblImageTitle.setPrefSize(200, 100);
// Set the font in the label and the text field
lblImageTitle.setFont(new Font("SansSerif", 16));
taDescription.setFont(new Font("Serif", 14));
taDescription.setWrapText(true);
taDescription.setEditable(false);
// Create a scroll pane to hold the text area
ScrollPane scrollPane = new ScrollPane(taDescription);
// Place label and scroll pane in the border pane
setLeft(lblImageTitle);
setCenter(scrollPane);
setPadding(new Insets(5, 5, 5, 5));
}
/** Set the title */
public void setTitle(String title) {
lblImageTitle.setText(title);
}
/** Set the image view */
public void setImageView(ImageView icon) {
lblImageTitle.setGraphic(icon);
}
/** Set the text description */
public void setDescription(String text ) {
taDescription.setText(text);
}
#Override
public void start(Stage primaryStage) {
Scene scene = new Scene(taDescription, 400, 200);
primaryStage.setTitle("RadioButtonDemo");
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args) {
Application.launch(args);
}
}
I also paste the errors here. The errors are shown as follows. Can anyone give me a help to fix the problem. Thank you so much!
Exception in thread "main" java.lang.RuntimeException: Error: class DescriptionPane is not a subclass of javafx.application.Application
at javafx.graphics/javafx.application.Application.launch(Unknown Source)
at DescriptionPane.main(DescriptionPane.java:69)
The code seems to be flawed. The implementation of the start-method and the calls of the setLeft-, setCenter- and setPadding-method exclude each other. The last three methods belong to the BorderPane-class and therfore require this class as base class. The BorderPane-class on the other hand has no start-method which could be overwritten.
Since this is a JavaFX application the class implementing the start-method must be derived from the Application-class as it is already stated in the comments.
Assuming this is a JavaFX-project, the easiest way to fix the problem is: Create a new public class, e.g. Main, which extends the Application class. Copy your start- and main-method inside this class. Inside the copied start-method replace also "Scene scene = new Scene(taDescription, 400, 200)" with "Scene scene = new Scene(new DescriptionPane(), 400, 200)". Remove the start- and main-method from your DescriptionPane-class.
I have a problem using custom Fonts in Javafx 8.
Whenever I try to display a text it gets convertet to upper case A's
my code goes as follows:
package main;
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.canvas.Canvas;
import javafx.scene.canvas.GraphicsContext;
import javafx.scene.layout.Pane;
import javafx.scene.paint.Color;
import javafx.scene.text.Font;
import javafx.stage.Stage;
public class Main extends Application {
private Canvas can;
private GraphicsContext gc;
public static void main(String[] args) {
launch(args);
}
#Override
public void start(Stage stage) throws Exception {
Pane root = new Pane();
Scene scene = new Scene(root, 800, 400);
stage.setTitle("Test");
can = new Canvas(scene.getWidth(), scene.getHeight());
gc = can.getGraphicsContext2D();
root.getChildren().add(can);
stage.setResizable(false);
stage.setScene(scene);
stage.show();
InputStream is = Main.class.getResourceAsStream("Font/SSF4ABUKET.ttf");
Font font = Font.loadFont(is, 30);
gc.setFont(font);
gc.setFill(Color.RED);
gc.fillText("This is a test", 10, 200);
}
}
If I try this Font in a normal Text Editor (e.g. Open Office) it works perfectly fine.
Thanks for your help in advance.
I'm trying to learn JavaFX. To do so I've been attempting to make a text editor that includes multiple line text box support, as well as the possibility of having syntax highlighting down the road.
Currently, the biggest problem I've been facing is that the ScrollPane I've been encapsulating all my FlowPanes in won't resize according to the size of the Pane it's in. I've been researching this problem for about half a week now and simply cannot get the ScrollPane to just fill the window it's in. The code below displays a JavaFX stage that has working keyboard input and the ScrollPane is always the same size no matter what. Thanks to all in advance!
Here's my Main:
import javafx.application.Application;
import javafx.scene.Scene;
import javafx.stage.Stage;
public class Launcher extends Application {
public static void main(String[] args) {
launch(args);
}
#Override
public void start(Stage primaryStage) throws Exception {
primaryStage.setScene(new Scene(new DynamicTextBox(),500,500));
primaryStage.show();
}
}
TextBox class:
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.event.EventHandler;
import javafx.geometry.Bounds;
import javafx.geometry.Orientation;
import javafx.scene.control.ScrollPane;
import javafx.scene.input.KeyEvent;
import javafx.scene.layout.FlowPane;
import javafx.scene.layout.Pane;
import javafx.scene.text.Text;
public class DynamicTextBox extends Pane {
//currentLinePane is made to handle all the direct user inputs
//multiLinePane, while not really used yet will create a new line when the enter key is struck.
private FlowPane currentLinePane, multiLinePane;
private ScrollPane editorScroller;
public DynamicTextBox() {
super();
currentLinePane = new FlowPane(Orientation.HORIZONTAL);
multiLinePane = new FlowPane(Orientation.VERTICAL);
multiLinePane.getChildren().add(currentLinePane);
editorScroller = new ScrollPane(multiLinePane);
editorScroller.setVbarPolicy(ScrollPane.ScrollBarPolicy.AS_NEEDED);
editorScroller.setHbarPolicy(ScrollPane.ScrollBarPolicy.NEVER);
editorScroller.setOnKeyPressed(new EventHandler<KeyEvent>() {
#Override
public void handle(KeyEvent event) {
configureInput(event);
}
});
super.getChildren().add(editorScroller);
editorScroller.requestFocus();
}
private void configureInput(KeyEvent event) {
currentLinePane.getChildren().add(new Text(event.getText()));
}
}
You're using
ScrollPane.ScrollBarPolicy.AS_NEEDED
which, according to the docs at Oracle, "Indicates that a scroll bar should be shown when required." Instead, use
ScrollPane.ScrollBarPolicy.ALWAYS
alternatively, recall these are constants. you can get the height of the parent using boundsInParent: https://docs.oracle.com/javafx/2/api/javafx/scene/Node.html#boundsInParentProperty
alternatively, you can use getParent() to get the parent and then get its height using computeMinWidth() https://docs.oracle.com/javafx/2/api/javafx/scene/Node.html#getParent()